table_helper 0.0.5 → 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,119 +1,116 @@
1
1
  require 'table_helper/body_row'
2
2
 
3
- module PluginAWeek #:nodoc:
4
- module TableHelper
5
- # Represents the body of the table. In HTML, you can think of this as
6
- # the <tbody> tag of the table.
7
- class Body < HtmlElement
8
- # If set to :odd or :even, every odd or even-numbered row will have the
9
- # class 'alternate' appended to its html attributes, respectively.
10
- # Default is nil.
11
- attr_accessor :alternate_rows
3
+ module TableHelper
4
+ # Represents the body of the table. In HTML, you can think of this as
5
+ # the <tbody> tag of the table.
6
+ class Body < HtmlElement
7
+ # If set to :odd or :even, every odd or even-numbered row will have the
8
+ # class 'alternate' appended to its html attributes. Default is nil.
9
+ attr_accessor :alternate_rows
10
+
11
+ # The caption to display in the collection is empty
12
+ attr_accessor :empty_caption
13
+
14
+ def initialize(collection, header) #:nodoc:
15
+ super()
12
16
 
13
- # The caption to display in the collection is empty
14
- attr_accessor :empty_caption
17
+ @collection, @header = collection, header
18
+ @empty_caption = 'No matches found.'
19
+ end
20
+
21
+ def alternate_rows=(value) #:nodoc:
22
+ raise ArgumentError, 'alternate_rows must be set to :odd or :even' if value && ![:odd, :even].include?(value)
23
+ @alternate_rows = value
24
+ end
25
+
26
+ # Builds the body of the table. This includes the actual data that is
27
+ # generated for each object in the collection.
28
+ #
29
+ # +build+ expects a block that defines the data in each cell. Each
30
+ # iteration of the block will provide the object being rendered, the row
31
+ # within the table that will be built and the index of the object. For
32
+ # example,
33
+ #
34
+ # body.build do |row, post, index|
35
+ # row.title "<div class=\"wrapped\">#{post.title}</div>"
36
+ # row.category post.category.name
37
+ # end
38
+ #
39
+ # In addition, to specifying the data, you can also modify the html
40
+ # options of the row. For more information on doing this, see the
41
+ # BodyRow class.
42
+ #
43
+ # If the collection is empty and +empty_caption+ is set on the body,
44
+ # then the actual body will be replaced by a single row containing the
45
+ # html that was stored in +empty_caption+.
46
+ #
47
+ # == Default Values
48
+ #
49
+ # Whenever possible, the default value of a cell will be set to the
50
+ # object's attribute with the same name as the cell. For example,
51
+ # if a Post consists of the attribute +title+, then the cell for the
52
+ # title will be prepopulated with that attribute's value:
53
+ #
54
+ # body.build do |row, post index|
55
+ # row.category post.category.name
56
+ # end
57
+ #
58
+ # <tt>row.title</tt> is already set to post.category so there's no need to
59
+ # manually set the value of that cell. However, it is always possible
60
+ # to override the default value like so:
61
+ #
62
+ # body.build do |row, post, index|
63
+ # row.title link_to(post.title, post_url(post))
64
+ # row.category post.category.name
65
+ # end
66
+ def build(&block)
67
+ @content = ''
15
68
 
16
- def initialize(collection, header) #:nodoc:
17
- super()
69
+ # Display nothing if there are no objects to display
70
+ if @collection.empty? && @empty_caption
71
+ row = Row.new
72
+ row[:class] = 'no_content'
18
73
 
