.: Draw Text on Screen
|
|
| |
As of XNA version 2.0 there exists a method of drawing text using spritefonts, however you can still use this method if you want to. Using the source code from the first tutorial, we will now implement a way of drawing text on screen. This method is a mixture of ideas from various XNA blogs and sites, as well as my own ideas and modification. So, copy the code folder and rename the copy to DisplayText, open the project and we will start by adding a new module. Right-click on the project name and select Add Module, call this module FontModule and add the following code: |
|
Imports Microsoft.Xna.Framework
Imports Microsoft.Xna.Framework.Graphics
Imports System.Drawing
Module FontModule
Public Device As Microsoft.Xna.Framework.Graphics.GraphicsDevice = Nothing
'A couple of Global objects that will be set using the WriteText Sub below and run from the Render loop
Public SB As SpriteBatch = Nothing
Public TexPub As Texture2D = Nothing
Public StringvectorPub As Vector2 = Nothing
'The Sub that will create and define the necessary objects and variables
Public Sub WriteText(ByVal str As String, ByVal FontName As String, ByVal FontSize As Single, ByVal _FontStyle As FontStyle, _
ByVal StringColour As Brush, ByVal BitmapXPos As Single, ByVal BitmapYPos As Single, ByRef Texture1 as Texture2D, ByRef Vector1 as Vector2)
Dim NewFont As Font = New Font(FontName, FontSize, _FontStyle) ' The font that the text will be written in
Dim Graphics As Graphics = System.Drawing.Graphics.FromHwnd(My.Forms.Form1.Handle) ' The Graphics object that will
'write the text onto the bitmap
Dim StringSize As SizeF = Graphics.MeasureString(str, NewFont) 'The length of the text
Dim Bitmap As Bitmap = New Bitmap(CInt(StringSize.Width), CInt(StringSize.Height)) ' the bitmap that will hold the text
Graphics = System.Drawing.Graphics.FromImage(Bitmap) 'tell the graphics object that it will be using the bitmap
Graphics.TextRenderingHint = Drawing.Text.TextRenderingHint.AntiAliasGridFit ' and how it will display the text
Graphics.DrawString(str, NewFont, StringColour, 0, 0) ' Draw the string on the bitmap
Dim MemStream As System.IO.MemoryStream = New System.IO.MemoryStream 'set aside a portion of memory to hold the bitmap
Bitmap.Save(MemStream, System.Drawing.Imaging.ImageFormat.Png) ' save the bitmap to the portion of memory
MemStream.Position = 0 ' dont know what this does, but it is necessary
Texture1 = Texture2D.FromFile(Device, MemStream) ' create a texture to be used in the spritebatch from the
Vector1 = New Vector2(BitmapXPos, BitmapYPos) ' set the position of the texture
End Sub
End Module
The first declaration for the xna device and the second one for the spritebatch should be removed if you have already declared a device and spritebatch in your game, the rest of the code is necessary and this is what it does. First we declare a texture that will be used by the spritebatch to draw the text on screen, the vector2 is the 2D point where the texture will be drawn. Next is the WriteText Sub that creates a Font and a Drawing component called Graphics, StringSize is the length and height of the text string and Bitmap is the bitmap that will have the string drawn on it. The text string is drawn on to the bitmap and the bitmap is stored in memory as a Bmp file. The texture is then imprinted with the bitmap. Most components such as the font used, font size, text colour, position and font style can be configured when the function is called.
In the Render loop of the Form1 code, the following code was added:
Public Sub Render()
If Device Is Nothing Then Return
'Clear the backbuffer to a blue color
Device.Clear(ClearOptions.Target, Microsoft.Xna.Framework.Graphics.Color.Black, 1.0F, 0)
SB.Begin(SpriteBlendMode.AlphaBlend)
x += 1
'Create the texture that holds the text
WriteText("x = " & x, "Mirror", 48, FontStyle.Bold, Brushes.Crimson, 280, 250, TexPub, StringVectorpub)
'Use the Spritebatch to draw the Text Texture
SB.Draw(TexPub, StringvectorPub, Color.White)
SB.End()
Device.Present()
The WriteText function call includes all the user defined components necessary to configure the texture for drawing in the next line of code, x is just an Integer declared outside the render loop and initially set to 0. The WriteText Sub is CPU intensive if it is run continuously, if the text you are displaying is static then dont put the function call in the render loop where it will be repeated, put it in the Form1_Load or InitializeGraphics Sub. If the text is not static, then you could create some code that only runs the sub when the text needs changed. The SB.Draw part must be run on every loop. You can create a separate Texture and Vector Object and use the Function for multiple Strings.
If you run the code it should look like this:

and then

As you can see it works fine, feel free to use and modify my code as you see fit. Now you can return to the tutorials page. Enjoy
Write Text on Screen Source Code - 42Kb
Web site contents © Copyright Alan Phipps 2006, All rights reserved.
Website templates |