<?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>GameArchitect</title>
	<atom:link href="http://gamearchitect.net/feed/" rel="self" type="application/rss+xml" />
	<link>http://gamearchitect.net</link>
	<description>Musings on Game Engine Design</description>
	<lastBuildDate>Mon, 30 Mar 2009 16:11:29 +0000</lastBuildDate>
	<generator>http://wordpress.org/?v=2.9.2</generator>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
			<item>
		<title>GDC 2009:  The Year We Went Hungry</title>
		<link>http://gamearchitect.net/2009/03/29/gdc-2009-the-year-we-went-hungry/</link>
		<comments>http://gamearchitect.net/2009/03/29/gdc-2009-the-year-we-went-hungry/#comments</comments>
		<pubDate>Mon, 30 Mar 2009 05:50:31 +0000</pubDate>
		<dc:creator>Kyle</dc:creator>
				<category><![CDATA[GDC]]></category>

		<guid isPermaLink="false">http://gamearchitect.net/?p=31</guid>
		<description><![CDATA[ 
I&#8217;ve written before that at SIGGRAPH you starve while at GDC they stuff you like a foie gras goose.  No more.  This year there were no breakfast pastries before the lectures started.  There were no cookies at the coffee breaks.  Some lines ran out of lunches and sodas.  Perhaps CMP took a look at the [...]]]></description>
			<content:encoded><![CDATA[<p> </p>
<p>I&#8217;ve written <a href="http://www.gamearchitect.net/Articles/GDC2004.html">before</a> that at SIGGRAPH you starve while at GDC they stuff you like a foie gras goose.  No more.  This year there were no breakfast pastries before the lectures started.  There were no cookies at the coffee breaks.  Some lines ran out of lunches and sodas.  Perhaps CMP took a look at the girth of the attendees and decided that the average game developer would benefit from a diet.</p>
<p>The lean times extended to the recruiting floor.  It was obvious looking at the career expo that, despite rumors to the contrary, our industry is far from recession proof.  There looked to be about half as many booths as there were last year.</p>
<p>Recruiting aside, GDC looked as crowded as ever&#8211;which is pretty impressive considering that attendance last year was <a href="http://www.gamasutra.com/php-bin/news_index.php?story=17651">18,000</a> developers.  Unfortunately, this whole paragraph from my write-up <a href="http://gamearchitect.net/2008/03/12/gdc-2008/">last year</a> is still accurate:</p>
<blockquote><p>GDC hasn’t managed to scale to handle its growth.  Internet connectivity was poor throughout the convention center&#8230;. proceedings didn’t become available at all until <em>after</em> the conference, and those in the form of a slim handful of PowerPoint decks.  The clever people have taken to bringing cameras to the talks and snapping pictures of each slide that goes up, which is distracting but understandable.  The state of the GDC proceedings is an embarrassment to the industry, but it’s one that I don’t expect to change unless CMP stops handing out Gigapasses to speakers who show up without their slides.</p></blockquote>
<p>This year, even AT&amp;T&#8217;s 3G network was overwhelmed.  I had to switch my phone back to the EDGE network to get any bandwidth.   18,000 geeks use a <em>lot</em> of bandwidth.</p>
<p>What&#8217;s hot:  SPU task profiles.  Screen-space postprocessing.  iPhones.  AI.  Larrabee.  Producers explicitly defending crunch.  Margaret Robertson.</p>
<p>What&#8217;s not:  Spherical harmonics (still).  Every mobile phone except the iPhone.  Scrum (it&#8217;s lost its New Process smell&#8230; crunch is the new scrum).  <a href="http://www.quartertothree.com/game-talk/showthread.php?t=22810">The 7 to 9 scale</a>.  OnLive.</p>
<p><span id="more-31"></span>In no particular order, these are the talks I found noteworthy:</p>
<h3><strong>The Game Design Challenge:  My First Time</strong></h3>
<p>This year&#8217;s Game Design Challenge was supposed to be about &#8220;sex and autobiography,&#8221; an assignment that the designers took literally.  The scheduled participants were Kim Swift of Valve, Sulka Haro of Habbo and industry veteran Steve Meretzky.  Management at Valve apparently decided that the topic was too explicit for them to be associated with, though, because Kim Swift withdrew on short notice to be replaced by the two-woman team of <a href="http://www.moboid.com/">Heather Kelley</a> and <a href="http://www.livelyivy.com/">Erin Robinson</a>.</p>
<p>Kelley and Robinson pitched a series of minigames that explicitly (in every sense) reenacted their first sexual experiences.  They proposed an arcadey Wii-style game, like a cross between Barbie Fashion Designer and Cooking Mama, with challenges such as:</p>
<ul>
<li>Pick the least complicated/easiest to remove outfit</li>
<li>Shave your legs</li>
<li>Choose the sexiest LP</li>
<li>Unbuckle partner&#8217;s clothing</li>
<li>Etc&#8230;</li>
</ul>
<p>Sulka Haro pitched &#8220;Your First Time&#8221;, a 4-6 player co-op anonymous story game.  One player would pick an image from <a href="http://www.flickr.com">Flickr</a>.  Other players would respond with a brief fiction based on the image, and the original player would judge the results like you would in a game of <a href="http://en.wikipedia.org/wiki/Apples_to_apples">Apples to Apples</a>.  I think Haro&#8217;s submission was the most mature design, but it adhered least to the assigned subject.  The game sounds like it would work as well with stories about Star Trek characters as sexual experiences, and it&#8217;s in no way autobiographical.</p>
<p>Steve Meretzky looked back to his Infocom days, proposing a text adventure, &#8220;Wait.  Time Passes&#8230;&#8221; in which the player tried to pick up women at different phases in his life, starting as a loser high school student doomed to failure but eventually growing up into a successful game designer who has all the sex he wants.  The gameplay seemed somewhat questionable, though, since the player&#8217;s only real option at any point is to wait until he outgrows his adolescent awkwardness.</p>
<p>Kelley and Robinson won.  I find it notable that the women&#8217;s autobiographical stories have no possibility that they&#8217;ll fail to find sex if they want to have it, but also make it clear that they&#8217;re the ones who initiate the act.  Which I guess means that (a) they&#8217;re women and (b) they&#8217;re dating geek men, poor things.</p>
<h3>Stop Wasting My Time, Margaret Robinson</h3>
<p>Margaret Robinson gave the most enjoyable talk of the show.  She analyzed what kind of storytelling does and doesn&#8217;t work in games, offering less high-concept theory than a discussion of what storytelling mechanisms did and didn&#8217;t work in a variety of specific games.</p>
<p>Robinson cites <em>Call of Duty 4</em>, for example, not for its high-level plot (there&#8217;s a terrorist&#8230; and Russians&#8230; and a nuclear weapon&#8230; and, um, I forget the rest) but for the relationship between the SAS operator inhabited by the player and Captain Price, his gruff commanding officer.  At the beginning of the game, the player is the new guy, and Price and the rest of his squad treat him with casual disrespect.  Over the course of the game, the player gets better at the game and the other characters treat him as more of an equal.  Then, in a key chapter, the game does something that no movie or book could do:  it shifts point of view and lets the player <em>become </em>Captain Price in a flashback mission.  When he returns to being an SAS squaddie, his relationship with Captain Price has fundamentally changed.</p>
<p>In the notes for his last novel, F. Scott Fitzgerald wrote, &#8220;Action is character.&#8221;  And the equality of action and character is very useful to us, Robertson observed, because action is what games are good at.</p>
<p>There are lots of different ways of telling a story in a game, and they form a hierarchy:</p>
<ul>
<li>HUD</li>
<li>art</li>
<li>animation</li>
<li>sound</li>
<li>text</li>
<li>voice-over</li>
<li>video</li>
</ul>
<p>As you move down that list, cost increases while player engagement decreases.  Robinson&#8217;s point is that the thing that is easiest is the thing that is best for us!  Implicit storytelling is superior to explicit storytelling in games.  Story in games is important for setting tone and for putting the player in an emotional context.  Exposition is expensive&#8211;you need to hire voice actors and make cinematic animations&#8211;and it takes the player out of the game.  The best way to tell a story in a game is through the systems with which the player is already interacting.</p>
<p>So if you&#8217;re creating a game, ask yourself if you need a story at all.  If so, what&#8217;s it for?  What&#8217;s it about?  What&#8217;s it really about?  What systems does it depict?</p>
<p>&#8220;I read a load of game pitches that start with the inner psychology of the character, and that&#8217;s not a good place to start,&#8221; Robinson said.  &#8221;Think about your game idea, and if it would look really good on the silver screen&#8211;dump it!&#8221;</p>
<p>Margaret Robertson talks about games with a rare mix of enthusiasm and insight.  If you get a chance to hear her speak, don&#8217;t miss it.</p>
<h3>Valve&#8217;s Approach to Playtesting</h3>
<p>I&#8217;ve listened to a talk or two about Valve&#8217;s playtesting process before, so I wasn&#8217;t expecting to learn much from this talk by Mike Ambinder, but it ended up being pretty remarkable.  Where Valve&#8217;s earlier playtest talks have focused on why they do user testing, how they recruit testers, and how they integrate testing into their content creation process, this talk focused on the lengths to which Valve goes in order to extract accurate data from their testers.</p>
<p>There are a lot of problems with getting honest responses from experimental participants.  Humans have strong cognitive biases toward consensus, toward confirmation of preconceptions, and toward self-serving interpretations.  Ambinder said, &#8220;If you ask a group if a level is hard, the first person to respond wins.&#8221;  Even individually, they tend to give the answers they think questioners want to hear.</p>
<p>Valve tries to work around these issues to some extent by using multiple choice surveys so that players can&#8217;t equivocate and by asking questions designed to give specific limited factual answers.</p>
<p>A more direct path to honest answers, though, is to use biometic data to measure the player&#8217;s emotional state directly instead of quizzing him about how he feels.  Valve tries to gather data by measuring players:</p>
<ul>
<li>heart rate</li>
<li>skin conductance</li>
<li>eye tracking (blink rate, pupil dilation)</li>
<li>facial expression</li>
<li>EEG readings</li>
<li>EMG readings (<a href="http://en.wikipedia.org/wiki/Electromyography">electomyography</a>, which infers emotional state by measuring facial muscle contractions)</li>
</ul>
<p>They caution that all of these measures are noisy and sometimes hard to interpret.  But they&#8217;re refreshingly free of the biases that make focus test results so frustrating.</p>
<p>Valve is clearly pushing the edge of the envelope when it comes to gathering data from user testing.</p>
<h3>Game Critics Rant</h3>
<p>I went to the Game Critics Rant because I wanted to see Tom Chick, who moderates the<a href="http://www.quartertothree.com"> Quarter to Three</a> forums on which I spend more time lurking than I should.  In the event, Chick didn&#8217;t make it&#8211;really, SciFi?  You couldn&#8217;t afford to buy the guy a lousy plane ticket from LA?&#8211;but the rant session ended up being so much fun that I stuck around anyway.</p>
<p>N&#8217;Gai Croal, formerly of Newsweek, opened the event by vivisecting the idea of a &#8220;hardcore gamer.&#8221;  &#8221;Hardcore,&#8221; he points out, describes a genre rather than how games fit into people&#8217;s lives.  Why is a person who plays Bejeweled sixteen hours a day considered a casual gamer while a person who plays Halo once a week is considered hardcore?  &#8221;Please Google the phrase &#8216;<a href="http://www.google.com/search?rlz=1C1GGLS_enUS291US304&amp;sourceid=chrome&amp;ie=UTF-8&amp;q=a+new+taxonomy+of+gamers">a new taxonomy of gamers</a>&#8216;,&#8221; Croal said.</p>
<p>Stephen Totilo continued with another critic&#8217;s rant against his own.  He pointed out that game journalists are often criticized for not being reporters.  &#8221;Our reporting is fine&#8230; it&#8217;s our writing that sucks,&#8221; he observed.  &#8221;We abandon what should be the mandate to write in clear crisp ways.&#8221;  He then called on game reviewers to abandon:</p>
<ul>
<li>&#8220;Compelling&#8221;</li>
<li>&#8220;Visceral&#8221;</li>
<li>&#8220;Very&#8221;</li>
<li>Adverbs</li>
</ul>
<p>I thought his rant was very viscerally compelling.  Also, very <em>is</em> an adverb.</p>
<p>Leigh Alexander of Gamasutra gave a rant that was a little incoherent, opening with the complaint that Gamasutra is &#8220;dealing with an unpleasable audience that sends the message that they don&#8217;t care about quality&#8221; and going on to say that there&#8217;s a &#8220;three-way ecosystem of negativity&#8221; between readers, game developers and writers.  She suggested that she wanted to establish trust&#8211;but then immediately blamed game studios for making her talk to PR drones instead of letting her talk to developers who&#8217;d tell the unvarnished truth.</p>
<p>Still, if her message was a little mixed, she made some good points.  Journalists in the game industry don&#8217;t have any contact with the people who actually make games.  Most of them don&#8217;t come from game development themselves and don&#8217;t have a detailed understanding of the development process.  No matter how talented they are as writers and cultural critics, these are challenges that make it hard for them to do their jobs well.  So if any writers out there ever want analysis from an actual developer, feel free to drop me an e-mail.</p>
<p>Jason Della Rocca talked about why he&#8217;s stepping down as chair of the IGDA:  &#8221;In IGDA, 1% were doing the work.  The rest of you were really fucking lazy and didn&#8217;t do shit&#8230;  Sorry about not doing better when you guys bitched of getting you to do stuff.&#8221;  Geez.  All I said was that I missed the cookies.</p>
<p>Author <a href="http://www.amazon.com/Smartbomb-Quest-Entertainment-Videogame-Revolution/dp/B001QCXDG4/ref=pd_bbs_sr_1?ie=UTF8&amp;s=books&amp;qid=1238389461&amp;sr=8-1">Heather Chaplin</a> continued the transition from critics criticizing their own industry to criticizing mine.  Specifically, she complained that we&#8217;re still making games about space marines and big-boobed chicks in metal bikinis.  Some people say that the industry is still immature because games are an art form that&#8217;s only 35 years old, she said.  But by the time rock and roll was 35 years old, it had created The Beatles.  By the time movies were 35 years old, they&#8217;d produced Fritz Lang and film noir.  The problem, she claimed, isn&#8217;t that games development is in its adolescence, it&#8217;s that game <em>developers</em> are permanently stuck in adolescent &#8220;guy culture&#8221;.  Guys, Chaplin said, fear four things:</p>
<ul>
<li>Responsibility</li>
<li>Introspection</li>
<li>Intimacy</li>
<li>Intellectual discovery</li>
</ul>
<p>When you&#8217;re talking about culture makers, she said, this is a problem.  &#8221;What, if you sure that you&#8217;re really sensitive people might pick up on that you&#8217;re basically a bunch of kids masquerading as men?&#8221;</p>
<p>I&#8217;ve got a lot of respect for Chaplin for having the guts to get up in front of a room full of developers and give that rant, but I think her ire is misplaced.  Here are the ten <a href="http://multiplayerblog.mtv.com/2009/01/15/best-selling-game-of-2008-mystery-its-wii-play-or-gta-iv/">best-selling games from 2008</a>:</p>
<ol>
<li>Wii Play</li>
<li>Mario Kart (Wii)</li>
<li>Wii Fit</li>
<li>Super Smash Bros:  Brawl</li>
<li>Grand Theft Auto IV (Xbox 360)</li>
<li>Call of Duty:  World at War (Xbox 360)</li>
<li>Gears of War 2</li>
<li>Grand Theft Auto IV (PS3)</li>
<li>Madden NFL 09</li>
<li>Mario Kart (Nintendo DS)</li>
</ol>
<p>Here are the ten best-selling movies from 2008:</p>
<ol>
<li>The Dark Knight</li>
<li>Iron Man</li>
<li>Indiana Jones and the Kingdom of the Crystal Skull</li>
<li>Hancock</li>
<li>WALL-E</li>
<li>Kung Fu Panda</li>
<li>Twilight</li>
<li>Madagascar:  Escape 2 Africa</li>
<li>Quantum of Solace</li>
<li>Dr. Seuss&#8217; Horton Hears a Who!</li>
</ol>
<p>I&#8217;m supposed to believe that game developers are adolescent because they make <em>Mario Kart</em> instead of <em>Horton Hears a Who</em>?  Big hit movies are every bit as childish as big hit games.  Sure, you can find movies that actually say something meaningful about the human condition, if you watch indie films that don&#8217;t sell very well.  But you can also find games that challenge players preconceptions and aspire to be art if you look at indie games instead of the big-budget lowest-common-denominator stuff that clogs the shelves at Gamestop.</p>
<p>Chris Hecker was invited up to present this year&#8217;s &#8220;Duct Tape Award&#8221; to Ubisoft&#8217;s Clint Hocking for the best rant from last year.  Hecker then gave a rant of his own, starting from three axioms:</p>
<ul>
<li>Journalism is an important job.  (Probably even more important than game development.)</li>
<li>Journalism affects people.</li>
<li>With great power comes great responsibility.</li>
</ul>
<p>Hecker then proceeded to eviscerate two particular stories.  In one, 1up took two posts in different on-line forums and turned them into an article titled <a href="http://www.1up.com/do/newsStory?cId=3171021">&#8220;Chris Hecker Apparently Responsible For Simplified Sport Gameplay&#8221;</a>&#8211;despite the fact that one of the two forum posts consisted of Hecker calling the accusation &#8220;nonsense&#8221;.  No one at 1up ever actually tried to talk to Hecker about the story.  In his other citation, Hecker quoted as <a href="http://pc.ign.com/articles/135/135304p1.html">an example of game journalism</a>:</p>
<blockquote><p>&#8220;There&#8217;s a tendency among the press to attribute the creation of a game to a single person,&#8221; says Warren Spector, creator of Thief and Deus Ex.</p></blockquote>
<p>Ouch.  Coming on the heels of so many liberal arts majors, Hecker rants like a programmer:  his points are like mathematical proofs.  There&#8217;s just not really any counterargument to make.</p>
<p>The final rant, from Adam Sessler of G4, was titled &#8220;Fuck Metacritic&#8221;.  Sessler said that he had heard from an angry developer because he had given a game a 40%.  But he&#8217;d given the game two stars out of five.  When Sessler complained to Metacritic that they shouldn&#8217;t map that to a 40% score, they told him that they&#8217;d map it however they pleased.  Sessler said he didn&#8217;t understand how a hundred-point scale worked, anyway:  &#8221;Somebody in the room tell me the difference between a 73 and a 74!&#8221;</p>
<p>Sessler lamented that game publishers are now actually using Metacritic scores to determine how much developers get paid.  &#8221;Shame on you ever single publisher that&#8217;s pulling this stunt&#8230;. There&#8217;s a really good tool for determining if a game as good or not:  the market!&#8221;</p>
<h3>Robot Testing to the Rescue</h3>
<p>Paul Du Bois of Doublefine described how the company uses a robot &#8220;player&#8221; scripted in Lua to drive functional tests of <em>Brütal Legend</em>, their upcoming open world rock-and-roll fantasy game (which looks like <a href="http://en.wikipedia.org/wiki/Savage_Skies">Savage Skies</a>).  Their Lua scripts simulate controller input to progress through combat, skip cinematics, and generally cheat a lot.</p>
<p>This is all administered by a TestRunner app running on a host PC that looks for idle dev kits and starts test sessions of the game on any that haven&#8217;t been used in the last five minutes.  TestRunner monitors each test for errors, warnings and crashes.</p>
<p>Their Lua implementation emulates cooperative multitasking with sleep calls.  A player test script might look something like:</p>
<blockquote><p>function Class:waitForActiveLine(self, ent)<br />
while true do<br />
  self:sleep(0)<br />
    if ent.CoVoice.HasActiveVoiceLine then<br />
      return<br />
    end<br />
  end<br />
end</p></blockquote>
<p>As a debugging tool, this has several useful characteristics.  &#8221;Failed tests tend to be that the game has crashed or the bot has gotten stuck,&#8221; Du Bois said.  They also catch &#8220;desyncs&#8221;&#8211;determinism failures when they&#8217;re running two networked copies of the game in lockstep during multiplayer.  And they generate graphs of performance/memory usage that can be analyzed either over the course of a single game session or from one build to another.</p>
<p>Debug builds are usually so slow that humans don&#8217;t want to play them.  But the test robot is infinitely patient.  It will play at any framerate, however slow, and crashes with debug symbols.</p>
<h3>Best quotes from GDC</h3>
<p>&#8220;Entertainment is supposed to be enjoyable.  If it can&#8217;t be enjoyed, it&#8217;s not the consumer&#8217;s fault.  The fault belongs to us.&#8221;  &#8211; Satoru Iwata</p>
<p>&#8220;There&#8217;s nothing more humbling than looking at regular people trying to play your game without assistance.&#8221;  &#8211; Gordon Walton</p>
<p>&#8220;One of the danger signs [on Star Wars Galaxies] was that people didn&#8217;t play the game.  In a AAA game company, everybody plays the game.&#8221;  &#8211; Rich Vogel</p>
]]></content:encoded>
			<wfw:commentRss>http://gamearchitect.net/2009/03/29/gdc-2009-the-year-we-went-hungry/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>The Race for a New Game Machine</title>
		<link>http://gamearchitect.net/2009/03/01/the-race-for-a-new-game-machine/</link>
		<comments>http://gamearchitect.net/2009/03/01/the-race-for-a-new-game-machine/#comments</comments>
		<pubDate>Mon, 02 Mar 2009 05:45:28 +0000</pubDate>
		<dc:creator>Kyle</dc:creator>
				<category><![CDATA[Uncategorized]]></category>

		<guid isPermaLink="false">http://gamearchitect.net/?p=26</guid>
		<description><![CDATA[&#8220;I always envied the guys who wrote the software that would power the PlayStation 3.&#8221;  (p. 58)
The Race For a New Game Machine, by David Shippy and Mickie Phipps, is a clumsily-written and frustratingly vague book, but game developers should read it anyway.
Shippy led the team that developed the PowerPC core common to the PS3&#8217;s Cell processor [...]]]></description>
			<content:encoded><![CDATA[<p><img class="alignleft size-full wp-image-28" style="margin: 5px;" title="Race For A New Game Machine" src="http://gamearchitect.net/wp-content/uploads/2009/03/race.jpg" alt="Race For A New Game Machine" width="161" height="250" />&#8220;I always envied the guys who wrote the software that would power the PlayStation 3.&#8221;  (p. 58)</p>
<p><em>The Race For a New Game Machine</em>, by David Shippy and Mickie Phipps, is a clumsily-written and frustratingly vague book, but game developers should read it anyway.</p>
<p>Shippy led the team that developed the PowerPC core common to the PS3&#8217;s Cell processor and the Xbox 360 CPU.  Although his subordinate Mickie Phipps is given equal authorial credit, <em>Race </em>is written entirely in Shippy&#8217;s voice.  Shippy was middle management, two levels up from the engineers designing the logic and circuitry of the processor and two levels down from the corporate VPs negotiating with Microsoft and Sony.  As a result the book mixes corporate politics and technical detail.  Unfortunately it rarely gives a satisfying dose of either.</p>
<p>&#8220;When the [Halo 3] player swings the joystick and levels a weapon at a charging alien beast,&#8221; Shippy writes in his introduction, &#8220;then presses the button and showers it with lead, splattering it straight back to hell, the quality of the experience depends less on the fancy code written by the people at Microsoft than on the processor brains in the chip inside the box.&#8221;  I&#8217;m a software developer, so my biases are obvious, but the primacy of hardware strikes me as a difficult argument to make.  There are plenty of games available for the Xbox 360 that most players would agree don&#8217;t come close to the &#8220;quality of the experience&#8221; delivered by Halo, though they run on the same platform.  And consumers voting with their money seem to think that Wii Fitness delivers a higher-quality experience than Halo does, on hardware with a fraction of the processing power.  I&#8217;d argue that hardware has been a commodity for some time, that game code is in the process of becoming a commodity, and that for a game to differentiate itself in the market today, it has to do so in the quality of its creative attributes:  art direction, story and game design.</p>
<p>Unfortunately Shippy has a habit of  resorting to purple prose at the cost of clarity and accuracy.  Consider his description of the history of electronic gaming:</p>
<blockquote><p>Throughout the 1970s and 1980s the PC industry skyrocketed, too, providing the perfect low-cost platform for game developers.  They capitalized on each step up in the PC&#8217;s speed or bandwidth, each increase in the size of its memory or access time, and every decrease in power consumption.  Graphics engines (separate chips that could handle the graphics creation for the games) allowed the PC&#8217;s microprocessor to focus on the calculations to create characters that move and behave more like real people and environments that are more intense&#8230;. The rise in the PC games market dealt a near death blow to the game console industry.  By the early 1980s, even with new models still on the shelf, consumers were rapidly losing interest in the aging Atari game machine, and no heir-apparent was in sight&#8230;. It took nearly a decade, but the game console market suddenly bounced back from the dead with the launch of Sony&#8217;s Playstation in 1994&#8230;</p></blockquote>
<p>In the space of a page, Shippy gives the impression that</p>
<ul>
<li>Consumer PC 3D graphics cards existed in the eighties</li>
<li>PC game developers care about power consumption</li>
<li>Gaming PCs with graphics and sound acceleration killed the Atari 2600</li>
<li>The Nintendo NES never existed</li>
</ul>
<p>Coming from a pair of engineers, such technical imprecision is astonishing.  The clumsiness extends to the authors&#8217; use of language as well.  They &#8220;hone in on&#8221; solutions and &#8220;flush out ideas.&#8221;  Shippy interrupts a discussion of logic changes with the tortuously mixed metaphor, &#8220;In other words, there would be road construction to add new highways, and the traffic cop would have a lot more balls up in the air to juggle.&#8221;</p>
<p>But if a good copy editor could have helped the writers with their wording, he would have been powerless to correct their technical sloppiness.  For example, Shippy provides the oddest description of a game&#8217;s update-render loop that I&#8217;ve ever heard:</p>
<blockquote><p>Although it may seem like magic to most people, game code is really quite simple.  It can fundamentally be broken down into three major options.  First it requires incoming streams of large amounts of data generated from a peripheral such as a joystick, controller, or keyboard.  This is called &#8220;read streaming.&#8221;  Second, that incoming data stream has to be processed by one or more numeric engines.  Finally, the data processed in the numeric engines has to be streamed back out to the video display to create the colorful graphics.  This is called &#8220;write streaming.&#8221;</p></blockquote>
<p>I&#8217;ve worked as a software engineer on games for more than a decade, most of that in core technology, and I&#8217;ve never heard of &#8220;read streaming&#8221; or &#8220;write streaming&#8221; before.  Controller inputs provide a trivially small amount of data.  (That&#8217;s why networked real-time strategy games tend to sync inputs and run deterministic simulations instead of syncing all game state.)  Write streaming, or &#8220;rendering&#8221; as we call it in the biz, is more memory-bandwidth intensive, but Shippy confuses matters by blurring the line between operations performed on the CPU and operations performed on the graphics processor.</p>
<p>Whether Shippy intends &#8220;write streaming&#8221; to refer to the transfer of data from CPU to GPU or from the GPU to the framebuffer, it accounts for a small fraction of a frame.  Most of the CPU processing time for any game is spent marshaling data and performing general-purpose logic, with smaller portions of the frame devoted to number-crunching for physics, animation or graphics.  Or as <a href="http://crystaltips.typepad.com/wonderland/2005/03/burn_the_house_.html">Chris Hecker puts it</a>, &#8220;graphics and physics grind on large homogenous floating point data structures in a very straight-line structured way.  Then we have AI and gameplay code.  Lots of exceptions, tunable parameters, indirections and often messy.  We hate this code, it’s a mess, but this is the code that makes the game DIFFERENT.&#8221;</p>
<p>You have to wonder if the difference between Hecker&#8217;s understanding of how a frame loop operates and Shippy&#8217;s is part of the reason why the PS3 contains a CPU optimized for stream processing rather than one optimized for messy game logic.  And puzzles like this are the reason why <em>The Race for a New Game Machine</em> is worth reading despite its flaws.  The book tells a story, and if it&#8217;s awkwardly written and frustratingly vague, it also offers occasional fascinating insights into how the consoles on which we develop were created.</p>
<p>As the book relates, the Power core used in the Xbox 360 and the PS3 was originally developed in a joint venture between Sony, Toshiba and IBM.  While development was still ongoing, IBM&#8211;which retained the rights to use the chip in products for other clients&#8211;contracted with Microsoft to use the new Power core in their console.  This arrangement left Sony engineers in an IBM facility unknowingly working on features to support Sony&#8217;s biggest competitor, and left Shippy and other IBM engineers feeling conflicted in their loyalties.</p>
<p><em>Race </em>paints a striking picture of the different corporate cultures at Sony and Microsoft.  Sony comes across as a vast impersonal hierarchy ruled by the impulses of Ken Kutaragi, then head of Sony Computer Entertainment.  Most of the high-level innovations of the Cell processor are attributed to Kutaragi.  So are other  strange and whimsical mandates.  At one point Kutaragi demands that the Cell must have eight Synergistic Processing Units, rather than the originally agreed-upon six, because &#8220;eight is beautiful.&#8221;  IBM complies and produces a chip with eight SPUs.  (The book doesn&#8217;t mention that, <a href="http://en.wikipedia.org/wiki/PlayStation_3_hardware">as Wikipedia points out</a>, the PS3 only has &#8220;six accessible [SPUs] &#8230; to improve production yields.&#8221;  It also never mentions that the 4 GHz core Shippy set out to design became a 3.2 GHz core in the shipping consoles, presumably also to improve yields.)</p>
<p>Microsoft is the agile hare to Sony&#8217;s tortoise.  Individual Microsoft engineers come across as having more initiative&#8211;and a certain cockiness to go with it&#8211;but their desires are less grandiose than Kutaragi&#8217;s and they seem to have a better idea what they want.  Microsoft is focused on software and services.  They want simpler hardware than Sony&#8217;s Cell processor and they&#8217;re flexible in cutting features as long as they make their intended ship date.  Because they&#8217;re developing a processor more similar to an off-the-shelf PowerPC chip, Microsoft is able to put development kits in the hands of game developers a year and a half before Sony.  Because they control their manufacturing risks, they&#8217;re able to put final hardware on shelves a year before Sony.</p>
<p>For readers who are more familiar with the design of software than hardware, <em>The Race for a New Game Machine</em> offers a window into a strange parallel world where much is intriguingly similar and some things are very different.  In the early days of development on the new Power core, Shippy describes junior engineers &#8220;chomping at the bit to dive into the detailed implementation&#8221; before the high-level design is done, an experience familiar to most experienced software developers.  But a few pages later, Shippy tells how a &#8220;junior engineer&#8217;s face lit up with enthusiasm&#8221; at the idea of getting a new idea patented.  Software patents are anathema to most game developers!  The technical work the book describes is a mix of logic design, which sounds familiar to anyone used to writing code, and physical layout, which sounds more like playing SimCity as the chip designers map that logic onto actual circuits on the smallest chip possible.  Finally, Shippy&#8217;s description of the brutal crunch engineers experienced in finishing the chip&#8217;s design will be all too familiar to anyone who&#8217;s shipped a game.</p>
<p>One of the unnecessary risks Sony took on in developing the PS3 was an attempt to build their own graphics processor.  Toward the end of the Cell&#8217;s development, Shippy writes, &#8220;the graphics chip designed by the Sony engineers was slipping schedule.  Sony had designed simple graphics chips in the past, but it was clearly not their area of expertise.  After many months of schedule slips, it became obvious that Sony could not deliver the promised graphics chip.&#8221;  This story raises as many questions as it answers.  Was Sony trying to develop a full GPU, or merely developing a rasterizer in the assumption that the Cell&#8217;s SPUs could handle vertex transformation?  If the latter, did the graphics processor fail to perform, did the SPUs, or could the platform not transfer data from SPUs to processor fast enough?</p>
<p>The story raises as many questions as it answers.  But if <em>The Race for a New Game Machine</em> hadn&#8217;t been written, we wouldn&#8217;t know to ask those questions at all.  We&#8217;re better off for having read the book.  It&#8217;s just a shame the book&#8217;s not better.</p>
]]></content:encoded>
			<wfw:commentRss>http://gamearchitect.net/2009/03/01/the-race-for-a-new-game-machine/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
		</item>
		<item>
		<title>Good Middleware</title>
		<link>http://gamearchitect.net/2008/09/19/good-middleware/</link>
		<comments>http://gamearchitect.net/2008/09/19/good-middleware/#comments</comments>
		<pubDate>Sat, 20 Sep 2008 05:17:11 +0000</pubDate>
		<dc:creator>Kyle</dc:creator>
				<category><![CDATA[Game Engine Design]]></category>
		<category><![CDATA[General Industry]]></category>
		<category><![CDATA[Software Development]]></category>

		<guid isPermaLink="false">http://gamearchitect.net/?p=21</guid>
		<description><![CDATA[Love is patient, love is kind.  It does not envy, it does not boast, it is not proud.  It is not rude, it is not self-seeking, it is not easily angered, it keeps no record of wrongs.  Love does not delight in evil but rejoices with the truth.  It always protects, always trusts, always hopes, [...]]]></description>
			<content:encoded><![CDATA[<blockquote><p>Love is patient, love is kind.  It does not envy, it does not boast, it is not proud.  It is not rude, it is not self-seeking, it is not easily angered, it keeps no record of wrongs.  Love does not delight in evil but rejoices with the truth.  It always protects, always trusts, always hopes, always perseveres.</p></blockquote>
<blockquote><p>1 Corinthians 13</p></blockquote>
<p>Love is easy.  Middleware is hard.</p>
<p>We used middleware on Fracture for physics, tree rendering, audio, animation, facial animation, network transport, and various other systems.  Now that the game is finished, we&#8217;re taking stock of the lessons that we learned and deciding what packages we want to keep and what we want to replace as we move forward.</p>
<p>Middleware offers two main benefits, each of which is balanced by an associated cost:</p>
<p style="padding-left: 30px;"><strong>1.  </strong>Middleware provides you with more code than you could write yourself for a fraction of what it would cost you to try.  No matter how clever you are, that&#8217;s how the economics of the situation work.  The costs of developing a piece of software are largely fixed.  But once written, any piece of software can be sold over and over again.  Because they can spread their costs over a large number of customers, middleware vendors can afford to keep larger, more experienced teams working on a given piece of functionality than independent game developers can.  During Fracture, we watched a couple of pieces of immature middleware spring up after we&#8217;d written similar tools ourselves.  We watched those pieces of middleware grow and surpass our tools, because we couldn&#8217;t afford to devote the resources to our tools that the middleware vendors devoted to theirs.</p>
<p style="padding-left: 30px;">The corresponding cost is that none of the functionality you get is <em>exactly</em> what you would have written yourself, and much of it will be entirely useless to you.  Middleware is written to support the most common cases.  If you have specific needs that differ from the norm, you may be better off implementing a solution yourself.</p>
<p style="padding-left: 30px;"><strong>2.  </strong>Middleware offers structure.  Middleware draws a line between the things that you have to worry about and the things you don&#8217;t.  As long as it&#8217;s reasonably well documented and stable, you don&#8217;t need to waste mental bandwidth worrying about the things that go on underneath your middleware&#8217;s public API.  As games grow ever-larger and more complex it&#8217;s become incredibly valuable to be able to draw a line and say, <em>The stuff on the other side of that line isn&#8217;t my responsibility, and I don&#8217;t have to worry about it.</em></p>
<p style="padding-left: 30px;">The associated cost is that you can&#8217;t change what&#8217;s on the other side of that line.  If you&#8217;re going to use middleware, you have to be willing to accept a certain amount of inflexibility in dealing with the problems that the middleware solves.  You have to be willing to shape your own technology to suit the third-party libraries that you&#8217;re buying.  Trying to do otherwise is a recipe for misery.</p>
<p>Given those benefits and costs, it makes sense to use middleware wherever you can&#8211;as long as you don&#8217;t try to license technology in the areas where you want your game to be unique.  Every game has certain unique selling propositions:  things that make it distinct from every other game on the market.  Likewise, every game has certain characteristics that it shares with many others.  When it comes to the latter, you should buy off-the-shelf technology, accept that technology&#8217;s inflexibility, and modify your game design to suit it.  When it comes to the former, you should write the code in-house.  As Joel Spolsky says, don&#8217;t <a href="http://www.joelonsoftware.com/articles/fog0000000007.html">outsource your core competency</a>.</p>
<p>So now that you&#8217;ve figured out which game functions you should be implementing through middleware, how do you decide which of the scads of available middleware packages is best for you?  There are a number of issues to keep in mind.</p>
<p><strong>Good middleware lets you hook your own memory allocator.</strong>  If your approach to memory is to partition the entire free space up front and minimize runtime allocations, then you&#8217;ll want the ability to reserve a block for your middleware and allocate out of that.  Even if you allow dynamic allocations at any time, you&#8217;ll want to track how much memory is used by each system and instrument allocations to detect memory leaks.  Any piece of middleware that goes behind your back and allocates memory directly just isn&#8217;t worth buying.</p>
<p><strong>Good middleware lets you hook your own I/O functions.</strong>  Most games store resources in package files like the old Doom <a href="http://en.wikipedia.org/wiki/WAD_file">WAD files</a>.  Middleware that doesn&#8217;t let you hook file I/O doesn&#8217;t let you put its resources in packfiles.  Many modern games stream resources off DVD as the player progresses through a level.  If you can&#8217;t control middleware I/O operations, then you can&#8217;t sort file accesses to minimize DVD seeks.  You&#8217;ll waste read bandwidth and your game will be subject to unpredictable hitches.  Again, any piece of middleware that does file I/O directly just isn&#8217;t worth buying.</p>
<p><strong>Good middleware has extensible functionality.</strong>  No middleware package will do everything you want out of the box.  But you shouldn&#8217;t have to modify any piece of middleware to make it do what you need.  Good middleware offers abstract interfaces that you can implement and callbacks that you can hook where you need to do something unique to your game.  An animation package may let you implement custom animation controllers.  A physics package may let you write your own collision primitives.  Your objects should be first-class citizens of your middleware&#8217;s world.</p>
<p><strong>Good middleware avoids symbol conflicts.</strong>  Beware of middleware that uses the Standard Template Library carelessly.  It&#8217;ll work fine until you try to switch to STLPort or upgrade to a new development environment, and then you&#8217;ll suddenly find that your engine has multiple conflicting definitions of std::string and other common classes.  To avoid symbol clashes, every class in a middleware library should start with a custom prefix or be scoped inside a library namespace.  And if a piece of middleware is going to use the STL, it should do so carefully, making sure that every STL class instantiated uses a custom allocator.  That allows you to hook your own memory allocator <em>and</em> avoids symbol conflicts.</p>
<p><strong>Good middleware is explicit about its thread safety.</strong>  We live in an ever-more-multithreaded world, but one where most game engines are still bound by main thread operations most of the time.  For best performance, you want to offload any operations you can onto other threads.  To do that with a piece of middleware, you need to know which operations can be performed concurrently and which have to happen sequentially.  Ideally a piece of middleware will let you create resources asynchronously so you can construct objects in a loader thread before handing them off to the game.</p>
<p><strong>Good middleware fits into your data pipeline.</strong>  Most companies export data in an inefficient platform-independent format, then cook it into optimized platform-specific formats and build package files out of those as part of a resource build.  Any piece of middleware should allow content creators to export their assets in a platform-independent format.  Ideally, that format should still be directly loadable.  The build process should be able to generate platform-specific versions of those assets using command-line tools.</p>
<p><strong>Good middleware is stable.</strong>  One of the main benefits of middleware is that it frees your mind to focus on more critical things.  In this respect, middleware is like your compiler:  It frees you from having to think about low-level implementation details&#8211;<em>but only as long as you trust the compiler!</em>  A buggy piece of middleware is a double curse, because instead of freeing your attention from a piece of functionality, it forces you to focus your attention there, on code that was written by a stranger and that no one in your company understands.  Worse still, if you&#8217;re forced to make bug fixes yourself, then you need to carry them forward with each new code drop you get of your middleware libraries.  You shouldn&#8217;t need to concern yourself with the implementation details of your middleware.  Middleware is only a benefit to the extent that its API remains inviolate.</p>
<p><strong>Good middleware gives you source.</strong>  Despite the previous point, having access to the source for any middleware package is a must.  Sometimes you&#8217;ll suspect that there&#8217;s a bug in the middleware.  Sometimes you need to see how a particular input led to a particular result before you can understand why the input was wrong.  Sometimes you&#8217;ll have to fix a bug no matter how good the middleware is.  And frequently you&#8217;ll need to recompile to handle a new platform SDK release or to link with some esoteric build configuration.</p>
<p>There are other questions to ask about any piece of middleware:  How much memory does it use?  How much CPU time does it require?  What&#8217;s the upgrade path for your current code and data?  How does it interact with your other middleware?  How good is the vendor&#8217;s support?  How much does it cost?</p>
<p>But those questions have vaguer answers.  Acceptable performance or cost will vary depending on the nature of your product.  A cell phone game probably can&#8217;t afford to license the Unreal Engine&#8211;and probably couldn&#8217;t fit it in available memory if it did!  Data upgrade paths are less of a concern if you&#8217;re writing a new engine from scratch than if you&#8217;re making the umpteenth version of an annual football game.</p>
<p>The rules that don&#8217;t vary are:  You should buy middleware wherever you can do so without outsourcing your core competency.  And to be worth buying, any piece of middleware should behave itself with respect to resource management and concurrency.</p>
]]></content:encoded>
			<wfw:commentRss>http://gamearchitect.net/2008/09/19/good-middleware/feed/</wfw:commentRss>
		<slash:comments>12</slash:comments>
		</item>
		<item>
		<title>An Anatomy of Despair:  Managers and Contexts</title>
		<link>http://gamearchitect.net/2008/09/13/an-anatomy-of-despair-managers-and-contexts/</link>
		<comments>http://gamearchitect.net/2008/09/13/an-anatomy-of-despair-managers-and-contexts/#comments</comments>
		<pubDate>Sun, 14 Sep 2008 02:46:48 +0000</pubDate>
		<dc:creator>Kyle</dc:creator>
				<category><![CDATA[Despair Engine]]></category>
		<category><![CDATA[Game Engine Design]]></category>
		<category><![CDATA[Software Development]]></category>

		<guid isPermaLink="false">http://gamearchitect.net/?p=18</guid>
		<description><![CDATA[Many of the design ideas that shaped the Despair Engine were reactions to problems that had arisen in earlier projects that we&#8217;d worked on.  One of those problems was the question of how to handle subsystem managers.
Many systems naturally lend themselves to a design that gathers the high-level functionality of the system behind a single interface:  A FileManager, for [...]]]></description>
			<content:encoded><![CDATA[<p>Many of the design ideas that shaped the Despair Engine were reactions to problems that had arisen in earlier projects that we&#8217;d worked on.  One of those problems was the question of how to handle subsystem managers.</p>
<p>Many systems naturally lend themselves to a design that gathers the high-level functionality of the system behind a single interface:  A FileManager, for example, might expose functions for building a file database from packfiles and loose files.  An AudioManager might expose functions for loading and playing sound cues.  A SceneManager might expose functions for loading, moving and rendering models.</p>
<p>Once upon a time, these objects would all have been global variables.  There are a number of problems with using global objects as managers, though, the most critical of which is the uncertainty of static initialization and destruction order.  Your managers start out in a pristine garden of Eden, free of all knowledge of good, evil, and (most importantly) one another.  But as your game gets more and more complicated, your managers are going to develop more dependencies on one another.  To add streaming of sounds to AudioManager, for example, you may need to make it reference FileManager.  To stream asynchronously, you may also need to reference AsyncJobManager.  But at construction time, you can&#8217;t be sure that any of those managers exist yet.</p>
<p>This prompts clever people who&#8217;ve read <a href="http://www.amazon.com/Design-Patterns-Object-Oriented-Addison-Wesley-Professional/dp/0201633612/ref=pd_bbs_sr_1?ie=UTF8&amp;s=books&amp;qid=1220327789&amp;sr=8-1">Design Patterns</a> to think, <em>Aha!  I&#8217;ll make all my managers <a href="http://en.wikipedia.org/wiki/Singleton_pattern">Meyers singletons</a>!</em>  And they go and write something like</p>
<pre>FileManager&amp; GetFileManager()
{ 
    static FileManager theFileManager; 
    return theFileManager;
}</pre>
<p>This function will create a FileManager object the first time it&#8217;s called and register it for destruction at program exit.  There are still a couple of problems with that, though:</p>
<ul>
<li>First, like all function-local static variables in C++98, theFileManager is inherently unthreadsafe.  If two threads happen to call GetFileManager simultaneously, and theFileManager hasn&#8217;t been constructed yet, they&#8217;ll both try to construct it.  Wackiness ensues.  This quibble is <a href="http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2008/n2660.htm">due to be fixed</a> in C++0x.</li>
<li>Imagine what happens if the constructor for AudioManager calls GetFileManager and the constructor for FileManager calls GetAudioManager.  To quote chapter and verse of the ISO C++ Standard, &#8220;If control re-enters the declaration (recursively) while the [static] object is being initialized, the behavior is undefined.&#8221; (ISO Standard 6.7.4) The compiler can do whatever it wants, and whatever it does is unlikely to be what <em>you</em> want.</li>
<li>Although Meyers singletons give you a JIT safe order of construction, they make no promises about their order of destruction.  If AudioManager is destroyed at program exit time, but FileManager wants to call one last function in AudioManager from its destructor, then again you have undefined behavior.</li>
</ul>
<p>We dealt with those issues in MechAssault 2 by eschewing automatic singletons in favor of explicitly constructed and destroyed singletons.  Every manager-type object had an interface that looked something like </p>
<pre>class FileManager
{
public:  
    static bool CreateInstance();
    static void DestroyInstance();
    static FileManager* GetInstance();
};</pre>
<p>This works better than automatic singletons.  It worked well enough that we were able to ship a couple of quite successful games with this approach.  We wrote a high-level function in the game that constructed all the managers in some order and another high-level function that shut them all down again.  This was thread-safe, explicitly ordered and deterministic in its order of destruction.</p>
<p>But as we added more and more library managers, cracks started to show.  The main problem was that although we constructed managers in an explicit order, dependencies between managers were still <span style="font-style: italic">implicit</span>.  Suppose, for example, that AudioManager is created before FileManager, but that you&#8217;re tasked with scanning the filesystem for audio files at start-up time.  That makes AudioManager dependent on FileManager for the first time.  Now AudioManager needs to be created <span style="font-style: italic">after</span> FileManager.</p>
<p>Changing the order in which managers were constructed was always fraught with peril.  Finding a new working order was a time-consuming process because ordering failures weren&#8217;t apparent at compile time.  To catch them, you needed to actually run the game and see what code would crash dereferencing null pointers.  And once a new ordering was found, it needed to be propagated to every application that used the reordered managers.  Day 1 has always placed a strong emphasis on its content creation tools, and most of those tools link with some subset of the game&#8217;s core libraries, so a change might need to be duplicated in six or eight tools, all of which would always compile&#8211;but possibly fail at runtime.</p>
<p>With Despair, one of our governing principles has been to make implicit relationships explicit.  As applied to system manager construction, that meant that managers would no longer have static GetInstance functions that could be called whether the manager existed or not.  Instead, each manager takes pointers to other managers as constructor parameters.  As long as you don&#8217;t try to pass a manager&#8217;s constructor a null pointer (which will assert), any order-of-initialization errors will be compile-time failures.  To make sure that managers are also destroyed in a valid order, we use ref-counted smart pointers to refer from one manager to another.  As long any manager exists, the managers that it requires will also exist.</p>
<p>Our current code looks something like  </p>
<p><code>class IAudioManager<br />
{<br />
public:<br />
      IAudioManagerPtr Create(const IFileManagerPtr&amp; fileMgr);<br />
};</code></p>
<p><code> </code></p>
<p><code>class AudioManager<br />
{<br />
public:<br />
      explicit AudioManager(const IFileManagerPtr&amp; fileMgr);<br />
};<br />
</code></p>
<p>One problem remains.  Although AudioManager exposes the public interface of the audio library to the rest of the application, there are also private support and utility functions that the audio system should only expose to its own resources.  Furthermore, many of these utility functions will probably need access to lower-level library managers.</p>
<p>This could be solved by having global utility functions that take manager references as parameters and by making every audio resource hold onto pointers to every lower-level manager that it might use.  But that would bloat our objects and add reference-counting overhead.  A more efficient and better-encapsulated solution was to give each library a context object.  As Allan Kelly describes in his paper on the <a href="http://www.allankelly.net/static/patterns/encapsulatecontext.pdf">Encapsulated Context</a> pattern:  </p>
<blockquote><p>A system contains data that must be generally available to divergent parts of the system but we wish to avoid using long parameter lists to functions or globaldata.  Therefore, we place the necessary data in a Context Object and pass this object from function to function.    </p></blockquote>
<p>In our case, that meant wrapping up all smart pointers to lower-level libraries in a single library context, which would in turn be owned by the library manager and (for maximum safety) by all other objects in the library that need to access a lower-level manager.  Over time, other private library shared state has crept into our library contexts as well.  To maintain a strict ordering, the library manager generally references all the objects that it creates, and they reference the library context, but know nothing about the library manager.</p>
<p>This architecture has generally worked well for us, and has been entirely successful in avoiding the manager order-of-creation and order-of-shutdown issues that plagued earlier games we worked on.  It does have definite costs, however:</p>
<ul>
<li> <span style="font-weight: bold">A lot of typing.</span>  Library managers know about library resource objects which know about library contexts.  But frequently there&#8217;s some functionality that you&#8217;d like to be accessible both to objects outside the library and objects inside the library.  In this architecture, there&#8217;s nowhere to put that functionality except in the library context, with pass-through functions in the library manager.  Since the library manager is usually hidden behind an abstract interface, you can end up adding function declarations to three headers and implementations to two cpp files before you&#8217;re done.</li>
<li><span style="font-weight: bold">Even more typing.</span>  All the lower-level managers held by a library also get passed through a creation function to the library manager&#8217;s constructor to the library context&#8217;s constructor.  That was a mild annoyance when the engine was small and managers were few, but Despair now comprises over fifty libraries.  Most of those libraries have managers, and there are a handful of high-level library managers that take almost all lower-level library managers as constructor parameters.  Managers that take forty or fifty smart pointers as parameters are hard to create and slow to compile.</li>
<li><span style="font-weight: bold">Reference counting woes.</span>  In principle, every object should strongly reference its library context to maintain a strict hierarchy of ownership and to make sure that nothing is left accessing freed memory at program shutdown time.  In practice, though, this doesn&#8217;t work well when objects can be created in multiple threads.  Without interlocked operations, your reference counts will get out of sync and eventually your program will probably crash.  But <span style="font-style: italic">with</span> interlocked operations, adding references to library contexts becomes much more expensive, and can become a significant part of your object creation costs.  In practice, we&#8217;ve ended up using raw pointers to contexts in several libraries where the extra safety wasn&#8217;t worth the additional reference cost.</li>
</ul>
<p>So managers and contexts are far from perfect.  They&#8217;re just the best way we&#8217;ve found so far to stay safe in an ever-more complex virtual world.</p>
]]></content:encoded>
			<wfw:commentRss>http://gamearchitect.net/2008/09/13/an-anatomy-of-despair-managers-and-contexts/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
		</item>
		<item>
		<title>An Anatomy of Despair:  Aggregation Over Inheritance</title>
		<link>http://gamearchitect.net/2008/06/01/an-anatomy-of-despair-aggregation-over-inheritance/</link>
		<comments>http://gamearchitect.net/2008/06/01/an-anatomy-of-despair-aggregation-over-inheritance/#comments</comments>
		<pubDate>Mon, 02 Jun 2008 02:02:20 +0000</pubDate>
		<dc:creator>Kyle</dc:creator>
				<category><![CDATA[Despair Engine]]></category>
		<category><![CDATA[Game Engine Design]]></category>
		<category><![CDATA[Software Development]]></category>

		<guid isPermaLink="false">http://gamearchitect.net/2008/06/01/an-anatomy-of-despair-aggregation-over-inheritance/</guid>
		<description><![CDATA[One of the first decisions that Adrian and I made in our initial work on Despair was to prefer aggregation to inheritance whenever possible.  A game object in Despair, for example, is basically a thin wrapper around a UID and a standard vector of game components.  Components can be queried for type information and dynamically cast.  The game object knows nothing about component implementations.]]></description>
			<content:encoded><![CDATA[<p>One of the first decisions that Adrian and I made in our initial work on Despair was to prefer aggregation to inheritance whenever possible.  This is not an original idea.  If you Google for &#8220;aggregation inheritance&#8221; or &#8220;composition inheritance,&#8221; you&#8217;ll get a million hits.  The C++ development community has been renouncing its irrational exuberance over inheritance for the last few years now.  Sutter and Alexandrescu even include &#8220;prefer composition to inheritance&#8221; as a <a href="http://www.artima.com/cppsource/codestandards3.html">guideline</a> in <a href="http://www.amazon.com/C%2B%2B-Coding-Standards-Guidelines-Depth/dp/0321113586/ref=pd_bbs_sr_1?ie=UTF8&amp;s=books&amp;qid=1211858088&amp;sr=8-1">C++ Coding Standards</a>.</p>
<p><img border="0" align="right" width="240" src="http://gamearchitect.net/wp-content/uploads/2008/06/liberation2.jpg" alt="liberation2.jpg" height="521" />Nonetheless, every game engine we&#8217;d worked on before Despair had a similar deep inheritance hierarchy of the sort that was in vogue in the mid-nineties:  a player class might inherit from some kind of combatant class, which would inherit from a mover class, which would inherit from a physical object class, which would inherit from a base game object class.</p>
<p>This architecture has a lot of shortcomings.  Let me enumerate a few of them:</p>
<p>First, it&#8217;s inflexible.  If you want to create a new AI enemy that has some of the capabilities of enemy A and some of the capabilities of enemy B, that&#8217;s not a task that fits naturally into a hierarchical object classification.  Ideally, you&#8217;d like the designers to be able to create a new enemy type without involving you, the programmer, at all.  But with a deep object hierarchy, you have to get involved and you have to try to pick the best implementation from several bad options:  to have your new enemy class inherit from one object and cut-and-paste the functions you need from the other; to not inherit from either, and to cut-and-paste the functions you need from both; or to tiptoe down the treacherous slippery slope of multiple inheritance and hope that it doesn&#8217;t lead to a <a href="http://en.wikipedia.org/wiki/Diamond_of_Death">diamond of death</a>.</p>
<p>Second, a handful of classes in your hierarchy tend to grow without bound over a game&#8217;s development.  If the player class is part of the object hierarchy, then you can expect this class to include input and control systems, custom animation controls, pickup and inventory systems, targeting assistance, network synchronization&#8211;plus any special systems required by the particular game that you&#8217;re making.  One previous game that we worked on features a 13,000 line player class implementation, and the player class inherited from a 12,000 physical object class.  It&#8217;s hard to find anything in files that size, and they&#8217;re frequent spots for merge conflicts since everyone&#8217;s trying to add new stuff to them all the time.</p>
<p>Third, deep inheritance is poor <em>physical</em> structure.  If class A inherits from class B which inherits from class C, then the header file for A&#8211;A.h&#8211;has to #include B.h and C.h.  As your hierarchy gets deeper, you&#8217;ll find that all of your leaf classes have to include four or five extra headers for their base classes at different levels.  For most modern games, as much compile time is spent opening and reading header files as is spent actually compiling code.  The more loosely your code is coupled, the faster you can compile.  (See <a href="http://www.amazon.com/Large-Scale-Software-Addison-Wesley-Professional-Computing/dp/0201633620/ref=sr_1_1?ie=UTF8&amp;s=books&amp;qid=1212369301&amp;sr=8-1">Lakos</a> for more details.)</p>
<p>Therefore we resolved to make Despair as component-based as we could, and to keep our inheritance hierarchies as flat as possible.  A game object in Despair, for example, is basically a thin wrapper around a UID and a standard vector of game components.  Components can be queried for type information and dynamically cast.  The game object provides only lifetime management and identifier scoping.  It knows nothing about component implementations.  It contains no traditional game object state like position, bounds, or visual representation.</p>
<p>This approach has informed other systems as well.  Our scene object implementation is similar to the game object implementation, with a single object representing each model that provides lifetime management for a vector of scene nodes.  Scene nodes manage their own hierarchies for render state or skeletal transforms.</p>
<p>Another family of systems is built on a flow-graph library for visual editing.  Game logic, animation systems, and materials can all be built by non-programmers wiring together graph components in the appropriate tools.</p>
<p>Using composition instead of inheritance has worked very well for us.  Our primary concern when we set out in this new direction was that we&#8217;d end up with something that had horrible runtime performance.  With <em>Fracture</em> almost complete, though, there&#8217;s no evidence that our performance is worse than it would have been with a deep inheritance hierarchy.  If anything, I&#8217;m inclined to suspect that it&#8217;s better, since well-encapsulated components have better cache locality than large objects and since the fact that we only update dirty components each frame means that we can decide what does and doesn&#8217;t need to be updated at a finer granularity.</p>
<p>If I were starting over again, the only change I&#8217;d make with respect to object composition is to make scene objects more opaque and less like game objects.  Scene objects have a different problem to solve.  We have several hundred game components now, with more going in all the time, and the flexibility of having a thin game object interface that allows querying components for type has paid big dividends.  I think that our game object system is close to ideal for iterating rapidly on gameplay.  Scene objects are a different kind of problem, though.  We haven&#8217;t added any new scene node types since the scene library was written, and all scene nodes are implemented in the scene library instead of in higher-level code.  At the same time, it would be nice to be able to experiment with different optimizations of updating skeletal hierarchies without breaking higher-level code.  All of this argues that following the <a href="http://en.wikipedia.org/wiki/Law_Of_Demeter">Law of Demeter</a> and hiding scene object implementation details would have been appropriate for scene objects even if it wasn&#8217;t appropriate in the rapid-prototyping environment of game objects.</p>
<p>Beyond the perfect abstract world of software architecture, component based design also created a couple of surprises in the messier world of development process and human interaction.  One lesson of working with a composition-based engine is that the learning curve for new programmers is steeper.  For programmers who are used to being able to step through a few big nested functions and see the whole game, it can be disorienting to step through the game and discover that there&#8217;s just no <em>there</em> there.  For example, Despair contains over 500 classes with the word &#8220;component&#8221; in their names and 100 classes with the word &#8220;object&#8221; in their names.  Our games aren&#8217;t defined by C++ objects, they&#8217;re defined by relationships between them.  To understand those relationships, you need good documentation and communication more than ever.</p>
<p>Another composition lesson is that component-based design takes a lot of the <img border="0" width="1" src="http://gamearchitect.net/wp-admin/" height="1" />complexity that used to exist in code and pushes it into data.  Designers aren&#8217;t used to designing objects and constructing inheritance hierarchies.  Working with components requires new processes and good people.  Cross-pollination is important.  Your programmers need to work building objects in your tools, as well as writing code for components, and they need to work hand-in-hand with good technical designers who can provide tool feedback and build on the object primitives available to them.  Like a game, your team isn&#8217;t defined by its individual components but by the relationships between them.</p>
]]></content:encoded>
			<wfw:commentRss>http://gamearchitect.net/2008/06/01/an-anatomy-of-despair-aggregation-over-inheritance/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>An Anatomy of Despair:  Orthogonal Views</title>
		<link>http://gamearchitect.net/2008/04/19/an-anatomy-of-despair-orthogonal-views/</link>
		<comments>http://gamearchitect.net/2008/04/19/an-anatomy-of-despair-orthogonal-views/#comments</comments>
		<pubDate>Sun, 20 Apr 2008 01:26:31 +0000</pubDate>
		<dc:creator>Kyle</dc:creator>
				<category><![CDATA[Despair Engine]]></category>
		<category><![CDATA[Game Engine Design]]></category>
		<category><![CDATA[Software Development]]></category>

		<guid isPermaLink="false">http://gamearchitect.net/2008/04/19/an-anatomy-of-despair-orthogonal-views/</guid>
		<description><![CDATA[A frustrating feature of previous game engines we&#8217;d used was that they tended to overload hierarchy to mean multiple things.
The engine that we used at Cyan, for example, was a pure scene graph.  Every part of the game was represented by one or more nodes in a hierarchy.  But the hierarchy represented logical relationships in some [...]]]></description>
			<content:encoded><![CDATA[<p><span style="font-family: Georgia">A frustrating feature of previous game engines we&#8217;d used was that they tended to overload hierarchy to mean multiple things.</span></p>
<p><span style="font-family: Georgia">The engine that we used at Cyan, for example, was a <img border="0" align="left" width="251" src="http://gamearchitect.net/wp-content/uploads/2008/04/tree.gif" alt="Tree" height="179" />pure scene graph.  Every part of the game was represented by one or more nodes in a hierarchy.  But the hierarchy represented logical relationships in some places and kinematic relationships in others.  Throughout the graph, ownership was conflated with update order:  children would be deleted when their parents were deleted and parents always updated before their children.  Kinematic attachment was performed by pruning and grafting trees in the graph, which had the effect of tying the lifetimes of attached objects to the lifetimes of their parents.</span></p>
<p><span style="font-family: Georgia"><span id="more-10"></span></span></p>
<p><span style="font-family: Georgia">The engine used for MechAssault 2 was similar, except that it had separate game object and scene hierarchies.  In both hierarchies, graph relationships defined ownership and update order:  children would be deleted when their parents were deleted and parents were always updated before their children.  In the game object graph, hierarchy also defined logical relationships that varied based on the objects involved.  Triggers, for example, would treat certain of their child objects as inputs to be checked and others as objects to be acted on.  In principle, the entire game object hierarchy updated, then the entire scene hierarchy updated.  In practice, we needed to know the final animated positions of some objects so that we knew where to create effects, so some trees in the scene hierarchy got explicitly updated during the game object update.</span></p>
<p><span style="font-family: Georgia">All of this was very confusing.  It also meant that changes to the hierarchy motivated by one concern tended to have unforeseen side-effects in other areas.  And it necessitated odd hacks like the MechAssault&#8217;s explicit updating of sub-trees in the scene graph. In developing Despair, therefore, we decided to have one data-structure per purpose.  As mentioned <a href="http://gamearchitect.net/2008/04/15/an-anatomy-of-despair-object-ownership/"><font color="#800080">previously</font></a>, we have a well-defined ownership hierarchy among our objects.  For example,</span></p>
<ul type="disc">
<li style="margin: 0in 0in 0pt; line-height: 15.6pt; tab-stops: list .5in" class="MsoNormal"><span style="font-family: Georgia">The streaming manager owns worlds<o:p></o:p></span></li>
<li style="margin: 0in 0in 0pt; line-height: 15.6pt; tab-stops: list .5in" class="MsoNormal"><span style="font-family: Georgia">Worlds own game objects<o:p></o:p></span></li>
<li style="margin: 0in 0in 0pt; line-height: 15.6pt; tab-stops: list .5in" class="MsoNormal"><span style="font-family: Georgia">Game objects own game components</span></li>
<li style="margin: 0in 0in 0pt; line-height: 15.6pt; tab-stops: list .5in" class="MsoNormal"><span style="font-family: Georgia">Game components own scene objects (and audio resources, and HUD elements, etc&#8230;)<o:p></o:p></span></li>
<li style="margin: 0in 0in 0pt; line-height: 15.6pt; tab-stops: list .5in" class="MsoNormal"><span style="font-family: Georgia">Scene objects own mesh nodes (and transform nodes, and light nodes, etc&#8230;)<o:p></o:p></span></li>
<li style="margin: 0in 0in 0pt; line-height: 15.6pt; tab-stops: list .5in" class="MsoNormal"><span style="font-family: Georgia">Mesh nodes own vertex groups and index lists<o:p></o:p></span></li>
</ul>
<p><span style="font-family: Georgia">In some cases ownership is shared and in some cases it isn&#8217;t, but each object has its level of the hierarchy.  <o:p></o:p></span><span style="font-family: Georgia">But in addition to the hierarchy that we use for ownership, we also have parallel data structures for<o:p></o:p></span></p>
<ul type="disc">
<li style="margin: 0in 0in 0pt; line-height: 15.6pt; tab-stops: list .5in" class="MsoNormal"><span style="font-family: Georgia">the object registry used for object look-up<o:p></o:p></span></li>
<li style="margin: 0in 0in 0pt; line-height: 15.6pt; tab-stops: list .5in" class="MsoNormal"><span style="font-family: Georgia">the dependency graph used for object update<o:p></o:p></span></li>
<li style="margin: 0in 0in 0pt; line-height: 15.6pt; tab-stops: list .5in" class="MsoNormal"><span style="font-family: Georgia">the physical representation of the world (stored in Havok&#8217;s internal hierarchy)<o:p></o:p></span></li>
<li style="margin: 0in 0in 0pt; line-height: 15.6pt; tab-stops: list .5in" class="MsoNormal"><span style="font-family: Georgia">the renderable representation of the world (stored in our own sphere tree of renderable objects)<o:p></o:p></span></li>
<li style="margin: 0in 0in 0pt; line-height: 15.6pt; tab-stops: list .5in" class="MsoNormal"><span style="font-family: Georgia">etc.<o:p></o:p></span></li>
</ul>
<p><span style="font-family: Georgia">This has been a big win in terms of clarity and flexibility.  It&#8217;s clear when looking at a component what its lifetime will be.  It&#8217;s easy to make a component update later in the frame, or not update at all, without having to worry that your change will affect when the object is deleted or whether it&#8217;s rendered.  Scene objects and game components are part of the same dependency hierarchy.  Therefore, the component that creates a fire effect can make itself dependent on the scene object for the player&#8217;s weapon.  That way the fire effect won&#8217;t be created until the weapon has determined its final position for the frame, and the fire effect will be created at the correct location.</span></p>
<p><span style="font-family: Georgia">The performance implications of orthogonal views are unclear.  One of the frustrations of building a game engine is that you never have the leisure of changing one architectural variable while keeping all others constant.  That means that you can never be sure you&#8217;ve made the best decision.  You can only be sure&#8211;sometimes&#8211;when you&#8217;ve made a very bad one.<o:p></o:p></span><span style="font-family: Georgia"><img border="0" align="right" width="244" src="http://gamearchitect.net/wp-content/uploads/2008/04/tree2.gif" alt="Trees" height="169" />Having orthogonal views of our data was clearly not a decision worthy of regret.  But it&#8217;s difficult to be certain whether it&#8217;s a net win in terms of performance.  On the negative side, all these different hierarchies are scattered at widely different locations in memory, and on modern hardware memory locality drives performance more than the number of instructions executed does.  But on the other hand, having independent views of the data means that each only needs to process what matters.  Our update pass only updates objects that are actually changing.  Our render pass doesn&#8217;t waste any overhead on objects that aren&#8217;t renderable.  And when those systems operate, they perform similar operations on sorted lists of similar objects, which is the sort of thing that modern hardware has gotten very good at.  So I think this idiom is a performance win, but the only hard data I have to back that up is that we&#8217;re spending less time waiting on cache misses than we were in MechAssault 2.  Given the other differences between Despair and the MechAssault 2 engine and between the Xbox 360 and the original Xbox, that evidence is suggestive but not conclusive.</span></p>
<p><span style="font-family: Georgia">The one area in which orthogonal views have a clear cost is memory.  As objects add themselves to all our different systems, they may have representations in the registry, in the dependency graph, the scene hierarchy, the physics hierarchy, the render hierarchy, and probably one or two other systems that I&#8217;m forgetting.  I&#8217;d estimate that this overhead adds up to somewhere between two and three megabytes for a typical level in Fracture.  On a console with 512 megabytes of memory that cost seems justifiable, but it would have been less practical on an Xbox or PlayStation 2 game.</span></p>
]]></content:encoded>
			<wfw:commentRss>http://gamearchitect.net/2008/04/19/an-anatomy-of-despair-orthogonal-views/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>An Anatomy of Despair:  Object Ownership</title>
		<link>http://gamearchitect.net/2008/04/15/an-anatomy-of-despair-object-ownership/</link>
		<comments>http://gamearchitect.net/2008/04/15/an-anatomy-of-despair-object-ownership/#comments</comments>
		<pubDate>Wed, 16 Apr 2008 05:16:29 +0000</pubDate>
		<dc:creator>Kyle</dc:creator>
				<category><![CDATA[Despair Engine]]></category>
		<category><![CDATA[Game Engine Design]]></category>
		<category><![CDATA[Software Development]]></category>

		<guid isPermaLink="false">http://gamearchitect.net/2008/04/15/an-anatomy-of-despair-object-ownership/</guid>
		<description><![CDATA[In every game engine that I worked on before Despair, I spent a lot of time tracking down memory leaks.  Some leaks were obvious and easy to find.  Some leaks involved complex patterns of ownership that thoroughly obscured what object was supposed to be responsible for deleting another.  And some leaks involved AddRef/Release mismatches that [...]]]></description>
			<content:encoded><![CDATA[<p>In every game engine that I worked on before Despair, I spent a lot of time tracking down memory leaks.  Some leaks were obvious and easy to find.  Some leaks involved complex patterns of ownership that thoroughly obscured what object was <em>supposed</em> to be responsible for deleting another.  And some leaks involved AddRef/Release mismatches that would create cycles of ownership or that would leak whole object hierarchies.</p>
<p><span id="more-7"></span></p>
<p>We wanted to improve stability and leak less memory in Despair, and this led us to consider exception safety.  Exception safety is the idea that a program should always remain in a valid state in the presence of exceptions.  Operations should succeed or fail, but if they fail, they should have no side effects and program data should remain unchanged.  Memory leaks frequently occur when exception <em>unsafe</em> code encounters an exceptional situation.  A function may throw an exception to signal bad data, for example, and thereby skip clean-up of temporary objects done at the end of the function.</p>
<p>Despair doesn&#8217;t use exceptions, because they introduce <a href="http://www.gamearchitect.net/Articles/ExceptionsAndErrorCodes.html">significant overhead</a>, but we do use error codes and FAIL_RETURN macros that may early exit from a function.  These introduce similar problems.  Therefore we try to be exception-safe wherever possible without hurting performance.  In practice, performance concerns generally keep us from using the <a href="http://en.wikipedia.org/wiki/Opaque_pointer">PIMPL idiom</a> to implement atomic transactions.  But we do use the <a href="http://en.wikipedia.org/wiki/Resource_Acquisition_Is_Initialization">Resource Acquisition Is Initialization</a> idiom extensively.  Our XML writer uses scoped EnterElement/LeaveElement objects.  Our critical sections use scoped locks.  And we use smart pointers extensively.</p>
<p>The Despair Engine contains about ten smart pointer types, depending on how broadly you define a smart pointer.  I&#8217;ve had very smart, experienced engineers roll their eyes and say, &#8220;One smart pointer type is too many!&#8221; when I tell them that, but in actual practice they&#8217;ve worked so well for us that I couldn&#8217;t imagine working again on an engine that didn&#8217;t use smart pointers.</p>
<p>There are some things that must be borne in mind when using smart pointers:</p>
<ul>
<li><strong>Smart pointers don&#8217;t remove any of the decisions about object ownership that have to be made in designing an engine.</strong>  You still need to decide what objects are shared, if any, and you need to define a strict ordering of which objects own which other objects.  All that smart pointers do is help document that ordering (you <em>know</em> that the object with a scoped_ptr owns the one without, even if there are pointers going both ways) and help enforce that ownership across the space of possible execution paths.</li>
<li><strong>Smart pointers are not the same as raw pointers.</strong>  They may use pointer syntax, but it&#8217;s impossible to use them efficiently without understanding what they are and understanding when they&#8217;re going to free memory or call AddRef/Release functions.  Smart pointers passed as function parameters should almost always be passed by const reference.</li>
</ul>
<p>Our smart pointer menagerie includes</p>
<ul>
<li>a pointer types for internally-refcounted objects</li>
<li>a pointer type for externally-refcounted objects (rarely used)</li>
<li>scoped pointers (a std::auto_ptr replacement that&#8217;s sane)</li>
<li>scoped arrays</li>
<li>resource pointers that start NULL and are filled in as resources load asynchronously</li>
<li>intrusive weak pointers</li>
<li>and a few other specific pointers for managing internally-refcounted objects in third-party APIs</li>
</ul>
<p>Programmers are encouraged to establish strong references at load time and use them at runtime.  Because we don&#8217;t generally create or pass around smart pointers during a frame, the runtime cost of smart pointers in Despair is minimal.</p>
<p>I credit our use of smart pointers, our rules for ownership, and our use of the RAII idiom for giving us an engine more stable than any I&#8217;ve ever worked on before, even as the number of engineers writing code in it has grown from two to thirty.  A new memory leak shows up about every month or two, and is almost always the result of someone&#8217;s <em>not </em>using smart pointers and then forgetting to call delete in all code paths.  In our engine, if you find yourself having to type out the keyword &#8220;delete&#8221;, then you&#8217;re probably doing something wrong.</p>
<p>Another, less frequent, error that sometimes occurs is for someone to introduce a cyclic reference that causes approximately every object in the game to leak.  In Despair, this happens about once every six months.  This is <em>not</em> a consequence of our use of smart pointers.  Most of the other game engines that I&#8217;ve worked on had manually-refcounted objects, and had similar issues on occasion.  Despair&#8217;s smart-pointer classes do help when we&#8217;re trying to debug this situation, though.  A debug macro enables capturing the callstack on each AddRef and associating each callstack with a particular smart pointer.  We can thus report the callstack of all leaked AddRef calls for each refcounted object.  Like I said, we don&#8217;t need this capability very often, but it&#8217;s nice to have.</p>
]]></content:encoded>
			<wfw:commentRss>http://gamearchitect.net/2008/04/15/an-anatomy-of-despair-object-ownership/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>An Anatomy of Despair:  Introduction</title>
		<link>http://gamearchitect.net/2008/04/15/an-anatomy-of-despair-introduction/</link>
		<comments>http://gamearchitect.net/2008/04/15/an-anatomy-of-despair-introduction/#comments</comments>
		<pubDate>Wed, 16 Apr 2008 05:15:28 +0000</pubDate>
		<dc:creator>Kyle</dc:creator>
				<category><![CDATA[Despair Engine]]></category>
		<category><![CDATA[Game Engine Design]]></category>
		<category><![CDATA[Software Development]]></category>

		<guid isPermaLink="false">http://gamearchitect.net/2008/04/15/an-anatomy-of-despair-introduction/</guid>
		<description><![CDATA[I&#8217;ve been working for a little more than three years on the Despair Engine, the game engine that Day 1 is using in Fracture and another, as-yet-unannounced, title.  In the beginning, there were two of us working on the technology, me and my longtime friend and collaborator Adrian Stone.  Now we&#8217;ve got thirty programmers working [...]]]></description>
			<content:encoded><![CDATA[<p>I&#8217;ve been working for a little more than three years on the Despair Engine, the game engine that Day 1 is using in <a href="http://www.lucasarts.com/games/fracture/">Fracture</a> and another, as-yet-unannounced, title.  In the beginning, there were two of us working on the technology, me and my longtime friend and collaborator Adrian Stone.  Now we&#8217;ve got thirty programmers working in the same codebase.  Fracture&#8217;s getting close to shipping.  This seems like a good time to look back at the principles that shaped our initial architecture and at the decisions whose consequences we&#8217;re living with today.</p>
<p>The name started as a joke.  Adrian and I were out to lunch with our lead one day.  Somebody made a crack about naming the engine &#8220;Despair.&#8221;  One thing led to another, and by the end of the meal we&#8217;d plotted out a whole suite of despair-themed content creation tools, most of which never got made.  It was 2004.  We were starting from scratch on core technology for big-budget AAA games running on consoles that didn&#8217;t even exist yet.  We figured that &#8220;Despair&#8221; would work one way or the other, either as an imperative to our competitors if we succeeded or as a sadly accurate description of our own feelings if we failed.</p>
<p><span id="more-6"></span></p>
<p>There are two broad opposing ideologies when it comes to engine design for games.</p>
<p>Call the first the Low-Level Faction.  This school of design traces its roots to embedded devices and to early consoles like the Dreamcast and the first PlayStation.  This school is characterized by a preference for coding close to the metal, tends to produce games rather than game engines, and eschews abstraction in favor of raw performance.  Many of the games produced by this school of thought are raw C rather than C++, or if they are C++, they tend to minimize use of C++ features like polymorphism, virtual functions and templates.  When Insomniac&#8217;s Mike Action says at GDC that &#8220;Software is not a platform!  Hardware is a platform!&#8221; he&#8217;s voicing this faction&#8217;s frustrations.</p>
<p>Call the other group the Abstraction Faction.  This school of game engine development grew out of PC game development, where audio, graphics and I/O devices are hidden behind a driver layer.  Programming straight to the hardware simply isn&#8217;t an option.  The programmers of this school learned their trade on a platform with virtual memory and highly variable capabilities, so they learned to use levels of indirection to abstract away platform differences.  When the Epic guys say they&#8217;d sacrifice 10% of their runtime performance for a 50% improvement in content creation time, they&#8217;re justifying their higher level of abstraction.</p>
<p>Both ideologies of engine development have produced great games.  Halo, for example, is a straight-C game of the Low-Level Faction.  Gears of War is an example of a game with a lot of abstraction that uses lots of script and the advanced features of C++.</p>
<p>The lesson that I&#8217;ve learned in a decade of software development is that the specific decisions you make are less important than that decisions are made at all.  Software requires structure.  Every decision has tradeoffs, but once made, even seemingly-arbitrary decisions have to be enforced, or entropy will consume your codebase with a vengeance.  Every-man-for-himself design will get you a million lines of code, any one of which may reference any other, and any one of which may have undefined side effects.</p>
<p>The Despair Engine is an unapologetic representative of the Abstraction Faction of game engine design.  This is not because I think that&#8217;s the only way to create games.  It&#8217;s because that&#8217;s the way that <em>I</em> know how to create games.  We use the advanced features of C++ very aggressively.  If our history of uncovering compiler errors is any indication, the Despair Engine is unique among game engines in the degree to which it pushes the infrequently-explored edges of the language.  We use STL containers and algorithms.  We use the <a href="http://www.boost.org/">Boost</a> library of C++ template extensions.  We use template metaprogramming to create our own embedded domain-specific reflection language.  And we use abstraction and polymorphism throughout our code.</p>
<p>Over the coming weeks, I&#8217;d like to discuss some of the Despair&#8217;s more unusual idioms and axioms.  For each, I&#8217;ll describe the problem that our approach was intended to solve, and I&#8217;ll talk about the continuing challenges of the solution that we implemented.</p>
]]></content:encoded>
			<wfw:commentRss>http://gamearchitect.net/2008/04/15/an-anatomy-of-despair-introduction/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>GDC 2008</title>
		<link>http://gamearchitect.net/2008/03/12/gdc-2008/</link>
		<comments>http://gamearchitect.net/2008/03/12/gdc-2008/#comments</comments>
		<pubDate>Wed, 12 Mar 2008 15:51:04 +0000</pubDate>
		<dc:creator>Kyle</dc:creator>
				<category><![CDATA[GDC]]></category>

		<guid isPermaLink="false">http://gamearchitect.net/?p=5</guid>
		<description><![CDATA[This year was the tenth anniversary of my first GDC.  It&#8217;s milestones like this that make one pause and take stock of one&#8217;s life.  Over the last decade, one of my college classmates was appointed United States Attorney for South Carolina; another lost a limb fighting in Iraq; another married actor Steve Martin (yes, that Steve [...]]]></description>
			<content:encoded><![CDATA[<p>This year was the tenth anniversary of my first GDC.  It&#8217;s milestones like this that make one pause and take stock of one&#8217;s life.  Over the last decade, one of my college classmates was appointed United States Attorney for South Carolina; another lost a limb fighting in Iraq; another married actor Steve Martin (yes, <em>that </em>Steve Martin).  And I&#8230; I have spent most of my waking hours contributing, in my own small way, to the <a href="http://www.dallasnews.com/sharedcontent/dws/dn/opinion/points/stories/DN-hymowitz_27edi.ART0.State.Edition1.378ca5b.html">perpetual adolescence of the American male</a>.</p>
<p>Like a career in game development, GDC is a mix of small rewards and great frustrations&#8211;and yet the two somehow balance each other out.  Back in 1998, the attendees were a small brash crowd, excited that gaming had finally arrived and enthusiastic about the future.  I think that was the first time somebody announced the oft-repeated canard about how we&#8217;re bigger than the movie industry.  My friends and I all made the crawl from room to room on Suite Night, availing ourselves of the free drinks and the catered food from the warming trays.  There was a party on the Queen Mary.  I got a thick pile of t-shirts and an Intel graphics card, and thought, <em>3dfx better watch out now that Intel&#8217;s getting into the market</em>.</p>
<p>Now GDC has become like SIGGRAPH.  The crowds are enormous&#8211;nearly 15,000 in attendance this year, I&#8217;m told.  But it&#8217;s not the size of the crowds that makes it less intimate.  It&#8217;s the fact that so many of the people there don&#8217;t really have much to say to each other:  there are indie game developers, console game developers, serious game developers, mobile phone game developers, people selling middleware and hardware and outsourcing to all of the above, recruiters, wannabes, publishers trying to sign developers, developers looking for a publisher, HR folks looking to hire artists and programmers and musicians, and press trying to cover the whole spectacle.  The death of E3 meant that this year there were more sessions than ever that could be summed up as, &#8221;look at my game and how awesome it is.&#8221;  I tried to avoid those.  I spent my three days at GDC looking for quiet places to talk to the people who do the same thing I do.  I didn&#8217;t go to any of the parties.<span id="more-5"></span></p>
<p>GDC hasn&#8217;t managed to scale to handle its growth.  Internet connectivity was poor throughout the convention center&#8211;even worse than <a href="http://www.gamearchitect.net/Articles/GDC2007.html">last year</a>.  The food is as identically terrible as ever.  And this year, for the first time, proceedings didn&#8217;t become available at all until <em>after</em> the conference, and <a href="https://www.cmpevents.com/GD08/a.asp?option=C&amp;V=1&amp;SB=4&amp;Pv=2">those</a> in the form of a slim handful of PowerPoint decks.  The clever people have taken to bringing cameras to the talks and snapping pictures of each slide that goes up, which is distracting but understandable.  The state of the GDC proceedings is an embarrassment to the industry, but it&#8217;s one that I don&#8217;t expect to change unless CMP stops handing out Gigapasses to speakers who show up without their slides.</p>
<p>My main interest this year was learning how other developers are dealing with problems of scale.  The team I&#8217;m working on at Day 1 has gone from three people to eighty people in the last three years.  Our engine just passed a million lines of code.  We&#8217;ve had to turn our resource installers into multi-volume installers because they crossed the two-gig threshold that&#8217;s the largest file size <a href="http://www.jrsoftware.org/isinfo.php">Inno Setup</a> supports.  I think that we&#8217;re dealing with our scale better than GDC is, but it&#8217;s always good to gather additional perspectives.  I&#8217;ll talk more about the things that we&#8217;re doing and what we can learn from the presenters at GDC as I go.</p>
<p><strong>Running Halo 3 Without a Hard Drive</strong></p>
<p>Part of the problem of scale in next-generation console development is that console memory is getting larger and content sizes are growing to match, but DVDs and memory aren&#8217;t getting a whole lot faster.  That means that we developers have to work harder and harder to keep players fed with fresh content.</p>
<p>Mat Noguchi&#8217;s talk on streaming content in Halo 3 was interesting mostly because it showed how Bungie approached the problem of streaming from the opposite end from what we&#8217;ve done at Day 1, but we seem to be ending up in similar places.  They took existing level technology and shoehorned streaming into BSP regions.  We built levels up out of smaller streamable primitives.  Bungie has always emphasized separation of file I/O (deciding what gets loaded) and resource management (managing data once it&#8217;s been loaded), and they do lots of off-line computation to determine what resources actually need to be loaded for each level.  We allow any asynchronous resource load to trigger other asynchronous resources loads, and don&#8217;t return requested resources to the main game thread until the entire requested resource tree is complete.  In short, their system was designed for the most efficient player experience and ours was designed to be as flexible as possible while we&#8217;re iterating on content creation.</p>
<p>In the end, though, we&#8217;re doing similar optimizations to get to where we need to be to ship.  We&#8217;re sorting resources in the order they&#8217;ll be read to minimize DVD seeks, we&#8217;re grouping resources that have similar level ownership, and we&#8217;re compressing groups that will all be read together.  Like Bungie, we&#8217;re having problems with audio resources interacting badly with everything else that needs to be streamed&#8211;they solved that problem by just not playing any streamed AI voices if the player doesn&#8217;t have a hard drive to cache to.</p>
<p>Bungie seemed to give half the talks at GDC this year, and they were even kind enough to make their <a href="http://www.bungie.net/Inside/publications.aspx">slides</a> available&#8211;though not on the GDC Proceedings site.</p>
<p><strong>Automating Regression Discovery: Finding the Wrenches in the GEARS OF WAR</strong></p>
<p>I&#8217;m the senior engineer at Day 1 most interested in build infrastructure and automated testing, so I always like to hear what other teams are doing in that department.  Epic&#8217;s test and metrics infrastructure isn&#8217;t quite up to <a href="http://www.wired.com/gaming/virtualworlds/magazine/15-09/ff_halo">Microsoft standards</a>, but they do as well as any independent developer I&#8217;ve heard of.  They use <a href="http://cruisecontrol.sourceforge.net/">CruiseControl</a> as a continuous integration framework, building all configurations of the Unreal Engine across ten dedicated build machines every time a developer checks in.  They also do continuous integration for content, building fresh cooked resources every time an artist or designer checks in.</p>
<p>The resource build process collects performance and automated test data for each level.  Any crashes get logged to a database.  Mesh and texture size information gets dumped to spreadsheets covering the resource usage of each level.  The system collects performance data from fly-through camera paths, bot matches, human playthroughs, and render sample points scattered around each level.  Their performance gathering for UT3 definitely benefited from the fact that it was a bot-based multiplayer game, but their performance gathering across the board sounds second-to-none.</p>
<p>One of the gems I took away from this talk was the oh-yeah-that&#8217;s-obvious point that collecting performance data about average framerate really isn&#8217;t very useful.  On the consoles, we&#8217;re always V-synced at 60, 30, 20, 15, 10 or 5 Hz anyway&#8211;usually 30 or 20.  A more useful statistic to collect is the percent of frames, during a playthrough of any level, that are below 30 Hz.  It&#8217;s also useful to collect the percent below 5 or 10 Hz to catch dramatic stalls.  If you have more than a couple of percent below 30 Hz, and if you have <em>any</em> frames below 10 Hz, then something needs to be done to improve performance.</p>
<p><strong>Sharing Code Roundtable</strong></p>
<p>I attended the sharing code roundtable partly because we&#8217;re sharing the same engine across two projects at Day 1, and partly because I interviewed with the moderator, <a href="http://www.blueandorange.org/blue/">Brian Sharp</a>, at Ion Storm, and I think he&#8217;s a smart guy and I was interested in what he had to say.  In the end, though, I found the session frustrating because no two people in the room even had problems similar enough to be able to have a &#8220;this worked for me, what worked for you?&#8221; conversation.  We mostly ended up talking past each other.  A few of the forty-or-so attendees:</p>
<ul>
<li>Me:  Working on one big-budget console game, sharing an engine with another game being developed in another Perforce branch, and integrating back and forth every week.</li>
<li>Brian Sharp:  Organizing an effort to share code across all Midway studios&#8230; his challenge was trying to improve communication between different studios.</li>
<li>A guy from EA Canada:  EAC is like a middleware provider to the other EA studios, and as a dedicated middleware provider, he wanted to know how, after giving another studio a drop of some technology, EAC could merge back fixes and new features with a minimum of pain.</li>
<li>A guy from academia:  He was working on a distributed development project with undergraduate students in different countries, and wanted to know what the rest of us thought of distributed source control systems like <a href="http://www.selenic.com/mercurial/wiki/">Mercurial</a> and <a href="http://git.or.cz/">Git</a>.  I&#8217;m pretty sure most of us had never heard of them.</li>
</ul>
<p>I think Brian did a good job moderating, but it just seemed like the wrong group of forty people to have a conversation.  Or maybe it was just the wrong conversation for forty people to have.</p>
<p>I did have one startled and happy moment when the conversation tangentially touched on automated testing.  I had a similar moment in the Gears of War infrastructure talk when Martin Sweitzer talked about Epic&#8217;s use of <a href="http://www.gimpel.com/">PC-Lint</a>.  They said:  <em>We have all this existing legacy code</em> <em>and it doesn&#8217;t have unit tests and Lint generates a million warnings for it.  How can we test the new code we write without having to touch the ugly legacy stuff that we know works and that we&#8217;re afraid to change?</em>  Day 1&#8217;s in-house Despair Engine is three years old, and it was written with automated unit tests running for every library and a nightly Linting of the entire engine from the very beginning.  We pass all our tests.  We don&#8217;t generate any Lint warnings&#8211;at least not the ones we care about.  Modern console development is really, really hard.  It&#8217;s nice, sometimes, to hear about the problems you <em>don&#8217;t</em> have.</p>
<p><strong>Ray Kurzweil</strong></p>
<p>I missed the Microsoft keynote on Wednesday for a meeting, but I was happy to be able to make Ray Kurzweil&#8217;s keynote on Thursday.  Kurzweil&#8217;s an inventor and futurist, and the author of <a href="http://www.amazon.com/Age-Spiritual-Machines-Computers-Intelligence/dp/0140282025/ref=pd_bbs_sr_2?ie=UTF8&amp;s=books&amp;qid=1205209592&amp;sr=8-2">The Age of Spiritual Machines</a> and <a href="http://www.amazon.com/Singularity-Near-Humans-Transcend-Biology/dp/0143037889/ref=pd_bbs_sr_1?ie=UTF8&amp;s=books&amp;qid=1205209592&amp;sr=8-1">The Singularity is Near:  When Humans Transcend Biology</a>.  He&#8217;s what we used to call an <a href="http://en.wikipedia.org/wiki/Extropian">extropian</a> back while I was in college.  His talk covered much of the same material that he covered in <em>The Age of Spiritual Machines </em>(and presumably <em>The Singularity is Near</em>, though I haven&#8217;t read that one):  innovation and intelligence are increasing at an exponential pace, and in the near-future we&#8217;re going to cross a super-evolutionary threshold so sudden and so steep that we have no ability to predict the future of humanity beyond it.</p>
<p>All of this has a shrill ring of millenarianism to it that is easily dismissed as the <a href="http://en.wikipedia.org/wiki/Technological_singularity#Criticism">&#8220;rapture of the nerds&#8221;</a>, but I&#8217;ve always been willing to forgive the extropians their evident <a href="http://www.kurzweilai.net/meme/frame.html?main=/articles/art0093.html?m%3D9">wackiness</a> because they&#8217;re probably right:  human science has advanced more in the last hundred years than in the thousand before that, and while Kurzweil sounds a little optimistic to me&#8211;I don&#8217;t expect to ascend to nerdvanna in the next twenty years&#8211;it&#8217;s hard for me to believe that in a hundred years people will still be dying of old age because we still haven&#8217;t figured out how the genes for aging work.</p>
<p>So here&#8217;s the techno-optimism:  In the last 40 years, Kurzweil says, computing power has increased a billion times and computer size has decreased 100,000 times.  The same will happen again over the next 25 years to produce injectable computers the size of blood cells that can enter your brain and feed your senses a full 3D virtual reality.</p>
<p>Or those injectable computers can rewire your body chemistry.  The software running our bodies is obsolete, evolved for a hunter-gatherer lifestyle tens of thousands of years ago.  Your body stores fat because our genes evolved in a time of scarcity.  But now we live in a time of abundance.  RNA interference is on the verge of being able to turn off genes for storing fat.  Current diet drugs work by suppressing appetite, which, Kurzweil notes, &#8220;is like birth control that works by inhibiting interest in sex.&#8221;</p>
<p>Our ability to predict the future also evolved in a different time, when exponential progress was so slow that it was indistinguishable from linear progress because the exponential curve was so flat.  Now people make stupid predictions that Social Security will go bankrupt and that greenhouse gasses will melt the ice caps even though technologies are coming that will soon render all those assumptions obsolete.  Within five years, Kurzweil says, nano-engineered solar panels will be more cost-effective than fossil fuels.  Within twenty years, we&#8217;ll have largely replaced fossil fuels as a means of power production.</p>
<p>And so on.  Slides <a href="https://www.cmpevents.com/sessions/GD/S7036i1.ppt">here</a>.  If you&#8217;re skeptical about his claim that by 2010 desktop computers will disappear and wearable ubiquitous computing devices will project high-definition augmented-reality images directly into our retinas, so am I.  But I want to believe.  Kurzweil has a way of making you feel like we&#8217;re living in the future right now.</p>
<p><strong>Life on the Bungie Farm</strong></p>
<p>For Halo 3, Bungie had a build farm of 180 computers with 300 processors.  These ran in-house client/server software written in C# that communicated through atomic transactions in a SQL database to manage</p>
<ul>
<li>code builds and automated tests</li>
<li>lightmap rendering</li>
<li>content builds</li>
<li>other tasks (cubemap rendering, shader compilation, builds of <a href="http://www.bungie.net/">bungie.net</a>, and maintenance)</li>
</ul>
<p>It&#8217;s a neat set-up.  I wish that we had a half-million dollars to spend on build hardware, but honestly I&#8217;m not sure what we&#8217;d do with that many computers.  The majority of Bungie&#8217;s workload was lightmap rendering.  I&#8217;ve read elsewhere that they were cooking spherical harmonic coefficients for reflection functions into their lightmaps, similar to Half Life 2&#8217;s orthogonal lightmap basis, which I suppose helps explain why their lightmaps were so much more expensive than, say lightmap generation in Quake I.</p>
<p>But Day 1&#8217;s games are all about environmental destruction, which means that we really can&#8217;t get away with static lighting.  All lighting in both our current games is dynamic.  I wouldn&#8217;t mind having, say, twenty build machines to throw at code and resource builds, but I think that would take care of our needs just fine.</p>
<p>That said, there are definitely some features of Bungie&#8217;s set-up that make me envious.  A C# client/server model communicating through SQL would be a step up from our PHP build scripts communicating through text files.  And Bungie uploads all symbols from their automated builds to a symbol server, as we do, but they also copy all source to a fixed location on the network and link the executable to the location of the source with which it was built using the undocumented-and-not-mentioned-anywhere-else /SOURCEMAP linker option.  We&#8217;ll probably make those changes to our build system in the next few months.</p>
<p><strong>Internal &amp; Outsourcer Management of Tools &amp; Pipelines</strong></p>
<p>I&#8217;m not really interested in the process of outsourcing, which is more of an art and production function, but I&#8217;m very interested in how tools get built and distributed to the people who use them.  Day 1 has about 140 developers working on two different games now.  We build Inno Setup installers for all our tools every night as part of our automated build, they get tested by our QA department every morning, and if there aren&#8217;t any showstopper bugs then we update the latest release version in a SQL database.  A little system-tray app that we run turns yellow on everyone&#8217;s desktop and prompts them to right-click and select &#8220;Update&#8221; to install latest.</p>
<p>Volition has even larger teams than we do:  100 internal developers and 20 outsourcers on Saints Row; 101 internal developers and 44 outsourcers on Saints Row 2; and 80 internal developers and 52 outsourcers on Red Faction.  Like us, they&#8217;ve invested in some automatic distribution infrastructure.  They have an app called vInstaller that runs MSBuild scripts to do tool installs.  I think that I prefer having a proper installer, since it means that our tools can be uninstalled through the Add/Remove Programs option in the Windows Control Panel.  Volition devs have to uninstall through vInstaller, which apparently makes Windows Vista unhappy.  Their IT guys apparently had to disable User Account Control on all their Vista machines.</p>
<p>They did say that on one occasion they&#8217;d had the misfortune of auto-deploying a virus to all developers.  We&#8217;ve been lucky enough to avoid that one so far.</p>
<p>They integrated an art outsourcing company in Shanghai into their existing tool distribution framework, which created new challenges.  The outsourcers didn&#8217;t use Perforce.  Users weren&#8217;t admins on their own machines.  And they tended to install tools into many different locations, which broke non-robust tools.</p>
<p>We generate a slightly trimmed-down installer for outsourcers of just the tools that they need to preview assets in our engine.  Here again, I think that we benefit from having a traditional Windows installer instead of a standalone installation app.  I&#8217;m don&#8217;t think a user even needs to be an admin to run the installer and I&#8217;m pretty confident that our tools will work whatever path you install them to.  We usually install to C:\Program Files, and we don&#8217;t expect to access any other tools or data through relative paths.</p>
<p>Slides for Volition&#8217;s talk <a href="http://www.volition-inc.com/gdc/">here</a>.</p>
<p><strong>Unreal Tournament 3 Postmortem</strong></p>
<p>I went to the UT3 postmortem with some hesitation, because Epic has a bit of a rep for turning every talk into a sales pitch for the Unreal Engine.  In the event, I was very pleasantly surprised by the candor with which Jeff Morris and Mike Capps talked about UT3&#8217;s successes and shortcomings.</p>
<p>The talk followed the now-traditional What Went Right/What Went Wrong format of every post-mortem in Game Developer magazine, but like most developers, Jeff and Mike seemed to find more passion in talking about what went wrong than what went right:</p>
<ul>
<li>They wasted a lot of effort on a character customization system that had no effect on actual gameplay.  With characters moving at 30 MPH in front of often-animated backgrounds, you couldn&#8217;t tell <em>what</em> they looked like.</li>
<li>The single-player campaign gameplay came together too late to be polished or balanced.  &#8220;Head and shoulders above any UT game we had made in the past, but it wasn&#8217;t Bioshock,&#8221; Mike said.  Of course, Bioshock <em>is</em> an Unreal Engine game.</li>
<li>The game didn&#8217;t have enough polish time overall, and releases were scheduled badly.  They diluted their marketing efforts by releasing at different times on different platforms and in different regions.  And they walked into the most competitive season ever for first-person shooters, going up against Bioshock, Call of Duty 4 and Halo 3.  &#8220;We&#8217;re very big in Russia,&#8221; Mike observed sardonically.</li>
</ul>
<p><strong>The Best Talk I Missed</strong></p>
<p>I like to listen to GDC Audio proceedings while I take long road trips, and Ubisoft Creative Director Clint Hocking showed up on my radar when I heard his excellent talk on Narrative in the Splinter Cell Trilogy and his robust showing at the Game Design Challenge at GDC 2005.  I&#8217;d already noticed as I played the Splinter Cell games that all the ones that came out of Ubisoft Montreal were fantastic, and the ones that came out of Ubisoft Shanghai were&#8230; not so much.  After hearing Clint&#8217;s GDC 2005 talks, I suspected that he might be one of the big reasons for that.</p>
<p>Unfortunately, I had conflicts that kept me from being able to make it to Clint&#8217;s talk at GDC 2008, I-fi:  Immersive Fidelity in Game Design, but he&#8217;s been generous enough to make his slides and an <em>actual paper</em> available on <a href="http://clicknothing.typepad.com/click_nothing/2008/02/gdc-2008---part.html">his blog</a>.  He discusses player immersion in terms both critical and creative.  I&#8217;m a proponent of more scientific game design:  I believe that designers should form credible hypotheses regarding what is and isn&#8217;t fun and create experiments that test those hypotheses.  I think that application of the scientific method is the only way to consistently create more involving games.  I&#8217;m not sure that I-fi is even quite a hypothesis yet, but it&#8217;s close, and it suggests avenues of advance that can only make the games we create more compelling.</p>
<p><strong>Looking Ahead</strong></p>
<p>All in all, there was some really good material at GDC this year.  I felt like the overall tone of presentation was somewhat muted, though.  Game developers are a typically cocky bunch, but scaling up to handle hundred-man teams and multi-core development has been a challenge, and I think it&#8217;s left a lot of us feeling less like we know The Way to solve these issues.  Everybody&#8217;s trying, and the companies that are still standing are clearly doing better than the many companies that aren&#8217;t, but even the survivors are a little shell-shocked.</p>
<p>And we have two years until the next console generation comes along and shakes everything up again, multiplying memory and core counts by a factor of eight and team sizes by a factor of two.  &#8220;If you&#8217;re planning a project today that&#8217;s going to take more than six months,&#8221; Ray Kurzweil said, &#8220;then the pace of change is so great that you really need to take exponential growth into account.&#8221;  Our industry has been living with that reality for a while.</p>
]]></content:encoded>
			<wfw:commentRss>http://gamearchitect.net/2008/03/12/gdc-2008/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>WordPress</title>
		<link>http://gamearchitect.net/2008/03/09/wordpress/</link>
		<comments>http://gamearchitect.net/2008/03/09/wordpress/#comments</comments>
		<pubDate>Mon, 10 Mar 2008 01:26:35 +0000</pubDate>
		<dc:creator>Kyle</dc:creator>
				<category><![CDATA[Admin]]></category>

		<guid isPermaLink="false">http://gamearchitect.net/?p=3</guid>
		<description><![CDATA[When I started GameArchitect, the word blog didn&#8217;t exist yet, and there was, therefore, a real shortage of decent blogging software.  I ended up buying Joel Spolsky&#8217;s CityDesk, mostly because it was what he used for Joel on Software and I like the look of his site.
CityDesk hasn&#8217;t had a lot of work over the [...]]]></description>
			<content:encoded><![CDATA[<p>When I started GameArchitect, the word blog didn&#8217;t exist yet, and there was, therefore, a real shortage of decent blogging software.  I ended up buying Joel Spolsky&#8217;s <a href="http://www.fogcreek.com/CityDesk/">CityDesk</a>, mostly because it was what he used for <a href="http://www.joelonsoftware.com/">Joel on Software</a> and I like the look of his site.</p>
<p>CityDesk hasn&#8217;t had a lot of work over the last couple of years, though, and I never have managed to figure out how to make it generate a proper RSS feed.  So I&#8217;m switching the site over to <a href="http://wordpress.com/">WordPress</a>, about which I&#8217;ve heard good things.  All old content is still available at <a href="http://www.gamearchitect.net/citydesk.html">http://www.gamearchitect.net/citydesk.html</a>.  Pardon the dust and plaster.</p>
]]></content:encoded>
			<wfw:commentRss>http://gamearchitect.net/2008/03/09/wordpress/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
	</channel>
</rss>
