イタリアのウェブデザイナーのSpinelliさんのブログ記事"BUILD AND PUBLISH AN HTML5 GAME FOR IPAD"を訳してみました。(Spinelliさんにも事後承諾いただきました。)

これは私が現在手がけているプロジェクト/実験についての一連の投稿の最初のものです。目標はiPad用に(canvasを使わない)純粋なHTMLゲームを作り、Apple Store(原文のまま)で公開することです。私の日々の経験や示唆、コードの断片を見ることになるでしょう。

This is the first of a series of posts about a project/experiment I’m currently working on. The challenge is to build a pure HTML game (no canvas) for iPad and publish it to the Apple Store. Here you’ll find my day to day experience, suggestions and pieces of code.

この実験の目的はフルスクリーンのcanvasの中ではなくDOM上で作られたHTMLゲームを開発することです。HTMLだけを使って100%ネイティブに感じるまずまずのゲームを得られるか見いだしたいのです。また、Androidでバイスや古いiDevice, iOSへの扉を開けておきたいのです。それらは特にcanvasが良くありません。

The purpose of this experiment is to develop an HTML game built on DOM and not inside a full screen canvas. I want to find out if you can get a decent game that feels 100% native using just HTML. Also I want to keep the door open to Android devices and older iDevices and iOS versions, and none of them are particularly good at canvas.


I choose a game because they tend to be more complex than standard applications. Basically if you can do a game you can do anything.

ゲームはApple Storeに提出されて、$0.99レンジで販売される予定です。

The game will be submitted to the Apple Store and will be sold in the $0.99 range.
I know I’m not going to sell much, but sales statistics are part of the experiment.


The app is not finished yet, but at this stage I feel comfortable at reporting the first steps of the development process.

ステップ 1: ゲームのアイデアと技術的制約

ネイティブコードを使っていないので、アイデアは簡単でなければいけませんし、多大な処理能力を要求してはいけません。特に、たくさんのスプライト、エフェクト、複雑な物理を使うアクションゲームは避けたかった。パズルゲームを、特に単語パズルを選びました。iTunes storeでざっと検索してみると、そんなゲームが大量に見つかりましたが同じロジックを使ったものはたった1つで、正直に言えば言及に値さえしないものでした。

I am not using native code, so the idea must be simple and mustn’t require too much processing power. Notably I wanted to avoid action games with too many sprites, effects and complex physics. I opted for a puzzle game and specifically a word puzzle. A quick search on the iTunes store revealed a plethora of such games but only one with the same logic and sincerely it’s not even worth a mention.


Initially it seemed the perfect idea… It wasn’t. Word games are obviously based on a dictionary, and dictionaries have the bad habit of being huge. Words are injected into a web sql database and sqlite queries are slow, at least they are not game-fast. You can reach decent performance with a well indexed database, but 2mb of terms easily becomes 8mb of indexed db, well beyond the web sql 5mb limit.

Mobile Safariは、ユーザーの確認が要求されますが5MBを越えられることに注意してください―しかし、私はアプリをWebViewに埋め込むつもりで、私の知る限りこのシナリオの中で5MB制限を越える方法はありません。Objective-CでネイティブのSQLiteデータベース用ラッパーを作るのが解かもしれませんが、それでは純粋なHTMLゲームにはならなく、Android互換性も失われます。

Please note that mobile Safari can go over 5mb –even though an user confirmation is required– but I’m going to embed the app into a WebView and to my knowledge there’s no way to overcome the 5mb limit in this scenario. The solution might be to build a wrapper for the native sqlite database in object-c, but it wouldn’t be a pure HTML game that way, and I’d loose Android compatibility.


It was too late to change the game idea so I decided I would have solved this with pre-calculated schemas and reduced AI (more on this in the next post).

ステップ 2: コールバック(別名 PhoneGap)

アプリはApple Storeに提出されるのでネイティブアプリの内部にラップする必要があります。PhoneGapは使いたくありませんでした。最終的に必要なものはuiWebViewだけでしたが、JSよりもObjective-Cに時間を費やすことになり、HTMLゲーム製作としてはよくありませんでした。

The app will be submitted to the Apple Store so I need to wrap it inside a native app. I didn’t want to use PhoneGap, at the end all I needed was an uiWebView, but I found myself investing more time on Object-C than on JS, and that’s not good for an HTML game.


