uijs

A controvertial canvas based ui system for real mobile apps

npm install uijs
1 downloads in the last week
4 downloads in the last month

Welcome to uijs

Build Status

uijs is (yet another) cross platform mobile UI toolkit for apps.

Stability: 1 - Experimental. uijs is in early stages of development. It is still not mature enough for building actual apps with but we are looking for awesome hackers to join in and solve all those crazy problems.

Our goal is to create a UI software stack for mobile apps that looks and behaves like native mobile UI. Current stacks like jQuery Mobile, jQTouch and Sencha Touch are doing an excellent job with HTML5. We thought it would be interesting to try out something a little different and use the HTML5 canvas as our basis for the entire UI system.

Our thesis, which is yet to be proven, is that since we have almost full control on both rendering and behavior we might be able to create a great experience, which mobile users are accustomed to in native apps today.

At this point (v0.0.1), uijs is not yet usable. We are building it as you read this (yes!). If you are interested in contributing or trying it out, you are more then welcome. Ping us at the uijs google group.

uijs's codebase is maintained on github (of course) and published via npm as CommonJS modules. See Getting Started for more information on how to install uijs and build uijs apps.

We believe in the "batteries are not included" philosophy employed in projects like node.js. For frontend libraries, this is even more critical because one would want to keep the footprint of their app as small as possible, so we didn't want to put too much into the core library.

Installing uijs-devtools

You'll need node, which comes bundled with npm.

To installl the development tools globally, type:

$ npm install -g uijs-devtools

Now, create a directory for your app/module and install uijs there:

$ cd hello-uijs
$ npm install uijs

Contributors: Instead of using npm install you can use npm link to reference a local copy of a the uijs module. Git clone https://github.com/uijs/uijs into a local directory, run npm link within that directory and then you can use npm link uijs to install the uijs module as a link. You will see that node_modules/uijs will be a symlink instead of a real directory. Loving npm!

This will create a node_modules/uijs directory with the uijs core module.

Hello, uijs!

uijs apps/modules are CommonJS libraries (require, module.exports) which export a uijs box. A box is a visual rectanglurly-bound element that can draw itself and may have child boxes. In uijs everything is a box.

Let's create a simple box that prints 'hello, uijs!'.

Create a file named hello.js:

var uijs = require('uijs');

var app = uijs.box();

app.add(uijs.label({
  x: 10, y: 10, width: 200, height: 50,
  text: 'Hello, uijs!',
  color: '#1c8bdc',
  size: 30,
  bold: true,
  shadowColor: '#ccc',
  shadowOffsetX: 2,
  shadowOffsetY: 2,
  shadowBlur: 5,
}));

module.exports = app;

Basically what we did here is create an app box with a single child label (which is also a box). The label box has some properties like bounds (x, y, width and height), which is common to all boxes and some label-specific properties (text, color, etc). The function box.add(child) is used to add a child box to the app.

Notice that we do not specify any bounds for the app because by default it will be stretched to fill the entire browser window.

Building

Now, build and open the resulting html file:

$ uijs build hello.js
dist/hello.uijs.js created
dist/hello.uijs.html created

The uijs program is the entry point for the devtools. We use the build command, passing it hello.js as the input. Type uijs -h for usage.

build created two outputs: dist/hello.uijs.js and dist/hello.uijs.html:

  • The .js file is our app bundled using Browserify. It basically allows including a uijs app using a <script> tag within any HTML document.
  • The .html file is a standard uijs HTML shim with the bundled app embedded and contains the uijs bootstrapping code. In most cases, you will only need this file to serve your app to clients via CDN or some other static file server.

Open dist/hello.uijs.html with a web browser and you should see something like this:

image

Yeah!

Working iteratively

Passing -w to uijs build will start a file watch on the directory and automatically rebuild when your code changes, so you can work iteratively and refresh the browser window.

$ uijs build hello.js -w
Watching /Users/eladb/hello-uijs exclude: [ 'dist', 'node_modules', '.git', /\.tmp.+/ ]
dist/hello.uijs.js created
dist/hello.uijs.html created    
...
/Users/eladb/hello-uijs/hello.js changed. rebuilding
dist/hello.uijs.js created
dist/hello.uijs.html created    
...

Pretty useful!

Binding

One of uijs's freakingly awesome features is it's binding system. You can read more about it here. Simply put, you can bind any box property to a function and watch any property for changes (even if they are bound to functions (hell, yeah!)).

Let's edit hello.js and bind the label's text to something useful:

Replace this:

  text: 'Hello, uijs!',

With this:

  text: uijs.bind(function() { return window.innerWidth + 'x' + window.innerHeight; }),

Now you should see something like this:

image

If you change the browser window dimensions, you should see these values change immediately.

Running on a mobile device

uijs is all about mobile apps, so we are trying to make it super easy to serve your app for development and access it through the local network via your mobile browser.

Execute:

$ uijs debug hello.js -w
Watching /Users/eladb/hello-uijs exclude: [ 'dist', 'node_modules', '.git', /\.tmp.+/ ]
dist/hello.uijs.js created
dist/hello.uijs.html created
starting debugger for /Users/eladb/hello-uijs/dist/hello.uijs.js
uijs debugger listening on port 5000

As you can see, the debugger is listening on port 5000. Now all you need to do is point your mobile device to http://<your-machine-ip-address>:5000 and your app should show up.

Since most mobile browsers do not have a console window, if you use console.log in your codebase, those logs will be outputed on the console of your host machine, making your life so much better.

Since we used -w, the file watch will also work in this mode.

Samples

Samples are simple uijs apps. In order to open a sample, use uijs build (or uijs debug) with the sample file:

For example:

$ cd samples
$ uijs build interaction-sample.js
dist/interaction-sample.uijs.js created
dist/interaction-sample.uijs.html created
$ open dist/interaction-sample.uijs.html

Running Tests

npm test will run all tests. These are the regression tests that should be executed before commiting code into the repository.

We have two types of tests:

  1. Functional tests are located under test/*.test.js. Functional tests are simply node.js scripts. If they exit with a non zero exit code, the test failed.
  2. This is broken: Visual tests are located under test/*.cantest.{js|png}. Visual tests use node-canvas and cantest and can be executed using cantest xxx.cantest.js. Read more about visual tests in the cantest README file. To run visual tests, you will have to install cairo. On a mac with homebrew just type brew install cairo.

Running all tests:

$ npm test
> uijs@0.0.1 test
> cd test && ./run.sh

Running catest tests
Running functional tests

Benchmarks

Benchmarks are uijs apps (export a box). All benchmarks are under the benchmarks directory. To run a benchmark, use the uijs devtool bench or prof commands. By default the benchmark will run for 5 seconds. If prof is used, it will show a profiler output.

$ cd benchmarks
$ uijs bench the-box.js
the-box.js 34303.2fps
$ uijs prof the-box.js
...
... # benchmark results
...
the-box.js 36176.4fps

Note that since benchmarks are regular uijs apps, they can usually be also opened from the browser. The fps measurements will be outputed to the console.

$ cd benchmarks
$ uijs debug the-jumping-box.js
http://localhost:5000

Results

All results are from MacBook Air 1.8 GHz i7 4GB

+---------------------------------+-------------------+
| test               | b87c5582d2 | 8119a6f096        |
+--------------------+------------+-------------------+
| the-box.js         | 13,592fps  | 66,870fps (+491%) |
| the-jumping-box.js | 141.4fps   | 1,398fps (+988%)  |
+---------------------------------+-------------------+

License

(The MIT License)

Copyright (c) 2012 uijs.org and other uijs contributors

Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:

The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.

THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

npm loves you