barby 0.6.5 → 0.6.8

Sign up to get free protection for your applications and to get access to all the features.
Files changed (41) hide show
  1. checksums.yaml +5 -5
  2. data/.gitignore +2 -0
  3. data/CHANGELOG +8 -0
  4. data/Gemfile +5 -0
  5. data/README.md +21 -20
  6. data/Rakefile +15 -0
  7. data/barby.gemspec +31 -0
  8. data/lib/barby/barcode/codabar.rb +82 -0
  9. data/lib/barby/barcode.rb +3 -3
  10. data/lib/barby/outputter/cairo_outputter.rb +11 -3
  11. data/lib/barby/outputter/png_outputter.rb +43 -11
  12. data/lib/barby/outputter/prawn_outputter.rb +12 -9
  13. data/lib/barby/outputter/rmagick_outputter.rb +38 -11
  14. data/lib/barby/outputter/svg_outputter.rb +11 -18
  15. data/lib/barby/outputter.rb +1 -1
  16. data/lib/barby/version.rb +2 -2
  17. data/test/barcodes.rb +20 -0
  18. data/test/bookland_test.rb +54 -0
  19. data/test/codabar_test.rb +58 -0
  20. data/test/code_128_test.rb +470 -0
  21. data/test/code_25_iata_test.rb +19 -0
  22. data/test/code_25_interleaved_test.rb +116 -0
  23. data/test/code_25_test.rb +110 -0
  24. data/test/code_39_test.rb +210 -0
  25. data/test/code_93_test.rb +144 -0
  26. data/test/data_matrix_test.rb +30 -0
  27. data/test/ean13_test.rb +169 -0
  28. data/test/ean8_test.rb +100 -0
  29. data/test/outputter/cairo_outputter_test.rb +129 -0
  30. data/test/outputter/html_outputter_test.rb +68 -0
  31. data/test/outputter/pdfwriter_outputter_test.rb +37 -0
  32. data/test/outputter/png_outputter_test.rb +49 -0
  33. data/test/outputter/prawn_outputter_test.rb +79 -0
  34. data/test/outputter/rmagick_outputter_test.rb +83 -0
  35. data/test/outputter/svg_outputter_test.rb +89 -0
  36. data/test/outputter_test.rb +134 -0
  37. data/test/pdf_417_test.rb +45 -0
  38. data/test/qr_code_test.rb +78 -0
  39. data/test/test_helper.rb +24 -0
  40. data/test/upc_supplemental_test.rb +109 -0
  41. metadata +157 -7
