2017-08-23 69 views
2

所以即時通訊旨在使您繪製一個表面多邊形的系統,它基本上使多邊形周圍的虛線邊框。問題是我想這個邊框是一個設置的大小,這意味着每個短劃線應該是圍繞多邊形的一個設置大小。此外,我正試圖弄清楚如何使它如此,如果你增加了一個表面多邊形的邊界大小,它不會向外擴展,只有向內,這種方式尺寸是傾斜的。Java美國國家航空航天局與內部邊界的多邊形

長話短說我開始基本上計算自己的虛線邊框,並手工繪製每個短劃線。與此相關的問題出現在它們相遇的角度,並在短劃線延伸到多邊形之外時切斷多餘的長度。附圖顯示了我到目前爲止以及它的本質應該是什麼樣子。我也想按照圖片的方式保持多邊形上的正常邊框,但這不是強制性的。

我想我很驚訝這是很難做到這一點在美國國家航空航天局世界風,其中directX是約20行。這讓我覺得我正在走錯方向。

就像一個筆記。我研究了使用模板緩衝區,但這證明幾乎是浪費時間來開展工作並在世界範圍內正確運行。我不認爲我有足夠的把握來正確地做到這一點。

P.S.我已經開始使用的所有東西都沒有設置。我只需要最終的結果是正確的。謝謝您的幫助。

What I have so far with drawing each polygon of the border.

TLDR:需要一個與設置寬度的內部邊界繪製多邊形。

+1

你當然可以這樣做是幾何着色器,吐出兩個三角形本身和粗線邊框。然而,這是相當先進的。所有線圖庫都必須考慮連接時的斜角,圓角,斜角等。這是一個不平凡的主題。可能太多以至於無法回答。 – Robinson

+0

你能否指出我在哪裏可以找到關於幾何着色器的更多信息?我很驚訝,使一個簡單的邊界是如此艱難。 – crychair

+0

那裏有很多東西。谷歌的「幾何着色器+ opengl」,也許「幾何着色器+粗線+ opengl」。 – Robinson

回答

2

我建議先繪製(綠色)區域,然後再繪製一條虛線(白色)線條。
繪製直線時,可以使用Geometry Shader將線段轉換爲四邊形(包含4個點的三角形條紋),這些四邊形包圍在給定線條粗細中由實線填充的薄區域。片段着色器finnaly必須衝破線(切割線的部分)。最後,Fragment Shader必須產生虛線(切出部分)。

畫線,所述Primitive類型GL_LINE_STRIP_ADJACENCY必須使用(見GLSL Tutorial - Primitive Assembly),因爲每個線段具有知道其前身和後繼者,來計算在拐角處的角度平分線。如果多邊形是由一系列線條定義的,那麼可以很容易地完成。列表的最後一點必須添加在點列表的開始位置,列表的第一個點必須添加在點列表的末尾。

例如如果一個多邊形組成的點的Çd,那麼爲GL_LINE_STRIP_ADJACENCY點的清單將是dÇDA。這會得到下列4線段:

  • ,與前身d和後繼Ç
  • Ç,與前身和繼任者D
  • Cd,與前身和後繼
  • d,與前身Ç和後繼

Vertex Shader只是必須穿過多邊形的角點:

#version 400 

layout (location = 0) in vec3 inPos; 

out TVertexData 
{ 
    out vec3 pos; 
} outData; 

void main() 
{ 
    outData.pos = inPos; 
    gl_Position = vec4(inPos, 1.0); 
} 

Geometry Shader計算每條線段末端起始端的角平分線,並根據線的粗細生成一個四邊形。
由於片段着色器仍然需要生成虛線,因此會計算線的長度和線的中心並將其傳遞給片段着色器。

#version 400 

layout(lines_adjacency) in; 
layout(triangle_strip, max_vertices = 4) out; 

in TVertexData 
{ 
    vec3 pos; 
} inData[]; 

out TGeometryData 
{ 
    vec3 linePos; 
    vec3 lineMidPoint; 
    float lineLen; 
} outData; 

uniform float u_thickness; 

void main() 
{ 
    if (gl_InvocationID != 0) 
     return; 

    vec3 pos0 = inData[1].pos; 
    vec3 pos1 = inData[2].pos; 
    vec3 dirPred = normalize(inData[0].pos - pos0); 
    vec3 dirSucc = normalize(inData[3].pos - pos1); 
    vec3 dirLine = normalize(pos1 - pos0); 
    vec3 dirNorm = normalize(dirPred - dirLine * dot(dirLine, dirPred)); 
    dirSucc = faceforward(dirSucc, -dirNorm, dirSucc); 

    vec3 dir0 = abs(dot(dirPred, dirLine)) > 0.99 ? dirNorm : normalize(dirPred + dirLine); 
    vec3 dir1 = abs(dot(dirSucc, dirLine)) > 0.99 ? dirNorm : normalize(dirSucc - dirLine); 

    vec3 pos01 = pos0 + dir0 * u_thickness/dot(dir0, dirNorm); 
    vec3 pos11 = pos1 + dir1 * u_thickness/dot(dir1, dirNorm); 

    vec3 lineMidPoint0 = (pos0 + pos1) * 0.5; 
    vec3 lineMidPoint1 = lineMidPoint0 + dirNorm * u_thickness; 

    outData.lineLen = length(pos1 - pos0); 

    outData.lineMidPoint = lineMidPoint0; 
    outData.linePos = pos0; 
    gl_Position = vec4(pos0, 1.0); EmitVertex(); 
    outData.linePos = pos1; 
    gl_Position = vec4(pos1, 1.0); EmitVertex(); 

    outData. lineMidPoint = lineMidPoint1; 
    outData.linePos = pos01; 
    gl_Position = vec4(pos01, 1.0); EmitVertex(); 
    outData.linePos = pos11; 
    gl_Position = vec4(pos11, 1.0); EmitVertex(); 

    EndPrimitive(); 
} 

最後,Fragment Shader通過丟棄間隙中的碎片來產生虛線。

#version 400 

in TGeometryData 
{ 
    vec3 linePos; 
    vec3 lineMidPoint; 
    float lineLen; 
} inData; 

out vec4 fragColor; 

uniform float u_dashLen; 
uniform float u_gapLen; 
uniform vec4 u_color; 

void main() 
{ 
    float midDist = length(inData.linePos - inData.lineMidPoint); 
    float modDist = mod(midDist + u_dashLen * 0.5, u_dashLen + u_gapLen); 
    float onDash = max(step(modDist, u_dashLen), 
          step(inData.lineLen * 0.5 - u_dashLen, midDist)); 
    if (onDash < 0.5) 
     discard; 
    fragColor  = u_color * onDash; 
} 

注意,這Fragment Shader使用discard關鍵字,丟棄片段,它是在虛線的間隙。如果使用Blending,則可以省略(if (onDash < 0.5) discard;),因爲間隙中的片段將用0通道繪製。

如果先填充(綠色)多邊形,並且虛線(白色)繪製線條第二,那麼結果可能會是這樣的:

enter image description here

+0

這真棒。非常感謝。討厭甚至問,但你能否加上你從NASA世界風中稱呼這些的方式。意思是如何將着色器應用於G1對象。 – crychair

+0

所以我一直在現有的代碼中進行設置。我得到了着色器來激活,但它把世界各地的東西搞砸了,因爲它好像被應用於一切。我如何將着色器應用於某個可渲染的? – crychair