prawn 0.2.3 → 0.3.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (144) hide show
  1. data/README +6 -10
  2. data/Rakefile +4 -13
  3. data/data/encodings/win_ansi.txt +29 -0
  4. data/data/images/fractal.jpg +0 -0
  5. data/data/images/letterhead.jpg +0 -0
  6. data/examples/bounding_box/bounding_boxes.rb +44 -0
  7. data/examples/bounding_box/lazy_bounding_boxes.rb +28 -0
  8. data/examples/bounding_box/padded_box.rb +24 -0
  9. data/examples/{russian_boxes.rb → bounding_box/russian_boxes.rb} +9 -6
  10. data/examples/general/background.rb +20 -0
  11. data/examples/{canvas.rb → general/canvas.rb} +6 -2
  12. data/examples/general/measurement_units.rb +52 -0
  13. data/examples/{multi_page_layout.rb → general/multi_page_layout.rb} +6 -3
  14. data/examples/{page_geometry.rb → general/page_geometry.rb} +6 -2
  15. data/examples/{image.rb → graphics/basic_images.rb} +8 -4
  16. data/examples/graphics/cmyk.rb +13 -0
  17. data/examples/graphics/curves.rb +12 -0
  18. data/examples/{hexagon.rb → graphics/hexagon.rb} +5 -5
  19. data/examples/graphics/image_fit.rb +16 -0
  20. data/examples/graphics/image_flow.rb +38 -0
  21. data/examples/graphics/image_position.rb +18 -0
  22. data/examples/{line.rb → graphics/line.rb} +4 -2
  23. data/examples/{png_types.rb → graphics/png_types.rb} +4 -4
  24. data/examples/{polygons.rb → graphics/polygons.rb} +5 -4
  25. data/examples/graphics/remote_images.rb +12 -0
  26. data/examples/{ruport_helpers.rb → graphics/ruport_style_helpers.rb} +8 -5
  27. data/examples/graphics/stroke_bounds.rb +23 -0
  28. data/examples/{chinese_text_wrapping.rb → m17n/chinese_text_wrapping.rb} +7 -4
  29. data/examples/m17n/euro.rb +16 -0
  30. data/examples/m17n/sjis.rb +29 -0
  31. data/examples/m17n/utf8.rb +14 -0
  32. data/examples/m17n/win_ansi_charset.rb +55 -0
  33. data/examples/{addressbook.csv → table/addressbook.csv} +0 -0
  34. data/examples/{cell.rb → table/cell.rb} +8 -6
  35. data/examples/{currency.csv → table/currency.csv} +0 -0
  36. data/examples/{fancy_table.rb → table/fancy_table.rb} +9 -6
  37. data/examples/{ruport_formatter.rb → table/ruport_formatter.rb} +6 -3
  38. data/examples/{table.rb → table/table.rb} +6 -2
  39. data/examples/table/table_alignment.rb +18 -0
  40. data/examples/table/table_border_color.rb +17 -0
  41. data/examples/table/table_colspan.rb +19 -0
  42. data/examples/table/table_header_color.rb +19 -0
  43. data/examples/table/table_header_underline.rb +15 -0
  44. data/examples/{alignment.rb → text/alignment.rb} +5 -2
  45. data/examples/text/family_based_styling.rb +25 -0
  46. data/examples/{flowing_text_with_header_and_footer.rb → text/flowing_text_with_header_and_footer.rb} +19 -8
  47. data/examples/text/font_calculations.rb +91 -0
  48. data/examples/text/font_size.rb +34 -0
  49. data/examples/{kerning.rb → text/kerning.rb} +5 -1
  50. data/examples/text/simple_text.rb +18 -0
  51. data/examples/text/simple_text_ttf.rb +18 -0
  52. data/examples/{span.rb → text/span.rb} +5 -2
  53. data/examples/text/text_box.rb +26 -0
  54. data/examples/{text_flow.rb → text/text_flow.rb} +5 -2
  55. data/lib/prawn.rb +26 -20
  56. data/lib/prawn/compatibility.rb +5 -8
  57. data/lib/prawn/document.rb +29 -13
  58. data/lib/prawn/document/annotations.rb +63 -0
  59. data/lib/prawn/document/bounding_box.rb +18 -3
  60. data/lib/prawn/document/destinations.rb +81 -0
  61. data/lib/prawn/document/internals.rb +16 -2
  62. data/lib/prawn/document/page_geometry.rb +58 -57
  63. data/lib/prawn/document/span.rb +8 -0
  64. data/lib/prawn/document/table.rb +81 -31
  65. data/lib/prawn/document/text.rb +66 -21
  66. data/lib/prawn/document/text/box.rb +77 -0
  67. data/lib/prawn/encoding.rb +121 -0
  68. data/lib/prawn/errors.rb +4 -0
  69. data/lib/prawn/font.rb +70 -42
  70. data/lib/prawn/font/metrics.rb +64 -119
  71. data/lib/prawn/graphics.rb +105 -87
  72. data/lib/prawn/graphics/cell.rb +55 -28
  73. data/lib/prawn/graphics/color.rb +8 -0
  74. data/lib/prawn/images.rb +55 -12
  75. data/lib/prawn/images/jpg.rb +2 -1
  76. data/lib/prawn/images/png.rb +2 -1
  77. data/lib/prawn/literal_string.rb +14 -0
  78. data/lib/prawn/measurement_extensions.rb +46 -0
  79. data/lib/prawn/measurements.rb +71 -0
  80. data/lib/prawn/name_tree.rb +165 -0
  81. data/lib/prawn/pdf_object.rb +8 -1
  82. data/spec/annotations_spec.rb +90 -0
  83. data/spec/destinations_spec.rb +15 -0
  84. data/spec/document_spec.rb +39 -2
  85. data/spec/font_spec.rb +22 -0
  86. data/spec/graphics_spec.rb +99 -87
  87. data/spec/images_spec.rb +29 -1
  88. data/spec/measurement_units_spec.rb +23 -0
  89. data/spec/metrics_spec.rb +3 -2
  90. data/spec/name_tree_spec.rb +103 -0
  91. data/spec/pdf_object_spec.rb +15 -5
  92. data/spec/png_spec.rb +14 -14
  93. data/spec/spec_helper.rb +8 -6
  94. data/spec/table_spec.rb +40 -0
  95. data/spec/text_spec.rb +6 -4
  96. data/vendor/ttfunk/data/fonts/DejaVuSans.ttf +0 -0
  97. data/vendor/ttfunk/data/fonts/comicsans.ttf +0 -0
  98. data/vendor/ttfunk/example.rb +5 -0
  99. data/vendor/ttfunk/lib/ttfunk.rb +48 -0
  100. data/vendor/ttfunk/lib/ttfunk/table.rb +27 -0
  101. data/vendor/ttfunk/lib/ttfunk/table/cmap.rb +94 -0
  102. data/vendor/ttfunk/lib/ttfunk/table/directory.rb +25 -0
  103. data/vendor/ttfunk/lib/ttfunk/table/head.rb +25 -0
  104. data/vendor/ttfunk/lib/ttfunk/table/hhea.rb +27 -0
  105. data/vendor/ttfunk/lib/ttfunk/table/hmtx.rb +20 -0
  106. data/vendor/ttfunk/lib/ttfunk/table/kern.rb +48 -0
  107. data/vendor/ttfunk/lib/ttfunk/table/maxp.rb +17 -0
  108. data/vendor/ttfunk/lib/ttfunk/table/name.rb +52 -0
  109. metadata +93 -62
  110. data/examples/bounding_boxes.rb +0 -30
  111. data/examples/curves.rb +0 -10
  112. data/examples/family_based_styling.rb +0 -21
  113. data/examples/font_size.rb +0 -19
  114. data/examples/image2.rb +0 -13
  115. data/examples/image_flow.rb +0 -29
  116. data/examples/lazy_bounding_boxes.rb +0 -19
  117. data/examples/remote_images.rb +0 -7
  118. data/examples/simple_text.rb +0 -15
  119. data/examples/simple_text_ttf.rb +0 -16
  120. data/examples/sjis.rb +0 -21
  121. data/examples/utf8.rb +0 -12
  122. data/vendor/font_ttf/ttf.rb +0 -20
  123. data/vendor/font_ttf/ttf/datatypes.rb +0 -189
  124. data/vendor/font_ttf/ttf/encodings.rb +0 -140
  125. data/vendor/font_ttf/ttf/exceptions.rb +0 -28
  126. data/vendor/font_ttf/ttf/file.rb +0 -290
  127. data/vendor/font_ttf/ttf/fontchunk.rb +0 -77
  128. data/vendor/font_ttf/ttf/table/cmap.rb +0 -408
  129. data/vendor/font_ttf/ttf/table/cvt.rb +0 -49
  130. data/vendor/font_ttf/ttf/table/fpgm.rb +0 -48
  131. data/vendor/font_ttf/ttf/table/gasp.rb +0 -88
  132. data/vendor/font_ttf/ttf/table/glyf.rb +0 -452
  133. data/vendor/font_ttf/ttf/table/head.rb +0 -86
  134. data/vendor/font_ttf/ttf/table/hhea.rb +0 -96
  135. data/vendor/font_ttf/ttf/table/hmtx.rb +0 -98
  136. data/vendor/font_ttf/ttf/table/kern.rb +0 -186
  137. data/vendor/font_ttf/ttf/table/loca.rb +0 -75
  138. data/vendor/font_ttf/ttf/table/maxp.rb +0 -81
  139. data/vendor/font_ttf/ttf/table/name.rb +0 -222
  140. data/vendor/font_ttf/ttf/table/os2.rb +0 -172
  141. data/vendor/font_ttf/ttf/table/post.rb +0 -120
  142. data/vendor/font_ttf/ttf/table/prep.rb +0 -27
  143. data/vendor/font_ttf/ttf/table/vhea.rb +0 -45
  144. data/vendor/font_ttf/ttf/table/vmtx.rb +0 -36
