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

Rails Webook

自社のECを開発している会社で働いています。Rails情報やサービスを成長させる方法を書いていきます

RailsにTwitter Bootstrapの導入と簡易な使い方

Rails gem UI/UX

f:id:nipe880324:20141215222604j:plain:w420

RailsでTwitter Bootstrap 3のインストール方法を説明します。
また、Bootstrapのエラーメッセージの表示、ナビゲーションバーの追加、simple_formとの連携などの使い方を説明します。

動作確認

  • Rails 4.1
  • twitter-bootstrap-rails 3.2.0

目次

  1. Railsプロジェクトの作成
  2. Twitter Bootstrapのインストール方法1
  3. Twitter Bootstrapのインストール方法2
  4. カスタマイズ(ViewファイルへのTwitter Bootstrapの適用)
  5. カスタマイズ(サクセス、エラーメッセージの表示)
  6. カスタマイズ(simple_formとの連携: フォーム上でのエラーメッセージの表示)
  7. カスタマイズ(Sidebarの追加)
  8. カスタマイズ(NavigationBarの追加)

1. Railsプロジェクトの作成

まずは、Railsプロジェクトを作成し、ScaffoldでProductを作成します。

rails new twitter-bootstrap
5||<

次に確認用にデータをScaffoldを実行します。
>||
rails g scaffold Product name:string price:integer
rake db:migrate

rails sでサーバーを起動し現在の画面を確認しましょう。
データを3件入れました。

f:id:nipe880324:20141215222616j:plain:w420




2. Twitter Bootstrapのインストール方法1

インストール方法1では、Gemを使って簡易にBootstrapを導入していきます。

Gemfileに下記の3つのgemを追加します。

# Gemfile

gem 'therubyracer' # javascript runtime。lessをコンパイルするために必要
gem 'less-rails' # Railsでlessを使えるようにする。Bootstrapがlessで書かれているため
gem 'twitter-bootstrap-rails' # Bootstrapの本体

そして、gemをインストールします。

bundle insatll

では、Railsプロジェクトにbootstrapのファイルを追加します。

$ rails g bootstrap:install
      insert  app/assets/javascripts/application.js
      create  app/assets/javascripts/bootstrap.js.coffee
      create  app/assets/stylesheets/bootstrap_and_overrides.css.less
      create  config/locales/en.bootstrap.yml
        gsub  app/assets/stylesheets/application.css
        gsub  app/assets/stylesheets/application.css

これで、RailsにTwitter Bootstrapを導入できました。
rails serverで画面を確認してみましょう。
上の画面と比べると、それっぽくなっているのではないでしょうか。

f:id:nipe880324:20141215222635j:plain:w420




3. Twitter Bootstrapのインストール方法2

インストール方法2では、LessやGemとかよく分からないという方に、
Bootstrpeの公式ページからファイルをダウンロードし、Railsに追加する方法を説明します。

まずBootstrapのダウンロードページからBootstrapのソースコードをダウンロードします。

そして、解凍し、dist内の下記のファイルをRailsプロジェクトにコピーします。

コピー元コピー先
dist/css/bootstrap.min.cssvendor/assets/stylesheets/.
dist/js/bootstrap.min.jsvendor/assets/javascripts/.
dist/fontsvendor/assets/.

そして、Railsに追加したbootstrapを読み込ませるようにします。

# app/assets/javascripts/application.js

...
//
//= require jquery
//= require jquery_ujs
//= require bootstrap.min
//= require turbolinks
//= require_tree .
#app/assets/stylesheets/application.css

 ...
 *
 *= require bootstrap.min
 *= require_tree .
 *= require_self
 */


4. カスタマイズ(ViewファイルへのTwitter Bootstrapの適用)

では、ここからはカスタマイズをして行きましょう。
基本的に、それぞれのカスタマイズ項目は独立していますが、少し依存関係がある箇所もありますのでご注意ください。

現在の画面は、まだまだTwitter Bootstrapさがでていないですね。

f:id:nipe880324:20141215222635j:plain:w420



