スマートフォンアプリとタブレットアプリでは、求められるUI/UXが若干異なります。タブレットアプリでは、より多くの情報が一画面中に表示できるのが魅力です。スマートフォンがユーザー向けで簡単に入力・閲覧できるアプリが向いているのに対して、タブレットアプリでは管理画面などデータが多い表示に向いています。
そこで今回はタブレットアプリに向いたUI/UXを提供するために、Bootstrapを使ったUIを紹介します。
Bootstrapの導入
BootstrapはCSS、JavaScriptファイルを読み込めば利用できます。基本形は以下のようになります。
<!doctype html>
<html lang="ja">
<head>
<!-- 文字エンコーディングをUTF-8に設定 -->
<meta charset="utf-8">
<!-- ビューポートの設定。画面幅に合わせて表示を最適化 -->
<meta name="viewport" content="width=device-width, initial-scale=1">
<!-- ページのタイトル -->
<title>Bootstrap demo</title>
<!-- Bootstrap CSSファイルの読み込み -->
<link href="https://cdn.jsdelivr.net/npm/bootstrap@5.3.0/dist/css/bootstrap.min.css" rel="stylesheet" integrity="sha384-9ndCyUaIbzAi2FUVXJi0CjmCapSmO7SnpJef0486qhLnuZ2cdeRhO02iuK6FUUVM" crossorigin="anonymous">
</head>
<body>
<!-- ページの見出し -->
<h1>Hello, world!</h1>
<!-- Bootstrap JavaScriptファイルの読み込み -->
<script src="https://cdn.jsdelivr.net/npm/bootstrap@5.3.0/dist/js/bootstrap.bundle.min.js" integrity="sha384-geWF76RCwLtnZ8qwWowPQNguL3RmwHVBC9FhGdlKrxdiJJigb/j/68SIy3Te4Bkz" crossorigin="anonymous"></script>
</body>
</html>
ここにMonacaアプリとして必要な情報を盛り込むと以下のようになります。
<!doctype html>
<html lang="ja">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>Bootstrap demo</title>
<meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1, user-scalable=no">
<meta http-equiv="Content-Security-Policy" content="default-src * data: gap: content: https://ssl.gstatic.com; style-src * "unsafe-inline"; script-src * "unsafe-inline" "unsafe-eval"">
<script src="components/loader.js"></script>
<link rel="stylesheet" href="components/loader.css">
<link href="https://cdn.jsdelivr.net/npm/bootstrap@5.3.0/dist/css/bootstrap.min.css" rel="stylesheet" integrity="sha384-9ndCyUaIbzAi2FUVXJi0CjmCapSmO7SnpJef0486qhLnuZ2cdeRhO02iuK6FUUVM" crossorigin="anonymous">
<link href="css/styles.css" rel="stylesheet" />
</head>
<body>
<h1>Hello, world!</h1>
<script src="https://cdn.jsdelivr.net/npm/bootstrap@5.3.0/dist/js/bootstrap.bundle.min.js" integrity="sha384-geWF76RCwLtnZ8qwWowPQNguL3RmwHVBC9FhGdlKrxdiJJigb/j/68SIy3Te4Bkz" crossorigin="anonymous"></script>
</body>
</html>
サンプル
今回はSB Admin - Free Bootstrap Admin Template - Start Bootstrapをベースに進めています。
サイドメニュー
タブレットを横向きにすると幅広く使えるので、左側にメニューを表示することが多いです。Bootstrapを使えば、以下のようにしてサイドメニューを簡単に作成できます。
利用するコンポーネントや機能は以下の通りです。メニューの折り畳みにアコーディオンを利用しています。
また、アイコンはFontawesomeを利用しています。
<body class="sb-nav-fixed">
<!-- ナビゲーションバー -->
<nav class="sb-topnav navbar navbar-expand navbar-dark bg-dark">
<!-- ナビゲーションバーのブランド -->
<a class="navbar-brand ps-3" href="index.html">Start Bootstrap</a>
<!-- サイドバーのトグルボタン -->
<button class="btn btn-link btn-sm order-1 order-lg-0 me-4 me-lg-0" id="sidebarToggle" href="#!">
<i class="fas fa-bars"></i>
</button>
</nav>
<!-- レイアウトのコンテナ -->
<div id="layoutSidenav">
<!-- サイドナビゲーション -->
<div id="layoutSidenav_nav">
<nav class="sb-sidenav accordion sb-sidenav-dark" id="sidenavAccordion">
<!-- サイドナビゲーションのメニュー -->
<div class="sb-sidenav-menu">
<div class="nav">
<!-- メニューのセクション: Core -->
<div class="sb-sidenav-menu-heading">Core</div>
<a class="nav-link" href="index.html">
<div class="sb-nav-link-icon"><i class="fas fa-tachometer-alt"></i></div>
Dashboard
</a>
<!-- メニューのセクション: Interface -->
<div class="sb-sidenav-menu-heading">Interface</div>
<!-- Layoutsのメニュー項目 -->
<a class="nav-link collapsed" href="#" data-bs-toggle="collapse" data-bs-target="#collapseLayouts" aria-expanded="false" aria-controls="collapseLayouts">
<div class="sb-nav-link-icon"><i class="fas fa-columns"></i></div>
Layouts
<div class="sb-sidenav-collapse-arrow"><i class="fas fa-angle-down"></i></div>
</a>
<!-- Layoutsのサブメニュー -->
<div class="collapse" id="collapseLayouts" aria-labelledby="headingOne" data-bs-parent="#sidenavAccordion">
<nav class="sb-sidenav-menu-nested nav">
<a class="nav-link" href="layout-static.html">Static Navigation</a>
<a class="nav-link" href="layout-sidenav-light.html">Light Sidenav</a>
</nav>
</div>
<!-- Pagesのメニュー項目 -->
<a class="nav-link collapsed" href="#" data-bs-toggle="collapse" data-bs-target="#collapsePages" aria-expanded="false" aria-controls="collapsePages">
<div class="sb-nav-link-icon"><i class="fas fa-book-open"></i></div>
Pages
<div class="sb-sidenav-collapse-arrow"><i class="fas fa-angle-down"></i></div>
</a>
<!-- Pagesのサブメニュー -->
<div class="collapse" id="collapsePages" aria-labelledby="headingTwo" data-bs-parent="#sidenavAccordion">
<nav class="sb-sidenav-menu-nested nav accordion" id="sidenavAccordionPages">
<!-- Authenticationのメニュー項目 -->
<a class="nav-link collapsed" href="#" data-bs-toggle="collapse" data-bs-target="#pagesCollapseAuth" aria-expanded="false" aria-controls="pagesCollapseAuth">
Authentication
<div class="sb-sidenav-collapse-arrow"><i class="fas fa-angle-down"></i></div>
</a>
<!-- Authenticationのサブメニュー -->
<div class="collapse" id="pagesCollapseAuth" aria-labelledby="headingOne" data-bs-parent="#sidenavAccordionPages">
<nav class="sb-sidenav-menu-nested nav">
<a class="nav-link" href="login.html">Login</a>
<a class="nav-link" href="register.html">Register</a>
<a class="nav-link" href="password.html">Forgot Password</a>
</nav>
</div>
<!-- Errorのメニュー項目 -->
<a class="nav-link collapsed" href="#" data-bs-toggle="collapse" data-bs-target="#pagesCollapseError" aria-expanded="false" aria-controls="pagesCollapseError">
Error
<div class="sb-sidenav-collapse-arrow"><i class="fas fa-angle-down"></i></div>
</a>
<!-- Errorのサブメニュー -->
<div class="collapse" id="pagesCollapseError" aria-labelledby="headingOne" data-bs-parent="#sidenavAccordionPages">
<nav class="sb-sidenav-menu-nested nav">
<a class="nav-link" href="401.html">401 Page</a>
<a class="nav-link" href="404.html">404 Page</a>
<a class="nav-link" href="500.html">500 Page</a>
</nav>
</div>
</nav>
</div>
<!-- メニューのセクション: Addons -->
<div class="sb-sidenav-menu-heading">Addons</div>
<a class="nav-link" href="charts.html">
<div class="sb-nav-link-icon"><i class="fas fa-chart-area"></i></div>
Charts
</a>
<a class="nav-link" href="tables.html">
<div class="sb-nav-link-icon"><i class="fas fa-table"></i></div>
Tables
</a>
</div>
</div>
<!-- サイドナビゲーションのフッター -->
<div class="sb-sidenav-footer">
<div class="small">Logged in as:</div>
Start Bootstrap
</div>
</nav>
</div>
<!-- 省略 -->
</div>
</body>
また、このままでは動的な部分は動かないので、JavaScriptを以下のように記述します。クラスを変えることで、アコーディオンの開閉を制御しています。また、localStorageを使って開閉状態を保存しています。
// Cordovaを使用している場合は"deviceready"イベント、そうでない場合は"DOMContentLoaded"イベントを待つ
const event = window.cordova ? "deviceready" : "DOMContentLoaded";
// 指定されたイベントが発生した時に実行される関数を登録
document.addEventListener(event, event => {
// "sidebarToggle"というIDを持つ要素を取得
const sidebarToggle = document.body.querySelector("#sidebarToggle");
// サイドバーのトグルボタンが存在しない場合は終了
if (!sidebarToggle) return;
// サイドバーのトグルボタンにクリックイベントのリスナーを追加
sidebarToggle.addEventListener("click", event => {
// ボタンのデフォルトの動作をキャンセル
event.preventDefault();
// <body>要素のクラスリストに"sb-sidenav-toggled"クラスを切り替えて、サイドバーの表示/非表示を切り替える
document.body.classList.toggle("sb-sidenav-toggled");
// サイドバーの状態をローカルストレージに保存
localStorage.setItem("sb|sidebar-toggle", document.body.classList.contains("sb-sidenav-toggled"));
});
});
カード型のコンポーネント
管理画面のUIでは、グラフや一覧などをコンポーネントとして表示することが多いです。Bootstrapを使えば、以下のようにしてカード型のコンポーネントを簡単に作成できます。
4つのコンポーネント
KPIなど、ダッシュボード中に集計された数値を表示する際に便利な形です。
<!-- カードを含む行 -->
<div class="row">
<!-- 最初の列(Primary Card) -->
<div class="col-xl-3 col-md-6">
<div class="card bg-primary text-white mb-4">
<div class="card-body">Primary Card</div>
<div class="card-footer d-flex align-items-center justify-content-between">
<a class="small text-white stretched-link" href="#">View Details</a>
<div class="small text-white"><i class="fas fa-angle-right"></i></div>
</div>
</div>
</div>
<!-- 2番目の列(Warning Card) -->
<div class="col-xl-3 col-md-6">
<div class="card bg-warning text-white mb-4">
<div class="card-body">Warning Card</div>
<div class="card-footer d-flex align-items-center justify-content-between">
<a class="small text-white stretched-link" href="#">View Details</a>
<div class="small text-white"><i class="fas fa-angle-right"></i></div>
</div>
</div>
</div>
<!-- 3番目の列(Success Card) -->
<div class="col-xl-3 col-md-6">
<div class="card bg-success text-white mb-4">
<div class="card-body">Success Card</div>
<div class="card-footer d-flex align-items-center justify-content-between">
<a class="small text-white stretched-link" href="#">View Details</a>
<div class="small text-white"><i class="fas fa-angle-right"></i></div>
</div>
</div>
</div>
<!-- 4番目の列(Danger Card) -->
<div class="col-xl-3 col-md-6">
<div class="card bg-danger text-white mb-4">
<div class="card-body">Danger Card</div>
<div class="card-footer d-flex align-items-center justify-content-between">
<a class="small text-white stretched-link" href="#">View Details</a>
<div class="small text-white"><i class="fas fa-angle-right"></i></div>
</div>
</div>
</div>
</div>
グラフ
グラフを表示するカードです。なお、グラフはChart.jsを使っています。
<!-- グラフを表示するカードのコンテナ -->
<div class="row">
<!-- 左側のカード: エリアチャート -->
<div class="col-xl-6">
<div class="card mb-4">
<div class="card-header">
<i class="fas fa-chart-area me-1"></i>
Area Chart Example
</div>
<div class="card-body">
<!-- エリアチャートのキャンバス -->
<canvas id="myAreaChart" width="100%" height="40"></canvas>
</div>
</div>
</div>
<!-- 右側のカード: 棒グラフ -->
<div class="col-xl-6">
<div class="card mb-4">
<div class="card-header">
<i class="fas fa-chart-bar me-1"></i>
Bar Chart Example
</div>
<div class="card-body">
<!-- 棒グラフのキャンバス -->
<canvas id="myBarChart" width="100%" height="40"></canvas>
</div>
</div>
</div>
</div>
このコードでは、rowクラスを持つ<div>
要素が2つのカードを含んでいます。それぞれのカードはcol-xl-6クラスを持つ<div>
要素によって分割され、左側にエリアチャート、右側に棒グラフが表示されます。
各カードには、cardクラスを持つ<div>
要素があり、その中にcard-headerとcard-bodyクラスを持つ<div>
要素が含まれています。card-headerにはグラフのタイトルとアイコンが表示され、card-bodyにはグラフを描画するための<canvas>
要素が含まれています。
グラフの描画には、Chart.jsライブラリを使用しています。<canvas>
要素のid属性を使って、JavaScript側からグラフを操作します。
データ一覧系
データの一覧はtableタグを使います。Bootstrapであれば、table表示も綺麗にできます。
<!-- データ一覧を表示するカード -->
<div class="card mb-4">
<!-- カードのヘッダー -->
<div class="card-header">
<!-- ヘッダーのアイコン -->
<i class="fas fa-table me-1"></i>
<!-- ヘッダーのタイトル -->
DataTable Example
</div>
<!-- カードの本体 -->
<div class="card-body">
<!-- データ一覧を表示するテーブル -->
<table id="datatablesSimple">
<!-- テーブルのヘッダー -->
<thead>
<tr>
<th>Name</th>
<th>Position</th>
<th>Office</th>
<th>Age</th>
<th>Start date</th>
<th>Salary</th>
</tr>
</thead>
<!-- テーブルの本体 -->
<tbody>
<!-- データの行 -->
<tr>
<td>Tiger Nixon</td>
<td>System Architect</td>
<td>Edinburgh</td>
<td>61</td>
<td>2011/04/25</td>
<td>$320,800</td>
</tr>
<!-- 以下省略 -->
</tbody>
</table>
</div>
</div>
まとめ
サイドメニューとカード型コンポーネントを組み合わせることで、管理UIとしての見栄えを良くできるでしょう。Bootstrapを使えば、簡単に実装できるので、ぜひ活用してみてください。
今回試したSB Adminには、ログインやダーク/ライトレイアウトなど参考になりそうなUIが多数用意されています。こうしたテンプレートをベースにすれば、アプリ開発の効率化にもつながるでしょう。