extface 0.2.4 → 0.2.5

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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: c5694ea075490fadb29202d3113d02a0963ab8d1
4
- data.tar.gz: 0fccac085b944d300d7571da5652e8e7687e24e0
3
+ metadata.gz: 0f43e7be656154e78b1e024bb74d6dbc833998e9
4
+ data.tar.gz: e3287aa51199d87998f457a52011fd3228ee25ed
5
5
  SHA512:
6
- metadata.gz: 5cd19d2b097b1891328347a7c1780c6d45bb6a8e9ae3d346e731f28aa8f1ff3aab457845e305a7ba79aad1a42bf19817664fc93599df0516a07637736972b064
7
- data.tar.gz: a8d425df6a8f08ac450401a09d1d48c445fc8b3036785c79e99e33996824e32bdb8e3e7a21b7fe01b3c211959f58ba0886eece123052260afb6eba24bb52ee78
6
+ metadata.gz: 7a1bc3344bfcc42fd1e215f21d3bf4f68a10f85f07d2cccd9bed97945ceecf25c713e610963975653e5d7241baa5ac0e37d7457af7a004b85c323e8983d952f0
7
+ data.tar.gz: f4e0d647d299eb222e418b7556206ee86b45cd51d33aad8ec180d5407a563ff8089d9d24a01963e5eb2f277695aeed55e0a6492c724500c8e262aa4476e6cbf4
@@ -42,7 +42,26 @@ module Extface
42
42
  "#{driver.class::NAME} #{t('.control_panel')}".html_safe
43
43
  end +
44
44
  content_tag(:div, class: 'panel-body') do
45
- render "extface/driver/#{driver.class.name.demodulize.underscore}/control"
45
+ content_tag(:div, class: 'col-sm-8') do
46
+ control_partial = "extface/driver/#{driver.class.name.demodulize.underscore}/control"
47
+ begin
48
+ render control_partial
49
+ rescue ActionView::MissingTemplate
50
+ case
51
+ when driver.fiscal? then
52
+ render "extface/driver/control_fiscal"
53
+ when driver.print? then
54
+ render "extface/driver/control_print"
55
+ when driver.report? then
56
+ render "extface/driver/control_report"
57
+ else
58
+ render "extface/driver/control_raw"
59
+ end
60
+ end
61
+ end +
62
+ content_tag(:div, class: 'col-sm-4') do
63
+ text_area_tag :extface_control_monitor, nil, rows: 8, class: 'form-control'
64
+ end
46
65
  end
47
66
  end
48
67
  end
@@ -4,7 +4,7 @@ module Extface
4
4
  def subdrivers(object)
5
5
  [].tap do |drivers|
6
6
  object.subclasses.each do |s|
7
- drivers << s
7
+ drivers << s unless s.abstract_class
8
8
  drivers << subdrivers(s) if s.subclasses.any?
9
9
  end
10
10
  end
@@ -14,7 +14,7 @@ module Extface
14
14
  Extface::Engine.eager_load! if Rails.env.development?
15
15
  [].tap do |drivers|
16
16
  Extface::Driver.subclasses.each do |s|
17
- drivers << s
17
+ drivers << s unless s.abstract_class
18
18
  drivers << subdrivers(s)
19
19
  end
20
20
  end.flatten.group_by{ |x| x::GROUP }.sort.collect{ |group, drivers| [group, drivers.collect{ |d| [d::NAME, d.to_s] }.sort ] }
