One of the first articles I wrote for this page was a explanation of the simple Tic Tac Toe game for VB 6. (Click Here for this article.) The Tic Tac Toe example has now been used in a whole series of articles to demonstrate a range of features of both .NET and GDI+. The second article was "minimal" conversion of the program into VB.NET using the Microsoft Upgrade Wizard. (Click Here for this article.) And the third article made an attempt to completely convert the program while keeping the same VB 6 program architecture. (Click Here for this article.)
To download the source code for this version, Click Here.
Since the New Tic Tac Toe program really was coded from scratch, almost nothing is the same as the original. In brief, here's a summary of the major changes:
- The entire game playing grid is now created by GDI+.
GDI+ graphics and VB.NET components no longer share the same screen space and the program is now written to complement the automatic refresh of graphics managed by Windows. Except for one statement to erase all of the graphics when a new game is started, all graphics are in a single OnPaint subroutine that is automatically called whenever Windows determines that graphics need to be refreshed. This means that the bug in the previous version that would erase graphics when the game window was covered for some reason, such as a MsgBox, is now gone. Graphics are simply restored when the game window is repainted. Consequently, the use of MsgBox windows to control game play are back in this version. And the many flags and variables that were used to control display of components in the previous version are gone.
- The entire game grid is also relative to a single Point in the program. In fact, they're relative to this point:
Dim Pt As Point = New Point(20, 20)
To prove it, you can change the beginning point above to some other value, like say, (50, 50), and notice that the whole playing grid moves, X and O markers, win lines and all, and the game still works (even though the playing grid isn't centered on the form very well anymore).
The relative distances of the game components to each other is a lot more intuitive and easy to understand. But it's still easier to program if you create a "road map" of where the points are that you can follow. Compare the illustration with the "eight points at the ends of grid lines" declaration in the source code.
- The mathematical calculation of win lines has been replaced with a simple Case structure.
The original VB 6 program used a pair of two dimensional arrays that were passed to a common subroutine and then analyzed using some clever math statements. While that idea would be considered to be "elegant" by a lot of programmers, in my experience, long term maintenance costs as well as short term programming costs -- as well as execution speed -- usually argues in favor of the "Keep It Simple" approach.
A move is complete when the MouseUp event subroutine is called. The MouseUp event subroutine then simply checks every row, column, and diagonal for a winner in a single, one-dimensional subroutine that doesn't have to be passed to another routine. To allow the use of a single array, a positive 1 in the array is consider to be an X move, a negative 1 is an O move. Every possible win is assigned a number and a Case statement in the OnPaint event draws the right win line.
- Naming and style is generally cleaned up to VB.NET standards.
The idea of keeping track of the type of variables as part of the name --
strVariable for a string
intVariable for an integer
-- and so forth.
-- became popular when Visual Basic "variant" variables made it uncertain just what type a variable was supposed to be. Since VB.NET is now "strongly typed" again, that isn't a problem anymore. Variable names in this version are designed to be easily understood.
And VB.NET built in types are used whenever possible as well. For example:
~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Dim Ans As MsgBoxResult
Ans = MsgBox("It's a Draw! Play Again?", _
MsgBoxStyle.YesNo)
If Ans = MsgBoxResult.Yes Then
~~~~~~~~~~~~~~~~~~~~~~~~~~~~
- And, just because I thought it needed it, the number of "Draw" games is tracked in the scoreboard too.
In this final article, a .NET version of the game has been coded "from bare metal up". The problems of the previous programs, which were crippled by the use of the original VB 6 program architecture, are solved here. The main goal here was to demonstrate the differences between the VB 6 way to code things and the VB.NET/GDI+ way. Sometimes, it's just better to start over.
Nothing is completely "final", but this version is "final" until an About Visual Basic reader shows me a better way to code the program! To download the source code for this version, Click Here.

