blocks 0.1

Sign up to get free protection for your applications and to get access to all the features.
data/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ The MIT License
2
+
3
+ Copyright (c) <year> <copyright holders>
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in
13
+ all copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
21
+ THE SOFTWARE.
data/README ADDED
@@ -0,0 +1 @@
1
+ This is blocks it's easy and fun
@@ -0,0 +1,76 @@
1
+ <%= table.define :edit do |options| %>
2
+ <%= link_to "Edit", [:edit, options[:scope], options[:record]].flatten %>
3
+ <% end %>
4
+
5
+ <%= table.define :show do |options| %>
6
+ <%= link_to "Show", [options[:scope], options[:record]].flatten %>
7
+ <% end %>
8
+
9
+ <%= table.define :delete do |options| %>
10
+ <%= link_to "Delete", [options[:scope], options[:record]].flatten, :method => "delete", :confirm => "Are you sure you want to delete this #{options[:record].class.to_s.humanize}?" %>
11
+ <% end %>
12
+
13
+ <%= table.define :thead do %>
14
+ <thead>
15
+ <%= table.use :header_row %>
16
+ </thead>
17
+ <% end %>
18
+
19
+ <%= table.define :header_row do %>
20
+ <tr>
21
+ <%= table.use :header_columns %>
22
+ </tr>
23
+ <% end %>
24
+
25
+ <%= table.define :header_columns do |options| %>
26
+ <% table.columns.each do |column| %>
27
+ <%= content_tag :th, options.merge(column.options)[:header_html] do %>
28
+ <%= table.use "#{column.name.to_s}_header", options.merge(:column => column) %>
29
+ <% end %>
30
+ <% end %>
31
+ <% end %>
32
+
33
+ <% table.columns.each do |column| %>
34
+ <%= table.define "#{column.name.to_s}_header", :column => column do |options| %>
35
+ <%= column.options[:label] ? column.options[:label] : column.name.to_s.titleize %>
36
+ <% end %>
37
+ <% end %>
38
+
39
+ <%= table.define :tbody do %>
40
+ <tbody>
41
+ <%= table.use :rows %>
42
+ </tbody>
43
+ <% end %>
44
+
45
+ <%= table.define :rows do %>
46
+ <% records.each do |record| %>
47
+ <%= table.use :row, :record => record %>
48
+ <% end %>
49
+ <% end %>
50
+
51
+ <%= table.define :row do |options| %>
52
+ <%= content_tag :tr, evaluated_content_options(options[:row_html]) do %>
53
+ <%= table.use :data_columns, options %>
54
+ <% end %>
55
+ <% end %>
56
+
57
+ <%= table.define :data_columns do |options| %>
58
+ <% table.columns.each do |column| %>
59
+ <%= content_tag :td, options.merge(column.options)[:data_html] do %>
60
+ <%= table.use column, options.merge(:column => column) %>
61
+ <% end %>
62
+ <% end %>
63
+ <% end %>
64
+
65
+ <% table.columns.each do |column| %>
66
+ <%= table.define column.name, :column => column do |options| %>
67
+ <%= options[:record].send(options[:column].name) %>
68
+ <% end %>
69
+ <% end %>
70
+
71
+ <%= table.use :table do |options| %>
72
+ <%= content_tag :table, options[:table_html] do %>
73
+ <%= table.use :thead %>
74
+ <%= table.use :tbody %>
75
+ <% end %>
76
+ <% end %>
data/lib/blocks.rb ADDED
@@ -0,0 +1,7 @@
1
+ module Blocks; end
2
+
3
+ require 'blocks/context'
4
+ require 'blocks/table_for'
5
+ # require 'blocks/helper'
6
+
7
+
@@ -0,0 +1,197 @@
1
+ module Blocks
2
+ class Container
3
+ attr_accessor :name, :options, :block
4
+ end
5
+
6
+ class Context
7
+
8
+ attr_accessor :view, :blocks, :block_positions, :anonymous_block_number,
9
+ :start_rendering_blocks, :block_groups, :shared_options
10
+
11
+ # If a method is missing, we'll assume the user is starting a new block group by that missing method name
12
+ def method_missing(m, options={}, &block)
13
+ # If the specified block group has already been defined, it is simply returned here for iteration.
14
+ # It will consist of all the blocks used in this block group that have yet to be rendered,
15
+ # as the call for their use occurred before the template was rendered
16
+ return self.block_groups[m] unless self.block_groups[m].nil?
17
+
18
+ # Allows for nested block groups, store the current block positions array and start a new one
19
+ original_block_positions = self.block_positions
20
+ self.block_positions = []
21
+ self.block_groups[m] = self.block_positions
22
+
23
+ # Capture the contents of the block group (this will only capture block definitions and block uses)
24
+ view.capture(shared_options.merge(options), &block) if block_given?
25
+
26
+ # restore the original block positions array
27
+ self.block_positions = original_block_positions
28
+ nil
29
+ end
30
+
31
+ def before(name, options={}, &block)
32
+ name = "before_#{name.to_s}".to_sym
33
+
34
+ block_container = Blocks::Container.new
35
+ block_container.name = name
36
+ block_container.options = options
37
+ block_container.block = block
38
+
39
+ if blocks[name].nil?
40
+ blocks[name] = [block_container]
41
+ else
42
+ blocks[name] << block_container
43
+ end
44
+
45
+ nil
46
+ end
47
+
48
+ def after(name, options={}, &block)
49
+ name = "after_#{name.to_s}".to_sym
50
+
51
+ block_container = Blocks::Container.new
52
+ block_container.name = name
53
+ block_container.options = options
54
+ block_container.block = block
55
+
56
+ if blocks[name].nil?
57
+ blocks[name] = [block_container]
58
+ else
59
+ blocks[name] << block_container
60
+ end
61
+
62
+ nil
63
+ end
64
+
65
+ def define(name, options={}, &block)
66
+ block_container = Blocks::Container.new
67
+ block_container.name = name
68
+ block_container.options = options
69
+ block_container.block = block
70
+
71
+ blocks[name.to_sym] = block_container if blocks[name.to_sym].nil?
72
+ nil
73
+ end
74
+
75
+ def use(*args, &block)
76
+ options = args.extract_options!
77
+
78
+ # If the user doesn't specify a block name, we generate an anonymous block name to assure other
79
+ # anonymous blocks don't override its definition
80
+ name = args.first ? args.first : self.anonymous_block_name
81
+
82
+ block_container = Blocks::Container.new
83
+ block_container.name = name
84
+ block_container.options = options
85
+ block_container.block = block
86
+
87
+ blocks[name.to_sym] = block_container if !name.is_a?(Blocks::Container) and blocks[name.to_sym].nil? and block
88
+
89
+ if start_rendering_blocks
90
+ render_block name, options
91
+ else
92
+ # Delays rendering this block until the partial has been rendered and all the blocks have had a chance to be defined
93
+ self.block_positions << block_container
94
+ end
95
+ end
96
+
97
+ def render
98
+ self.start_rendering_blocks = false
99
+
100
+ if shared_options[:block]
101
+ view.capture(self, &shared_options[:block])
102
+ end
103
+
104
+ self.start_rendering_blocks = true
105
+
106
+ view.render shared_options[:template], shared_options
107
+ end
108
+
109
+ protected
110
+
111
+ def initialize(options)
112
+ self.view = options[:view]
113
+ self.shared_options = options
114
+
115
+ options[options[:variable] ? options[:variable].to_sym : :blocks] = self
116
+ options[:templates_folder] = "blocks" if options[:templates_folder].nil?
117
+
118
+ self.block_positions = []
119
+ self.blocks = {}
120
+ self.anonymous_block_number = 0
121
+ self.block_groups = {}
122
+ self.start_rendering_blocks = true
123
+ end
124
+
125
+ def anonymous_block_name
126
+ self.anonymous_block_number = self.anonymous_block_number + 1
127
+ "block_#{anonymous_block_number}"
128
+ end
129
+
130
+ def render_block(name_or_container, options={})
131
+ render_options = options
132
+
133
+ if (name_or_container.is_a?(Blocks::Container))
134
+ name = name_or_container.name.to_sym
135
+ render_options = render_options.merge(name_or_container.options)
136
+ else
137
+ name = name_or_container.to_sym
138
+ end
139
+
140
+ ret = render_before_blocks(name, options)
141
+
142
+ if blocks[name]
143
+ block_container = blocks[name]
144
+ ret.concat(view.capture shared_options.merge(block_container.options).merge(render_options), &block_container.block)
145
+ elsif view.request_blocks.blocks[name]
146
+ block_container = view.request_blocks.blocks[name]
147
+ ret.concat(view.capture shared_options.merge(block_container.options).merge(render_options), &block_container.block)
148
+ else
149
+ begin
150
+ ret.concat(view.render "#{shared_options[:templates_folder]}/#{name.to_s}", shared_options.merge(render_options))
151
+ rescue
152
+
153
+ end
154
+ end
155
+
156
+ ret.concat(render_after_blocks(name, options))
157
+ end
158
+
159
+ def render_before_blocks(name, options={})
160
+ name = "before_#{name.to_s}".to_sym
161
+
162
+ ret = ActionView::NonConcattingString.new
163
+ unless blocks[name].nil?
164
+ blocks[name].each do |block_container|
165
+ ret.concat(view.capture shared_options.merge(block_container.options).merge(options), &block_container.block)
166
+ end
167
+ end
168
+
169
+ unless view.request_blocks.blocks[name].nil?
170
+ view.request_blocks.blocks[name].each do |block_container|
171
+ ret.concat(view.capture shared_options.merge(block_container.options).merge(options), &block_container.block)
172
+ end
173
+ end
174
+
175
+ ret
176
+ end
177
+
178
+ def render_after_blocks(name, options={})
179
+ name = "after_#{name.to_s}".to_sym
180
+
181
+ ret = ActionView::NonConcattingString.new
182
+ unless blocks[name].nil?
183
+ blocks[name].each do |block_container|
184
+ ret.concat(view.capture shared_options.merge(block_container.options).merge(options), &block_container.block)
185
+ end
186
+ end
187
+
188
+ unless view.request_blocks.blocks[name].nil?
189
+ view.request_blocks.blocks[name].each do |block_container|
190
+ ret.concat(view.capture shared_options.merge(block_container.options).merge(options), &block_container.block)
191
+ end
192
+ end
193
+
194
+ ret
195
+ end
196
+ end
197
+ end
@@ -0,0 +1,13 @@
1
+ require "blocks"
2
+ require "rails"
3
+
4
+ module Blocks
5
+ class Engine < Rails::Engine
6
+ engine_name :blocks
7
+ initializer "blocks.initialize_helpers" do
8
+ ActionView::Base.class_eval do
9
+ include Blocks::Helper
10
+ end
11
+ end
12
+ end
13
+ end
@@ -0,0 +1,18 @@
1
+ module Blocks
2
+ class TableFor < Blocks::Context
3
+ alias columns block_positions
4
+ alias column use
5
+
6
+ def header(name, options={}, &block)
7
+ define("#{name.to_s}_header", options, &block)
8
+ end
9
+
10
+ def initialize(options)
11
+ options[:template] = "blocks/tables/table"
12
+ options[:templates_folder] = "tables"
13
+ options[:record_variable] = "records"
14
+ options[:variable] = "table"
15
+ super
16
+ end
17
+ end
18
+ end
metadata ADDED
@@ -0,0 +1,75 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: blocks
3
+ version: !ruby/object:Gem::Version
4
+ hash: 9
5
+ prerelease: false
6
+ segments:
7
+ - 0
8
+ - 1
9
+ version: "0.1"
10
+ platform: ruby
11
+ authors:
12
+ - Andrew Hunter
13
+ - Todd Fisher
14
+ autorequire:
15
+ bindir: bin
16
+ cert_chain: []
17
+
18
+ date: 2010-12-06 00:00:00 -05:00
19
+ default_executable:
20
+ dependencies: []
21
+
22
+ description: Blocks makes it easy to create advanced ERB helpers
23
+ email: andrew@captico.com
24
+ executables: []
25
+
26
+ extensions: []
27
+
28
+ extra_rdoc_files:
29
+ - LICENSE
30
+ - README
31
+ files:
32
+ - lib/blocks/context.rb
33
+ - lib/blocks/engine.rb
34
+ - lib/blocks/table_for.rb
35
+ - lib/blocks.rb
36
+ - app/views/blocks/tables/_table.html.erb
37
+ - README
38
+ - LICENSE
39
+ has_rdoc: true
40
+ homepage: http://blocks.rubyforge.org/
41
+ licenses: []
42
+
43
+ post_install_message:
44
+ rdoc_options: []
45
+
46
+ require_paths:
47
+ - lib
48
+ - app
49
+ required_ruby_version: !ruby/object:Gem::Requirement
50
+ none: false
51
+ requirements:
52
+ - - ">="
53
+ - !ruby/object:Gem::Version
54
+ hash: 3
55
+ segments:
56
+ - 0
57
+ version: "0"
58
+ required_rubygems_version: !ruby/object:Gem::Requirement
59
+ none: false
60
+ requirements:
61
+ - - ">="
62
+ - !ruby/object:Gem::Version
63
+ hash: 3
64
+ segments:
65
+ - 0
66
+ version: "0"
67
+ requirements: []
68
+
69
+ rubyforge_project: blocks
70
+ rubygems_version: 1.3.7
71
+ signing_key:
72
+ specification_version: 3
73
+ summary: blocks makes erb fun again
74
+ test_files: []
75
+