diff --git a/ClassicalSharp/GraphicsAPI/Direct3D9Api.cs b/ClassicalSharp/GraphicsAPI/Direct3D9Api.cs index 369242c3e..c5039edb1 100644 --- a/ClassicalSharp/GraphicsAPI/Direct3D9Api.cs +++ b/ClassicalSharp/GraphicsAPI/Direct3D9Api.cs @@ -230,7 +230,14 @@ namespace ClassicalSharp.GraphicsAPI { }; public override int CreateVb( T[] vertices, VertexFormat format, int count ) { - VertexBuffer buffer = CreateVb( vertices, count, format ); + GCHandle handle = GCHandle.Alloc( vertices, GCHandleType.Pinned ); + VertexBuffer buffer = CreateVertexBuffer( handle.AddrOfPinnedObject(), count, format ); + handle.Free(); + return GetOrExpand( ref vBuffers, buffer, vBufferSize ); + } + + public override int CreateVb( IntPtr vertices, VertexFormat format, int count ) { + VertexBuffer buffer = CreateVertexBuffer( vertices, count, format ); return GetOrExpand( ref vBuffers, buffer, vBufferSize ); } @@ -247,26 +254,22 @@ namespace ClassicalSharp.GraphicsAPI { return GetOrExpand( ref iBuffers, buffer, iBufferSize ); } - unsafe VertexBuffer CreateVb( T[] vertices, int count, VertexFormat format ) { - int sizeInBytes = count * strideSizes[(int)format]; - D3D.VertexFormat d3dFormat = formatMapping[(int)format]; - VertexBuffer buffer = new VertexBuffer( device, sizeInBytes, Usage.None, d3dFormat, Pool.Managed ); + unsafe VertexBuffer CreateVertexBuffer( IntPtr src, int count, VertexFormat format ) { + int size = count * strideSizes[(int)format]; + VertexBuffer buffer = new VertexBuffer( device, size, Usage.None, formatMapping[(int)format], Pool.Managed ); - IntPtr vbData = buffer.Lock( 0, sizeInBytes, LockFlags.None ); - GCHandle handle = GCHandle.Alloc( vertices, GCHandleType.Pinned ); - IntPtr source = handle.AddrOfPinnedObject(); - memcpy( source, vbData, sizeInBytes ); + IntPtr vbData = buffer.Lock( 0, size, LockFlags.None ); + memcpy( src, vbData, size ); buffer.Unlock(); - handle.Free(); return buffer; } unsafe IndexBuffer CreateIndexBuffer( IntPtr src, int count ) { - int sizeInBytes = count * sizeof( ushort ); - IndexBuffer buffer = new IndexBuffer( device, sizeInBytes, Usage.None, Pool.Managed, true ); + int size = count * sizeof( ushort ); + IndexBuffer buffer = new IndexBuffer( device, size, Usage.None, Pool.Managed, true ); - IntPtr vbData = buffer.Lock( 0, sizeInBytes, LockFlags.None ); - memcpy( src, vbData, sizeInBytes ); + IntPtr vbData = buffer.Lock( 0, size, LockFlags.None ); + memcpy( src, vbData, size ); buffer.Unlock(); return buffer; } @@ -279,28 +282,17 @@ namespace ClassicalSharp.GraphicsAPI { Delete( iBuffers, ib ); } - public override void DrawVb( DrawMode mode, VertexFormat format, int id, int startVertex, int verticesCount ) { - device.SetStreamSource( 0, vBuffers[id], 0, strideSizes[(int)format] ); - device.SetVertexFormat( formatMapping[(int)format] ); - device.DrawPrimitives( modeMappings[(int)mode], startVertex, NumPrimitives( verticesCount, mode ) ); - } - int batchStride; public override void BeginVbBatch( VertexFormat format ) { device.SetVertexFormat( formatMapping[(int)format] ); batchStride = strideSizes[(int)format]; } - public override void DrawVbBatch( DrawMode mode, int id, int startVertex, int verticesCount ) { + public override void DrawVb( DrawMode mode, int id, int startVertex, int verticesCount ) { device.SetStreamSource( 0, vBuffers[id], 0, batchStride ); device.DrawPrimitives( modeMappings[(int)mode], startVertex, NumPrimitives( verticesCount, mode ) ); } - public override void BeginIndexedVbBatch() { - device.SetVertexFormat( formatMapping[(int)VertexFormat.Pos3fTex2fCol4b] ); - batchStride = VertexPos3fTex2fCol4b.Size; - } - public override void BindVb( int vb ) { device.SetStreamSource( 0, vBuffers[vb], 0, batchStride ); } diff --git a/ClassicalSharp/GraphicsAPI/IGraphicsApi.cs b/ClassicalSharp/GraphicsAPI/IGraphicsApi.cs index 751c89f1d..9df9e20c4 100644 --- a/ClassicalSharp/GraphicsAPI/IGraphicsApi.cs +++ b/ClassicalSharp/GraphicsAPI/IGraphicsApi.cs @@ -104,6 +104,8 @@ namespace ClassicalSharp.GraphicsAPI { public abstract int CreateVb( T[] vertices, VertexFormat format, int count ) where T : struct; + public abstract int CreateVb( IntPtr vertices, VertexFormat format, int count ); + public abstract int CreateIb( ushort[] indices, int indicesCount ); public abstract int CreateIb( IntPtr indices, int indicesCount ); @@ -120,13 +122,9 @@ namespace ClassicalSharp.GraphicsAPI { public abstract void DrawDynamicVb( DrawMode mode, int vb, T[] vertices, VertexFormat format, int count ) where T : struct; - public abstract void DrawVb( DrawMode mode, VertexFormat format, int id, int startVertex, int verticesCount ); - public abstract void BeginVbBatch( VertexFormat format ); - public abstract void DrawVbBatch( DrawMode mode, int id, int startVertex, int verticesCount ); - - public abstract void BeginIndexedVbBatch(); + public abstract void DrawVb( DrawMode mode, int id, int startVertex, int verticesCount ); public abstract void DrawIndexedVb( DrawMode mode, int indicesCount, int startVertex, int startIndex ); diff --git a/ClassicalSharp/GraphicsAPI/OpenGLApi.cs b/ClassicalSharp/GraphicsAPI/OpenGLApi.cs index 6bab2b6d1..4b6820adc 100644 --- a/ClassicalSharp/GraphicsAPI/OpenGLApi.cs +++ b/ClassicalSharp/GraphicsAPI/OpenGLApi.cs @@ -182,28 +182,35 @@ namespace ClassicalSharp.GraphicsAPI { Action setupBatchFunc; Action setupBatchFuncTex2f, setupBatchFuncCol4b, setupBatchFuncTex2fCol4b; - public unsafe override int CreateDynamicVb( VertexFormat format, int maxVertices ) { + public override int CreateDynamicVb( VertexFormat format, int maxVertices ) { int id = GenAndBind( BufferTarget.ArrayBuffer ); int sizeInBytes = maxVertices * strideSizes[(int)format]; GL.BufferDataARB( BufferTarget.ArrayBuffer, new IntPtr( sizeInBytes ), IntPtr.Zero, BufferUsageHint.DynamicDraw ); return id; } - public unsafe override int CreateVb( T[] vertices, VertexFormat format, int count ) { + public override int CreateVb( T[] vertices, VertexFormat format, int count ) { int id = GenAndBind( BufferTarget.ArrayBuffer ); int sizeInBytes = count * strideSizes[(int)format]; GL.BufferDataARB( BufferTarget.ArrayBuffer, new IntPtr( sizeInBytes ), vertices, BufferUsageHint.StaticDraw ); return id; } - public unsafe override int CreateIb( ushort[] indices, int indicesCount ) { + public override int CreateVb( IntPtr vertices, VertexFormat format, int count ) { + int id = GenAndBind( BufferTarget.ArrayBuffer ); + int sizeInBytes = count * strideSizes[(int)format]; + GL.BufferDataARB( BufferTarget.ArrayBuffer, new IntPtr( sizeInBytes ), vertices, BufferUsageHint.StaticDraw ); + return id; + } + + public override int CreateIb( ushort[] indices, int indicesCount ) { int id = GenAndBind( BufferTarget.ElementArrayBuffer ); int sizeInBytes = indicesCount * sizeof( ushort ); GL.BufferDataARB( BufferTarget.ElementArrayBuffer, new IntPtr( sizeInBytes ), indices, BufferUsageHint.StaticDraw ); return id; } - public unsafe override int CreateIb( IntPtr indices, int indicesCount ) { + public override int CreateIb( IntPtr indices, int indicesCount ) { int id = GenAndBind( BufferTarget.ElementArrayBuffer ); int sizeInBytes = indicesCount * sizeof( ushort ); GL.BufferDataARB( BufferTarget.ElementArrayBuffer, new IntPtr( sizeInBytes ), indices, BufferUsageHint.StaticDraw ); @@ -242,13 +249,6 @@ namespace ClassicalSharp.GraphicsAPI { GL.DeleteBuffersARB( 1, &id ); } - public override void DrawVb( DrawMode mode, VertexFormat format, int id, int startVertex, int verticesCount ) { - BeginVbBatch( format ); - GL.BindBufferARB( BufferTarget.ArrayBuffer, id ); - setupBatchFunc(); - GL.DrawArrays( modeMappings[(int)mode], startVertex, verticesCount ); - } - VertexFormat batchFormat = (VertexFormat)999; public override void BeginVbBatch( VertexFormat format ) { if( format == batchFormat ) return; @@ -276,11 +276,7 @@ namespace ClassicalSharp.GraphicsAPI { } } - public override void BeginIndexedVbBatch() { - BeginVbBatch( VertexFormat.Pos3fTex2fCol4b ); - } - - public override void DrawVbBatch( DrawMode mode, int id, int startVertex, int verticesCount ) { + public override void DrawVb( DrawMode mode, int id, int startVertex, int verticesCount ) { GL.BindBufferARB( BufferTarget.ArrayBuffer, id ); setupBatchFunc(); GL.DrawArrays( modeMappings[(int)mode], startVertex, verticesCount ); diff --git a/ClassicalSharp/Model/IModel.cs b/ClassicalSharp/Model/IModel.cs index e60a3370a..58cf48139 100644 --- a/ClassicalSharp/Model/IModel.cs +++ b/ClassicalSharp/Model/IModel.cs @@ -27,6 +27,7 @@ namespace ClassicalSharp.Model { graphics.PushMatrix(); Matrix4 mat = Matrix4.RotateY( -p.YawRadians ) * Matrix4.Translate( p.Position ); graphics.MultiplyMatrix( ref mat ); + graphics.BeginVbBatch( VertexFormat.Pos3fTex2fCol4b ); DrawPlayerModel( p ); graphics.PopMatrix(); } diff --git a/ClassicalSharp/Model/ModelPart.cs b/ClassicalSharp/Model/ModelPart.cs index 83fc09150..aa32ce6b0 100644 --- a/ClassicalSharp/Model/ModelPart.cs +++ b/ClassicalSharp/Model/ModelPart.cs @@ -16,7 +16,7 @@ namespace ClassicalSharp { } public void Render( int vb ) { - Graphics.DrawVb( DrawMode.Triangles, VertexFormat.Pos3fTex2fCol4b, vb, Offset, Count ); + Graphics.DrawVb( DrawMode.Triangles, vb, Offset, Count ); } } diff --git a/ClassicalSharp/Rendering/MapEnvRenderer.cs b/ClassicalSharp/Rendering/MapEnvRenderer.cs index f3d0ac9aa..39743ebf7 100644 --- a/ClassicalSharp/Rendering/MapEnvRenderer.cs +++ b/ClassicalSharp/Rendering/MapEnvRenderer.cs @@ -39,27 +39,22 @@ namespace ClassicalSharp { MakeTexture( ref sideTexId, ref lastSideTexLoc, Map.SidesBlock ); ResetSidesAndEdges( null, null ); } - - public void RenderMapSides( double deltaTime ) { - if( sidesVboId == -1 ) return; - + + public void Render( double deltaTime ) { + if( sidesVboId == -1 || edgesVboId == -1 ) return; Graphics.Texturing = true; Graphics.Bind2DTexture( sideTexId ); - Graphics.DrawVb( DrawMode.Triangles, VertexFormat.Pos3fTex2fCol4b, sidesVboId, 0, sidesVertices ); - Graphics.Texturing = false; - } - - public void RenderMapEdges( double deltaTime ) { - if( edgesVboId == -1 ) return; + Graphics.BeginVbBatch( VertexFormat.Pos3fTex2fCol4b ); + Graphics.DrawVb( DrawMode.Triangles, sidesVboId, 0, sidesVertices ); + // Do not draw water when we cannot see it. // Fixes 'depth bleeding through' issues with 16 bit depth buffers on large maps. - if( Window.LocalPlayer.EyePosition.Y < 0 ) return; - - Graphics.Texturing = true; - Graphics.AlphaBlending = true; - Graphics.Bind2DTexture( edgeTexId ); - Graphics.DrawVb( DrawMode.Triangles, VertexFormat.Pos3fTex2fCol4b, edgesVboId, 0, edgesVertices ); - Graphics.AlphaBlending = false; + if( Window.LocalPlayer.EyePosition.Y >= 0 ) { + Graphics.AlphaBlending = true; + Graphics.Bind2DTexture( edgeTexId ); + Graphics.DrawVb( DrawMode.Triangles, edgesVboId, 0, edgesVertices ); + Graphics.AlphaBlending = false; + } Graphics.Texturing = false; } @@ -160,7 +155,7 @@ namespace ClassicalSharp { DrawZPlane( 0, 0, Map.Width, 0, groundLevel, sidesCol, vertices ); DrawZPlane( Map.Length, 0, Map.Width, 0, groundLevel, sidesCol, vertices ); DrawXPlane( 0, 0, Map.Length, 0, groundLevel, sidesCol, vertices ); - DrawXPlane( Map.Width, 0, Map.Length, 0, groundLevel, sidesCol, vertices ); + DrawXPlane( Map.Width, 0, Map.Length, 0, groundLevel, sidesCol, vertices ); sidesVboId = Graphics.CreateVb( vertices, VertexFormat.Pos3fTex2fCol4b ); } @@ -170,7 +165,7 @@ namespace ClassicalSharp { foreach( Rectangle rec in OutsideMap( Window.ViewDistance ) ) { DrawYPlane( rec.X, rec.Y, rec.X + rec.Width, rec.Y + rec.Height, waterLevel, edgesCol, vertices ); - } + } edgesVboId = Graphics.CreateVb( vertices, VertexFormat.Pos3fTex2fCol4b ); } @@ -212,7 +207,7 @@ namespace ClassicalSharp { edgesVboId = Graphics.CreateVb( vertices, VertexFormat.Pos3fTex2fCol4b ); } - const int axisSize = 128; + const int axisSize = 128; void DrawXPlaneParts( int x, int z1, int z2, int y1, int y2, FastColour col, VertexPos3fTex2fCol4b[] vertices ) { int endZ = z2, endY = y2, startY = y1; for( ; z1 < endZ; z1 += axisSize ) { @@ -265,7 +260,7 @@ namespace ClassicalSharp { Window.Graphics.DeleteTexture( ref texId ); texId = Window.TerrainAtlas.LoadTextureElement( texLoc ); } - } + } void DrawXPlane( int x, int z1, int z2, int y1, int y2, FastColour col, VertexPos3fTex2fCol4b[] vertices ) { TextureRectangle rec = new TextureRectangle( 0, 0, z2 - z1, y2 - y1 ); diff --git a/ClassicalSharp/Rendering/MapRenderer.cs b/ClassicalSharp/Rendering/MapRenderer.cs index 64b362997..6bf6297d3 100644 --- a/ClassicalSharp/Rendering/MapRenderer.cs +++ b/ClassicalSharp/Rendering/MapRenderer.cs @@ -194,8 +194,7 @@ namespace ClassicalSharp { api.BindIb( chunkIb ); RenderNormal(); - game.MapEnvRenderer.RenderMapSides( deltaTime ); - game.MapEnvRenderer.RenderMapEdges( deltaTime ); + game.MapEnvRenderer.Render( deltaTime ); api.BindIb( chunkIb ); RenderTranslucent(); } @@ -263,7 +262,7 @@ namespace ClassicalSharp { // These blocks are treated as having an alpha value of either none or full. void RenderNormal() { int[] texIds = game.TerrainAtlas1D.TexIds; - api.BeginIndexedVbBatch(); + api.BeginVbBatch( VertexFormat.Pos3fTex2fCol4b ); api.Texturing = true; api.AlphaTest = true; @@ -298,7 +297,7 @@ namespace ClassicalSharp { void RenderTranslucent() { // First fill depth buffer int[] texIds = game.TerrainAtlas1D.TexIds; - api.BeginIndexedVbBatch(); + api.BeginVbBatch( VertexFormat.Pos3fTex2fCol4b ); api.Texturing = false; api.AlphaBlending = false; api.ColourWrite = false; diff --git a/ClassicalSharp/Rendering/StandardEnvRenderer.cs b/ClassicalSharp/Rendering/StandardEnvRenderer.cs index f27eca468..0a6353505 100644 --- a/ClassicalSharp/Rendering/StandardEnvRenderer.cs +++ b/ClassicalSharp/Rendering/StandardEnvRenderer.cs @@ -29,7 +29,8 @@ namespace ClassicalSharp.Renderers { Vector3 pos = Window.LocalPlayer.EyePosition; if( pos.Y < Map.Height + skyOffset ) { - Graphics.DrawVb( DrawMode.Triangles, VertexFormat.Pos3fCol4b, skyVbo, 0, skyVertices ); + Graphics.BeginVbBatch( VertexFormat.Pos3fCol4b ); + Graphics.DrawVb( DrawMode.Triangles, skyVbo, 0, skyVertices ); } RenderClouds( deltaTime ); ResetFog(); @@ -97,7 +98,8 @@ namespace ClassicalSharp.Renderers { Graphics.AlphaTest = true; Graphics.Texturing = true; Graphics.Bind2DTexture( cloudTexture ); - Graphics.DrawVb( DrawMode.Triangles, VertexFormat.Pos3fTex2fCol4b, cloudsVbo, 0, cloudsVertices ); + Graphics.BeginVbBatch( VertexFormat.Pos3fTex2fCol4b ); + Graphics.DrawVb( DrawMode.Triangles, cloudsVbo, 0, cloudsVertices ); Graphics.AlphaTest = false; Graphics.Texturing = false; diff --git a/ClassicalSharp/Selections/SelectionBox.cs b/ClassicalSharp/Selections/SelectionBox.cs index 4ce2d0361..0b5da8940 100644 --- a/ClassicalSharp/Selections/SelectionBox.cs +++ b/ClassicalSharp/Selections/SelectionBox.cs @@ -19,9 +19,9 @@ namespace ClassicalSharp.Selections { public void Render( double delta ) { Graphics.DepthWrite = false; - Graphics.DrawVbBatch( DrawMode.Triangles, Vb, 0, VerticesCount ); + Graphics.DrawVb( DrawMode.Triangles, Vb, 0, VerticesCount ); Graphics.DepthWrite = true; - Graphics.DrawVbBatch( DrawMode.Lines, LineVb, 0, LineVerticesCount ); + Graphics.DrawVb( DrawMode.Lines, LineVb, 0, LineVerticesCount ); } static VertexPos3fCol4b[] vertices = new VertexPos3fCol4b[VerticesCount];