9. August, 2007
11. September, 2007
in by Michael Neumann

Okay, I am in the progress of porting Google Web Toolkit to RubyJS. The first 2500 lines of code (that includes a lot of comments) went pretty well. So far the basic is up and running. 99% of the DOM code (which I split up into Event and Element classes and renamed some methods accordingly) is functional. UIObject and Widget classes as well. But then it really starts to become Java-centric. Iterators, a lot of interfaces (e.g. class Label implments following interfaces: SourcesClickEvents, SourcesMouseEvents, SourcesMouseWheelEvents, HasHorizontalAlignment, HasText, HasWordWrap) and big switch statements make it now more difficult to continue with a mostly line-by-line translation. While I could just port everything line-by-line, I don't think this is the Ruby way. Right now I am looking at the Tree.java file, whose onBrowserEvent method (the Widgets central event dispatch method) contains a big, no a huge switch statement. As long as each case is followed by a break that's just fine. But it's not the case. What I really find ugly is this piece of code:

case Event.ONKEYDOWN:
/* lots of code removed */

  // Intentional fallthrough.
case Event.ONKEYUP:
  if (eventType == Event.ONKEYUP) {
    /* ... */
  }

  // Intentional fallthrough.
case Event.ONKEYPRESS:

How can a human understand that. It's as bad as goto.

Instead of huge switch statements, I have invented a event dispatch mechanism, which comes at no memory overhead (or only very little, at least no new object exists) and only one additional method call. So you can write:

mapEvent(Event::ONCLICK, `#<self>.#<m:onClick>`)
mapEvent(Event::ONMOUSEUP, `#<self>.#<m:onMouseDown>`)

and the ONCLICK event will trigger the onClick() call. If this extra method call would be too much overhead, this could be removed by moving the code into the Event dispatcher code (which currently calls onBrowserEvent).