@@ -0,0 +1,165 @@
1
+ # encoding: utf-8
2
+
3
+ # name_tree.rb : Implements NameTree for PDF
4
+ #
5
+ # Copyright November 2008, Jamis Buck. All Rights Reserved.
6
+ #
7
+ # This is free software. Please see the LICENSE and COPYING files for details.
8
+ #
9
+ require 'prawn/literal_string'
10
+ require 'prawn/reference'
11
+
12
+ module Prawn
13
+ module NameTree #:nodoc:
14
+ class Node #:nodoc:
15
+ attr_reader :children
16
+ attr_reader :limit
17
+ attr_reader :document
18
+ attr_accessor :parent
19
+ attr_accessor :ref
20
+
21
+ def initialize(document, limit, parent=nil)
22
+ @document = document
23
+ @children = []
24
+ @limit = limit
25
+ @parent = parent
26
+ @ref = nil
27
+ end
28
+
29
+ def empty?
30
+ children.empty?
31
+ end
32
+
33
+ def size
34
+ leaf? ? children.size : children.inject(0) { |sum, child| sum + child.size }
35
+ end
36
+
37
+ def leaf?
38
+ children.empty? || children.first.is_a?(Value)
39
+ end
40
+
41
+ def add(name, value)
42
+ self << Value.new(name, value)
43
+ end
44
+
45
+ def to_hash
46
+ hash = {}
47
+
48
+ hash[:Limits] = [least, greatest] if parent
49
+ if leaf?
50
+ hash[:Names] = children if leaf?
51
+ else
52
+ hash[:Kids] = children.map { |child| child.ref }
53
+ end
54
+
55
+ return hash
56
+ end
57
+
58
+ def least
59
+ if leaf?
60
+ children.first.name
61
+ else
62
+ children.first.least
63
+ end
64
+ end
65
+
66
+ def greatest
67
+ if leaf?
68
+ children.last.name
69
+ else
70
+ children.last.greatest
71
+ end
72
+ end
73
+
74
+ def <<(value)
75
+ if children.empty?
76
+ children << value
77
+ elsif leaf?
78
+ children.insert(insertion_point(value), value)
79
+ split! if children.length > limit
80
+ else
81
+ fit = children.detect { |child| child >= value }
82
+ fit << value
83
+ end
84
+
85
+ value
86
+ end
87
+
88
+ def >=(value)
89
+ children.empty? || children.last >= value
90
+ end
91
+
92
+ def split!
93
+ if parent
94
+ parent.split(self)
95
+ else
96
+ left, right = new_node(self), new_node(self)
97
+ split_children(self, left, right)
98
+ children.replace([left, right])
99
+ end
100
+ end
101
+
102
+ protected
103
+
104
+ def split(node)
105
+ new_child = new_node(self)
106
+ split_children(node, node, new_child)
107
+ index = children.index(node)
108
+ children.insert(index+1, new_child)
109
+ split! if children.length > limit
110
+ end
111
+
112
+ private
113
+
114
+ def new_node(parent=nil)
115
+ node = Node.new(document, limit, parent)
116
+ node.ref = document.ref(node)
117
+ return node
118
+ end
119
+
120
+ def split_children(node, left, right)
121
+ half = (node.limit+1)/2
122
+
123
+ left_children, right_children = node.children[0...half], node.children[half..-1]
124
+
125
+ left.children.replace(left_children)
126
+ right.children.replace(right_children)
127
+
128
+ unless node.leaf?
129
+ left_children.each { |child| child.parent = left }
130
+ right_children.each { |child| child.parent = right }
131
+ end
132
+ end
133
+
134
+ def insertion_point(value)
135
+ children.each_with_index do |child, index|
136
+ return index if child >= value
137
+ end
138
+ return children.length
139
+ end
140
+ end
141
+
142
+ class Value #:nodoc:
143
+ include Comparable
144
+
145
+ attr_reader :name
146
+ attr_reader :value
147
+
148
+ def initialize(name, value)
149
+ @name, @value = Prawn::LiteralString.new(name), value
150
+ end
151
+
152
+ def <=>(leaf)
153
+ name <=> leaf.name
154
+ end
155
+
156
+ def inspect
157
+ "#<Value: #{name.inspect} : #{value.inspect}>"
158
+ end
159
+
160
+ def to_s
161
+ "#{name} : #{value}"
162
+ end
163
+ end
164
+ end
165
+ end
@@ -34,7 +34,10 @@ module Prawn
34
34
  when Numeric then String(obj)
