developing

Powerful tools for developing Web Apps

In the recent years, web development changed drastically. The emergence of the mobile web and the new form factor of smart phones created the demand for different solutions than the former desktop-only web.

Since then a lot of frameworks and tools have been created, with new ones being added almost weekly. Now, we web developers are faced with a different problem: for every development concern, there are multiple options to consider, without clear pros or cons. It is easy to feel intimidated not only by the choices available, but also by how similar those choices are.

Every day, web developers have to successfully overcome this issue and turn this diversity from a daunting proposition into an empowering one.

But why reinvent the wheel all the time?

A set of solid recommendations for app developers

Mozilla is putting together a core set of tools and recommendations that we believe are the most useful for making Web apps.

The key considerations for what we might recommend are:

  • Sufficiently well-documented and straightforward to use for an average developer (we will concisely document the required knowledge one needs in order to engage with the technology).
  • Loosely coupled and as modular as possible (so you can follow one recommendation but not another if you are so inclined).
  • Tested on Mozilla products (i.e. the UI components will perform well on Firefox OS, etc), but with cross-platform apps in mind

The upcoming, initial set of recommendations involves a toolchain that’s core to any modern web app, like a JavaScript framework, templating interface, UI framework and task runner. We will employ existing solutions wherever possible and write libraries or utilities to fill in the gaps.

On an ongoing basis, we’ll expand this systematically across the different parts of the development experience, such as offline handling or the use of various Web APIs.

All of this will be delivered in one central spot: The App Center on the Mozilla Developer Network (MDN), our established, renowned resource for web app development.

But I already have it all figured out!

We encourage you to share your success story with us. Heck, share your failures too. We need all the feedback we can get from everyday web developers. If you have a tool chain of your own, with your favorite JavaScript framework, etc., we’re not interested in converting you to something else. We’re trying to help developers who aren’t sure how to go about making these kinds of decisions.

Come join us!

In the Mozilla tradition, this is a community-driven process. This means your input is encouraged and appreciated, and we would like your help to make this a successful initiative!

The main discussions around this will happen in the following places:

For the initial tool chain recommendations, I started a thread on the mailing list already, go ahead and weigh in.

If you have ideas for topics worth exploring in future iterations, don’t be shy and open a new thread to get the discussion started.

What’s next?

If this whets your appetite, then great! 2014 is an exciting year to be a web app developer. We’ll keep you updated here on Hacks, as well as the MDN App Center over the coming months.

View full post on Mozilla Hacks – the Web developer blog

VN:F [1.9.22_1171]
Rating: 0.0/10 (0 votes cast)
VN:F [1.9.22_1171]
Rating: 0 (from 0 votes)

Notes on developing an API – Mobozi, a WebFWD project

HTML5 has made it easy to do a lot of really cool stuff on the mobile web, but one thing that is still pretty difficult is dealing with photos. Android has supported access to the device camera via the File API since version 3.0 and iOS opened it up last Fall with iOS 6. Allowing users to snap and upload photos in HTML5 is not as simple as just connecting a form to a database however. With a multitude of devices, OS versions, and browsers the image files come in different orientations, sizes, and with different encoding.

I frequently encountered this headache when developing HTML5 apps, which lead myself and my partner to create Mobozi. Mobozi is a front end library that optimizes and normalizes images across mobile devices, OSs, and browsers and also a simple API for photo upload and serving. This post is a brief overview of how we went about creating the API to to be functional and also easy and effort free for developers to use.

Planning

The first thing we did was map our all the functionality we would need and walk through the different use cases and flows from our users perspective. We thought about things like formatting and version control and how we could structure them to make it as developer friendly as possible.

We also considered data formats and decided to support JSON, XML and JSONP in order to keep the API as flexible as possible. We also made sure to model the API calls in a way that they were predictable and did not require the developer to guess. For example, to add an item, POST method is always used and to retrieve GET is used.

Security

