collection_select

表单辅助方法(三)
2009-06-29 16:36

此文原文在http://guides.rubyonrails.org/form_helpers.html我根据自己的理解作的一些笔记。

3 轻松构建 Select Boxes
在HMTL里Select Boxes需要大量的标记,这些标记是可以动态生成的。
HMTL里的Select Boxes:
<select name="city_id" id="city_id">
<option value="1">Lisbon</option>
<option value="2">Madrid</option>
...
<option value="12">Berlin</option>
</select>

接下来看一看Rails里如何做。

3.1 Select和Option标签
最普通的辅助方法select_tag
<%= select_tag(:city_id, '<option value="1">Lisbon</option>...') %>

这里还没有使用动态创建option标签。可以使用options_for_select辅助方法生成option 标签。
<%= options_for_select([['Lisbon', 1], ['Mardrid', 2], ...])%>
生成的HTML代码:
<option value="1">Lisbon</option>
<option value="2">Lisbon</option>
...

结合两者的使用:
<%= select_tag(:city_id, options_for_select(...))%>

options_for_select允许设置一个预选值:
<%= options_for_select([['Lisbon', 1], ['Madrid', 2], ...],2)
生成的HTML代码:
<option value="1">Lisbon</option>
<option value="2" selected="selected">Madrid</option>
...

3.2 Select Boxes处理模型
表单控制器更多的时候是要处理数据库模型。Rails提供了这样的辅助方法。
# controller:
@person = Person.new(:city_id => 2)

#View:
<%= select(:person, :city_id, [['Lisbon', 1], ['Madrid', 2], ...] %>
如果select辅助方法是用在一个form builder对象上,语法是这样:
<%= f.select(:city_id, [['Lisbon', 1], ['Madrid', 2], ...]) %> ) %>

如果使用select(或者collection_select, select_tag)设置一个belongs_to关系的对象,就必须使用外键的名称(这里用的是city_id)。

3.3 Option标签收集对象
options_for_select生成options标签需要一个数组。如果有一个City模型,也可以收集这个模型的对象来生成option标签。

<% cities_array = City.all.map { |city| [city.name, city.id] } %>
<%= opitons_for_select(cities_array) %>

Rails还提供了一个更有效的方法:
options_from_collection_for_select

<%= options_from_collection_for_select(City.all, :id, :name) %>

再来看一个方法collection_select,它集合了select_tag with options_from_collection_for_select。

<%= collection_select(:person, :city_id, City.all, :id, :name) %>

3.4 国家和时区选择
Rails支持时区的选择,使用time_zone_select方法来生成。
<%= time_zone_select(:person, :time_zone) %>

选择可以有country_select方法,但这个方法也经抽取出来作为一个插件了。地址:http://github.com/rails/country_select/tree/master

Rails中view helper collection_select方法的selected问题
2007-07-12 00:08

手册中的说明:
collection_select(object, method, collection, value_method, text_method, options = {}, html_options = {})

没有详细提到selected的问题,往下到select方法的用法:
select(object, method, choices, options = {}, html_options = {})

其中有提到selected的用法:
By default, post.person_id is the selected option. Specify :selected => value to use a different selection or :selected => nil to leave all options unselected.

也就是说,这样写:
collection_select(:album, :id, albums, :id, :name}

它会自动比较@album的id方法的值

现在需要的做关联处理,需要这样构造:
collection_select(:photo, :album_id, albums, :id, :name, {:selected => @album}     )

但不起作用。

这里 和 这里 都说修正了,但实际测试都不行,WIKI里也说不行

非官方几个select helper的详细介绍

后来想想,其实关联实现其实只是要求select的id 和 name符合规则就行了,可以这样hard code:
collection_select(:album, :id, albums, :id, :name, {}, {:id => 'photo_album_id', :name => 'photo[album_id]'} )

问题解决。

 

 

 

原文地址:https://www.cnblogs.com/lexus/p/1885309.html