読者です 読者をやめる 読者になる 読者になる

Sencha Touch と ExtJS

sencha sencha touch

Sencha Advent Calendar 2013 7日目です。

最近、私が Sencha に詳しいと言うことで、とある仕事で Sencha を使うことになりました。しかし、Sencha でも ExtJS の方。私が得意なのは Touch なんだけど。。。最近の ExtJS は全く知らない(汗

とはいえ、ExtJS4 になって Ext.define とか MVC とか Sencha cmd とか似たような感じっぽい。というよりむしろ Touch の元になったものなので、何とかなるだろうと始めてみました。最初は使うコンポーネントが違うくらいだろうと思ったのですが、使い出していると意外と細かいところで違うものなんだなぁ、と気がつきました。

というわけで、今日のテーマは「ここが違うよ!ExtJS と Sencha Touch
Sencha Touch と ExtJS の両方をある程度知っている人にしか分からない、細かすぎて伝わらないネタです。

configが違う

Sencha Touchでは、Ext.define で渡すコンフィグオブジェクトに、config という名前のプロパティオブジェクトを付けると、それは特殊なconfigプロパティとして認識されます。例えば、config オブジェクトに name というプロパティをセットすると、自動的に updateName や applyName というメソッドが追加されます。それらをオーバーライドすることで、各プロパティをセットしたときのフックが定義できます。

ExtJSでも config は使えるのですが、各種コンポーネントがこの作りに対応していません。Touchのコンポーネントは基本的にこのconfigを使って作られているため、プロパティのフックが簡単に行えるのですが、ExtJSではできません。そのうち対応してくれると嬉しいなぁ。

コントローラーが違う

ExtJSも4からMVCアーキテクチャが導入され、Controllerクラスが使えます。ただし、これも Touch のController と少し違います。
ExtJSのControllerの定義は次のような感じ。

 Ext.define('MyApp.controller.Users', {
     extend: 'Ext.app.Controller',

     refs: [{
         ref: 'list',
         selector: 'grid'
     }],

     init: function() {
         this.control({
             'button': {
                 click: this.refreshGrid
             }
         });
     },

     refreshGrid: function() {
         this.getList().store.load();
     }
 });

対して、Touchのコントローラーはこんな感じ。

Ext.define('MyApp.controller.Main', {
    extend: 'Ext.app.Controller',

    config: {
        control: {
            loginButton: {
                tap: 'doLogin'
            },
            'button[action=logout]': {
                tap: 'doLogout'
            }
        },

        refs: {
            loginButton: 'button[action=login]'
        }
    },

    doLogin: function() {
        //called whenever the Login button is tapped
    },

    doLogout: function() {
        //called whenever any Button with action=logout is tapped
    }
});


refs で コンポーネントをComponentQuery で指定するのはほとんど同じです。しかし、control定義が全然違う。少し驚きですね。また、ExtJS の control定義では、refs で定義した名前が使えない!!これにはやられました。Touchから入った人ははまるポイントではないでしょうか。(ってそんな人いるのか・・?)

bootloaderが違う

Sencha Cmdで、sencha generate app でアプリケーションを作るときに、sdkパスを Touch か ExtJSを切り替えるだけで、どっちのアプリケーションでも簡単に作れます。index.html も作ってくれるのですが、これが読み込む JS がまた違う。

Touch のほうは、microloader というのを読み込んで、それがアプリケーションを読み込んでくれます。この microloader を development か production を切り替えるだけで開発と本番を切り替えられます。次のような index.htmlが作られます。

<!DOCTYPE HTML>
<html manifest="" lang="en-US">
<head>
    <meta charset="UTF-8">
    <title>Sample</title>
    <style type="text/css">/* 略 */</style>
    <script id="microloader" type="text/javascript" src=".sencha/app/microloader/development.js"></script>
</head>
<body>
    <div id="appLoadingIndicator">
        <div></div>
        <div></div>
        <div></div>
    </div>
</body>
</html>

ExtJSは全然違います。次は ExtJS の index.html です。

<!DOCTYPE HTML>
<html>
<head>
    <meta charset="UTF-8">
    <title>Sample</title>
    <!-- <x-compile> -->
        <!-- <x-bootstrap> -->
            <link rel="stylesheet" href="bootstrap.css">
            <script src="ext/ext-dev.js"></script>
            <script src="bootstrap.js"></script>
        <!-- </x-bootstrap> -->
        <script src="app.js"></script>
    <!-- </x-compile> -->
</head>
<body></body>
</html>

bootstrap という 似たような物があるのですが、microloaderとはまた別の物。これが結構くせ者で、ビルドする度にパスが変わったりで慣れるまで苦労しました。実は ExtJS のテンプレートの方にも .sencha/app/microloader/ があります。これが使えるのか検証してないですが、使えるようになってくれると嬉しい。

まとめ

総じて、やはりTouchのほうが新しいため、アーキテクチャも洗練されているように感じます。もちろん ExtJS には便利で強力なコンポーネントが山ほどあるのが魅力ですが、既存のコンポーネントを新しくするのは影響も大きく大変なのでしょう。近い将来、どちらも同じように使えるようになることを期待しています。

以上、Sencha Touch から見た ExtJS の違いでした。