Nature, science, photography and other things that interest me.

Ruby On Rails acts_as_tree select menu

This time I would like to share a helper I wrote for rails. I was trying to write a form to add categories and I wanted to present a neatly formatted select box of existing categories to select as the parent category. It also needed infinite nested subcategories. I could not find a tutorial or example code anywhere for what I was trying to do. So I wrote this little snippet.

application_helper.rb:

  def tree_select(categories, model, name, selected=0, level=0, init=true)
    html = ""
    # The "Root" option is added
    # so the user can choose a parent_id of 0
    if init
        # Add "Root" to the options
        html << "


\\n" if init
    return html
  end

View:

<%= tree_select(Category.find(:all, :conditions => "parent_id = 0"),
                        'category', 'parent_id', @category) %>

Tree Select Menu

13 Responses

  1. Santiago

    Great helper! Thanks a lot!

    February 21, 2008 at 11:53 pm

  2. Jochen

    Perfect – just what I was looking for!

    March 15, 2008 at 1:35 pm

  3. There’s nobody I like more than the man who saves me time. Great post. Thanks for writing the snippit.

    April 15, 2008 at 7:14 am

  4. SuddenHead

    really cool! thanx!

    December 23, 2008 at 11:55 am

  5. This tag works wonderfully when editing records within the Category table. However, I need help making it work on my Tag table. My Tag table
    belongs_to :category

    I can get the select menu to display the existing tree of Cateogries, but not to select the preset value in the Tag table record’s “category_id” cell.

    Any help you can supply would be appreciated.

    January 4, 2009 at 11:57 pm

  6. I figured this out. I just removed your “def tree_select” from the “application_helper.rb” file, and then placed it elsewhere with minor edits as follows:

    1) I put it on the “categories_helper.rb” just as you had written it, with your two references to “selected.parent_id”.

    2) I then put a slightly modified version of it on the other “…_helper.rb” templates where I want to use it, but replaced the “selected.parent_id” with “selected.id”. You can leave it as “selected.parent_id”, but will see that it selects the next higher node on the tree branch.

    Note that one must remove the code from the “application_helper.rb” in order for this distributed instance model to work.

    Your code is very sweet, and I thank you muchly!

    January 6, 2009 at 11:03 am

  7. Also, on the particular helper pages I replaced
    html \n”

    with hard-coded field “name” and “id”

    html \n”

    This one is for the “category_id” field on the “tag” helper.

    January 6, 2009 at 11:53 am

  8. f3ex

    Thank you for your item.

    Note: In Rails with SQLite3
    :conditions => “parent_id = 0″
    replace by this:

    :conditions => “parent_id IS NULL “

    February 21, 2009 at 10:00 am

  9. Sweet! After stumbling over it a little, I managed to get it. Thanks a million, George!

    May 18, 2009 at 3:20 am

  10. Much thanks for sharing this – I was just about to try to hack out something myself and am VERY happy not to have to do all that work :)

    May 23, 2009 at 10:19 pm

  11. def tree_options_for_select(categories, selected=nil, level=0)
    result = ”

    # if level==0
    # end

    categories.each do |c|
    result #{c.name}”
    result

    August 17, 2009 at 3:30 am

  12. def tree_options_for_select(categories, selected=nil, level=0)
    result = ”

    # if level==0
    # end

    categories.each do |c|
    result #{c.name}”
    result

    August 17, 2009 at 3:31 am

  13. I really liked your solution, thanks for this post :)

    September 16, 2009 at 6:45 am

Leave a Reply

Your email address will not be published. Required fields are marked *

*

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>