Ejemplo n.º 1
0
 private void Allocate()
 {
     if (vertexBuffer == null || vertexBuffer.IsDisposed)
     {
         vertexBuffer              = new DynamicVertexBuffer(graphicsDevice, typeof(VertexPositionColorTexture), 8192, BufferUsage.WriteOnly);
         vertexBufferPosition      = 0;
         vertexBuffer.ContentLost += delegate
         {
             vertexBufferPosition = 0;
         };
     }
     if (indexBuffer != null && !indexBuffer.IsDisposed)
     {
         return;
     }
     if (fallbackIndexData == null)
     {
         fallbackIndexData = new short[12288];
         for (int i = 0; i < 2048; i++)
         {
             fallbackIndexData[i * 6]     = (short)(i * 4);
             fallbackIndexData[i * 6 + 1] = (short)(i * 4 + 1);
             fallbackIndexData[i * 6 + 2] = (short)(i * 4 + 2);
             fallbackIndexData[i * 6 + 3] = (short)(i * 4);
             fallbackIndexData[i * 6 + 4] = (short)(i * 4 + 2);
             fallbackIndexData[i * 6 + 5] = (short)(i * 4 + 3);
         }
     }
     indexBuffer = new DynamicIndexBuffer(graphicsDevice, typeof(short), 12288, BufferUsage.WriteOnly);
     indexBuffer.SetData(fallbackIndexData);
     indexBuffer.ContentLost += delegate
     {
         indexBuffer.SetData(fallbackIndexData);
     };
 }
Ejemplo n.º 2
0
        /// <summary>
        /// Resets the vertex buffer object from the verticies.
        /// <param Name="device">GPU to draw with.</param></summary>
        public virtual void ResetBuffer(GraphicsDevice device)
        {
            //if(DwarfGame.ExitGame)
            //{
            //    return;
            //}

            //lock (VertexLock)
            {
                if (VertexBuffer != null && !VertexBuffer.IsDisposed)
                {
                    VertexBuffer.Dispose();
                }
                VertexBuffer = null;

                if (IndexBuffer != null && !IndexBuffer.IsDisposed)
                {
                    IndexBuffer.Dispose();
                }
                IndexBuffer = null;

                if (IndexCount <= 0 && Indexes != null)
                {
                    IndexCount = Indexes.Length;
                }

                if (VertexCount <= 0 && Vertices != null)
                {
                    VertexCount = Vertices.Length;
                }

                if (Vertices != null)
                {
                    try
                    {
                        VertexBuffer = new DynamicVertexBuffer(device, ExtendedVertex.VertexDeclaration, Vertices.Length, BufferUsage.WriteOnly);
                        VertexBuffer.SetData(Vertices, 0, VertexCount);
                    }
                    catch (Exception exception)
                    {
                        Console.Out.WriteLine(exception.ToString());
                        VertexBuffer = null;
                    }
                }

                if (Indexes != null)
                {
                    try
                    {
                        IndexBuffer = new DynamicIndexBuffer(device, typeof(ushort), Indexes.Length, BufferUsage.None);
                        IndexBuffer.SetData(Indexes, 0, IndexCount);
                    }
                    catch (Exception exception)
                    {
                        Console.Out.WriteLine(exception.ToString());
                        IndexBuffer = null;
                    }
                }
            }
        }
Ejemplo n.º 3
0
 public static void LoadContent()
 {
     _iboQuad = new DynamicIndexBuffer(Device, IndexElementSize.SixteenBits, MAX_QUADS * 6, BufferUsage.WriteOnly);
     _iboQuad.SetData(QuadIndices, 0, MAX_QUADS * 6);
     _iboFan = new DynamicIndexBuffer(Device, IndexElementSize.SixteenBits, MAX_QUADS * 3, BufferUsage.WriteOnly);
     _iboFan.SetData(FanIndices, 0, MAX_QUADS * 3);
 }
Ejemplo n.º 4
0
        /// <summary>
        /// This is called when the game should draw itself.
        /// </summary>
        /// <param name="gameTime">Provides a snapshot of timing values.</param>
        protected override void Draw(GameTime gameTime)
        {
            GraphicsDevice.Clear(Color.CornflowerBlue);

            // Compute camera matrices.
            Matrix View = Matrix.CreateLookAt(eye, at, up);

            Matrix Projection = Matrix.CreatePerspectiveFieldOfView(fov, GraphicsDevice.Viewport.AspectRatio, zNear, zFar);

            cubeRotation += (0.0025f) * (float)gameTime.ElapsedGameTime.TotalMilliseconds;
            Matrix World = Matrix.CreateRotationY(cubeRotation);

            // TODO: Add your drawing code here

            vertexBuffer.SetData(cube, 0, 8, SetDataOptions.Discard);
            indexBuffer.SetData(cubeIndices, 0, 36, SetDataOptions.Discard);

            GraphicsDevice device = basicEffect.GraphicsDevice;

            device.SetVertexBuffer(vertexBuffer);
            device.Indices = indexBuffer;

            basicEffect.View       = View;
            basicEffect.Projection = Projection;
            basicEffect.World      = World;
            foreach (EffectPass pass in basicEffect.CurrentTechnique.Passes)
            {
                pass.Apply();
                device.DrawIndexedPrimitives(PrimitiveType.TriangleList, 0, 0, 8, 0, 36);
            }
            base.Draw(gameTime);
        }
Ejemplo n.º 5
0
        private void SetUpBuffers()
        {
            v_buffer = new DynamicVertexBuffer(Game.device, VertexPositionTexture.VertexDeclaration, vertices.Length, BufferUsage.WriteOnly);
            i_buffer = new DynamicIndexBuffer(Game.device, typeof(int), indices.Length, BufferUsage.WriteOnly);

            v_buffer.SetData(vertices);
            i_buffer.SetData(indices);
        }
Ejemplo n.º 6
0
 public void BeginRender(Vertex[] vertexBuffer, int[] indexBuffer, int vertexCount, int indexCount)
 {
     EnsureBufferSize(vertexCount, indexCount);
     _vertexBuffer.SetData(vertexBuffer, 0, vertexCount);
     _indexBuffer.SetData(indexBuffer, 0, indexCount);
     GraphicsDevice.SetVertexBuffer(_vertexBuffer);
     GraphicsDevice.Indices = _indexBuffer;
 }
Ejemplo n.º 7
0
        /// <summary>
        /// Draws vertices from vertex buffer and empties it.
        /// </summary>
        private static void DrawVertices()
        {
            BasicEffect.View = CurrentTransformMatrix;

            __drawcalls += 1;

            if (_vertices.Count > 0)
            {
                BasicEffect.Texture        = _currentTexture;
                BasicEffect.TextureEnabled = (_currentTexture != null);


                PrimitiveType type;
                int           prCount;

                if (_currentPipelineMode == PipelineMode.OutlinePrimitives)
                {
                    type    = PrimitiveType.LineList;
                    prCount = _indices.Count / 2;
                }
                else
                {
                    type    = PrimitiveType.TriangleList;
                    prCount = _indices.Count / 3;
                }

                // Passing primitive data to the buffers.
                _vertexBuffer.SetData(_vertices.ToArray(), 0, _vertices.Count, SetDataOptions.None);
                _indexBuffer.SetData(_indices.ToArray(), 0, _indices.Count);
                // Passing primitive data to the buffers.

                if (_rasterizer != null)
                {
                    Device.RasterizerState = _rasterizer;
                }

                if (_sampler != null)
                {
                    Device.SamplerStates[0] = _sampler;
                }

                Device.ScissorRectangle = _scissorRectangle;

                foreach (EffectPass pass in BasicEffect.CurrentTechnique.Passes)
                {
                    pass.Apply();
                    Device.DrawIndexedPrimitives(type, 0, 0, prCount);
                }

                _vertices.Clear();
                _indices.Clear();
            }
        }
Ejemplo n.º 8
0
        void AllocateBuffers()
        {
            if (vertexBuffer == null || vertexBuffer.IsDisposed == true)
            {
                vertexBuffer         = new DynamicVertexBuffer(graphicsDevice, typeof(GlyphVertex), vertexBufferSize, BufferUsage.WriteOnly);
                vertexBufferPosition = 0;
            }

            if (indexBuffer == null || indexBuffer.IsDisposed == true)
            {
                indexBuffer = new DynamicIndexBuffer(graphicsDevice, typeof(short), indexBufferSize, BufferUsage.WriteOnly);
                indexBuffer.SetData <short>(CreateIndexData());
            }
        }
