Search code examples
ruby-on-railsruby-on-rails-3forms

How do i write a cleaner date picker input for SimpleForm


I love the simple_form gem for rails but i dont like this line of code:

<%= f.input :deadline, :as => :string, :input_html => { :class => 'date_picker' } %>

I would like to write:

<%= f.input :deadline, :as => :date_picker %>

or even over write the :date / :datetime matchers completely.

But i dont really want to write a whole custom_simple_form

I think it must be possible...

Please help thanks


Solution

  • You have to define a new DatePickerInput class.

    module SimpleForm
      module Inputs
        class DatePickerInput < Base
          def input
            @builder.text_field(attribute_name,input_html_options)
          end    
        end
      end
    end
    

    And you can now write

    <%= f.input :deadline, :as => :date_picker %>
    

    Off course you also need

     $("input.date_picker").datepicker();
    

    in application.js

    This is very useful to localize dates. Look at this:

    module SimpleForm
      module Inputs
        class DatePickerInput < Base
          def input
            @builder.text_field(attribute_name, input_html_options.merge(datepicker_options(object.send(attribute_name))))
          end
    
          def datepicker_options(value = nil)
            datepicker_options = {:value => value.nil?? nil : I18n.localize(value)}
          end
    
        end
      end
    end
    

    You have now a localized date in the text field!

    Update: a cleaner way to do the same

    module SimpleForm
      module Inputs
        class DatePickerInput < SimpleForm::Inputs::StringInput
          def input_html_options
            value = object.send(attribute_name)
            options = {
              value: value.nil?? nil : I18n.localize(value),
              data: { behaviour: 'datepicker' }  # for example
            }
            # add all html option you need...
            super.merge options
          end
        end
      end
    end
    

    Inherit from SimpleForm::Inputs::StringInput (as @kikito said) and add some html options. If you need also a specific class you can add something like

    def input_html_classes
      super.push('date_picker')
    end