【Rails】セレクトボックスを作る方法と注意点【f.select】

エンジニア|ポートフォリオ
新人

セレクトボックスの使い方について知りたいな。

でも、なんか難しそう。

今回の記事は上記のような方におすすめ。

今回の記事では、Railsでセレクトボックスを作る方法について…Rails初心者でもわかるよう、わかりやすく解説いたします!

Railsでセレクトボックスを作る方法はいくつかあります。その中でも簡単な方法をご紹介します!モデルとの紐づけも必要みたいだし、Railsでのセレクトボックスの作り方って難しそう、と苦手意識を持つ方にもおすすめの記事です!

エンジニア|ポートフォリオ
新人

間違っている箇所あったらコメントで教えてね。

本記事の内容

なおこの記事は3分で読める内容です。

rails:セレクトボックスとは?

railsのセレクトボックス関連のメソッドを使用すれば、入力フォームにセレクトボックスを追加できます。

また、セレクトボックスの作成方法はいくつかありますが、それぞれ指定できる項目なども異なるため、使い方には注意が必要です。

作成方法①:select メソッド

おすすめ度
3.5

select メソッドを使ったセレクトボックスの構文は下記です。

select(オブジェクト名, オプションタグの要素(配列 or ハッシュ), オプション, HTMLオプション)

まず、コントローラーでselect に渡す要素を準備する必要があります。どのような方法でも良いですが、例として下記のような取得方法があるでしょう。

@users = User.pluck(:name, :id)
# => [["A太郎", 1], ["B太郎", 2], ["C太郎", 3]]

@users = User.all.map { |user| [ user.name, user.id ] }
# => [["A太郎", 1], ["B太郎", 2], ["C太郎", 3]]

ビューに渡す値が、[[“表示するHTML”, 渡すvalue値], [“表示するHTML”, 渡すvalue値], [“表示するHTML”, 渡すvalue値]…]の形式になるように値を取得します。配列はもちろん、ハッシュ形式でも問題ありません。

ビュー側は以下のように書きます。

<%= f.select :id, @users, {prompt: "選択してください"}, :class => 'form-control', :id => 'user_id' %>

また、オプションを指定することもできます。

オプション説明
:multiple複数選択を有効にするか
:disabled選択無効化 ★よく使う
:include_blank先頭に空の要素を追加
:prompt選択されていない時に表示される文字 ★よく使う
セレクトボックス「select」に指定できるオプション

HTML関連のオプションも指定可能です。こちらは色々種類ありますね。詳細は、こちらのRailsドキュメントをご覧ください。

オプション説明
:acceptフォームで受付可能なMIMEタイプ
:readonlyフォームの内容変更禁止 ★よく使う
(デフォルト値を設定して変更したくない場合に使う)
:tabindexTabキーによる入力欄の移動順
:id要素固有の識別子 ★よく使う
:classクラス名 ★よく使う
セレクトボックス「select」に指定できるHTMLオプション

作成方法②:select_tag メソッド

おすすめ度
2.5

select_tag メソッドを使ったセレクトボックスの構文は下記です。

select_tag(要素名, オプションタグを表す文字列, オプション, HTMLオプション, イベント属性)

select メソッドとの一番の違いは、「オプションタグを表す文字列」です。つまりはセレクトボックスのoptionに指定する文字を「文字列そのまま」記述する必要があります。例として下記を「タグを表す文字列」にそのままズラーっと指定します。

<option value="1">A太郎</option><option value="2">B太郎</option>...

ただし、HTMLオプションをそのまま記述するのは冗長です。保守の観点からもあまりよろしくありませんよね。そこで、実際には、ズラーっと書くかわりに「options_for_select」メソッドや「options_from_collection_for_select」メソッドを使用することが多いです。

<%= f.select_tag :id, options_from_collection_for_select( User.all, :id, :name ), { prompt: "選択してください" } %>

「options_from_collection_for_select」についての詳細は、options_from_collection_for_selectを理解する(プルダウンリストを簡単に作りたい)[Rails]をご覧ください。上記のHTML結果ソースがこんな感じです↓

<select name="id" id="id">
  <option value="1">A太郎</option>
  <option value="2">B太郎</option>
</select>

また、オプションを指定することもできます。

select_tagのオプション

オプション説明
:multiple複数選択を有効にするか
:disabled選択無効化 ★よく使う
:include_blank先頭に空の要素を追加
:prompt選択されていない時に表示される文字 ★よく使う
セレクトボックス「select_tag」に指定できるオプション

