erector 0.7.2 → 0.8.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.
Files changed (67) hide show
  1. data/README.txt +17 -3
  2. data/VERSION.yml +2 -2
  3. data/bin/erector +1 -1
  4. data/lib/erector.rb +22 -2
  5. data/lib/erector/after_initialize.rb +34 -0
  6. data/lib/erector/caching.rb +93 -0
  7. data/lib/erector/convenience.rb +58 -0
  8. data/lib/erector/dependencies.rb +24 -0
  9. data/lib/erector/dependency.rb +21 -0
  10. data/lib/erector/{erect.rb → erect/erect.rb} +14 -4
  11. data/lib/erector/{erected.rb → erect/erected.rb} +6 -4
  12. data/lib/erector/{indenting.rb → erect/indenting.rb} +0 -0
  13. data/lib/erector/{rhtml.treetop → erect/rhtml.treetop} +51 -11
  14. data/lib/erector/errors.rb +12 -0
  15. data/lib/erector/extensions/hash.rb +21 -0
  16. data/lib/erector/externals.rb +88 -24
  17. data/lib/erector/html.rb +352 -0
  18. data/lib/erector/inline.rb +5 -5
  19. data/lib/erector/jquery.rb +36 -0
  20. data/lib/erector/mixin.rb +3 -5
  21. data/lib/erector/needs.rb +94 -0
  22. data/lib/erector/output.rb +117 -0
  23. data/lib/erector/rails.rb +2 -2
  24. data/lib/erector/rails/extensions/action_controller.rb +5 -3
  25. data/lib/erector/rails/extensions/rails_helpers.rb +159 -0
  26. data/lib/erector/rails/extensions/rails_widget.rb +98 -56
  27. data/lib/erector/rails/rails_form_builder.rb +8 -4
  28. data/lib/erector/rails/rails_version.rb +2 -2
  29. data/lib/erector/rails/template_handlers/ert_handler.rb +1 -1
  30. data/lib/erector/rails/template_handlers/rb_handler.rb +42 -1
  31. data/lib/erector/raw_string.rb +2 -2
  32. data/lib/erector/sass.rb +22 -0
  33. data/lib/erector/widget.rb +100 -653
  34. data/lib/erector/widgets.rb +1 -0
  35. data/lib/erector/widgets/external_renderer.rb +51 -0
  36. data/lib/erector/widgets/page.rb +45 -63
  37. data/lib/erector/widgets/table.rb +9 -1
  38. data/spec/erect/erect_rails_spec.rb +19 -17
  39. data/spec/erect/erect_spec.rb +11 -1
  40. data/spec/erect/erected_spec.rb +76 -5
  41. data/spec/erect/rhtml_parser_spec.rb +11 -1
  42. data/spec/erector/caching_spec.rb +267 -0
  43. data/spec/erector/convenience_spec.rb +258 -0
  44. data/spec/erector/dependency_spec.rb +46 -0
  45. data/spec/erector/externals_spec.rb +233 -0
  46. data/spec/erector/html_spec.rb +508 -0
  47. data/spec/erector/indentation_spec.rb +84 -24
  48. data/spec/erector/inline_spec.rb +19 -8
  49. data/spec/erector/jquery_spec.rb +35 -0
  50. data/spec/erector/mixin_spec.rb +1 -1
  51. data/spec/erector/needs_spec.rb +120 -0
  52. data/spec/erector/output_spec.rb +199 -0
  53. data/spec/erector/sample-file.txt +1 -0
  54. data/spec/erector/sass_spec.rb +33 -0
  55. data/spec/erector/widget_spec.rb +113 -932
  56. data/spec/erector/widgets/field_table_spec.rb +6 -6
  57. data/spec/erector/widgets/form_spec.rb +3 -3
  58. data/spec/erector/widgets/page_spec.rb +52 -6
  59. data/spec/erector/widgets/table_spec.rb +4 -4
  60. data/spec/spec_helper.rb +70 -29
  61. metadata +56 -19
  62. data/lib/erector/rails/extensions/rails_widget/rails_helpers.rb +0 -137
  63. data/spec/core_spec_suite.rb +0 -3
  64. data/spec/erector/external_spec.rb +0 -110
  65. data/spec/rails_spec_suite.rb +0 -3
  66. data/spec/spec.opts +0 -1
  67. data/spec/spec_suite.rb +0 -40
