E: me@sabisin.com | T: +4915168651209

Mario Mushroom: Now with 80% less awesome

tl;dr: Don’t use the Mario Mushroom Operator if you don’t want your setter to be invoked more than once.

Update: I totally forgot to mention that I found out about this problem with @darscan while working on Swiftsuspenders and Robotlegs code.

The Details I think it was @robpenner who coined the term “Mario Mushroom Operator”.

In case you’re wondering, the Mario Mushroom Operator is this: ||=.

A good translation for how the MMO™ works seems to be this:

if (!field) { field = value; }

In case you’re still wondering, here’s how you’d use it:

function useRuntimeDefault(input:Object):void { 
   input ||= getDefaultValue(); 
}

I.e., the most important use-case for the MMO™ is to apply runtime-determined default values for method arguments.

Now, that’s really useful and you might be wondering what could possibly go wrong with that.

Consider this snipped of code:

private var _setOnce : Boolean; private var _value : Object;

public function set value(value : Object) : void { 
   if (_setOnce) { 
      throw new Error('Value can only be set once'); 
   } 
   _setOnce = true; 
   _value = value; 
}
public function get value() : Object { 
   return _value; 
}

Used in a class, this code encapsulates a value that can be set exactly once, after which it can only be read.

With me still? Splendid.

In fact, you’re probably already guessing what comes now: Using the MMO™ to assign this once-settable value iff it hasn’t already been set:

value ||= {};

And here, finally, things go awry. As it turns out, the MMO™’s translation given earlier isn’t quite correct. Instead, the compiler (or the VM, I haven’t checked the bytecode) seems to translate our usage of the MMO™ to something along the following lines:

field = field ? field : {};

In summary, instead of guarding the assignment to a field as an if statement would do, the MMO™ only chooses between two values to use in the assignment like the ternary operator does.

In case you’re now thinking that that doesn’t affect you because you, just as every sane person you know, don’t ever have use-cases for one-time assignable fields, ask yourself whether you can be certain that all your setters are side-effect free if you re-assign the same value and that you never, ever, care about the overhead associated with double-setting values needlessly. “Yes” and “yes”? Cool. “Mmh” and “not sure”: Weep with me.

iCloudANE

iCloudANE is a native extension that enables the use of iCloud storage service. The extension supports String Key-Value Stores, that can be combined with JSON to store complex data. The iCloud service allows iOS application to share information among different devices.

http://airextensions.net/shop/extensions/icloud-by-vitapoly/

Sample

var iCloud:iCloudANE = new iCloudANE();

// storing data
// so.data is some shared object data. but it can just be a generic string
iCloud.store("save", JSON.stringify(so.data));	

// retrieving data
var iCloudSave:String = iCloud.getStringForKey("save");

GameKit

GameKit is a native extension that allows the use of iOS GameKit framework. The extension allows your game to setup real time Game Center matches for up to 4 players, send and receive custom data between players, and enable voice chat during gameplay. It implements a subset of the iOS GameKit framework.

http://airextensions.net/shop/extensions/game-kit-by-vitapoly

Sample

var gamekit:GameKit = new GameKit();
 
// Authenticate the local player, but listen to the events first:
gamekit.addEventListener(GameKit.LOCAL_PLAYER_AUTHENTICATED_EVENT, function(e:Event):void {
    trace("LOCAL_PLAYER_AUTHENTICATED_EVENT");
});
 
gamekit.addEventListener(GameKit.LOCAL_PLAYER_NOT_AUTHENTICATED_EVENT, function(e:Event):void {
    trace("LOCAL_PLAYER_NOT_AUTHENTICATED_EVENT");
});
 
gamekit.authenticateLocalPlayer();
 
//Get info about local player after successful authentication:
var localPlayer:LocalPlayer = gamekit.getLocalPlayer();
trace(localPlayer.displayName);
 
for (var friend:Player in localPlayer.friends)
    trace("friend: " + friend.displayName);
 
//Show native Game Center interface:
gamekit.showGameCenter();
 
//Start a real time match, but listen to events first:
gamekit.addEventListener(GameKit.MATCH_MAKER_FAILED_EVENT, function(e:ErrorEvent):void {
    debug("MATCH_MAKER_FAILED_EVENT: " + e.errorID + ", " + e.text);
});
 
gamekit.addEventListener(GameKit.MATCH_MAKER_CANCELLED_EVENT, function(e:Event):void {
    debug("MATCH_MAKER_CANCELLED_EVENT");
});
 
gamekit.addEventListener(GameKit.MATCH_MAKER_FOUND_MATCH_EVENT, function(e:MatchFoundEvent):void {
    debug("MATCH_MAKER_FOUND_MATCH_EVENT: " + JSON.stringify(e));
 
    match = e.match; // save the match somewhere
    if (match.expectedPlayerCount == 0)
        startGame(); // start game if not expecting anymore players
});
 
// bring up native match making interface for a match with 2 to 4 players
gamekit.startRealTimeMatch(2, 4);
 
// Send data to other players during game:
var data:ByteArray = new ByteArray();
data.writeUTFBytes("hello");
 
// send a reliable packet to all players
match.sendDataToAll(data, true);
 
// send an unreliable packet to the match's first player
match.sendData(match.players[0], data, false);
 
// Receive data from other players:
match.addEventListener(RealTimeMatch.RECEIVED_DATA_EVENT, function(e:DataReceivedEvent):void {
    debug("RealTimeMatch.RECEIVED_DATA_EVENT from " + e.player.playerID + ": " + e.data.toString());
});
 
// Start a voice chat with other players:
var chat:VoiceChat = match.getVoiceChat("all");
 
// join the voice chat so the player can hear other players
chat.join();
 
// set talk to true so other players can hear this player
chat.talk = true;
 
// Disconnect and properly dispose the match:
match.disconnect();
match.dispose(); // releases the native match object

Hungry Hero goes Open Source

hUngaryhEro

Hungry Hero is an open source Flash game built on Starling Framework. This game is built to give developers an idea of how a typical Starling based game looks like. The basic idea is to showcase how easy it is to build a Stage3D game, giving your games the power of GPU rendering or Hardware acceleration.

http://www.hsharma.com/games/hungry-hero-goes-open-source/