<?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>addChild(blog)</title>
	<atom:link href="http://blog.andrewtraviss.com/feed/" rel="self" type="application/rss+xml" />
	<link>http://blog.andrewtraviss.com</link>
	<description>Flash and Flex Game Development</description>
	<lastBuildDate>Fri, 28 Oct 2011 07:57:16 +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>Using Ethics to Fight Contrivances? Have We Learned Nothing from Pokemon?</title>
		<link>http://blog.andrewtraviss.com/2011/10/28/using-ethics-to-fight-contrivances-have-we-learned-nothing-from-pokemon/</link>
		<comments>http://blog.andrewtraviss.com/2011/10/28/using-ethics-to-fight-contrivances-have-we-learned-nothing-from-pokemon/#comments</comments>
		<pubDate>Fri, 28 Oct 2011 07:57:16 +0000</pubDate>
		<dc:creator>ninjasquirrel</dc:creator>
				<category><![CDATA[Uncategorized]]></category>

		<guid isPermaLink="false">http://blog.andrewtraviss.com/?p=544</guid>
		<description><![CDATA[Recently, Adam Saltsman made a two part post (Part One) (Part Two) critiquing aspects of social games and &#8220;freemium&#8221; business models. I share the distaste for the tactics, but we need to carefully consider what our opponent&#8217;s strengths and weaknesses are. Otherwise all we&#8217;re doing is talking for the sake of talk. First of all, [...]]]></description>
			<content:encoded><![CDATA[<p>Recently, Adam Saltsman made a two part post (<a href="http://www.gamasutra.com/blogs/AdamSaltsman/20111018/8685/Contrivance_and_Extortion_InApp_Purchases__Microtransactions.php" title="Part One" target="_blank">Part One</a>) (<a href="http://www.gamasutra.com/blogs/AdamSaltsman/20111020/8703/Contrivance_and_Extortion_II_Clarifications_Feedback__Suggestions.php" title="Part Two" target="_blank">Part Two</a>) critiquing aspects of social games and &#8220;freemium&#8221; business models. I share the distaste for the tactics, but we need to carefully consider what our opponent&#8217;s strengths and weaknesses are. Otherwise all we&#8217;re doing is talking for the sake of talk.<br />
<a href="http://blog.andrewtraviss.com/wp-content/uploads/2011/10/ethicsnotveryeffective.png"><img src="http://blog.andrewtraviss.com/wp-content/uploads/2011/10/ethicsnotveryeffective.png" alt="Ethics: Not very effective" title="Ethics: Not very effective" width="500" height="137" class="aligncenter size-full wp-image-550" /></a></p>
<p><span id="more-544"></span></p>
<p>First of all, it&#8217;s not going to work. At best you can stop indie developers from copy-catting the big players in the industry by talking ethics. You&#8217;re not going to have any effect on the massive tide of dollars Zynga is riding by imploring their developers to reconsider doing what Zynga is asking them to do.</p>
<p>Furthermore, when we use ethics to attack the techniques used by abusive freemium titles, we are implying that these techniques are <b>too effective</b> and that there is no recourse available to us but to abstain from their use. As if they were some kind of super weapon. Which is ridiculous, because every one of the problematic techniques relies on flat-out bad game design. Really, the recipe for a lucrative freemium game is to take a solid game design and strategically break it in several places. Then you charge the player to get past the things you broke.</p>
<p><img src="http://blog.andrewtraviss.com/wp-content/uploads/2011/10/designsupereffective.png" alt="" title="designsupereffective" width="500" height="137" class="aligncenter size-full wp-image-553" /></p>
<p>We should be looking back at arcades and asking ourselves what killed them and the equally exploitative design choices that they encouraged. It wasn&#8217;t a sudden epidemic of ethics on the part of developers and publishers that killed arcades. Better games killed arcades. Games that didn&#8217;t lure you in with one relatively easy level and then beat you up for your lunch money. I think that our current situation is exactly the same, minus the better games. It&#8217;s about time for history to repeat itself.</p>
<p>So, my question is, why are we fighting inferior game design with ethics, rather than with superior game design?</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.andrewtraviss.com/2011/10/28/using-ethics-to-fight-contrivances-have-we-learned-nothing-from-pokemon/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Performance Monitoring Tool for Actionscript 3.0</title>
		<link>http://blog.andrewtraviss.com/2011/04/23/performance-monitoring-tool-for-actionscript-3-0/</link>
		<comments>http://blog.andrewtraviss.com/2011/04/23/performance-monitoring-tool-for-actionscript-3-0/#comments</comments>
		<pubDate>Sat, 23 Apr 2011 13:17:39 +0000</pubDate>
		<dc:creator>ninjasquirrel</dc:creator>
				<category><![CDATA[Libraries]]></category>
		<category><![CDATA[performancemonitor]]></category>

		<guid isPermaLink="false">http://blog.andrewtraviss.com/?p=497</guid>
		<description><![CDATA[For a recent project I created a performance graph which helped me to identify which parts of my engine were responsible for performance issues. Based on that, I have developed a flexible PerformanceMonitor class which can expanded on to track performance in a number of ways. The default implementation produces a pair of graphs like [...]]]></description>
			<content:encoded><![CDATA[<p>For a recent project I created a performance graph which helped me to identify which parts of my engine were responsible for performance issues. Based on that, I have developed a flexible PerformanceMonitor class which can expanded on to track performance in a number of ways. The default implementation produces a pair of graphs like so.</p>
<p><img class="alignnone size-medium wp-image-498" title="performancegraph" src="http://blog.andrewtraviss.com/wp-content/uploads/2011/04/performancegraph.png" alt="" width="300" height="184" /></p>
<p>Each colour corresponds to a different task that my application performs. Perhaps blue represents AI execution time, red represents rendering, and teal represents mouse handling. The graph on the left reports the time spent on each task I am tracking per update. The green area gives me an indication of whether Flash is dropping frames due to the execution time of my code. On the right is a bar graph showing the relative weight of each task over the lifetime of the application. More details on use after the cut.</p>
<p><a href="https://github.com/andrewtraviss/PerformanceMonitor">Get it from GitHub.</a></p>
<p><span id="more-497"></span></p>
<p>There are a few simple steps to tracking performance with this tool. The first is to create the graphs themselves.</p>
<p>The GraphTimePerUpdate graph is configured with a target time per update, which should be chosen depending on your frame rate. The limit specified in the next line controls the scale of the graph. In this example, an update which uses exactly 99 units of time will fill the whole vertical height of the graph. Then we create the display at the desired size and add it to the stage.</p>
<pre class="brush: as3; title: ; notranslate">private function createPerUpdateGraph():void
{
	_perUpdateGraph = new GraphTimePerUpdate();
	_perUpdateGraph.targetTimePerUpdate(33);
	_perUpdateGraph.limitTimeForDisplay(99);
	var graphData:BitmapData = _perUpdateGraph.createDisplay(300,200);
	var graphBitmap:Bitmap = new Bitmap(graphData);
	addChild(graphBitmap);
}</pre>
<p>Creating the GraphTotalTimeSpent graph is a much simpler process. We only need to create the display and add it to the stage.</p>
<pre class="brush: as3; title: ; notranslate">private function createTotalGraph():void
{
	_totalGraph = new GraphTotalTimeSpent();
	var graphData:BitmapData = _totalGraph.createDisplay(24, 200);
	var graphBitmap:Bitmap = new Bitmap(graphData);
	graphBitmap.x = 300;
	addChild(graphBitmap);
}</pre>
<p>With our two graphs constructed, we need to configure the PerformanceMonitor that drives them. The first three lines declare the performance metrics that will be tracked, and what colours to use when rendering them. The following lines plug the graphs into the PerformanceMonitor to receive updates.</p>
<pre class="brush: as3; title: ; notranslate">private function configureMonitor():void
{
	var monitor:PerformanceMonitor = PerformanceMonitor.instance;
	monitor.initializePerformanceMetric(&quot;rendering&quot;, 0, 0xff0000);
	monitor.initializePerformanceMetric(&quot;ai&quot;, 1, 0x0000ff);
	monitor.initializePerformanceMetric(&quot;mouse&quot;, 2, 0x00ffff);
	monitor.addReporter(_perUpdateGraph);
	monitor.addReporter(_totalGraph);
}</pre>
<p>With that configured, the PerformanceMonitor is ready to go. All that remains is to report metrics and tell the PerformanceMonitor to update. For this example, I am just randomizing the first two metrics and basing the second off of mouse movement in order to illustrate how to report them. Normally you would use getTimer to determine the time to execute some complex functionality and then report the result of that.</p>
<pre class="brush: as3; title: ; notranslate">private function handleEnterFrame(in_event:Event):void
{
	PerformanceMonitor.instance.recordPerformanceMetric(0, Math.random()*5 + 10);
	PerformanceMonitor.instance.recordPerformanceMetric(1, Math.random()*5);
	PerformanceMonitor.instance.update();
}

private function handleMouseMove(in_event:MouseEvent):void
{
	var xDiff:Number = mouseX - _lastX;
	var yDiff:Number = mouseY - _lastY;
	var distance:Number = Math.sqrt((xDiff*xDiff)+(yDiff*yDiff));
	PerformanceMonitor.instance.recordPerformanceMetric(2, distance);
	_lastX = mouseX;
	_lastY = mouseY;
}</pre>
]]></content:encoded>
			<wfw:commentRss>http://blog.andrewtraviss.com/2011/04/23/performance-monitoring-tool-for-actionscript-3-0/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>Studio Space for Game Developers in Toronto</title>
		<link>http://blog.andrewtraviss.com/2011/04/22/studio-space-for-game-developers-in-toronto/</link>
		<comments>http://blog.andrewtraviss.com/2011/04/22/studio-space-for-game-developers-in-toronto/#comments</comments>
		<pubDate>Fri, 22 Apr 2011 14:43:05 +0000</pubDate>
		<dc:creator>ninjasquirrel</dc:creator>
				<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[Game Development]]></category>
		<category><![CDATA[Toronto]]></category>

		<guid isPermaLink="false">http://blog.andrewtraviss.com/?p=493</guid>
		<description><![CDATA[I just read this post by Greg Beaton on his Art of Game blog from back in February. Late last year I was talking to Alex about the same basic idea. Whenever I&#8217;m working on game projects I&#8217;m usually holed up in my computer room at home for hours on end, and sometimes the creative [...]]]></description>
			<content:encoded><![CDATA[<p>I just read this <a href="http://artofgame.wordpress.com/2011/02/08/community-studio/">post</a> by Greg Beaton on his <a href="http://artofgame.wordpress.com/">Art of Game blog</a> from back in February. Late last year I was talking to Alex about the same basic idea. Whenever I&#8217;m working on game projects I&#8217;m usually holed up in my computer room at home for hours on end, and sometimes the creative energy can be really difficult to sustain. Unlike a lot of other artistic disciplines, game developers are more tethered to equipment needs and can&#8217;t easily get a change of scenery while working. A common studio space for game development is a fantastic idea.</p>
<p>I&#8217;m not so sure about adding the additional overhead of selling merchandise on site, especially at the onset. Although, decent quality concessions are a pretty easy sell with game developers, as the TOJam concession stand demonstrates every year.</p>
<p>Game jams bring us together to achieve a short term goal every once in a while, but I&#8217;m really interested in a studio concept that would see local developers working closely on an ongoing basis. I hope this idea goes somewhere. I&#8217;m going to start bringing it up with other local developers and see if there&#8217;s any traction.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.andrewtraviss.com/2011/04/22/studio-space-for-game-developers-in-toronto/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Game Engine Design, Part Two: Triggers, Responses, and Katamaris</title>
		<link>http://blog.andrewtraviss.com/2011/04/16/game-engine-design-part-two-triggers-responses-and-katamaris/</link>
		<comments>http://blog.andrewtraviss.com/2011/04/16/game-engine-design-part-two-triggers-responses-and-katamaris/#comments</comments>
		<pubDate>Sat, 16 Apr 2011 17:31:26 +0000</pubDate>
		<dc:creator>ninjasquirrel</dc:creator>
				<category><![CDATA[General Software Development]]></category>
		<category><![CDATA[Engine Design]]></category>
		<category><![CDATA[Game Development]]></category>

		<guid isPermaLink="false">http://blog.andrewtraviss.com/?p=468</guid>
		<description><![CDATA[This is the second part of my series on game engine design. I&#8217;ve spent some time throwing around various ideas about the principal entities that a game engine should be concerned with and how they relate to each other. I&#8217;m going to hold off on any class diagrams or specific examples for the time being. [...]]]></description>
			<content:encoded><![CDATA[<p>This is the second part of my series on game engine design. I&#8217;ve spent some time throwing around various ideas about the principal entities that a game engine should be concerned with and how they relate to each other. I&#8217;m going to hold off on any class diagrams or specific examples for the time being. This is all a thought exercise until the next entry, where I&#8217;ll analyze some specific examples and start generating some pseudo code for how I would like those use cases to look from the game developer&#8217;s perspective.</p>
<p><span id="more-468"></span></p>
<h2>The Rules</h2>
<p>Let&#8217;s get the obvious one out of the way first. Rules have a couple of parts that I plan to treat separately. Any rules, in its simplest form, consists of a trigger and a response. All rules can be broken down and expressed in this form, and in terms of responsibilities at the code level the division makes sense. These two concepts are troublemakers. They tend to need access to every system and object in your game to do their jobs, which gets messy fast.</p>
<h3>Trigger</h3>
<p>A trigger&#8217;s responsibility is to recognize a scenario and report that recognition to the system. They must be informed of state changes and have the ability to poll systems for information.</p>
<h3>Response</h3>
<p>A response has the responsibility of executing a change to the game&#8217;s entities. They require the ability to manipulate the relationship between objects and game systems, change object properties and potentially trigger non-game functionality (metrics reporting, client/server protocol, etc)</p>
<h2>The Infamous GameObject</h2>
<h3>Making a Katamari of System Data</h3>
<p>There&#8217;s a common problem in game development. You have various systems that each need their own object-specific data, and you have your game object. In most cases, the game object class rolls through your code like a Katamari picking up odds and ends from every minor subsystem and feature in your game. Avoiding the Katamari game object anti-pattern is probably one of the best things that a game engine can strive for. If this is allowed to happen, the game object class becomes monolothic and inevitable naming collisions result in awkward or confusing variable and method names. How often have you seen duplicate position variables to handle world coordinates vs screen coordinates?</p>
<h3>Divide and Conquer</h3>
<p>There&#8217;s actually no compelling reason to store all of the data for a single conceptual object in one class. It feels natural to associate a single software object with the single conceptual object that it represents, but it&#8217;s neither necessary nor wise. A better system is to create multiple views of an object. A PhysicsView might have a bounding box, mass, x-velocity, and y-velocity properties, for example. A PlayerStatsView class might hold the player&#8217;s health and energy. Neither system needs to be aware of the other or the data it uses.</p>
<h3>Synchronization</h3>
<p>We&#8217;ve separated our systems from each other and sequestered their related data, so we need a method to synchronize data between the Views which actually represent the same or related information. I&#8217;ve identified two ways of doing this which I&#8217;m planning to test out in my initial implementation.</p>
<p>If a value is encapsulated in an object, rather than being a native type that is passed by value, you can share that reference between the View classes. This solution performs well and is easy to implement, but it only works in situations where the value should be exactly the same from the perspective of both systems.</p>
<p>The second method of synchronization is through explicit synchronization classes which are fully aware of the two (or more) Views that they will synchronize. These are much less flexible in terms of how they are integrated. They must make an assumption about the order in which systems are updated. However, they are flexible in terms of how values can related to each other.</p>
<h3>Atomic Power</h3>
<p>I have shied away from dynamic objects for a long time because I associate them with Actionscript 1.0 debugging nightmares. It&#8217;s time to dust it off and employ the technique where it makes sense. If we separate all of our object data, we still need a centralized way to access that data from responses and triggers without having to hunt around in a dozen places for it. Enter Flash&#8217;s &#8220;Atom&#8221; type, denoted by an asterisk (*).</p>
<p>If we store references to all of the views on the atomic object, we can still benefit from the speed advantage of strict typing, because any performance-sensitive system works with a strongly-type View class. At the same time, we don&#8217;t need to maintain a game object class with variables defined for every possible type of data that an object might need to hold.</p>
<p>An additional benefit is that every game object only has to carry the data that it actually needs with it. You won&#8217;t be stuck creating infinite subclasses of GameObject to add specific capabilities. Composition over inheritance.</p>
<h3>Objects At Rest</h3>
<p>It&#8217;s very important to note that with this system, objects have no functions to call. Views should not have any function either, aside from those which report state information. The great thing about this type of system is that when your objects have no behaviour, you can test the behaviour a lot more easily, and mix behaviours a lot more freely, just by pointing the appropriate system at your game objects.</p>
<h2>Templating</h2>
<p>Most of the time, games need to create several similar or identical objects. This is pretty straightforward if you&#8217;re just subclassing left and right, but if we&#8217;re using composition there&#8217;s a little more legwork involved. The game engine will need a templating system which can take care of creating the appropriate Views and assigning them to the game object, as well as applying any initial rules and plugging the game object into the appropriate systems.</p>
<p>That&#8217;s our cast of characters for the time being. It will be a little while before I can get to part three; crunch time is upon me for two projects at once and I want to keep working away on AScalpel, but I&#8217;ll have it up as soon as it&#8217;s ready.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.andrewtraviss.com/2011/04/16/game-engine-design-part-two-triggers-responses-and-katamaris/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>AScalpel Basic User Guide</title>
		<link>http://blog.andrewtraviss.com/2011/04/12/ascalpel-user-guide/</link>
		<comments>http://blog.andrewtraviss.com/2011/04/12/ascalpel-user-guide/#comments</comments>
		<pubDate>Wed, 13 Apr 2011 01:59:57 +0000</pubDate>
		<dc:creator>ninjasquirrel</dc:creator>
				<category><![CDATA[Library]]></category>
		<category><![CDATA[AScalpel]]></category>

		<guid isPermaLink="false">http://blog.andrewtraviss.com/?p=395</guid>
		<description><![CDATA[I&#8217;ve been working away on AScalpel for a while now, polishing it and adding some new features to it. It&#8217;s settled enough now that I can sit down and write a real step-by-step guide to using it. There is also a sample application included with the AScalpel library which is already integrated. Compile com.andrewtraviss.ascalpel.sample::BouncingBallSample.as as [...]]]></description>
			<content:encoded><![CDATA[<p>I&#8217;ve been working away on AScalpel for a while now, polishing it and adding some new features to it. It&#8217;s settled enough now that I can sit down and write a real step-by-step guide to using it.</p>
<p>There is also a sample application included with the AScalpel library which is already integrated. Compile com.andrewtraviss.ascalpel.sample::BouncingBallSample.as as an application to view it.<br />
<span id="more-395"></span></p>
<h2>Setup</h2>
<h3>Downloads</h3>
<ol>
<li>Latest AScalpel build from <a title="AScalpel on GitHub" href="https://github.com/andrewtraviss/AScalpel/" target="_blank">GitHub</a></li>
<li>Latest Minimal Components from <a title="Minimal Components on GitHub" href="https://github.com/minimalcomps/minimalcomps" target="_blank">GitHub</a></li>
</ol>
<h3>Project Setup</h3>
<p>Start by creating a new Actionscript 3.0 project and copying the AScalpel and Minimal Component source files into the source directory. Once that&#8217;s done, you need to do two things to get AScalpel up and running. By default, AScalpel isn&#8217;t configured to handle most situations. The AScalpel package includes a helper class to configure it for common cases. Once you call StandardBit101Components.install, the system is ready to handle basic data types using the Minimal Components.</p>
<p>In order to actually see the editors you need to add AScalpel to the display list. AScalpel is a singleton, so you&#8217;ll need to access its display through AScalpel.instance.display. Be sure to keep this object on top of your game.</p>
<p>Your Main constructor should look something like this now.</p>
<pre class="brush: as3; title: ; notranslate">[SWF(width=&quot;600&quot;, height=&quot;450&quot;)]
public class Main extends Sprite
{
	public function Main()
	{
		StandardBit101Editors.install();
		addChild(AScalpel.instance.display);
	}
}</pre>
<h2>Simple Integration</h2>
<h3>Opening the Object Editor</h3>
<p>Before we get started, we&#8217;ll need an object to play with. For the sake of example, I&#8217;m going to use a simple bouncing ball demo. Here is our BouncingBall class without any metadata.</p>
<pre class="brush:as3">package com.andrewtraviss.ascalpel.sample
{
	import flash.display.DisplayObject;
	import flash.display.Sprite;
	import flash.utils.getQualifiedClassName;

	public class BouncingBall
	{
		public function BouncingBall()
		{
			_sprite = new Sprite();
			redraw();
		}

		public function redraw():void
		{
			_sprite.graphics.clear();
			_sprite.graphics.beginFill(_color);
			_sprite.graphics.drawCircle(x,y,_radius);
			_sprite.graphics.endFill();
		}

		public function get radius():Number
		{
			return _radius;
		}
		public function set radius(in_value:Number):void
		{
			_radius = in_value;
			redraw();
		}

		public function get color():uint
		{
			return _color;
		}
		public function set color(in_value:uint):void
		{
			_color = in_value;
			redraw();
		}

		public function get sprite():DisplayObject
		{
			return _sprite;
		}

		public var x:Number = 0;
		public var y:Number = 0;
		public var xVelocity:Number = 0;
		public var yVelocity:Number = 0;
		public var name:String;

		private var _radius:Number = 1;
		private var _color:uint = 0x000000;
		private var _sprite:Sprite;
	}
}</pre>
<p>Once we have our object class, all we need to do is create an instance of it, and use AScalpel to open it. Our updated constructor looks like this.</p>
<pre class="brush:as3">[SWF(width="600", height="450")]
public class Main extends Sprite
{
	public function Main()
	{
		StandardBit101Editors.install();
		var ball:BouncingBall = new BouncingBall();
		addChild(ball.sprite);
		addChild(AScalpel.instance.display);
		AScalpel.instance.open(ball);
	}
}</pre>
<p>If you run this simple example, you should see a tiny editor window with nothing in it.</p>
<p><img class="alignnone size-full wp-image-404" title="emptyEditor" src="http://blog.andrewtraviss.com/wp-content/uploads/2011/04/emptyEditor.png" alt="" width="52" height="57" /></p>
<p>There&#8217;s nothing in it because we haven&#8217;t  told AScalpel anything about the BouncingBall class yet.</p>
<h3>A Little Bit About Metadata</h3>
<p>If you haven&#8217;t worked with metadata before, it&#8217;s fairly simple. All metadata is enclosed in square brackets, as in [Editable]. If there are parameters being passed with metadata, they are placed in parentheses inside the square brackets. For example, [Editable(explicitCommit="true")]. Metadata is available at runtime through the describeType method. This spits out an XML that contains every detail about the object you apply it to. AScalpel uses this XML to create its editor windows.</p>
<h3>Adding Basic AScalpel Metadata</h3>
<p>The easiest way to integrate with AScalpel is to simply slap the [Editable] tag on the line above each property you want to edit. For example:</p>
<pre class="brush:as3">[Editable]
public var x:Number = 0;</pre>
<p>In our example, I chose to make all of the public variables and getter/setters editable except for the name property. If you do that and run the example again, you&#8217;ll see something that looks much more useful than the last time.</p>
<p><img class="alignnone size-full wp-image-409" title="editorStep2" src="http://blog.andrewtraviss.com/wp-content/uploads/2011/04/editorStep2.png" alt="" width="182" height="271" /></p>
<p>You can now edit all of these properties. There&#8217;s a problem, though. As you type numbers into the fields, the object reacts to the changes instantly. This is probably not what you want in all cases. When you type in 400 for x, the object shouldn&#8217;t move to 4, then 40, then 400. AScalpel has a solution for this problem. For the position and velocity properties, we&#8217;ll use the explicitCommit option.</p>
<pre class="brush:as3">[Editable(explicitCommit="true")]
public var x:Number = 0;</pre>
<p>And now that section of the editor looks like this. When a property is marked for explicit commit, the editor creates a button for that property which applies the current value when you click on it.<br />
<img class="alignnone size-full wp-image-411" title="editorStep3" src="http://blog.andrewtraviss.com/wp-content/uploads/2011/04/editorStep3.png" alt="" width="234" height="109" /></p>
<h2>Advanced Integration</h2>
<h3>Specifying Editors</h3>
<p>Continuing our above example, there are a few things that could be improved. The colour field accepts a uint value instead of a proper colour hex value, which is cumbersome to work with. To solve this problem, we can tell AScalpel to use a different control to edit the colour field. By using editorClass we can use any custom class as an editor. In this case, the Minimal Components Color Chooser control is enough, and is part of the standard installation. So we can just change the Editable tag for the color property like so.</p>
<pre class="brush:as3">
[Editable(editorClass="com.bit101.components.ColorChooser")]
public function get color():uint
{
	return _color;
}
public function set color(in_value:uint):void
{
	_color = in_value;
	redraw();
}
</pre>
<p>Which gives us this.<br />
<img title="editorStep4" src="http://blog.andrewtraviss.com/wp-content/uploads/2011/04/editorStep4.png" alt="" width="240" height="24" /></p>
<h3>Editor Properties</h3>
<p>Perhaps we want to limit the radius of the ball within a particular range. The NumericStepper component supports minimum and maximum, so we will use that. We can set the minimum and maximum, and the step size on the NumericStepper just by adding those properties into the Editable tag. If AScalpel doesn&#8217;t recognize a metadata property, it will check for that property on the editor class and try to apply the value to it.</p>
<pre class="brush:as3">[Editable(editorClass="com.bit101.components.NumericStepper", minimum="1", maximum="30", step="0.1")]
public function get radius():Number
{
	return _radius;
}
public function set radius(in_value:Number):void
{
	_radius = in_value;
	redraw();
}</pre>
<p><img title="editorStep5" src="http://blog.andrewtraviss.com/wp-content/uploads/2011/04/editorStep5.png" alt="" width="236" height="23" /><br />
I will post an Advanced User Guide later on to describe how to create custom editors and change the default behaviour of AScalpel.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.andrewtraviss.com/2011/04/12/ascalpel-user-guide/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>A Quick Guide to TOJamming</title>
		<link>http://blog.andrewtraviss.com/2011/04/08/a-quick-guide-to-tojamming/</link>
		<comments>http://blog.andrewtraviss.com/2011/04/08/a-quick-guide-to-tojamming/#comments</comments>
		<pubDate>Fri, 08 Apr 2011 12:56:17 +0000</pubDate>
		<dc:creator>ninjasquirrel</dc:creator>
				<category><![CDATA[Events]]></category>
		<category><![CDATA[TOJam]]></category>

		<guid isPermaLink="false">http://blog.andrewtraviss.com/?p=337</guid>
		<description><![CDATA[With the announcement that TOJam 6 is imminent. We&#8217;ve done a little better each year and I&#8217;m really looking forward to this one. I wanted to take some time to share what I&#8217;ve learned by attending five of these crazy things and share what advice I have on improving your chances of success and minimizing your [...]]]></description>
			<content:encoded><![CDATA[<p>With the announcement that <a title="TOJam" href="http://www.tojam.ca/" target="_blank">TOJam 6</a> is imminent. We&#8217;ve done a little better each year and I&#8217;m really looking forward to this one. I wanted to take some time to share what I&#8217;ve learned by attending five of these crazy things and share what advice I have on improving your chances of success and minimizing your stress. TOJam only comes once a year, so make the most of it!<br />
<span id="more-337"></span><br />
<h2>Preparation</h2>
<p>Every year, I&#8217;ve handled preparation a bit differently. There&#8217;s a few practices that have emerged which seem to pay off quite well once you sit down at TOJam to start working on your game.</p>
<h3>Focus Your Game Design</h3>
<p>It takes quite a bit of time to balance and refine a game mechanic and make it really fun. If your game requires a few mechanics working together before it starts to be fun, chances are you won&#8217;t have nearly enough time to balance them out after you&#8217;ve finished implementing them all. You may not finish implemnting them all in the first place. I&#8217;ve done <a title="big" href="http://www.tojam.ca/games_2007/urban_tactics.asp">big</a> <a title="concepts" href="http://www.tojam.ca/games_2008/der_baron_von_cheese.asp">concepts </a>before and it is a nerve-wracking experience. You can get a whole lot done and feel surprisingly unaccomplished because it&#8217;s questionable whether you&#8217;ve actually got a complete game.</p>
<p>If you take a look at the award winners each year, you&#8217;ll  notice that they all do one thing and do it extremely well. This is not coincidental.</p>
<h3>Plan in Stages</h3>
<p>We decided to try a staged approach for Der Baron Von Ubercheesen: Cheese Factory. We laid out our plan with some definite milestones, and listed the things we wanted to have complete in order to call that milestone done. It didn&#8217;t lead us to be 100% successful, because the idea was just too big, but what we had done felt polished and cohesive. We used the same type of approach for Flip The Beach the next year, and it really clicked. There were a few advantages to this approach.</p>
<p>Completing a milestone gives you a little momentum boost. It also gives you a point where it makes sense to stop working for a moment and just test out the game so far. Take a break, look around at the other games in progress, give any conscious team members a high-five. Then package up a playable build and put it somewhere safe. When you sit down and start on the next milestone, you&#8217;ll be feeling pretty good about yourself.</p>
<p>It may seem too much like work, but figure out how long you expect each milestone to take, it will help you recognize early on if you aren&#8217;t going to be able to complete a whole milestone by the end of the Jam. This could save you some time and give you the opportunity to polish things up or focus your energy on things you can accomplish easily.</p>
<h3>Build Boring Things Ahead</h3>
<p>The rules for TOJam state that you can build some things like menu screens ahead of time. Don&#8217;t waste your time at the jam on this stuff. Arrive on Friday ready to start on actual gameplay code. It&#8217;s a waste of precious time and energy to do it at the Jam.</p>
<h3>Know Your Art Needs</h3>
<p>Make sure the artists on your team have an explicit list of assets they need to create before the Jam starts. If you&#8217;ve planned your game out, you should be able to do this, and even be able to tell them what order you&#8217;ll want things in. This is doubly important if you are going to be relying on floaters. Your access to their time is limited, so make it count by being prepared.</p>
<h2>At The Jam</h2>
<h3>Play Other People&#8217;s Games</h3>
<p>Maintaining inspiration is important, so don&#8217;t waste the fact that you are surrounded by creative people. Don&#8217;t intrude on people who are obviously busy, but if someone is looking for help play testing or if they are taking a break you may want to strike up a conversation about their game or give it a try in its current state. It only costs you a few minutes of downtime, but sharing the creative energy and seeing what other people are doing can help keep you motivated.</p>
<h3>Avoid Scouting</h3>
<p>Before the Jam make sure you know the food options in the area and the nearest location of your favourite coffee shop and any convenience stores. Check their hours. There were no 24-hour Tim Horton&#8217;s anywhere near George Brown that we could find last year. It took far too long to figure this out. It&#8217;s easy to waste a lot of time. (Aside: If you know of a 24-hour Tim Horton&#8217;s near George Brown, please let me know)</p>
<h3>Sleep</h3>
<p>I didn&#8217;t sleep at all at the first TOJam. Don&#8217;t do that. Trust me. You are going to spend the final day primarily fixing bugs, polishing, and balancing. These tasks are detail-oriented and  much harder to do when you are tired. Personally, I pull an all-nighter from Friday until Saturday and get a full night&#8217;s sleep Saturday night so I can hit the ground running on Sunday morning. Everyone is different, so you&#8217;ll have to figure out what works for you. That&#8217;s a pretty popular model, though.</p>
<p>That being said, if you can go all night once, do it. The overnight is an essential part of the TOJam experience, in my opinion.</p>
<h3>Roll With the Punches</h3>
<p>Plan to make your game playable in some form as soon as you can. Do the bare minimum for each aspect of the game and get a complete picture. You might find out that one of your major design choices isn&#8217;t actually terribly fun. Don&#8217;t give up, though. If there&#8217;s one thing I would like to stress above all else, it&#8217;s <strong><em>do not give up if something goes wrong</em></strong>. Just do what you can.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.andrewtraviss.com/2011/04/08/a-quick-guide-to-tojamming/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Runtime Object Editing in Actionscript 3.0 with AScalpel</title>
		<link>http://blog.andrewtraviss.com/2011/04/01/runtime-object-editing-in-actionscript-3-0-with-ascalpel/</link>
		<comments>http://blog.andrewtraviss.com/2011/04/01/runtime-object-editing-in-actionscript-3-0-with-ascalpel/#comments</comments>
		<pubDate>Fri, 01 Apr 2011 17:29:56 +0000</pubDate>
		<dc:creator>ninjasquirrel</dc:creator>
				<category><![CDATA[Libraries]]></category>
		<category><![CDATA[Actionscript 3]]></category>
		<category><![CDATA[AScalpel]]></category>
		<category><![CDATA[Game Development]]></category>

		<guid isPermaLink="false">http://blog.andrewtraviss.com/?p=346</guid>
		<description><![CDATA[There was a bit of buzz in the indie game community recently around the idea of editing object properties at runtime as a great way to tune gameplay quickly. I haven&#8217;t seen any attempts at a reusable system to handle it, so I thought I&#8217;d give it a go. AScalpel is a basic editor shell [...]]]></description>
			<content:encoded><![CDATA[<p>There was a bit of buzz in the indie game community recently around the idea of editing object properties at runtime as a great way to tune gameplay quickly. I haven&#8217;t seen any attempts at a reusable system to handle it, so I thought I&#8217;d give it a go. AScalpel is a basic editor shell which uses metadata to dynamically create editors for custom classes. There&#8217;s still some issues to iron out with it, but I don&#8217;t really have enough free time to do it. It&#8217;s up on Git now.</p>
<p>Normally I&#8217;m a diehard Flex fan, but I know not everyone shares my views so I&#8217;ve used the <a title="Bit-101 Minimal Components" href="http://www.bit-101.com/blog/?category_name=components" target="_blank">Bit-101 Minimal Components</a> for this. It could easily be retrofitted to use Flex as well (I will probably do this later). For this initial release, it is purely an Actionscript 3.0 library. I&#8217;ve set up a <a title="AScalpel Git Repository" href="https://github.com/andrewtraviss/AScalpel/" target="_blank">Git repository</a> to share it with everyone. An explanation of how to use it, below the cut. You&#8217;ll need the Bit-101 components in order to use it at the moment. Currently hosted on Google Code, <a title="Minimal Components on Google Code" href="http://code.google.com/p/minimalcomps/" target="_blank">here</a></p>

<object classid="clsid:D27CDB6E-AE6D-11cf-96B8-444553540000"
			id="fm_BouncingBallSample_1009398152"
			class="flashmovie"
			width="600"
			height="450">
	<param name="movie" value="http://blog.andrewtraviss.com/wp-content/uploads/2011/04/BouncingBallSample.swf" />
	<!--[if !IE]>-->
	<object	type="application/x-shockwave-flash"
			data="http://blog.andrewtraviss.com/wp-content/uploads/2011/04/BouncingBallSample.swf"
			name="fm_BouncingBallSample_1009398152"
			width="600"
			height="450">
	<!--<![endif]-->
		
	<!--[if !IE]>-->
	</object>
	<!--<![endif]-->
</object>
<p><span id="more-346"></span></p>
<h2>AScalpel Class</h2>
<p>The main AScalpel class is a singleton which holds onto the root of the editor display. You have full control over where and how this is created, hidden, and shown. The AScalpel class is used to create and destroy LiveEditor instances, as well as for registering custom editors and setting global options. In the simplest case all that needs to be done is the following. Details on that first call are later in the post.</p>
<pre class="brush: as3; title: ; notranslate">StandardBit101Editors.install();
addChild(AScalpel.instance.display);</pre>
<p>There are two ways to create editor windows for objects. You can add objects to an internal list using AScalpel.instance.addObject and then select objects from the dropdown that appears to create editors for them. Alternatively, you can call AScalpel.instance.open directly and just create editor windows without clogging the screen with the main editor window.</p>
<h2>[Editable]</h2>
<p>The [Editable] tag is the core of the system. Any public variable or getter/setter pair tagged as [Editable] will have a matching field created in the editor. If the member is a basic Actionscript type, the bare [Editable] tag will likely be enough. AScalpel has default fields defined for all of the basic data types. There are additional parameters that are available to handle other situations or to enhance the editor that is created.</p>
<h3>explicitCommit=true</h3>
<p>By default, all editors will apply their updated values to the target object as you type. In many cases this may be undesirable due to unexpected or invalid values being set. If explicitCommit is set to &#8220;true&#8221;, a Commit button will be added next to the field and the updated value will only be passed into the target object when the button is clicked.</p>
<pre class="brush:as3">[Editable(explicitCommit="true")]
public function get x():Number
{
	return _x;
}
public function set x(in_value:Number):void
{
	_x = in_value;
}
private var _x:Number;</pre>
<h3>customEditor=&#8221;com.fully.qualified.ClassName&#8221;</h3>
<p>You can specify a custom class to be used for the field for this particular member. A common case for this would be using a colour picker control for colour properties. AScalpel will try to figure out how to use any editor class, but is is always better to explicitly register it. That&#8217;s covered near the end of this post.</p>
<pre class="brush:as3">[Editable(editorClass="com.bit101.components.ColorChooser")]
public function get color():uint
{
	return _color;
}
public function set color(in_value:uint):void
{
	_color = in_value;
	redraw();
}
private var _color:uint = 0x000000;</pre>
<h3>Any Property Supported by the Editor</h3>
<p>If a parameter of the editor field is not recognized by the ObjectEditor, it will check if a property of that name exists on the field editor itself and apply the value if so. For example:</p>
<pre class="brush:as3">[Editable(editorClass="com.bit101.components.NumericStepper", minimum="1", maximum="30", step="0.1")]
public function get radius():Number
{
	return _radius;
}
public function set radius(in_value:Number):void
{
	_radius = in_value;
	redraw();
}</pre>
<h2>Configuration</h2>
<h3>Assigning default editors</h3>
<p>For types which are used in multiple places in the game, it&#8217;s much more convenient to define a default editor for that type than to specify it in every [Editable] tag. This is done using AScalpel.instance.setDefaultEditorClassForType method of the ASCalpel singleton.</p>
<h3>Configuring custom editors</h3>
<p>All custom editors should ideally be configured, even if they would work with the default values; It&#8217;s a convenient way to be sure that the custom editor is actually visible to the compiler. When registering an editor, you pass four things to AScalpel through AScalpel.instance.registerEditorClass</p>
<ol>
<li>A reference to the editor class (not an instance of the class or the name of the class)</li>
<li>The name of the member variable which is used to set and retrieve the current value of the editor</li>
<li>The event which the component dispatches when it is initialized (or null if there is no such event)</li>
<li>The event which the component dispatches when the value changes</li>
</ol>
<p>The first version of AScalpel has integration with the Bit-101 minimal components built in, through the StandardBit101Editors class, shown below. This provides a relatively simple example of how to configure AScalpel.</p>
<pre class="brush:as3">package com.andrewtraviss.ascalpel
{
	import com.bit101.components.CheckBox;
	import com.bit101.components.ColorChooser;
	import com.bit101.components.Component;
	import com.bit101.components.InputText;
	import com.bit101.components.Knob;
	import com.bit101.components.NumericStepper;
	import com.bit101.components.Slider;
	import com.bit101.components.TextArea;

	import flash.events.Event;
	import flash.events.MouseEvent;

	public class StandardBit101Editors
	{
		public static function install():void
		{
			AScalpel.instance.registerEditorClass(com.bit101.components.InputText, "text", Component.DRAW, Event.CHANGE);
			AScalpel.instance.registerEditorClass(com.bit101.components.NumericStepper, "value", Component.DRAW, Event.CHANGE);
			AScalpel.instance.registerEditorClass(com.bit101.components.ColorChooser, "value", Component.DRAW, Event.CHANGE);
			AScalpel.instance.registerEditorClass(com.bit101.components.CheckBox, "selected", Component.DRAW, MouseEvent.CLICK);
			AScalpel.instance.registerEditorClass(com.bit101.components.Knob, "value", Component.DRAW, Event.CHANGE);
			AScalpel.instance.registerEditorClass(com.bit101.components.Slider, "value", Component.DRAW, Event.CHANGE);
			AScalpel.instance.registerEditorClass(com.bit101.components.TextArea, "text", Component.DRAW, Event.CHANGE);

			AScalpel.instance.setDefaultEditorClassForType("com.bit101.components.InputText", String);
			AScalpel.instance.setDefaultEditorClassForType("com.bit101.components.InputText", Number, {restrict:"0-9.\\-"});
			AScalpel.instance.setDefaultEditorClassForType("com.bit101.components.InputText", int, {restrict:"0-9\\-"});
			AScalpel.instance.setDefaultEditorClassForType("com.bit101.components.InputText", uint, {restrict:"0-9"});
			AScalpel.instance.setDefaultEditorClassForType("com.bit101.components.CheckBox", Boolean);
		}
	}
}</pre>
]]></content:encoded>
			<wfw:commentRss>http://blog.andrewtraviss.com/2011/04/01/runtime-object-editing-in-actionscript-3-0-with-ascalpel/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
		</item>
		<item>
		<title>Game Engine Design, Part One: The Role of the Engine</title>
		<link>http://blog.andrewtraviss.com/2011/03/14/game-engine-design-part-one-the-role-of-the-engine/</link>
		<comments>http://blog.andrewtraviss.com/2011/03/14/game-engine-design-part-one-the-role-of-the-engine/#comments</comments>
		<pubDate>Mon, 14 Mar 2011 13:33:53 +0000</pubDate>
		<dc:creator>ninjasquirrel</dc:creator>
				<category><![CDATA[General Software Development]]></category>
		<category><![CDATA[Engine Design]]></category>
		<category><![CDATA[Game Development]]></category>

		<guid isPermaLink="false">http://blog.andrewtraviss.com/?p=331</guid>
		<description><![CDATA[I&#8217;ve been responsible for a number of engines and frameworks over time, but they have been predominantly built for the purpose of solving some specific technically difficult problems. As we have embarked on the business of developing games ourselves, the need for a more comprehensive game engine is evident. We could use one of the [...]]]></description>
			<content:encoded><![CDATA[<p>I&#8217;ve been responsible for a number of engines and frameworks over time, but they have been predominantly built for the purpose of solving some specific technically difficult problems. As we have embarked on the business of developing games ourselves, the need for a more comprehensive game engine is evident. We could use one of the existing engines out there, but my history with developing them leaves me with too many ideas on the subject to give it up.</p>
<p>In this first instalment, I explain my thoughts on the role of a game engine and the overall scope of what I intend to achieve.<br />
<span id="more-331"></span><br />
<em>The challenge facing a game engine is to help the developer express their game design concisely.</em></p>
<p>An engine for resolving the challenge of physics or rendering is great, but that isn&#8217;t a game engine at all.  It&#8217;s a graphics engine, or a physics engine, usually with a token entity system built on top of that. These types of technically-oriented solutions can simplify code that deals with their particular subsystem, but do little to assist the general process.</p>
<p>What then are the basic elements of a game design that an engine should treat as its basic units? Rules. Many of these rules are simple; &#8220;Mario is hurt if he touches the sides of a goomba&#8221;, and others take the form of simulation systems such as physics. Entities are defined in terms of how the game rules apply to them. This is rarely described in such a formal way by game designers, but during implementation the core task is to distil the design down to these types of basic ideas and then express them in code. The goal of the game engine is to allow each game rule to be specified with as little code as possible.</p>
<p>There are three key factors I will be focusing on in my own engine design:</p>
<p>1. Minimize code to define a rule.</p>
<p>2. Allow custom rules with minimal overhead.</p>
<p>3. Make gameplay code as readable as possible.</p>
<p>&nbsp;</p>
<p>In the next Game Engine Design post, I&#8217;ll lay out the high-level component view of the engine and describe how I intend for the parts to work together.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.andrewtraviss.com/2011/03/14/game-engine-design-part-one-the-role-of-the-engine/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Moved to Mediatemple</title>
		<link>http://blog.andrewtraviss.com/2011/03/10/moved-to-mediatemple/</link>
		<comments>http://blog.andrewtraviss.com/2011/03/10/moved-to-mediatemple/#comments</comments>
		<pubDate>Fri, 11 Mar 2011 00:15:44 +0000</pubDate>
		<dc:creator>ninjasquirrel</dc:creator>
				<category><![CDATA[Uncategorized]]></category>

		<guid isPermaLink="false">http://blog.andrewtraviss.com/?p=273</guid>
		<description><![CDATA[After over a year of persistent downtime and performance issues under WebHost4Life, I&#8217;ve moved over to Mediatemple. Already feeling much more comfortable here. The lack of problems should improve post motivation. A great deal has happened over the past year. Quit my job. Started a company. I&#8217;ve done some work for Manulife Financial and have [...]]]></description>
			<content:encoded><![CDATA[<p>After over a year of persistent downtime and performance issues under WebHost4Life, I&#8217;ve moved over to Mediatemple. Already feeling much more comfortable here. The lack of problems should improve post motivation.</p>
<p>A great deal has happened over the past year. Quit my job. <a href="http://www.goldengeargames.com/">Started a company</a>. I&#8217;ve done some work for Manulife Financial and have been on contract for a social game developer for some time. I spent enough time migrating my blog tonight, however, so I&#8217;ll have to share more details in a future post.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.andrewtraviss.com/2011/03/10/moved-to-mediatemple/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>A TOJam 5 Retrospective</title>
		<link>http://blog.andrewtraviss.com/2010/04/28/a-tojam-5-retrospective/</link>
		<comments>http://blog.andrewtraviss.com/2010/04/28/a-tojam-5-retrospective/#comments</comments>
		<pubDate>Wed, 28 Apr 2010 14:08:33 +0000</pubDate>
		<dc:creator>ninjasquirrel</dc:creator>
				<category><![CDATA[Events]]></category>
		<category><![CDATA[Game Development]]></category>
		<category><![CDATA[Reentry]]></category>
		<category><![CDATA[TOJam]]></category>

		<guid isPermaLink="false">http://blog.andrewtraviss.com/?p=271</guid>
		<description><![CDATA[It is done! 180 people this year, 160 of them on-site. And amazingly, with 35 more people than TOJam 3, it actually felt less hectic. The organizers were more sane and better rested, and actually had time to sit and chat more. Pro Tip:Talking to Jim McGinley for 30 minutes or so when you are [...]]]></description>
			<content:encoded><![CDATA[<p>It is done! 180 people this year, 160 of them on-site. And amazingly, with 35 more people than TOJam 3, it actually felt less hectic. The organizers were more sane and better rested, and actually had time to sit and chat more.</p>
<p><strong>Pro Tip:</strong>Talking to Jim McGinley for 30 minutes or so when you are exhausted to the point of passing out will generally restore your energy for the remainder of the day. Or at least long enough for the caffeine to take over</p>
<p>As always, I had an awesome time, even if I was more tired this year than previous years. That largely due to the fact that I was up until 3 am the night before the Jam trying to get SVN set up on my machine so that Alex and I could forego the USB time sync. <a href="http://psychology.wikia.com/wiki/Irrational_escalation">Irrational Escalation</a> at its finest.</p>
<p>Alex covered the event really well with some video blogs. Find them <a href="http://www.drunkenmonkeystyle.com/blog/?p=121">here</a>.</p>
<p>There were some fantastic games out there, I sunk quite a bit of time into Michael Todd&#8217;s dogfighting game. Shawn McGrath&#8217;s game would probably conquer XBox Live Arcade if it were to appear there. Some screenshots and description of our game after the cut</p>
<p><span id="more-271"></span></p>
<p>Our game this year was &#8220;Reentry&#8221; a game about misplaced guidance systems and creepy starship pilots. This year had a lot of ups and down for us.</p>
<h2>Good: Sound and music</h2>
<p>This year&#8217;s game used more sound assets than all 4 of the previous games I&#8217;ve worked on put together.</p>
<p><img src="http://blog.andrewtraviss.com/media/reentry-title.jpg" alt="Reentry Title Page" align="right" /></p>
<p>Alex worked with a friend of his to record voice tracks for the main characters who I have dubbed Captain Helium and Lt. Commander Creeper McShady. The voices<br />
add a lot to the experience. The game feels a little dull without them, but that&#8217;s in line with our plan. The characters are a big part of the design.</p>
<p>We also got a great music track from chiptune artist <a href="http://www.oxygenstarpower.com/">OxygenStar</a> and editted it into 3 loops connected by transitions. It turned out great.</p>
<p>For sound effects, we used <a href="http://www.drpetter.se/project_sfxr.html">SFXR</a>, which belongs in every indie developer&#8217;s toolbox. Thanks to Steven Hill for throwing that one our way. All of the sound effects in the game were generated by Alex using this tool. I&#8217;m excited to try out the music creation tool <a href="http://www.drpetter.se/project_musagi.html">Musagi</a> by the same developer</p>
<h2>Bad: Source Control</h2>
<p>If you ever think about trying to set up SVN the night before a 72-hour game development event, and further think about starting at 11 pm, with no prior experience doing so, do yourself a favour and don&#8217;t.</p>
<p><img src="http://blog.andrewtraviss.com/media/reentry-screenshot-1.jpg" alt="Reentry Screenshot" align="left" /></p>
<p>Our hackjob solution made me worry quite a bit but ended up working out. We set up the Flex project on Alex&#8217;s computer in a network share folder and both pointed our environments at that location directly. There were some hiccups where one of us would temporarily break the build for the other, but I don&#8217;t think we lost more than 30 mins over the course of the Jam. That&#8217;s much better than what we wasted with our USB juggling last year.</p>
<p>Next year I&#8217;ll try to get SVN set up again, but this time a month in advance at least.</p>
<h2>Good: Scope Control</h2>
<p>We wanted to aim for a smaller game idea this year. We have trended towards big ideas before, and felt that it didn&#8217;t leave us enough time to refine the gameplay for the actual fun factor. I think we pulled it off this time, despite ignoring a game breaking bug right until the end of the event.</p>
<p><img src="http://blog.andrewtraviss.com/media/reentry-screenshot-2.jpg" alt="Reentry Screenshot" align="right" /></p>
<p>Balancing ship movement to be challenging without killing you was very time consuming You have to click the appropriate thruster and hold the mouse down (not necessarily over the thruster) to keep it firing. There are two thrusters that push your ship side to side, and two more that control your rotation. Figuring out the right amount of force for each engine to apply, as well as turbulence and impacts took up a pretty significant chunk of my time at the event.</p>
<p>Next time I&#8217;m adding some mechanism to adjust these values in the game itself, to make tweaking less time consuming</p>
<h2>Bad: Miscommunication</h2>
<p>This mostly happened prior to the event, but apparently everyone had a different picture in their head of what the game would actually look and play like up until the week of the event.</p>
<p><img src="http://blog.andrewtraviss.com/media/reentry-screenshot-3.jpg" alt="Reentry Screenshot" align="left" /></p>
<p>It wasn&#8217;t until we actually started sketching out the game that everything became clear. Lesson learned. The storyboard comes before everything else. It&#8217;s much harder to have a misunderstanding based on visual information than written or spoken information.</p>
<h2>Things To Change Next Year</h2>
<p>Based on my experience this year, there are several things I want to keep in mind when TOJam 6 rolls around. Some good practices from previous years were not observed, and they proved their value in their absence.</p>
<ol>
<li>Use an engine. Not using Flixel this time made sense, but the decision should have come earlier, and a more appropriate technology selected. The best games every year leverage existing technologies. Motor physics really gave us a leg up last year.</li>
<li>Simple gameplay. We went simpler this year, in terms of number of mechanics, but we didn&#8217;t actually choose a simpler mechanic for the core of the game.</li>
<li>Revive last year&#8217;s formal approach. Alex and I both work better against a well defined schedule. Not having one this year wasn&#8217;t a good change</li>
<li>Prove it&#8217;s fun ahead of time. We took a risk on this one with a small idea and really only one major mechanic that we hadn&#8217;t seen much of elsewhere. I liked doing this, but there should have been some pre-Jam prototyping just to be sure that the idea was actually a good one.</li>
<li>Consider abstract graphics. Every year so far I&#8217;ve worked with representative graphics, and it can be limiting in some ways even if it brings a lot of benefits along with it. Besides, if <a href="http://www.spookysquid.com/">Miguel Sternberg</a> can make a game without developers, we need to show him we can make a game without artists!</li>
</ol>
]]></content:encoded>
			<wfw:commentRss>http://blog.andrewtraviss.com/2010/04/28/a-tojam-5-retrospective/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
	</channel>
</rss>

<!-- Dynamic page generated in 1.239 seconds. -->
<!-- Cached page generated by WP-Super-Cache on 2012-02-22 17:25:12 -->