@@ -0,0 +1,78 @@
1
+ module Extface
2
+ class Driver::Base::Fiscal < Extface::Driver
3
+ self.abstract_class = true
4
+
5
+ NAME = 'Fiscal Device Name'.freeze
6
+
7
+ GROUP = Extface::FISCAL_DRIVER
8
+
9
+ DEVELOPMENT = true #driver is not ready for production (not passing all tests or has major bugs)
10
+
11
+ # Select driver features
12
+ RAW = true #responds to #push(data) and #pull
13
+ PRINT = false #POS, slip printers
14
+ FISCAL = true #cash registers, fiscal printers
15
+ REPORT = false #only transmit data that must be parsed by handler, CDR, report devices
16
+
17
+ def handle(buffer) raise_not_implemented end
18
+
19
+ #tests
20
+ def non_fiscal_test() raise_not_implemented end
21
+ def fiscal_test() raise_not_implemented end
22
+
23
+ #reports
24
+ def z_report_session() raise_not_implemented end
25
+ def x_report_session() raise_not_implemented end
26
+ def period_report_session(from, to, detailed = true) raise_not_implemented end
27
+
28
+ #repair interrupted doc
29
+ def cancel_doc_session() raise_not_implemented end
30
+
31
+ #print driver compatibility session
32
+ # device.session do |s|
33
+ # s.open_non_fiscal_doc if device.fiscal?
34
+ # s.print
35
+ # s.print
36
+ # ...
37
+ # s.close_non_fiscal_doc if device.fiscal?
38
+ # end
39
+ def open_non_fiscal_doc() raise_not_implemented end
40
+ def print() raise_not_implemented end
41
+ def close_non_fiscal_doc() raise_not_implemented end
42
+
43
+ #fiscal wild session
44
+ def open_fiscal_doc(operator = '', password = '') raise_not_implemented end
45
+ def add_sale(sale_item) raise_not_implemented end #instance of Extface::Driver::Base::Fiscal::SaleItem
46
+ def add_comment(text = '') raise_not_implemented end
47
+ def add_payment(type_num, value = 0.00) raise_not_implemented end
48
+ def total_payment() raise_not_implemented end #auto calculated total default payment
49
+ def close_fiscal_doc() raise_not_implemented end
50
+
51
+ def cancel_doc_session() raise_not_implemented end #repair from broken doc session
52
+
53
+ #fiscal basket session of Extface::Driver::Base::Fiscal::SaleItem instances
54
+ def sale_and_pay_items_session(sale_items = [], operator = '', password = '') raise_not_implemented end
55
+
56
+ class SaleItem
57
+ include ActiveModel::Validations
58
+ attr_reader :price, # Float
59
+ :text1, :text2, # String
60
+ :tax_group, #Float
61
+ :qty, #Fixnum
62
+ :percent, #Float
63
+ :neto,
64
+ :number #Fixnum
65
+ def initialize(attributes)
66
+ @price, @text1, @text2, @tax_group, @qty, @percent, @neto, @number = attributes[:price], attributes[:text1].to_s, attributes[:text2].to_s, attributes[:tax_group], attributes[:qty], attributes[:percent], attributes[:neto], attributes[:number]
67
+ raise "invalid price" unless price.kind_of?(Float)
68
+ raise "invalid tax group" if tax_group.present? && !tax_group.kind_of(Integer)
69
+ raise "invalid qty" if qty.present? && !qty.kind_of(Float)
70
+ end
71
+ end
72
+
73
+ private
74
+ def raise_not_implemented
75
+ raise "not implemented"
76
+ end
77
+ end
78
+ end
@@ -11,17 +11,8 @@
11
11
  #01h 20h–FFh 20h–FFh 20h–FFh 20h–FFh 04h 80h–FFh 05h 30h–3Fh 03h
12
12
 
13
13
  module Extface
14
- class Driver::DaisyFx1200 < Extface::Driver
14
+ class Driver::DaisyFx1200 < Extface::Driver::Base::Fiscal
15
15
  NAME = 'Daisy FX1200 (Serial)'.freeze
16
- GROUP = Extface::FISCAL_DRIVER
17
-
18
- DEVELOPMENT = true #driver is not ready for production (not passing all tests or has major bugs)
19
-
20
- # Select driver features
21
- RAW = true #responds to #push(data) and #pull
22
- PRINT = false #POS, slip printers
23
- FISCAL = true #cash registers, fiscal printers
24
- REPORT = false #only transmit data that must be parsed by handler, CDR, report devices
25
16
 
26
17
  RESPONSE_TIMEOUT = 3 #seconds
27
18
  INVALID_FRAME_RETRIES = 6 #seconds
@@ -55,25 +46,48 @@ module Extface
55
46
  end
56
47
  end
57
48
 
58
- def autocut(partial = true) # return "P" - success, "F" - failed
59
- resp = fsend(Printer::CUT)
60
- resp == "P"
61
- end
62
-
49
+ #tests
63
50
  def non_fiscal_test
64
51
  device.session("Non Fiscal Text") do |s|
65
52
  s.notify "Printing Non Fiscal Text"
66
- s.fsend Sales::START_NON_FISCAL_DOC
67
- s.fsend Sales::PRINT_NON_FISCAL_TEXT, "********************************"
68
- s.fsend Sales::PRINT_NON_FISCAL_TEXT, "Extface Print Test".center(32)
69
- s.fsend Sales::PRINT_NON_FISCAL_TEXT, "********************************"
53
+ s.open_non_fiscal_doc
54
+ s.print "********************************"
55
+ s.print "Extface Print Test".center(32)
56
+ s.print "********************************"
70
57
  s.fsend Printer::MOVE, "1"
