Destination .NET! Platform Tools, Technologies & Resources
1 3 5 7 9
2 4 6 8 10
From VB4, C++ and Java to working on .Net Since Beta, 1.0.
Improving partner satisfaction and accelerating Microsoft platform adoption for managed ISVs.
Is your application compatible with Windows Vista? Make sure today by taking our self-test. Just follow the five steps of the Works with Windows Vista program so that you and your customers can be confident in your solution’s compatibility. Read More >>
What product/topic are you most interested in?
(Choose your top answer.)
Windows Vista
Windows Server 2008
2007 Microsoft Office system
SQL Server 2008
ASP.NET
Visual Studio 2008
Windows Mobile
Software as a Service
A little bit of everything
Just browsing, thanks

View Results
Whether you love the site or hate it, we want to know. Tell us what topics to cover, help us improve things, or just sound off on something we could've done better. Send your feedback directly to the editor by email.
 Print Print
Rate this item | 0 users have rated this item.
Walkthrough: Building a Mobile Game in Visual Studio® 2008 (cont'd)

Step Three: Add a W80 Word Database
With Visual Studio 2008, you can build and manage SQL Server Compact Edition 3.5 databases directly in the IDE. In the Data Sources pane, you can launch the "Add New Data Source" wizard to pull in an existing database or create a new one. Since any good word game uses lots of words, you can find a 99-word database here. Download it and pull it into your app by doing the following:

  • Choose Add New Data Source
  • Choose "Database" as Data Source Type
  • Click New Connection
  • Add Connection should indicate ".NET Framework Data Provider for Microsoft SQL Server Compact 3.5" as the Data source. Under Database you can Create or Browse for your database. If this was a new database, you could create it here and the wizard would walk you through building it column by column. But in this case, choose Browse and navigate to your download folder for the W80Base.sdf file.
  • This database is not password protected, so click Test Connection to make sure you can read it. If it succeeds, then click Ok.
  • Click Next. You should get a prompt that "the connection you selected uses a local data file that is not in the current project." Go ahead and copy the file to your project and modify the connection automatically.
  • When choosing your Database Objects, you'll have the option of only one table and only one field (like I said, this is a very simple database). Check the box next to Tables and name the DataSet "W80BaseDataSet".
  • Click Finish. The wizard should add the new database to your project and create a W80BaseDataSet.xsd file for it, along with three other files: W80BaseDataSet.Designer.cs, W80BaseDataSet.xsc, and W80BaseDataSet.xss.
  • In your Data Sources pane, you should be able to navigate through your new database, including bringing up a Preview window.

Step Four: Configure and Connect to the Database
Open up W80BaseDataSet.xsd and you'll see a very simple diagram of the database, which includes just the WordList table, along with a Table Adapter. You have many ways for your app to connect to your data. Using the extra layer of abstraction generated by this process may add some overhead to your app beyond, say, hand-coding a Connection object. But it gives you a lot of nice flexibility and a fast way to get the job done.

By default, the database wizard you just ran adds all the data management queries you would need for a full read/write database. But in this case, you're just going to do simple reads, though it would be a good exercise to add word entry and editing functionality at a later date.

To remove some of the default functionality:

  • Right-click on WordListTableAdapter and choose Configure.
  • The default SQL Statement should be pretty simple: "SELECT [word] FROM [WordList]". Note that the TableAdapter Configuration Wizard offers you a Query Builder tool and advanced options—leave those for now and click Next.
  • For Methods to Generate, you only want the first two: Fill a DataTable ("Fill") and Return a DataTable ("GetData"). If the last option is checked, then uncheck it. Click Next.
  • On the review page, click Finish. You should return back to the .xsd design.
Though the adapter exists and is correctly configured, it's not going to show up in your Toolbox until you compile the project. So go ahead and Build.

Check your Toolbox. You should see WordListTableAdapter available under "W80Word Components".
To finish hooking up the database:

  • Go back to the design view of the mobile form. Drag the WordListTableAdapter control onto the form (onto the section at the bottom, below the device skin). Change its name to taWords.
  • Also under "W80Word Components", you should see the W80BaseDataSet control. Drag it onto the form, too. In the configuration prompt, this should be a "Typed dataset" with the name W80Words.W80BaseDataSet.
  • The new control should appear below the form. Rename it to "dsWordList".

Step Five: Add Game Classes
You need a couple of classes to handle the logic of the game. Go ahead and right-click on the project and select Add -> Class. Call the first one "Guesses.cs" (these are both C# classes). This class tracks the player's guessed letters for the current game.

Open Guesses.cs and replace the contents with Listing 1.

Listing 1: Guesses.cs

using System;
using System.Linq;
using System.Collections.Generic;
using System.Text;

namespace W80Words
{
    class Guesses
    {
        private string _word = "";
        const int LIMIT = 6;

        public Guesses()
        {

        }

        public bool Contains(string letter)
        {
            return _word.Contains(letter);
        }

        public void Add(string letter)
        {
            _word += letter;
        }

        public bool isGameOver()
        {
            return (_word.Length >= LIMIT);
        }

        public int ImageIndex()
        {
            return _word.Length;
        }

        public string Get()
        {
            return _word;
        }

    }
}
Take a look through the code for Guesses.cs. Nothing really new here except for the default inclusion of a System.Linq references, which isn't used in this walkthrough.

In this version of the game, you get 6 guesses, hence the Constant value for LIMIT. All guesses are kept in a private string called _word as a solid string. This allows you to use string members that are not available to chars, so you can quickly compare and manipulate your variables.

Other functions: Contains checks for the existence of a single letter, which means it's already been guessed. Add appends a new letter to the end of those already guessed. Get returns the current list of guessed letters. isGameOver returns true if the number of guessed letters equals or exceeds the LIMIT constant.

ImageIndex returns the number of letters that have been guessed. This integer is used in choosing the correct picture to display on the form. For this walkthrough, I decided to hard-code the list of graphic assets in an ImageList control, then reference the images by index by simply returning the .Length property of the guessed letter concatenation thus far. One change you might consider for your own project is to move the images, or image file names, to a SQL Server Compact Edition database, or another table in the database used here. That way you have the option in the future of allowing users to load their own images to show game progress.

The other game class you need is Answer.cs, which holds the correct answer and provides members for checking against it and tracking progress. Create a new class called Answer.cs and replace its contents with Listing 2.

Listing 2: Answer.cs

using System;
using System.Linq;
using System.Collections.Generic;
using System.Text;

namespace W80Words
{
    class Answer
    {
        private string _word = "";
        private string _sofar = "";

        public Answer()
        {
            
        }

        public string Get()
        {
            return _word;
        }

        public void Set(string word)
        {
            _word = word;
            for (int i = 0; i < _word.Length; i++ )
            {
                _sofar += "0";
            }
        }

        public bool Contains(string letter)
        {
            return _word.Contains(letter);
        }

        public void Add(string letter)
        {
            letter = letter.Substring(0,1).ToLower();
            string newPattern = "";

            for (int i = 0; i < _word.Length; i++)
            {
                if (_word.Substring(i, 1) == letter)
                {
                    newPattern += "1";
                }
                else
                {
                    newPattern += _sofar.Substring(i, 1);
                }
            }

            _sofar = newPattern;
        }

        public bool isGameOver()
        {
            return !(_sofar.Contains("0"));
        }

        public string Draw()
        {
            string answer = "";
            for (int i = 0; i < _word.Length; i++)
            {
                if (_sofar.Substring(i, 1) == "0")
                {
                    answer += "_";
                }
                else
                {
                    answer += _word.Substring(i, 1);
                }
                answer += " ";
            }
            return answer.TrimEnd();
        }

        public string RevealAnswer()
        {
            _sofar = _sofar.Replace("0", "1");
            return Draw();
        }
    }
}
Again, the constructor for this class does nothing. The correct answer is kept in a private string called _word, while _sofar serves as a sort of binary mask. It's used to keep track of which letters to reveal during the game and stores either 0 or 1 for each letter position in the correct answer. This string is initialized in the Set method, where the correct answer gets assigned.

Whereas Guesses.Add appends an incorrect guess to its list, Answer.Add appends a correct guess, in a sense. More accurately, it iterates through the _sofar mask and flags the position to 1 for each occurrence of the current correct guess. This way, a win condition can be checked in isGameOver simply by looking for a 0.

The Draw routine returns the player's current progress in traditional Hangman format, i.e. with letters spaced and unguessed letters replaced with underscores. In the case of a lose condition (from Guesses.isGameOver), the correct answer is revealed by flipping all 0s to 1s in the _sofar mask and calling the Draw routine again.

Page 2 of 3
Previous Page: Project Architecture Next Page: Adding Graphics
Page 1: Project ArchitecturePage 3: Adding Graphics
Page 2: Add a W80 Word Database 
Submit article to:
Extending your solution to run on Microsoft technology is easier than ever. Through NXT, you can reach more customers, increase revenues and slash development time and costs, accelerating both your time to market and profitability. Get the details on NTX. >>
Sign up for your free e-mail newsletters today!
DevX Windows Developer Update

More Newsletters
.NET Building Blocks: Custom User Control Fundamentals
Quickly Copy Data Rows from DataReader to a DataTable
Introduction to the WPF Command Framework
Taming Trees: Building Branching Structures
Implement Drag and Drop in Your Windows Forms Applications



JupiterOnlineMedia

internet.com earthweb.com Devx.com mediabistro.com Graphics.com

Search:

Jupitermedia Corporation has two divisions: Jupiterimages and JupiterOnlineMedia

Jupitermedia Corporate Info

Copyright 2008 Jupitermedia Corporation All Rights Reserved.
Legal Notices, Licensing, Reprints, & Permissions, Privacy Policy.

Web Hosting | Newsletters | Tech Jobs | Shopping | E-mail Offers