我是looking at content_for的工作方式,并观察block.call
方法中的capture_erb_with_buffer
。它显然是神奇地写入缓冲变量然后被修剪。但是,我认为这已被弃用,您现在可以立即致电<%=yield :tag%>
。这是如何运作的?如果我从ERB模板中调用yield,那么它会产生什么?
非常感谢一个简单的代码示例来说明这一点。
答案 0 :(得分:4)
我不确定yield
如何在ERB级别上运行,但我知道在应用于布局时它是如何工作的。
下载示例layout.html.erb文件:
<html>
<head>
<title> <%= @title || 'Plain Title' %> </title>
<%= yield :head %>
</head>
<body>
<div id='menu'>
<%= yield :menu %>
</div>
<div id='content'>
<%= yield %>
</div>
<div id='footer'>
<%= yield :footer %>
</div>
</body>
我定义了4个yield(:head,:menu,:footer和default)和一个实例变量@title。
现在,控制器操作可以渲染插入这些位置的视图。请注意,视图在布局之前呈现,因此我可以在视图中定义类似@title的变量,并在布局中定义它。
示例视图: 关于页面
<% @title = 'About' %>
<% content_for :menu do %>
<%= link_to 'Back to Home', :action => :home %>
<% end %>
We rock!
<% content_for :footer do %>
An Illinois based company.
<% end %>
编辑页面
<% @title = 'Edit' %>
<% content_for :head do %>
<style type='text/css'> .edit_form div {display:inline-block;} </style>
<% end %>
<% form_for :thing, :html => {:class => 'edit_form'} do |f| %>
...
<% end %>
您可以混合和匹配要放入数据的产量,content_for :something
中出现的内容将插入到布局文件中匹配的yield :something
中。
它甚至适用于partials,partial可以插入自己的content_for:某个块,它将被添加到任何其他content_for调用。
答案 1 :(得分:2)
execute
中名为ActionView::Base
的这个小小方法解释了这一切。
http://google.com/codesearch/p?hl=en#m8Vht-lU3vE/vendor/rails/actionpack/lib/action_view/base.rb&q=capture_helper.rb&d=5&l=337
def execute(template)
send(template.method, template.locals) do |*names|
instance_variable_get "@content_for_#{names.first || 'layout'}"
end
end
do |*names|... end
块是接收yield
的块。您会注意到@content_for_#{names.first}
与content_for
进程中设置的变量匹配。
在#render中从AV :: TemplateHandlers :: Compilable调用它,我也会假设其他地方。
def render(template)
@view.send :execute, template
end
答案 2 :(得分:-1)
简单地:
在方法中调用yield会执行通过块传递给方法的代码。
例如
def my_method
yield
end
my_method { puts "Hello" }
my_method { puts "World" }
这5行将产生以下输出到屏幕
Hello
World
有关Ruby中的yield的详细讨论,请参阅以下页面:Ruby Yield