Trailblazer's file layout for Cells.
Trailblazer cells are view components based on the Cells gem, but following the Trailblazer naming conventions.
├── app
│ ├── concepts
│ │ ├── blog_post
│ │ │ ├── cell
│ │ │ │ ├── edit.rb
│ │ │ │ ├── item.rb
│ │ │ │ ├── new.rb
│ │ │ │ └── show.rb
│ │ │ └── view
│ │ │ ├── edit.erb
│ │ │ ├── item.erb
│ │ │ ├── new.erb
│ │ │ └── show.erb
│ │ │ └── author_list.erb
# app/concepts/blog_post/cell/edit.rb
module BlogPost
module Cell
class Edit < Trailblazer::Cell
# You can have helper methods.
def post_url
new_blog_post_path(model.id)
end
def summary
"#{model.text[0..99]}..."
end
end # New
end
end# app/concepts/blog_post/view/edit.erb
<h1>
You're editing <%= model.titel %>
</h1>
<div class="summary">
<%= summary %>
</div>
<%= render :edit_form %># app/concepts/blog_post/view/edit_form.erb
<%= simple_form_for model, url: post_url do %>
...
<% end %># app/controllers/blog_post_controller.rb
class BlogPostController < ApplicationController
def edit
@blog_post = BlogPost.find(params[:id]) # do whatever you need here.
render cell(BlogPost::Cell::Edit, @blog_post)
end
endIn Trailblazer, class structures such as the following are very common, let's say for a post concept, here are the class headers, and where the view directory gets resolved to.
module Post
module Cell
class New < Trailblazer::Cell # => app/concepts/post/view
class Show < Trailblazer::Cell # => app/concepts/post/view
class SideBar < Trailblazer::Cell # => app/concepts/post/viewYou don't have to define a show method, Trailblazer::Cell will have one that looks as follows.
class Trailblazer::Cell
def show
render
endWhen calling render, the view name is inferred from the class name.
module Post
module Cell
class New < Trailblazer::Cell # => new.erb
class Show < Trailblazer::Cell # => show.erb
class SideBar < Trailblazer::Cell # => side_bar.erbYou can still override using render view: :name.
You can pass a layout cell into every Trailblazer::Cell which will render the layout.
Post::Cell::Show.new(post, layout: Gemgem::Cell::Layout).()The :layout option has to refer to a cell class. When invoked, the layout cell will receive the content of the actual cell under :content, resulting in a call as follows.
Gemgem::Cell::Layout.new(post,
content: Post::Cell::Show.new(post)
)The layout cell's show view can sit in any directory, for example gemgem/view/layout.rb.
<html>
Yay, I'm the layout!
<%= content %>
</html>It's up to you what you do with the :content option. Here's the Trailblazer way.
class Gemgem::Cell::Layout < Trailblazer::Cell
self.view_paths = ["gemgem"]
def content
@options[:content]
end
endCells with layout cells allow replacing a frameworks entire view stack, e.g. ActionView.
It works identical with namespaces.
Some projects do not use the app/concept view path. This can be changed as follows.
Trailblazer::Cell.view_paths = ["concepts"]Note that this will change for all cells, including bundled in gems. Introduce an Application::Cell if you don't like that.
This gem has only one dependency: cells. Note that it does not need trailblazer.