Ejemplo n.º 9
0
        private void CalculateBuffers()
        {
            if (fPoints.Count > 0)
            {
                fNumberOfParticles = fPoints.Count;
                fNumberOfVertices  = fPoints.Count * 4;
                fNumberOfIndices   = fPoints.Count * 6;
                VertexBillboardParticle[] vertices = new VertexBillboardParticle[fNumberOfVertices];
                short[] indices       = new short[fNumberOfIndices];
                int     verticeNumber = 0;
                int     indiceNumber  = 0;
                for (int i = 0; i < fNumberOfParticles; i++)
                {
                    MyPoint point             = fPoints[i];
                    int     verticeNumberBase = verticeNumber;
                    vertices[verticeNumber++] = new VertexBillboardParticle(point.Position, Vector2.Zero, point.Size, Color.White);
                    vertices[verticeNumber++] = new VertexBillboardParticle(point.Position, new Vector2(1, 0), point.Size, Color.White);
                    vertices[verticeNumber++] = new VertexBillboardParticle(point.Position, new Vector2(0, 1), point.Size, Color.White);
                    vertices[verticeNumber++] = new VertexBillboardParticle(point.Position, Vector2.One, point.Size, Color.White);
                    indices[indiceNumber++]   = (short)(0 + verticeNumberBase);
                    indices[indiceNumber++]   = (short)(1 + verticeNumberBase);
                    indices[indiceNumber++]   = (short)(2 + verticeNumberBase);
                    indices[indiceNumber++]   = (short)(1 + verticeNumberBase);
                    indices[indiceNumber++]   = (short)(3 + verticeNumberBase);
                    indices[indiceNumber++]   = (short)(2 + verticeNumberBase);
                }

                // 2020-04-01 Out of memory, which hasent happened before
                //fIndexBuffer = new DynamicIndexBuffer(GraphicsDevice, IndexElementSize.SixteenBits, fNumberOfIndices, BufferUsage.WriteOnly);
                //fIndexBuffer.SetData(indices);
                //fVertexBuffer = new DynamicVertexBuffer(GraphicsDevice, VertexBillboardParticle.VertexDeclaration, fNumberOfVertices, BufferUsage.WriteOnly);
                //fVertexBuffer.SetData(vertices);

                if (fIndexBuffer != null)
                {
                    fIndexBuffer.Dispose();
                }
                if (fVertexBuffer != null)
                {
                    fVertexBuffer.Dispose();
                }

                fIndexBuffer  = new DynamicIndexBuffer(GraphicsDevice, IndexElementSize.SixteenBits, fNumberOfIndices, BufferUsage.WriteOnly);
                fVertexBuffer = new DynamicVertexBuffer(GraphicsDevice, VertexBillboardParticle.VertexDeclaration, fNumberOfVertices, BufferUsage.WriteOnly);

                fIndexBuffer.SetData(indices);
                fVertexBuffer.SetData(vertices);
            }
        }
Ejemplo n.º 10
0
            public GUIRenderer(IGUIMapper mapper, Matrix renderMatrix /*, CollisionObject colObj*/)
            {
                this.mapper       = mapper;
                this.renderMatrix = renderMatrix;
                //this.colObj = colObj;

                guiTexture = new Texture2D(State.Device, mapper.GUIWidth, mapper.GUIHeight,
                                           false, mapper.TextureFormat);
                texCoords = new VertexPositionTexture[4];

                // Calculate the GUI positions where it will rendered in the 3D world
                Matrix texPos = Matrix.Identity;

                width  = guiTexture.Width * mapper.DrawingScaleFactor.X / 2;
                height = guiTexture.Height * mapper.DrawingScaleFactor.Y / 2;

                texCoords[0].Position          = new Vector3(-width, height, 0);
                texCoords[0].TextureCoordinate = new Vector2(0, 1);

                texCoords[1].Position          = new Vector3(width, -height, 0);
                texCoords[1].TextureCoordinate = new Vector2(1, 0);

                texCoords[2].Position          = new Vector3(-width, -height, 0);
                texCoords[2].TextureCoordinate = new Vector2(0, 0);

                texCoords[3].Position          = new Vector3(width, height, 0);
                texCoords[3].TextureCoordinate = new Vector2(1, 1);

                vb = new DynamicVertexBuffer(State.Device, VertexPositionTexture.VertexDeclaration, 4, BufferUsage.WriteOnly);
                vb.SetData(texCoords);

                short[] indices = new short[6];

                indices[0] = 0;
                indices[1] = 1;
                indices[2] = 2;
                indices[3] = 3;
                indices[4] = 1;
                indices[5] = 0;

                ib = new DynamicIndexBuffer(State.Device, typeof(short), 6, BufferUsage.WriteOnly);
                ib.SetData(indices);

                textureData = mapper.GUITexture;

                //colObj = GoblinSetting.UICollisionWorld.Add2Dto3DGUI(new Vector2(width * 2, height * 2),
                //            renderMatrix, mapper.GetGUIName());
            }
Ejemplo n.º 11
0
        protected override unsafe void SetBuffers(byte[] vertices, ushort[] indices, int indicesCount, int vertexCount)
        {
            if (vertexCount == 0)
            {
                return;
            }

            var result = new VertexPositionColorTexture[vertexCount];

            fixed(VertexPositionColorTexture *vx = &result[0])
            {
                var b = (byte *)vx;

                for (int i = 0; i < vertexCount * sizeof(VertexPositionColorTexture); i++)
                {
                    *(b + i) = vertices[i];
                }
            }

            for (var i = 0; i < vertexCount; i++)
            {
                var c = result[i].Color;
                result[i].Color = new Color(c.B, c.G, c.R, c.A);
            }

            if (_vertexBuffer.VertexCount < result.Length)
            {
                // Resize vertex buffer if data doesnt fit
                _vertexBuffer = new DynamicVertexBuffer(_device, VertexPositionColorTexture.VertexDeclaration, result.Length * 2,
                                                        BufferUsage.WriteOnly);
            }
            _vertexBuffer.SetData(result);


            if (_indexBuffer.IndexCount < indicesCount)
            {
                // Resize index buffer if data doesnt fit
                _indexBuffer = new DynamicIndexBuffer(_device, typeof(ushort), indicesCount * 2, BufferUsage.WriteOnly);
            }

            _indexBuffer.SetData(indices, 0, indicesCount);
        }
Ejemplo n.º 12
0
        protected override void LoadContent()
        {
            device       = graphics.GraphicsDevice;
            basicEffect  = new BasicEffect(device, null);
            cCross       = new CoordCross(device);
            grassTexture = Content.Load <Texture2D>("grass");

            Texture2D heightMap = Content.Load <Texture2D>("heightmap");

            heightData = LoadHeightData(heightMap);

            myVertexDeclaration = new VertexDeclaration(device, VertexPositionNormalTexture.VertexElements);
            VertexPositionNormalTexture[] terrainVertices = CreateTerrainVertices();
            int[] terrainIndices = CreateTerrainIndices();
            terrainVertices     = GenerateNormalsForTriangleStrip(terrainVertices, terrainIndices);
            terrainVertexBuffer = new VertexBuffer(device, VertexPositionNormalTexture.SizeInBytes * terrainVertices.Length, BufferUsage.WriteOnly);
            terrainVertexBuffer.SetData(terrainVertices);

            int      terrainSize   = 1024;
            Triangle leftTriangle  = new Triangle(null, new Vector2(0, 0), new Vector2(terrainSize, 0), new Vector2(0, terrainSize), heightData);
            Triangle rightTriangle = new Triangle(null, new Vector2(terrainSize, terrainSize), new Vector2(0, terrainSize), new Vector2(terrainSize, 0), heightData);

            leftTriangle.AddNeighs(null, null, rightTriangle);
            rightTriangle.AddNeighs(null, null, leftTriangle);

            triangleList = new List <Triangle>();
            triangleList.Add(leftTriangle);
            triangleList.Add(rightTriangle);

            indicesList = new List <int>();
            foreach (Triangle t in triangleList)
            {
                t.AddIndices(ref indicesList);
            }

            dynTerrainIndexBuffer = new DynamicIndexBuffer(device, typeof(int), indicesList.Count, BufferUsage.WriteOnly);
            dynTerrainIndexBuffer.SetData(indicesList.ToArray(), 0, indicesList.Count, SetDataOptions.Discard);
            dynTerrainIndexBuffer.ContentLost += new EventHandler(dynIndexBuffer_ContentLost);

            orthoView = Matrix.CreateLookAt(new Vector3(terrainSize / 2, 100, -terrainSize / 2), new Vector3(terrainSize / 2, 0, -terrainSize / 2), Vector3.Forward);
            orthoProj = Matrix.CreateOrthographic(terrainSize, terrainSize, 1, 1000);
        }
Ejemplo n.º 13
0
        public void SetIndices(ushort[] indices, int indexCount)
        {
            if (indices == null)
            {
                throw new ArgumentNullException("indices");
            }
            if (indexCount < 0 || indices.Length < indexCount)
            {
                throw new ArgumentOutOfRangeException("vertexCount");
            }

            IndexCount     = indexCount;
            PrimitiveCount = indexCount / 3;

            if (indexCount != 0)
            {
                if (indexBuffer != null && indexBuffer.IndexCount != indexCount)
                {
                    indexBuffer.Dispose();
                    indexBuffer = null;
                }

                if (indexBuffer == null)
                {
                    indexBuffer = new DynamicIndexBuffer(
                        graphicsDevice, IndexElementSize.SixteenBits, indexCount, BufferUsage.WriteOnly);
                }

                indexBuffer.SetData(indices, 0, indexCount, SetDataOptions.Discard);
            }
            else
            {
                if (indexBuffer != null)
                {
                    indexBuffer.Dispose();
                    indexBuffer = null;
                }
            }
        }
Ejemplo n.º 14
0
        protected override void  LoadModel(GraphicFactory factory, out BatchInformation[][] BatchInformations, out TextureInformation[][] TextureInformation)

        {
            vertexBufferS = factory.CreateDynamicVertexBuffer(VertexPositionTexture.VertexDeclaration, vertices.Count(), BufferUsage.None);
            vertexBufferS.SetData(vertices);
            int noVertices  = vertices.Count();
            int noTriangles = indices.Count() / 3;

            indexBufferS = factory.CreateDynamicIndexBuffer(IndexElementSize.ThirtyTwoBits, indices.Count(), BufferUsage.None);
            indexBufferS.SetData(indices);

            BatchInformations = new BatchInformation[1][];
            BatchInformation[] b = new BatchInformation[1];
            b[0] = new BatchInformation(0, noVertices, noTriangles, 0, 0, VertexPositionTexture.VertexDeclaration, VertexPositionTexture.VertexDeclaration.VertexStride, BatchType.INDEXED);
            b[0].VertexBuffer    = vertexBufferS;
            b[0].IndexBuffer     = indexBufferS;
            BatchInformations[0] = b;

            TextureInformation       = new TextureInformation[1][];
            TextureInformation[0]    = new TextureInformation[1];
            TextureInformation[0][0] = new TextureInformation(false, factory);
            TextureInformation[0][0].SetTexture(diffuseName, TextureType.DIFFUSE);
        }