19
- @collection, @header = collection, header
20
- @empty_caption = 'No matches found.'
21
- end
22
-
23
- def alternate_rows=(value) #:nodoc:
24
- raise ArgumentError, 'alternate_rows must be set to :odd or :even' if value && ![:odd, :even].include?(value)
25
- @alternate_rows = value
26
- end
27
-
28
- # Builds the body of the table. This includes the actual data that is
29
- # generated for each object in the collection.
30
- #
31
- # build expects a block that defines the data in each cell. Each
32
- # iteration of the block will provide the object being rendered, the row
33
- # within the table that will be built and the index of the object. For
34
- # example,
35
- #
36
- # body.build do |row, post, index|
37
- # row.title "<div class=\"wrapped\">#{post.title}</div>"
38
- # row.category post.category.name
39
- # end
40
- #
41
- # In addition, to specifying the data, you can also modify the html
42
- # options of the row. For more information on doing this, see the
43
- # BodyRow class.
44
- #
45
- # If the collection is empty and +empty_caption+ is set on the Body,
46
- # then the actual body will be replaced by a single row containing the
47
- # html that was stored in +empty_caption+.
48
- #
49
- # == Default Values
50
- #
51
- # Whenever possible, the default value of a cell will be set to the
52
- # object's attribute with the same name as the cell. For example,
53
- # if a Post consists of the attribute +title+, then the cell for the
54
- # title will be prepopulated with that attribute's value:
55
- #
56
- # body.build do |row, post index|
57
- # row.category post.category.name
58
- # end
59
- #
60
- # +row.title+ is already set to post.category so there's no need to
61
- # manually set the value of that cell. However, it is always possible
62
- # to override the default value like so:
63
- #
64
- # body.build do |row, post, index|
65
- # row.title link_to(post.title, post_url(post))
66
- # row.category post.category.name
67
- # end
68
- def build(&block)
69
- @content = ''
74
+ html_options = {}
75
+ html_options[:colspan] = @header.column_names.size if @header.column_names.size > 1
76
+ row.cell nil, @empty_caption, html_options
70
77
 
71
- # Display nothing if there are no objects to display
72
- if @collection.empty? && @empty_caption
73
- row = Row.new
74
- row[:class] = 'no_content'
75
-
76
- html_options = {}
77
- html_options[:colspan] = @header.column_names.size if @header.column_names.size > 1
78
- row.cell nil, @empty_caption, html_options
79
-
80
- @content << row.html
81
- else
82
- @collection.each_with_index do |object, i|
83
- @content << build_row(object, i, &block)
84
- end
78
+ @content << row.html
79
+ else
80
+ @collection.each_with_index do |object, i|
81
+ @content << build_row(object, i, &block)
85
82
  end
86
-
87
- @content
88
83
  end
89
84
 
90
- # Builds a row for an object in the table.
91
- #
92
- # The provided block should set the values for each cell in the row.
93
- def build_row(object, index = @collection.index(object), &block)
94
- row = BodyRow.new(object, @header)
95
- row.alternate = alternate_rows ? index.send("#{@alternate_rows}?") : false
96
-
97
- yield row.builder, object, index if block_given?
98
-
99
- row.html
100
- end
85
+ @content
86
+ end
87
+
88
+ # Builds a row for an object in the table.
89
+ #
90
+ # The provided block should set the values for each cell in the row.
91
+ def build_row(object, index = @collection.index(object), &block)
92
+ row = BodyRow.new(object, @header)
93
+ row.alternate = alternate_rows ? index.send("#{@alternate_rows}?") : false
101
94
 
102
- def html #:nodoc:
103
- html_options = @html_options.dup
104
- html_options[:class] = (html_options[:class].to_s + ' alternate').strip if alternate_rows
105
-
106
- content_tag(tag_name, content, html_options)
107
- end
95
+ yield row.builder, object, index if block_given?
108
96
 
109
- private
110
- def tag_name
111
- 'tbody'
112
- end
113
-
114
- def content
115
- @content
116
- end
97
+ row.html
117
98
  end
99
+
100
+ def html #:nodoc:
101
+ html_options = @html_options.dup
102
+ html_options[:class] = (html_options[:class].to_s + ' alternate').strip if alternate_rows
103
+
104
+ content_tag(tag_name, content, html_options)
105
+ end
106
+
107
+ private
108
+ def tag_name
109
+ 'tbody'
110
+ end
111
+
112
+ def content
113
+ @content
114
+ end
118
115
  end
119
116
  end
@@ -1,86 +1,70 @@
1
1
  require 'table_helper/row'
