Posts by Justin Liew
  1. Optimizing Workflow ( Counting comments... )
  2. Visualizing Bugs ( Counting comments... )
  3. C++0x - Viable? ( Counting comments... )
  4. Team Building (Mini Game Week) ( Counting comments... )
  5. Debugging Tools ( Counting comments... )
  6. Lessons from a Failed Project ( Counting comments... )

There is a certain frame of mind programmers step into when doing any sort of optimization.  I've found this way of thinking about optimization has come in useful for me when improving my daily workflow.

When we optimize code, we go through a process similar to this:

  1. Establish a reproducible set of steps.
  2. Profile this to get baseline numbers for the metric we wish to improve.
  3. From that baseline profile, identify hotspots.
  4. Fix said bottlenecks.
  5. Re-profile to see deltas.
  6. Iterate as necessary.

Obviously this is greatly simplified, but the important points are to have something to compare against, and constant iteration and comparison against that baseline to determine the effects of your changes.  I have taken this approach to my daily workflow, and have found it has helped my productivity.


Here is a rough outline of a typical day-to-day workflow:

"Get Latest" workflow

  • Sync to head in Perforce.
  • Compile code.
  • Build data.
  • Deploy build to target platforms.

"Work Loop" workflow

  • Run game.  Execute steps 1, 2,...,n to get to a location in game.
  • Check bug or feature.
  • Debug.
  • Close the game.
  • Iterate on code.

"Verify and Check In" workflow

  • Run game.  Execute steps 1, 2,...,n to get to a location in game.
  • Verify feature works correctly or bug is fixed.
  • Repeat for multiple platforms depending on how likely changes are to affect other platforms.  Ideally test on a different platform than the primary platform I used to fix the bug or implement the feature.
  • Run memory leak test.
  • If necessary, check performance/load times/memory usage tools to determine impact.
  • Shelve and buddy changelist on another machine to ensure there are no missed files or dependencies on other changelists.

"Main" workflow

  • "Get Latest".
  • Go for Coffee.
  • Look at task list and highlight top priority items to work on.
  • While bug is not fixed or feature not complete, run "Work Loop" on that task.
  • "Get Latest"
  • "Verify and Check In"


Main Workflow

At a first glance, it is pretty obvious that most of my time is spent iterating on the "Work Loop".  So it makes sense to start there.  As I run the game and debug, I note things that I'm doing over and over that are inefficient or easily automated.  Such a list might include:

  • Navigating the UI.
  • Connecting multiple machines to test online features.
  • Walking to a location in the world.
  • Spawning various items.

Once I've identified these, it's easy enough to create debug functionality that'll make them easier.  I point out a few in a previous post.  In this case, debug options to skip the UI, auto-load a level or save file, auto-connect to a specific host machine, or debug spawning of items are easy to do and can greatly cut down on common rote tasks.  Documenting these and letting the team know about them is a good way to help others improve their efficiency as well.  It's also contagious - as that culture of stepping outside the bounds of the tasks at hand to help out the greater good becomes more prevalent, more people are hopefully likely to jump in.



The next thing to look at is the code IDE.  We use Visual Studio 2010 at work, which is a source of much frustration amongst the team due to poor performance.  For me, the proper solution would be to switch IDEs (some people here use VIM or EMACS, and I've seen Sublime mentioned as well)  The main downside is we still need to compile/debug with Visual Studio, so there's only so much we can do.  VsVim, for example, might be a good compromise for those who have the muscle memory but still want easy access to the debugger.

For Visual Studio, there are billions of hotkey combos that can help cut down on needless mouse clicking, as well as various hidden pieces of functionality.  When those fail, plugins will often solve your problem.  Here are some quick examples of things I use:

  • Ctrl-Comma for the "Navigate To" dialog, which makes it easy to find symbols, files, and more.  Downside is it's sometimes really, really slow.  If you don't have Visual Assist it replaces VA's more efficient File Open dialog.
  • Pin to Source is great for commonly inspected data.  Also keeps a basic history so if you accidentally stop debugging you can still see the last value.
  • Source Control integration is a sticky issue.  I've heard Nifty Perforce (written by our very own @jtilander!) is great.  I use macros bound to keyboard shortcuts that hit p4 edit, p4 history, etc.

For plugins:

  • Visual Assist is of course the de facto plugin.  But it's expensive and even more so now.  If you don't have access, there are some free plugins that can help bring some of that power back.
  • Highlighterr gives VA-like code colouring.
  • Productivity Power Tools has the MetaScroll/RockScroll scroll bar for 2010, and other small useful things.



Of course, not everything happens in the IDE or game.  Scripts need to be run, files need to be copied or edited, and external tools need to be used.  Rather than using Windows Explorer and navigating through folders to find things, why not use the computer to do what it does best - organizing the data it knows about!  There are 2 tools I use that are indispensable for this: Launchy and Everything.

Launchy lets you bring up a text window and as you start typing in commands it'll try to find programs to launch that match your keyword.  To make this even more efficient, I point Launchy to a single shortcuts folder, and every time I find myself doing a task more than once, I create a shortcut for it, drop it in that folder, and I can run it instantly.  The main advantages of this are twofold: Launchy is faster if it only needs to catalogue one folder, and I can then customize the script names to encompass parameters, so I can give them names that are optimized for what I'd want to type to launch them.  Instead of "build data win32 game-name", I can run the "win32buildgame" and by the time I type "win32b" it'll auto-fill it in.

Everything is a better "Find in Windows" that has powerful wild cards and regex support.  It catalogs as you work, so finding is instant.

One way I monitor my time is by using Rescue Time, which logs computer activity.  It lets you set whether a process is "productive" or "distracting" and will give you graphs and history for your daily work.  This gives me a high level overview of where I spend my time.   A Smoky Kitchen was a post that inspired this.

Get Latest and Checking In

I've left this to the end, because while a lot of us focus on having a single batch file to try to sync, compile, build and deploy, this typically only happens a small number of times a day.  Our compile times are not excessive and we don't build data unless we're changing it, so I haven't been too motivated to work on this as much.  At a previous job, however, our data builds were in the order of 10's of minutes, so one forward-thinking SE wrote an Outlook filter that would act on an email sent from his home account and kick off a sync-compile-build script.  Then, by automating the email from a web page, he could create an icon on his iPhone that would kick off his build, and do that when he left the house.  Simple to do, but was a godsend.


Hopefully I've conveyed the thought process by which I've selected tools to use and functionality to devote my time to, and how that thought process isn't one that is new to most of us.  And as a bonus, perhaps some readers will find a new tool that will help them out!