7
5

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

Ruby on Rails 4 - bootstrap3+simple_form+datetimepicker

Last updated at Posted at 2016-01-22

simple_form と bootstrap3は導入されているという前提で進めます。

#Gemの追加

Bootstrap 3 Datepickerのマニュアルの通り

Gemfile
gem 'momentjs-rails', '>= 2.9.0'
gem 'bootstrap3-datetimepicker-rails', '~> 4.14.30'

を追加します。

追記したあと、bundle installをしましょう。

#inilinitializers設定

まず、/config/inilinitializers/に下記の設定ファイルを作ります

date_time_picker_input.rbを作成。

  • サンプルソース1
/config/inilinitializers/date_time_picker_input.rb
class DateTimePickerInput < SimpleForm::Inputs::Base
  def input
    # classにform_datetimeを指定することで、coffee scriptの方で要素指定に使用されています。(見た目は変わりません)
    template.content_tag(:div, class: 'input-group date form_datetime') do
      template.concat @builder.text_field(attribute_name, input_html_options)
      template.concat span_table
    end
  end

  def input_html_options
    # classには配列で複数の設定が入ってくるので、それに'form-control'を追加してあげる
    # 単純にmergeしてしまうと、前のものが消えて'form-control'のみになってしまいバグる
    classes = (super[:class] || [])
    classes << :'form-control'
    # viewで指定された'readonly'がある場合は上書きしないようにする
    # カレンダーからの入力のみを許可したい場合は readonly: true を設定
    options = super
    options.merge({class: classes})
    options.merge({readonly: false}) unless options[:readonly]
    options
  end


  def span_table
    template.content_tag(:span, class: 'input-group-addon') do
      template.concat icon_table
    end
  end

  def icon_table
    "<span class='glyphicon glyphicon-calendar'></span>".html_safe
  end

end
  • input_html_optionsメソッドでは**readonly: falseを指定していますが、カレンダーからの入力のみを許可したい場合はreadonly: true**を設定してください。
  • inputメソッドの最初でclassに**form_datetime**を設定していますが、これを使用してcoffee script側で要素指定しています。

参考サイトのsimple_form Wiki - Custom inputs examplesでは、下記のようになっています。

app/inputs/date_time_picker_input.rb
class DateTimePickerInput < SimpleForm::Inputs::Base
  def input
    template.content_tag(:div, class: 'input-group date form_datetime') do
      template.concat @builder.text_field(attribute_name, input_html_options)
      template.concat span_remove  # サンプルソース1では削除
      template.concat span_table
    end
  end

  def input_html_options
    super.merge({class: 'form-control', readonly: true})  # サンプルソース1では readonly: false に設定
  end

  # サンプルソース1では削除
  def span_remove
    template.content_tag(:span, class: 'input-group-addon') do
      template.concat icon_remove
    end
  end

  def span_table
    template.content_tag(:span, class: 'input-group-addon') do
      template.concat icon_table
    end
  end

  # サンプルソース1では削除
  def icon_remove
    "<i class='glyphicon glyphicon-remove'></i>".html_safe
  end

  def icon_table
    "<i class='glyphicon glyphicon-th'></i>".html_safe # サンプルソース1では<span>タグに変更
  end

end
  • 上記で紹介したサンプルソース1ではspan_removeicon_removeを削除。
  • icon_tableメソッドで追加しているHTMLタグを<i>から<span>へ変更。
  • アイコンのクラス指定をglyphicon-thからglyphicon-calendarに変更

これは、Bootstrap 3 Datepicker v4 Docsにあるサンプルソースに合わせるためです。

また、/app/inputs/配下にdate_time_picker_input.rbを作成していますが、サンプルソース1では、/config/inilinitializers/配下に作成しています。 初期設定で行うべき処理に思うので/config/inilinitializers/に移動しました。

#coffee scriptサンプル

24時間表記で日本にロケールを合わせる場合は下記のようにします。

init_datetimepciker = ->
  (->
    $(".form_datetime").datetimepicker
      locale: "ja"
      format: "YYYY/MM/DD HH:mm"
      sideBySide: true
  )

$(document).ready ->
  init_datetimepciker()

$(document).on "ready page:load", init_datetimepciker()
  • sideBySide: trueを指定するのは見た目が私はこちらのほうが好きなので、指定しています。
    ポップアップのカレンダーの見た目が変わるだけです。

  • turbolinksを使用していると、ページ遷移時にcoffee scriptが動作しない(リロードすれば動作する状態)なので"ready page:load"時も実行するよう設定しています。

  • $(".form_datetime")で要素を選択しています。classform_datetimeが指定されている要素全てが対象になるので、cssの方で重ならないよう注意してください。class名変更などカスタマイズしたい場合は/config/inilinitializers/date_time_picker_input.rb(rubyコード)と合わせて調整する必要があります。


参考サイトのsimple_form Wiki - Custom inputs examplesでは、下記のようになっています。

$(document).ready ->
  $('.form_datetime').datetimepicker({
    autoclose: true,
    todayBtn: true,
    pickerPosition: "bottom-left",
    format: 'mm-dd-yyyy hh:ii'
  });

#view側の呼び出し

f.input :my_date, as: :date_time_picker

#参考URL

Bootstrap 3 Datepicker v4 Docs

simple_form Wiki - Custom inputs examples

#まとめ(忙しい人のためのやること一覧)

1. Install

Gemfile
gem 'momentjs-rails', '>= 2.9.0'
gem 'bootstrap3-datetimepicker-rails', '~> 4.14.30'

を追加します。

追記したあと、bundle install


2. DateTimePickerInputクラス追加

/config/inilinitializers/date_time_picker_input.rb
class DateTimePickerInput < SimpleForm::Inputs::Base
  def input
    template.content_tag(:div, class: 'input-group date form_datetime') do
      template.concat @builder.text_field(attribute_name, input_html_options)
      template.concat span_table
    end
  end

  def input_html_options
    # classには配列で複数の設定が入ってくるので、それに'form-control'を追加してあげる
    # 単純にmergeしてしまうと、前のものが消えて'form-control'のみになってしまいバグる
    classes = (super[:class] || [])
    classes << :'form-control'
    # viewで指定された'readonly'がある場合は上書きしないようにする
    # カレンダーからの入力のみを許可したい場合は readonly: true を設定
    options = super
    options.merge({class: classes})
    options.merge({readonly: false}) unless options[:readonly]
    options
  end


  def span_table
    template.content_tag(:span, class: 'input-group-addon') do
      template.concat icon_table
    end
  end

  def icon_table
    "<span class='glyphicon glyphicon-calendar'></span>".html_safe
  end

end

を追加。


3. coffeeスクリプトを追加

init_datetimepciker = ->
  (->
    $(".form_datetime").datetimepicker
      locale: "ja"
      format: "YYYY/MM/DD HH:mm"
      sideBySide: true
  )

$(document).ready ->
  init_datetimepciker()

$(document).on "ready page:load", init_datetimepciker()

を追加。


※補足
javascriptで指定したい場合はcoffee scriptjavascriptの相互変換は下記サイトでできます。
http://js2coffee.thomaskalka.de/


4. view側の呼び出し

as: :date_time_pickerを指定して呼び出し。

f.input :my_date, as: :date_time_picker
7
5
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
7
5

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?