71
- s.fsend Sales::PRINT_NON_FISCAL_TEXT, "Driver: " + "#{self.class::NAME}".truncate(24)
72
- s.fsend Sales::END_NON_FISCAL_DOC
58
+ s.print "Driver: " + "#{self.class::NAME}".truncate(24)
59
+ s.close_non_fiscal_doc
73
60
  s.notify "Printing finished"
74
61
  end
75
62
  end
76
63
 
64
+ def fiscal_test
65
+ sale_and_pay_items_session([
66
+ SaleItem.new( price: 0.01, text1: "Extface Test" )
67
+ ])
68
+ end
69
+
70
+ #reports
71
+ def z_report_session
72
+ device.session("Z Report") do |s|
73
+ s.notify "Z Report Start"
74
+ s.fsend Closure::DAY_FIN_REPORT, "0"
75
+ s.notify "Z Report End"
76
+ end
77
+ end
78
+
79
+ def x_report_session
80
+ device.session("X Report") do |s|
81
+ s.notify "X Report Start"
82
+ s.fsend Closure::DAY_FIN_REPORT, "2"
83
+ s.notify "X Report End"
84
+ end
85
+ end
86
+
87
+ def period_report_session(from, to, detailed = true)
88
+ end
89
+
90
+ #print
77
91
  def open_non_fiscal_doc
78
92
  fsend Sales::START_NON_FISCAL_DOC
79
93
  @print_session = true
@@ -89,62 +103,69 @@ module Extface
89
103
  @print_session = false
90
104
  end
91
105
 
92
- def fiscal_test
93
- sale_and_pay_items_session([
94
- { price: 0.01, text1: "Extface Test" }
95
- ])
106
+ #fiscal
107
+ def open_fiscal_doc(operator = "1", password = "1")
108
+ fsend Sales::START_FISCAL_DOC, "#{operator.presence || "1"},#{password.presence || "1"},00001"
109
+ @fiscal_session = true
96
110
  end
97
111
 
98
- def build_sale_data(price, text1 = nil, text2 = nil, tax_group = 2, qty = nil, percent = nil, neto = nil)
99
- "".tap() do |data|
100
- data << text1 unless text1.blank?
101
- data << "\x0a#{text2}" unless text2.blank?
102
- data << "\t"
103
- data << TAX_GROUPS_MAP[tax_group || 2]
104
- data << price.to_s
105
- data << "*#{qty.to_s}" unless qty.blank?
106
- data << ",#{percent}" unless percent.blank?
107
- data << "$#{neto}" unless neto.blank?
108
- end
112
+ def close_fiscal_doc
113
+ raise "Not in fiscal session" unless @fiscal_session
114
+ fsend Sales::END_FISCAL_DOC
115
+ @fiscal_session = false
116
+ end
117
+
118
+ def add_sale(sale_item)
119
+ raise "Not in fiscal session" unless @fiscal_session
120
+ fsend Sales::SALE_AND_SHOW, build_sale_data(sale_item)
121
+ end
122
+
123
+ def add_comment(text)
124
+ raise "Not in fiscal session" unless @fiscal_session
109
125
  end
110
126
 
127
+ def add_payment(type_num)
128
+ raise "Not in fiscal session" unless @fiscal_session
129
+ end
130
+
131
+ def total_payment
132
+ raise "Not in fiscal session" unless @fiscal_session
133
+ fsend(Sales::TOTAL, "\t")
134
+ end
135
+
136
+ #basket
111
137
  def sale_and_pay_items_session(items = [], operator = "1", password = "1")
112
138
  device.session("Fiscal Doc") do |s|
113
139
  s.notify "Fiscal Doc Start"
114
- s.fsend Sales::START_FISCAL_DOC, "#{operator || "1"},#{password || "1"},00001"
140
+ s.open_fiscal_doc
141
+ s.notify "Register Sale"
115
142
  items.each do |item|
116
- s.fsend Sales::SALE_AND_SHOW, build_sale_data(item[:price], item[:text1], item[:text2], item[:tax_group], item[:qty], item[:percent], item[:neto])
143
+ s.add_sale(item)
117
144
  end
118
- s.fsend(Sales::TOTAL, "\t")
119
- s.fsend(Sales::END_FISCAL_DOC)
145
+ s.notify "Register Payment"
146
+ s.total_payment
147
+ s.notify "Close Fiscal Receipt"
148
+ s.close_fiscal_doc
120
149
  s.notify "Fiscal Doc End"
121
150
  end
122
151
  end
