2

我正在构建一个应用程序,其中七个页面是静态的,看起来几乎相同并共享相同的控制器,StaticPagesControllerStaticPagesController刚刚定义了 7 个与static_pages目录中视图名称相对应的空操作。

所有静态页面都将基于通用应用程序布局(layouts/application.html.erb由页眉和页脚组成),并且它们都将在顶部包含一个“英雄单元”(带有图片的大横幅),在其下方是两列。第一列将包含每页不同的一段文本,在第二列我将呈现 ActiveModel 对象的集合(每页上将显示不同的对象子集,但我想能够只编写一次渲染代码)。

问题

我想要实现的是一个继承页眉和页脚的布局,layouts/application.html.erb并允许我只编写将在每个页面之间更改的代码,并避免重复结构、英雄渲染和集合渲染。

我的(可能是错误的)解决方案

我找到了一种可行的方法,但是在阅读了有关嵌套布局的 Rails 指南后,我有点困惑,我不确定这是否是正确的方法。这是我的做法:

layouts/static_page.html.erb使用以下代码创建:

<%= render partial: 'shared/hero', locals: { big: true, big_text: hero_big_text } %>

<div class="container">
  <div class="row">
    <div class="col-sm-6">
      <%= yield :introduction %>

      <%= render 'hook_button' %>
    </div>
    <div class="col-sm-6 bo-offers-col">
      The @collection will be rendered here
    </div>
  </div>
</div>

第一行渲染了英雄,将一些本地人传递给它,其中一个必须在视图中定义。其余代码创建两列并introduction在第一列中生成代码,并应该在第二列中呈现@collection 对象(将在控制器中定义)。

以下是其中一个视图包含的内容:

<%# Page title %>
<% provide :title, "Page title" %>

<%# Specify the content %>
<% content_for :hero, yield(:title) %>

<% content_for :introduction do %>
  <h2>Page subtitle</h2>
  <p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Mauris congue fermentum quam a lacinia.</p>
  <p>Maecenas at sapien ut risus congue sodales eget quis enim. Etiam pulvinar nulla non libero lobortis vulputate. Aliquam convallis sapien nec velit sagittis molestie. Morbi porta pulvinar varius. Donec nec velit at nisi ultrices commodo viverra eu enim.</p>
<% end %>

<%# Render the stuff %>
<%= render template: 'layouts/static_page', locals: { hero_big_text: false } %>

首先,我提供了一个标题,它将用作页面<title>和英雄内部的文本。我content_for还用来提供第一列的内容。
最后,我<%= render template: 'layouts/static_page', locals: { hero_big_text: false } %>用来渲染我之前定义的模板,传递我使用的本地来决定显示哪种类型的英雄(在英雄局部中使用)。

这个解决方案有效,但我不确定它在语义上是否正确,或者是否有更好的方法来做到这一点。我还没有找到任何文件或问题来解决这个确切的问题,我想知道是否有更好的方法来做到这一点。

4

1 回答 1

1

我建议在这里使用部分布局来简化许多不同的content_for调用。所以从您的视图文件中执行此操作

<%= render layout: 'hero_layout', locals: { hero_big_text: false } do %>
  <h2>Page subtitle</h2>
  <p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Mauris congue fermentum quam a lacinia.</p>
  <p>Maecenas at sapien ut risus congue sodales eget quis enim. Etiam pulvinar nulla</p>
<% end %>

然后,不要使用layouts/static_page.html.erb创建上面代码中提到的部分布局,而是使用app/views/application/_hero_layout.html.erb如下代码:

<%= render partial: 'hero', locals: { big: true, big_text: hero_big_text } %>

<div class="container">
  <div class="row">
    <div class="col-sm-6">
      <%= yield %>

      <%= render 'hook_button' %>
    </div>
    <div class="col-sm-6 bo-offers-col">
      The @collection will be rendered here
    </div>
  </div>
</div>

另请注意,使用shared文件夹保存部分内容不再是正确的方法。相反,您可以使用模板继承。因此,hero部分将从您的模板继承路径中获取。这可能意味着您需要将其定位,/app/views/application/_hero.html.erb但这取决于您的应用程序的具体情况。

于 2013-09-05T03:41:17.617 回答