Javascript Singleton Pattern

Here’s a pattern for a javascript singleton that I’ve been using for a while.

window.singletonName = window.singletonName || new (function(argument) {
	console.log("argument: " + argument);
	this.pub = "foo"; // window.singletonName.pub will be "foo" 
	var priv = "bar"; // window.singletonName.priv will be undefined
})("test argument");

No matter how many times you run this code, window.singletonName will still refer to the function you created the first time you ran it.

Rolling my own very simple, MVC patterned Javascript Canvas game without an MVC framework

Recently we (at Primal) were asked to create a game that had to run on iOS and Android, in the browser. We picked the new CreateJS framework by Grant Skinner and Adobe, which is designed to make javascript and canvas work more like Actionscript and Flash. The docs are a little light on examples, but apart from that, I’m extremely happy with the performance and features of CreateJS.

Anyway, this isn’t about CreateJS, this is about MVC in Javascript, without an MVC framework. Here’s a very stripped down version of how it worked. I’m not saying this is the right way to do it, or the best way to do it, but it worked really well for me.

Note that in Javascript, there are no classes, so we fake them with functions. It works pretty much the same way, and you don’t have to learn any standardized constructor/destructor stuff.

The HTML:
In the case of a javascript game, the HTML really only serves to load the JS files, and kick things off when everything is loaded.

<html>
<head>
	
	
	
	
	
	
		
</head>

	
	

</html>

The Controller:
I had just one controller that represented the game’s main logic tree.

function GameController() {
	var self = this;
	this.toString = function() { return "GameController"; }

	this.gameModel;

	this.uiView;
	this.avatarView;
	this.hudView;
	this.scoreView;
	this.etcView;

	this.create = function() {
		self.gameModel = new GameModel();
		
		self.uiView = new UiView();
		self.uiView.create();
		
		self.avatarView = new AvatarView();
		self.avatarView.create();
		
		self.hudView = new HudView();
		self.hudView.create();
		
		// and so on
		
		self.initGame();
	}

	this.initGame = function() {
		// now that we've created all the view elements,
		// and the model, get the game started
	}
}

The Model:
Note that this isn’t a singleton. I had just one controller, so I didn’t run the risk of duplicating the Model, but if I did, I would have made this a singleton.

function GameModel() {
	var self = this;
	this.toString = function() { return "GameModel"; }

	this.something;

	this.getSomething = function() {
		return self.something;
	}
	this.setSomething = function(data) {
		self.something = data;
	}

}

The Views:
Views come and go, so they need to be created and destroyed. In the destroy, make sure you clean up everything.

function UiView() {
	var self = this;
	this.toString = function() { return "UiView"; }

	this.someUiElement;
	this.anotherUiElement;

	this.create = function() {
		// load and display bitmaps, or whatever
		// fetch the URL for a bitmap from the model like this:
		game.gameModel.getSomething();
	}
	this.destroy = function(data) {
		// unload all assets and unset all variables.
	}
}

And that’s about it. Every view and model is a variable in the main GameController, which itself is a global variable (I called it game), so you can find anything through that game variable.

Also note these lines that appear at the top of every class.

var self = this;
this.toString = function() { return "NameOfClass"; }

Defining a var called self as this lets you refer to self anywhere in that class, and not worry about scope. For example, if you used a setTimeout to delay something, this would be redefined to the setTimeout handler function, but self would still refer to the class.
Redefining toString to return the name of the class is optional, but it makes your console clearer if you want to console.log where something is coming from.

Dos and Don’ts of Animating for iPad 1 using CSS or JS/TweenMax

I’m working on a project at Primal right now for a big TV network you’ve heard of who is making an iPad app. They’re bringing the content, and another company is writing the app, but they’ve brought us in to make some funny interstitials/easter eggs. The minimum specs are these:

- iOS 5 (thankyou!)
- iPad 1 (ouch)
- Loaded in a UIWebView, i.e. HTML5, CSS3, JS: Mobile Webkit’s capabilities.
- 100kb limit on prepackaged assets, but we can load more as needed.

So I’m learning what is tough on the hardware (kills the framerate) and what it likes, and I thought I’d share.

Dos:
- Use this trick I’ve mentioned before
- Use 3D transforms, and other webkit native stuff
- Failing that, use absolute positioning of elements, i.e. top and left, not margins

Don’ts:
- Animate background-position. Not sure why, but a box-in-a-box, where the inner box has the background and it moves within the outer box, is more efficient
- Animate padding, margins, or the dimensions of inline elements. These cause the page renderer to worry about whether it needs to rewrap lines, and push other objects around.
- Use huge images. iPad 1 has a 4mb texture buffer, which comes out to 5 1024×768 images. You can use up to 2048×2048, but of course that’s 4 1024s in itself, so just one.
- Use transition-delay to offset one animation from another, if they need to stay in sync. The delayed one will try to start on time, but sometimes it loses sync. Instead, start the animations at the same time, and just have the animation that would be delayed do nothing for a while.