123
152
 
124
- def z_report_session
125
- device.session("Z Report") do |s|
126
- s.notify "Z Report Start"
127
- s.fsend Closure::DAY_FIN_REPORT, "0"
128
- s.notify "Z Report End"
129
- end
130
- end
131
-
132
- def x_report_session
133
- device.session("X Report") do |s|
134
- s.notify "X Report Start"
135
- s.fsend Closure::DAY_FIN_REPORT, "2"
136
- s.notify "X Report End"
137
- end
138
- end
139
-
140
153
  def cancel_doc_session
141
154
  device.session("Doc cancel") do |s|
142
155
  s.notify "Doc Cancel Start"
143
156
  s.fsend Sales::CANCEL_DOC
157
+ s.autocut
144
158
  s.notify "Doc Cancel End"
145
159
  end
146
160
  end
147
-
161
+
162
+ #other
163
+ def autocut(partial = true) # return "P" - success, "F" - failed
164
+ resp = fsend(Printer::CUT)
165
+ resp == "P"
166
+ end
167
+
168
+ # auto called for session, return true for OK
148
169
  def check_status
149
170
  flush
150
171
  fsend(Info::STATUS) # return 6 byte status
@@ -163,16 +184,7 @@ module Extface
163
184
  packet << ETX
164
185
  end
165
186
  end
166
-
167
- def fsend!(cmd, data = "") # return data or raise
168
- push build_packet(cmd, data) # return 6 byte status
169
- if resp = frecv(RESPONSE_TIMEOUT)
170
- return resp.data if resp.valid?
171
- else
172
- raise errors.full_messages.join(', ')
173
- end
174
- end
175
-
187
+
176
188
  def fsend(cmd, data = "") #return data or nil
177
189
  packet_data = build_packet(cmd, data)
178
190
  result = false
@@ -199,7 +211,20 @@ module Extface
199
211
  end
200
212
  end
201
213
 
202
- private
214
+ private
215
+ def build_sale_data(item)
216
+ "".tap() do |data|
217
+ data << item.text1 unless item.text1.blank?
218
+ data << "\x0a#{text2}" unless item.text2.blank?
219
+ data << "\t"
220
+ data << TAX_GROUPS_MAP[item.tax_group || 2]
221
+ data << item.price.to_s
222
+ data << "*#{item.qty.to_s}" unless item.qty.blank?
223
+ data << ",#{item.percent}" unless item.percent.blank?
224
+ data << "$#{neto}" unless item.neto.blank?
225
+ end
226
+ end
227
+
203
228
  def bcc(buffer)
204
229
  sum = 0
205
230
  buffer.each_byte do |byte|
@@ -36,7 +36,11 @@ module Extface
36
36
  PRINT_RECEIPT_HEADER = 0x38
37
37
  end
38
38
  module Reports
39
- SILENT0_PLU = 0x22
39
+ FP_DETAILED_BLOCKS = 0x1C
40
+ FP_GENERAL_BLOCKS = 0x1D
41
+ FP_DETAILED_DATES = 0x1E
42
+ FP_GENERAL_DATES = 0x1F
43
+ SILENT_PLU = 0x22
40
44
  SILENT_PRINTER = 0x23
41
45
  PLU_REPORT = 0x32
42
46
  DAILY_REPORT = 0x33
@@ -5,17 +5,8 @@
5
5
  #AAh 55h 0–FFh 0–FFh 10h–70h 0-FFh 30h–3Fh 0-FFh
6
6
 
7
7
  module Extface
8
- class Driver::EltradeTmU220 < Extface::Driver
9
- NAME = 'Eltrade TM-U220 (Serial)'.freeze
10
- GROUP = Extface::FISCAL_DRIVER
11
-
12
- DEVELOPMENT = true #driver is not ready for production (not passing all tests or has major bugs)
13
-
14
- # Select driver features
15
- RAW = true #responds to #push(data) and #pull
16
- PRINT = false #POS, slip printers
17
- FISCAL = true #cash registers, fiscal printers
18
- REPORT = false #only transmit data that must be parsed by handler, CDR, report devices
8
+ class Driver::EltradeTmU220 < Extface::Driver::Base::Fiscal
9
+ NAME = 'Eltrade TM-U220 (Serial)'.freeze
19
10
 
20
11
  RESPONSE_TIMEOUT = 3 #seconds
21
12
  INVALID_FRAME_RETRIES = 6 #count
@@ -43,54 +34,75 @@ module Extface
43
34
  return bytes_processed
44
35
  end
45
36
 