Ejemplo n.º 15
0
        // Draw any queued objects and reset our line buffers
        private void FlushDrawing()
        {
            if (IndexCount > 0)
            {
                vertexBuffer.SetData(Vertices, 0, VertexCount, SetDataOptions.Discard);
                indexBuffer.SetData(Indices, 0, IndexCount, SetDataOptions.Discard);

                GraphicsDevice device = basicEffect.GraphicsDevice;
                device.SetVertexBuffer(vertexBuffer);
                device.Indices = indexBuffer;

                foreach (EffectPass pass in basicEffect.CurrentTechnique.Passes)
                {
                    pass.Apply();
                    device.DrawIndexedPrimitives(PrimitiveType.LineList, 0, 0, VertexCount, 0, IndexCount / 2);
                }

                device.SetVertexBuffer(null);
                device.Indices = null;
            }
            IndexCount  = 0;
            VertexCount = 0;
        }
Ejemplo n.º 16
0
        // -------------------------------------------------------------------
        // CreateTex : coords = [x,y,width,height]
        // -------------------------------------------------------------------

        public void CreateTex(int[] coords, Texture2D texture)
        {
            // Texture coords
            float left  = ((float)coords[0]) / texture.Width;
            float top   = ((float)coords[1]) / texture.Height;
            float bot   = ((float)(coords[1] + coords[3])) / texture.Height;
            float right = ((float)(coords[0] + coords[2])) / texture.Width;

            // Adjust in order to limit risk of textures flood
            float width  = left + right;
            float height = top + bot;
            int   coef   = 10000;

            left  += width / coef;
            right -= width / coef;
            top   += height / coef;
            bot   -= height / coef;

            // Vertex Position and Texture
            Vertices = new VertexPositionTexture[]
            {
                new VertexPositionTexture(WANOK.VERTICESFLOOR[0], new Vector2(left, top)),
                new VertexPositionTexture(WANOK.VERTICESFLOOR[1], new Vector2(right, top)),
                new VertexPositionTexture(WANOK.VERTICESFLOOR[2], new Vector2(right, bot)),
                new VertexPositionTexture(WANOK.VERTICESFLOOR[3], new Vector2(left, bot))
            };

            // Vertex Indexes
            Indexes = new int[]
            {
                0, 1, 2, 0, 2, 3
            };

            // Update buffers
            VB.SetData(Vertices);
            IB.SetData(Indexes);
        }
Ejemplo n.º 17
0
        /// <summary>
        /// Ends line drawing and resores render states.
        /// </summary>
        public void End()
        {
            if (_indexCount > 0)
            {
                _vertexBuffer.SetData(_vertices, 0, _vertexCount, SetDataOptions.Discard);
                _indexBuffer.SetData(_indices, 0, _indexCount, SetDataOptions.Discard);

                GraphicsDevice graphicsDevice = _basicEffect.GraphicsDevice;
                graphicsDevice.SetVertexBuffer(_vertexBuffer);
                graphicsDevice.Indices = _indexBuffer;

                foreach (EffectPass pass in _basicEffect.CurrentTechnique.Passes)
                {
                    pass.Apply();
                    graphicsDevice.DrawIndexedPrimitives(PrimitiveType.LineList, 0, 0, _vertexCount, 0, _indexCount / 2);
                }

                graphicsDevice.SetVertexBuffer(null);
                graphicsDevice.Indices = null;
            }

            _indexCount  = 0;
            _vertexCount = 0;
        }
Ejemplo n.º 18
0
 protected override void AddDataNative <VertexType>(Chunk textureChunk, VertexType[] vertexData,
                                                    short[] indices, int numberOfVertices, int numberOfIndices)
 {
     nativeDevice.SetVertexBuffer(null);
     nativeVertexBuffer.SetData(totalVertexOffsetInBytes, vertexData, 0, numberOfVertices,
                                vertexSize, currentDataHint);
     if (!UsesIndexBuffer)
     {
         currentDataHint = SetDataOptions.Discard;
         return;
     }
     nativeDevice.Indices = null;
     if (indices == null)
     {
         indices = ComputeIndices(textureChunk.NumberOfVertices, numberOfVertices);
     }
     else if (textureChunk.FirstVertexOffsetInBytes > 0)
     {
         indices = RemapIndices(indices, numberOfIndices);
     }
     nativeIndexBuffer.SetData(totalIndexOffsetInBytes, indices, 0, numberOfIndices,
                               currentDataHint);
     currentDataHint = SetDataOptions.Discard;
 }
Ejemplo n.º 19
0
        private void RenderFilledItems(GraphicsDevice graphicsDevice, ref Matrix world, ref Matrix view, ref Matrix projection)
        {
            if (_batchFilledItems.Count == 0)
            {
                return;
            }

            if (_vertexBuffer == null || _vertexBuffer.VertexCount < _filledVerticesCount)
            {
                _vertexBuffer = new DynamicVertexBuffer(graphicsDevice, VertexPositionColorTexture.VertexDeclaration, _filledVerticesCount, BufferUsage.WriteOnly);
            }

            if (_indexBuffer == null || _indexBuffer.IndexCount < _filledIndicesCount)
            {
                _indexBuffer = new DynamicIndexBuffer(graphicsDevice, IndexElementSize.ThirtyTwoBits, _filledIndicesCount, BufferUsage.WriteOnly);
            }

            int vertexId = 0,
                indexId  = 0;

            int[] indices = new int[_filledIndicesCount];
            VertexPositionColorTexture[] vertices = new VertexPositionColorTexture[_filledVerticesCount];

            foreach (PrimitiveBatchItem batchItem in _batchFilledItems)
            {
                System.Array.Copy(batchItem.VertexData, 0, vertices, vertexId, batchItem.VertexData.Length);

                for (int i = 0; i < batchItem.IndexData.Length; i++)
                {
                    indices[indexId + i] = vertexId + batchItem.IndexData[i];
                }

                vertexId += batchItem.VertexData.Length;
                indexId  += batchItem.IndexData.Length;
            }

            _vertexBuffer.SetData(
                vertices,
                0,
                vertices.Length,
                SetDataOptions.Discard
                );

            _indexBuffer.SetData(
                indices,
                0,
                indices.Length,
                SetDataOptions.Discard
                );

            BasicShader shader = Shader as BasicShader;

            // transformations
            shader.World      = world;
            shader.View       = view;
            shader.Projection = projection;

            shader.DiffuseColor = Color.White;
            shader.Alpha        = 1f;

            shader.TextureEnabled = false;

            graphicsDevice.RasterizerState   = RasterizerState.CullNone;
            graphicsDevice.DepthStencilState = DepthStencilState.None;

            foreach (object pass in shader)
            {
                graphicsDevice.Indices = _indexBuffer;
                graphicsDevice.SetVertexBuffer(_vertexBuffer);
                graphicsDevice.DrawIndexedPrimitives(PrimitiveType.TriangleList, 0, 0, _vertexBuffer.VertexCount, 0, indexId / 3);
            }

            shader.ResetParameters();

#if DEBUG
            TotalFilledDrawCalls++;
#endif
        }