35
35
  when Array
36
36
  "[" << obj.map { |e| PdfObject(e, in_content_stream) }.join(' ') << "]"
37
- when String
37
+ when Prawn::LiteralString
38
+ obj = obj.gsub(/[\\\n\(\)]/) { |m| "\\#{m}" }
39
+ "(#{obj})"
40
+ when String
38
41
  obj = "\xFE\xFF" + obj.unpack("U*").pack("n*") unless in_content_stream
39
42
  "<" << obj.unpack("H*").first << ">"
40
43
  when Symbol
@@ -57,6 +60,10 @@ module Prawn
57
60
  output << ">>"
58
61
  when Prawn::Reference
59
62
  obj.to_s
63
+ when Prawn::NameTree::Node
64
+ PdfObject(obj.to_hash)
65
+ when Prawn::NameTree::Value
66
+ PdfObject(obj.name) + " " + PdfObject(obj.value)
60
67
  else
61
68
  raise Prawn::Errors::FailedObjectConversion,
62
69
  "This object cannot be serialized to PDF"
@@ -0,0 +1,90 @@
1
+ # encoding: utf-8
2
+
3
+ require File.join(File.expand_path(File.dirname(__FILE__)), "spec_helper")
4
+
5
+ class PageAnnotations
6
+ attr_reader :pages
7
+
8
+ def self.parse(document)
9
+ receiver = new
10
+ PDF::Reader.string(document.render, receiver)
11
+ return receiver
12
+ end
13
+
14
+ def initialize
15
+ @pages = []
16
+ end
17
+
18
+ def begin_page(params)
19
+ @pages << params
20
+ end
21
+ end
22
+
23
+ describe "When creating annotations" do
24
+
25
+ before(:each) { create_pdf }
26
+
27
+ it "should append annotation to current page" do
28
+ @pdf.start_new_page
29
+ @pdf.annotate(:Rect => [0,0,10,10], :Subtype => :Text, :Contents => "Hello world!")
30
+ obj = PageAnnotations.parse(@pdf)
31
+ obj.pages[0][:Annots].nil?.should == true
32
+ obj.pages[1][:Annots].length.should == 1
33
+ end
34
+
35
+ it "should force :Type to be :Annot" do
36
+ opts = @pdf.annotate(:Rect => [0,0,10,10], :Subtype => :Text, :Contents => "Hello world!")
37
+ opts[:Type].should == :Annot
38
+ opts = @pdf.annotate(:Type => :Bogus, :Rect => [0,0,10,10], :Subtype => :Text, :Contents => "Hello world!")
39
+ opts[:Type].should == :Annot
40
+ end
41
+
42
+ end
43
+
44
+ describe "When creating text annotations" do
45
+
46
+ before(:each) do
47
+ @rect = [0,0,10,10]
48
+ @content = "Hello, world!"
49
+ create_pdf
50
+ end
51
+
52
+ it "should build appropriate annotation" do
53
+ opts = @pdf.text_annotation(@rect, @content)
54
+ opts[:Type].should == :Annot
55
+ opts[:Subtype].should == :Text
56
+ opts[:Rect].should == @rect
57
+ opts[:Contents].should == @content
58
+ end
59
+
60
+ it "should merge extra options" do
61
+ opts = @pdf.text_annotation(@rect, @content, :Open => true, :Subtype => :Bogus)
62
+ opts[:Subtype].should == :Text
63
+ opts[:Open].should == true
64
+ end
65
+
66
+ end
67
+
68
+ describe "When creating link annotations" do
69
+
70
+ before(:each) do
71
+ @rect = [0,0,10,10]
72
+ @dest = "home"
73
+ create_pdf
74
+ end
75
+
76
+ it "should build appropriate annotation" do
77
+ opts = @pdf.link_annotation(@rect, :Dest => @dest)
78
+ opts[:Type].should == :Annot
79
+ opts[:Subtype].should == :Link
80
+ opts[:Rect].should == @rect
81
+ opts[:Dest].should == @dest
82
+ end
83
+
84
+ it "should merge extra options" do
85
+ opts = @pdf.link_annotation(@rect, :Dest => @dest, :Subtype => :Bogus)
86
+ opts[:Subtype].should == :Link
87
+ opts[:Dest].should == @dest
88
+ end
89
+
90
+ end
@@ -0,0 +1,15 @@
1
+ # encoding: utf-8
2
+
3
+ require File.join(File.expand_path(File.dirname(__FILE__)), "spec_helper")
4
+
5
+ describe "When creating destinations" do
6
+
7
+ before(:each) { create_pdf }
8
+
9
+ it "should add entry to Dests name tree" do
10
+ @pdf.dests.data.empty?.should == true
11
+ @pdf.add_dest "candy", "chocolate"
12
+ @pdf.dests.data.size.should == 1
13
+ end
14
+
15
+ end
@@ -1,6 +1,16 @@
1
1
  # encoding: utf-8