46
- def open_receipt(variant = nil)
47
- fsend Receipt::OPEN_RECEIPT
48
- unless variant.blank?
49
- fsend Receipt::PRINT_RECEIPT, variant
37
+ #tests
38
+ def non_fiscal_test
39
+ device.session("Non Fiscal Text") do |s|
40
+ s.notify "Printing Non Fiscal Text"
41
+ s.open_non_fiscal_doc
42
+ s.print "********************************"
43
+ s.print "Extface Print Test".center(32)
44
+ s.print "********************************"
45
+ s.print ""
46
+ s.print "Driver: " + "#{self.class::NAME}".truncate(24)
47
+ s.close_non_fiscal_doc
48
+ s.notify "Printing finished"
50
49
  end
51
- status = get_printer_status
52
50
  end
53
51
 
54
- def close_receipt
55
- fsend Receipt::CLOSE_RECEIPT
56
- status = get_printer_status
52
+ def fiscal_test
53
+ sale_and_pay_items_session([
54
+ SaleItem.new( price: 0.01, text1: "Extface Test" )
55
+ ])
57
56
  end
58
57
 
59
- def send_comment(text)
60
- fsend Receipt::PRINT_RECEIPT, Receipt::Variant::COMMENT + text
61
- status = get_printer_status
58
+ #reports
59
+ def z_report_session
60
+ device.session("Z Report") do |s|
61
+ s.notify "Z Report Start"
62
+ s.fsend Reports::DAILY_REPORT, FLAG_TRUE
63
+ status = s.get_printer_status
64
+ s.notify "Z Report End"
65
+ end
62
66
  end
63
67
 
64
- def send_plu(plu_data)
65
- fsend Receipt::PRINT_RECEIPT, Receipt::Variant::PLU + plu_data
66
- status = get_printer_status
68
+ def x_report_session
69
+ device.session("Z Report") do |s|
70
+ s.notify "X Report Start"
71
+ s.fsend Reports::DAILY_REPORT, FLAG_FALSE
72
+ status = s.get_printer_status
73
+ s.notify "X Report End"
74
+ end
67
75
  end
68
76
 
69
- def send_payment(type_num = 0, value = nil) # 0, 1, 2, 3
70
- value_bytes = "\x00\x00\x00\x00" # recalculate
71
- unless value.nil?
72
- value_units = (value * 100).to_i # !FIXME
73
- value_bytes = "".b
74
- 4.times{ |shift| value_bytes.insert 0, ((value_units >> shift*8) & 0xff).chr }
77
+ def period_report_session(from, to, detailed = true)
78
+ device.session("FP Report #{from.to_date.human} = #{to.to_date.human}") do |s|
79
+ dates_bytes = "".b
80
+ dates_bytes << from.day
81
+ dates_bytes << from.month
82
+ dates_bytes << from.year - 2000
83
+ dates_bytes << 0
84
+ dates_bytes << to.day
85
+ dates_bytes << to.month
86
+ dates_bytes << to.year - 2000
87
+ dates_bytes << 0
88
+ s.notify "FP Report Start"
89
+ s.fsend detailed ? Reports::FP_DETAILED_DATES : Reports::FP_GENERAL_DATES, dates_bytes
90
+ status = s.get_printer_status
91
+ s.notify "FP Report End"
75
92
  end
76
- fsend Receipt::PRINT_RECEIPT, "" << (9 + type_num).chr << value_bytes
77
- status = get_printer_status
78
93
  end
79
94
 
80
- def non_fiscal_test
81
- device.session("Non Fiscal Text") do |s|
82
- s.notify "Printing Non Fiscal Text"
83
- s.open_non_fiscal_doc
84
- s.send_comment "********************************"
85
- s.send_comment "Extface Print Test".center(32)
86
- s.send_comment "********************************"
87
- s.send_comment ""
88
- s.send_comment "Driver: " + "#{self.class::NAME}".truncate(24)
89
- s.close_non_fiscal_doc
90
- s.notify "Printing finished"
95
+ def cancel_doc_session
96
+ device.session("Doc cancel") do |s|
97
+ s.notify "Doc Cancel Start"
98
+ # cancel old one by open/close new one
99
+ s.open_fiscal_doc
100
+ s.close_fiscal_doc
101
+ s.notify "Doc Cancel End"
91
102
  end
92
103
  end
93
104
 
105
+ #print
94
106
  def open_non_fiscal_doc
95
107
  open_receipt Receipt::Variant::START_COMMENT_RECEIPT
96
108
  @print_session = true