これは、適切なTwitter Bootstrap用のclass値が設定されていないためです。
そのため、Twitter Bootstrapを適用させます。ソースコードを変更してくれます。
下記のファイルに何か修正を加えていた場合は上書きするかどうか聞かれます。
※ インストール方法2で入れた場合は、このコマンドは使えません。

$ rails g bootstrap:themed Products
       force  app/views/products/index.html.erb
       force  app/views/products/new.html.erb
       force  app/views/products/edit.html.erb
       force  app/views/products/_form.html.erb
       force  app/views/products/show.html.erb


では、サーバを起動して、画面を確認してみましょう。
一気にそれっぽい雰囲気がでてきましたね。

f:id:nipe880324:20141215222722j:plain:w420


先ほどの少しだけソースコードを見てみましょう。
table table-stripedbtn btn-primaryなどTwitter Bootstrapのclass値が指定されていますね。
実際にどのようなclass値が使えるかは公式ドキュメントを参照して下さい。

# app/views/products/index.html.erb
...
<table class="table table-striped">
   ...
</table>

<%= link_to t('.new', :default => t("helpers.links.new")),
            new_product_path,
            :class => 'btn btn-primary' %>


5. カスタマイズ(サクセス、エラーメッセージの表示)

実は、現在2つ問題があります。
・データを作成/更新したときにサクセスメッセージとエラーが発生したときにエラーメッセージが表示されない
・フォームでエラーメッセージ表示されない

1つ目について、ここで解消します。2つ目は次の「simple_formとの連携」で解消します。
サクセスメッセージやエラーメッセージは、flash[:notice]flash[:error]のどちらかに入ってきます。
また、Twitter Bootstrapでは、アラートは、alert alert-successalert alert-errorで表示させます。
そのため、下記のようなコードを追加します。

# app/views/layouts/application.html.erb
  ...
<body>
<% flash.each do |name, msg| %>
  <div class="alert alert-<%= name == "notice" ? "success" : "error" %>">
    <a class="close" data-dismiss="alert">×</a> <!-- アラートダイアログに×ボタンをつける -->
    <%= msg %>
  </div>
<% end %>

<%= yield %>

</body>
</html>

では、サーバを起動し、画面を確認します。
データを登録すると上記にサクセスメッセージが表示されていますね。

f:id:nipe880324:20141215222742j:plain:w420




6. カスタマイズ(simple_formとの連携: フォーム上でのエラーメッセージの表示)

では、もう1つの問題の、フォーム上でエラーメッセージを表示しましょう。
まず、エラーメッセージを出すために、ModelにValidationを追加します。

# app/models/product.rb
class Product < ActiveRecord::Base
  validates :name,  presence: true
  validates :price, presence: true
end

次に、simple_formを導入します。

# Gemfile
gem 'simple_form'

そして、gemをインストールします。

$ bundle install
$ rails g simple_form:install --bootstrap
      create  config/initializers/simple_form.rb
      create  config/initializers/simple_form_bootstrap.rb
       exist  config/locales
      create  config/locales/simple_form.en.yml
      create  lib/templates/erb/scaffold/_form.html.erb
===============================================================================

  Be sure to have a copy of the Bootstrap stylesheet available on your
  application, you can get it on http://twitter.github.com/bootstrap.

  Inside your views, use the 'simple_form_for' with one of the Bootstrap form
  classes, '.form-horizontal', '.form-inline', '.form-search' or
  '.form-vertical', as the following:

    = simple_form_for(@user, html: {class: 'form-horizontal' }) do |form|

===============================================================================

フォームをsimple_formで書き換えます。

# app/views/products/_form.html.erb
<%= simple_form_for @product, :html => { :class => 'form-horizontal' } do |f| %>
  <%= f.input :name %>
  <%= f.input :price %>

  <div class="form-actions">
    <%= f.submit nil, :class => 'btn btn-primary' %>
    <%= link_to t('.cancel', :default => t("helpers.links.cancel")),
                products_path, :class => 'btn' %>
  </div>
<% end %>


