Before we dive further into the strategy game we need to optimize our UI, by lowering our openGL calls. On this post after performance we'll cover map resizing and displaying text on screen (in order to fill that nice new user interface from last post).
Optimizing performance
I'll add some lines of code in order to optimize performance (by only drawing tiles that are visible to the screen). Now with our UI (I created mine to be 140 pixels and drawn x2 so my screen visible tiles will be the ones that are inside X values (0 to Screen_width - 140x2) and Y values (0 to Screen_height). And in order to test this we'll add the same clause in the mini-map where we'll draw all of the tiles but tint the ones that don't show.
Doing so should give us steady fps even in extra large maps with 500x500 tiles.
If (GridWorld(X, Y).SX + OffSetX) > -GridWidth And (GridWorld(X, Y).SX + OffSetX) < (ScreenWidth - 240) And (GridWorld(X, Y).SY + OffSetY) >= -GridHeight And (GridWorld(X, Y).SY + OffSetY) < ScreenHeight + 40 Then
'Drawing
End if
Tinting the ones outside the screen should show on our mini-map like this.
Zooming in and out
In order to add zoom in/out functionality we need to create a new sub which will change our map array X,Y values (only for our isometric projection) and of course add a scaling float variable which will resize the end result for our drawing calls.
Let's do some math for this.
In order to add this functionality we declare a Scaling float, (Public ZoomVar As Single = 1.0F), and create a sub to call when we press to zoom in/out.
Public Sub Grid_Resize(ByVal Func As String)
If Func = "Minus" Then 'When we zoom out
If ZoomVar > 0.6F Then
ZoomVar -= 0.2F
End If
ElseIf Func = "Plus" Then 'When we zoom in
If ZoomVar < 2.4F Then
ZoomVar += 0.2F
End If
End If
'Re-arrange our grid based on our isometric math and multiply it by our zoom float
For X = 0 To MaxGridX
For Y = 0 To MaxGridY
GridWorld(X, Y).SX = ((X - Y) * GridWidth / 2) * ZoomVar
GridWorld(X, Y).SY = ((X + Y) * GridHeight / 2) * ZoomVar
Next
Next
End Sub
And on our projection drawing we'll change the target rectangle to the following
dRect = New Rectangle(GridWorld(X, Y).SX + OffSetX, GridWorld(X, Y).SY + OffSetY - 8, 64 * ZoomVar, 40 * ZoomVar) 'we just multiply the projection width and height with our float
And the last but hardest part of our code is the mouse over tile detection math which again is found by reversing the equations we used when we created our tile-map.
Public Sub GLMouseMove(ByVal X1 As Integer, ByVal Y1 As Integer)
Dim X, Y As Integer
X = (X1 - OffSetX)
Y = (Y1 - OffSetY)
GridPX = (Y + X / 2) / (GridHeight * ZoomVar)
GridPY = GridPX - (X) / (GridHeight * ZoomVar)
FOVGridTemporary()
End Sub
Just call Grid_Resize (with Plus or Minus) to zoom in/out and you'll see that your mouse moving will identify the tile when resizing. You will also notice a visible change when you zoom in/out on our X,Y coordinates. I tweaked my code like this to make it smoother
'Tweaking Offset on Minus
OffSetX += 50
OffSetY += 220
'Tweaking Offset on Plus
OffSetX -= 50
OffSetY -= 220
Displaying text on openGL
Now that we created our fonts sprite sheet (see post #12 about the way to create it), we need a way to display a text since we can't call all fonts one by one whenever we want to write something on screen.
Our system-y fonts sprite sheet |
The rendering call is the following, which I will explain right under
Public Sub DrawText(ByVal Text As String, ByVal X As Integer, ByVal Y As Integer, ByVal Size As Single, ByVal OffsZ As Single, ByVal R As Single, ByVal G As Single, ByVal B As Single, ByVal A As Single)
Dim MaxTextArrLng As Integer = Text.Length
If Text.Length = 0 Then 'Debug just in case the sub gets called with no text
Text = " "
MaxTextArrLng = 1
End If
Dim TextARR(MaxTextArrLng) As Point
Dim TextARRLength As Integer
Dim I As Integer
Dim ILength As Integer
ILength = MaxTextArrLng
For I = 0 To (ILength - 1)
TextARR(I).X = Asc(Text(I)) Mod 10
TextARR(I).Y = (Asc(Text(I)) \ 10) - 3
Next
TextARRLength = ILength
For I = 0 To TextARRLength
sRect = New Rectangle(TextARR(I).X * 8, TextARR(I).Y * 8, 8, 8)
dRect = New Rectangle(X + (8 * Size * I), Y, 8 * Size, 8 * Size)
DrawTexturedQuad(sRect, dRect, 80, 80, 4, OffsZ, R, G, B, A)
Next
End Sub
As you can see it's the same process we use to draw a tile, only now it's getting automated for the characters in our string to draw, while using Asc to get the position of our char.
Now let's test our new drawing text sub. (I'll make a call to it while drawing our mouse over tile for testing reasons)
That was it! Now we can draw text on our map too. It's a pretty easy process and you can easily (Not as easy as picking fonts to be honest..) modify your text sheet depending on how you want your text to look.
Size when you call the sub refers to font size, and RGBA (Red, Green, Blue, Alpha) is included on the call.
With this last code part, I think we finished our basic drawing calls and we can dive deeper into the game's more complex and more fun aspects.
Comments
Post a Comment