Ejemplo n.º 20
0
        private void CreateVerticies()
        {
            Indexes        = new ushort[36];
            FlippedIndexes = new ushort[36];
            Vertices       = new ExtendedVertex[NumVertices];

            // Calculate the position of the vertices on the top face.
            Vector3 topLeftFront  = new Vector3(0.0f, Height, 0.0f);
            Vector3 topLeftBack   = new Vector3(0.0f, Height, 1.0f);
            Vector3 topRightFront = new Vector3(Width, Height, 0.0f);
            Vector3 topRightBack  = new Vector3(Width, Height, 1.0f);

            // Calculate the position of the vertices on the bottom face.
            Vector3 btmLeftFront  = new Vector3(0.0f, 0.0f, 0.0f);
            Vector3 btmLeftBack   = new Vector3(0.0f, 0.0f, 1.0f);
            Vector3 btmRightFront = new Vector3(Width, 0.0f, 0.0f);
            Vector3 btmRightBack  = new Vector3(Width, 0.0f, 1.0f);

            // Normal vectors for each face (needed for lighting / display)


            // Add the vertices for the FRONT face.
            Vertices[0] = new ExtendedVertex(topLeftFront, Color.White, Color.White, UVs.Uvs[0], UVs.Bounds[0]);
            Vertices[1] = new ExtendedVertex(btmLeftFront, Color.White, Color.White, UVs.Uvs[1], UVs.Bounds[0]);
            Vertices[2] = new ExtendedVertex(btmRightFront, Color.White, Color.White, UVs.Uvs[2], UVs.Bounds[0]);
            Vertices[3] = new ExtendedVertex(topRightFront, Color.White, Color.White, UVs.Uvs[3], UVs.Bounds[0]);

            /*
             *  0 . . . 3
             *  .     . .
             *  .   .   .
             *  . .     .
             *  1 . . . 2
             */
            Indexes[0] = 0;
            Indexes[1] = 1;
            Indexes[2] = 3;
            Indexes[3] = 3;
            Indexes[4] = 1;
            Indexes[5] = 2;

            /*
             *  0 . . . 3
             *  . .     .
             *  .   .   .
             *  .     . .
             *  1 . . . 2
             */
            FlippedIndexes[0] = 0;
            FlippedIndexes[1] = 1;
            FlippedIndexes[2] = 2;
            FlippedIndexes[3] = 3;
            FlippedIndexes[4] = 0;
            FlippedIndexes[5] = 2;

            // Add the vertices for the BACK face.
            Vertices[4] = new ExtendedVertex(topRightBack, Color.White, Color.White, UVs.Uvs[4], UVs.Bounds[1]);
            Vertices[5] = new ExtendedVertex(btmRightBack, Color.White, Color.White, UVs.Uvs[5], UVs.Bounds[1]);
            Vertices[6] = new ExtendedVertex(btmLeftBack, Color.White, Color.White, UVs.Uvs[6], UVs.Bounds[1]);
            Vertices[7] = new ExtendedVertex(topLeftBack, Color.White, Color.White, UVs.Uvs[7], UVs.Bounds[1]);


            /*
             *  4 . . . 7
             *  .     . .
             *  .   .   .
             *  . .     .
             *  5 . . . 6
             */
            Indexes[6]  = 4;
            Indexes[7]  = 5;
            Indexes[8]  = 7;
            Indexes[9]  = 7;
            Indexes[10] = 5;
            Indexes[11] = 6;

            /*
             *  4 . . . 7
             *  . .     .
             *  .   .   .
             *  .     . .
             *  5 . . . 6
             */
            FlippedIndexes[6]  = 4;
            FlippedIndexes[7]  = 5;
            FlippedIndexes[8]  = 6;
            FlippedIndexes[9]  = 6;
            FlippedIndexes[10] = 7;
            FlippedIndexes[11] = 4;

            // Add the vertices for the TOP face.
            Vertices[8]  = new ExtendedVertex(topLeftBack, Color.White, Color.White, UVs.Uvs[8], UVs.Bounds[2]);
            Vertices[9]  = new ExtendedVertex(topLeftFront, Color.White, Color.White, UVs.Uvs[9], UVs.Bounds[2]);
            Vertices[10] = new ExtendedVertex(topRightFront, Color.White, Color.White, UVs.Uvs[10], UVs.Bounds[2]);
            Vertices[11] = new ExtendedVertex(topRightBack, Color.White, Color.White, UVs.Uvs[11], UVs.Bounds[2]);


            /*
             *  8 . . .11
             *  .     . .
             *  .   .   .
             *  .  .    .
             *  9 . . . 10
             */
            Indexes[12] = 8;
            Indexes[13] = 9;
            Indexes[14] = 11;
            Indexes[15] = 10;
            Indexes[16] = 11;
            Indexes[17] = 9;


            /*
             *  8 . . .11
             *  . .     .
             *  .   .   .
             *  .     . .
             *  9 . . .10
             */
            FlippedIndexes[12] = 8;
            FlippedIndexes[13] = 10;
            FlippedIndexes[14] = 11;
            FlippedIndexes[15] = 10;
            FlippedIndexes[16] = 8;
            FlippedIndexes[17] = 9;

            // Add the vertices for the BOTTOM face.
            Vertices[12] = new ExtendedVertex(btmLeftFront, Color.White, Color.White, UVs.Uvs[12], UVs.Bounds[3]);
            Vertices[13] = new ExtendedVertex(btmLeftBack, Color.White, Color.White, UVs.Uvs[13], UVs.Bounds[3]);
            Vertices[14] = new ExtendedVertex(btmRightBack, Color.White, Color.White, UVs.Uvs[14], UVs.Bounds[3]);
            Vertices[15] = new ExtendedVertex(btmRightFront, Color.White, Color.White, UVs.Uvs[15], UVs.Bounds[3]);


            /*
             *  12. . .15
             *  .     . .
             *  .   .   .
             *  .  .    .
             *  13. . .14
             */

            Indexes[18] = 12;
            Indexes[19] = 13;
            Indexes[20] = 15;
            Indexes[21] = 15;
            Indexes[22] = 13;
            Indexes[23] = 14;


            /*
             *  12. . .15
             *  . .     .
             *  .   .   .
             *  .     . .
             *  13. . .14
             */
            FlippedIndexes[18] = 12;
            FlippedIndexes[19] = 13;
            FlippedIndexes[20] = 14;
            FlippedIndexes[21] = 15;
            FlippedIndexes[22] = 12;
            FlippedIndexes[23] = 14;

            // Add the vertices for the LEFT face.
            Vertices[16] = new ExtendedVertex(topLeftBack, Color.White, Color.White, UVs.Uvs[16], UVs.Bounds[4]);
            Vertices[17] = new ExtendedVertex(btmLeftBack, Color.White, Color.White, UVs.Uvs[17], UVs.Bounds[4]);
            Vertices[18] = new ExtendedVertex(btmLeftFront, Color.White, Color.White, UVs.Uvs[18], UVs.Bounds[4]);
            Vertices[19] = new ExtendedVertex(topLeftFront, Color.White, Color.White, UVs.Uvs[19], UVs.Bounds[4]);

            /*
             *  16. . .19
             *  .     . .
             *  .   .   .
             *  .  .    .
             *  17. . .18
             */
            Indexes[24] = 16;
            Indexes[25] = 17;
            Indexes[26] = 19;
            Indexes[27] = 18;
            Indexes[28] = 19;
            Indexes[29] = 17;


            /*
             *  16. . .19
             *  . .     .
             *  .   .   .
             *  .     . .
             *  17. . .18
             */
            FlippedIndexes[24] = 16;
            FlippedIndexes[25] = 17;
            FlippedIndexes[26] = 18;
            FlippedIndexes[27] = 18;
            FlippedIndexes[28] = 19;
            FlippedIndexes[29] = 16;


            // Add the vertices for the RIGHT face.
            Vertices[20] = new ExtendedVertex(topRightFront, Color.White, Color.White, UVs.Uvs[20], UVs.Bounds[5]);
            Vertices[21] = new ExtendedVertex(btmRightFront, Color.White, Color.White, UVs.Uvs[21], UVs.Bounds[5]);
            Vertices[22] = new ExtendedVertex(btmRightBack, Color.White, Color.White, UVs.Uvs[22], UVs.Bounds[5]);
            Vertices[23] = new ExtendedVertex(topRightBack, Color.White, Color.White, UVs.Uvs[23], UVs.Bounds[5]);

            /*
             *  20. . .23
             *  .     . .
             *  .   .   .
             *  .  .    .
             *  21. . .22
             */
            Indexes[30] = 20;
            Indexes[31] = 21;
            Indexes[32] = 23;
            Indexes[33] = 23;
            Indexes[34] = 21;
            Indexes[35] = 22;

            /*
             *  20. . .23
             *  . .     .
             *  .   .   .
             *  .     . .
             *  21. . .22
             */
            FlippedIndexes[30] = 20;
            FlippedIndexes[31] = 21;
            FlippedIndexes[32] = 22;
            FlippedIndexes[33] = 23;
            FlippedIndexes[34] = 20;
            FlippedIndexes[35] = 22;

            try
            {
                IndexBuffer = new DynamicIndexBuffer(GameState.Game.GraphicsDevice, typeof(ushort), Indexes.Length, BufferUsage.WriteOnly);
                IndexBuffer.SetData(Indexes);
            }
            catch (Exception exception)
            {
                IndexBuffer = null;
            }

            Faces = new List <FaceDescriptor>
            {
                new FaceDescriptor
                {
                    Face         = BoxFace.Top,
                    VertexCount  = 4,
                    IndexCount   = 6,
                    IndexOffset  = 12,
                    VertexOffset = 8
                },
                new FaceDescriptor
                {
                    Face         = BoxFace.Bottom,
                    VertexCount  = 4,
                    IndexCount   = 6,
                    IndexOffset  = 18,
                    VertexOffset = 12
                },
                new FaceDescriptor
                {
                    Face         = BoxFace.Left,
                    VertexCount  = 4,
                    IndexCount   = 6,
                    IndexOffset  = 24,
                    VertexOffset = 16
                },
                new FaceDescriptor
                {
                    Face         = BoxFace.Right,
                    VertexCount  = 4,
                    IndexCount   = 6,
                    IndexOffset  = 30,
                    VertexOffset = 20
                },
                new FaceDescriptor
                {
                    Face         = BoxFace.Front,
                    VertexCount  = 4,
                    IndexCount   = 6,
                    IndexOffset  = 0,
                    VertexOffset = 0
                },
                new FaceDescriptor
                {
                    Face         = BoxFace.Back,
                    VertexCount  = 4,
                    IndexCount   = 6,
                    IndexOffset  = 6,
                    VertexOffset = 4
                },
            };
        }