2
2
 
3
- module PluginAWeek #:nodoc:
4
- module TableHelper
5
- # Represents a single row within the body of a table. The row can consist
6
- # of either data cells or header cells.
7
- #
8
- # == Borders
9
- #
10
- # Each row has an optional special border row that can be generated either
11
- # immediately before or immediately after this row. A separate border row
12
- # is usually used when you cannot express borders in the css of the row
13
- # containing the data (e.g. dotted borders in Internet Explorer).
14
- #
15
- # To modify the properties of the border, you can access +row.border+ like
16
- # so:
17
- #
18
- # r = BodyRow.new
19
- # r.border_type = :before
20
- # r.border[:style] = 'color: #ff0000;'
21
- #
22
- # == Alternating rows
23
- #
24
- # Alternating rows can be automated by setting the +alternate+ property.
25
- # For example,
26
- #
27
- # r = BodyRow.new
28
- # r.alternate = true
29
- class BodyRow < Row
30
- # True if this is an alternating row, otherwise false. Default is false.
31
- attr_accessor :alternate
3
+ module TableHelper
4
+ # Represents a single row within the body of a table. The row can consist
5
+ # of either data cells or header cells.
6
+ #
7
+ # == Alternating rows
8
+ #
9
+ # Alternating rows can be automated by setting the +alternate+ property.
10
+ # For example,
11
+ #
12
+ # r = BodyRow.new
13
+ # r.alternate = true
14
+ class BodyRow < Row
15
+ # True if this is an alternating row, otherwise false. Default is false.
16
+ attr_accessor :alternate
17
+
18
+ def initialize(object, header) #:nodoc:
19
+ super()
32
20
 
33
- def initialize(object, header) #:nodoc:
34
- super()
35
-
36
- @header = header
37
- @alternate = false
38
- @html_options[:class] = ('row ' + @html_options[:class].to_s).strip
21
+ @header = header
22
+ @alternate = false
23
+ @html_options[:class] = ('row ' + @html_options[:class].to_s).strip
24
+
25
+ # For each column defined in the table, see if we can prepopulate the
26
+ # cell based on the data in the object. If not, we can at least
27
+ # provide shortcut accessors to the cell
28
+ @header.column_names.each do |column|
29
+ if object.respond_to?(column)
30
+ cell(column, object.send(column))
31
+ else
32
+ builder.define_cell(column)
33
+ end
34
+ end
35
+ end
36
+
37
+ # Generates the html for this row in additional to the border row
38
+ # (if specified)
39
+ def html
40
+ original_options = @html_options.dup
41
+ @html_options[:class] = (@html_options[:class].to_s + ' alternate').strip if alternate
42
+ html = super
43
+ @html_options = original_options
44
+ html
45
+ end
46
+
47
+ private
48
+ # Builds the row's cells based on the order of the columns in the
49
+ # header. If a cell cannot be found for a specific column, then a blank
50
+ # cell is rendered.
51
+ def content
52
+ number_to_skip = 0 # Keeps track of the # of columns to skip
39
53
 
40
- # For each column defined in the table, see if we can prepopulate the
41
- # cell based on the data in the object. If not, we can at least
42
- # provide shortcut accessors to the cell
54
+ html = ''
43
55
  @header.column_names.each do |column|
44
- if object.respond_to?(column)
45
- cell(column, object.send(column))
56
+ number_to_skip -= 1 and next if number_to_skip > 0
57
+
58
+ if cell = @cells[column]
59
+ number_to_skip = (cell[:colspan] || 1) - 1
46
60
  else
47
- builder.define_cell(column)
61
+ cell = Cell.new(column, '', :class => 'empty')
48
62
  end
63
+
64
+ html << cell.html
49
65
  end
50
- end
51
-
52
- # Generates the html for this row in additional to the border row
53
- # (if specified)
54
- def html
55
- original_options = @html_options.dup
56
- @html_options[:class] = (@html_options[:class].to_s + ' alternate').strip if alternate
57
- html = super
58
- @html_options = original_options
66
+
59
67
  html