Next we thought security, one of the most important parts of any public facing API. We decided to serve our API from a subdomain (https://api.mobozi.com) and allow CORS (Cross Origin Resource Sharing) on this domain only (our main domain and all other sub domains don’t entertain any request that originated from a different domain). Additionally, CORS on Apache is a great resource.

Developer Experience

Once all the nuts and bolts of the domain had been decided upon, we had to think about how developers would actually get access to and implement our API. We decided to provide an API key and use an HTTP token authentication in order to authenticate them. We also spent a lot of time refining our docs and are continuing to listen to feedback in order to get them as streamlined as possible.

Technology

Once we decided on the functionality the API would need to provide, as well as how it would be implemented, we had to choose a stack to build it on. We chose PHP/MySQL because it’s stable, scaleable, and most importantly because our team was very comfortable and familiar with it. Next we began searching for a framework that would keep our API lightweight but also offer our users a very quick response time.

After researching and testing out different API frameworks we found two that met our needs – Limonade and Slim. Limonade is a PHP micro framework for rapid web development and prototyping. Slim is also a PHP micro framework that helps you quickly write simple yet powerful web applications and APIs.

We eventually decided on Limonade because it was easier to implement and provides functionality we needed like clean URLs and cross origin request handling. Slim was powerful and light as well but had issues with cross origin requests as well as with the auto loader.

Here is a brief example from our API. This code will allow you upload an image from any device and get back the URL where it is being stored.

Include this snippet in your page’s head

<script src="http://zeptojs.com/zepto.min.js"></script>
<script src="//js.mobozi.com/v1/mobozi.js"></script>
mobozi.init('123456789');
function uploadImage(){    
    var myFile = document.getElementById('idimage').files[0];
    var imageData = {
        "file": myFile 
    };
    mobozi.image.uploadGetUrl(imageData,function(response) { 
        if (response.status == 201){
            $('#imgUrl').html('URL: ' + response.data.imageUrl);
            $('#upImage').attr('src',response.data.imageUrl);  
        } else {
            alert (response.error);
        }
    });
}

Include this snippet in your page’s body

<input id="idimage" name="idimage" type="file" accept="image/*"/>
<button type="button" id="btnup" onclick="uploadImage();">Upload Image</button>
<div id="imgUrl"></div>
<div><img id="upImage" src=""></div>

A working example

Outreach

So the functionality has been hashed out, the plan of attack decided, and the code written; what next? Get developers to use the thing! And hopefully get feedback from them on how to make it better. This is what we’re currently doing at Mobozi by holding a Hackathon (awesome HiFi speaker for the winner). More details in that page and feel free to ask any questions at founders@mobozi.com.

View full post on Mozilla Hacks – the Web developer blog

VN:F [1.9.22_1171]
Rating: 0.0/10 (0 votes cast)
VN:F [1.9.22_1171]
Rating: 0 (from 0 votes)

Developing a simple HTML5 space shooter

Experimenting with modern web technologies is always fun. For my latest project, I came up with the following requirements:

  • Not a complex game, rather a proof-of-concept
  • Space shooter theme
  • Canvas-based rendering, but no WebGL
  • Re-use of existing sprites (I am no artist)
  • Rudimentary audio support
  • AI/Bots
  • Working network multiplayer

I worked on this project only in my spare time; after approx. two weeks, the work was done: Just Spaceships! This article describes some decisions and approaches I took during the development. If you are interested in the code, you can check the relevant Google Code project.

Animation & timing

There are two basic ways to maintain an animation: requestAnimationFrame and setTimeout/setInterval. What are their strengths and weaknesses?

  • requestAnimationFrame instructs the browser to execute a callback function when it is a good time (for animation). In most browsers this means 60fps, but other values are used as well (30fps on certain tablets). Deciding the correct timing is up to the browser; the developer has no control over it. When the page is in background (user switches to another tab), animation can be automatically slowed down or even completely stopped. This approach is well suited for fluent animation tasks.
  • setTimeout instructs the browser to execute your next (animation) step after a given time has passed; the browser will try to fulfill this request as precisely as possible. No slowdowns are performed when the page is in background, which means that this approach is well suited for physics simulation.

To solve animation-related stuff, I created a HTML5 Animation Framework (HAF), which combines both approaches together. Two independent loops are used: one for simulation, the second one for rendering. Our objects (actors in HAF terminology) must implement two basic methods:

/* simulation: this is called in a setTimeout-based loop */
Ship.prototype.tick = function(dt) {
	var oldPosition = this._position;
	this._position += dt * this._velocity;
	return (oldPosition != this._position);
}
 
/* animation: this is called in a requestAnimationFrame loop */
Ship.prototype.draw = function(context) {
	context.drawImage(this._image, this._position);
}

Note that the tick method returns a boolean value: it corresponds to the fact that a (visual) position of an object might (or might not) change during the simulation. HAF takes care of this – when it comes to rendering, it redraws only those actors that returned true in their tick method.

Rendering

Just Spaceships makes extensive use of sprites; pre-rendered images which are drawn to canvas using its drawImage method. I created a benchmarking page which you can try online; it turns out that using sprites is way faster than drawing stuff via beginPath or putImageData.

Most sprites are animated: their source images contain all animation frames (such as in CSS sprites) and only one frame (rectangular part of the full source image) is drawn at a time. Therefore, the core drawing part for an animated sprite looks like this:

Ship.prototype.draw = function(context) {
	var fps = 10;          /* frames per second */
	var totalFrames = 100; /* how many frames the whole animation has? */
	var currentFrame = Math.floor(this._currentTime * fps) % totalFrames;
 
	var size = 16; /* size of one sprite frame */
 
	context.drawImage(
		/* HTML &lt;img&gt; or another canvas */
		this._image,
 
		/* position and size within source sprite */
		0, currentFrame * size, size, size,
 
		/* position and size within target canvas */
		this._x, this._y, size, size
	);
}

By the way: the sprites for Just Spaceships! have been taken from Space Rangers 2, my favourite game.

The golden rule of rendering is intuitive: redraw only those parts of the screen which actually changed. While it sounds pretty simple, following it might turn out to be rather challenging. In Just Spaceships, I took two different approaches for re-drawing sprites:

  • Ships, lasers and explosions use technique known as “dirty rectangles”; when an object changes (moves, animates, …), we redraw (clearRect + drawImage) only the area covered by its bounding box. Some deeper bounding box analysis must be performed, because bounding boxes of multiple objects can overlap; in this case, all overlapping objects must be redrawn.
  • Starfield background has its own layer (canvas), positioned below other objects. The full background image is first pre-rendered into a large (3000×3000px) hidden canvas; when the viewport changes, a subset of this large canvas is drawn into background’s layer.

Sound

Using HTML5 audio is a piece of cake – at least for desktop browsers. There were only two issues that needed to be taken care of:

  1. File format – the format war is far from being over; the most universal approach is to offer both MP3 and OGG versions.
  2. Performance issues on certain slower configurations when playing multiple sounds simultaneously. More particularly, my Linux box exhibited some slowdowns; it would be best to offer an option to turn the whole audio off (not implemented yet).

At the end of the day, the audio code looks basically like this:

/* detection */
var supported = !!window.Audio &amp;&amp; !audio_disabled_for_performance_reasons;
 
/* format */
var format = new Audio().canPlayType("audio/ogg") ? "ogg" : "mp3";
 
/* playback */
if (supported) { new Audio(file + "." + format).play(); }

Multiplayer & networking model

Choosing a proper networking model is crucial for user experience. For a realtime game, I decided to go with a client-server architecture. Every client maintains a WebSocket connection to central server, which controls the game flow.

In an ideal world, clients would send just keystrokes and the server would repeat them to other clients. Unfortunately, this is not possible (due to latency); to maintain consistency and synchronicity between players, it is necessary to run the full simulation at server and periodically notify clients about various physical attributes of ships and other entities. This approach is known as an authoritative server.

Finally, clients cannot just wait for server packets to update their state; players need the game to work even between periodical server messages. This means that browsers run their version of the simulation as well – and correct their internal state by data sent by server. This is known as a client-side prediction. A sample implementation of these principles looks like this:

/* physical simulation step - client-side prediction */
Ship.prototype.tick = function(dt) {
	/*
		assume only these physical properties:
			acceleration, velocity and position
	*/
	this._position += dt * this._velocity;
	this._velocity += dt * this._acceleration;
}
 
/* "onmessage" event handler for a WebSocket data connection;
	used to override our physical attributes by server-sent values */
Ship.prototype.onMessage = function(e) {
	var data = JSON.parse(e.data);
 
	this._position = data.position;
	this._velocity = data.velocity;
	this._acceleration = data.acceleration;
}

You can find very useful reading about this at Glenn Fiedler’s site.

Multiplayer & server

Choosing a server-side solution was very easy: I decided to go with v8cgi, a multi-purpose server-side javascripting environment, based on V8. Not only it is older than Node, but (most importantly) it was created and maintained by myself ;-).