Ejemplo n.º 21
0
        // SpriteManager
        public SpriteManager()
        {
        #if !RELEASE
            RasterizerState_WireFrame          = new RasterizerState();
            RasterizerState_WireFrame.FillMode = FillMode.WireFrame;
        #endif

            GraphicsDevice = _UI.Game.GraphicsDevice;

            PresentationParameters pp = GraphicsDevice.PresentationParameters;
            BackBufferSize = new Vector2(pp.BackBufferWidth, pp.BackBufferHeight);

            SpriteCountMax = _UI.Settings.Sprite_Count;
            Sprites        = new Sprite[SpriteCountMax];
            SpriteCount    = 0;
            CurrentSprite  = 0;

            HasBatched = new bool[_UI.Settings.Sprite_RenderPassCount];

            TopLayer = _UI.Settings.Sprite_LayerCount - 1;

            RenderPassLayerSprites = new List <List <int>[]>(_UI.Settings.Sprite_RenderPassCount);
            RenderPass3dMask       = _UI.Settings.Sprite_RenderPass3dMask;

            for (int i = 0; i < _UI.Settings.Sprite_RenderPassCount; ++i)
            {
                List <int>[] layerSprites = new List <int> [_UI.Settings.Sprite_LayerCount];

                for (int j = 0; j < layerSprites.Length; ++j)
                {
                    layerSprites[j] = new List <int>();
                }

                RenderPassLayerSprites.Add(layerSprites);
            }

            PreMatrixPool  = new Matrix[_UI.Settings.Sprite_PreMatrixCount];
            PreMatrixCount = 0;

            PostMatrixPool  = new Matrix[_UI.Settings.Sprite_PostMatrixCount];
            PostMatrixCount = 0;

            Matrix identity = Matrix.Identity;

            // reserve identity
            StorePreMatrix(ref identity);
            StorePostMatrix(ref identity);

            RenderStatePool  = new object[_UI.Settings.Sprite_RenderStateCount];
            RenderStateCount = 0;

            // default renderstates
            StoreRenderState(DepthStencilState.None);
            StoreRenderState(RasterizerState.CullNone);

            RenderStateStack_Blend        = new Stack <int>(_UI.Settings.Sprite_RenderStateStackCount);
            RenderStateStack_DepthStencil = new Stack <int>(_UI.Settings.Sprite_RenderStateStackCount);
            RenderStateStack_Rasterizer   = new Stack <int>(_UI.Settings.Sprite_RenderStateStackCount);

            VertexCorners = new Vector2[VertexCount]
            {
                new Vector2(0.0f, 0.0f),
                new Vector2(1.0f, 0.0f),
                new Vector2(1.0f, 1.0f),
                new Vector2(0.0f, 1.0f),
            };

            VertexCornersFlipped = new Vector2[VertexCount]
            {
                new Vector2(0.0f, 1.0f),
                new Vector2(1.0f, 1.0f),
                new Vector2(1.0f, 0.0f),
                new Vector2(0.0f, 0.0f),
            };

            VertexOffsetAligned = new Vector2[(int)E_Align.Count]
            {
                new Vector2(0.0f, 0.0f),           // None
                new Vector2(0.0f, 0.0f),           // TopLeft
                new Vector2(0.5f, 0.0f),           // TopCentre
                new Vector2(1.0f, 0.0f),           // TopRight
                new Vector2(0.0f, 0.5f),           // MiddleLeft
                new Vector2(0.5f, 0.5f),           // MiddleCentre
                new Vector2(1.0f, 0.5f),           // MiddleRight
                new Vector2(0.0f, 1.0f),           // BottomLeft
                new Vector2(0.5f, 1.0f),           // BottomCentre
                new Vector2(1.0f, 1.0f),           // BottomRight
            };

            VertexOffsetAlignedFlipped = new Vector2[(int)E_Align.Count]
            {
                new Vector2(0.0f, 1.0f),           // None
                new Vector2(0.0f, 1.0f),           // TopLeft
                new Vector2(0.5f, 1.0f),           // TopCentre
                new Vector2(1.0f, 1.0f),           // TopRight
                new Vector2(0.0f, 0.5f),           // MiddleLeft
                new Vector2(0.5f, 0.5f),           // MiddleCentre
                new Vector2(1.0f, 0.5f),           // MiddleRight
                new Vector2(0.0f, 0.0f),           // BottomLeft
                new Vector2(0.5f, 0.0f),           // BottomCentre
                new Vector2(1.0f, 0.0f),           // BottomRight
            };

            VertexCornersAligned = new Vector3[(int)E_Align.Count][];

            for (int i = 0; i < VertexCornersAligned.Length; ++i)
            {
                VertexCornersAligned[i] = new Vector3[VertexCount];
            }

            VertexCornersAlignedFlipped = new Vector3[(int)E_Align.Count][];

            for (int i = 0; i < VertexCornersAlignedFlipped.Length; ++i)
            {
                VertexCornersAlignedFlipped[i] = new Vector3[VertexCount];
            }

            for (int i = 0; i < (int)E_Align.Count; ++i)
            {
                for (int j = 0; j < VertexCount; ++j)
                {
                    VertexCornersAligned[i][j]        = new Vector3(VertexCorners[j] - VertexOffsetAligned[i], 0.0f);
                    VertexCornersAlignedFlipped[i][j] = new Vector3(VertexCornersFlipped[j] - VertexOffsetAlignedFlipped[i], 0.0f);
                }
            }

            TransformMatrix2D = Matrix.CreateTranslation(-0.5f, -0.5f, 0.0f) * Matrix.CreateOrthographicOffCenter(0.0f, pp.BackBufferWidth, pp.BackBufferHeight, 0.0f, -1500.0f, 1500.0f);
            TransformMatrix   = TransformMatrix2D;   // default

            RenderPassTransformMatrix = new Matrix[_UI.Settings.Sprite_RenderPassCount];

            for (int i = 0; i < RenderPassTransformMatrix.Length; ++i)
            {
                RenderPassTransformMatrix[i] = Matrix.Identity;
            }

            AutoTransformIndex  = 0;
            AutoTransformOffset = new Vector3();

            VertexData     = new VertexSprite[VertexCount * SpriteCountMax];
            VertexPosition = 0;

            DynamicVB = new DynamicVertexBuffer(GraphicsDevice, VertexSprite.VertexDeclaration, SpriteCountMax * VertexCount, BufferUsage.WriteOnly);

        #if WINDOWS
            DynamicVB.ContentLost += ((sender, e) => { VertexPosition = 0; });
        #endif

            short   primitiveCount = 0;
            short[] dataIB         = new short[SpriteCountMax * IndexCount];

            for (int i = 0; i < dataIB.Length;)
            {
                short offset = (short)(primitiveCount * VertexCount);

                dataIB[i++] = (short)(0 + offset);
                dataIB[i++] = (short)(1 + offset);
                dataIB[i++] = (short)(2 + offset);
                dataIB[i++] = (short)(2 + offset);
                dataIB[i++] = (short)(3 + offset);
                dataIB[i++] = (short)(0 + offset);

                ++primitiveCount;
            }

            DynamicIB = new DynamicIndexBuffer(GraphicsDevice, IndexElementSize.SixteenBits, SpriteCountMax * IndexCount, BufferUsage.WriteOnly);
            DynamicIB.SetData(dataIB);

        #if WINDOWS
            DataIB = dataIB;
            DynamicIB.ContentLost += ((sender, e) => { DynamicIB.SetData(DataIB); });
        #endif
        }
Ejemplo n.º 22
0
        private void CalculateLightVertices(List <Vector2> rayCastHits)
        {
            List <VertexPositionTexture> vertices = new List <VertexPositionTexture>();

            Vector2 drawPos = position;

            if (ParentSub != null)
            {
                drawPos += ParentSub.DrawPosition;
            }

            float cosAngle = (float)Math.Cos(Rotation);
            float sinAngle = -(float)Math.Sin(Rotation);

            Vector2 uvOffset            = Vector2.Zero;
            Vector2 overrideTextureDims = Vector2.One;

            if (overrideLightTexture != null)
            {
                overrideTextureDims = new Vector2(overrideLightTexture.SourceRect.Width, overrideLightTexture.SourceRect.Height);
                uvOffset            = (overrideLightTexture.Origin / overrideTextureDims) - new Vector2(0.5f, 0.5f);
            }

            // Add a vertex for the center of the mesh
            vertices.Add(new VertexPositionTexture(new Vector3(position.X, position.Y, 0),
                                                   new Vector2(0.5f, 0.5f) + uvOffset));

            // Add all the other encounter points as vertices
            // storing their world position as UV coordinates
            foreach (Vector2 vertex in rayCastHits)
            {
                Vector2 rawDiff = vertex - drawPos;
                Vector2 diff    = rawDiff;
                diff /= range * 2.0f;
                if (overrideLightTexture != null)
                {
                    Vector2 originDiff = diff;

                    diff.X = originDiff.X * cosAngle - originDiff.Y * sinAngle;
                    diff.Y = originDiff.X * sinAngle + originDiff.Y * cosAngle;
                    diff  *= (overrideTextureDims / overrideLightTexture.size) * 2.0f;

                    diff += uvOffset;
                }

                vertices.Add(new VertexPositionTexture(new Vector3(position.X + rawDiff.X, position.Y + rawDiff.Y, 0),
                                                       new Vector2(0.5f, 0.5f) + diff));
            }

            // Compute the indices to form triangles
            List <short> indices = new List <short>();

            for (int i = 0; i < rayCastHits.Count - 1; i++)
            {
                indices.Add(0);
                indices.Add((short)((i + 2) % vertices.Count));
                indices.Add((short)((i + 1) % vertices.Count));
            }

            indices.Add(0);
            indices.Add((short)(1));
            indices.Add((short)(vertices.Count - 1));

            vertexCount = vertices.Count;
            indexCount  = indices.Count;

            //TODO: a better way to determine the size of the vertex buffer and handle changes in size?
            //now we just create a buffer for 64 verts and make it larger if needed
            if (lightVolumeBuffer == null)
            {
                lightVolumeBuffer      = new DynamicVertexBuffer(GameMain.Instance.GraphicsDevice, VertexPositionTexture.VertexDeclaration, Math.Max(64, (int)(vertexCount * 1.5)), BufferUsage.None);
                lightVolumeIndexBuffer = new DynamicIndexBuffer(GameMain.Instance.GraphicsDevice, typeof(short), Math.Max(64 * 3, (int)(indexCount * 1.5)), BufferUsage.None);
            }
            else if (vertexCount > lightVolumeBuffer.VertexCount)
            {
                lightVolumeBuffer.Dispose();
                lightVolumeIndexBuffer.Dispose();

                lightVolumeBuffer      = new DynamicVertexBuffer(GameMain.Instance.GraphicsDevice, VertexPositionTexture.VertexDeclaration, (int)(vertexCount * 1.5), BufferUsage.None);
                lightVolumeIndexBuffer = new DynamicIndexBuffer(GameMain.Instance.GraphicsDevice, typeof(short), (int)(indexCount * 1.5), BufferUsage.None);
            }

            lightVolumeBuffer.SetData <VertexPositionTexture>(vertices.ToArray());
            lightVolumeIndexBuffer.SetData <short>(indices.ToArray());
        }
