@thorikiriのてょりっき

@thorikiriがWebとかAndroidとかの技術ネタや本を読んだブログです

jQueryMobileでiPad向けの2カラムのWebページをデザインする その4

前回までで基本的なデザインは出来上がりました。と言うことにしておきましょう。
次は画面遷移をしたいと思うのですが、jQueryMobileのデフォルトの挙動ではメニュー部分だけとか、コンテンツ部分だけを画面遷移させることが出来ないですね。
という訳で、今回はメニュー部分の画面遷移を実装していこうと思います。

事前準備

まずは大元になるページを切り替えられるようにしておきます。
戻るボタンとかで戻れるようにしたいので、別ページとして定義します。

  • sample.html
    <section data-role="page" id="index" data-mainpage="#main" data-mainpagetitle="content" data-menupage="#menu" data-menupagetitle="menu">
      <div class="ui-grid-a ipad-grid">
        <div class="ui-block-a ipad-menu-block">
          <header data-role="header" data-theme="c" class="ipad-menu-header" id="menuHeader">
            <h1>menu</h1>
          </header>
          <div data-role="content" class="ipad-menu-body" id="menuBody">
          </div>
        </div>
        <div class="ui-block-b ipad-content-block">
          <header data-role="header" data-theme="c" class="ipad-content-header" id="contentHeader">
            <h1>content</h1>
          </header>
          <div data-role="content" class="ipad-content-body" id="contentBody">
          </div>
        </div>
      </div>
    </section>
    <section id="main" data-role="page">
      <div class="ui-grid-a ipad-grid">
        <div class="ui-block-b ipad-content-block">
          <div data-role="content" class="ipad-content-body">
            <form>
              <label for="searchText">検索:</label>
              <input type="search" name="searchText" id="searchText"/>
              <label for="searchDueDate">期限:</label>
              <input type="date" name="searchDueDate" id="searchDueDate" />
              <label for="searchStatus">ステータス:</label>
              <select id="searchStatus" name="searchStatus">
                <option>----</option>
                <option value="0">未着手</option>
                <option value="1">作業中</option>
                <option value="2">完了</option>
              </select>
              <button data-theme="b">検索</button>
            </form>
            <h2>検索結果</h2>
            <ul data-role="listview" data-inset="true">
              <li>
                <a href="#">
                  <h3>TODO-1</h3>
                  <p class="ui-li-aside">2012/12/30 まで</p>
                  <p><strong>未着手</strong></p>
                </a>
              </li>
              <!-- 繰り返し -->
            </ul>
          </div>
        </div>
      </div>
    </section>
    <section id="menu" data-role="page">
      <div class="ui-grid-a ipad-grid">
        <div class="ui-block-a ipad-menu-block">
          <div data-role="content" class="ipad-menu-body">
            <ul data-role="listview">
              <li><a href="#main">content</a></li>
              <li><a href="#menu1">Menu-1</a></li>
              <li><a href="#menu2" data-href-target="menu">Menu-2</a></li>
              <li><a href="#menu3">Menu-3</a></li>
              <li><a href="#menu4">Menu-4</a></li>
              <li><a href="#menu5">Menu-5</a></li>
              <li><a href="#menu6">Menu-6</a></li>
              <li><a href="#menu7">Menu-7</a></li>
              <li><a href="#menu8">Menu-8</a></li>
              <li><a href="#menu9">Menu-9</a></li>
              <li><a href="#menu10">Menu-10</a></li>
              <li><a href="#menu11">Menu-11</a></li>
              <li><a href="#menu12">Menu-12</a></li>
              <li><a href="#menu13">Menu-13</a></li>
              <li><a href="#menu14">Menu-14</a></li>
              <li><a href="#menu15">Menu-15</a></li>
              <li><a href="#menu16">Menu-16</a></li>
              <li><a href="#menu17">Menu-17</a></li>
              <li><a href="#menu18">Menu-18</a></li>
              <li><a href="#menu19">Menu-19</a></li>
              <li><a href="#menu20">Menu-20</a></li>
            </ul>
          </div>
        </div>
      </div>
    </section>

レイアウトの骨組みのページとメニューページ、コンテンツページの3つに分割しました。
次に、初期表示の時に、このメニューページとコンテンツページを読み込みましょう。

  • sample.js