It was a tight competition between TweenMax and CSS animation. In the end, CSS had a very slight edge in performance, but writing it all was a huge pain. Keyframes assigned by percent? Thanks W3C. I’d suggest TweenMax to anyone but the biggest CSS geeks, or those wanting every last ounce of performance.

I’ll keep adding to this list as I find more.

Sublime Text Font Smoothing (anti-aliasing) issues in Mountain Lion

I just upgraded to Mountain Lion, and to my astonishment, everything seemed to work just as it did before. Maybe even a little faster. That’s pretty rare for OS X point upgrades. Anyway, after looking around for a while, I finally came across a difference. Sublime Text 2 is over “smoothing” the text. And being a code editor, that’s a very bad thing. Eye-strain and all that.

Wrong:

Right:

You can see how fat the type looks. Very hard to read. A bit of googling tells me that it’s something to do with OS X identifying my non-Apple monitors, and possibly thinking they are CRTs, and using the old CRT font smoothing levels. Going into the System Pref/General leaves me wondering why Apple actually removed some of the smoothing options, and playing with whats there seems to do nothing. Instead, we have to do some terminal magic. Just open up a terminal window and enter this:

defaults -currentHost write -globalDomain AppleFontSmoothing -int 0

… then restart Sublime Text. Note that the number at the end denotes which level of smoothing we want, 0 being the least, 3 being the most.

iTunes playlists out of order when synced to iPhone/iPod/iPad

I have a playlist called 5 Star. It’s a smart playlist, and it is set to include all songs with 5 stars. At my desk, I just turn on the Date Added column and sort by that, so the top of the playlist is the most recent song I bought and gave 5 stars. This works great on the desktop.

On my iPhone (and iPad) though it doesn’t work the same way. I get the playlist on the device, but it’s in whatever order iTunes puts it in naturally, as if I’m in iTunes and it’s sorted by the first column, with the numbers. This sucks. Here’s the fix.

Make a new smart playlist (you can’t just edit the old one for some reason) and set it up like this:

1) Put in the normal criteria for your playlist. Mine was just rating 5 stars.
2) Here’s the secret sauce: Limit to some extraordinary number you’ll never hit, selected by whatever the criteria is that you want it sorted by on all your devices.
3) Sync your device (or wait for iTunes Match to sync it, which only takes 10 seconds or so)
4) Enjoy

Why we (mobile website designers) need to learn CSS animation.

I got a comment on an earlier post about making animation look better on mobile, and there seemed to be some confusion about using javascript animation versus css animation, when targeting mobile browsers. I wrote back and explained my thoughts, but I thought it might make for a good post too. So here goes…

It is absolutely vital for mobile developers to learn CSS animation instead of javascript.

The reason is that Javascript is actually very inefficient for animation, and it’s only recently, with the proliferation of mobile browsers, that we are starting to notice this. If we had been trying to do javascript animation on the computers we had back in the late nineties (which were of similar power to our current mobile phones), we’d have seen it then.

You see, with a JS animation (e.g. created using jQuery’s animate function), the javascript library sets an interval timer (lets say, 33ms, which is about 30 frames per second), and on that interval, it figures out where the animated element should be, using some pretty complex math calculated by the CPU, and then puts it there. Unfortunately, if the CPU is too slow to do that calculation every interval, it gets backed up and the animation stutters. jQuery and other JS animation tools do some work to combat this, sensing a drop in frame rate and trying to make the interval wider, to give it more time to complete the calculations, but it’s often too-little-too-late.

On the other hand, when you do a CSS animation (e.g. using the transform or webkit-transform css properties), you leave it to the GPU to simply calculate where the element should be as often as it can. As soon as it calculates the element’s new position and places it there, the GPU starts the calculation again. This means the animation is always as smooth as the GPU can possibly make it, no matter what. If you animate too many elements for the GPU to handle it may still have trouble, but instead of ugly stuttering, it will be a more graceful drop in framerate.

That’s why CSS animation is a must for mobile targeted websites. The good news is that all mobile browsers (the ones we care about anyway) support CSS3′s animation techniques, so there’s no need for capability detection and fallbacks.

Stop Google from hijacking arrow key presses on Search Result pages

If, like me, you use the arrow keys to scroll, or command key with an arrow key to scroll to the top or bottom of webpages on a daily basis, then you’ve been burned recently by google’s “helpful” new keyboard navigation on Search Result pages.

Yes, google thought it would be just a great idea to make their website the only one of the frickin internet that takes over our arrow keys and makes them much less useful.