@@ -1,10 +1,11 @@
1
1
  require File.expand_path("#{File.dirname(__FILE__)}/../spec_helper")
2
2
 
3
3
  describe "indentation" do
4
+ include Erector::Mixin
4
5
 
5
6
  it "can detect newliney tags" do
6
7
  widget = ::Erector.inline
7
- widget.instance_eval do
8
+ widget.instance_eval do
8
9
  @prettyprint = true
9
10
  end
10
11
  widget.send(:newliney?, "i").should == false
@@ -17,21 +18,21 @@ describe "indentation" do
17
18
  b "World"
18
19
  end.to_pretty.should == "Hello, <b>World</b>"
19
20
  end
20
-
21
+
21
22
  it "should add newlines before open newliney tags" do
22
23
  Erector.inline do
23
24
  p "foo"
24
25
  p "bar"
25
26
  end.to_pretty.should == "<p>foo</p>\n<p>bar</p>\n"
26
27
  end
27
-
28
+
28
29
  it "should add newlines between text and open newliney tag" do
29
30
  Erector.inline do
30
31
  text "One"
31
32
  p "Two"
32
33
  end.to_pretty.should == "One\n<p>Two</p>\n"
33
34
  end
34
-
35
+
35
36
  it "should add newlines after end newliney tags" do
36
37
  Erector.inline do
37
38
  tr do
@@ -39,7 +40,7 @@ describe "indentation" do
39
40
  end
40
41
  end.to_pretty.should == "<tr>\n <td>cell</td>\n</tr>\n"
41
42
  end
42
-
43
+
43
44
  it "should treat empty elements as start and end" do
44
45
  Erector.inline do
45
46
  p "before"
@@ -47,13 +48,13 @@ describe "indentation" do
47
48
  p "after"
48
49
  end.to_pretty.should == "<p>before</p>\n<br />\n<p>after</p>\n"
49
50
  end
50
-
51
+
51
52
  it "empty elements sets at_start_of_line" do
52
53
  Erector.inline do
53
54
  text "before"
54
55
  br
55
56
  p "after"
56
- end.to_pretty.should == "before\n<br />\n<p>after</p>\n"
57
+ end.to_pretty.should == "before<br />\n<p>after</p>\n"
57
58
  end
58
59
 
59
60
  it "will not insert extra space before/after input element" do
@@ -65,7 +66,7 @@ describe "indentation" do
65
66
  text 'after'
66
67
  end.to_pretty.should == 'Name<input type="text" />after'
67
68
  end
68
-
69
+
69
70
  it "will indent" do
70
71
  Erector.inline do
71
72
  html do
@@ -91,7 +92,7 @@ describe "indentation" do
91
92
  </html>
92
93
  END
93
94
  end
94
-
95
+
95
96
  it "preserves indentation for sub-rendered widgets" do
96
97
  tea = Erector.inline do
97
98
  div do
@@ -101,10 +102,10 @@ END
101
102
  cup = Erector.inline do
102
103
  div do
103
104
  p "fine china"
104
- tea.write_via(self)
105
+ widget tea
105
106
  end
106
107
  end
107
-
108
+
108
109
  cup.to_pretty.should == <<END
109
110
  <div>
110
111
  <p>fine china</p>
@@ -114,38 +115,97 @@ END
114
115
  </div>
115
116
  END
116
117
  end
117
-
118
- it "can turn off newlines" do
118
+
119
+ # see http://github.com/pivotal/erector/issues/#issue/5
120
+ it "indents scripts properly" do
121
+ pending
119
122
  Erector.inline do
