trenni-formatters 0.5.3 → 1.0.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 3010072052341464ed8f33309fd8b9b59b827c8b
4
- data.tar.gz: 4d4e10b75652a479706624c450ef5905c67507d0
3
+ metadata.gz: 38446eb1ee4817cddda1a893f8ac201d994102cd
4
+ data.tar.gz: 0a5bdcf731d0aab78c21cb8ec379c385aff4c561
5
5
  SHA512:
6
- metadata.gz: dc49678aecb21aef566d29fd8c4e1a8dbb734d54160dc76b6c39ef28b1dfe581000de5723080f840374bceca8f5dfa87471e0707213004b00df038bc52e2cce1
7
- data.tar.gz: e6a51446102c792d38f64315ffbd64bdf55ac091048fd3a2bf3a4ac3bc3438f6e4b4ffea49b18cd3c3cb34dc27425dddfa7069d816555d50ddaad99f93ea9aa6
6
+ metadata.gz: 5c764c5ed7624b752f6fa3c1171db00f945bb1c449bc115cc06cdd9fe849c4bee7d0124e9ff291fe779e3944d75b4449d7e19b093454cbfb49b5236a8760ceb5
7
+ data.tar.gz: 693f5abca9f92b155338aa2a7d2bbd0a1f9c61cfec40b5d910e5f226e2333cf5a885524075b9bffb8d42c7a8fd3c3bb421b7755dff4418e20e22eea2d835f278
data/README.md CHANGED
@@ -11,19 +11,23 @@ formatting needs.
11
11
  [![Code Climate](https://codeclimate.com/github/ioquatix/trenni-formatters.png)](https://codeclimate.com/github/ioquatix/trenni-formatters)
12
12
  [![Coverage Status](https://coveralls.io/repos/ioquatix/trenni-formatters/badge.svg)](https://coveralls.io/r/ioquatix/trenni-formatters)
13
13
 
14
+ ## Motivation
15
+
16
+ `Trenni::Formatters` was a library extracted from [Financier](https://github.com/ioquatix/financier) which is a CouchDB backed invoicing system, itself, derived from an old Rails app. I was a bit envious of `form_for` in terms of the ease of generating forms, but found that it wasn't very extendable. I also found myself generating code to format model data as rich HTML. `Trenni::Formatters` attempts to be an easily extendable formatting module which can generate rich text, links and HTML.
17
+
14
18
  ## Installation
15
19
 
16
20
  Add this line to your application's Gemfile:
17
21
 
18
- gem 'trenni-formatters'
22
+ gem 'trenni-formatters'
19
23
 
20
24
  And then execute:
21
25
 
22
- $ bundle
26
+ $ bundle
23
27
 
24
28
  Or install it yourself as:
25
29
 
26
- $ gem install trenni-formatters
30
+ $ gem install trenni-formatters
27
31
 
28
32
  ## Usage
29
33
 
@@ -36,9 +40,9 @@ a mapping corresponding to the objects type:
36
40
  "String: #{value}"
37
41
  end
38
42
 
39
- assert_equal "String: foobar", formatter.format("foobar")
43
+ expect(formatter.format("foobar")).to be == "String: foobar"
40
44
 
41
- For more examples please see `test/`.
45
+ For more examples please see `spec/`.
42
46
 
43
47
  ## Contributing
44
48
 
@@ -0,0 +1,34 @@
1
+ # Copyright, 2012, by Samuel G. D. Williams. <http://www.codeotaku.com>
2
+ #
3
+ # Permission is hereby granted, free of charge, to any person obtaining a copy
4
+ # of this software and associated documentation files (the "Software"), to deal
5
+ # in the Software without restriction, including without limitation the rights
6
+ # to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
7
+ # copies of the Software, and to permit persons to whom the Software is
8
+ # furnished to do so, subject to the following conditions:
9
+ #
10
+ # The above copyright notice and this permission notice shall be included in
11
+ # all copies or substantial portions of the Software.
12
+ #
13
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
14
+ # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
15
+ # FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
16
+ # AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
17
+ # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
18
+ # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
19
+ # THE SOFTWARE.
20
+
21
+ require 'sanitize'
22
+ require 'kramdown'
23
+
24
+ module Trenni::Formatters::Format
25
+ module Markdown
26
+ def markdown(text)
27
+ config = Sanitize::Config::BASIC.dup
28
+
29
+ config[:elements] += ['h1', 'h2', 'h3']
30
+
31
+ Sanitize.clean(Kramdown::Document.new(text).to_html, config)
32
+ end
33
+ end
34
+ end
@@ -0,0 +1,50 @@
1
+ # Copyright, 2012, by Samuel G. D. Williams. <http://www.codeotaku.com>
2
+ #
3
+ # Permission is hereby granted, free of charge, to any person obtaining a copy
4
+ # of this software and associated documentation files (the "Software"), to deal
5
+ # in the Software without restriction, including without limitation the rights
6
+ # to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
7
+ # copies of the Software, and to permit persons to whom the Software is
8
+ # furnished to do so, subject to the following conditions:
9
+ #
10
+ # The above copyright notice and this permission notice shall be included in
11
+ # all copies or substantial portions of the Software.
12
+ #
13
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
14
+ # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
15
+ # FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
16
+ # AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
17
+ # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
18
+ # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
19
+ # THE SOFTWARE.
20
+
21
+ require 'trenni/strings'
22
+ require 'mapping/model'
23
+
24
+ module Trenni::Formatters::Format
25
+ module Text
26
+ def truncated_text(content, options = {}, &block)
27
+ if content
28
+ length = options.fetch(:length, 30)
29
+
30
+ content = self.class.truncate_text(content, length, options)
31
+
32
+ return self.format(content)
33
+ end
34
+ end
35
+
36
+ def self.truncate_text(text, truncate_at, options = {})
37
+ return text.dup unless text.length > truncate_at
38
+
39
+ options[:omission] ||= '...'
40
+ length_with_room_for_omission = truncate_at - options[:omission].length
41
+ stop = if options[:separator]
42
+ text.rindex(options[:separator], length_with_room_for_omission) || length_with_room_for_omission
43
+ else
44
+ length_with_room_for_omission
45
+ end
46
+
47
+ "#{text[0...stop]}#{options[:omission]}"
48
+ end
49
+ end
50
+ end
@@ -0,0 +1,39 @@
1
+ # Copyright, 2012, by Samuel G. D. Williams. <http://www.codeotaku.com>
2
+ #
3
+ # Permission is hereby granted, free of charge, to any person obtaining a copy
4
+ # of this software and associated documentation files (the "Software"), to deal
5
+ # in the Software without restriction, including without limitation the rights
6
+ # to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
7
+ # copies of the Software, and to permit persons to whom the Software is
8
+ # furnished to do so, subject to the following conditions:
9
+ #
10
+ # The above copyright notice and this permission notice shall be included in
11
+ # all copies or substantial portions of the Software.
12
+ #
13
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
14
+ # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
15
+ # FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
16
+ # AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
17
+ # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
18
+ # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
19
+ # THE SOFTWARE.
20
+
21
+ require 'trenni/strings'
22
+ require 'mapping/model'
23
+
24
+ module Trenni::Formatters::Format
25
+ module Time
26
+ def included(base)
27
+ base.map(Time) do |object, options|
28
+ # Ensure we display the time in localtime, and show the year if it is different:
29
+ if object.localtime.year != Time.now.year
30
+ object.localtime.strftime("%B %-d, %-l:%M%P, %Y")
31
+ else
32
+ object.localtime.strftime("%B %-d, %-l:%M%P")
33
+ end
34
+ end
35
+ end
36
+ end
37
+ end
38
+ end
39
+
@@ -19,24 +19,30 @@
19
19
  # THE SOFTWARE.
20
20
 
21
21
  require 'trenni/strings'
22
+ require 'mapping/model'
22
23
 
23
24
  module Trenni
24
25
  module Formatters
25
- class Formatter
26
+ class Formatter < Mapping::Model
26
27
  def initialize(options = {})
27
28
  @options = options
28
- @formatters = {}
29
+ end
30
+
31
+ def format_unspecified(object, options)
32
+ if object
33
+ Strings::to_html(object.to_s)
34
+ else
35
+ options[:blank] || ""
36
+ end
29
37
  end
30
38
 
31
39
  def format(object, options = {})
32
- if formatter = @formatters[object.class]
33
- formatter.call(object, options)
40
+ method_name = self.method_for_mapping(object)
41
+
42
+ if self.respond_to?(method_name)
43
+ self.send(method_name, object, options)
34
44
  else
35
- if object
36
- Strings::to_html(object.to_s)
37
- else
38
- options[:blank] || ""
39
- end
45
+ format_unspecified(object, options)
40
46
  end
41
47
  end
42
48
 
@@ -45,10 +51,6 @@ module Trenni
45
51
  def [] key
46
52
  @options[key]
47
53
  end
48
-
49
- def for(klass, &block)
50
- @formatters[klass] = block
51
- end
52
54
  end
53
55
  end
54
56
  end
@@ -34,8 +34,14 @@ module Trenni
34
34
  options = @options.merge(options)
35
35
 
36
36
  Builder.fragment do |builder|
37
- builder.inline(:dt) { builder.text title_for(options) }
38
-
37
+ builder.inline(:dt) do
38
+ builder.text title_for(options)
39
+
40
+ if details = details_for(options)
41
+ builder.inline(:small) { builder.text details }
42
+ end
43
+ end
44
+
39
45
  builder.inline(:dd) do
40
46
  builder.tag :input, input_attributes_for(options)
41
47
  end
@@ -50,7 +56,9 @@ module Trenni
50
56
  builder.inline(:dt) { builder.text title_for(options) }
51
57
 
52
58
  builder.inline(:dd) do
53
- builder.tag :output, output_attributes_for(options)
59
+ builder.inline :output, output_attributes_for(options) do
60
+ builder.text value_for(options)
61
+ end
54
62
  end
55
63
  end
56
64
  end
@@ -60,7 +68,13 @@ module Trenni
60
68
  options = @options.merge(options)
61
69
 
62
70
  Builder.fragment do |builder|
63
- builder.inline(:dt) { builder.text title_for(options) }
71
+ builder.tag(:dt) do
72
+ builder.text title_for(options)
73
+
74
+ if details = details_for(options)
75
+ builder.inline(:small) { builder.text details }
76
+ end
77
+ end
64
78
 
65
79
  builder.inline(:dd) do
66
80
  builder.tag :textarea, textarea_attributes_for(options) do
@@ -77,8 +91,11 @@ module Trenni
77
91
  Builder.fragment do |builder|
78
92
  builder.tag(:dd) do
79
93
  builder.tag :input, :type => :hidden, :name => name_for(options), :value => 'false'
80
- builder.tag :input, checkbox_attributes_for(options)
81
- builder.text " " + title_for(options)
94
+ builder.inline(:label) do
95
+ builder.tag :input, checkbox_attributes_for(options)
96
+ # We would like a little bit of whitespace between the checkbox and the title.
97
+ builder.text " " + title_for(options)
98
+ end
82
99
  end
83
100
  end
84
101
  end
@@ -86,13 +103,8 @@ module Trenni
86
103
  # A submission button
87
104
  def submit(options = {})
88
105
  options = @options.merge(options)
106
+ options[:title] ||= submit_title_for(options)
89
107
 
90
- if title = title_for(options)
91
- options[:title] = title
92
- else
93
- options[:title] ||= new_record? ? 'Create' : 'Update'
94
- end
95
-
96
108
  Builder.fragment do |builder|
97
109
  builder.tag :input, submit_attributes_for(options)
98
110
  end
@@ -103,7 +115,14 @@ module Trenni
103
115
  buffer = Trenni::Template.buffer(block.binding)
104
116
 
105
117
  buffer << Builder.fragment do |builder|
106
- builder.inline(:dt) { builder.text title_for(options) }
118
+ builder.inline(:dt) do
119
+ builder.text title_for(options)
120
+
121
+ if details = details_for(options)
122
+ builder.inline(:small) { builder.text details }
123
+ end
124
+ end
125
+
107
126
  builder.tag(:dd) do
108
127
  klass.call(self, options, builder, &block)
109
128
  end
@@ -37,10 +37,15 @@ module Trenni
37
37
  return !object.saved?
38
38
  end
39
39
  end
40
-
40
+
41
+ # Any additional details relating to a field (e.g. explanation text)
42
+ def details_for(options)
43
+ options[:details]
44
+ end
45
+
41
46
  # The name of the field, used for the name attribute of an input.
42
47
  def name_for(options)
43
- (options[:name] || options[:field]).to_s
48
+ options[:name] || options[:field]
44
49
  end
45
50
 
46
51
  def field_for(options)
@@ -49,17 +54,21 @@ module Trenni
49
54
 
50
55
  # A title is a text string that will be displayed next to or on top of the control to describe it or its value:
51
56
  def title_for(options)
52
- title = options[:title]
53
- return Strings::to_html(title) if title
54
-
55
- field_name = field_for(options)
57
+ if title = options[:title]
58
+ return title
59
+ end
56
60
 
57
- # Remove postfix "_id" or "_ids":
58
- return Strings::to_title(field_name.to_s.sub(/_ids?/, '')) if field_name
61
+ # Generate a title from a field name:
62
+ if field_name = field_for(options)
63
+ # Remove postfix "_id" or "_ids":
64
+ return Strings::to_title(field_name.to_s.sub(/_ids?/, ''))
65
+ end
59
66
  end
60
67
 
61
68
  def object_value_for(options)
62
- options[:object].send(field_for(options)) if options[:object]
69
+ if object = options[:object] and field = field_for(options)
70
+ object.send(field)
71
+ end
63
72
  end
64
73
 
65
74
  def raw_value_for(options)
@@ -71,7 +80,9 @@ module Trenni
71
80
 
72
81
  # The value of the field.
73
82
  def value_for(options)
74
- self.format(raw_value_for(options), options)
83
+ if value = raw_value_for(options)
84
+ self.format(value, options)
85
+ end
75
86
  end
76
87
 
77
88
  def pattern_for(options)
@@ -157,7 +168,11 @@ module Trenni
157
168
  :value => title_for(options),
158
169
  }
159
170
  end
160
-
171
+
172
+ def submit_title_for(options)
173
+ title_for(options) || (new_record? ? 'Create' : 'Update')
174
+ end
175
+
161
176
  def hidden_attributes_for(options)
162
177
  return {
163
178
  :type => options[:type] || 'hidden',
@@ -176,6 +191,38 @@ module Trenni
176
191
  builder.tag :input, hidden_attributes_for(options)
177
192
  end
178
193
  end
194
+
195
+ def button_attributes_for(options)
196
+ return {
197
+ :type => options[:type] || 'submit',
198
+ :name => name_for(options),
199
+ :id => options[:id],
200
+ :class => options[:class],
201
+ :disabled => options[:disabled],
202
+ :value => value_for(options),
203
+ }
204
+ end
205
+
206
+ def button_title_for(options)
207
+ type = options.fetch(:type, 'submit').to_sym
208
+
209
+ if type == :submit
210
+ submit_title_for(options)
211
+ else
212
+ title_for(options) || Strings::to_title(type.to_s)
213
+ end
214
+ end
215
+
216
+ # A hidden field.
217
+ def button(options = {})
218
+ options = @options.merge(options)
219
+
220
+ Builder.fragment do |builder|
221
+ builder.inline :button, button_attributes_for(options) do
222
+ builder.text button_title_for(options)
223
+ end
224
+ end
225
+ end
179
226
  end
180
227
  end
181
228
  end
@@ -42,13 +42,13 @@ module Trenni
42
42
  end
43
43
 
44
44
  def name_for(options)
45
- name = @formatter.name_for(options)
46
-
47
- if options[:multiple]
48
- name += '[]'
45
+ if name = @formatter.name_for(options)
46
+ if options[:multiple]
47
+ name = "#{name}[]"
48
+ end
49
+
50
+ return name
49
51
  end
50
-
51
- return name
52
52
  end
53
53
 
54
54
  def value_for(options)
@@ -85,7 +85,7 @@ module Trenni
85
85
  end
86
86
 
87
87
  def group(options = {}, &block)
88
- Builder.fragment do |builder|
88
+ Builder.fragment(@builder) do |builder|
89
89
  builder.tag :optgroup, group_attributes_for(options) do
90
90
  if options[:optional]
91
91
  item(:title => '', :value => '', :builder => builder)
@@ -24,7 +24,7 @@ module Trenni
24
24
  module Formatters
25
25
  module HTML
26
26
  # Table based select boxes using per-row checkboxes.
27
- class TableSelect
27
+ class RadioSelect
28
28
  def self.call(formatter, options, builder, &block)
29
29
  instance = self.new(formatter, options, builder)
30
30
 
@@ -97,7 +97,6 @@ module Trenni
97
97
  end
98
98
  end
99
99
  end
100
-
101
100
  end
102
101
  end
103
102
  end
@@ -20,6 +20,6 @@
20
20
 
21
21
  module Trenni
22
22
  module Formatters
23
- VERSION = "0.5.3"
23
+ VERSION = "1.0.0"
24
24
  end
25
25
  end
@@ -20,8 +20,6 @@
20
20
 
21
21
  require 'trenni/formatters'
22
22
  require 'trenni/formatters/html/definition_list_form'
23
- require 'trenni/formatters/html/option_select'
24
- require 'trenni/formatters/html/table_select'
25
23
 
26
24
  module Trenni::Formatters::FormFormatterSpec
27
25
  class FormFormatter < Trenni::Formatters::Formatter
@@ -32,8 +30,8 @@ module Trenni::Formatters::FormFormatterSpec
32
30
  let(:formatter) {FormFormatter.new(:object => double(:bar => 10))}
33
31
 
34
32
  it "should generate form" do
35
- output_tag = formatter.input(:field => :bar)
36
- expect(output_tag).to be == %Q{<dt>Bar</dt>\n<dd><input name="bar" value="10"/></dd>}
33
+ result = formatter.input(:field => :bar)
34
+ expect(result).to be == %Q{<dt>Bar</dt>\n<dd><input name="bar" value="10"/></dd>}
37
35
  end
38
36
 
39
37
  it "should have default value" do
@@ -42,8 +40,8 @@ module Trenni::Formatters::FormFormatterSpec
42
40
  end
43
41
 
44
42
  it "should have a different title" do
45
- output_tag = formatter.input(:field => :bar, :title => "Title")
46
- expect(output_tag).to be == %Q{<dt>Title</dt>\n<dd><input name="bar" value="10"/></dd>}
43
+ result = formatter.input(:field => :bar, :title => "Title")
44
+ expect(result).to be == %Q{<dt>Title</dt>\n<dd><input name="bar" value="10"/></dd>}
47
45
  end
48
46
  end
49
47
 
@@ -57,8 +55,8 @@ module Trenni::Formatters::FormFormatterSpec
57
55
  expect(attributes[:max]).to be == 20
58
56
  expect(attributes[:step]).to be == 2
59
57
 
60
- output_tag = formatter.input(:field => :bar, :min => 10)
61
- expect(output_tag).to be == %Q{<dt>Bar</dt>\n<dd><input name="bar" value="10" min="10"/></dd>}
58
+ result = formatter.input(:field => :bar, :min => 10)
59
+ expect(result).to be == %Q{<dt>Bar</dt>\n<dd><input name="bar" value="10" min="10"/></dd>}
62
60
  end
63
61
 
64
62
  it "should not specify required, readonly or disabled" do
@@ -79,16 +77,87 @@ module Trenni::Formatters::FormFormatterSpec
79
77
  attributes = formatter.checkbox_attributes_for(:value => true)
80
78
  expect(attributes[:checked]).to be true
81
79
 
82
- output_tag = formatter.checkbox(:field => :bob)
83
- expect(output_tag).to be == %Q{<dd>\n\t<input type="hidden" name="bob" value="false"/>\t<input type="checkbox" name="bob" value="true" checked/>\tBob\n</dd>}
80
+ result = formatter.checkbox(:field => :bob)
81
+ expect(result).to be == %Q{<dd>\n\t<input type="hidden" name="bob" value="false"/>\n\t<label><input type="checkbox" name="bob" value="true" checked/> Bob</label>\n</dd>}
84
82
  end
85
83
 
86
84
  it "should generate unchecked checkbox" do
87
85
  attributes = formatter.checkbox_attributes_for(:value => false)
88
86
  expect(attributes[:checked]).to be nil
89
87
 
90
- output_tag = formatter.checkbox(:field => :dole)
91
- expect(output_tag).to be == %Q{<dd>\n\t<input type="hidden" name="dole" value="false"/>\t<input type="checkbox" name="dole" value="true"/>\tDole\n</dd>}
88
+ result = formatter.checkbox(:field => :dole)
89
+ expect(result).to be == %Q{<dd>\n\t<input type="hidden" name="dole" value="false"/>\n\t<label><input type="checkbox" name="dole" value="true"/> Dole</label>\n</dd>}
90
+ end
91
+ end
92
+
93
+ describe '<input type="hidden">' do
94
+ let(:formatter) {FormFormatter.new(:object => double(age: 20))}
95
+
96
+ it "should generate hidden field" do
97
+ result = formatter.hidden(:field => :age)
98
+ expect(result).to be == %Q{<input type="hidden" name="age" value="20"/>}
99
+ end
100
+
101
+ it "should escape characters correctly" do
102
+ result = formatter.submit
103
+ expect(result).to be == %Q{<input type="submit" value="Update"/>}
104
+ end
105
+
106
+ it "can have custom title" do
107
+ result = formatter.submit(title: 'Alice')
108
+ expect(result).to be == %Q{<input type="submit" value="Alice"/>}
109
+ end
110
+ end
111
+
112
+ describe '<input type="submit">' do
113
+ let(:new_record_formatter) {FormFormatter.new(:object => double(new_record?: true))}
114
+ let(:formatter) {FormFormatter.new(:object => double(new_record?: false))}
115
+
116
+ it "should have correct title for new_record?" do
117
+ result = new_record_formatter.submit
118
+ expect(result).to be == %Q{<input type="submit" value="Create"/>}
119
+ end
120
+
121
+ it "should escape characters correctly" do
122
+ result = formatter.submit
123
+ expect(result).to be == %Q{<input type="submit" value="Update"/>}
124
+ end
125
+
126
+ it "can have custom title" do
127
+ result = formatter.submit(title: 'Alice')
128
+ expect(result).to be == %Q{<input type="submit" value="Alice"/>}
129
+ end
130
+ end
131
+
132
+ describe "<textarea>" do
133
+ let(:formatter) {FormFormatter.new(:object => double(details: "foo<bar>"))}
134
+
135
+ it "should escape characters correctly" do
136
+ result = formatter.textarea(:field => :details)
137
+ expect(result).to be == %Q{<dt>\n\tDetails\n</dt>\n<dd><textarea name=\"details\">foo&lt;bar&gt;</textarea></dd>}
138
+ end
139
+ end
140
+
141
+ describe "<output>" do
142
+ let(:formatter) {FormFormatter.new(:object => double(bar: 10, bob: true, dole: false))}
143
+
144
+ it "should show output value" do
145
+ result = formatter.output(:field => :bar)
146
+ expect(result).to be == %Q{<dt>Bar</dt>\n<dd><output name=\"bar\">10</output></dd>}
147
+ end
148
+
149
+ it "should show output value" do
150
+ result = formatter.output(:name => :total)
151
+ expect(result).to be == %Q{<dt></dt>\n<dd><output name=\"total\"></output></dd>}
152
+ end
153
+ end
154
+
155
+ describe "<button>" do
156
+ let(:formatter) {FormFormatter.new}
157
+
158
+ it "should generate reset button" do
159
+ result = formatter.button(:type => :reset)
160
+ expect(result).to be == %Q{<button type="reset">Reset</button>}
92
161
  end
93
162
  end
94
163
  end
@@ -21,25 +21,37 @@
21
21
  require 'trenni/formatters'
22
22
 
23
23
  module Trenni::FormattersSpec
24
- describe Trenni::Formatters do
25
- before do
24
+ class TestFormatter < Trenni::Formatters::Formatter
25
+ def initialize(*)
26
26
  @count = 0
27
- @formatter = Trenni::Formatters::Formatter.new
27
+
28
+ super
29
+ end
28
30
 
29
- @formatter.for(String) do |value, options|
30
- @count += 1
31
- "String: #{value}"
32
- end
31
+ attr :count
32
+
33
+ map(String) do |value, options|
34
+ @count += 1
35
+
36
+ "String: #{value}"
33
37
  end
38
+ end
39
+
40
+ describe Trenni::Formatters do
41
+ let(:test_formatter) {TestFormatter.new(foo: :bar)}
34
42
 
35
43
  it "should format string" do
36
- expect(@formatter.format("foobar")).to be == "String: foobar"
37
- expect(@count).to be == 1
44
+ expect(test_formatter.format("foobar")).to be == "String: foobar"
45
+ expect(test_formatter.count).to be == 1
38
46
  end
39
47
 
40
48
  it "should format numbers" do
41
- expect(@formatter.format(10)).to be == "10"
42
- expect(@count).to be == 0
49
+ expect(test_formatter.format(10)).to be == "10"
50
+ expect(test_formatter.count).to be == 0
51
+ end
52
+
53
+ it "has options" do
54
+ expect(test_formatter[:foo]).to be == :bar
43
55
  end
44
56
  end
45
57
  end
@@ -19,6 +19,7 @@
19
19
  # THE SOFTWARE.
20
20
 
21
21
  require 'trenni/formatters'
22
+ require 'trenni/formatters/html/option_select'
22
23
 
23
24
  module Trenni::Formatters::HTML::OptionSelectSpec
24
25
  class FormFormatter < Trenni::Formatters::Formatter
@@ -31,10 +32,9 @@ module Trenni::Formatters::HTML::OptionSelectSpec
31
32
 
32
33
  describe Trenni::Formatters::HTML::OptionSelect do
33
34
  let(:formatter) {FormFormatter.new(:object => double(:bar => 10))}
35
+ let(:_out) {Array.new}
34
36
 
35
- it "should format items" do
36
- _out = []
37
-
37
+ it "should list items" do
38
38
  formatter.select :field => :bar do |select|
39
39
  _out << select.item(:title => "A", :value => 0)
40
40
  _out << select.item(:title => "B", :value => 10)
@@ -42,5 +42,45 @@ module Trenni::Formatters::HTML::OptionSelectSpec
42
42
 
43
43
  expect(_out.join).to be == "<dt>Bar</dt>\n<dd>\n\t<select name=\"bar\">\n\t\t<option value=\"0\">A</option><option value=\"10\" selected>B</option>\n\t</select>\n</dd>"
44
44
  end
45
+
46
+ it "should list items for multiple selection" do
47
+ formatter.select :field => :bar, multiple: true do |select|
48
+ _out << select.item(:title => "A", :value => 0)
49
+ _out << select.item(:title => "B", :value => 10)
50
+ end
51
+
52
+ expect(_out.join).to be == "<dt>Bar</dt>\n<dd>\n\t<select name=\"bar[]\" multiple>\n\t\t<option value=\"0\">A</option><option value=\"10\" selected>B</option>\n\t</select>\n</dd>"
53
+ end
54
+
55
+ it "should add optional item" do
56
+ formatter.select :field => :bar, optional: true do |select|
57
+ _out << select.item(:title => "A", :value => 0)
58
+ _out << select.item(:title => "B", :value => 10)
59
+ end
60
+
61
+ expect(_out.join).to be == "<dt>Bar</dt>\n<dd>\n\t<select name=\"bar\">\n\t\t<option value=\"\"></option>\t\t<option value=\"0\">A</option><option value=\"10\" selected>B</option>\n\t</select>\n</dd>"
62
+ end
63
+
64
+ it "should add optional item in group" do
65
+ formatter.select :field => :bar do |select|
66
+ select.group(title: 'group', optional: true) do
67
+ _out << select.item(:title => "A", :value => 0)
68
+ end
69
+ _out << select.item(:title => "B", :value => 10)
70
+ end
71
+
72
+ expect(_out.join).to be == "<dt>Bar</dt>\n<dd>\n\t<select name=\"bar\">\n\t\t<optgroup label=\"group\">\n\t\t\t<option value=\"\"></option>\t\t\t<option value=\"0\">A</option>\n\t\t</optgroup>\t\t<option value=\"10\" selected>B</option>\n\t</select>\n</dd>"
73
+ end
74
+
75
+ it "should add a group" do
76
+ formatter.select :field => :bar do |select|
77
+ select.group(title: 'group') do
78
+ _out << select.item(:title => "A", :value => 0)
79
+ end
80
+ _out << select.item(:title => "B", :value => 10)
81
+ end
82
+
83
+ expect(_out.join).to be == "<dt>Bar</dt>\n<dd>\n\t<select name=\"bar\">\n\t\t<optgroup label=\"group\">\n\t\t\t<option value=\"0\">A</option>\n\t\t</optgroup>\t\t<option value=\"10\" selected>B</option>\n\t</select>\n</dd>"
84
+ end
45
85
  end
46
86
  end
@@ -0,0 +1,46 @@
1
+ # Copyright, 2014, by Samuel G. D. Williams. <http://www.codeotaku.com>
2
+ #
3
+ # Permission is hereby granted, free of charge, to any person obtaining a copy
4
+ # of this software and associated documentation files (the "Software"), to deal
5
+ # in the Software without restriction, including without limitation the rights
6
+ # to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
7
+ # copies of the Software, and to permit persons to whom the Software is
8
+ # furnished to do so, subject to the following conditions:
9
+ #
10
+ # The above copyright notice and this permission notice shall be included in
11
+ # all copies or substantial portions of the Software.
12
+ #
13
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
14
+ # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
15
+ # FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
16
+ # AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
17
+ # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
18
+ # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
19
+ # THE SOFTWARE.
20
+
21
+ require 'trenni/formatters'
22
+ require 'trenni/formatters/html/radio_select'
23
+
24
+ module Trenni::Formatters::HTML::RadioSelectSpec
25
+ class FormFormatter < Trenni::Formatters::Formatter
26
+ include Trenni::Formatters::HTML::DefinitionListForm
27
+
28
+ def select(options = {}, &block)
29
+ element(Trenni::Formatters::HTML::RadioSelect, options, &block)
30
+ end
31
+ end
32
+
33
+ describe Trenni::Formatters::HTML::RadioSelect do
34
+ let(:formatter) {FormFormatter.new(:object => double(:bar => 10))}
35
+ let(:_out) {Array.new}
36
+
37
+ it "should list items" do
38
+ formatter.select :field => :bar do |select|
39
+ _out << select.item(:title => "A", :value => 0)
40
+ _out << select.item(:title => "B", :value => 10)
41
+ end
42
+
43
+ expect(_out.join).to be == %Q{<dt>Bar</dt>\n<dd>\n\t<table>\n\t\t<tbody>\n\t\t\t<tr>\n\t\t\t\t<td class="handle"><input type="radio" name="bar" value="0"/></td>\n\t\t\t\t<td class="item">A</td>\n\t\t\t</tr><tr>\n\t\t\t\t<td class="handle"><input type="radio" name="bar" value="10"/></td>\n\t\t\t\t<td class="item">B</td>\n\t\t\t</tr>\n\t\t</tbody>\n\t</table>\n</dd>}
44
+ end
45
+ end
46
+ end
@@ -24,7 +24,9 @@ Gem::Specification.new do |spec|
24
24
  spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
25
25
  spec.require_paths = ["lib"]
26
26
 
27
- spec.add_dependency "trenni", "~> 1.4.0"
27
+ spec.add_dependency "trenni", "~> 1.5.0"
28
+
29
+ spec.add_dependency "mapping", "~> 1.0.0"
28
30
 
29
31
  spec.add_development_dependency "bundler", "~> 1.3"
30
32
  spec.add_development_dependency "rspec", "~> 3.4.0"
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: trenni-formatters
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.5.3
4
+ version: 1.0.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Samuel Williams
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2016-01-10 00:00:00.000000000 Z
11
+ date: 2016-03-10 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: trenni
@@ -16,14 +16,28 @@ dependencies:
16
16
  requirements:
17
17
  - - "~>"
18
18
  - !ruby/object:Gem::Version
19
- version: 1.4.0
19
+ version: 1.5.0
20
20
  type: :runtime
21
21
  prerelease: false
22
22
  version_requirements: !ruby/object:Gem::Requirement
23
23
  requirements:
24
24
  - - "~>"
25
25
  - !ruby/object:Gem::Version
26
- version: 1.4.0
26
+ version: 1.5.0
27
+ - !ruby/object:Gem::Dependency
28
+ name: mapping
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - "~>"
32
+ - !ruby/object:Gem::Version
33
+ version: 1.0.0
34
+ type: :runtime
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - "~>"
39
+ - !ruby/object:Gem::Version
40
+ version: 1.0.0
27
41
  - !ruby/object:Gem::Dependency
28
42
  name: bundler
29
43
  requirement: !ruby/object:Gem::Requirement
@@ -84,15 +98,19 @@ files:
84
98
  - README.md
85
99
  - Rakefile
86
100
  - lib/trenni/formatters.rb
101
+ - lib/trenni/formatters/format/markdown.rb
102
+ - lib/trenni/formatters/format/text.rb
103
+ - lib/trenni/formatters/format/time.rb
87
104
  - lib/trenni/formatters/formatter.rb
88
105
  - lib/trenni/formatters/html/definition_list_form.rb
89
106
  - lib/trenni/formatters/html/form_formatter.rb
90
107
  - lib/trenni/formatters/html/option_select.rb
91
- - lib/trenni/formatters/html/table_select.rb
108
+ - lib/trenni/formatters/html/radio_select.rb
92
109
  - lib/trenni/formatters/version.rb
93
110
  - spec/trenni/formatters/form_formatter_spec.rb
94
111
  - spec/trenni/formatters/formatters_spec.rb
95
112
  - spec/trenni/formatters/html/option_select_spec.rb
113
+ - spec/trenni/formatters/html/radio_select_spec.rb
96
114
  - trenni-formatters.gemspec
97
115
  homepage: https://github.com/ioquatix/trenni-formatters
98
116
  licenses: []
@@ -113,7 +131,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
113
131
  version: '0'
114
132
  requirements: []
115
133
  rubyforge_project:
116
- rubygems_version: 2.4.6
134
+ rubygems_version: 2.5.2
117
135
  signing_key:
118
136
  specification_version: 4
119
137
  summary: Formatters for Trenni, to assist with typical views and form based interfaces.
@@ -121,3 +139,4 @@ test_files:
121
139
  - spec/trenni/formatters/form_formatter_spec.rb
122
140
  - spec/trenni/formatters/formatters_spec.rb
123
141
  - spec/trenni/formatters/html/option_select_spec.rb
142
+ - spec/trenni/formatters/html/radio_select_spec.rb