@@ -0,0 +1,169 @@
1
+ require 'test_helper'
2
+ require 'barby/barcode/ean_13'
3
+
4
+ class EAN13Test < Barby::TestCase
5
+
6
+ describe 'validations' do
7
+
8
+ before do
9
+ @valid = EAN13.new('123456789012')
10
+ end
11
+
12
+ it "should be valid with 12 digits" do
13
+ assert @valid.valid?
14
+ end
15
+
16
+ it "should not be valid with non-digit characters" do
17
+ @valid.data = "The shit apple doesn't fall far from the shit tree"
18
+ refute @valid.valid?
19
+ end
20
+
21
+ it "should not be valid with less than 12 digits" do
22
+ @valid.data = "12345678901"
23
+ refute @valid.valid?
24
+ end
25
+
26
+ it "should not be valid with more than 12 digits" do
27
+ @valid.data = "1234567890123"
28
+ refute @valid.valid?
29
+ end
30
+
31
+ it "should raise an exception when data is invalid" do
32
+ lambda{ EAN13.new('123') }.must_raise(ArgumentError)
33
+ end
34
+
35
+ end
36
+
37
+ describe 'data' do
38
+
39
+ before do
40
+ @data = '007567816412'
41
+ @code = EAN13.new(@data)
42
+ end
43
+
44
+ it "should have the same data as was passed to it" do
45
+ @code.data.must_equal @data
46
+ end
47
+
48
+ it "should have the expected characters" do
49
+ @code.characters.must_equal @data.split(//)
50
+ end
51
+
52
+ it "should have the expected numbers" do
53
+ @code.numbers.must_equal @data.split(//).map{|s| s.to_i }
54
+ end
55
+
56
+ it "should have the expected odd_and_even_numbers" do
57
+ @code.odd_and_even_numbers.must_equal [[2,4,1,7,5,0], [1,6,8,6,7,0]]
58
+ end
59
+
60
+ it "should have the expected left_numbers" do
61
+ #0=second number in number system code
62
+ @code.left_numbers.must_equal [0,7,5,6,7,8]
63
+ end
64
+
65
+ it "should have the expected right_numbers" do
66
+ @code.right_numbers.must_equal [1,6,4,1,2,5]#5=checksum
67
+ end
68
+
69
+ it "should have the expected numbers_with_checksum" do
70
+ @code.numbers_with_checksum.must_equal @data.split(//).map{|s| s.to_i } + [5]
71
+ end
72
+
73
+ it "should have the expected data_with_checksum" do
74
+ @code.data_with_checksum.must_equal @data+'5'
75
+ end
76
+
77
+ it "should return all digits and the checksum on to_s" do
78
+ @code.to_s.must_equal '0075678164125'
79
+ end
80
+
81
+ end
82
+
83
+ describe 'checksum' do
84
+
85
+ before do
86
+ @code = EAN13.new('007567816412')
87
+ end
88
+
89
+ it "should have the expected weighted_sum" do
90
+ @code.weighted_sum.must_equal 85
91
+ @code.data = '007567816413'
92
+ @code.weighted_sum.must_equal 88
93
+ end
94
+
95
+ it "should have the correct checksum" do
96
+ @code.checksum.must_equal 5
97
+ @code.data = '007567816413'
98
+ @code.checksum.must_equal 2
99
+ end
100
+
101
+ it "should have the correct checksum_encoding" do
102
+ @code.checksum_encoding.must_equal '1001110'
103
+ end
104
+
105
+ end
106
+
107
+ describe 'encoding' do
108
+
109
+ before do
110
+ @code = EAN13.new('750103131130')
111
+ end
112
+
113
+ it "should have the expected checksum" do
114
+ @code.checksum.must_equal 9
115
+ end
116
+
117
+ it "should have the expected checksum_encoding" do
118
+ @code.checksum_encoding.must_equal '1110100'
119
+ end
120
+
121
+ it "should have the expected left_parity_map" do
122
+ @code.left_parity_map.must_equal [:odd, :even, :odd, :even, :odd, :even]
123
+ end
124
+
125
+ it "should have the expected left_encodings" do
126
+ @code.left_encodings.must_equal %w(0110001 0100111 0011001 0100111 0111101 0110011)
127
+ end
128
+
129
+ it "should have the expected right_encodings" do
130
+ @code.right_encodings.must_equal %w(1000010 1100110 1100110 1000010 1110010 1110100)
131
+ end
132
+
133
+ it "should have the expected left_encoding" do
134
+ @code.left_encoding.must_equal '011000101001110011001010011101111010110011'
135
+ end
136
+
137
+ it "should have the expected right_encoding" do
138
+ @code.right_encoding.must_equal '100001011001101100110100001011100101110100'
139
+ end
140
+
141
+ it "should have the expected encoding" do
142
+ #Start Left Center Right Stop
143
+ @code.encoding.must_equal '101' + '011000101001110011001010011101111010110011' + '01010' + '100001011001101100110100001011100101110100' + '101'
144
+ end
145
+
146
+ end
147
+
148
+ describe 'static data' do
149
+
150
+ before :each do
151
+ @code = EAN13.new('123456789012')
152
+ end
153
+
154
+ it "should have the expected start_encoding" do
155
+ @code.start_encoding.must_equal '101'
156
+ end
157
+
158
+ it "should have the expected stop_encoding" do
159
+ @code.stop_encoding.must_equal '101'
160
+ end
161
+
162
+ it "should have the expected center_encoding" do
163
+ @code.center_encoding.must_equal '01010'
164
+ end
165
+
166
+ end
167
+
168
+ end
169
+
data/test/ean8_test.rb ADDED
@@ -0,0 +1,100 @@
1
+ require 'test_helper'
2
+ require 'barby/barcode/ean_8'
3
+
4
+ class EAN8Test < Barby::TestCase
5
+
6
+ describe 'validations' do
7
+
8
+ before do
9
+ @valid = EAN8.new('1234567')
10
+ end
11
+
12
+ it "should be valid with 7 digits" do
13
+ assert @valid.valid?
14
+ end
15
+
16
+ it "should not be valid with less than 7 digits" do
17
+ @valid.data = '123456'
18
+ refute @valid.valid?
19
+ end
20
+
21
+ it "should not be valid with more than 7 digits" do
22
+ @valid.data = '12345678'
23
+ refute @valid.valid?
24
+ end
25
+
26
+ it "should not be valid with non-digits" do
27
+ @valid.data = 'abcdefg'
28
+ refute @valid.valid?
29
+ end
30
+
31
+ end
32
+
33
+ describe 'checksum' do
34
+
35
+ before :each do
36
+ @code = EAN8.new('5512345')
37
+ end
38
+
39
+ it "should have the expected weighted_sum" do
40
+ @code.weighted_sum.must_equal 53
41
+ end
42
+
43
+ it "should have the expected checksum" do
44
+ @code.checksum.must_equal 7
45
+ end
46
+
47
+ end
48
+
49
+ describe 'data' do
50
+
51
+ before :each do
52
+ @data = '5512345'
53
+ @code = EAN8.new(@data)
54
+ end
55
+
56
+ it "should have the expected data" do
57
+ @code.data.must_equal @data
58
+ end
59
+
60
+ it "should have the expected odd_and_even_numbers" do
61
+ @code.odd_and_even_numbers.must_equal [[5,3,1,5],[4,2,5]]
62
+ end
63
+
64
+ it "should have the expected left_numbers" do
65
+ #EAN-8 includes the first character in the left-hand encoding, unlike EAN-13
66
+ @code.left_numbers.must_equal [5,5,1,2]
67
+ end
68
+
69
+ it "should have the expected right_numbers" do
70
+ @code.right_numbers.must_equal [3,4,5,7]
71
+ end
72
+
73
+ it "should return the data with checksum on to_s" do
74
+ @code.to_s.must_equal '55123457'
75
+ end
76
+
77
+ end
78
+
79
+ describe 'encoding' do
80
+
81
+ before :each do
82
+ @code = EAN8.new('5512345')
83
+ end
84
+
85
+ it "should have the expected left_parity_map" do
86
+ @code.left_parity_map.must_equal [:odd, :odd, :odd, :odd]
87
+ end
88
+
89
+ it "should have the expected left_encoding" do
90
+ @code.left_encoding.must_equal '0110001011000100110010010011'
91
+ end
92
+
93
+ it "should have the expected right_encoding" do
94
+ @code.right_encoding.must_equal '1000010101110010011101000100'
95
+ end
96
+
97
+ end
98
+
99
+ end
100
+
@@ -0,0 +1,129 @@
1
+ require 'test_helper'
2
+
3
+ class CairoOutputterTest < Barby::TestCase
4
+
5
+ def ps_available?
6
+ Cairo.const_defined?(:PSSurface)
7
+ end
8
+
9
+ def eps_available?
10
+ ps_available? and Cairo::PSSurface.method_defined?(:eps=)
11
+ end
12
+
13
+ def pdf_available?
14
+ Cairo.const_defined?(:PDFSurface)
15
+ end
16
+
17
+ def svg_available?
18
+ Cairo.const_defined?(:SVGSurface)
19
+ end
20
+
21
+ before do
22
+ load_outputter('cairo')
23
+ @barcode = Barby::Barcode.new
24
+ def @barcode.encoding; '101100111000'; end
25
+ @outputter = Barby::CairoOutputter.new(@barcode)
26
+ @outputters = Barby::Barcode.outputters
27
+ @surface = Cairo::ImageSurface.new(100, 100)
28
+ @context = Cairo::Context.new(@surface)
29
+ end
30
+
31
+ it "should have defined the render_to_cairo_context method" do
32
+ @outputters.must_include(:render_to_cairo_context)
33
+ end
34
+
35
+ it "should have defined the to_png method" do
36
+ @outputters.must_include(:to_png)
37
+ end
38
+
39
+ it "should have defined the to_ps and to_eps method if available" do
40
+ if ps_available?
41
+ @outputters.must_include(:to_ps)
42
+ if eps_available?
43
+ @outputters.must_include(:to_eps)
44
+ else
45
+ @outputters.wont_include(:to_eps)
46
+ end
47
+ else
48
+ @outputters.wont_include(:to_ps)
49
+ @outputters.wont_include(:to_eps)
50
+ end
51
+ end
52
+
53
+ it "should have defined the to_pdf method if available" do
54
+ if pdf_available?
55
+ @outputters.must_include(:to_pdf)
56
+ else
57
+ @outputters.wont_include(:to_pdf)
58
+ end
59
+ end
60
+
61
+ it "should have defined the to_svg method if available" do
62
+ if svg_available?
63
+ @outputters.must_include(:to_svg)
64
+ else
65
+ @outputters.wont_include(:to_svg)
66
+ end
67
+ end
68
+
69
+ it "should return the cairo context object it was given in render_to_cairo_context" do
70
+ @barcode.render_to_cairo_context(@context).object_id.must_equal @context.object_id
71
+ end
72
+
73
+ it "should return PNG image by the to_png method" do
74
+ png = @barcode.to_png
75
+ data = ruby_19_or_greater? ? png.force_encoding('BINARY') : png
76
+ data.must_match(/\A\x89PNG/n)
77
+ end
78
+
79
+ it "should return PS document by the to_ps method" do
80
+ if ps_available?
81
+ @barcode.to_ps.must_match(/\A%!PS-Adobe-[\d.]/)
82
+ end
83
+ end
84
+
85
+ it "should return EPS document by the to_eps method" do
86
+ if eps_available?
87
+ @barcode.to_eps.must_match(/\A%!PS-Adobe-[\d.]+ EPSF-[\d.]+/)
88
+ end
89
+ end
90
+
91
+ it "should return PDF document by the to_pdf method" do
92
+ if pdf_available?
93
+ pdf = @barcode.to_pdf
94
+ data = ruby_19_or_greater? ? pdf.force_encoding('BINARY') : pdf
95
+ data.must_match(/\A%PDF-[\d.]+/n)
96
+ end
97
+ end
98
+
99
+ it "should return SVG document by the to_svg method" do
100
+ if svg_available?
101
+ @barcode.to_svg.must_match(/<\/svg>\s*\Z/m)
102
+ end
103
+ end
104
+
105
+ it "should have x, y, width, height, full_width, full_height, xdim and margin attributes" do
106
+ @outputter.must_respond_to(:x)
107
+ @outputter.must_respond_to(:y)
108
+ @outputter.must_respond_to(:width)
109
+ @outputter.must_respond_to(:height)
110
+ @outputter.must_respond_to(:full_width)
111
+ @outputter.must_respond_to(:full_height)
112
+ @outputter.must_respond_to(:xdim)
113
+ @outputter.must_respond_to(:margin)
114
+ end
115
+
116
+ it "should not change attributes when given an options hash to render" do
117
+ %w(x y height xdim).each do |m|
118
+ @outputter.send("#{m}=", 10)
119
+ @outputter.send(m).must_equal 10
120
+ end
121
+ @outputter.render_to_cairo_context(@context,
122
+ :x => 20,
123
+ :y => 20,
124
+ :height => 20,
125
+ :xdim => 20)
126
+ %w(x y height xdim).each{|m| @outputter.send(m).must_equal 10 }
127
+ end
128
+
129
+ end
@@ -0,0 +1,68 @@
1
+ require 'test_helper'
2
+ require 'barby/barcode/code_128'
3
+ #require 'barby/outputter/html_outputter'
4
+
5
+ class HtmlOutputterTest < Barby::TestCase
6
+
7
+ class MockCode
8
+ attr_reader :encoding
9
+ def initialize(e)
10
+ @encoding = e
11
+ end
12
+ def two_dimensional?
13
+ encoding.is_a? Array
14
+ end
15
+ end
16
+
17
+ before do
18
+ load_outputter('html')
19
+ @barcode = Barby::Code128B.new('BARBY')
20
+ @outputter = HtmlOutputter.new(@barcode)
21
+ end
22
+
23
+ it "should register to_html" do
24
+ Barcode.outputters.must_include(:to_html)
25
+ end
26
+
27
+ it 'should have the expected start HTML' do
28
+ assert_equal '<table class="barby-barcode"><tbody>', @outputter.start
29
+ end
30
+
31
+ it 'should be able to set additional class name' do
32
+ @outputter.class_name = 'humbaba'
33
+ assert_equal '<table class="barby-barcode humbaba"><tbody>', @outputter.start
34
+ end
35
+
36
+ it 'should have the expected stop HTML' do
37
+ assert_equal '</tbody></table>', @outputter.stop
38
+ end
39
+
40
+ it 'should build the expected cells' do
41
+ assert_equal ['<td class="barby-cell on"></td>', '<td class="barby-cell off"></td>', '<td class="barby-cell off"></td>', '<td class="barby-cell on"></td>'],
42
+ @outputter.cells_for([true, false, false, true])
43
+ end
44
+
45
+ it 'should build the expected rows' do
46
+ assert_equal(
47
+ [
48
+ "<tr class=\"barby-row\">#{@outputter.cells_for([true, false]).join}</tr>",
49
+ "<tr class=\"barby-row\">#{@outputter.cells_for([false, true]).join}</tr>",
50
+ ],
51
+ @outputter.rows_for([[true, false],[false, true]])
52
+ )
53
+ end
54
+
55
+ it 'should have the expected rows' do
56
+ barcode = MockCode.new('101100')
57
+ outputter = HtmlOutputter.new(barcode)
58
+ assert_equal outputter.rows_for([[true, false, true, true, false, false]]), outputter.rows
59
+ barcode = MockCode.new(['101', '010'])
60
+ outputter = HtmlOutputter.new(barcode)
61
+ assert_equal outputter.rows_for([[true, false, true], [false, true, false]]), outputter.rows
62
+ end
63
+
64
+ it 'should have the expected html' do
65
+ assert_equal @outputter.start + @outputter.rows.join + @outputter.stop, @outputter.to_html
66
+ end
67
+
68
+ end
@@ -0,0 +1,37 @@
1
+ unless RUBY_VERSION >= '1.9'
2
+
3
+ require 'test_helper'
4
+ require 'pdf/writer'
5
+
6
+ class PDFWriterOutputterTest < Barby::TestCase
7
+
8
+ before do
9
+ load_outputter('pdfwriter')
10
+ @barcode = Barcode.new
11
+ def @barcode.encoding; '101100111000'; end
12
+ @outputter = PDFWriterOutputter.new(@barcode)
13
+ @pdf = PDF::Writer.new
14
+ end
15
+
16
+ it "should have registered annotate_pdf" do
17
+ Barcode.outputters.must_include(:annotate_pdf)
18
+ end
19
+
20
+ it "should have defined the annotate_pdf method" do
21
+ @outputter.must_respond_to(:annotate_pdf)
22
+ end
23
+
24
+ it "should return the pdf object it was given in annotate_pdf" do
25
+ @barcode.annotate_pdf(@pdf).object_id.must_equal @pdf.object_id
26
+ end
27
+
28
+ it "should have x, y, height and xdim attributes" do
29
+ @outputter.must_respond_to(:x)
30
+ @outputter.must_respond_to(:y)
31
+ @outputter.must_respond_to(:height)
32
+ @outputter.must_respond_to(:xdim)
33
+ end
34
+
35
+ end
36
+
37
+ end
@@ -0,0 +1,49 @@
1
+ require 'test_helper'
2
+
3
+ class PngTestBarcode < Barby::Barcode
4
+ def initialize(data)
5
+ @data = data
6
+ end
7
+ def encoding
8
+ @data
9
+ end
10
+ end
11
+
12
+ class PngOutputterTest < Barby::TestCase
13
+
14
+ before do
15
+ load_outputter('png')
16
+ @barcode = PngTestBarcode.new('10110011100011110000')
17
+ @outputter = PngOutputter.new(@barcode)
18
+ end
19
+
20
+ it "should register to_png and to_image" do
21
+ Barcode.outputters.must_include(:to_png)
22
+ Barcode.outputters.must_include(:to_image)
23
+ end
24
+
25
+ it "should return a ChunkyPNG::Datastream on to_datastream" do
26
+ @barcode.to_datastream.must_be_instance_of(ChunkyPNG::Datastream)
27
+ end
28
+
29
+ it "should return a string on to_png" do
30
+ @barcode.to_png.must_be_instance_of(String)
31
+ end
32
+
33
+ it "should return a ChunkyPNG::Image on to_canvas" do
34
+ @barcode.to_image.must_be_instance_of(ChunkyPNG::Image)
35
+ end
36
+
37
+ it "should have a width equal to Xdim * barcode_string.length" do
38
+ @outputter.width.must_equal @outputter.barcode.encoding.length * @outputter.xdim
39
+ end
40
+
41
+ it "should have a full_width which is the sum of width + (margin*2)" do
42
+ @outputter.full_width.must_equal @outputter.width + (@outputter.margin*2)
43
+ end
44
+
45
+ it "should have a full_height which is the sum of height + (margin*2)" do
46
+ @outputter.full_height.must_equal @outputter.height + (@outputter.margin*2)
47
+ end
48
+
49
+ end
@@ -0,0 +1,79 @@
1
+ require 'test_helper'
2
+
3
+ class PrawnOutputterTest < Barby::TestCase
4
+
5
+ before do
6
+ load_outputter('prawn')
7
+ @barcode = Barcode.new
8
+ def @barcode.encoding; '10110011100011110000'; end
9
+ @outputter = PrawnOutputter.new(@barcode)
10
+ end
11
+
12
+ it "should register to_pdf and annotate_pdf" do
13
+ Barcode.outputters.must_include(:to_pdf)
14
+ Barcode.outputters.must_include(:annotate_pdf)
15
+ end
16
+
17
+ it "should have a to_pdf method" do
18
+ @outputter.must_respond_to(:to_pdf)
19
+ end
20
+
21
+ it "should return a PDF document in a string on to_pdf" do
22
+ @barcode.to_pdf.must_be_instance_of(String)
23
+ end
24
+
25
+ it "should return the same Prawn::Document on annotate_pdf" do
26
+ doc = Prawn::Document.new
27
+ @barcode.annotate_pdf(doc).object_id.must_equal doc.object_id
28
+ end
29
+
30
+ it "should default x and y to margin value" do
31
+ @outputter.margin = 123
32
+ @outputter.x.must_equal 123
33
+ @outputter.y.must_equal 123
34
+ end
35
+
36
+ it "should default ydim to xdim value" do
37
+ @outputter.xdim = 321
38
+ @outputter.ydim.must_equal 321
39
+ end
40
+
41
+ it "should be able to calculate width required" do
42
+ @outputter.width.must_equal @barcode.encoding.length
43
+ @outputter.xdim = 2
44
+ @outputter.width.must_equal @barcode.encoding.length * 2
45
+ @outputter.full_width.must_equal @barcode.encoding.length * 2
46
+ @outputter.margin = 5
47
+ @outputter.full_width.must_equal((@barcode.encoding.length * 2) + 10)
48
+
49
+ #2D
50
+ barcode = Barcode2D.new
51
+ def barcode.encoding; ['111', '000', '111'] end
52
+ outputter = PrawnOutputter.new(barcode)
53
+ outputter.width.must_equal 3
54
+ outputter.xdim = 2
55
+ outputter.margin = 5
56
+ outputter.width.must_equal 6
57
+ outputter.full_width.must_equal 16
58
+ end
59
+
60
+ it "should be able to calculate height required" do
61
+ @outputter.full_height.must_equal @outputter.height
62
+ @outputter.margin = 5
63
+ @outputter.full_height.must_equal @outputter.height + 10
64
+
65
+ #2D
66
+ barcode = Barcode2D.new
67
+ def barcode.encoding; ['111', '000', '111'] end
68
+ outputter = PrawnOutputter.new(barcode)
69
+ outputter.height.must_equal 3
70
+ outputter.xdim = 2 #ydim defaults to xdim
71
+ outputter.margin = 5
72
+ outputter.height.must_equal 6
73
+ outputter.full_height.must_equal 16
74
+ outputter.ydim = 3 #ydim overrides xdim when set
75
+ outputter.height.must_equal 9
76
+ outputter.full_height.must_equal 19
77
+ end
78
+
79
+ end