views:

525

answers:

3

Hello,

I am useing searchlogic to search some paintings. Each painting belong to a single category. What I would like to do is add multiple checkboxes to my search form, so that users can mark multiple categories. (joined with or) Is this possible with searchlogic? The query I am looking for is something like this:

SELECT * FROM paintings WHERE category LIKE "white" OR category LIKE "red"...

f.check_box :category (white)
f.check_box :category (black)
f.check_box :category (red)
f.check_box :category (green)

etc.

+1  A: 

Could you please see if something like that works in your case? I'm willing to put some time into this if nobody knows a better solution:

I'm looking forward to hear your feedback ;)!

in app/helper/conditions_builder.rb

class ConditionsBuilder < ActionView::Helpers::FormBuilder
  def multiple_select(collection, possibilities)
    content = []
    id = "#{object_name}[#{collection}][]"
    content << @template.hidden_field_tag(id, "")

    ids = Set.new(self.object.send(collection))
    possibilities.each do |p, label|
      uid = @template.sanitize_to_id("#{id}#{p}")
      checked = ids.include?(p)
      content <<  @template.content_tag("div",
                  @template.check_box_tag(id, p, checked, :id => uid) + " " +
                  @template.label_tag(uid, label))
    end

    return content.join(" ")
  end
end

in app/helper/application.helper add:

def conditions_form(&blk)
  form_for @search, :builder => ConditionsBuilder, &blk
end

In your view you add: (in my case I use haml)

 - conditions_form do |f|
   - f.fields_for @search.conditions do |s|
     = s.label 'Name'
     = s.text_field 'name_contains'
     = s.multiple_select :state_equals, ['open', 'active', 'gone'].collect{|s| [s, _state(s)]}
     = f.submit _("Search"), :class => 'buttons'

In my case I set some defaults: (not sure if this is the best way to do that):

  unless params[:search]
    @search.conditions.state_equals = ['open', 'active']
  end
reto
+1  A: 

Is the search happening through a POST request? If so you can do it like this...

<% for category in %w[white red black] %>
  <p>
    <%= check_box_tag "categories[]", category, (params[:categories] && params[:categories].include?(category)) %>
    <%=h category %>
  </p>
<% end %>

And then perform a search like this..

Painting.all(:conditions => { :category => params[:categories] })

BTW, I recommend extracting out the category column into a Category model which has id and name columns. You can then use category_id in paintings to link up the association. This way the database is normalized and you can, for example, easily rename and add a category. You could also loop through them all with Category.all.

ryanb
+2  A: 

Here's the super duper easy way to do it (assuming your search object is @search):

f.check_box :category_equals_any, {:name => "search[category_equals_any][]"}, "white"
f.check_box :category_equals_any, {:name => "search[category_equals_any][]"}, "black"
f.check_box :category_equals_any, {:name => "search[category_equals_any][]"}, "red"
f.check_box :category_equals_any, {:name => "search[category_equals_any][]"}, "green"
Jarin Udom