@@ -102,85 +114,70 @@ module Extface
102
114
  end
103
115
 
104
116
  def close_non_fiscal_doc
117
+ raise "Not in print session" unless @print_session
105
118
  close_receipt
106
119
  @print_session = false
107
120
  end
121
+
122
+
123
+ #fiscal
124
+ def open_fiscal_doc(operator = '', password = '')
125
+ set_operatior(operator) if operator.present?
126
+ open_receipt
127
+ @fiscal_session = true
128
+ end
108
129
 
109
- def fiscal_test
110
- sale_and_pay_items_session([
111
- { price: 0.01, text1: "Extface Test" }
112
- ])
130
+ def close_fiscal_doc
131
+ raise "Not in fiscal session" unless @fiscal_session
132
+ close_receipt
133
+ @fiscal_session = false
134
+ end
135
+
136
+ def add_sale(sale_item)
137
+ raise "Not in fiscal session" unless @fiscal_session
138
+ send_plu build_sale_data(sale_item)
139
+ add_comment(sale_item.text2) if sale_item.text2.present?
113
140
  end
114
141
 
115
- def build_sale_data(price, text1 = "", text2 = nil, tax_group = 2, qty = 1, percent = nil, neto = nil, number = nil)
116
- "".b.tap() do |data|
117
- price_units = (price * 100).to_i # !FIXME
118
- price_bytes = "".b
119
- 4.times{ |shift| price_bytes.insert 0, ((price_units >> shift*8) & 0xff).chr }
120
- data << price_bytes
121
- qty_units = ((qty || 1) * 1000).to_i # !FIXME
122
- qty_bytes = "".b
123
- 4.times{ |shift| qty_bytes.insert 0, ((qty_units >> shift*8) & 0xff).chr }
124
- data << qty_bytes
125
- data << "\x00".b #number len FIXME
126
- data << "\xAA\xAA\xAA\xAA\xAA\xAA".b #number FIXME
127
- text = text1.truncate(20)
128
- data << text.length.chr
129
- data << text.ljust(20, " ").b
130
- data << (tax_group || 2).chr
142
+ def add_comment(text)
143
+ raise "Not in fiscal session" unless @fiscal_session
144
+ send_comment text
145
+ end
146
+
147
+ def add_payment(type_num = 0, value = nil) # 0, 1, 2, 3
148
+ raise "Not in fiscal session" unless @fiscal_session
149
+ value_bytes = "\x00\x00\x00\x00" # recalculate
150
+ unless value.nil?
151
+ value_units = (value * 100).to_i # !FIXME
152
+ value_bytes = "".b
153
+ 4.times{ |shift| value_bytes.insert 0, ((value_units >> shift*8) & 0xff).chr }
131
154
  end
155
+ fsend Receipt::PRINT_RECEIPT, "" << (9 + type_num).chr << value_bytes
156
+ status = get_printer_status
132
157
  end
133
158
 
134
- def sale_and_pay_items_session(items = [], operator = "1", password = "1")
159
+ def total_payment
160
+ raise "Not in fiscal session" unless @fiscal_session
161
+ add_payment
162
+ end
163
+
164
+ #basket
165
+ def sale_and_pay_items_session(items = [], operator = '', password = '')
135
166
  device.session("Fiscal Doc") do |s|
136
167
  s.notify "Open Fiscal Receipt"
137
- s.open_receipt
168
+ s.open_fiscal_doc operator, password
138
169
  s.notify "Register Sale"
139
170
  items.each do |item|
140
- s.send_plu build_sale_data(item[:price], item[:text1], nil, item[:tax_group], item[:qty], nil, nil, item[:number])
141
- s.send_comment(item[:text2]) unless item[:text2].blank?
171
+ s.add_sale(item)
142
172
  end
143
173
  s.notify "Register Payment"
144
- s.send_payment
174
+ s.total_payment
145
175
  s.notify "Close Fiscal Receipt"
146
- s.close_receipt
176
+ s.close_fiscal_doc
147
177
  s.notify "Fiscalization Completed!"
148
178
  end
149
179
  end
150
180
 