Ejemplo n.º 23
0
        public override void UpdateGeometry(GraphicsDevice device)
        {
            rand = new Random(Seed);

            List <Branch> branches = new List <Branch>();
            List <Leaf>   leaves   = new List <Leaf>();

            float step = .4f;

            float max = step + MathHelper.Clamp(1f - TimeLeft / TimeToMature, 0, 1) * (height - step);

            branches.Add(new Branch(Vector3.Zero, Matrix.CreateRotationX(MathHelper.PiOver2), step));
            Vector3 last = new Vector3(0, step, 0);
            float   h    = step;

            while (h < max)
            {
                float y = Math.Min(max, h + step) - h;
                for (float i = 0; i < MathHelper.TwoPi;)
                {
                    leaves.Add(new Leaf(last + new Vector3(0, step * (float)rand.NextDouble(), 0),
                                        Matrix.CreateRotationX((float)rand.NextDouble() * MathHelper.PiOver2 * .5f) * Matrix.CreateRotationY(i),
                                        .3f + (float)rand.NextDouble() * .3f));

                    i += .5f + (float)rand.NextDouble() * 2;
                }
                Branch b = new Branch(last, Matrix.CreateRotationX(MathHelper.PiOver2), y);
                branches.Add(b);
                last = b.End;
                h   += y;
            }

            List <VertexPositionColorNormal> verts = new List <VertexPositionColorNormal>();
            List <int> tris  = new List <int>();
            float      r     = .05f;
            int        sides = 6;

            #region branch geometry
            foreach (Branch b in branches)
            {
                float x1       = b.Start.Y / max,
                            x2 = b.End.Y / max;
                float r1       = r * MathHelper.Clamp(-(float)Math.Pow(x1, 7) + 1, 0, 1);
                float r2       = r * MathHelper.Clamp(-(float)Math.Pow(x2, 7) + 1, 0, 1);

                int bi = verts.Count;
                for (int s = 0; s < sides; s++)
                {
                    Matrix m = b.Direction * Matrix.CreateRotationY((s / (float)sides) * MathHelper.TwoPi);
                    verts.Add(new VertexPositionColorNormal(b.Start + m.Up * r1, Color.Green, m.Up));
                    verts.Add(new VertexPositionColorNormal(b.End + m.Up * r2, Color.Green, m.Up));
                }

                // cap on final branch
                if (b.Equals(branches[branches.Count - 1]))
                {
                    verts.Add(new VertexPositionColorNormal(b.End + b.Direction.Forward * .15f, Color.Green, b.Direction.Forward));
                }

                for (int i = 0; i < sides * 2; i += 2)
                {
                    int i0 = i,
                        i1 = i + 1,
                        i2 = (i + 2) % (sides * 2),
                        i3 = (i + 3) % (sides * 2);
                    tris.AddRange(new int[] {
                        bi + i0, bi + i3, bi + i2,
                        bi + i0, bi + i1, bi + i3
                    });

                    // cap on final branch
                    if (b.Equals(branches[branches.Count - 1]))
                    {
                        tris.AddRange(new int[] {
                            verts.Count - 1, bi + i3, bi + i1
                        });
                    }
                }
            }
            #endregion

            #region leaf generation
            foreach (Leaf l in leaves)
            {
                if (l.Position.Y < max * .75f)
                {
                    float scale = MathHelper.Clamp(max / height, 0, 1);

                    // do twice (top & bottom)
                    for (int x = 0; x < 2; x++)
                    {
                        int     bi = verts.Count;
                        Matrix  m  = l.Direction;
                        Vector3 p  = l.Position;
                        for (int i = 0; i < 3; i++)
                        {
                            float d = r;
                            if (i == 0)
                            {
                                d *= .6f;
                            }
                            else if (i == 1)
                            {
                                d *= 1.1f;
                            }

                            if (x == 0)
                            {
                                verts.Add(new VertexPositionColorNormal(p + m.Left * d * scale, Color.Green, m.Up));
                                verts.Add(new VertexPositionColorNormal(p + m.Right * d * scale, Color.Green, m.Up));
                            }
                            else
                            {
                                verts.Add(new VertexPositionColorNormal(p + m.Right * d * scale, Color.Green, m.Down));
                                verts.Add(new VertexPositionColorNormal(p + m.Left * d * scale, Color.Green, m.Down));
                            }

                            m *= Matrix.CreateRotationX(l.Drop * .3333f * scale);
                            p += m.Forward * 2 * r * scale;
                        }
                        if (x == 0)
                        {
                            verts.Add(new VertexPositionColorNormal(p + m.Forward * r * scale, Color.Green, m.Up));
                        }
                        else
                        {
                            verts.Add(new VertexPositionColorNormal(p + m.Forward * r * scale, Color.Green, m.Down));
                        }

                        tris.AddRange(new int[] {
                            bi, bi + 2, bi + 1, bi + 1, bi + 2, bi + 3,
                            bi + 2, bi + 4, bi + 3, bi + 3, bi + 4, bi + 5,
                            bi + 4, bi + 6, bi + 5
                        });
                    }
                }
            }
            #endregion

            // set data
            //if (VBuffer == null)
            VBuffer = new DynamicVertexBuffer(device, typeof(VertexPositionColorNormal), verts.Count, BufferUsage.WriteOnly);
            VBuffer.SetData(verts.ToArray());

            //if (IBuffer == null)
            IBuffer = new DynamicIndexBuffer(device, typeof(int), tris.Count, BufferUsage.WriteOnly);
            IBuffer.SetData(tris.ToArray());
        }
Ejemplo n.º 24
0
 public void SetIndices(short[] indices)
 {
     indexBuffer.SetData(0, indices, 0, indices.Length, SetDataOptions.Discard);
 }
