Better way to concatenate options to collection_select?

I've just been through 4 pages of similar threads, but nothing quite
satisfying.

What I'm trying to achieve:

<select>
  <option value="-1">Please select</option>
  <option value="0">ALL</option>
  <option value="1">Forum 1</option>
  <option value="2">Forum 2</option>
  ...
<select>

The way I'm currently doing it:

# Plugin
class FakeModel
  def initialize(hash)
    @hash = hash
  end

  def id
    @hash[:id]
  end

  def method_missing(meth_id)
    @hash[meth_id]
  end
end

# Controller
@forums = [
  FakeModel.new(:id => -1, :name => 'Please select'),
  FakeModel.new(:id => 0, :name => 'ALL')
] + Forum.all(:order => 'name')

# View
<%= collection_select :thread, 'forum_id', @forums, :id, :name %>

Just wondering if there's a more natural (and undocumented) way of doing
it...

# View
<%= collection_select :thread, 'forum_id', @forums, :id, :name %>

Just wondering if there's a more natural (and undocumented) way of doing
it...

In a small experiment,

collection_select :thread, 'forum_id', @forums, :id, :name, :prompt =>
true, :include_blank => 'All'

seems to work for me. If that doesn't work out, i'd use select instead
of collection_select - collection_select is trying to make one use
case of select easier, but if you're jumping through hoops then it's
no longer easier than just using select.

Fred

Frederick Cheung wrote:

In a small experiment,

collection_select :thread, 'forum_id', @forums, :id, :name, :prompt =>
true, :include_blank => 'All'

seems to work for me. If that doesn't work out, i'd use select instead
of collection_select - collection_select is trying to make one use
case of select easier, but if you're jumping through hoops then it's
no longer easier than just using select.

Overwriting ActionView::Helpers::InstanceTag#add_options() could also
work:

module ActionView
  # Find original in
/usr/lib64/ruby/gems/1.8/gems/actionpack-2.3.5/lib/action_view/helpers/form_options_helper.rb
  module Helpers
    class InstanceTag
      private
        def add_options(option_tags, options, value = nil)
          if options[:start_with]
            options[:start_with].reverse_each do |element|
              option_text, option_value = option_text_and_value(element)
              selected_attribute = ' selected="selected"' if
options[:selected] && option_value_selected?(option_value,
options[:selected])
              option_tags = "<option
value=\"#{html_escape(option_value.to_s)}\"#{selected_attribute}>#{html_escape(option_text.to_s)}</option>\n"
+ option_tags
            end
          end
          if options[:end_with]
            options[:end_with].reverse_each do |element|
              option_text, option_value = option_text_and_value(element)
              selected_attribute = ' selected="selected"' if
options[:selected] && option_value_selected?(option_value,
options[:selected])
              option_tags += "<option
value=\"#{html_escape(option_value.to_s)}\"#{selected_attribute}>#{html_escape(option_text.to_s)}</option>\n"
            end
          end
          if options[:include_blank]
            option_tags = "<option value=\"\">#{options[:include_blank]
if options[:include_blank].kind_of?(String)}</option>\n" + option_tags
          end
          if value.blank? && options[:prompt]
            prompt = options[:prompt].kind_of?(String) ?
options[:prompt] : I18n.translate('support.select.prompt', :default =>
'Please select')
            "<option value=\"\">#{prompt}</option>\n" + option_tags
          else
            option_tags
          end
        end
    end
  end
end

Now I could do:

:start_with => [['- Select category -', -1], ['- All -', 0]]

However, select() might be a wiser approach.