Rails验证|将类添加到周围的<div> </div>

时间:2009-10-20 02:40:46

标签: ruby-on-rails validation

Rails问题。错误验证的默认行为是输入字段周围的fieldWithError样式div,如下所示

<div class="type-text" id="pre_negotiation_value_div">
<label for="contract_budget_holder">Budget Holder</label>
<div class="fieldWithErrors">
<input id="contract_budget_holder"name="contract[budget_holder]" size="30" type="text" value="" />
</div>
</div>

我想要完成的是,用标记的div标签包围标签和输入字段,如下所示:

<div class="type-text fieldWithErrors" id="pre_negotiation_value_div">
<label for="contract_budget_holder">Budget Holder</label>      
<input id="contract_budget_holder"name="contract[budget_holder]" size="30" type="text" value="" />      
</div>

任何想法如何实现这一目标?你能把javascript挂钩到ActionView :: Base.field_error_proc吗?

我是Rails的新手,如果这非常容易,我道歉!

感谢您的帮助。

乔纳森

2 个答案:

答案 0 :(得分:2)

完全按照自己的意愿行事并不容易,但如果你有这样的ERB:

<div id="pre_negotiation_value_div" class="type-text">
  <%= f.label :name %>
  <%= f.text_field :name %>
</div>          

你会得到这样的HTML:

<div id="pre_negotiation_value_div" class="type-text">
  <div class="fieldWithErrors"><label for="foo_name">Name</label></div>
  <div class="fieldWithErrors"><input id="foo_name" name="foo[name]" size="30" type="text" value="" />
</div>

标签和text_field都将包含fieldWithErrors div。根据您想要的样式,这可能足够好。如果它不够好,你将不得不做这样的自定义助手:

class ActionView::Helpers::FormBuilder
  def labeled_input(method, options={}, &block)
    (options[:class] ||= "") << " fieldWithErrors" if @object.errors.on(method)
    ActionView::Helpers::InstanceTag.send(:alias_method, :original_error_wrapping, :error_wrapping)
    ActionView::Helpers::InstanceTag.send(:define_method, :error_wrapping,
      Proc.new {|html_tag, has_error| html_tag})
    @template.concat(@template.content_tag(:div, @template.capture(&block), options))
  ensure
    ActionView::Helpers::InstanceTag.send(:alias_method, :error_wrapping, :original_error_wrapping)
    ActionView::Helpers::InstanceTag.send(:remove_method, :original_error_wrapping)
  end
end

将其放入config/initializers/labeled_input.rb。这是一堆Ruby meta-foo,但它的作用是将“fieldWithErrors”类放在外部div上。它暂时重新定义error_wrapping的{​​{1}}方法,以便内部标签和text_field标签没有围绕它们的“fieldWithErrors”div。你可以在ERB中使用它:

InstanceTag

答案 1 :(得分:0)

RAILS 3 UPDATE

我正在将我的应用更新为rails 3.如果您已经使用此方法进行升级,则会出现一些弃用警告和表单字段出现两次或多次。

解决这些问题:

1)更改labeled_input.rb中检查错误的行。这会停止访问错误的弃用警告:

(options[:class] ||= "") << " fieldWithErrors" unless @object.errors[method].empty?

2)在'ensure'之前更改labeled_input.rb中的行。这会停止多次出现的表单元素:

@template.content_tag(:div, @template.capture(&block), options)

3)在您调用labeled_input的视图文件中,使用&lt;%=而不是&lt;%。这可以防止弃用警告。

希望能节省你一些时间。