Ejemplo n.º 25
0
        private void CalculateLightVertices(List <Vector2> rayCastHits)
        {
            vertexCount = rayCastHits.Count * 2 + 1;
            indexCount  = (rayCastHits.Count) * 9;

            //recreate arrays if they're too small or excessively large
            if (vertices == null || vertices.Length < vertexCount || vertices.Length > vertexCount * 3)
            {
                vertices = new VertexPositionColorTexture[vertexCount];
                indices  = new short[indexCount];
            }

            Vector2 drawPos = position;

            if (ParentSub != null)
            {
                drawPos += ParentSub.DrawPosition;
            }

            float cosAngle = (float)Math.Cos(Rotation);
            float sinAngle = -(float)Math.Sin(Rotation);

            Vector2 uvOffset            = Vector2.Zero;
            Vector2 overrideTextureDims = Vector2.One;

            if (OverrideLightTexture != null)
            {
                overrideTextureDims = new Vector2(OverrideLightTexture.SourceRect.Width, OverrideLightTexture.SourceRect.Height);

                Vector2 origin = OverrideLightTexture.Origin;
                if (LightSpriteEffect == SpriteEffects.FlipHorizontally)
                {
                    origin.X = OverrideLightTexture.SourceRect.Width - origin.X;
                }
                if (LightSpriteEffect == SpriteEffects.FlipVertically)
                {
                    origin.Y = OverrideLightTexture.SourceRect.Height - origin.Y;
                }
                uvOffset = (origin / overrideTextureDims) - new Vector2(0.5f, 0.5f);
            }

            // Add a vertex for the center of the mesh
            vertices[0] = new VertexPositionColorTexture(new Vector3(position.X, position.Y, 0),
                                                         Color.White, GetUV(new Vector2(0.5f, 0.5f) + uvOffset, LightSpriteEffect));

            //hacky fix to exc excessively large light volumes (they used to be up to 4x the range of the light if there was nothing to block the rays).
            //might want to tweak the raycast logic in a way that this isn't necessary
            float     boundRadius = Range * 1.1f / (1.0f - Math.Max(Math.Abs(uvOffset.X), Math.Abs(uvOffset.Y)));
            Rectangle boundArea   = new Rectangle((int)(drawPos.X - boundRadius), (int)(drawPos.Y + boundRadius), (int)(boundRadius * 2), (int)(boundRadius * 2));

            for (int i = 0; i < rayCastHits.Count; i++)
            {
                if (MathUtils.GetLineRectangleIntersection(drawPos, rayCastHits[i], boundArea, out Vector2 intersection))
                {
                    rayCastHits[i] = intersection;
                }
            }

            // Add all the other encounter points as vertices
            // storing their world position as UV coordinates
            for (int i = 0; i < rayCastHits.Count; i++)
            {
                Vector2 vertex = rayCastHits[i];

                //we'll use the previous and next vertices to calculate the normals
                //of the two segments this vertex belongs to
                //so we can add new vertices based on these normals
                Vector2 prevVertex = rayCastHits[i > 0 ? i - 1 : rayCastHits.Count - 1];
                Vector2 nextVertex = rayCastHits[i < rayCastHits.Count - 1 ? i + 1 : 0];

                Vector2 rawDiff = vertex - drawPos;

                //calculate normal of first segment
                Vector2 nDiff1 = vertex - nextVertex;
                float   tx     = nDiff1.X; nDiff1.X = -nDiff1.Y; nDiff1.Y = tx;
                nDiff1 /= Math.Max(Math.Abs(nDiff1.X), Math.Abs(nDiff1.Y));
                //if the normal is pointing towards the light origin
                //rather than away from it, invert it
                if (Vector2.DistanceSquared(nDiff1, rawDiff) > Vector2.DistanceSquared(-nDiff1, rawDiff))
                {
                    nDiff1 = -nDiff1;
                }

                //calculate normal of second segment
                Vector2 nDiff2 = prevVertex - vertex;
                tx      = nDiff2.X; nDiff2.X = -nDiff2.Y; nDiff2.Y = tx;
                nDiff2 /= Math.Max(Math.Abs(nDiff2.X), Math.Abs(nDiff2.Y));
                //if the normal is pointing towards the light origin
                //rather than away from it, invert it
                if (Vector2.DistanceSquared(nDiff2, rawDiff) > Vector2.DistanceSquared(-nDiff2, rawDiff))
                {
                    nDiff2 = -nDiff2;
                }

                //add the normals together and use some magic numbers to create
                //a somewhat useful/good-looking blur
                Vector2 nDiff = nDiff1 + nDiff2;
                nDiff /= Math.Max(Math.Abs(nDiff.X), Math.Abs(nDiff.Y));
                nDiff *= 50.0f;

                Vector2 diff = rawDiff;
                diff /= Range * 2.0f;
                if (OverrideLightTexture != null)
                {
                    //calculate texture coordinates based on the light's rotation
                    Vector2 originDiff = diff;

                    diff.X = originDiff.X * cosAngle - originDiff.Y * sinAngle;
                    diff.Y = originDiff.X * sinAngle + originDiff.Y * cosAngle;
                    diff  *= (overrideTextureDims / OverrideLightTexture.size);// / (1.0f - Math.Max(Math.Abs(uvOffset.X), Math.Abs(uvOffset.Y)));
                    diff  += uvOffset;
                }

                //finally, create the vertices
                VertexPositionColorTexture fullVert = new VertexPositionColorTexture(new Vector3(position.X + rawDiff.X, position.Y + rawDiff.Y, 0),
                                                                                     Color.White, GetUV(new Vector2(0.5f, 0.5f) + diff, LightSpriteEffect));
                VertexPositionColorTexture fadeVert = new VertexPositionColorTexture(new Vector3(position.X + rawDiff.X + nDiff.X, position.Y + rawDiff.Y + nDiff.Y, 0),
                                                                                     Color.White * 0.0f, GetUV(new Vector2(0.5f, 0.5f) + diff, LightSpriteEffect));

                vertices[1 + i * 2]     = fullVert;
                vertices[1 + i * 2 + 1] = fadeVert;
            }

            // Compute the indices to form triangles
            for (int i = 0; i < rayCastHits.Count - 1; i++)
            {
                //main light body
                indices[i * 9]     = 0;
                indices[i * 9 + 1] = (short)((i * 2 + 3) % vertexCount);
                indices[i * 9 + 2] = (short)((i * 2 + 1) % vertexCount);

                //faded light
                indices[i * 9 + 3] = (short)((i * 2 + 1) % vertexCount);
                indices[i * 9 + 4] = (short)((i * 2 + 3) % vertexCount);
                indices[i * 9 + 5] = (short)((i * 2 + 4) % vertexCount);

                indices[i * 9 + 6] = (short)((i * 2 + 2) % vertexCount);
                indices[i * 9 + 7] = (short)((i * 2 + 1) % vertexCount);
                indices[i * 9 + 8] = (short)((i * 2 + 4) % vertexCount);
            }

            //main light body
            indices[(rayCastHits.Count - 1) * 9]     = 0;
            indices[(rayCastHits.Count - 1) * 9 + 1] = (short)(1);
            indices[(rayCastHits.Count - 1) * 9 + 2] = (short)(vertexCount - 2);

            //faded light
            indices[(rayCastHits.Count - 1) * 9 + 3] = (short)(1);
            indices[(rayCastHits.Count - 1) * 9 + 4] = (short)(vertexCount - 1);
            indices[(rayCastHits.Count - 1) * 9 + 5] = (short)(vertexCount - 2);

            indices[(rayCastHits.Count - 1) * 9 + 6] = (short)(1);
            indices[(rayCastHits.Count - 1) * 9 + 7] = (short)(2);
            indices[(rayCastHits.Count - 1) * 9 + 8] = (short)(vertexCount - 1);

            //TODO: a better way to determine the size of the vertex buffer and handle changes in size?
            //now we just create a buffer for 64 verts and make it larger if needed
            if (lightVolumeBuffer == null)
            {
                lightVolumeBuffer      = new DynamicVertexBuffer(GameMain.Instance.GraphicsDevice, VertexPositionColorTexture.VertexDeclaration, Math.Max(64, (int)(vertexCount * 1.5)), BufferUsage.None);
                lightVolumeIndexBuffer = new DynamicIndexBuffer(GameMain.Instance.GraphicsDevice, typeof(short), Math.Max(64 * 3, (int)(indexCount * 1.5)), BufferUsage.None);
            }
            else if (vertexCount > lightVolumeBuffer.VertexCount || indexCount > lightVolumeIndexBuffer.IndexCount)
            {
                lightVolumeBuffer.Dispose();
                lightVolumeIndexBuffer.Dispose();

                lightVolumeBuffer      = new DynamicVertexBuffer(GameMain.Instance.GraphicsDevice, VertexPositionColorTexture.VertexDeclaration, (int)(vertexCount * 1.5), BufferUsage.None);
                lightVolumeIndexBuffer = new DynamicIndexBuffer(GameMain.Instance.GraphicsDevice, typeof(short), (int)(indexCount * 1.5), BufferUsage.None);
            }

            lightVolumeBuffer.SetData <VertexPositionColorTexture>(vertices, 0, vertexCount);
            lightVolumeIndexBuffer.SetData <short>(indices, 0, indexCount);

            Vector2 GetUV(Vector2 vert, SpriteEffects effects)
            {
                if (effects == SpriteEffects.FlipHorizontally)
                {
                    vert.X = 1.0f - vert.X;
                }
                else if (effects == SpriteEffects.FlipVertically)
                {
                    vert.Y = 1.0f - vert.Y;
                }
                else if (effects == (SpriteEffects.FlipHorizontally | SpriteEffects.FlipVertically))
                {
                    vert.X = 1.0f - vert.X;
                    vert.Y = 1.0f - vert.Y;
                }
                vert.Y = 1.0f - vert.Y;
                return(vert);
            }

            translateVertices      = Vector2.Zero;
            rotateVertices         = 0.0f;
            prevCalculatedPosition = position;
            prevCalculatedRotation = rotation;
        }
Ejemplo n.º 26
0
        public void Setup(int columns, int rows, Size tileSize)
        {
            if (Columns == columns && Rows == rows && TileSize == tileSize)
            {
                return;
            }

            Columns  = columns;
            Rows     = rows;
            TileSize = tileSize;
            Size     = new Size(Columns, Rows) * tileSize;

            if (Columns == 0 || Rows == 0)
            {
                return;
            }

            VertexPositionColor[] vertices = new VertexPositionColor[(Columns + Rows) * 2];
            int[] indices = new int[vertices.Length + 4];


            if (_vertexBuffer == null || vertices.Length > _vertexBuffer.VertexCount)
            {
                _vertexBuffer = new DynamicVertexBuffer(Game.Instance.GraphicsDevice, VertexPositionColor.VertexDeclaration, vertices.Length, BufferUsage.WriteOnly);
            }

            if (_indexBuffer == null || indices.Length > _indexBuffer.IndexCount)
            {
                _indexBuffer = new DynamicIndexBuffer(Game.Instance.GraphicsDevice, IndexElementSize.ThirtyTwoBits, indices.Length, BufferUsage.WriteOnly);
            }

            //
            // Vertices layout:
            //
            //(n-4)--4----6--(n-3)
            //  |    |    |    |
            //  |    |    |    |
            //  0----+----+----1
            //  |    |    |    |
            //  |    |    |    |
            //  2----+----+----3
            //  |    |    |    |
            //  |    |    |    |
            //(n-1)--5----7--(n-2)
            //

            int id = 0; // vertex/index id

            for (int row = 1; row < Rows; row++, id += 2)
            {
                vertices[id]     = new VertexPositionColor(new Microsoft.Xna.Framework.Vector3(0f, row * TileSize.Height, 0f), Color.White);
                vertices[id + 1] = new VertexPositionColor(new Microsoft.Xna.Framework.Vector3(Columns * TileSize.Width, row * TileSize.Height, 0f), Color.White);
                indices[id]      = id;
                indices[id + 1]  = id + 1;
            }

            for (int column = 1; column < Columns; column++, id += 2)
            {
                vertices[id]     = new VertexPositionColor(new Microsoft.Xna.Framework.Vector3(column * TileSize.Width, 0f, 0f), Color.White);
                vertices[id + 1] = new VertexPositionColor(new Microsoft.Xna.Framework.Vector3(column * TileSize.Width, Rows * TileSize.Height, 0f), Color.White);
                indices[id]      = id;
                indices[id + 1]  = id + 1;
            }

            // top-left
            vertices[id] = new VertexPositionColor(Microsoft.Xna.Framework.Vector3.Zero, Color.White);

            // top-right
            vertices[id + 1] = new VertexPositionColor(new Microsoft.Xna.Framework.Vector3(Columns * TileSize.Width, 0f, 0f), Color.White);

            // bottom-right
            vertices[id + 2] = new VertexPositionColor(new Microsoft.Xna.Framework.Vector3(Columns * TileSize.Width, Rows * TileSize.Height, 0f), Color.White);

            // bottom-left
            vertices[id + 3] = new VertexPositionColor(new Microsoft.Xna.Framework.Vector3(0f, Rows * TileSize.Height, 0f), Color.White);

            // top border
            indices[id]     = 0;
            indices[id + 1] = 1;

            // right border
            indices[id + 2] = 1;
            indices[id + 3] = 2;

            // bottom border
            indices[id + 4] = 2;
            indices[id + 5] = 3;

            // left border
            indices[id + 6] = 3;
            indices[id + 7] = 0;

            _usingVerticesCount = vertices.Length;
            _usingIndicesCount  = indices.Length;

            _vertexBuffer.SetData(vertices, 0, vertices.Length, SetDataOptions.Discard);
            _indexBuffer.SetData(indices, 0, indices.Length, SetDataOptions.Discard);
        }
Ejemplo n.º 27
0
 private void dynIndexBuffer_ContentLost(object sender, EventArgs e)
 {
     dynTerrainIndexBuffer.Dispose();
     dynTerrainIndexBuffer.SetData(indicesList.ToArray(), 0, indicesList.Count, SetDataOptions.Discard);
 }
