A plea to IE

Please, please implement getters and setters in your JavaScript engine. I cannot tell you how much I want to add this to JS.Class:

var MagicMethods = {
  included: function(klass) {

    var define = function(object, name) {
      var shortName = name.replace(/^[gs]et[A-Z]/,
          function(s) { return s.charAt(3).toLowerCase() });

      if (/^get[A-Z]/.test(name))
        object.__defineGetter__(shortName,
          function() { return this[name]() });

      if (/^set[A-Z]/.test(name))
        object.__defineSetter__(shortName,
          function(value) { return this[name](value) });
    };

    for (var key in klass.prototype)
      define(klass.prototype, key);

    if (klass.instanceMethod)
      klass.instanceMethod = (function(wrapped) {
        return function() {
          var name = arguments[0];
          define(klass.prototype, name);
          return wrapped.apply(klass, arguments);
        };
      })(klass.instanceMethod);
  }
};

This mixin needs a few type checks adding but I didn’t want to obscure the main idea. When mixed into a class, MagicMethods will intercept all instance method definitions and, if the method name looks like getX or setX it will add a shorthand getter or setter to the class. So, for example, the main collection class in Ojay has a bunch of methods like setStyle, getRegion and what-not. If we use the above mixin, we can get more intuitive code:

Ojay.DomCollection.include(MagicMethods);

// Set style of all paras
$('p').setStyle({fontStyle: 'italic'});    // old
$('p').style = {fontStyle: 'italic'};      // new

// Find region of the title
var region = $('h1').getRegion();    // old
var region = $('h1').region;         // new

Granted, I’m not saving a huge amount of typing here, but getters and setters get you out of the trap of having to make everything a method rather than a property to enforce encapsulation. style= and region in the above code look like property accesses, but are really function calls to setStyle() and getRegion() under the covers. You can implement something as a property to begin with, then later on you can change it to a getter method without breaking anyone’s code. It really comes into its own when using MethodChain:

MagicMethods.included(JS.MethodChain);

$('p').on('mouseover').style = {color: 'red'};
$('a').on('click', $.stopDefault).content = 'Clicked!'

This makes for a more declarative style for doing simpe event handling.

Anyways, this is all a moot point because this technique only works in Firefox and Safari. If we’re going to count beta versions, Opera 9.5 supports it too (thanks to John Resig for the heads-up). I’ve no idea whether IE8 plans to support it, and I don’t think it’s in the ECMAScript standard (3 or 4) so they’ve really no obligation to (comments proving me wrong greatly appreciated). In any case, the need to support IE 6 and 7 for the foreseeable future means I can’t use this feature, and I’m pretty sure there’s no way to reliably fake it in IE. Any ideas on 3-by-5 cards, please.