これで、完成です。画面を開き、エラーメッセージを表示させましょう。
f:id:nipe880324:20141215222817j:plain:w420


もし、simple_formについて、より詳しく知りたい場合は、Railsのgemフォームコードをすっきりさせる simple_form - Rails Webookを参照ください。




7. カスタマイズ(Sidebarの追加)

サイドバーを追加して行きますが、Twitter Bootstrapでは、

  • fixed:940pxで横幅が要素の位置が固定される
  • fluid:ブラウザサイズに応じてと要素が広がる

の2つがあります。

今回は、fixedでサイドバーを追加して行きます。
Twitter Bootstrapでは、下記のような構成でレイアウトを作っていきます。

...
<body>
<div class="container"> <!-- container で全体を囲む -->
  <div class="row"> <!-- row で列を作る -->
    <div class="span8"> <!-- 12分割のグリッドシステムの8を使用 -->
      ... メインコンンツを記載 ...
    </div>
    <div class="span4"> <!-- 12分割のグリッドシステムの4を使用 -->
      ... サイドバーコンンツを記載 ...
    </div>
  </div>
</div>
</body>


では、上記の構成を全体のレイアウトファイルに適用させましょう。

# app/views/layouts/application.html.erb
....
<body>
<div class="container">
  <div class="row">
    <% flash.each do |name, msg| %>
      <div class="alert alert-<%= name == "notice" ? "success" : "error" %>">
        <a class="close" data-dismiss="alert">×</a>
        <%= msg %>
      </div>
    <% end %>
    <div class="span8">
      <%= yield %>
    </div>
    <div class="span4">
      <h2>Side bar</h2>
      <p>Lorem ipsum dolor sit amet, consectetur adipisicing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum.</p>
    </div>
  </div>
</div>

</body>
</html>


では、サイドバーが追加されたことがわかると思います。
f:id:nipe880324:20141215222844j:plain:w420


ちなみに、ブラウザの横幅を狭めていくと、サイドバーが下側に移動すると思います。既に、レスポンシブデザインが適用されている証拠です。




8. カスタマイズ(NavigationBarの追加)

可読性を上げるために、headerを外部ファイル化します。
renderメソッドでheaderを呼び出ます。

# app/views/layouts/application.html.erb
...
<body>
<%= render 'layouts/header' %>
<div class="container">
  <div class="row">
    <div class="span8">
...


では、headerファイルを作ります。
Twitter BootstrapのNavigation Barの項目を参考に作成します。

# app/views/layouts/_haeder.html.erb
<header>
  <div class="navbar navbar-default" role="navigation">
    <div class="navbar-inner">
      <div class="container">
        <a class="btn btn-navbar" data-toggle="collapse" data-target=".nav-collapse">
          <span class="icon-bar"></span>
          <span class="icon-bar"></span>
          <span class="icon-bar"></span>
        </a>
        <a class="brand" href="#">Some Store</a>
        <div class="nav-collapse">
          <ul class="nav">
            <li><%= link_to "Products", products_path %></li>
            <li><%= link_to "Price List" %></li>
            <li><%= link_to "Contact Us" %></li>
            <li><%= link_to "Cart" %></li>
          </ul>
        </div>
      </div>
    </div>
  </div>
</header>


また、IEの古いバージョンだとHTML5が上手く動かないので、それに対処するコードを追加します。
さらに、モバイル端末での表示が良くするために、viewportを指定します。

# app/views/layouts/application.html.erb
...
<head>
  <title>TwitterBootstrap</title>
  <%= stylesheet_link_tag    'application', media: 'all', 'data-turbolinks-track' => true %>
  <%= javascript_include_tag 'application', 'data-turbolinks-track' => true %>
  <%= csrf_meta_tags %>
  <!--[if lt IE 9]>
    <script src="http://html5shim.googlecode.com/svn/trunk/html5.js" type="text/javascript"></script>
  <![endif]-->
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
</head>
...


では、画面にナビゲーションバーが表示されていることを確認しましょう。
f:id:nipe880324:20141215222917j:plain:w420