2
2
 
3
- require File.join(File.expand_path(File.dirname(__FILE__)), "spec_helper")
3
+ require File.join(File.expand_path(File.dirname(__FILE__)), "spec_helper")
4
+
5
+ describe "The cursor" do
6
+ it "should equal pdf.y - bounds.absolute_bottom" do
7
+ pdf = Prawn::Document.new
8
+ pdf.cursor.should == pdf.bounds.top
9
+
10
+ pdf.y = 300
11
+ pdf.cursor.should == pdf.y - pdf.bounds.absolute_bottom
12
+ end
13
+ end
4
14
 
5
15
  describe "When creating multi-page documents" do
6
16
 
@@ -38,7 +48,23 @@ describe "When beginning each new page" do
38
48
  pdf.render
39
49
 
40
50
  call_count.should == 3
41
- end
51
+ end
52
+ describe "Background template feature" do
53
+ before(:each) do
54
+ @filename = "#{Prawn::BASEDIR}/data/images/pigs.jpg"
55
+ @pdf = Prawn::Document.new(:background => @filename)
56
+ end
57
+ it "should place a background image if it is in options block" do
58
+ output = @pdf.render
59
+ images = PDF::Inspector::XObject.analyze(output)
60
+ # there should be 2 images in the page resources
61
+ images.page_xobjects.first.size.should == 1
62
+ end
63
+ it "should place a background image if it is in options block" do
64
+ @pdf.instance_variable_defined?(:@background).should == true
65
+ @pdf.instance_variable_get(:@background).should == @filename
66
+ end
67
+ end
42
68
 
