My blog has been moved to ariya.ofilabs.com.

Saturday, January 08, 2011

command line CoffeeScript

CoffeeScript seems to be picking up some momentum these days. No doubt, it is very valuable to help writing cleaner code.

The command-line choices to run CoffeeScript compiler right now are either using Rhino (jcoffeescript) or using NodeJS. While I love NodeJS, seems that it is an overkill to require the entire NodeJS stack/infrastructure/package manager to invoke CoffeeScript compiler.

The solution is to use V8, the powerful JavaScript engine, with a little binding so that it can access file system. This is exactly filejs, something I have shown before, e.g. to invoke JSLint from command line.

Combining filejs and CoffeeScript is terribly easy. Just follow these steps.

Note: filejs does not support Windows yet. Sorry.

First of all, if you have not done it, build filejs. Go to the X2 repository, it is under the javascript/filejs folder. Open the included README.TXT and follow the instructions on how to build V8 and filejs.

After you build it, copy both filejs executable and coffee.js to somewhere in your PATH. Usually I stash that kind of stuff in ~/bin and ensure that ~/bin is in my PATH.

Now get coffee-script.js (the CoffeeScript to JavaScript compiler) and store it somewhere, e.g. ~/bin again.

Create a new file called coffee, which has the following one-line content:

filejs ~/bin/coffee.js $1

Make that file executable and then save it to ~/bin (again).

Open coffee.js and modify the value of the compiler variable to point to your coffee-script.js. Note: this must use the absolute path name.

Now you can do the following:

coffee hello.coffee

If hello.coffee is your script written in CoffeeScript, the converted JavaScript version will be dumped to the standard output.

Feel free to tweak coffee.js so that it understands and passes various CoffeeScript compiler options!

Fun, isn't it?

Saturday, January 01, 2011

X2 from Ofi Labs: wrap-up 2010

X2It got started when I needed a new home for my examples. It has even a nice logo.

sensor

accelerometer viewer for Maemo 5 (Nokia N900).

bouncing ball, where the gravity affects the movement of the ball.

box of marbles, where the gravity affects a bunch of colored marbles.

combining accelerometer and network to do inter-device marbles transfer.

motion and orientation for web applications.

web-based version of marble box.

widgets

morphing clock, where the transition between the digital and analog version is a kind of morphing effect.

qpalette viewer so you know which color is which one.

graphics

fast approximation of Gaussian blur to create a blurry drop shadow.

command-line capture tool to save maps from OpenStreetMap, MapQuest and Ovi Maps.

simple tool to list all chunks inside a PNG image.

webkit & javascript

file processing, including using jslint, in command-line using JavaScript.

play Canvas-based game as normal desktop app.

offline, command line beautifier for JavaScript code, utilizing Qt Script.

another variant of the beautifier, this time using V8.

minimalistic editing widget for JavaScript code, with custom syntax highlighting.

white background is boring? just try some color inverted web pages.

detect the closest link to ease following it on a touch device.

Canvas pixel manipulation for plasma effect.

network

simple proxy server for HTTP, in 100 lines.

tracenet: trap all network requests+replies to show them with Speed Tracer.

filterproxy: another variant of the proxy server with added URL filtering feature.

Thursday, December 16, 2010

motion vs orientation

I already showed the use of device orientation in a fun game called Box of Marbles. Based on my experience trying out this API implementation, often it is easy to get confused by device motion vs device orientation. Thus, I created two web-based applications (using on Sencha Touch): Device Motion and Device Orientation. Each basically just visualizes the values of the data in a bunch of sliders:

You can find the code in the usual X2 repository, under the subdirectory javascript/devicemotion and javascript/deviceorientation, respectively. Obviously, the rest of Sencha Touch library is needed before you can deploy and run the examples. For the lazy, just run the live demo for Device Motion and Device Orientation (they support offline mode).

While right now only iOS 4.2 on iPhone/iPad/iPod Touch implements this API, I have a strong hope that Android (post Gingerbread) and Nokia (thanks to QtWebKit and Qt Mobility) will support this cool API in the near future. Well, at least I do plan to revive my Symbian setup to custom compile QtWebKit and test it on Nokia N8.

Side note: from my limited understanding, seems that both accelerometer and gyroscope are needed in order to supply the accurate data, much like in an inertial navigation system ("Inertial Phone", anyone?).

Monday, December 13, 2010

the art of repository access

team

What will occur when a software team is working on a project? How to tackle the change control?

The first and foremost obvious approach is simply giving full access for everyone. This is what typically happens in a group of friends working together on a cool project, a school assignment, a short hackathon, an early prototype, or any other collaborative efforts.

While this approach is very democratic (all developers are created equal), it is not very scalable. It works on a small and agile team, mainly because everyone knows each other. Once the team grows beyond a certain limit, the overhead of the communication makes it impossible to continuously get a full picture of what is being work on by whom.

