我想将rails 3中存在的number_field表单助手添加到我的rails 2.3.15应用程序中,但是我在扩展模块时遇到了问题。
这些是我需要rails 3的方法
class InstanceTag
def to_number_field_tag(field_type, options = {})
options = options.stringify_keys
if range = options.delete("in") || options.delete("within")
options.update("min" => range.min, "max" => range.max)
end
to_input_field_tag(field_type, options)
end
end
def number_field(object_name, method, options = {})
InstanceTag.new(object_name, method, self, options.delete(:object)).to_number_field_tag("number", options)
end
def number_field_tag(name, value = nil, options = {})
options = options.stringify_keys
options["type"] ||= "number"
if range = options.delete("in") || options.delete("within")
options.update("min" => range.min, "max" => range.max)
end
text_field_tag(name, value, options)
end
我将此添加到我在应用程序帮助程序中包含的模块中。 to_number_field_tag
方法很简单,因为我可以打开类并添加覆盖。
FormHelper模块方法我遇到了麻烦,因为我无法弄清楚祖先的链条,也不知道如何限制我的覆盖范围。我不知道如何让它基本上起作用。
答案 0 :(得分:1)
我上面的问题是我没有覆盖FormBuilder。对于那些将来可能需要这个的人来说,这是一个解决方案。
我决定为所有新的HTML5输入制作一个通用助手,而不仅仅是实现type="number"
输入类型。我将此代码放在一个覆盖文件中,该文件包含在 application_helper.rb 中。
# file 'rails_overrides.rb`
ActionView::Helpers::InstanceTag.class_eval do
def to_custom_field_tag(field_type, options = {})
options = options.stringify_keys
to_input_field_tag(field_type, options)
end
end
ActionView::Helpers::FormBuilder.class_eval do
def custom_field(method, options = {}, html_options = {})
@template.custom_field(@object_name, method, objectify_options(options), html_options)
end
end
# form.custom_field helper to use in views
def custom_field(object_name, method, options = {}, html_options = {})
ActionView::Helpers::InstanceTag.new(object_name, method, self, options.delete(:object)).to_custom_field_tag(options.delete(:type), options)
end
# form.custom_field_tag helper to use in views
def custom_field_tag(name, value = nil, options = {})
options = options.stringify_keys
# potential sanitation. Taken from rails3 code for number_field
if range = options.delete("in") || options.delete("within")
options.update("min" => range.min, "max" => range.max)
end
text_field_tag(name, value, options)
end
然后在你的观点中使用它:
<% form_for... do |form| %>
<%= form.custom_field :user_age, :type=>"number", :min=>"0", :max=>"1000" %>
<%= form.custom_field :email, :type=>"email", :required=>"true" %>
<% end %>
这将生成<input type='number', and an <input type='email'
如果您有自定义表单构建器,则还需要扩展/覆盖它。命名空间可能会有所不同,但大多数标准都是这样的:
MySpecialFormBuilder.class_eval do
def custom_field(method, options = {}, html_options = {})
...custom form builder implementation
end
end