var app = {};
app.init = (function() {
	return function() {
		$('#contentBody').html($('#main').find('div[class=ipad-content-body]').html());
		$('#contentHeader h1').text('content');
		$('#menuBody').html($('#menu').find('div[class=ipad-menu-body]').html());
		$('#menuHeader h1').text('menu');
		// jQueryMobileのスタイル設定を行う
		$('#index').page();
	};
})();
$(function() {
	app.init();
});

これで初期表示時に以前までの画面を表示することが出来ました。

メニュー部分を切り替える

メニュー側のリンクやボタンを押された場合のイベントを定義しましょう。

  • sample.js
app.loadContentBody = (function() {
	return function(title, page) {
		var html = $(page).find('div[class=ipad-content-body]').html();
		$('#contentBody').html(html);
		$('#contentHeader h1').text(title);
		// 読み込む場合は一度destroyする必要がある
		$('#index').page('destroy').page();
	};
})();
app.loadMenuBody = (function() {
	return function(title, page) {
		var html = $(page).find('div[class=ipad-menu-body]').html();
		$('#menuBody').html(html);
		$('#menuHeader h1').text(title);
		// 読み込む場合は一度destroyする必要がある
		$('#index').page('destroy').page();
	};
})();

$(function() {
	app.init();
	$('#menuBody a').live('click', function(ev) {
		var target = $(this);
		// data-href-targetがmenuの場合はメニューが切り替わるようにする
		var hrefTarget = target.data('href-target');
		var title = target.text();
		var href = target.attr('href');
		if (hrefTarget === 'menu') {
			if (href && href !== '#') {
				// メニューを切り替える処理
				app.loadMenuBody(title, target.attr('href'));
				return false;
			}
		} else {
			if (href && href !== '#') {
				// コンテンツを切り替える処理
				app.loadContentBody(title, target.attr('href'));
				return false;
			}
		}
	});
});

動的にコンテンツを切り替えるので、 jQuery.click()を使うのではなく、liveを使ってDOMが生成された時に適用されるようにします。
リンクにdata-href-target="menu"の場合はメニューが切り替わるように、それ以外の場合はコンテンツが切り替わるようにします。現在はこの実装ですが、別画面に遷移することもあると思いますので、後で修正するようにしましょう。
あとは遷移先の画面ですね。適当に作りましょう。

  • sample.html
    <section id="menu1" data-role="page">
      <div class="ui-grid-a ipad-grid">
        <div class="ui-block-b ipad-content-block">
          <div data-role="content" class="ipad-content-body">
            <ul data-role="listview">
              <li>aaaa</li>
              <li>aaaa</li>
              <li>aaaa</li>
              <li>aaaa</li>
              <li>aaaa</li>
            </ul>
          </div>
        </div>
      </div>
    </section>
    <section id="menu2" data-role="page">
      <div class="ui-grid-a ipad-grid">
        <div class="ui-block-a ipad-menu-block">
          <div data-role="content" class="ipad-menu-body">
            <ul data-role="listview">
              <li><a href="#submenu1">SubMenu-1</a></li>
              <li><a href="#submenu2" data-href-target="menu">SubMenu-2</a></li>
              <li><a href="#submenu3">SubMenu-3</a></li>
              <li><a href="#submenu4">SubMenu-4</a></li>
              <li><a href="#submenu5">SubMenu-5</a></li>
              <li><a href="#submenu6">SubMenu-6</a></li>
            </ul>
          </div>
        </div>
      </div>
    </section>
    <section id="submenu1" data-role="page">
      <div class="ui-grid-a ipad-grid">
        <div class="ui-block-b ipad-block">
          <div data-role="content" class="ipad-content-body">
            SubMenu1 Content
          </div>
        </div>
      </div>
    </section>
    <section id="submenu2" data-role="page">
      <div class="ui-grid-a ipad-grid">
        <div class="ui-block-a ipad-block">
          <div data-role="content" class="ipad-menu-body">
            SubMenu2 Menu
          </div>
        </div>
      </div>
    </section>

出来た感じですね。次回はメニューのヘッダに戻るボタンを作りたいと思います。