The advantage of using server-side JavaScript is obvious: game’s server runs the identical code that is executed in browser. Even HAF works server-side; I just turned off its rendering loop and the simulation works as expected. This is a cool demonstration of client-server code sharing; something we will probably see more and more in the upcoming years.

Modulus

In order to make the game more interesting and challenging, I decided that the whole playing area should wrap around – think of the game universe as of a large toroidal surface. When a spaceship flies far to the left, it will appear from the right; the same holds for other directions as well. How do we implement this? Let’s have a look at a typical simulation time step:

/* Variant #1 - no wrapping */
Ship.prototype.tick = function(dt) {
	this._position += dt * this._velocity;
}

To create an illusion of a wrapped surface, we need the ship to remain in a fixed area of a given size. A modulus operator comes to help:

/* Variant #2 - wrapping using modulus operator */
Ship.prototype.tick = function(dt) {
	var universe_size = 3000; // some large constant number
	this._position += (dt * this._velocity) % universe_size;
}

However, there is a glitch. To see it, we have to solve this (elementary school) formula:

(-7) % 5 = ?

JavaScript’s answer is -2; Python says 3. Who is the winner? The correctness of the result depends on the definition, but for my purpose, the positive value is certainly more useful. A simple trick was necessary to correct JavaScript’s behavior:

/* Returned value is always &gt;= 0 &amp;&amp; &lt; n */
Number.prototype.mod = function(n) {
	return ((this % n) + n) % n;
}
 
/* Variant #3 - wrapping using custom modulus method */
Ship.prototype.tick = function(dt) {
	var universe_size = 3000; // some large constant number
	this._position += (dt * this._velocity).mod(universe_size);
}

Lessons learned

Here is a short summary of general tips & hints I gathered when developing JS games in general, but mostly during Just Spaceships development:

  • Know the language! It is very difficult to create anything without properly understanding the programming language.
  • Lack of art (sprites, music, sfx, …) should not stop you from developing. There are tons of resources for getting these assets; the need for original art is relevant only it later stages of the project.
  • Use the paper, Luke! You know what my favorite development tools are? A pen and a sheet of squared paper.
  • If you are not 100% sure about the whole game architecture, start with smaller (working) parts. Refactoring them later to form a larger project is natural, useful and easy.
  • Collect feedback as soon as possible – at the end of the day, it is the users’ opinion that matters the most.

TODO

As stated before, Just Spaceships is not a complete project. There is definitely room for improvements, most notably:

  • Optimize the network protocol by reducing the amount of data sent.
  • Offer more options to optimize canvas performance (decrease simulation FPS, turn off background, turn off audio, …).
  • Improve the AI by implementing different behavior models.

Even with these unfinished issues, I think the game reached a playable state. We had quite a lot of fun testing its multiplayer component; I hope you will enjoy playing it!

 

View full post on Mozilla Hacks – the Web developer blog

VN:F [1.9.22_1171]
Rating: 0.0/10 (0 votes cast)
VN:F [1.9.22_1171]
Rating: 0 (from 0 votes)