43
69
  end
44
70
 
@@ -84,6 +110,17 @@ describe "When ending each page" do
84
110
  pdf.render
85
111
  end
86
112
 
113
+ it "should result in a smaller file size when compressed" do
114
+ doc_uncompressed = Prawn::Document.new
115
+ doc_compressed = Prawn::Document.new(:compress => true)
116
+ [doc_compressed, doc_uncompressed].each do |pdf|
117
+ pdf.font "#{Prawn::BASEDIR}/data/fonts/gkai00mp.ttf"
118
+ pdf.text "更可怕的是,同质化竞争对手可以按照URL中后面这个ID来遍历" * 10
119
+ end
120
+
121
+ doc_compressed.render.length.should.be < doc_uncompressed.render.length
122
+ end
123
+
87
124
  end
88
125
 
89
126
  describe "When setting page size" do
@@ -70,6 +70,28 @@ describe "font style support" do
70
70
 
71
71
  end
72
72
 
73
+ describe "Transactional font handling" do
74
+ before(:each) { create_pdf }
75
+
76
+ it "should allow setting of size directly when font is created" do
77
+ @pdf.font "Courier", :size => 16
78
+ @pdf.font.size.should == 16
79
+ end
80
+
81
+ it "should allow temporary setting of a new font using a transaction" do
82
+ original = @pdf.font
83
+
84
+ @pdf.font "Courier", :size => 16 do
85
+ @pdf.font.name.should == "Courier"
86
+ @pdf.font.size.should == 16
87
+ end
88
+
89
+ @pdf.font.should == original
90
+ end
91
+
92
+ end
93
+
94
+
73
95
  describe "Document#page_fonts" do
