#8 Layouts and content_for
Mar 21, 2007 | 3 minutes |
Views
If you want to change something in the layout on a per-template basis, content_for is your answer! This allows templates to specify view code that can be placed anywhere in a layout.
- Download:
- mp4Full Size H.264 Video (5.9 MB)
- m4vSmaller H.264 Video (3.9 MB)
- webmFull Size VP8 Video (10.8 MB)
- ogvFull Size Theora Video (6.63 MB)
I don't like this method because you get two <link ... type="text/css" /> items in your HTML source.
I really don't think that this is an appropriate behavior.
@rs, that's a valid concern. However, I think it's acceptable if one page requires a lot of additional styling. No sense in putting all this styling in a global CSS file and requiring it on every other page. Also, if the users are coming from another page they will likely have the global "application.css" stylesheet cached.
hi,
what is the meaning of yield and :head in => <%= yield :head %>
The "yield" call in a layout will output the contents of the template. When supplying a parameter (:head in this case) it will output the contents of that content_for block. I explained this in the episode, sorry if it wasn't clear.
@rs and ryan,
it seems to me that having multiple <link.../> tags is like having multiple <script /> tags in the head. is there some rule that says multiple script tags are ok, but link tags for css should be in one file? eric meyer has 8 stylesheet links on his homepage (as of today). i think he knows what he's doing vis-a-vis css.
it's a fantastic little railscast, btw. these little tricks make dev so much easier and smarter. thanks for doing this! you're a mensch.
You can have multiple link tags. This is even used in the W3C standards to have multiple stylesheets specified for different medias, or simply to allow choice of stylesheets. (In Firefox, this shows up in the View Menu -> Page Style sub-menu.)
What is the best way and is there a best way to call a "content_for" between
<%=yield :mycontent %>
and
<%=@content_for_mycontent %>
kriom, there shouldn't be any difference, since content_for_mycontent is only old style version for yield in Rails, as far as I am concerned.
Great tip; It's really useful for including JavaScript/CSS that you only need on specific pages of your app.
I've used this technique to load some extra jQuery files and CSS that I needed for a sortable list and autocomplete widget. Very cool.
As per ur tutorial if i write the content_for in index.html.erb its working fine.other than that if write in any other file example news.html.erb its not taking.Please send ur reply to me
I'm having problems using content_for with yield in a rails 2.2.2 project. The content_for is not being rendered. Any one else experiencing problems with content_for in Rails 2.2.2?
@Mark
I have just experienced a similar issue. I upgraded HAML and it fixed the problem. (2.0.9)
I've built about 5 different helpers for different clients that do this. Then I started watching railscasts. Thanks for the great content. I've summarized the behavior on my website so I have a quick reference.
http://rails.lostjungles.com/content_for-multiple-yields-in-the-same-layout/2009/06
Keep up the great work!
I'm using Rails 2.3.2 - and doing content_for in the layout itself will NOT make that content visible if you yield in the layout as well.
i.e. if in application.html.erb, you do 'content_for :javascript', etc... and do a 'yield :javascript' in the same layout, it will not work. I'm not sure how to get the required behaviour since I was depending on this...
Annoying.....
@Asfand, renaming it to content_for :script worked for me in 2.3.2. Example below.
in your layout:
<% content_for :script do %>
<%= javascript_include_tag "nameofjsfile" %>
<% end %>
in your head: <%= yield :script %>
The place I needed it was actually in a partial that gets called inside a lightbox. It didn't work to have the code in the partial, so I had to add it into the page it was called from. I suspect that was a lightbox issue more than a partial issue.
I can't get it to work inside partials either. An issue have been raised on Lighthouse:
https://rails.lighthouseapp.com/projects/8994-ruby-on-rails/tickets/1896-content_for-not-rendering-from-partials-in-layout
But it seems that DHH invalidated it. Maybe it should be reopened?
I'm on rails 2.3.4 and content_for doesn't simply work when called within a partial..
@Ryan:
Can we use the same method to make a call to an item stored on a remote server? Say what if i want to http://google.com/somefolder/residingin/anotherfolder/somefile.js
As pointed out by Luca Guidi lighthouse ticket, it's a matter of ordering.
You should call
before
<%= yield :my_section %>
This has been updated to Rails 5 as a blog post Layouts and Content For Tag in Rails 5
As more of a backend dev I've thankfully yet to encounter the need for multiple specific stylesheets, which I could see becoming a scary proposition, but it's nice to have the tool in my arsenal in case I ever really did need to split a whole area or page off on its styling. (I guess the alternative would be namespacing everything you wanted on the specific page as well) Thanks for the railscast!
A good usage example is with the title of the page.
You can change it in base of each page.