Anyway, this guy ZimZat hated it too, so he made a Chrome extension called Arrow Key Guard to fix the problem.

If you’re not using Chrome, I don’t care, you have bigger problems anyway and you probably don’t use your keyboard for anything but typing shit about your cat into MS Powerpoint rainbow colored word-art objects anyway.

iTunes Match stuck on “Step 1: Gathering information about your iTunes Library”

I signed up for iTunes Match today, mostly just to upgrade all my music to un-DRM’d 256k (the iTunes Plus method would have cost about $100 at 30c a track). The jury is still out on whether I’ll renew the service next year.

Anyway, it got all the way 100% through Step 1: Gathering information about your iTunes library. and then stayed there for hours. Finally I noticed that a few songs in my library add a little cloud icon with a line through it. Closer inspection showed that those songs were DRM’d and were purchased on my ex-girlfriend’s iTunes account, which I am no longer authorized to use. Deleting, or removing them from the library (if you can foresee a need for DRM’d files you can’t open) will fix the problem.

Primal Screen’s Mic AS3 Output class

Today I committed the first version of my Mic AS3 class to Primal Screen‘s Github repository.

The purpose of this class is to organize your Output window into something much more usable. I wrote it in out typical relaxed Primal Screen style— very human readable, very easy to figure out what function does what.

First, import the class:

import com.primalscreen.utils.Mic;

Then say something into the Mic:

Mic.say("This is a test", this);

And you should see this in your output window:

myClass says:  This is a test

The Mic class uses that reference to “this” to grab the name of the class that is “talking” to it, so you can see where the message is coming from, then it adds spaces where needed to line everything up. When you say things from a few different classes, you see the power in this:

       myClass says:  This is a test
  SoundManager says:  Playing sound "1.mp3"
       myModel says:  The button was pushed
  myController says:  Message recieved!
        myView says:  All your base are belong to us!

That’s a lot of “says: ” isn’t it? Well that’s because we’re being calm, and well mannered. We’re saying things that ought to be said. Important things should be yelled!

Mic.yell("This must be important!", this);

When the app starts to get big, with lots of traces, and you just want the big picture, turn off the normal speech, so you just hear the important stuff that you yelled (or screamed, we’ll get to that):

Mic.ignoreSpeech();

Some things we don’t care about much, but on the off chance that we’re tearing our hair out in ├╝ber-debug mode, and want every last bit of data, we should still whisper it:

Mic.whisper("Nobody cares about what I'm saying right now", this);

Or if it’s super-duper important, we want to SCREAM it, and we can:

Mic.scream("Something crazy is happening!", this);

In the hierarchy it goes whisper, say, yell, scream, and when you ignore a level, you ignore the ones below it too. What about ignoring a class:

Mic.ignore(this);
Mic.ignore(SoundManager); 
// this is a reference to the SoundManager class object
Mic.ignore("SoundManager"); 
// this works too, and we don't need an actual object reference
Mic.silence(this); // an alias for ignore

Mic.unignore(this); 
Mic.unsilence(this); // an alias for unignore

What about the opposite, when we want to focus on the output of one particular class?

Mic.spotlight(this);
Mic.spotlight(SoundManager); // class ref
Mic.spotlight("SoundManager"); // class name as string
Mic.focus(this); // an alias for spotlight

Mic.unspotlight();
Mic.unfocus(this); // an alias for unspotlight

And I didn’t cover it above, but here are the other ignore functions:

Mic.ignoreWhispers();
Mic.ignoreSpeech();
Mic.ignoreSays(); // a grammatically incorrect alias
Mic.ignoreYells();
Mic.ignoreScreams();
Mic.ignoreAll(); // alias for ignore screams

Hope you like it!

UPDATE: Fix: CSS Animation slow or choppy in mobile browsers

Original post: http://chrissilich.com/blog/fix-css-animation-slow-or-choppy-in-mobile-browsers/

Even better than just adding this code to all the elements you want sped up…

-webkit-transform: translateZ(0);

Use -webkit-transform: translate3d() to do all your animations, instead of left, right, top, bottom, margin, or padding properties.

-webkit-transform: translate3d(50%, 0, 0);

Note that the values in the translate3d parentheses are x, y, z coordinates. Since -webkit-transform uses (yet another*) coordinate system, leaving a value as 0 will leave it unchanged (unless you used -webkit-transform somewhere else already).

Basically, the first example tells the browser to use the GPU to animate the element, which helps a fair bit, but the second code snippet uses the new CSS3 transform algorithms, which are WAY more efficient. The beautiful thing about it is all the modern smart phones use webkit, and therefore support -webkit-transform. My iPhone app now scrolls “like butter“!

*“Yet another” meaning you can move things relative to their point of origin with left/top, margin-left/margin-top, and now -webkit-transform;