예제 #1
0
        public static void RenderText(string message, float x, float y, float scale, float rotation, Color color)
        {
            // Apply the 2D orthographic matrix transformation
            SetOrthographicMatrix();

            rotation = rotation * 180f / Constants.pi_float;

            // Set the text shader program and pass in the color as a parameter
            GL.UseProgram(ShaderManager.TextShader.GpuHandle);
            int uniformLocation = GL.GetUniformLocation(ShaderManager.TextShader.GpuHandle, "color");

            GL.Uniform4(uniformLocation, new Color4(color.R / 255f, color.G / 255f, color.B / 255f, color.A / 255f));

            // Apply the model view matrix transformations
            GL.MatrixMode(MatrixMode.Modelview);
            GL.LoadIdentity();
            GL.Translate((x * _screenWidth - _screenWidth / 2f), (y * _screenHeight - _screenHeight / 2f), 0f);
            if (rotation != 0)
            {
                GL.Rotate(rotation, 0, 0, 1);
            }

            // Set up the verteces (hardware instanced for all character sprites)
            GL.BindBuffer(BufferTarget.ArrayBuffer, CharacterSprite.GpuVertexBufferHandle);
            GL.VertexPointer(3, VertexPointerType.Float, 0, IntPtr.Zero);
            GL.EnableClientState(ArrayCap.VertexArray);

            // this standardizes the size (not depedent on sprite sheet size)
            float sizeRatio = scale / (float)_font.LineHeight;

            for (int i = 0; i < message.Length; i++)
            {
                CharacterSprite sprite = _font.Get(message[i]);

                // Calculate the per-character transformational values
                float ySize    = sizeRatio * (float)sprite.OriginalHeight;
                float yOffset  = sizeRatio * (float)sprite.YOffset;
                float xSize    = sizeRatio * (float)sprite.OriginalWidth;
                float xRatio   = xSize / (float)(sprite.OriginalWidth);
                float xOffset  = xRatio * (float)sprite.XOffset;
                float xAdvance = xRatio * (float)sprite.XAdvance;
                // Kearning (extra adjustments between specific charasters)
                if (i + 1 < message.Length)
                {
                    xAdvance += xRatio * (float)sprite.CheckKearning(message[i + 1]);
                }

                // Apply the character offsets and scaling
                GL.Translate(xOffset, -yOffset, 0f);
                GL.Scale(xSize, ySize, 0f);

                // Bind the texture and set up the texture coordinates
                GL.BindTexture(TextureTarget.Texture2D, sprite.Texture.GpuHandle);
                GL.BindBuffer(BufferTarget.ArrayBuffer, sprite.GPUTextureCoordinateBufferHandle);
                GL.TexCoordPointer(2, TexCoordPointerType.Float, 0, IntPtr.Zero);
                GL.EnableClientState(ArrayCap.TextureCoordArray);

                // Perform the render
                //GL.DrawArrays(PrimitiveType.Triangles, 0, sprite.VertexCount);
                GL.DrawArrays(BeginMode.Triangles, 0, sprite.VertexCount);

                // Remove the per character transforms and advance to the next charachers position
                GL.Scale(1 / xSize, 1 / ySize, 0f);
                GL.Translate(-xOffset + xAdvance, yOffset, 0f);
            }
        }