ページごとにサイドバーのコンテンツを切替える
お手伝いしているRailsのサービスサイトで、サイドバーに全ページに共通の広告を表示しているのですが、掲載数の変更に伴いページごとに種類を変えて広告バナーを表示することにしました。
現状としてはapplication.html.erbで統一されたサイドバーを表示していますが、 これをページごとに分割するのに「名前付きyield」が使えそうです。
【目次】
名前付きyieldの指定
まずapplication.html.slim側では、= yield :name
の形式でyieldに名前をつけます。
現在広告バナーはページのcol-md-3の部分に表示しているため、col-md-9はそのまま現状のものを表示できるよう= yield
を、そしてxxxページ・yyyページでそれぞれバナーを変更したいcol-md-3の内部に名前付きyieldを記述します。
.row .col-md-9 = yield .col-md-3 .sidebar-content = yield :xxx = yield :yyy
viewのメイン部分は常に「名前なしyield」としてレンダリングされるため、コンテンツを名前付きのyieldとしてレンダリングするには、content_for
メソッドを使用します。
content_forメソッドでレイアウトに挿入
名前付きのyieldとしてレイアウトに挿入する場合、各ページ(index.html.slim)でcontent_for :name do
の形式で指定します。
xxx/index.html.slim
= h1 名前なしyieldとして挿入される - content_for :xxx do .sidebar-content h2 名前付きyieldとして挿入される .card
yyy/index.html.slim
= h1 名前なしyieldとして挿入される(yyy) - content_for :yyy do .sidebar-content h2 名前付きyieldとして挿入される(yyy) .card
これらのレンダリング結果がレイアウトに挿入されると、最終的には以下のようなHTMLとして出力されます。
xxx/index.html
<div class="row"> <div class="col-md-9"> <h1>名前なしyieldとして挿入される</h1> <div class="col-md-3"> <div class="sidebar-content"> <h2>名前付きyieldとして挿入される</h2> <div class="card">
yyy/index.html
<div class="row"> <div class="col-md-9"> <h1>名前なしyieldとして挿入される(yyy)</h1> <div class="col-md-3"> <div class="sidebar-content"> <h2>名前付きyieldとして挿入される(yyy)</h2> <div class="card">
これでxxxページ・yyyページそれぞれ異なる広告バナーを表示させることができるようになりました!
レイアウトをコントローラーごとに指定するのもいいかも
今回は各ページで広告バナーのみ切替がしたかったので使用しませんでしたが、コントローラーにレイアウトを指定することで表示を変える方法も良さそうです。
例えばxxx_controllerのshowページでは、applicationファイルのようなサイドバナー広告の表示が不要であるとします。
そんな時はviews/layouts下に、別途レイアウトファイルを作成し、コントローラーでlayoutメソッドを指定することで切り替えられます。
今回はバナーなしのno_banner.html.slimを作成したとします。
作成できたら、xxxコントローラーにて以下のように指定しましょう。
layout "no_banner", only: :show # または def show render layout: "no_banner" end