MOBILE

XNA Game Studio 4.0 Programming : The Many Keys Of A Keyboard (part 2) - Moving Sprite Based on Keyboard Input, Onscreen Keyboard

7/17/2012 3:09:13 PM

Moving Sprite Based on Keyboard Input

Now that we covered how to read the current state of the keyboard and can determine whether a key is pressed or released, let’s move a sprite around the screen using the keyboard. First, you need to declare some member variables to store your sprite texture, the sprites position, and the last keyboard state:

Texture2D spriteTexture;
Vector2 spritePosition;
float spriteSpeed = 100f;
KeyboardState lastKeyboardState;

Next, load a texture to use as your sprite. In the game’s LoadContent method, add the following line of code:

spriteTexture = Content.Load<Texture2D>("XnaLogo");

Now, you are ready for some keyboard input. In the game’s Update method, you need to store the current state and move the sprite’s position based on the arrow keys, as follows:

// Store the current state of the keyboard
KeyboardState currentKeyboardState = Keyboard.GetState();

// Move the sprite position based on keyboard input
if (currentKeyboardState.IsKeyDown(Keys.Left))
    spritePosition.X -= spriteSpeed * (float)gameTime.ElapsedGameTime.TotalSeconds;
if (currentKeyboardState.IsKeyDown(Keys.Right))
    spritePosition.X += spriteSpeed * (float)gameTime.ElapsedGameTime.TotalSeconds;
if (currentKeyboardState.IsKeyDown(Keys.Up))
    spritePosition.Y -= spriteSpeed * (float)gameTime.ElapsedGameTime.TotalSeconds;
if (currentKeyboardState.IsKeyDown(Keys.Down))
    spritePosition.Y += spriteSpeed * (float)gameTime.ElapsedGameTime.TotalSeconds;

// Store the keyboard state for next frame
lastKeyboardState = currentKeyboardState;

					  

Whenever the arrow keys are pressed, you move the sprite in the appropriate direction. Notice that “up” corresponds to moving the sprite in the negative Y direction because values for Y increase when moving down the screen.

When you move the sprite, you don’t move by a constant value. Take the elapsed game time into account. Each frame can take a different amount of time to complete. If a constant movement amount is used to update the position of the sprite, it might appear to shudder as it moves across the screen. Correct this using the GameTime.ElapsedGameTime property. You previously used the elapsed time in total seconds. This means pressing the right arrow for one second moves the sprite 100 pixels to the right no matter how many frames happen over that second.

Note

Older PC video games didn’t always take into account the elapsed time when animating and moving sprites. As computing power of PCs increased, these games were able to run faster and so did the animations and speed of the games, making some of the game unplayable.


Finally, you need to display the sprite on the screen using the position you have been updating. To display the sprite, add the following lines of code to your game’s Draw method:

spriteBatch.Begin();
spriteBatch.Draw(spriteTexture, spritePosition, Color.White);
spriteBatch.End();

Now if you run your game, you can control the sprite on the screen using the keyboard arrow keys. Congratulations—you have created your first XNA Game Studio interactive game. This simple game should look similar Figure 1.

Figure 1. Sprite controlled by user keyboard input

Onscreen Keyboard

If your goal is to gather user text input, the Keyboad class is not the best solution. If you try to implement text entry using the Keybord state APIs, you run into a number of issues such has handling the current shift state of the keyboard and making sure to call GetState quick enough that you don’t miss a single key press. The Keyboad API is not designed for text entry (see Figure 2).

Figure 2. Onscreen keyboard in the Windows Phone emulator


For text entry, use the Guide.BeginShowKeyboardInput method. If you are familiar with C#, notice that BeginShowKeyboardInput is an asynchronous method. This means that when you ask to show the keyboard, this method quickly returns but that does not mean the keyboard has been shown or that the user has entered text into the keyboard. For your game to continue running, it needs to handle a method that takes a number of frames to return. BeginShowKeyboardInput returns an IAsyncResult object. This object is used each frame to check on the state of the call to BeginShowKeyboardInput. If the IsCompleted property of the result is true, that means the call has completed and that you can request the string from the keyboard input. This is done calling Guide.EndShowKeyboardInput passing in the result. The method returns the string the user entered. The string might be null because the user can cancel the onscreen keyboard.

To add the onscreen keyboard to your game, store the async result over multiple frames. You also need to store the string returned. Add the following members to your game class:

IAsyncResult keyboardAsyncResult;
string message = "";

We cover the Guide.BeginShowKeyboardInput method, sometimes called gamer services. The important point to know now is that your game constructor needs to initialize gamer services on Windows and Xbox 360 to use the onscreen keyboard. This is done by adding the GamerServicesComponent to the Components list of your game. On Windows and Xbox, add the following line of code at the end of your game’s constructor:

Components.Add(new GamerServicesComponent(this));

Next, check for a spacebar press. If the user presses the spacebar and the onscreen keyboard is not already visible, you start to display the keyboard. Add the following lines of code to your game’s Update method:

if (keyboardAsyncResult == null &&
    currentKeyboardState.IsKeyDown(Keys.Space) && lastKeyboardState.IsKeyUp(Keys.Space))
{
    keyboardAsyncResult = Guide.BeginShowKeyboardInput(PlayerIndex.One,
                                                        "Title",
                                                        "Description",
                                                        "Default Text",
                                                        null, null);
}

					  

In the previous code, check the keyboard async result to make sure you are not already waiting for a previous call. Then, if the spacebar is pressed, you make a call to BeginShowKeyboardInput. The first parameter is the PlayerIndex you want to have control of the onscreen keyboard. This can be only PlayerIndex.One for the Windows and Windows Phone platforms, but on Xbox 360, up to four players can play a game and you might want player three to enter his or her character’s name. In this case, player three should be the one controlling the onscreen keyboard. The next three parameters are string values representing the title, description, and default text to display. We cover the last two values a little later.