60
68
  end
61
-
62
- private
63
- # Builds the row's cells based on the order of the columns in the
64
- # header. If a cell cannot be found for a specific column, then a blank
65
- # cell is rendered.
66
- def content
67
- number_to_skip = 0 # Keeps track of the # of columns to skip
68
-
69
- html = ''
70
- @header.column_names.each do |column|
71
- number_to_skip -= 1 and next if number_to_skip > 0
72
-
73
- if cell = @cells[column]
74
- number_to_skip = (cell[:colspan] || 1) - 1
75
- else
76
- cell = Cell.new(column, '', :class => 'empty')
77
- end
78
-
79
- html << cell.html
80
- end
81
-
82
- html
83
- end
84
- end
85
69
  end
86
70
  end
@@ -1,51 +1,49 @@
1
- module PluginAWeek #:nodoc:
2
- module TableHelper
3
- # Represents a single cell within a table. This can either be a regular
4
- # data cell (td) or a header cell (th). By default, all cells will have
5
- # their column name appended to the cell's class attribute.
6
- #
7
- # == Creating data cells
8
- #
9
- # Cell.new(:author, 'John Doe').build
10
- #
11
- # ...would generate the following tag:
12
- #
13
- # <td class="author">John Doe</td>
14
- #
15
- # == Creating header cells
16
- #
17
- # c = Cell.new(:author, 'Author Name')
18
- # c.content_type = :header
19
- # c.build
20
- #
21
- # ...would generate the following tag:
22
- #
23
- # <th class="author">Author Name</th>
24
- class Cell < HtmlElement
25
- def initialize(class_name, content = class_name.to_s.titleize, html_options = {}) #:nodoc
26
- super(html_options)
27
-
28
- @content = content
29
- @html_options[:class] = ("#{class_name} " + @html_options[:class].to_s).strip if class_name
30
-
31
- self.content_type = :data
32
- end
1
+ module TableHelper
2
+ # Represents a single cell within a table. This can either be a regular
3
+ # data cell (td) or a header cell (th). By default, all cells will have
4
+ # their column name appended to the cell's class attribute.
5
+ #
6
+ # == Creating data cells
7
+ #
8
+ # Cell.new(:author, 'John Doe').build
9
+ #
10
+ # ...would generate the following tag:
11
+ #
12
+ # <td class="author">John Doe</td>
13
+ #
14
+ # == Creating header cells
15
+ #
16
+ # c = Cell.new(:author, 'Author Name')
17
+ # c.content_type = :header
18
+ # c.build
19
+ #
20
+ # ...would generate the following tag:
21
+ #
22
+ # <th class="author">Author Name</th>
23
+ class Cell < HtmlElement
24
+ def initialize(class_name, content = class_name.to_s.titleize, html_options = {}) #:nodoc
25
+ super(html_options)
33
26
 
34
- # Indicates what type of content will be stored in this cell. This can
35
- # either be set to either :data or :header.
36
- def content_type=(value)
37
- raise ArgumentError, "content_type must be set to :data or :header, was: #{value.inspect}" unless [:data, :header].include?(value)
38
- @content_type = value
39
- end
27
+ @content = content
28
+ @html_options[:class] = ("#{class_name} " + @html_options[:class].to_s).strip if class_name
40
29
 
41
- private
42
- def tag_name
43
- @content_type == :data ? 'td' : 'th'
44
- end
45
-
46
- def content
47
- @content
48
- end
30
+ self.content_type = :data
31
+ end
32
+
33
+ # Indicates what type of content will be stored in this cell. This can
34
+ # be set to either :data or :header.
35
+ def content_type=(value)
36
+ raise ArgumentError, "content_type must be set to :data or :header, was: #{value.inspect}" unless [:data, :header].include?(value)
37
+ @content_type = value
49
38
  end
39
+
40
+ private
41
+ def tag_name
42
+ @content_type == :data ? 'td' : 'th'
43
+ end
44
+
45
+ def content
46
+ @content
47
+ end
50
48
  end
51
49
  end