151
- def z_report_session
152
- device.session("Z Report") do |s|
153
- s.notify "Z Report Start"
154
- s.fsend Reports::DAILY_REPORT, FLAG_TRUE
155
- status = s.get_printer_status
156
- s.notify "Z Report End"
157
- end
158
- end
159
-
160
- def x_report_session
161
- device.session("Z Report") do |s|
162
- s.notify "X Report Start"
163
- s.fsend Reports::DAILY_REPORT, FLAG_FALSE
164
- status = s.get_printer_status
165
- s.notify "X Report End"
166
- end
167
- end
168
-
169
- def cancel_doc_session
170
- device.session("Doc cancel") do |s|
171
- s.notify "Doc Cancel Start"
172
- # cancel old one by open/close new one
173
- s.open_receipt
174
- s.close_receipt
175
- s.notify "Doc Cancel End"
176
- end
177
- end
178
-
179
- def check_ready!
180
- fsend Info::GET_STATUS
181
- raise errors.full_messages.join(", ") if errors.any?
182
- end
183
-
184
181
  def get_printer_status
185
182
  PrinterStatus.new(fsend(Info::GET_PRINTER_STATUS))
186
183
  end
@@ -254,15 +251,58 @@ module Extface
254
251
  end
255
252
  end
256
253
 
257
- def check_sum(buffer)
258
- sum = 0
259
- buffer.each_byte do |byte|
260
- sum -= byte
261
- end
262
- sum & 0xff
263
- end
264
-
265
254
  private
255
+ def open_receipt(variant = nil)
256
+ fsend Receipt::OPEN_RECEIPT
257
+ unless variant.blank?
258
+ fsend Receipt::PRINT_RECEIPT, variant
259
+ end
260
+ status = get_printer_status
261
+ end
262
+
263
+ def close_receipt
264
+ fsend Receipt::CLOSE_RECEIPT
265
+ status = get_printer_status
266
+ end
267
+
268
+ def send_comment(text)
269
+ fsend Receipt::PRINT_RECEIPT, Receipt::Variant::COMMENT + text
270
+ status = get_printer_status
271
+ end
272
+
273
+ def send_plu(plu_data)
274
+ fsend Receipt::PRINT_RECEIPT, Receipt::Variant::PLU + plu_data
275
+ status = get_printer_status
276
+ end
277
+
278
+ #def build_sale_data(price, text1 = "", text2 = nil, tax_group = 2, qty = 1, percent = nil, neto = nil, number = nil)
279
+ def build_sale_data(sale_item)
280
+ "".b.tap() do |data|
281
+ price_units = (sale_item.price * 100).to_i # !FIXME
282
+ price_bytes = "".b
283
+ 4.times{ |shift| price_bytes.insert 0, ((price_units >> shift*8) & 0xff).chr }
284
+ data << price_bytes
285
+ qty_units = ((sale_item.qty || 1) * 1000).to_i # !FIXME
286
+ qty_bytes = "".b
287
+ 4.times{ |shift| qty_bytes.insert 0, ((qty_units >> shift*8) & 0xff).chr }
288
+ data << qty_bytes
289
+ data << "\x00".b #number len FIXME
290
+ data << "\xAA\xAA\xAA\xAA\xAA\xAA".b #number FIXME
291
+ text = sale_item.text1.truncate(20)
292
+ data << text.length.chr
293
+ data << text.ljust(20, " ").b
294
+ data << (sale_item.tax_group || 2).chr
295
+ end
296
+ end
297
+
298
+ def check_sum(buffer)
299
+ sum = 0
300
+ buffer.each_byte do |byte|
301
+ sum -= byte
302
+ end
303
+ sum & 0xff
304
+ end
305
+
266
306
  def sequence_number(increment = true)
267
307
  @seq ||= 0
268
308
  @seq += 1 if increment
@@ -308,7 +348,6 @@ module Extface
308
348
  end
309
349
 
310
350
  def response_code_validation
311
- p "############################### #{cmd.ord.to_s(16)}"
312
351
  case cmd.ord
313
352
  when 0x2c then
314
353
  case data[0] # printer error code
@@ -68,25 +68,14 @@
68
68
 
69
69
  <%= driver_control @device.driver %>
70
70
 
71
- <% if true #@device.print? %>
72
- <%= button_to 'Print Test Page', test_page_device_path(@device), remote: true, name: :test_page, value: true, class: 'btn btn-warning' %>
73
- <% end %>
74
- <% if @device.fiscal? %>
75
- <%= button_to 'Non Fiscal Test', fiscal_device_path(@device), remote: true, name: :non_fiscal_test, value: true, class: 'btn btn-warning' %>
76
- <%= button_to 'Fiscal Test', fiscal_device_path(@device), remote: true, name: :fiscal_test, value: true, class: 'btn btn-warning' %>
77
- <%= button_to 'X Report', fiscal_device_path(@device), remote: true, name: :x_report, value: true, class: 'btn btn-warning' %>
78
- <%= button_to 'Z Report', fiscal_device_path(@device), remote: true, name: :z_report, value: true, class: 'btn btn-warning' %>
79
- <%= button_to 'Cancel Fiscal Doc', fiscal_device_path(@device), remote: true, name: :cancel_fiscal_doc, value: true, class: 'btn btn-warning' %>
80
- <% end %>
81
-
82
- <br />Simulate push data from device
71
+ <!-- <br />Simulate push data from device
83
72
 