Now that you asked for the keyboard to display, it should display when the user presses the spacebar. But when a user enters text or cancels the keyboard, the return value is thrown away. To get the result of what the user enters into the keyboard, you need to call Guide.EndShowKeyboardInput. Calling this method blocks until the previous call to BeginShowKeyboardInput completes, so first check whether the call is complete. After the code you just added, place the following lines of code:

// Check to see if the result has completed
if (keyboardAsyncResult != null && keyboardAsyncResult.IsCompleted)
{
    message = Guide.EndShowKeyboardInput(keyboardAsyncResult);
    if (message == null)
    {
        // String is null since the user canceled the input
    }
    keyboardAsyncResult = null;
}

Notice that the EndShowKeyboardInput call takes the IAsyncResult from the BeginShowKeyboardInput call and returns the string entered by the user. This string can be null if the user canceled the onscreen keyboard.

In the previous code, you use the IAsyncResult from the BeginShowKeyboardInput call to check whether the call completed each frame. Instead of checking the status of each frame, you can use an AsyncCallback method that is called after the method completes. To use the callback method, add the following method to your game:

void StoreKeyboardResult(IAsyncResult result)
{
    message = Guide.EndShowKeyboardInput(result);

    if (message == null)
    {
        // String is null since the user canceled the input
    }
}

After the BeginShowKeyboardInput is complete and the user has entered text, this method is called. Similar to the previous example, you then call EndShowKeyboardInput and check the resulting string. To have BeginShowKeyboardInput use the callback, change the call to look like the following:

if (currentKeyboardState.IsKeyDown(Keys.Space) && lastKeyboardState.IsKeyUp(Keys.Space))
{
    keyboardAsyncResult = Guide.BeginShowKeyboardInput(PlayerIndex.One,
                                                        "Title",
                                                        "Description",
                                                        "Default Text",
                                                        StoreKeyboardResult, null);
}

					  

You no longer need to store the IAsyncResult because the StoreKeyboardResult method is called after the user has completed entering text.

The last parameter of BeginShowKeyboardInput is used to pass in an object to be stored in the IAsyncResult.AsyncState property. This can be useful when you need a specific object after the operation is completed. For example, if you are asking a user to enter his or her character name and you want to store the result in your game’s specific Character class, you can pass the user’s instance of that Character class into BeginShowKeyboardInput and when the call completes, use the IAsyncResult.AsyncState property to access the instance of the Character class.

Other  
  •  Personalize Your iPhone Case
  •  iOS 6's release
  •  Cheap smartphones at Computex 2012 : Acer CloudMobile S500, Gigabyte GSmart G1362, Malata Z500
  •  5 MP3 players in 2012
  •  Blackberry World 2012 (Part 3) - Mobile computing platform
  •  Blackberry World 2012 (Part 2) - BlackBerry 10, Apps and development
  •  Blackberry World 2012 (Part 1) - The keynote address
  •  World's Most Popular IM Client Just Got Hotter
  •  V For Venerable One
  •  The Human Touch
  •  Some Cool Apps From Various Flatforms To Make Your Life Easy
  •  A Bite of Apple iOS 6
  •  “TU ME” …vs Skype and Whatsapp.
  •  Pandora On Android-Your Best Music Buddy!
  •  Gemini Joytab 8” Tablet PC
  •  4G- Can Telecom Operators Count On 50%?
  •  World Atlas HD
  •  Mobile - A Challenger Appears
  •  Diet Coda
  •  Apple Retains Its Top Slot In The Tablet Market
  •  
    Top 10
    HP Spectre XT Touchsmart Review - Everything Is Fine Except Battery Life (Part 2)
    HP Spectre XT Touchsmart Review - Everything Is Fine Except Battery Life (Part 1)
    Lenovo Thinkpad Carbon Touch Ultrabook Review (Part 3)
    Lenovo Thinkpad Carbon Touch Ultrabook Review (Part 2)
    Lenovo Thinkpad Carbon Touch Ultrabook Review (Part 1)
    Blackberry 10 OS (Part 3)
    Blackberry 10 OS (Part 2)
    Blackberry 10 OS (Part 1)
    How To Keep High-End Speakers In Good Conditions
    How To Use TV As An Audio Converter
    Most View
    Windows Small Business Server 2011 : Managing User Roles
    Canon IXUS 510 HS
    Review: Nikon D4 – The master of the dark arts (Part 2)
    Sharepoint 2007: Use the My Links to Manage Your Links
    Every Cloud...(Part 2) - Mobility & Portability
    Searching for Google’s future (Part 1) - Taking the tablets
    Dell Inspiron 17R Special Edition - Battery Is A Disappointment
    10 Valuable TVs For Your Living Room
    Silverlight Recipes : Creating Silverlight Using Ruby, Python, or JScript
    Build A Home Theatre PC (Part 2)
    The Library In Your Pocket (Part 2) - iOS – iPad, Android – Kobo Vox, Kindle Fire, Binatone ReadMe, Google Nexus 7
    Samsung 830
    Windows 9 : What to expect - 32-bit support , WinRT & XNA
    Programming with DirectX : View Transformations
    Securing Your Silverlight Application
    Programming the Mobile Web : Mobilizing WordPress and Other CMSs
    Aerocool Silent Master Blue
    Getting Started with Device Manager
    Calendar Plus - Simple And Friendly
    Transact-SQL in SQL Server 2008 : New date and time Data Types and Functions