【问题标题】:How do i write a cleaner date picker input for SimpleForm如何为 SimpleForm 编写更简洁的日期选择器输入
【发布时间】:2011-02-15 18:24:50
【问题描述】:

我喜欢用于 rails 的 simple_form gem,但我不喜欢这行代码:

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

我想写:

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

甚至完全重写 :date / :datetime 匹配器。

但我真的不想写一个完整的custom_simple_form

我觉得应该是可以的……

请帮忙谢谢

【问题讨论】:

    标签: ruby-on-rails ruby-on-rails-3 forms


    【解决方案1】:

    如果您使用的是 simple_form 2.0,这里的答案似乎有点过时了。

    我已经为此奋斗了一段时间,并且能够编造出这个;它使用继承(注意它是StringInput 的子类,而不是Base),支持i18n 并以更简洁的方式添加datepicker css 类,恕我直言。

    # app/inputs/date_picker_input.rb
    
    class DatePickerInput < SimpleForm::Inputs::StringInput 
      def input                    
        value = input_html_options[:value]
        value ||= object.send(attribute_name) if object.respond_to? attribute_name
        input_html_options[:value] ||= I18n.localize(value) if value.present?
        input_html_classes << "datepicker"
    
        super # leave StringInput do the real rendering
      end
    end
    

    用法如上:

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

    并且 javascript 保持不变:

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

    【讨论】:

    • 它对我不起作用。我的日期格式如下“mer 06 nov 2013, 00:00:00 +0000”。我不知道为什么。
    • @AgostinoX 您的语言环境必须是法语。 I18n.localize 方法使用time.formats.default 键来格式化日期。见github.com/svenfuchs/rails-i18n/blob/master/rails/locale/…
    • 如果本地化无法正常工作,请向 javascript 添加选项。 $("input.date_picker").datepicker({format: 'dd.mm.yyyy'});
    【解决方案2】:

    您必须定义一个新的DatePickerInput 类。

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

    你现在可以写了

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

    当然你也需要

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

    application.js

    这对于本地化日期非常有用。看看这个:

    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
    

    您现在在文本字段中有一个本地化日期!

    更新:一种更简洁的方法

    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
    

    SimpleForm::Inputs::StringInput 继承(正如@kikito 所说)并添加一些 html 选项。 如果你还需要一个特定的类,你可以添加类似

    def input_html_classes
      super.push('date_picker')
    end
    

    【讨论】:

    • 很好的答案,完美运行。几个加分。自定义输入代码的第 5 行应该是 `@builder.text_field(attribute_name, :class=> 'date_picker')'。而这个类需要进入文件app/inputs/date_picker_input.rb。
    • 如果您使用的是 simple_form 2.x,请在下面查看我的答案
    • 谢谢。一个小错误,你更新的代码中有两个class
    • 您好,我已经使用此示例构建了一个小型 Gem,以将 SimpleForm 与 jQueryUI 日期选择器一起使用:rubygems.org/gems/simple-form-datepicker
    • 我使用的是 rails 4,在哪里添加 DatePickerInput 类?
    【解决方案3】:

    根据@kikito 的回答,我这样做是为了获得一个本地日期选择器(即没有特殊的 JS 类)。

    config/initializers/simple_form_datepicker.rb

    class SimpleForm::Inputs::DatepickerInput < SimpleForm::Inputs::StringInput 
      def input                    
        input_html_options[:type] = "date"
        super
      end
    end
    

    然后像这样使用它:

    f.input :paid_on, as: :datepicker
    

    请注意,如果您也有一个 simple_form_bootstrap3.rb 初始化程序或类似的,就像我们所做的那样,您应该:

    1. DatepickerInput 添加到其输入列表中
    2. 确保simple_form_bootstrap3.rb(或类似的)初始化程序加载simple_form_datepicker.rb,以便DatepickerInput 类可用。通过例如这样做将 datepicker 初始化程序重命名为 simple_form_0_datepicker.rb

    【讨论】:

    • 这很好用,不需要任何 gem 或外部插件,因为它利用现代浏览器显示内置日期选择器的功能。推荐!
    【解决方案4】:

    另一个选项也可以是覆盖默认的DateTimeInput 帮助器,这里是一个放在app/inputs/date_time_input.rb 中的示例

    class DateTimeInput < SimpleForm::Inputs::DateTimeInput
      def input
        add_autocomplete!
        @builder.text_field(attribute_name, input_html_options.merge(datetime_options(object.send(attribute_name))))
      end
    
      def label_target
        attribute_name
      end
    
      private
    
        def datetime_options(value = nil)
          return {} if value.nil?
    
          current_locale = I18n.locale
          I18n.locale = :en
    
          result = []
          result.push(I18n.localize(value, { :format => "%a %d %b %Y" })) if input_type =~ /date/
          if input_type =~ /time/
            hours_format = options[:"24hours"] ? "%H:%M" : "%I:%M %p"
            result.push(I18n.localize(value, { :format => hours_format }))
          end
    
          I18n.locale = current_locale
    
          { :value => result.join(', ').html_safe }
        end
    
        def has_required?
          options[:required]
        end
    
        def add_autocomplete!
          input_html_options[:autocomplete] ||= 'off'
        end
    end
    

    请注意,虽然使用此方法会使其成为表单的删除功能,但它也可能会与 simple_form 的未来版本中断。

    关于本地化日期的注意事项:据我所知,Ruby 仅按照几种格式解释日期,您可能需要在本地化它们之前小心谨慎,并确保 Ruby 可以处理它们。 从 https://github.com/ZenCocoon/I18n-date-parser 开始尝试更好地支持 Ruby 日期解析,但这不起作用。

    【讨论】:

      【解决方案5】:

      在新格式预览中,答案不起作用。见http://justinfrench.com/notebook/formtastic-2-preview-custom-inputs 这是一个简单的工作示例(保存到 app/inputs/date_picker_input.rb):

      class DatePickerInput < Formtastic::Inputs::StringInput
        def input_html_options
          {
            :class => 'date_picker',
          }.merge(super).merge({
            :size => '11'
          })
        end
      end
      

      创建一个包含内容的文件 app/assets/javascripts/date_picker.js:

      $(function() {
        $("input#.date_picker").datepicker();
      });
      

      您还需要加载 jquery-ui。为此,请插入 app/assets/javascripts/application.js 行:

      //= require jquery-ui
      

      或者干脆使用 CDN 例如:

      <%= javascript_include_tag "http://ajax.googleapis.com/ajax/libs/jquery/1.8.1/jquery.min.js" %>
      <%= javascript_include_tag "http://ajax.googleapis.com/ajax/libs/jqueryui/1.8.1/jquery-ui.min.js" %>
      

      jquery-ui 的样式表可以包含http://babinho.net/2011/10/rails-3-1-jquery-ui/ 或 来自 CDN:

      <%= stylesheet_link_tag    "application", "http://ajax.googleapis.com/ajax/libs/jqueryui/1.8.8/themes/ui-lightness/jquery-ui.css" %>
      

      【讨论】:

      • 感谢@LukasSvoboda,但问题是简单的形式而不是formtastic
      猜你喜欢
      • 1970-01-01
      • 2018-05-09
      • 2021-11-17
      • 2015-07-16
      • 1970-01-01
      • 2016-04-30
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多