84
73
  <div class="input-group">
85
74
  <input type="text" id='data' class="form-control">
86
75
  <span class="input-group-btn">
87
76
  <%= link_to 'Push', extface.push_url(@device.uuid), id: :push, class: 'btn btn-warning'%>
88
77
  </span>
89
- </div><!-- /input-group -->
78
+ </div>-->
90
79
 
91
80
  <h1>Jobs</h1>
92
81
  <table class='table'>
@@ -0,0 +1,8 @@
1
+ <%= button_to 'Non Fiscal Test', fiscal_device_path(@device), remote: true, name: :non_fiscal_test, value: true, class: 'btn btn-warning' %>
2
+ <%= button_to 'Fiscal Test', fiscal_device_path(@device), remote: true, name: :fiscal_test, value: true, class: 'btn btn-warning' %>
3
+
4
+ <%= button_to 'X Report', fiscal_device_path(@device), remote: true, name: :x_report, value: true, class: 'btn btn-warning' %>
5
+ <%= button_to 'Z Report', fiscal_device_path(@device), remote: true, name: :z_report, value: true, class: 'btn btn-warning' %>
6
+
7
+ <%= button_to 'Cancel Fiscal Doc', fiscal_device_path(@device), remote: true, name: :cancel_fiscal_doc, value: true, class: 'btn btn-warning' %>
8
+
@@ -0,0 +1 @@
1
+ <%= button_to 'Print Test Page', test_page_device_path(@device), remote: true, name: :test_page, value: true, class: 'btn btn-warning' %>
@@ -1,3 +1,3 @@
1
1
  module Extface
2
- VERSION = "0.2.4"
2
+ VERSION = "0.2.5"
3
3
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: extface
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.2.4
4
+ version: 0.2.5
5
5
  platform: ruby
6
6
  authors:
7
7
  - Alex Vangelov
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2014-06-14 00:00:00.000000000 Z
11
+ date: 2014-06-15 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rails
@@ -96,6 +96,7 @@ files:
96
96
  - app/helpers/extface/sse_helper.rb
97
97
  - app/models/extface/device.rb
98
98
  - app/models/extface/driver.rb
99
+ - app/models/extface/driver/base/fiscal.rb
99
100
  - app/models/extface/driver/daisy/commands_fx1200.rb
100
101
  - app/models/extface/driver/daisy_fx1200.rb
101
102
  - app/models/extface/driver/eltrade/commands_fp4.rb
@@ -109,15 +110,15 @@ files:
109
110
  - app/views/extface/devices/form.html.erb
110
111
  - app/views/extface/devices/index.html.erb
111
112
  - app/views/extface/devices/show.html.erb
112
- - app/views/extface/driver/daisy_fx1200/_control.html.erb
113
+ - app/views/extface/driver/_control_fiscal.html.erb
114
+ - app/views/extface/driver/_control_print.html.erb
115
+ - app/views/extface/driver/_control_raw.html.erb
116
+ - app/views/extface/driver/_control_report.html.erb
113
117
  - app/views/extface/driver/daisy_fx1200/_settings.html.erb
114
- - app/views/extface/driver/eltrade_tm_u220/_control.html.erb
118
+ - app/views/extface/driver/eltrade_tm_u220/_control_.html.erb
115
119
  - app/views/extface/driver/eltrade_tm_u220/_settings.html.erb
116
- - app/views/extface/driver/generic_pos/_control.html.erb
117
120
  - app/views/extface/driver/generic_pos/_settings.html.erb
118
- - app/views/extface/driver/star_scp700/_control.html.erb
119
121
  - app/views/extface/driver/star_scp700/_settings.html.erb
120
- - app/views/extface/driver/star_tsp200/_control.html.erb
121
122
  - app/views/extface/driver/star_tsp200/_settings.html.erb
122
123
  - app/views/extface/jobs/_form.html.erb
123
124
  - app/views/extface/jobs/edit.html.erb
@@ -1 +0,0 @@
1
- <%= __FILE__.gsub(Rails.root.to_s, "") %>
@@ -1 +0,0 @@
1
- <%= __FILE__.gsub(Rails.root.to_s, "") %>