借用官網範例改C#:
static Material lineMaterial; static void CreateLineMaterial() { if( !lineMaterial ) { lineMaterial = new Material( "Shader \"Lines/Colored Blended\" {" + "SubShader { Pass { " + " Blend SrcAlpha OneMinusSrcAlpha " + " ZWrite Off Cull Off Fog { Mode Off } " + " BindChannels {" + " Bind \"vertex\", vertex Bind \"color\", color }" + "} } }" ); lineMaterial.hideFlags = HideFlags.HideAndDontSave; lineMaterial.shader.hideFlags = HideFlags.HideAndDontSave; } } //在PostRender裡面呼叫GL才可以避免Render順序的問題 void OnPostRender() { CreateLineMaterial(); // set the current material lineMaterial.SetPass( 0 ); //繪製線條,每兩個點一線,請給雙數點 GL.Begin( GL.LINES ); GL.Color( new Color(1.0f,1.0f,1.0f,0.5f) ); GL.Vertex3( 0, 0, 0 ); GL.Vertex3( 1, 0, 0 ); GL.End(); }
二、OnPostRender方法沒有呼叫的狀況,因這個方法只有在這個Script掛載在Camera下面才會呼叫,所以請先檢查有這個方法的Component是否在Camera下。
三、當有兩個以上的Camera的時候,在ClearFlags都是Skybox的狀況下,只會畫出其中一個Camera的線條(使用上面範例,兩個Camera繪製不同座標線條),另外一個Camera的畫不出來。
同樣是執行順序的問題,在單一Camera下只要在OnPostRender裡呼叫GL,就可以確保GL是在Camera render後才執行。但是兩個以上的Camera狀況下,兩個Camera的Render順序不同,OnPostRender只能在該掛載的Camera render過後執行,接著第二個Camera開始更新,就會覆蓋掉第一個Camera的資料(ClearFlag:Skybox)
解決辦法就是讓OnPostRender裡面的GL等到該frame的尾端執行,確保所有的Camera都已經Render完畢,所以直接在OnPostRender()開頭加上WaitForEndOfFrame()就可以了。
C#版本,其餘部分跟第一個範例相同
//在PostRender開頭呼叫WaitForEndOfFrame調整順序的問題 IEnumerator OnPostRender() { yield return new WaitForEndOfFrame(); CreateLineMaterial(); // set the current material lineMaterial.SetPass( 0 ); //繪製線條,每兩個點一線,請給雙數點 GL.Begin( GL.LINES ); GL.Color( new Color(1.0f,1.0f,1.0f,0.5f) ); GL.Vertex3( 0, 0, 0 ); GL.Vertex3( 1, 0, 0 ); GL.End(); }
No comments:
Post a Comment