Usually this problem is minimized by having somebody responsible for each module, essentially putting some organizational hierarchy in the project. However, a slight problem in the communication (which happens quickly, we're talking about engineers here) is enough to provoke a situation where conflict occurs due to a certain check in which carries over the problems and bugs from one module to another (Law of Unintended Consequences).

Another approach, certainly an evolution from the first one, is limited commit access. This particularly works well if there is a dedicated army of maintainers, whose job is to review incoming patches, give feedback, check them in. Usually this approach is very beneficial for the new members of the team, because they can learn what works and what does not work (since they are indirectly guided by the maintainer).

Quality control is definitely easier since all patches will be always filtered. Limiting the damage due to a broken commit is also not difficult since the repository can be frozen while the disaster mitigation team carries out the work.

This approach however falls apart if there is not enough maintainers and/or the rate of submitted patches increases. The symptoms are easy to spot: patches stay far too long in the queue, a maintainer has no time to do his own development, bad patches sneak in due to the time pressure, etc.

Keep in mind that due to its implicit (often also explicit) social stratification, it is important to take into account what everyone thinks about the approach. There should not be someone who feels left behind because only certain chosen guardians have the ultimate privilege access the repository. When such a situation is not tackled early on, it would grow latently and explode at some point in the future.

If there is a worry like that, then another (slightly reversal) evolution is inevitable: full access to everyone, as long as the patch is reviewed. The gut of this approach is basically "Let's trust each other, but let's also watch each other's back". Thus, inherent code review becomes mandated as well. Everyone is free to check in his patch directly to the repository, as long as some other competent fellow has looked at it and gave the green light. In fact, this should be called "brotherhood repository access" except that it may sound too exclusive and mystical.

Sometimes the system is also setup as far as rejecting the commit (e.g. from the server-side) when the log does not contained something like Reviewed by: Joe Sixpack. This is of course not always necessary, it may even require a consensus from everyone, under the pretext of preventing accidental check in.

This last approach may still not work in some situations. For example, if the team is global and located in different time zones, then coordinating the review becomes challenging (distributed control system may alleviate the problem). When code review is not a encouraged culture, counterproductive dead lock can be depressing. Also, because it is based on mutual trust, it breaks down when some people do not play by the same rule. In short, the approach depends heavily on the strong and committed communication between the team members.

In the end, the repository access approach must be evaluated on a case by case basis. Of course, in some places, no approach will work to satisfy everyone. In that case, consider again that technology can't and won't solve every social problem.

What kind of repository access do you have in your group? Which one do you prefer and why?

Saturday, December 11, 2010

ubiQt

devdays

Since coming back from Qt Developer Days 2010 in San Francisco (more precisely in Burlingame, near SF airport), one thought really bothered my mind: "when will Qt become ubiquitous?".

Now, if you are active in the KDE and Qt community, this seems like a strange question. But ubiquitous means omnipresence, in particular for the whole developer community.

Flash back to ages ago. You wrote a cool Python script (could be also in Ruby, or Lua, pick your battle) to do FooBar, everyone you know was impressed, you wanted to share the love with the world and then some fellow hacker noticed, "That's cool, man. But I don't want to install Python, can you give me the executable?". What would you think?

The situation is similar with Qt these days. You write a nice Qt-based utility, running on different platforms, somebody spots it and the first thing he asks is "Where is the binary?"; never mind he has just grabbed and installed hundreds MB worth of utilities.

These days, when you are developing some software, the first thing you'd do on a fresh machine is to download and install a gazillion tools (Xcode with iOS SDK weighs around 3.8 GB). With the initiative towards open governance, I hope Nokia and others will be able to steward Qt in that direction: being included in the de-facto standard of development tool sets. The most interesting challenge is to overcome the doubt, "Why do I need to install some Nokia SDK to use your cool app?".

Saturday, November 27, 2010

Box of Marbles meets Device Orientation

Remember my Box of Marble demo?. It was a native Qt/C++ application running on Maemo-powered Nokia N900.

With the wave of DeviceOrientation Event Specification implementation, now it's possible to have the demo as a web app, running just inside the web browser. In fact, this is what you can see from this demo: ariya.github.com/js/marblebox.

Right now, it works with iPhone or iPad or iPod Touch running the new iOS 4.2, due to the brand new DeviceMotionEvent support. If you own a MacBook with accelerometer and you use Google Chrome, that works as well (tilt your laptop to see the gravity effect). But fear not, with the recent support to hook the acceleration data from Qt Mobilty to QtWebKit, don't be shocked if the next Nokia phone with built-in QtWebKit sports this feature as well.

While my previous demo uses Chipmunk physics engine, this web version relies on box2d-js instead, mostly because I am too lazy to port Chipmunk to JavaScript and also I want to try something else. If you are curious about the code, check the usual X2 repository under javascript/marblebox directory. Enjoy!

Wednesday, November 10, 2010

V8 + jslint + vim

Usually, you would want to use scripting solution, e.g. Perl/Python/whatever, to manipulate file contents. Somehow, it's also fun to use JavaScript instead. After I did the V8-based jsbeautify, I was doing V8-based jslint as well. Then I realized, let's just extend it to be generic. With API loosely modelled after CommonJS, filejs was born. Find it in the usual X2 repository under the javascript/filejs. There are two examples so far, ROT-13 and line counter. If you write more examples, feel free to pass them to me!

Of course, the twist is: use filejs to drive a command-line jslint. This is one way to do it. First build filejs (follow the instructions in the included README), then place the executable in your PATH. Create a simple shell script, which contains one line filejs /path/to/filejs/jslint.js $1 and make it executable. That's it! If you also store this shell script in your PATH, then you just need to run:

jslint source-code.js

If you use vim, jslint can be combined with Quickfix. First of all, associate *.js with the tool by putting this line in your personal .vimrc:

au FileType javascript set makeprg=jslint\ %

Now open a JavaScript file and run :make (or whatever shortcut you map this into), which will launch jslint with the current file. After a while, use :cope to open the quickfix little window, move up and down, and press Enter to bring you back to the main editor and set the cursor at the specified problem. Use standard window navigation, e.g. Ctrl+W W to switch to quickfix pane again. Check the quickfix documentation for details. All in all, you may want to map mostly used commands to some shortcuts for faster access.

Note that since this is dynamic JavaScript, rather than matching errorformat, technically I just tweaked the tool to spit something similar to what a C/C++ compiler would do. Also, if you need different jslint options, simply edit the invocation to suit your needs.

It's been a while since I blogged about vim. The last one was about the project plugin, which is surprisingly still quite popular. Hopefully this one also teaches you a trick or two, especially if you work a lot with JavaScript code.

Note 1: It does not work on Windows yet. No idea if I would have the time to do it, patch is welcomed.

Note 2: This is not a replacement for NodeJS, nor would it grow to include more functions.

Note 3: For the sake of completeness, let me mention that there are already other countless solutions for command-line jslint (using Rhino, SpiderMonkey, JSC, etc), even with vim integration.

Tuesday, November 09, 2010

chunks inside PNG

Here is a few minutes of hack which would hopefully help someone else:

pngchunks logo.png
File size: 5967 byte(s)

Offset    Chunk    Size
      8    IHDR      13
     33    iCCP    2627
   2672    IDAT    3271
   5955    IEND       0

Useful to quickly find out if we can further strip unnecessary chunks from the PNG image. Or even as a warming up before you fire your favorite hex viewer/editor.

It's pure, stand-alone, self-contained C code (i.e. compile using gcc -o pngchunks pngchunks.c), available at the usual X2 repository, find it under graphics/pngchunks.

Friday, November 05, 2010

the fun of remote JavaScript debugging

Remote feature of Web Inspector, whereby you use an instance of WebKit and debug another one in different machine, is one important feature (that is being worked on) of WebKit I can't wait to start using. Till that day, remote debugging is always a challenge. There are of course assorted workarounds out there. At Sencha we decide to have and share with you a little tool that helps JavaScript remote debugging. It is available in two flavors: GUI-based (using Qt obviously) and Python-based for scripts and automation. Right now, the target is Android WebKit but there is no reason why we should not march to other platforms as well (e.g. QtWebKit on Symbian and MeeGo). Get it while it's hot!

Thursday, October 28, 2010

morphing clock revisited

If you can't see the clock below, visit the stand alone demo.

Technically, I had wanted to wait till it can display the actual time and perhaps ask some designer to polish it. But rather than keeping this lunch-break hack in a safe deposit box forever, let me just release this ugly clock transition (since everyone is on the animation frenzy). So far it works only if you use latest version of Safari, Chrome, Opera, Firefox. Canvas and/or VML fallback (which sadly will require JavaScript) for other browser are in the pipeline.

Basically it is another version of my previous morphing clock attempt (see the video). The principle is the same, except now I modified that C++ program to also output an HTML which renders the clock as above.

Also it morphs only once. Reload the page to enjoy the morphing once more. Maybe I'll find the time (in another lunch break) to toggle the two clock modes. Update: morphing from/to both analog and digital mode is implemented.

Like I said, it's a creepy, machine-generated, ugly looking clock. You've been warned, but feel free to write me anything (should you need to vent your anger).

Wednesday, October 27, 2010

Look ma, no JavaScript!

Take a look at the following CSS 3 demo. No Flash. No JavaScript. No image.

Hungry for more? Enjoy some other demos created using Sencha Animator.