74
96
  before(:each) { create_pdf }
75
97
 
@@ -1,58 +1,70 @@
1
1
  # encoding: utf-8
2
2
 
3
- require File.join(File.expand_path(File.dirname(__FILE__)), "spec_helper")
4
-
3
+ require File.join(File.expand_path(File.dirname(__FILE__)), "spec_helper")
4
+
5
5
  describe "When drawing a line" do
6
-
6
+
7
7
  before(:each) { create_pdf }
8
-
8
+
9
9
  it "should draw a line from (100,600) to (100,500)" do
10
10
  @pdf.line([100,600],[100,500])
11
-
11
+
12
12
  line_drawing = PDF::Inspector::Graphics::Line.analyze(@pdf.render)
13
-
14
- line_drawing.points.should == [[100,600],[100,500]]
15
- end
16
-
13
+
14
+ line_drawing.points.should == [[100,600],[100,500]]
15
+ end
16
+
17
17
  it "should draw two lines at (100,600) to (100,500) " +
18
- "and (75,100) to (50,125)" do
19
- @pdf.line(100,600,100,500)
18
+ "and (75,100) to (50,125)" do
19
+ @pdf.line(100,600,100,500)
20
20
  @pdf.line(75,100,50,125)
21
-
21
+
22
22
  line_drawing = PDF::Inspector::Graphics::Line.analyze(@pdf.render)
23
-
24
- line_drawing.points.should ==
23
+
24
+ line_drawing.points.should ==
25
25
  [[100.0, 600.0], [100.0, 500.0], [75.0, 100.0], [50.0, 125.0]]
26
26
  end
27
27
 
28
28
  it "should properly set line width via line_width=" do
29
29
  @pdf.line_width = 10
30
- line = PDF::Inspector::Graphics::Line.analyze(@pdf.render)
31
- line.widths.first.should == 10
32
- end
33
-
30
+ line = PDF::Inspector::Graphics::Line.analyze(@pdf.render)
31
+ line.widths.first.should == 10
32
+ end
33
+
34
34
  it "should properly set line width via line_width(width)" do
35
35
  @pdf.line_width(10)
36
- line = PDF::Inspector::Graphics::Line.analyze(@pdf.render)
37
- line.widths.first.should == 10
38
- end
39
-
40
- describe "(Horizontally)" do
41
-
42
- before :each do
43
- @pdf = Prawn::Document.new
36
+ line = PDF::Inspector::Graphics::Line.analyze(@pdf.render)
37
+ line.widths.first.should == 10
38
+ end
39
+
40
+ describe "(Horizontally)" do
41
+ it "should draw from [x1,pdf.y],[x2,pdf.y]" do
44
42
  @pdf.horizontal_line(100,150)
45
43
  @line = PDF::Inspector::Graphics::Line.analyze(@pdf.render)