123
+ html :xmlns => 'http://www.w3.org/1999/xhtml' do
124
+ head do
125
+ javascript "Cufon.replace('#content');"
126
+ javascript '$(document).ready(function(){ $(document).pngFix(); });'
127
+ end
128
+ body do
129
+ end
130
+ end
131
+ end.to_pretty.should == <<-HTML
132
+ <html xmlns="http://www.w3.org/1999/xhtml">
133
+ <head>
134
+ <script type="text/javascript">
135
+ // <![CDATA[
136
+ Cufon.replace('#content');
137
+ // ]]>
138
+ </script>
139
+ <script type="text/javascript">
140
+ // <![CDATA[
141
+ $(document).ready(function(){ $(document).pngFix(); });
142
+ // ]]>
143
+ </script>
144
+ </head>
145
+ <body></body>
146
+ </html>
147
+ HTML
148
+ end
149
+
150
+ it "can turn off newlines" do
151
+ erector do
120
152
  text "One"
121
153
  p "Two"
122
- end.to_s.should == "One<p>Two</p>"
154
+ end.should == "One<p>Two</p>"
123
155
  end
124
-
156
+
125
157
  it "can turn newlines on and off" do
126
158
  widget = Erector.inline do
127
159
  text "One"
128
160
  p "Two"
129
161
  end
130
- widget.to_s.should == "One<p>Two</p>"
162
+ widget.to_html.should == "One<p>Two</p>"
131
163
  widget.to_pretty.should == "One\n<p>Two</p>\n"
132
- widget.to_s.should == "One<p>Two</p>"
164
+ widget.to_html.should == "One<p>Two</p>"
133
165
  end
134
-
166
+
135
167
  it "can turn on newlines via to_pretty" do
136
168
  widget = Erector.inline do
137
169
  text "One"
138
170
  p "Two"
139
171
  end.to_pretty.should == "One\n<p>Two</p>\n"
140
172
  end
141
-
173
+
142
174
  it "can turn newlines on/off via global variable" do
143
- Erector.inline { br }.to_s.should == "<br />"
175
+ erector { br }.should == "<br />"
144
176
  Erector::Widget.prettyprint_default = true
145
- Erector.inline { br }.to_s.should == "<br />\n"
177
+ erector { br }.should == "<br />\n"
146
178
  Erector::Widget.prettyprint_default = false
147
- Erector.inline { br }.to_s.should == "<br />"
179
+ erector { br }.should == "<br />"
148
180
  end
149
-
150
- end
151
181
 
182
+ describe ":max_length" do
183
+ it "wraps after N characters" do
184
+ Erector.inline do
185
+ div "the quick brown fox jumps over the lazy dog"
186
+ end.to_html(:max_length => 20).should ==
187
+ "<div>the quick brown\n" +
188
+ "fox jumps over the\n" +
189
+ "lazy dog</div>"
190
+ end
191
+
192
+ it "preserves pretty indent" do
193
+ Erector.inline do
194
+ div "the quick brown fox jumps over the lazy dog"
195
+ end.to_pretty(:max_length => 20).should ==
196
+ "<div>the quick brown\n" +
197
+ " fox jumps over the\n" +
198
+ " lazy dog</div>\n"
199
+ end
200
+
201
+ it "preserves raw strings" do
202
+ Erector.inline do
203
+ div raw("the quick <brown> fox <jumps> over the lazy dog")
204
+ end.to_html(:max_length => 20).should ==
205
+ "<div>the quick\n" +
206
+ "<brown> fox <jumps>\n" +
207
+ "over the lazy dog\n" +
208
+ "</div>"
209
+ end
210
+ end
211
+ end
@@ -3,18 +3,29 @@ require File.expand_path("#{File.dirname(__FILE__)}/../spec_helper")
3
3
  describe Erector::Widget do
4
4
  it "provides access to instance variables from the calling context" do
5
5
  @var = "yay"
6
- Erector::Widget.new { @var.should == "yay"; @var = "yum" }.to_s
6
+ Erector::Widget.new { @var.should == "yay"; @var = "yum" }.to_html
7
7
  @var.should == "yum"
8
8
  end
9
9
 
10
10
  it "provides access to bound variables from the calling context" do