Audio is the mobile browser chimera, there’s no way to use native


代替の解を追ううちに、AppMobiを見つけました。これはとても興味深いプロジェクトで、私の理解では彼らは要素をハードウェアアクセラレートするカスタムのSafari互換ブラウザ作りました。デフォルトのWebViewと比較して5倍のパフォーマンス強化を彼らは主張します。(小さな強化に見えますが、1秒当たり10フレームの代わりに50フレームを意味します。) Impact フレームワークと合わせてウェブ開発者の手で強力なツールです。

In the hunt for alternative solutions I’ve found AppMobi. This is a very interesting project, from what I understand they’ve built a custom Safari compatible browser that gives hardware acceleration to the element. They claim a 5x performance enhancement in canvas games compared to default WebView (it may seem a small upgrade but it means 50fps instead of 10!). Together with Impact framework it is a powerful tool in the hands of the web developer.


I briefly tested AppMobi and I don’t feel comfortable with it. The Chrome plugin, connected to some Java service, is a little unstable on my Mac and by the way my project goal was to use plain ol’ HTML.

次のプロジェクトでsecond spinに使おうと決めました。

I promised myself I’d take it for a second spin for the next project.

ステップ 3: JS フレームワーク


For such a targeted application I see no reason on Earth to use a bloated JS framework. It’s useless to uber-optimize the game logic if the foundation is a hog.


I’ve already talked about it, I have nothing against jQuery and company, they serve an important cause, but on mobile applications I see them as cumbersome luggage.


I’ve build a light core framework that I can shape to my needs. Remember that we are dealing with a game, every spared CPU cycle counts.


Just to make an example the following is my way to apply a property to a set of nodes:

function forEach (el, fn) {
	el = document.querySelectorAll(el);
	for (var i=0, l=el.length; i<l; i++) {


Fast and furious.

ステップ 4: 乱数生成器

ゲーム開発のまさに底辺にはいい乱数生成器があります。JSゲーム開発のチュートリアルの中で言及しているものは滅多に見ないものです。しかしデフォルトのMath.random()は2つの大きな欠陥があります: 1) シードを与えられない; 2) 出力が範囲内を一様に分布していない。セッション間で同じゲームスキーマを使いたいなら#1は重大です。#2は一つの行で10回同じ数が繰り返されるようないらいらを避けるため重要です。この振る舞いは実際には「ランダム」だと言われてきましたが、ゲームのために必要としているものではありません。

At the very bottom of game development there’s a good Random Number Generator. It’s something I rarely see mentioned in JS game dev tutorials, but the default Math.random() has two major flaws: 1) it can’t be seeded; 2) the output is not evenly spread inside the range. #1 is crucial if you want to regenerate the same game schema between sessions. #2 is important to avoid the annoyance of having the same number repeated 10 times in a row. I’ve being said that this behavior is actually “random”, but this is not what I need for the game.


Fortunately you can find lots of resources about random number generation in javascript, I suggest you to start from the very good piece wrote by Johannes Baagøe.

ステップ 5: デバッグ

やけになって頭痛の種を探しているのでない限り、X Codeで開発しないこと、PhoneGapラッパの中でデバッグしないこと。

Don’t develop under X Code and don’t debug inside the PhoneGap wrapper, unless you’re desperately looking for daily migraine.

アプリケーションの70%はデスクトップブラウザ SafariかChrome上で開発します。20%は実際のデバイス(今回iPad)上で。残りはPhoneGap上で。これはタッチイベントとマウスイベント両方をフックする必要があることを意味しますが、信じてください。それは小さな犠牲で後悔しないでしょう。そしてひょっとしたら、あなたは遅かれ早かれデスクトップバージョンを公開したくなるかもしれません。

70% of the application is done on desktop browser, Safari or Chrome. 20% on the actual device (iPad in this case). The remaining on PhoneGap. This means that you need to hook to both touch and mouse events, believe me, it’s a small sacrifice that you won’t regret doing! And who knows, you may want to release a desktop version sooner or later.



Hope you enjoyed this introductory tutorial. Next time I’ll cover more technical aspects, so stay tuned and prepare for beta testing.