46
- end
47
-
48
- it "should draw from [x1,pdf.y],[x2,pdf.y]" do
49
44
  @line.points.should == [[100.0 + @pdf.bounds.absolute_left, @pdf.y],
50
45
  [150.0 + @pdf.bounds.absolute_left, @pdf.y]]
51
- end
52
-
46
+ end
47
+
48
+ it "should draw a line from (200, 250) to (300, 250)" do
49
+ @pdf.horizontal_line(200,300,:at => 250)
50
+ line_drawing = PDF::Inspector::Graphics::Line.analyze(@pdf.render)
51
+ line_drawing.points.should == [[200,250],[300,250]]
52
+ end
53
+ end
54
+
55
+ describe "(Vertically)" do
56
+ it "should draw a line from (350, 300) to (350, 400)" do
57
+ @pdf.vertical_line(300,400,:at => 350)
58
+ line_drawing = PDF::Inspector::Graphics::Line.analyze(@pdf.render)
59
+ line_drawing.points.should == [[350,300],[350,400]]
60
+ end
61
+ it "should require a y coordinate" do
62
+ lambda { @pdf.vertical_line(400,500) }.
63
+ should.raise(ArgumentError)
64
+ end
53
65
  end
54
-
55
- end
66
+
67
+ end
56
68
 
57
69
  describe "When drawing a polygon" do
58
70
 
@@ -61,11 +73,11 @@ describe "When drawing a polygon" do
61
73
  it "should draw each line passed to polygon()" do
62
74
  @pdf.polygon([100,500],[100,400],[200,400])
63
75
 
64
- line_drawing = PDF::Inspector::Graphics::Line.analyze(@pdf.render)
76
+ line_drawing = PDF::Inspector::Graphics::Line.analyze(@pdf.render)
65
77
  line_drawing.points.should == [[100,500],[100,400],[200,400],[100,500]]
66
78
  end
67
79
 
68
- end
80
+ end
69
81
 
70
82
  describe "When drawing a rectangle" do
71
83
 
@@ -83,53 +95,53 @@ describe "When drawing a rectangle" do
83
95
 
84
96
  end
85
97
 
86
- end
98
+ end
99
+
100
+ describe "When drawing a curve" do
87
101
 
88
- describe "When drawing a curve" do
89
-
90
102
  before(:each) { create_pdf }
91
-
103
+
92
104
  it "should draw a bezier curve from 50,50 to 100,100" do
93
105
  @pdf.move_to [50,50]
94
106
  @pdf.curve_to [100,100],:bounds => [[20,90], [90,70]]
95
107
  curve = PDF::Inspector::Graphics::Curve.analyze(@pdf.render)
96
- curve.coords.should == [50.0, 50.0, 20.0, 90.0, 90.0, 70.0, 100.0, 100.0]
97
- end
98
-
108
+ curve.coords.should == [50.0, 50.0, 20.0, 90.0, 90.0, 70.0, 100.0, 100.0]
109
+ end
110
+
99
111
  it "should draw a bezier curve from 100,100 to 50,50" do
100
- @pdf.curve [100,100], [50,50], :bounds => [[20,90], [90,75]]
101
- curve = PDF::Inspector::Graphics::Curve.analyze(@pdf.render)
102
- curve.coords.should == [100.0, 100.0, 20.0, 90.0, 90.0, 75.0, 50.0, 50.0]
112
+ @pdf.curve [100,100], [50,50], :bounds => [[20,90], [90,75]]
113
+ curve = PDF::Inspector::Graphics::Curve.analyze(@pdf.render)
114
+ curve.coords.should == [100.0, 100.0, 20.0, 90.0, 90.0, 75.0, 50.0, 50.0]
103
115
  end
104
-
105
- end
116
+
117
+ end
106
118
 
107
119
  describe "When drawing an ellipse" do
108
- before(:each) do
120
+ before(:each) do
109
121
  create_pdf
110
122
  @pdf.ellipse_at [100,100], 25, 50
111
- @curve = PDF::Inspector::Graphics::Curve.analyze(@pdf.render)
112
- end
113
-
123
+ @curve = PDF::Inspector::Graphics::Curve.analyze(@pdf.render)
124
+ end
125
+
114
126
  it "should move the pointer to the center of the ellipse after drawing" do
115
127
  @curve.coords[-2..-1].should == [100,100]