11
11
  var = "yay"
12
- Erector::Widget.new { var.should == "yay"; var = "yum" }.to_s
12
+ Erector::Widget.new { var.should == "yay"; var = "yum" }.to_html
13
13
  var.should == "yum"
14
14
  end
15
15
 
16
16
  it "doesn't provide access to Erector methods" do
17
- Erector::Widget.new { lambda { text "yay" }.should raise_error(NoMethodError) }.to_s
17
+ Erector::Widget.new { lambda { text "yay" }.should raise_error(NoMethodError) }.to_html
18
+ end
19
+
20
+ describe ".inline" do
21
+ it "returns an instance with Erector::Inline mixed in" do
22
+ widget_subclass = Class.new(Erector::Widget)
23
+ widget_subclass.ancestors.should_not include(Erector::Inline)
24
+
25
+ inlined_instance = widget_subclass.inline
26
+ inlined_instance.class.ancestors.should include(widget_subclass)
27
+ inlined_instance.class.ancestors.should include(Erector::Inline)
28
+ end
18
29
  end
19
30
  end
20
31
 
@@ -25,16 +36,16 @@ describe Erector::Inline do
25
36
 
26
37
  it "doesn't provide access to instance variables from the calling context" do
27
38
  @var = "yay"
28
- Erector.inline { text @var }.to_s.should == ""
39
+ Erector.inline { text @var }.to_html.should == ""
29
40
  end
30
41
 
31
42
  it "provides access to bound variables from the calling context" do
32
43
  var = "yay"
33
- Erector.inline { text var }.to_s.should == "yay"
44
+ Erector.inline { text var }.to_html.should == "yay"
34
45
  end
35
46
 
36
47
  it "provides access to explicit assigns" do
37
- Erector.inline(:var => "yay") { text @var }.to_s.should == "yay"
48
+ Erector.inline(:var => "yay") { text @var }.to_html.should == "yay"
38
49
  end
39
50
 
40
51
  it "provides access to methods from the calling context" do
@@ -42,7 +53,7 @@ describe Erector::Inline do
42
53
  "yay"
43
54
  end
44
55
 
45
- Erector.inline { text helper }.to_s.should == "yay"
56
+ Erector.inline { text helper }.to_html.should == "yay"
46
57
  end
47
58
 
48
59
  describe "#call_block" do
@@ -53,7 +64,7 @@ describe Erector::Inline do
53
64
  end
54
65
 
55
66
  # inside the block...
56
- x.to_s.should ==
67
+ x.to_html.should ==
57
68
  "<arg>#{x.object_id}</arg>" + # the argument is the child
58
69
  "<self>#{x.object_id}</self>" # and self is also the child
59
70
  end
@@ -0,0 +1,35 @@
1
+ require File.expand_path("#{File.dirname(__FILE__)}/../spec_helper")
2
+
3
+ describe Erector::JQuery do
4
+ include Erector::Mixin
5
+
6
+ describe "#jquery" do
7
+ def expected(event, *args)
8
+
9
+ "<script #{'id="foo" ' if args.include? :id}type=\"text/javascript\">\n" +
10
+ "// <![CDATA[\n\n" +
11
+ "jQuery(document).#{event}(function($){\n" +
12
+ "alert('hello');\n});\n// ]]>\n</script>\n"
13
+ end
14
+
15
+ it "outputs a 'jquery ready' script block by default" do
16
+ erector { jquery "alert('hello');" }.should == expected("ready")
17
+ end
18
+
19
+ it "outputs attributes" do
20
+ erector { jquery "alert('hello');", :id => 'foo' }.should == expected("ready", :id)
21
+ end
22
+
23
+ it "outputs a 'jquery ready' script block when passed a symbol for the first arg" do
24
+ erector { jquery :ready, "alert('hello');" }.should == expected("ready")
25
+ end
26
+
27
+ it "outputs a 'jquery load' script block" do
28
+ erector { jquery :load, "alert('hello');" }.should == expected("load")
29
+ end
30
+
31
+ it "combines event, text, and attributes" do
32
+ erector { jquery :load, "alert('hello');", :id => "foo" }.should == expected("load", :id)
33
+ end
34
+ end
35
+ end
@@ -23,7 +23,7 @@ module MixinSpec
23
23
  Thing.new.name.should == "<span class=\"name\">Gabriel <i>Garcia</i> Marquez</span>"