HTML関連のオプションも指定可能です。こちらは色々種類ありますね。詳細は、こちらのRailsドキュメントをご覧ください。

select_tagのHTMLオプション

オプション説明
:acceptフォームで受付可能なMIMEタイプ
:readonlyフォームの内容変更禁止 ★よく使う
(デフォルト値を設定して変更したくない場合に使う)
:tabindexTabキーによる入力欄の移動順
:id要素固有の識別子 ★よく使う
:classクラス名 ★よく使う
セレクトボックス「select_tag」に指定できるHTMLオプション

select_tagのイベント属性

オプション説明
:onclickクリックされた時
:ondblclickダブルクリックされた時
:onfocusフォーカスされた時
セレクトボックス「select_tag」に指定できるイベント属性

作成方法③:collection_select メソッド【おすすめ】

おすすめ度
4.5

collection_select メソッドを使ったセレクトボックスの構文は下記です。

collection_select(オブジェクト名, メソッド名, 要素の配列, value属性の項目, テキストの項目, オプション, HTMLオプション, イベント属性)

select メソッドの際は、DBから取得したデータを select 用に加工したりしていました。しかし「collection_select」メソッドは加工することなく、セレクトボックスを簡単に作成できます!

<%= f.collection_select :id, User.all, :id, :name, {prompt: "選択してください"}, :class => 'form-control', :id => 'user_id' %>

データの整形や別メソッドと組み合わせる必要があるなどの面倒さがなく、簡単に記述できるので一番おすすめの方法です。

collection_selectのオプション

オプション説明
:selected選択されたオプション
:disabled選択無効化 ★よく使う
:include_blank先頭に空の要素を追加
:prompt選択されていない時に表示される文字 ★よく使う
セレクトボックス「collection_select」に指定できるオプション

HTML関連のオプションも指定可能です。こちらは色々種類ありますね。詳細は、こちらのRailsドキュメントをご覧ください。

collection_selectのHTMLオプション

オプション説明
:sizeフォームの幅
:maxlength入力フィールドに入力可能な最大文字数
:tabindexTabキーによる入力欄の移動順
:id要素固有の識別子 ★よく使う
:classクラス名 ★よく使う
セレクトボックス「collection_select」に指定できるHTMLオプション

collection_selectのイベント属性

オプション説明
:onclickクリックされた時
:ondblclickダブルクリックされた時
:onfocusフォーカスされた時
セレクトボックス「collection_select」に指定できるイベント属性

オプションの詳細【よく使う】

続いては、よく使うオプションについての説明です。下記のように記述すれば、デフォルトのvalue値を設定できます。

{selected: 1}

展開すると、下記のようになります。

<option value="1" selected>A太郎</option>

また、HTMLオプションを下記のように指定すれば…

{ class: 'form-control' , required: true }

このように展開されます。

<option value="1" class='form-control' required='required'>A太郎</option>

オプション指定の順番は注意!

さらには、オプションの指定には注意点もあります。HTMLオプションを指定する際には、先にオプションを必ず指定しなければ、うまく動きません(引数の順番が変わるので、当たり前と言えば当たり前なのかもですが)

# これはOK
<%= f.collection_select :id, User.all, :id, :name, {prompt: "選択してください"}, :class => 'form-control', :id => 'user_id' %>

# これもOK
<%= f.collection_select :id, User.all, :id, :name, {}, :class => 'form-control', :id => 'user_id' %>

# これはNG
<%= f.collection_select :id, User.all, :id, :name, :class => 'form-control', :id => 'user_id' %>

まとめ

書き方が色々あるので、どれが最適か迷いがちですが、状況に応じて選んで頂けたらと思う。個人的には、他のメソッドを呼び出したり、コントローラーで手を加えないと使えないメソッドよりは、書き方がシンプルなのがベストだと思うので、「collection_select」がおすすめ。

また、js周りのオプションも色々あるので、色々試して頂けたらと思う。

エンジニア|ポートフォリオ
新人

ふー!! 長かった!!

(深呼吸…)

参考

この記事を書いた人

竹田奈央

東京都港区勤務 / 国立大中退 / フルリモートの女性WEBエンジニア / アラサー / 独身 / 基本は石川県にいながら、都内の会社にてフルリモート勤務 / 7月〜東京・軽井沢・千葉 ADDress ワーケーション 中 / 松本人志・千鳥好き / 3日に1回ウンコツイート(←大事) / Twitterは @takeda_no_nao