116
- end
117
-
118
- end
128
+ end
129
+
130
+ end
119
131
 
120
132
  describe "When drawing a circle" do
121
- before(:each) do
133
+ before(:each) do
122
134
  create_pdf
123
- @pdf.circle_at [100,100], :radius => 25
135
+ @pdf.circle_at [100,100], :radius => 25
124
136
  @pdf.ellipse_at [100,100], 25, 25
125
- @curve = PDF::Inspector::Graphics::Curve.analyze(@pdf.render)
126
- end
127
-
128
- it "should stroke the same path as the equivalent ellipse" do
137
+ @curve = PDF::Inspector::Graphics::Curve.analyze(@pdf.render)
138
+ end
139
+
140
+ it "should stroke the same path as the equivalent ellipse" do
129
141
  middle = @curve.coords.length / 2
130
- @curve.coords[0...middle].should == @curve.coords[middle..-1]
142
+ @curve.coords[0...middle].should == @curve.coords[middle..-1]
131
143
  end
132
- end
144
+ end
133
145
 
134
146
  describe "When setting colors" do
135
147
 
@@ -144,54 +156,54 @@ describe "When setting colors" do
144
156
 
145
157
  it "should set fill colors" do
146
158
  @pdf.fill_color "ccff00"
147
- colors = PDF::Inspector::Graphics::Color.analyze(@pdf.render)
159
+ colors = PDF::Inspector::Graphics::Color.analyze(@pdf.render)
148
160
  # 80% red, 100% green, 0% blue
149
161
  colors.fill_color.should == [0.8,1.0,0]
150
- end
151
-
162
+ end
163
+
152
164
  it "should reset the colors on each new page if they have been defined" do
153
165
  @pdf.fill_color "ccff00"
154
- colors = PDF::Inspector::Graphics::Color.analyze(@pdf.render)
155
-
156
- colors.fill_color_count.should == 2
166
+ colors = PDF::Inspector::Graphics::Color.analyze(@pdf.render)
167
+
168
+ colors.fill_color_count.should == 2
157
169
  colors.stroke_color_count.should == 1
158
- @pdf.start_new_page
159
- @pdf.stroke_color "ff00cc"
160
-
161
- colors = PDF::Inspector::Graphics::Color.analyze(@pdf.render)
162
- colors.fill_color_count.should == 3
170
+ @pdf.start_new_page
171
+ @pdf.stroke_color "ff00cc"
172
+
173
+ colors = PDF::Inspector::Graphics::Color.analyze(@pdf.render)
174
+ colors.fill_color_count.should == 3
163
175
  colors.stroke_color_count.should == 3
164
-
176
+
165
177
  @pdf.start_new_page
166
- colors = PDF::Inspector::Graphics::Color.analyze(@pdf.render)
178
+ colors = PDF::Inspector::Graphics::Color.analyze(@pdf.render)
167
179
  colors.fill_color_count.should == 4
168
180
  colors.stroke_color_count.should == 4
169
-
181
+
170
182
  colors.fill_color.should == [0.8,1.0,0.0]
171
- colors.stroke_color.should == [1.0,0.0,0.8]
172
- end
183
+ colors.stroke_color.should == [1.0,0.0,0.8]
184
+ end
173
185
 
174
186
  end
175
187
 
176
188
  describe "When using painting shortcuts" do
177
189
  before(:each) { create_pdf }
178
-
190
+
179
191
  it "should convert stroke_some_method(args) into some_method(args); stroke" do
180
192
  @pdf.expects(:line_to).with([100,100])
181
193
  @pdf.expects(:stroke)
182
-
194
+
183
195
  @pdf.stroke_line_to [100,100]
184
- end
185
-
196
+ end
197
+
186
198
  it "should convert fill_some_method(args) into some_method(args); fill" do
187
- @pdf.expects(:line_to).with([100,100])
199
+ @pdf.expects(:line_to).with([100,100])
188
200
  @pdf.expects(:fill)
189
-
201
+
190
202
  @pdf.fill_line_to [100,100]
191
203
  end
192
-
204
+
193
205
  it "should not break method_missing" do
194
206
  lambda { @pdf.i_have_a_pretty_girlfriend_named_jia }.
195
- should.raise(NoMethodError)
207
+ should.raise(NoMethodError)
196
208
  end
197
- end
209
+ end