24
24
  end
25
25
 
26
- it "passes its parameters to to_s" do
26
+ it "passes its parameters to to_html" do
27
27
  class Thing
28
28
  include Erector::Mixin
29
29
  def pretty_name
@@ -0,0 +1,120 @@
1
+ require File.expand_path("#{File.dirname(__FILE__)}/../spec_helper")
2
+
3
+ describe Erector::Needs do
4
+ it "doesn't complain if there aren't any needs declared" do
5
+ class Thing1 < Erector::Widget
6
+ end
7
+ Thing1.new
8
+ end
9
+
10
+ it "allows you to say that you don't want any parameters" do
11
+ class Thing2 < Erector::Widget
12
+ needs nil
13
+ end
14
+ lambda { Thing2.new }.should_not raise_error
15
+ lambda { Thing2.new(:foo => 1) }.should raise_error
16
+ end
17
+
18
+ it "doesn't complain if you pass it a declared parameter" do
19
+ class Thing2b < Erector::Widget
20
+ needs :foo
21
+ end
22
+ lambda { Thing2b.new(:foo => 1) }.should_not raise_error
23
+ end
24
+
25
+ it "complains if you pass it an undeclared parameter" do
26
+ class Thing3 < Erector::Widget
27
+ needs :foo
28
+ end
29
+ lambda { Thing3.new(:bar => 1) }.should raise_error
30
+ end
31
+
32
+ it "allows multiple declared parameters" do
33
+ class Thing4 < Erector::Widget
34
+ needs :foo, :bar
35
+ end
36
+ lambda { Thing4.new(:foo => 1, :bar => 2) }.should_not raise_error
37
+ end
38
+
39
+ it "complains when passing in an extra parameter after declaring many parameters" do
40
+ class Thing5 < Erector::Widget
41
+ needs :foo, :bar
42
+ end
43
+ lambda { Thing5.new(:foo => 1, :bar => 2, :baz => 3) }.should raise_error
44
+ end
45
+
46
+ it "complains when you forget to pass in a needed parameter" do
47
+ class Thing6 < Erector::Widget
48
+ needs :foo, :bar
49
+ end
50
+ lambda { Thing6.new(:foo => 1) }.should raise_error
51
+ end
52
+
53
+ it "doesn't complain if you omit a parameter with a default value" do
54
+ class Thing7 < Erector::Widget
55
+ needs :foo
56
+ needs :bar => 7
57
+ needs :baz => 8
58
+ end
59
+ lambda {
60
+ thing = Thing7.new(:foo => 1, :baz => 3)
61
+ thing.instance_variable_get(:@bar).should equal(7)
62
+ thing.instance_variable_get(:@baz).should equal(3)
63
+ }.should_not raise_error
64
+ end
65
+
66
+ it "allows multiple values on a line, including default values at the end of the line" do
67
+ class Thing8 < Erector::Widget
68
+ needs :foo, :bar => 7, :baz => 8
69
+ end
70
+ lambda {
71
+ thing = Thing8.new(:foo => 1, :baz => 2)
72
+ thing.instance_variable_get(:@foo).should equal(1)
73
+ thing.instance_variable_get(:@bar).should equal(7)
74
+ thing.instance_variable_get(:@baz).should equal(2)
75
+ }.should_not raise_error
76
+ end
77
+
78
+ it "allows nil to be a default value" do
79
+ class Thing9 < Erector::Widget
80
+ needs :foo => nil
81
+ end
82
+ lambda {
83
+ thing = Thing9.new
84
+ thing.instance_variable_get(:@foo).should be_nil
85
+ }.should_not raise_error
86
+ end
87
+
88
+ it "accumulates needs across the inheritance chain even with modules mixed in" do
89
+ module Something
90
+ end
91
+
92
+ class Vehicle < Erector::Widget
93
+ needs :wheels
94
+ end
95
+
96
+ class Car < Vehicle
97
+ include Something
98
+ needs :engine
99
+ end
100
+
101
+ lambda { Car.new(:engine => 'V-8', :wheels => 4) }.should_not raise_error
102
+ lambda { Car.new(:engine => 'V-8') }.should raise_error
103
+ lambda { Car.new(:wheels => 4) }.should raise_error
104
+ end
105
+
106
+ it "no longer defines accessors for each of the needed variables" do
107
+ class NeedfulThing < Erector::Widget
108
+ needs :love
109
+ end
110
+ thing = NeedfulThing.new(:love => "all we need")
111
+ lambda {thing.love}.should raise_error(NoMethodError)
112
+ end
113
+
114
+ it "no longer complains if you attempt to 'need' a variable whose name overlaps with an existing method" do
115
+ class ThingWithOverlap < Erector::Widget
116
+ needs :text
117
+ end
118
+ lambda { ThingWithOverlap.new(:text => "alas") }.should_not raise_error(ArgumentError)
119
+ end
120
+ end
@@ -0,0 +1,199 @@
1
+ require File.expand_path("#{File.dirname(__FILE__)}/../spec_helper")
2
+
3
+ module Erector
4
+ describe Erector::Output do
5
+ before do
6
+ @output = Output.new
7
+ end
8
+
9
+ it "accepts a string via the << operator" do
10
+ @output.to_s.should == ""
11
+ @output << "foo"
12
+ @output.to_s.should == "foo"
13
+ @output << "bar"
14
+ @output.to_s.should == "foobar"
15
+ end
16
+
17
+ it "#<< accepts a number" do
18
+ @output << 1
19
+ @output.to_s.should == "1"
20
+ end
21
+
22
+ it "accepts chained <<s" do
23
+ @output << "foo" << "bar"
24
+ @output.to_s.should == "foobar"
25
+ end
26
+
27
+ it "provides a placeholder string to be filled in later" do
28
+ @output << "foo"
29
+ placeholder = @output.placeholder
30
+ @output << "bar"
31
+ @output.to_s.should == "foobar"
32
+ placeholder << "baz"
33
+ @output.to_s.should == "foobazbar"
34
+ end
35
+
36
+ describe '#to_a' do
37
+ it "emits an array" do
38
+ @output << "foo" << "bar"
39
+ @output.to_a.join.should == "foobar"
40
+ end
41
+ end
42
+
43
+ it "can be initialized with an existing string buffer" do
44
+ s = "foo"
45
+ @output = Output.new { s }
46
+ @output << "bar"
47
+ s.should == "foobar"
48
+ @output.to_s.should == "foobar"
49
+ end
50
+
51
+ it "accepts a prettyprint option" do
52
+ Erector::Output.new(:prettyprint => true).prettyprint.should be_true
53
+ Erector::Output.new(:prettyprint => false).prettyprint.should be_false
54
+ end
55
+
56
+ it "accepts the global prettyprint_default setting" do
57
+ old_default = Erector::Widget.new.prettyprint_default
58
+ begin
59
+ Erector::Widget.prettyprint_default = true
60
+ Erector::Output.new.prettyprint.should be_true
61
+ Erector::Widget.prettyprint_default = false
62
+ Erector::Output.new.prettyprint.should be_false
63
+ ensure
64
+ Erector::Widget.prettyprint_default = old_default
65
+ end
66
+ end
67
+
68
+ describe '#newline' do
69
+ it "inserts a newline if we're in prettyprint mode" do
70
+ @output = Output.new(:prettyprint => true)
71
+ @output << "foo"
72
+ @output.newline
73
+ @output.should be_at_line_start
74
+ @output.to_s.should == "foo\n"
75
+ end
76
+
77
+ it "tracks whether we're at the beginning of a line or not" do
78
+ @output = Output.new(:prettyprint => true)
79
+ @output.should be_at_line_start
80
+ @output << "foo"
81
+ @output.should_not be_at_line_start
82
+ @output.newline
83
+ @output.should be_at_line_start
84
+ @output << "bar"
85
+ @output.should_not be_at_line_start
86
+ @output.newline
87
+ @output.should be_at_line_start
88
+ end
89
+
90
+ it "doesn't insert a newline (or track line starts) if we're not in prettyprint mode" do
91
+ @output = Output.new(:prettyprint => false)
92
+ @output << "foo"
93
+ @output.newline
94
+ @output.should_not be_at_line_start
95
+ @output.to_s.should == "foo"
96
+ end
97
+ end
98
+
99
+ describe "pretty printing" do
100
+ before do
101
+ @output = Output.new(:prettyprint => true)
102
+ end
103
+
104
+ it "indents the next line when we're at line start and indented" do
105
+ @output << "foo"
106
+ @output.newline
107
+ @output.indent
108
+ @output << "bar"
109
+ @output.newline
110
+ @output.undent
111
+ @output << "baz"
112
+ @output.newline
113
+
114
+ @output.to_s.should == "foo\n bar\nbaz\n"
115
+ end
116
+
117
+ it "doesn't indent if there's a linebreak in the middle of a string" do
118
+ @output.indent
119
+ @output << "foo\nbar\nbaz\n"
120
+ @output.to_s.should == " foo\nbar\nbaz\n"
121
+ end
122
+
123
+ it "turns off if prettyprint is false" do
124
+ @output = Output.new(:prettyprint => false)
125
+ @output.indent
126
+ @output << "bar"
127
+ @output.to_s.should == "bar"
128
+ end
129
+
130
+ it "doesn't crash if indentation level is less than 0" do
131
+ @output.undent
132
+ @output << "bar"
133
+ @output.to_s.should == "bar"
134
+ # [@indentation, 0].max
135
+ end
136
+
137
+ it "accepts an initial indentation level" do
138
+ @output = Output.new(:prettyprint => true, :indentation => 2)
139
+ @output << "foo"
140
+ @output.to_s.should == " foo"
141
+ end
142
+
143
+ it "accepts a max line length" do
144
+ @output = Output.new(:prettyprint => true, :max_length => 10)
145
+ @output << "Now is the winter of our discontent made "
146
+ @output << "glorious summer by this sun of York."
147
+ @output.to_s.should ==
148
+ "Now is the\n" +
149
+ "winter of\n" +
150
+ "our\n" +
151
+ "discontent\n" +
152
+ "made \n" +
153
+ "glorious\n" +
154
+ "summer by\n" +
155
+ "this sun\n" +
156
+ "of York."
157
+ end
158
+
159
+ it "preserves leading and trailing spaces" do
160
+ @output = Output.new(:max_length => 10)
161
+ @output << "123456789"
162
+ @output << " foo "
163
+ @output << "bar"
164
+ @output.to_s.should == "123456789 \nfoo bar"
165
+ end
166
+
167
+ it "accepts a max line length wth indentation" do
168
+ # note that 1 indent = 2 spaces
169
+ @output = Output.new(:prettyprint => true, :indentation => 1, :max_length => 10)
170
+ @output << "Now is the winter of our discontent made glorious summer by this sun of York."
171
+ @output.to_s.should ==
172
+ " Now is\n" +
173
+ " the\n" +
174
+ " winter\n" +
175
+ " of our\n" +
176
+ " discontent\n" +
177
+ " made\n" +
178
+ " glorious\n" +
179
+ " summer\n" +
180
+ " by this\n" +
181
+ " sun of\n" +
182
+ " York."
183
+ end
184
+
185
+ end
186
+
187
+ class Puppy < Erector::Widget
188
+ end
189
+ class Kitten < Erector::Widget
190
+ end
191
+
192
+ it "can keep track of widget classes emitted to it" do
193
+ @output.widgets << Puppy
194
+ @output.widgets << Kitten
195
+ @output.widgets << Puppy
196
+ @output.widgets.to_a.should include_only [Puppy, Kitten]
197
+ end
198
+ end
199
+ end