<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Абструс! &#187; touch</title>
	<atom:link href="http://www.abstrys.com/tag/touch/feed/" rel="self" type="application/rss+xml" />
	<link>http://www.abstrys.com</link>
	<description>Writing, game development, and other enigmatic esoterica.</description>
	<lastBuildDate>Tue, 12 Apr 2011 17:14:49 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.3.1</generator>
		<item>
		<title>Making the Zune HD Sparkle with XNA Game Studio 3.1 &#8211; Part 2</title>
		<link>http://www.abstrys.com/2010/02/making-the-zune-hd-sparkle-with-xna-game-studio-3-1-part-2/</link>
		<comments>http://www.abstrys.com/2010/02/making-the-zune-hd-sparkle-with-xna-game-studio-3-1-part-2/#comments</comments>
		<pubDate>Thu, 18 Feb 2010 00:59:00 +0000</pubDate>
		<dc:creator>Eron</dc:creator>
				<category><![CDATA[Game Development]]></category>
		<category><![CDATA[programming]]></category>
		<category><![CDATA[touch]]></category>
		<category><![CDATA[UI]]></category>
		<category><![CDATA[user interface]]></category>
		<category><![CDATA[XNA Game Studio Docs & Resources]]></category>
		<category><![CDATA[Zune HD]]></category>

		<guid isPermaLink="false">http://www.abstrys.com/?p=28</guid>
		<description><![CDATA[Introduction This is part two of a two-part tutorial dealing with touch and accelerometer input on the Zune HD.  It&#8217;s assumed that readers have already read the first part, which provides a full discussion of building the application to this point, including required prerequisites.  If you haven&#8217;t read it already, see Making the Zune HD [...]]]></description>
			<content:encoded><![CDATA[<h2>Introduction</h2>
<p>This is part two of a two-part tutorial dealing with touch and accelerometer input on the Zune HD.  It&#8217;s assumed that readers have already read the first part, which provides a full discussion of building the application to this point, including required prerequisites.  If you haven&#8217;t read it already, see <a href="http://www.abstrys.com/2010/02/making-the-zune-hd-sparkle-with-xna-game-studio-3-1-part-1/" target="_self">Making the Zune HD Sparkle with XNA Game Studio 3.1 &#8211; Part 1</a>.</p>
<p>This part of the tutorial adds a number of GUI elements to the application, making it more complete by adding an instruction screen and a menu to manipulate the behavior of the display.</p>
<p><span id="more-28"></span></p>
<p>As before, the source code can be <a href="http://www.abstrys.com/files/source/InputToyZuneHD.zip">downloaded here</a>.</p>
<h2>Adding an Instructions Screen</h2>
<p>As I mentioned at the end of part one, the application, as it is, doesn&#8217;t give the user any indication of what to do: it initially starts with a black screen.</p>
<p>We&#8217;ll now add an instructions screen that will appear when the app is first started, and then will fade into the background, allowing the user to continue to create sparkles without the instructions visible.</p>
<p>I&#8217;ll do this as simply as possible: the instructions screen is simply another texture that will be displayed and faded.  The instructions look like this:</p>
<p><img class="alignnone" style="background: black;" title="Instructions image" src="http://www.abstrys.com/files/images/Instructions.png" alt="" width="228" height="231" /></p>
<p>Add this file (also in the source zip, if you downloaded it) to your content project.  The <strong>Asset Name</strong> should be &#8220;Instructions&#8221; and the <strong>Build Action</strong>, as before with the flare image, should be &#8220;Compile&#8221;.</p>
<h3>The Instructions Class</h3>
<p>We&#8217;ll add a new class to handle the instructions screen, to avoid mucking up Game1&#8242;s code.  In Visual Studio, add a new class called <em>Instructions.cs</em>.  If you create the class by right-clicking the <strong>InputToyZuneHD</strong> project and selecting <strong>Add&#8230;</strong>, then <strong>New Item</strong>, and then <strong>Class</strong>, you&#8217;ll be provided with some skeleton code for your class:</p>
<pre>using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace InputToyZuneHD
{
     class Instructions
     {
     }
}</pre>
<p>Replace all the <em>using</em> lines after <strong>System</strong> with the following <strong>Xna.Framework</strong> namespaces :</p>
<pre>using System;
<span style="color: #008000;"><strong>using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Content;</strong></span></pre>
<p>We&#8217;ll be making use of these namespaces in our code, but won&#8217;t be needing System.Collections.Generic, System.Linq, or System.Text.</p>
<p>Now, begin filling in the class, adding some class data members:</p>
<pre><span style="color: #008000;"><strong>private const float TIMETOSHOW = 6000.0f;
private const float FADETIME = 2000.0f;</strong><strong>

private State state;
private float timeRemaining;
private Texture2D image;
private Color color;
private Vector2 pos;</strong></span></pre>
<p>The <em>TIMETOSHOW </em>and <em>FADETIME</em><strong> </strong>members will be used to control how long to display the instructions, and are in milliseconds.  There is also a <strong>State </strong>enumeration, made <em>public</em> so it can be seen outside the class, and related data member to track the state of the instructions display.</p>
<p>The next four members: <em>timeRemaining</em>, <em>image</em>, <em>color</em>, and <em>pos</em>, are used to update and display the instructions.  Their use, if not already obvious, will be shortly.</p>
<p>Add a constructor, initializing the <em>state </em>and <em>color </em>members:</p>
<pre><span style="color: #008000;"><strong>public Instructions()
{
    state = State.HIDE;
    color = new Color(255,255,255,255);
}</strong></span><span style="color: #008000;">
</span></pre>
<p>Also, add a <strong>loadContent</strong> public method that will be used to fill the <em>image </em>and <em>pos </em>members:</p>
<pre><strong><span style="color: #008000;">public void loadContent(ContentManager cm, GraphicsDevice gd)
{
    image = cm.Load&lt;Texture2D&gt;("Instructions");
    pos = new Vector2(
        (gd.Viewport.Width - image.Width) * 0.5f,
        (gd.Viewport.Height - image.Height) * 0.5f);
}</span></strong>
</pre>
<p>We&#8217;re placing the image in the middle of the display area (provided by <strong>GraphicsDevice.Viewport</strong>), based on the image dimensions.</p>
<p>Next, add a public method to show the instructions, and another to check to see if the instructions are visible or not.  We&#8217;ll call these <strong>show</strong> and <strong>isVisible</strong>.  Yes, these methods practically name themselves:</p>
<pre><span style="color: #008000;"><strong>public void show()
{
    state = State.DISPLAY;
    color.A = 255;
    timeRemaining = TIMETOSHOW;
}

public bool isVisible()
{
    return (state != State.HIDE);
}</strong></span>
</pre>
<p>As long as the instructions are not in the HIDE state, they are visible.</p>
<p>The core of the Instruction class is really the update method, which serves to set the state and alpha-channel of the color, based on the time remaining:</p>
<pre><strong><span style="color: #008000;">public void update(float etms)
{
    if (state == State.HIDE)
    {
        return;
    }

    timeRemaining -= etms;
    if(timeRemaining &lt; 0)
    {
        state = State.HIDE;
        return;
    }
    else if (timeRemaining &lt; FADETIME)
    {
        // fading out
        state = State.FADEOUT;
        color.A = (byte)(255.0f * timeRemaining / FADETIME);
    }
}</span></strong>
</pre>
<p>You may recall that <em>etms</em>, the elapsed time in milliseconds since the last frame, was a value that we used in the first part of the tutorial.  It&#8217;s used here to reduce the time remaining.</p>
<p>Lastly, we&#8217;ll add a method to draw the instructions image, using a <strong>SpriteBatch</strong>:</p>
<pre><span style="color: #008000;"><strong>public void draw(SpriteBatch sb)
{
    if (state == State.HIDE)
    {
        return;
    }

    sb.Draw(image, pos, color);
}</strong></span>
</pre>
<p>Rather self-explanatory:  If the state of the instructions is HIDE, don&#8217;t draw it.  Otherwise, draw it with the <em>image</em>, <em>pos</em>, and <em>color </em>members.  Notice that this <strong>Draw </strong>call is far simpler than the one we used to draw the sparkles.  That&#8217;s because we&#8217;re not applying any rotation to the image.  If you&#8217;re simply drawing an unscaled, non-rotated image on the screen, this version of <strong>Draw </strong>is the way to go.</p>
<p>That&#8217;s it for the Instructions class!  Next, we&#8217;ll hook it in to our game loop.</p>
<h3>Adding the Instructions Class to the Game</h3>
<p>Open the Game1.cs class that we worked with in the first part of the tutorial.  We&#8217;ll add a new data member to <strong>Game1</strong>, and then initialize it in <strong>Game1</strong>&#8216;s constructor:</p>
<pre>List&lt;Sparkle&gt; sparkles;
<span style="color: #008000;"><strong>Instructions instructions;</strong></span>

public Game1()
{
    graphics = new GraphicsDeviceManager(this);
    sparkles = new List&lt;Sparkle&gt;();

<span style="color: #008000;"><strong>    instructions = new Instructions();</strong></span>

    Content.RootDirectory = "Content";
...
</pre>
<p>In <strong>Game1.LoadContent</strong>, add code to load the instructions content and show it (since we want the instructions to show as soon as the application starts):</p>
<pre>flareImage = this.Content.Load&lt;Texture2D&gt;("Flare");
flareOffset = new Vector2(
    flareImage.Width * 0.5f, flareImage.Height * 0.5f);
<strong><span style="color: #008000;">instructions.loadContent(this.Content, this.GraphicsDevice);
instructions.show();</span></strong>
</pre>
<p>In <strong>Game1.Update</strong>, update the instructions screen right after getting the elapsed time in milliseconds.  There&#8217;s no need to update instructions if it&#8217;s not visible, however:</p>
<pre>// elapsed time will be used in updating movement
float etms = gameTime.ElapsedGameTime.Milliseconds;

<span style="color: #008000;"><strong>// update the instructions state if needed
if (instructions.isVisible())
{
    instructions.update(etms);
}</strong></span>
</pre>
<p>The last thing we need to do is add the instructions to the draw code.  Since we want the player to be able to draw sparkles on the screen even while the instructions are showing, we&#8217;ll draw the instructions first, right after the call to SpriteBatch.Begin, and before drawing any sparkles.  In <strong>Game1.Draw</strong>, add:</p>
<pre>spriteBatch.Begin();
<span style="color: #008000;"><strong>// draw stuff in the background
if (instructions.isVisible())
{
    instructions.draw(spriteBatch);
}</strong>
</span>
// draw the sparkles
foreach(Sparkle s in sparkles)
...
</pre>
<p>You should be able to build and deploy the application.  Now, when you run it, you should be able to see the nifty instructions screen show as soon as the application loads, and watch it fade out after about six seconds.</p>
<h2>Adding a Menu</h2>
<p>There&#8217;s still one more part of the GUI that would be nice to have: the ability to show the instructions screen at will while the game is running, and also the ability to stop and re-start the sparkle fading, so the user can spend more time using the accelerometer to play with existing sparkles.</p>
<p>We&#8217;ll now add an interactive menu to accomplish this.  It will be small and unobtrusive so that it won&#8217;t interfere with sparkle creation, but large enough that the player can actually use the menu.  Our menu will consist of two buttons, one of which (the pause/play button for sparkle fading) will have two states.</p>
<p>The buttons look like this:</p>
<p><img class="alignnone" style="background: black;" title="Help Button" src="http://www.abstrys.com/files/images/btnHelp.png" alt="" width="34" height="34" /> <img class="alignnone" style="background: black;" title="Pause Button" src="http://www.abstrys.com/files/images/btnPause.png" alt="" width="34" height="34" /> <img class="alignnone" style="background: black;" title="Play Button" src="http://www.abstrys.com/files/images/btnPlay.png" alt="" width="34" height="34" /></p>
<p>Add these files to the InputToyZuneHD content project.  As before, they should have <strong>Asset Names</strong> that correspond to their filenames (&#8220;btnHelp&#8221;, &#8220;btnPause&#8221;, and &#8220;btnPlay&#8221;, respectively) and the <strong>Build Action</strong> of each should be set to &#8220;Compile&#8221;.</p>
<h3>The Menu Class</h3>
<p>As with the instruction screen, we&#8217;ll create a new class to handle the menu.  It&#8217;ll be called Menu.cs.  The using block should look like this:</p>
<pre>using System;
<span style="color: #008000;"><strong>using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Content;
using Microsoft.Xna.Framework.Input;</strong></span><span style="color: #008000;">
</span></pre>
<p>Declare the following private data members at the beginning of the new <strong>Menu</strong> class:</p>
<pre><span style="color: #008000;"><strong>private const int BUTTONMARGIN = 4;

private Texture2D pauseBtnImg;
private Texture2D playBtnImg;
private Vector2 pauseBtnPos;

private Texture2D helpBtnImg;
private Vector2 helpBtnPos;

private bool paused;</strong></span>
</pre>
<p>The <em>BUTTONMARGIN </em>represents the distance we&#8217;ll place each button from the edges of the screen, and the rest of the variables hold the texture and position of each button, and whether fading is paused or not.  You&#8217;ll note that we only need one position for the pause/play buttons, since they&#8217;ll appear in the same position on the screen.</p>
<p>Now, add Menu&#8217;s constructor, setting <em>paused</em> to <strong>false</strong>:</p>
<pre><strong><span style="color: #008000;">public Menu()
{
    paused = false;
}</span></strong></pre>
<p>As we did with the Instructions class, we&#8217;ll add a <strong>loadContent </strong>method to load the class content:</p>
<pre><strong><span style="color: #008000;">public void loadContent(ContentManager cm, GraphicsDevice gd)
{
    pauseBtnImg = cm.Load&lt;Texture2D&gt;("btnPause");
    playBtnImg = cm.Load&lt;Texture2D&gt;("btnPlay");
    pauseBtnPos = new Vector2(
        0, gd.Viewport.Height - pauseBtnImg.Height);

    helpBtnImg = cm.Load&lt;Texture2D&gt;("btnHelp");
    helpBtnPos = new Vector2(
        gd.Viewport.Width - helpBtnImg.Width,
        gd.Viewport.Height - helpBtnImg.Height);
}</span></strong>
</pre>
<p>The pause/play button is placed on the bottom-left part on the screen, and the help button is placed on the bottom-right.  This will provide a minimal, but useful, user interface.</p>
<p>We&#8217;ll also add a public <strong>isPaused</strong> method that the <strong>Game1 </strong>class can use to determine whether or not to fade the sparkles:</p>
<pre><span style="color: #008000;"><strong>public bool isPaused()
{
    return paused;
}</strong></span>
</pre>
<p>Now, we&#8217;ll get to the core of this class.  Unlike the instructions screen, the menu is interactive, so it must handle user input.  We&#8217;ll create a <strong>handleInput </strong>method that takes a <strong>TouchLocation</strong>, so it can determine if the <strong>TouchLocation </strong>intersects one of the buttons, and a reference to the <strong>Instructions </strong>class, so we can show the instructions screen if the help button is pressed:</p>
<pre><span style="color: #008000;"><strong>public bool handleInput(TouchLocation tl, Instructions instructions)
{
    if (tl.Position.Y &gt; (pauseBtnPos.Y - BUTTONMARGIN))
    {
        if (tl.Position.X &lt; (pauseBtnImg.Width + BUTTONMARGIN))
        {
            // toggle the pause state.
            paused = !paused;
        }
        else if (tl.Position.X &gt; (helpBtnPos.X - BUTTONMARGIN))
        {
            // show the game instructions.
            instructions.show();
        }

        return true;
     }

     return false;
}</strong></span>
</pre>
<p>The function returns true if it handled the input, and false if it didn&#8217;t.  We&#8217;ll use this in <strong>Game1 </strong>to determine whether or not to draw a new sparkle for this <strong>TouchLocation</strong>.</p>
<p>Finally, there will be a draw method for the menu, so it can be displayed:</p>
<pre><span style="color: #008000;"><strong>public void draw(SpriteBatch sb)
{
    // draw the buttons.
    sb.Draw((paused ? playBtnImg : pauseBtnImg), pauseBtnPos, Color.White);
    sb.Draw(helpBtnImg, helpBtnPos, Color.White);
}</strong></span>
</pre>
<p>It&#8217;s time to hook the menu to the game loop, and see how it all comes together!</p>
<h3>Adding the Menu Class to the Game</h3>
<p>Open Game1.cs again, and add a new member variable for the <strong>Menu</strong> class:</p>
<pre>List&lt;Sparkle&gt; sparkles;
Instructions instructions;
<span style="color: #008000;"><strong>Menu menu;</strong></span></pre>
<p>In Game1&#8242;s constructor, initialize the menu:</p>
<pre>instructions = new Instructions();
<span style="color: #008000;"><strong>menu = new Menu();</strong></span></pre>
<p>Load the menu&#8217;s content as we did for the instructions.  In Game1.LoadContent, add:</p>
<pre>flareOffset = new Vector2(
     flareImage.Width * 0.5f, flareImage.Height * 0.5f);
<span style="color: #008000;"><strong>menu.loadContent(this.Content, this.GraphicsDevice);</strong></span>
instructions.loadContent(this.Content, this.GraphicsDevice);
</pre>
<p>Next, we&#8217;ll need to send touch events to the menu, to see if any of the buttons were pressed.  Add the following lines of code to Game1.Update:</p>
<pre>foreach (TouchLocation tl in touchCollection)
{
    if ((tl.State == TouchLocationState.Pressed)
        || (tl.State == TouchLocationState.Moved))
    {
<span style="color: #008000;"><strong>        if (tl.State == TouchLocationState.Pressed)
        {
            if (menu.handleInput(tl, instructions))
            {
                break;
            }
        }
</strong></span>
        // add sparkles based on the touch location
        sparkles.Add(new Sparkle(tl.Position.X,
            tl.Position.Y, ttms));
...
</pre>
<p>You might be wondering why, if <em>tl.State == TouchLocation.Pressed</em> was already tested for, we&#8217;re testing for it again?</p>
<p>The reason is this: I made a design choice to not allow the menu to be activated if the player simply drags his or her finger over the menu area during a swipe meant to create sparkles.  Similarly, I didn&#8217;t want the pause/play button to be turned on and off if the player swipes the screen a little after pressing the button.  Only a new touch will activate the menu.</p>
<p>Another design choice has been made here: if a menu button was touched, we use break instead of continue in the foreach loop.  This causes all further touch-points to be ignored.</p>
<p>As an experiment, you might like to see what happens when you allow TouchLocationState.Moved to activate the menu, or use a continue instead of a break if a menu button was activated.  I find that experimenting with design choices such as the above really gives me an better idea of how to design my user interface elements to respond as the user expects them to.</p>
<p>There&#8217;s only one thing left to do here, and that&#8217;s to draw the menu!  In Game1.Draw, add a line to draw the menu, just before SpriteBatch.End is called:</p>
<pre><span style="color: #008000;"><strong>// draw the foreground (AKA the HUD)
menu.draw(spriteBatch);
</strong></span>
spriteBatch.End();
</pre>
<p>The menu is drawn after the sparkles so it will always appear over the sparkles.  This type of display is often called a heads-up display, or HUD, since it is drawn over any game action.  Health-bars, mini-maps and other such game interface elements are often drawn this way.</p>
<p>That&#8217;s all.  Build, deploy, and run the application again to see its final form (at least, for now).  You should be able to display the instructions again by pressing the help button, and you should be able to toggle the fading off and on by using the pause and play buttons.</p>
<p>I hope that you enjoyed the tutorial.  If you have any questions about its content, feel free to contact me.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.abstrys.com/2010/02/making-the-zune-hd-sparkle-with-xna-game-studio-3-1-part-2/feed/</wfw:commentRss>
		<slash:comments>4</slash:comments>
		</item>
		<item>
		<title>Making the Zune HD Sparkle with XNA Game Studio 3.1 &#8211; Part 1</title>
		<link>http://www.abstrys.com/2010/02/making-the-zune-hd-sparkle-with-xna-game-studio-3-1-part-1/</link>
		<comments>http://www.abstrys.com/2010/02/making-the-zune-hd-sparkle-with-xna-game-studio-3-1-part-1/#comments</comments>
		<pubDate>Tue, 16 Feb 2010 08:40:47 +0000</pubDate>
		<dc:creator>Eron</dc:creator>
				<category><![CDATA[Game Development]]></category>
		<category><![CDATA[programming]]></category>
		<category><![CDATA[accelerometer]]></category>
		<category><![CDATA[input]]></category>
		<category><![CDATA[touch]]></category>
		<category><![CDATA[XNA Game Studio Docs & Resources]]></category>
		<category><![CDATA[Zune HD]]></category>

		<guid isPermaLink="false">http://www.abstrys.com/?p=5</guid>
		<description><![CDATA[Introduction This article explores using XNA Game Studio to access the two primary forms of user input on the Zune HD: the multitouch screen, and the accelerometer. We&#8217;ll do this by building a small demo that allows the user to create sparkles by touching the screen, and to move them around by tilting the device. Over the course [...]]]></description>
			<content:encoded><![CDATA[<div id="Intro">
<h2>Introduction</h2>
<p><img class="alignright" src="http://www.abstrys.com/files/images/InputToy-Part1.png" alt="" width="200" height="264" />This article explores using XNA Game Studio to access the two primary forms of user input on the Zune HD: the multitouch screen, and the accelerometer. We&#8217;ll do this by building a small demo that allows the user to create sparkles by touching the screen, and to move them around by tilting the device.</p>
<p>Over the course of this tutorial, the following subjects will be covered:</p>
<ul>
<li>Multitouch input</li>
<li>Accelerometer input</li>
<li>Animating blended sprites</li>
<li>A simple UI  (in part two)</li>
</ul>
<p>I won&#8217;t be going over how to create a new XNA game project, nor will I describe how to add textures using the Content Pipeline. I assume that the reader has read enough about Game Studio to know how to do these things already. If you haven&#8217;t, I suggest downloading XNA Game Studio (a link is provided below) and going through the <a href="http://msdn.microsoft.com/en-us/library/bb203893.aspx">first tutorial</a> provided in the Game Studio documentation.</p>
<p><span id="more-5"></span></p>
<p>The full sample, including source code, images, and VS2008 project files, can be <a href="http://www.abstrys.com/files/source/InputToyZuneHD.zip">downloaded here</a>. Unless you want to make your own textures while following along with the tutorial, you&#8217;ll at least want to grab the images from the zip archive.</p>
</div>
<div id="Prereqs">
<h2>Prerequisites</h2>
<p><em>This is a Zune HD tutorial</em>: although some parts of the tutorial apply to all XNA Game Studio projects in general, much of the content here will apply only to devices that support both accelerometer and multi-touch input with XNA Game Studio 3.1. At the moment, that list begins and ends with the Zune HD. If you don&#8217;t already have a Zune HD, I&#8217;d recommend borrowing one from a friend, purchasing one, or sticking with Xbox 360 and Windows programming for now.</p>
<p>In addition to having access to a Zune HD, you&#8217;ll need the following software installed:</p>
<ul>
<li><em>Visual Studio 2008</em> &#8211; If you don&#8217;t already have Visual Studio 2008 Professional, you can download <a href="http://www.microsoft.com/express/Downloads/#2008-Visual-CS">Visual Studio 2008 Express edition</a>.</li>
<li><em>XNA Game Studio 3.1</em> &#8211; Available from the <a href="http://www.microsoft.com/downloads/details.aspx?FamilyID=80782277-D584-42D2-8024-893FCD9D3E82">Microsoft Download Center</a>.</li>
<li><em>XNA Game Studio 3.1 Zune Extensions</em> &#8211; Also available from the <a href="http://www.microsoft.com/downloads/details.aspx?familyid=48F7BA37-8BA7-4D16-8873-0B7F83EF77F9">Microsoft Download Center</a>.</li>
</ul>
<p>As I mentioned in the Introduction, you&#8217;ll also need an understanding of the basics of building an XNA Game Studio application.</p>
</div>
<div id="S1">
<h2>First Steps</h2>
<p>To begin, open Visual Studio 2008 and create a new XNA Game Studio project for Zune. Call it whatever you like. I called this project &#8220;InputToyZuneHD&#8221;.</p>
<p>Then, add some images to the project that we&#8217;ll be using. For now, all you&#8217;ll need is Flare.png, which contains the sparkle image. It looks like this:</p>
<p><img style="background: black;" src="http://www.abstrys.com/files/images/Flare.png" alt="The sparkle image" /><br />
Make sure the Asset Name in the <strong>Properties</strong> pane is &#8220;Flare&#8221; and the <strong>Build Action</strong> is &#8221;Compile&#8221;. We&#8217;re now ready to add some code to the project!</p>
</div>
<div id="AddingSparkles">
<h2>Adding Sparkles</h2>
<p>Open the file &#8220;Game1.cs&#8221; in your project, and right at the top of the <strong>Game1 </strong>class, add the following code:</p>
<pre>public class Game1 : Microsoft.Xna.Framework.Game
{
<span style="color: #008000;">    </span><strong><span style="color: #008000;">static Random random = new Random();
    class Sparkle
    {
        public Vector2 position;
        public Vector2 speed;
        public float rotation; // in radians
        public Color color;
        public long birthtime;

        public Sparkle(float x, float y, long time)
        {
            position = new Vector2(x, y);
            rotation = (float)(random.NextDouble() * 2.0 * Math.PI);
            color = Color.White;
            birthtime = time;
        }</span>
    <span style="color: #008000;">}</span></strong>
...</pre>
<p>First, we&#8217;re just setting up the random number generator, which we&#8217;ll be using when setting up sparkle rotation. Then, we create a class to hold information about each sparkle: its position, speed, rotation, color (which will be used to fade the sparkles), and birthtime (also used for fading).</p>
<p>Then, we&#8217;ll create a constructor that takes a position in screen coordinates (x,y), and a birthtime. We&#8217;re using the same image for all of the sparkles, so there&#8217;s no need to save any image-specific data in the sparkle class.</p>
<p>Notice that we use a random rotation for each sparkle when it&#8217;s created. This helps, since we&#8217;re using the same image, from keeping every sparkle look exactly like the others when it appears. <strong>Random.NextDouble</strong> produces a number between zero and one, so by multiplying it by 2*PI, we can get a random rotation in radians.</p>
<p>Next, we define some constants that will be used to fade sparkles. We&#8217;ll define a maximum lifetime for each sparkle, the maximum number of sparkles allowed on the screen at once, an acceleration factor for sparkle movement, and a factor to control how quickly the sparkles will fade out.</p>
<p>Add this code beneath the definition of the <strong>Sparkle</strong> class:</p>
<pre><span style="color: #008000;"><strong>const int SPARKLELIFE = 4000; // ticks
const int MAXSPARKLES = 100; // maximum number of sparkles, for performance tuning.
const float ACCELFACTOR = 0.01f;
const float FADEFACTOR = 255.0f / SPARKLELIFE;</strong></span></pre>
<p>We&#8217;ll now add a few variables to the class to hold the sparkle data. In <strong>Game1</strong>&#8216;s class data section, where the <em>graphics</em> and <em>spriteBatch </em>members are declared, add new data members called <em>flareImage</em>, <em>flareOffset</em>, and <em>sparkles</em>, as shown:</p>
<pre>GraphicsDeviceManager graphics;
SpriteBatch spriteBatch;
<span style="color: #008000;"><strong>Texture2D flareImage;
Vector2 flareOffset;
List&lt;Sparkle&gt; sparkles;</strong></span></pre>
</div>
<div id="LoadingSparkles">
<h2>Loading the Sparkle Image</h2>
<p>There&#8217;s one last thing we&#8217;ll need to do before creating and drawing sparkles, and that&#8217;s loading the sparkle image into the <strong>Texture2D</strong> that we&#8217;ve declared for it.</p>
<p>In <strong>Game1.LoadContent</strong>, add lines to load the flare image and set the flare offset:</p>
<pre>// Create a new SpriteBatch, which can be used to draw textures.
spriteBatch = new SpriteBatch(GraphicsDevice);<span style="color: #008000;">
<strong>flareImage = this.Content.Load&lt;Texture2D&gt;("Flare");
flareOffset = new Vector2(
    flareImage.Width * 0.5f, flareImage.Height * 0.5f);</strong></span></pre>
<p>The <em>flareOffset</em> will be used to rotate the sparkles, and is set to the middle of the sparkle texture.</p>
</div>
<div id="CreatingSparkles">
<h2>Creating Sparkles with Touch</h2>
<p>Now, let&#8217;s add some code that uses touch to create sparkles. We&#8217;ll allow the user to touch the screen to create a sparkle, or to create many sparkles by touching multiple points at the same time or by dragging a touch-point.</p>
<p>All of the code in this section will go into <strong>Game1.Update</strong>.</p>
<p>First, we&#8217;ll get the total game time as a <em>long</em>. The <strong>GameTime</strong> structure that&#8217;s passed to <strong>Update</strong> contains a number of members for different timing purposes. Since the sparkle birth-time is something that we&#8217;ll be tracking starting from the beginning of app launch, we&#8217;ll use the <strong>TotalGameTime</strong> member to get a timestamp for sparkle creation. This will allow us to fade the sparkles out over time, and to remove them from the list once they&#8217;ve faded.</p>
<p>To add a sparkle to a location touched on the screen, we&#8217;ll get the <strong>TouchCollection</strong> that contains all of the touch points (represented by the <strong>TouchLocation</strong> structure) that are active (either <strong>Pressed</strong> or <strong>Moved</strong>) this  frame. Iterating through the list and adding sparkes at the <strong>TouchLocation.Position</strong> points is simple, as shown in the following code:</p>
<p>Add the following code to <strong>Update</strong>:</p>
<pre>// Allows the game to exit
if (GamePad.GetState(PlayerIndex.One).Buttons.Back == ButtonState.Pressed)
{
   this.Exit();
}

<strong><span style="color: #008000;">long ttms = (long)gameTime.TotalGameTime.TotalMilliseconds;
<span style="color: #008000;">
</span></span><span style="color: #008000;">// Process touch events
TouchCollection touchCollection = TouchPanel.GetState();
foreach (TouchLocation tl in touchCollection)
{
      // add sparkles based on the touch location
      sparkles.Add(new Sparkle(tl.Position.X,
               tl.Position.Y, ttms));
}</span></strong>
</pre>
<p>We call <strong>TouchPanel.GetState</strong> to get the <strong>TouchCollection</strong>, and then simply iterate through each <strong>TouchLocation</strong>, passing the X and Y locations and the timestamp to <strong>Sparkle</strong>&#8216;s constructor to add a new sparkle to the list.</p>
<p>We now have the code to add sparkles, but there&#8217;s still a problem that we need to solve: if you simply continue to add sparkles, you&#8217;ll soon have many thousands of sparkles on the list, which could really drag down your framerate.</p>
<p>To keep the frame-rate up, we should limit the number of objects that are being updated and drawn each frame. We&#8217;ll impose a limit, represented by <em>MAXSPARKLES</em>, on the number of sparkles that can be in the list at once, by removing sparkles from the beginning of the list if there are too many sparkles in existence. Right after adding a new sparkle, add code to remove the sparkles:</p>
<pre>foreach (TouchLocation tl in touchCollection)
{
   // add sparkles based on the touch location
    sparkles.Add(new Sparkle(tl.Position.X,
             tl.Position.Y, ttms));
<span style="color: #008000;">
<strong>   // if there are too many sparkles, remove from the head.
   if (sparkles.Count &gt; MAXSPARKLES)
   {
      sparkles.RemoveAt(0);
   }</strong></span>
}
</pre>
<p><strong>Note:</strong> The sparkles are removed from the front of the list since these are the oldest sparkles: new sparkles are always added at the end. It would be quite unexpected (in other words, it would seem like a bug) from the user&#8217;s point-of-view if just-created sparkles suddenly disappeared!</p>
</div>
<div id="DrawingSparkles">
<h2>Drawing the Sparkles</h2>
<p>We now have the ability to add sparkles to our world, but unless we draw them on the screen, nobody (but you) will know they exist!</p>
<p>Drawing the sparkles on the screen is a simple matter of iterating through the list we&#8217;ve created, and drawing the Flare image at the location of each sparkle. In <strong>Game1.Draw</strong>, add the following code:</p>
<pre>protected override void Draw(GameTime gameTime)
{
    GraphicsDevice.Clear(<span style="color: #008000;"><strong>Color.Black</strong></span>);
<span style="color: #008000;">    <strong>spriteBatch.Begin();
    // draw the sparkles
    foreach(Sparkle s in sparkles)
    {
        // when drawing with a specified origin, the origin affects
        // both the rotation and position parameters.
        spriteBatch.Draw(
            flareImage, s.position, null, s.color, s.rotation,
            flareOffset, 1.0f, SpriteEffects.None, 0);
    }
    spriteBatch.End();
<span style="color: #000000;">...</span></strong></span></pre>
<p>There are a number of <strong>SpriteBatch.Draw</strong> overloads provided in Game Studio, but we&#8217;ll use the version shown above since we&#8217;ll eventually want to change the color and rotation of each sparkle. For now, the color will always be <strong>Color.White </strong>and the rotation will always be zero.</p>
<p>The default template code for an XNA Game Studio game clears the screen to <strong>Color.CornflowerBlue</strong>. While this is a good color to use for debugging purposes, I&#8217;ve designed the sparkle image to look best on a black background. The clear color was changed to <strong>Color.Black</strong> to complement this.</p>
<p>If you&#8217;d like, compile and run the application on your Zune HD. You should be able to draw sparkles on the screen with your fingertips, and watch them disappear as you pass the MAXSPARKLES threshhold.</p>
</div>
<div id="FadingSparkles">
<h2>Fading the Sparkles</h2>
<p>Although the above code removes sparkles from the list if there are too many, it&#8217;s likely that the user will notice sparkles suddenly vanishing from the display. It&#8217;s much nicer if we fade them out, so the user feels that the eventual dissapearance of the sparkle is natural within the design of the world we&#8217;re creating.</p>
<p>To do this, we&#8217;ll make use of the sparkle&#8217;s timestamp, comparing it to the current timestamp to fade the sparkle depending on its age. We&#8217;ll place this code directly after the code, entered in the previous section, that creates the sparkles in the Update method.</p>
<pre><span style="color: #008000;"><strong>// update the sparkles. We count from the end of the list in case
// we need to remove a sparkle (without upsetting the order).
for (int i = sparkles.Count - 1; i &gt;= 0; i--)
{
    Sparkle s = sparkles[i];
    if ((ttms - s.birthtime) &gt; SPARKLELIFE)
    {
        sparkles.RemoveAt(i);
        continue;
    }
    else
    {
        // fade the sparkle a bit, depending on its age.
        s.color.A = (byte)(255.0f - (ttms - s.birthtime) * FADEFACTOR);
    }
}</strong></span></pre>
<p>If the sparkle has passed the end of its lifetime, it&#8217;s removed from the list.</p>
<p>Rebuild and deploy your updated application. You should now see the sparkles fading!</p>
</div>
<div id="AddingMotion">
<h2>Adding Motion with the Accelerometer</h2>
<p>We&#8217;ll now use the Zune HD&#8217;s accelerometer to move the sparkles around on the screen, and add a little speed-based rotation to the sparkles to make them more interesting.</p>
<p>To do this, directly after the total game time calculation, get the elapsed game time in milliseconds, and then get the accelerometer state as shown:</p>
<pre>long ttms = (long)gameTime.TotalGameTime.TotalMilliseconds;

<span style="color: #008000;"><strong>// elapsed time will be used in updating movement
float etms = gameTime.ElapsedGameTime.Milliseconds;
</strong></span>
<span style="color: #008000;"><strong>// grab the accelerometer state.  This will be used for sparkle
// movement.</strong>
</span><span style="color: #008000;"><strong>AccelerometerState accelState = Accelerometer.GetState();</strong></span></pre>
<p>The elapsed game time will be used during sparkle movement. Since I&#8217;m only interested in the elapsed time since the last frame, and I&#8217;m not ever expecting this to be more than a second, I use only <strong>ElapsedGameTime.Milliseconds</strong>.</p>
<p>Next, inside the loop used to update the sparkles, right below the code to fade the sparkles, add the following lines:</p>
<pre>// fade the sparkle a bit, depending on its age.
s.color.A = (byte)(255.0f - (ttms - s.birthtime) * FADEFACTOR);

<span style="color: #008000;"><strong>// accelerate the sparkle depending on accelerometer action.
s.speed.X += accelState.Acceleration.X * ACCELFACTOR;
s.speed.Y += -accelState.Acceleration.Y * ACCELFACTOR;

// move the sparkle based on its speed.
s.position.X += s.speed.X * etms;
s.position.Y += s.speed.Y * etms;
s.rotation += s.speed.Length() * ACCELFACTOR * etms;</strong></span></pre>
<p>We&#8217;re adding speed to each sparkle based on the current state of the accelerometer, and then updating its position based on its speed. Additionally, we&#8217;re adding a bit of rotation depending on the magnitude of the resulting speed vector. As simple as it is, the effect looks fairly nice.</p>
<p>No changes are needed to the drawing code. Once you rebuild and deploy, you should now see the sparkles moving as you tilt the device.</p>
</div>
<div id="Next">
<h2>What&#8217;s Next?</h2>
<p>The Sparkle application is fairly complete, but for a user who doesn&#8217;t know how it works, it might seem a bit mystifying: unless you touch the screen once it starts, you only see a black screen.</p>
<p>It would be nice to have some instructions pop up as the application starts, and perhaps a way to &#8220;freeze&#8221; the sparkle fading so that the user has more time to play with the sparkles as they slide around the screen.</p>
<p>In the next part of the tutorial, I&#8217;ll add a GUI that consists of an instructions screen and a menu that appears at the bottom of the screen.</p>
<p><strong>Continue with</strong>: <a href="http://www.abstrys.com/2010/02/making-the-zune-hd-sparkle-with-xna-game-studio-3-1-part-2/" target="_self">Making the Zune HD Sparkle with XNA Game Studio 3.1 &#8211; Part 2</a></p>
</div>
]]></content:encoded>
			<wfw:commentRss>http://www.abstrys.com/2010/02/making-the-zune-hd-sparkle-with-xna-game-studio-3-1-part-1/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
	</channel>
</rss>