Ejemplo n.º 28
0
        private void CalculateLightVertices(List <Vector2> rayCastHits)
        {
            List <VertexPositionColorTexture> vertices = new List <VertexPositionColorTexture>();

            Vector2 drawPos = position;

            if (ParentSub != null)
            {
                drawPos += ParentSub.DrawPosition;
            }

            float cosAngle = (float)Math.Cos(Rotation);
            float sinAngle = -(float)Math.Sin(Rotation);

            Vector2 uvOffset            = Vector2.Zero;
            Vector2 overrideTextureDims = Vector2.One;

            if (overrideLightTexture != null)
            {
                overrideTextureDims = new Vector2(overrideLightTexture.SourceRect.Width, overrideLightTexture.SourceRect.Height);
                uvOffset            = (overrideLightTexture.Origin / overrideTextureDims) - new Vector2(0.5f, 0.5f);
            }

            // Add a vertex for the center of the mesh
            vertices.Add(new VertexPositionColorTexture(new Vector3(position.X, position.Y, 0),
                                                        Color.White, new Vector2(0.5f, 0.5f) + uvOffset));

            // Add all the other encounter points as vertices
            // storing their world position as UV coordinates
            for (int i = 0; i < rayCastHits.Count; i++)
            {
                Vector2 vertex = rayCastHits[i];

                //we'll use the previous and next vertices to calculate the normals
                //of the two segments this vertex belongs to
                //so we can add new vertices based on these normals
                Vector2 prevVertex = rayCastHits[i > 0 ? i - 1 : rayCastHits.Count - 1];
                Vector2 nextVertex = rayCastHits[i < rayCastHits.Count - 1 ? i + 1 : 0];

                Vector2 rawDiff = vertex - drawPos;
                Vector2 diff    = rawDiff;
                diff /= range * 2.0f;
                if (overrideLightTexture != null)
                {
                    //calculate texture coordinates based on the light's rotation
                    Vector2 originDiff = diff;

                    diff.X = originDiff.X * cosAngle - originDiff.Y * sinAngle;
                    diff.Y = originDiff.X * sinAngle + originDiff.Y * cosAngle;
                    diff  *= (overrideTextureDims / overrideLightTexture.size) * 2.0f;

                    diff += uvOffset;
                }

                //calculate normal of first segment
                Vector2 nDiff1 = vertex - nextVertex;
                float   tx     = nDiff1.X; nDiff1.X = -nDiff1.Y; nDiff1.Y = tx;
                nDiff1 /= Math.Max(Math.Abs(nDiff1.X), Math.Abs(nDiff1.Y));
                //if the normal is pointing towards the light origin
                //rather than away from it, invert it
                if (Vector2.DistanceSquared(nDiff1, rawDiff) > Vector2.DistanceSquared(-nDiff1, rawDiff))
                {
                    nDiff1 = -nDiff1;
                }

                //calculate normal of second segment
                Vector2 nDiff2 = prevVertex - vertex;
                tx      = nDiff2.X; nDiff2.X = -nDiff2.Y; nDiff2.Y = tx;
                nDiff2 /= Math.Max(Math.Abs(nDiff2.X), Math.Abs(nDiff2.Y));
                //if the normal is pointing towards the light origin
                //rather than away from it, invert it
                if (Vector2.DistanceSquared(nDiff2, rawDiff) > Vector2.DistanceSquared(-nDiff2, rawDiff))
                {
                    nDiff2 = -nDiff2;
                }

                //add the normals together and use some magic numbers to create
                //a somewhat useful/good-looking blur
                Vector2 nDiff = nDiff1 + nDiff2;
                nDiff /= Math.Max(Math.Abs(nDiff.X), Math.Abs(nDiff.Y));
                nDiff *= 50.0f;

                //finally, create the vertices
                VertexPositionColorTexture fullVert = new VertexPositionColorTexture(new Vector3(position.X + rawDiff.X, position.Y + rawDiff.Y, 0),
                                                                                     Color.White, new Vector2(0.5f, 0.5f) + diff);
                VertexPositionColorTexture fadeVert = new VertexPositionColorTexture(new Vector3(position.X + rawDiff.X + nDiff.X, position.Y + rawDiff.Y + nDiff.Y, 0),
                                                                                     Color.White * 0.0f, new Vector2(0.5f, 0.5f) + diff);

                vertices.Add(fullVert);
                vertices.Add(fadeVert);
            }

            // Compute the indices to form triangles
            List <short> indices = new List <short>();

            for (int i = 0; i < rayCastHits.Count - 1; i++)
            {
                //main light body
                indices.Add(0);
                indices.Add((short)((i * 2 + 3) % vertices.Count));
                indices.Add((short)((i * 2 + 1) % vertices.Count));

                //faded light
                indices.Add((short)((i * 2 + 1) % vertices.Count));
                indices.Add((short)((i * 2 + 3) % vertices.Count));
                indices.Add((short)((i * 2 + 4) % vertices.Count));

                indices.Add((short)((i * 2 + 2) % vertices.Count));
                indices.Add((short)((i * 2 + 1) % vertices.Count));
                indices.Add((short)((i * 2 + 4) % vertices.Count));
            }

            //main light body
            indices.Add(0);
            indices.Add((short)(1));
            indices.Add((short)(vertices.Count - 2));

            //faded light
            indices.Add((short)(1));
            indices.Add((short)(vertices.Count - 1));
            indices.Add((short)(vertices.Count - 2));

            indices.Add((short)(1));
            indices.Add((short)(2));
            indices.Add((short)(vertices.Count - 1));

            vertexCount = vertices.Count;
            indexCount  = indices.Count;

            //TODO: a better way to determine the size of the vertex buffer and handle changes in size?
            //now we just create a buffer for 64 verts and make it larger if needed
            if (lightVolumeBuffer == null)
            {
                lightVolumeBuffer      = new DynamicVertexBuffer(GameMain.Instance.GraphicsDevice, VertexPositionColorTexture.VertexDeclaration, Math.Max(64, (int)(vertexCount * 1.5)), BufferUsage.None);
                lightVolumeIndexBuffer = new DynamicIndexBuffer(GameMain.Instance.GraphicsDevice, typeof(short), Math.Max(64 * 3, (int)(indexCount * 1.5)), BufferUsage.None);
            }
            else if (vertexCount > lightVolumeBuffer.VertexCount || indexCount > lightVolumeIndexBuffer.IndexCount)
            {
                lightVolumeBuffer.Dispose();
                lightVolumeIndexBuffer.Dispose();

                lightVolumeBuffer      = new DynamicVertexBuffer(GameMain.Instance.GraphicsDevice, VertexPositionColorTexture.VertexDeclaration, (int)(vertexCount * 1.5), BufferUsage.None);
                lightVolumeIndexBuffer = new DynamicIndexBuffer(GameMain.Instance.GraphicsDevice, typeof(short), (int)(indexCount * 1.5), BufferUsage.None);
            }

            lightVolumeBuffer.SetData <VertexPositionColorTexture>(vertices.ToArray());
            lightVolumeIndexBuffer.SetData <short>(indices.ToArray());
        }
Ejemplo n.º 29
0
        private void DrawBatch(DrawingContext context, ref PrimitiveGroupEntry entry, Material material)
        {
            if (entry.VertexCount <= 0 && entry.IndexCount <= 0)
            {
                return;
            }

            material.texture = entry.Texture;
            material.world   = entry.World.HasValue ? entry.World.Value * AbsoluteTransform : AbsoluteTransform;
            material.BeginApply(context);

#if !WINDOWS_PHONE
            if (entry.LineWidth > 0)
            {
                if (thickLineMaterial == null)
                {
                    thickLineMaterial = new ThickLineMaterial(graphics);
                }
                thickLineMaterial.Thickness = entry.LineWidth;
                thickLineMaterial.world     = material.world;
                thickLineMaterial.BeginApply(context);
            }
#endif

            var vertexBufferSize = vertexSegments[entry.Segment + 1] - vertexSegments[entry.Segment];
#if SILVERLIGHT
            if (vertexBuffer == null || vertexBuffer.VertexCount < vertexBufferSize)
#else
            if (vertexBuffer == null || vertexBuffer.VertexCount < vertexBufferSize || vertexBuffer.IsContentLost)
#endif
            {
                if (vertexBuffer != null)
                {
                    vertexBuffer.Dispose();
                }
                vertexBuffer = new DynamicVertexBuffer(graphics, typeof(VertexPositionColorNormalTexture), Math.Max(initialBufferCapacity, vertexBufferSize), BufferUsage.WriteOnly);
            }

            context.SetVertexBuffer(null, 0);
            vertexBuffer.SetData(vertexData, vertexSegments[entry.Segment], vertexBufferSize, SetDataOptions.Discard);

            // Previous segments are not used, so use SetDataOption.Discard to boost performance.
            context.SetVertexBuffer(vertexBuffer, 0);

            if (entry.IndexCount > 0)
            {
                var indexBufferSize = indexSegments[entry.Segment + 1] - indexSegments[entry.Segment];
#if SILVERLIGHT
                if (indexBuffer == null || indexBuffer.IndexCount < indexBufferSize)
#else
                if (indexBuffer == null || indexBuffer.IndexCount < indexBufferSize || indexBuffer.IsContentLost)
#endif
                {
                    if (indexBuffer != null)
                    {
                        indexBuffer.Dispose();
                    }
                    indexBuffer = new DynamicIndexBuffer(graphics, IndexElementSize.SixteenBits, Math.Max(initialBufferCapacity, indexBufferSize), BufferUsage.WriteOnly);
                }

                graphics.Indices = null;
                indexBuffer.SetData(indexData, indexSegments[entry.Segment], indexBufferSize, SetDataOptions.Discard);

                var primitiveCount = Helper.GetPrimitiveCount(entry.PrimitiveType, entry.IndexCount);
                graphics.Indices = indexBuffer;
                graphics.DrawIndexedPrimitives(entry.PrimitiveType, 0, entry.StartVertex, entry.VertexCount, entry.StartIndex, primitiveCount);
            }
            else
            {
                var primitiveCount = Helper.GetPrimitiveCount(entry.PrimitiveType, entry.VertexCount);
                graphics.DrawPrimitives(entry.PrimitiveType, entry.StartVertex, primitiveCount);
            }

            material.EndApply(context);
        }