@iotize/device-com-nfc.cordova 3.3.0 → 3.4.1
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.
- package/bundles/iotize-device-com-nfc.cordova.umd.js +1 -1
- package/bundles/iotize-device-com-nfc.cordova.umd.js.map +1 -1
- package/bundles/iotize-device-com-nfc.cordova.umd.min.js +1 -1
- package/bundles/iotize-device-com-nfc.cordova.umd.min.js.map +1 -1
- package/esm2015/www/cordova-interface.js.map +1 -1
- package/esm2015/www/nfc-com-protocol.js +1 -1
- package/esm2015/www/nfc-com-protocol.js.map +1 -1
- package/fesm2015/iotize-device-com-nfc.cordova.js +1 -1
- package/fesm2015/iotize-device-com-nfc.cordova.js.map +1 -1
- package/package.json +1 -1
- package/plugin.xml +99 -97
- package/src/android/src/com/chariotsolutions/nfc/plugin/NfcPlugin.java +142 -38
- package/src/ios/ISO15Reader.swift +130 -129
- package/src/ios/NFCHelpers.swift +23 -0
- package/src/ios/NFCPlugin-Bridging-Header.h +1 -1
- package/src/ios/NFCTagReader.swift +102 -0
- package/src/ios/NFCTapPlugin.swift +130 -5
- package/www/cordova-interface.d.ts +14 -2
- package/www/phonegap-nfc.js +924 -885
|
@@ -9,77 +9,79 @@
|
|
|
9
9
|
import UIKit
|
|
10
10
|
import CoreNFC
|
|
11
11
|
|
|
12
|
-
|
|
13
|
-
public extension String {
|
|
14
|
-
|
|
15
|
-
func dataFromHexString() -> Data {
|
|
16
|
-
var bytes = [UInt8]()
|
|
17
|
-
for i in 0..<(count/2) {
|
|
18
|
-
let range = index(self.startIndex, offsetBy: 2*i)..<index(self.startIndex, offsetBy: 2*i+2)
|
|
19
|
-
let stringBytes = self[range]
|
|
20
|
-
let byte = strtol((stringBytes as NSString).utf8String, nil, 16)
|
|
21
|
-
bytes.append(UInt8(byte))
|
|
22
|
-
}
|
|
23
|
-
return Data(bytes: UnsafePointer<UInt8>(bytes), count:bytes.count)
|
|
24
|
-
}
|
|
25
|
-
|
|
26
|
-
}
|
|
27
|
-
|
|
28
|
-
extension Data {
|
|
29
|
-
|
|
30
|
-
func hexEncodedString() -> String {
|
|
31
|
-
let format = "%02hhX"
|
|
32
|
-
return map { String(format: format, $0) }.joined()
|
|
33
|
-
}
|
|
34
|
-
}
|
|
35
|
-
|
|
36
12
|
@available(iOS 13.0, *)
|
|
37
|
-
class ST25DVReader :
|
|
38
|
-
|
|
39
|
-
typealias Completion = (Error?) -> ()
|
|
40
|
-
|
|
41
|
-
private var comSession: NFCTagReaderSession?
|
|
42
|
-
private var tag: NFCISO15693Tag?
|
|
43
|
-
|
|
44
|
-
static var MB_CTRL_DYN : UInt8 = 0x0D
|
|
45
|
-
|
|
46
|
-
private var connectionCompleted : Completion?
|
|
13
|
+
class ST25DVReader : NFCTagReader {
|
|
47
14
|
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
static var ISO15693_CUSTOM_ST25DV_CMD_READ_MB_MSG_LENGTH : Int = 0xAB;
|
|
51
|
-
static var ISO15693_CUSTOM_ST25DV_CMD_READ_MB_MSG = 0xAC;
|
|
15
|
+
var iso15Tag: NFCISO15693Tag?
|
|
16
|
+
var detectionRetryCount = 0
|
|
52
17
|
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
static var DELAY : UInt32 = 1000; // timeout resolution in millionths of second
|
|
57
|
-
static var NB_MAX_RETRY : Int = 50;
|
|
58
|
-
|
|
59
|
-
override init() {
|
|
60
|
-
super.init()
|
|
18
|
+
override func invalidateSession( message :String) {
|
|
19
|
+
super.invalidateSession(message: message)
|
|
20
|
+
iso15Tag = nil
|
|
61
21
|
}
|
|
22
|
+
|
|
23
|
+
override func tagReaderSession(_ session: NFCTagReaderSession, didDetect tags: [NFCTag]) {
|
|
62
24
|
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
25
|
+
print( "tagReaderSession:didDectectTag" )
|
|
26
|
+
guard let session = self.comSession else {
|
|
27
|
+
return;
|
|
28
|
+
}
|
|
29
|
+
if tags.count > 1 {
|
|
30
|
+
// Restart polling in 500 milliseconds.
|
|
31
|
+
let retryInterval = DispatchTimeInterval.milliseconds(500)
|
|
32
|
+
session.alertMessage = "More than 1 Tap is detected. Please remove all tags and try again."
|
|
33
|
+
DispatchQueue.global().asyncAfter(deadline: .now() + retryInterval, execute: {
|
|
34
|
+
session.restartPolling()
|
|
35
|
+
})
|
|
67
36
|
return
|
|
68
37
|
}
|
|
69
38
|
|
|
70
|
-
|
|
39
|
+
guard let tag = tags.first else {
|
|
40
|
+
return;
|
|
41
|
+
}
|
|
71
42
|
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
43
|
+
switch tag {
|
|
44
|
+
case .iso15693(let iso15tag):
|
|
45
|
+
self.iso15Tag = iso15tag
|
|
46
|
+
detectionRetryCount = 0
|
|
47
|
+
|
|
48
|
+
// Connect to tag
|
|
49
|
+
|
|
50
|
+
session.connect(to: tag) { [weak self] (error: Error?) in
|
|
51
|
+
guard let strongSelf = self else {
|
|
52
|
+
return;
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
if error != nil {
|
|
56
|
+
let error = NFCReaderError( NFCReaderError.readerTransceiveErrorTagNotConnected )
|
|
57
|
+
strongSelf.invalidateSession( message: error.localizedDescription )
|
|
58
|
+
strongSelf.connectionCompleted?(error)
|
|
59
|
+
return
|
|
60
|
+
}
|
|
61
|
+
print( "connected to tag" )
|
|
62
|
+
strongSelf.tag = tag
|
|
63
|
+
strongSelf.connectionCompleted?(nil)
|
|
64
|
+
iso15tag.readNDEF(completionHandler: {(ndef: NFCNDEFMessage?, error: Error?) in
|
|
65
|
+
if (error != nil) {
|
|
66
|
+
strongSelf.onDiscoverCompletion?(iso15tag.toJSON(), nil)
|
|
67
|
+
}
|
|
68
|
+
})
|
|
69
|
+
strongSelf.onDiscoverCompletion?(iso15tag.toJSON(), nil)
|
|
70
|
+
}
|
|
71
|
+
return
|
|
72
|
+
default:
|
|
73
|
+
detectionRetryCount += 1
|
|
74
|
+
if (detectionRetryCount < 5) {
|
|
75
|
+
usleep(ST25DVReader.DELAY)
|
|
76
|
+
session.restartPolling()
|
|
77
|
+
return
|
|
78
|
+
}
|
|
79
|
+
let error = NFCReaderError( NFCReaderError.ndefReaderSessionErrorTagNotWritable )
|
|
80
|
+
invalidateSession( message: error.localizedDescription )
|
|
81
|
+
connectionCompleted?(error)
|
|
82
|
+
return
|
|
76
83
|
}
|
|
77
84
|
}
|
|
78
|
-
|
|
79
|
-
func invalidateSession( message :String) {
|
|
80
|
-
comSession?.alertMessage = message
|
|
81
|
-
comSession?.invalidate()
|
|
82
|
-
}
|
|
83
85
|
|
|
84
86
|
func send( request: String, completed: @escaping (Data?,Error?)->() ) {
|
|
85
87
|
|
|
@@ -99,7 +101,7 @@ class ST25DVReader : NSObject {
|
|
|
99
101
|
|
|
100
102
|
let requestData : Data = request.dataFromHexString()
|
|
101
103
|
print( "Transceive - \(requestData.hexEncodedString())" )
|
|
102
|
-
|
|
104
|
+
transceiveTap(request: requestData,
|
|
103
105
|
completed: { ( response: Data?, error: Error?) in
|
|
104
106
|
if nil != error {
|
|
105
107
|
self.invalidateSession( message: error?.localizedDescription ?? "Error" )
|
|
@@ -116,76 +118,12 @@ class ST25DVReader : NSObject {
|
|
|
116
118
|
|
|
117
119
|
}
|
|
118
120
|
|
|
119
|
-
@available(iOS 13.0, *)
|
|
120
|
-
extension ST25DVReader : NFCTagReaderSessionDelegate {
|
|
121
|
-
// MARK: - NFCTagReaderSessionDelegate
|
|
122
|
-
func tagReaderSessionDidBecomeActive(_ session: NFCTagReaderSession) {
|
|
123
|
-
// If necessary, you may perform additional operations on session start.
|
|
124
|
-
// At this point RF polling is enabled.
|
|
125
|
-
print( "tagReaderSessionDidBecomeActive" )
|
|
126
|
-
}
|
|
127
|
-
|
|
128
|
-
func tagReaderSession(_ session: NFCTagReaderSession, didInvalidateWithError error: Error) {
|
|
129
|
-
// If necessary, you may handle the error. Note session is no longer valid.
|
|
130
|
-
// You must create a new session to restart RF polling.
|
|
131
|
-
print( "tagReaderSession:didInvalidateWithError - \(error)" )
|
|
132
|
-
connectionCompleted?(error)
|
|
133
|
-
self.comSession = nil
|
|
134
|
-
}
|
|
135
|
-
|
|
136
|
-
func tagReaderSession(_ session: NFCTagReaderSession, didDetect tags: [NFCTag]) {
|
|
137
|
-
print( "tagReaderSession:didDectectTag" )
|
|
138
|
-
guard let session = self.comSession else {
|
|
139
|
-
return;
|
|
140
|
-
}
|
|
141
|
-
if tags.count > 1 {
|
|
142
|
-
// Restart polling in 500 milliseconds.
|
|
143
|
-
let retryInterval = DispatchTimeInterval.milliseconds(500)
|
|
144
|
-
session.alertMessage = "More than 1 Tap is detected. Please remove all tags and try again."
|
|
145
|
-
DispatchQueue.global().asyncAfter(deadline: .now() + retryInterval, execute: {
|
|
146
|
-
session.restartPolling()
|
|
147
|
-
})
|
|
148
|
-
return
|
|
149
|
-
}
|
|
150
|
-
|
|
151
|
-
guard let tag = tags.first else {
|
|
152
|
-
return;
|
|
153
|
-
}
|
|
154
|
-
|
|
155
|
-
switch tag {
|
|
156
|
-
case .iso15693(let iso15tag):
|
|
157
|
-
self.tag = iso15tag
|
|
158
|
-
default:
|
|
159
|
-
let error = NFCReaderError( NFCReaderError.ndefReaderSessionErrorTagNotWritable )
|
|
160
|
-
invalidateSession( message: error.localizedDescription )
|
|
161
|
-
connectionCompleted?(error)
|
|
162
|
-
return;
|
|
163
|
-
}
|
|
164
|
-
|
|
165
|
-
// Connect to tag
|
|
166
|
-
session.connect(to: tag) { [weak self] (error: Error?) in
|
|
167
|
-
guard let strongSelf = self else {
|
|
168
|
-
return;
|
|
169
|
-
}
|
|
170
|
-
|
|
171
|
-
if error != nil {
|
|
172
|
-
let error = NFCReaderError( NFCReaderError.readerTransceiveErrorTagNotConnected )
|
|
173
|
-
strongSelf.invalidateSession( message: error.localizedDescription )
|
|
174
|
-
strongSelf.connectionCompleted?(error)
|
|
175
|
-
return
|
|
176
|
-
}
|
|
177
|
-
print( "connected to tag" )
|
|
178
|
-
strongSelf.connectionCompleted?(nil)
|
|
179
|
-
}
|
|
180
|
-
}
|
|
181
|
-
}
|
|
182
|
-
|
|
183
121
|
@available(iOS 13.0, *)
|
|
184
122
|
extension ST25DVReader {
|
|
185
123
|
|
|
186
124
|
|
|
187
125
|
|
|
188
|
-
func
|
|
126
|
+
func transceiveTap(request: Data, completed: @escaping (Data?, Error?)->()){
|
|
189
127
|
|
|
190
128
|
|
|
191
129
|
checkMBEnabled( completed: { ( error: Error?) in
|
|
@@ -210,7 +148,7 @@ extension ST25DVReader {
|
|
|
210
148
|
}
|
|
211
149
|
|
|
212
150
|
func sendRequest(request: Data, nbTry: Int, completed: @escaping (Data?, Error?)->() ) {
|
|
213
|
-
guard let tag = self.
|
|
151
|
+
guard let tag = self.iso15Tag else {
|
|
214
152
|
let error = NFCReaderError( NFCReaderError.readerTransceiveErrorTagNotConnected )
|
|
215
153
|
invalidateSession( message: error.localizedDescription )
|
|
216
154
|
completed(nil, error )
|
|
@@ -227,6 +165,7 @@ extension ST25DVReader {
|
|
|
227
165
|
var parameters = Data( bytes:[request.count - 1], count: 1 )
|
|
228
166
|
parameters.append(request)
|
|
229
167
|
print( "Send - \(parameters.hexEncodedString())" )
|
|
168
|
+
|
|
230
169
|
tag.customCommand(requestFlags: [.highDataRate],
|
|
231
170
|
customCommandCode: 0xAA,
|
|
232
171
|
customRequestParameters: parameters,
|
|
@@ -244,7 +183,7 @@ extension ST25DVReader {
|
|
|
244
183
|
|
|
245
184
|
func readResponse( nbTry: Int, completed: @escaping (Data?, Error?)->() ) {
|
|
246
185
|
|
|
247
|
-
guard let tag = self.
|
|
186
|
+
guard let tag = self.iso15Tag else {
|
|
248
187
|
let error = NFCReaderError( NFCReaderError.readerTransceiveErrorTagNotConnected )
|
|
249
188
|
invalidateSession( message: error.localizedDescription )
|
|
250
189
|
completed( nil, error )
|
|
@@ -304,7 +243,7 @@ extension ST25DVReader {
|
|
|
304
243
|
}
|
|
305
244
|
|
|
306
245
|
func checkMBEnabled(completed: @escaping (Error?)->()) {
|
|
307
|
-
guard let tag = self.
|
|
246
|
+
guard let tag = self.iso15Tag else {
|
|
308
247
|
let error = NFCReaderError( NFCReaderError.readerTransceiveErrorTagNotConnected )
|
|
309
248
|
invalidateSession( message: error.localizedDescription )
|
|
310
249
|
completed( error )
|
|
@@ -372,5 +311,67 @@ extension ST25DVReader {
|
|
|
372
311
|
|
|
373
312
|
})
|
|
374
313
|
}
|
|
314
|
+
|
|
315
|
+
//full transparent mode
|
|
316
|
+
|
|
317
|
+
@available(iOS 14.0, *)
|
|
318
|
+
func transceiveRaw(request: Data, completed: @escaping (Data?, Error?) -> (), nbTry: Int = NB_MAX_RETRY) {
|
|
319
|
+
guard (request.count >= 2) else {
|
|
320
|
+
completed(nil, NFCReaderError(NFCReaderError.readerErrorInvalidParameterLength))
|
|
321
|
+
return
|
|
322
|
+
}
|
|
323
|
+
let flags = Int(request[0])
|
|
324
|
+
let commandCode = Int(request[1])
|
|
325
|
+
let dataToSend = request.dropFirst(2)
|
|
326
|
+
|
|
327
|
+
print("TRANSCEIVE RAW SEND \(request.hexEncodedString())")
|
|
328
|
+
|
|
329
|
+
guard let tag = self.iso15Tag else {
|
|
330
|
+
completed(nil, NFCReaderError(NFCReaderError.readerTransceiveErrorTagConnectionLost))
|
|
331
|
+
return
|
|
332
|
+
}
|
|
333
|
+
|
|
334
|
+
print("TRANSCEIVE RAW SEND ON ISO15TAG TRY \(nbTry), SESSION READY \(String(describing: comSession?.isReady))")
|
|
335
|
+
|
|
336
|
+
tag.sendRequest(requestFlags: flags, commandCode: commandCode, data: dataToSend, resultHandler: {(result: Result<(NFCISO15693ResponseFlag, Data?), any Error>) in
|
|
337
|
+
|
|
338
|
+
print("SEND_REQUEST_CALLBACK")
|
|
339
|
+
switch result {
|
|
340
|
+
case .success((let flag, let data)):
|
|
341
|
+
let firstByteBuffer = withUnsafeBytes(of: flag.rawValue) { Data($0)}
|
|
342
|
+
var resultData = Data(firstByteBuffer)
|
|
343
|
+
if let nonNilData = data {
|
|
344
|
+
resultData.append(nonNilData)
|
|
345
|
+
}
|
|
346
|
+
print("TRANSCEIVE RAW RETURN \(resultData.hexEncodedString())")
|
|
347
|
+
completed(resultData, nil)
|
|
348
|
+
return
|
|
349
|
+
case .failure(let error):
|
|
350
|
+
print("TRANSCEIVE RAW ERROR \(error.localizedDescription), TRY \(nbTry)")
|
|
351
|
+
if (nbTry >= 0) {
|
|
352
|
+
usleep(ST25DVReader.DELAY)
|
|
353
|
+
return self.transceiveRaw(request: request, completed: completed, nbTry: nbTry - 1)
|
|
354
|
+
}
|
|
355
|
+
completed(nil, error)
|
|
356
|
+
return
|
|
357
|
+
}
|
|
358
|
+
})
|
|
359
|
+
}
|
|
375
360
|
}
|
|
376
361
|
|
|
362
|
+
extension NFCISO15693Tag {
|
|
363
|
+
|
|
364
|
+
func toJSON(ndefMessage: NFCNDEFMessage? = nil) -> [AnyHashable: Any] {
|
|
365
|
+
|
|
366
|
+
let wrapper = NSMutableDictionary()
|
|
367
|
+
wrapper.setValue([UInt8](self.identifier) , forKey: "id")
|
|
368
|
+
|
|
369
|
+
let returnedJSON = NSMutableDictionary()
|
|
370
|
+
returnedJSON.setValue("tag", forKey: "type")
|
|
371
|
+
returnedJSON.setObject(wrapper, forKey: "tag" as NSString)
|
|
372
|
+
|
|
373
|
+
|
|
374
|
+
|
|
375
|
+
return returnedJSON as! [AnyHashable : Any]
|
|
376
|
+
}
|
|
377
|
+
}
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
|
|
2
|
+
public extension String {
|
|
3
|
+
|
|
4
|
+
func dataFromHexString() -> Data {
|
|
5
|
+
var bytes = [UInt8]()
|
|
6
|
+
for i in 0..<(count/2) {
|
|
7
|
+
let range = index(self.startIndex, offsetBy: 2*i)..<index(self.startIndex, offsetBy: 2*i+2)
|
|
8
|
+
let stringBytes = self[range]
|
|
9
|
+
let byte = strtol((stringBytes as NSString).utf8String, nil, 16)
|
|
10
|
+
bytes.append(UInt8(byte))
|
|
11
|
+
}
|
|
12
|
+
return Data(bytes: UnsafePointer<UInt8>(bytes), count:bytes.count)
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
public extension Data {
|
|
18
|
+
|
|
19
|
+
func hexEncodedString() -> String {
|
|
20
|
+
let format = "%02hhX"
|
|
21
|
+
return map { String(format: format, $0) }.joined()
|
|
22
|
+
}
|
|
23
|
+
}
|
|
@@ -0,0 +1,102 @@
|
|
|
1
|
+
import CoreNFC
|
|
2
|
+
|
|
3
|
+
@available(iOS 13.0, *)
|
|
4
|
+
class NFCTagReader : NSObject, NFCTagReaderSessionDelegate {
|
|
5
|
+
|
|
6
|
+
typealias Completion = (Error?) -> ()
|
|
7
|
+
typealias CompletionWithJSONResponse = ([AnyHashable: Any]?, Error?) -> ()
|
|
8
|
+
|
|
9
|
+
internal var comSession: NFCTagReaderSession?
|
|
10
|
+
internal var tag: NFCTag?
|
|
11
|
+
|
|
12
|
+
static var MB_CTRL_DYN : UInt8 = 0x0D
|
|
13
|
+
|
|
14
|
+
internal var connectionCompleted : Completion?
|
|
15
|
+
internal var onDiscoverCompletion : CompletionWithJSONResponse?
|
|
16
|
+
|
|
17
|
+
|
|
18
|
+
static var DELAY : UInt32 = 1000; // timeout resolution in millionths of second
|
|
19
|
+
static var NB_MAX_RETRY : Int = 50;
|
|
20
|
+
|
|
21
|
+
override init() {
|
|
22
|
+
super.init()
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
func initSession( pollingOption: NFCTagReaderSession.PollingOption, alertMessage: String, completed: @escaping (Error?)->() ) {
|
|
26
|
+
return self.initSession(pollingOption: pollingOption, alertMessage: alertMessage, completed: completed, onDiscover: nil)
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
func initSession( pollingOption: NFCTagReaderSession.PollingOption, alertMessage: String, completed: @escaping (Error?)->(), onDiscover: CompletionWithJSONResponse? ) {
|
|
30
|
+
connectionCompleted = completed
|
|
31
|
+
onDiscoverCompletion = onDiscover
|
|
32
|
+
|
|
33
|
+
if NFCNDEFReaderSession.readingAvailable {
|
|
34
|
+
comSession = NFCTagReaderSession(pollingOption: pollingOption, delegate: self, queue: nil)
|
|
35
|
+
comSession?.alertMessage = alertMessage
|
|
36
|
+
comSession?.begin()
|
|
37
|
+
} else {
|
|
38
|
+
completed(NFCReaderError.readerTransceiveErrorSessionInvalidated as? Error)
|
|
39
|
+
}
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
func invalidateSession( message :String) {
|
|
43
|
+
comSession?.alertMessage = message
|
|
44
|
+
comSession?.invalidate()
|
|
45
|
+
tag = nil
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
func tagReaderSessionDidBecomeActive(_ session: NFCTagReaderSession) {
|
|
49
|
+
// If necessary, you may perform additional operations on session start.
|
|
50
|
+
// At this point RF polling is enabled.
|
|
51
|
+
print( "tagReaderSessionDidBecomeActive" )
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
func tagReaderSession(_ session: NFCTagReaderSession, didInvalidateWithError error: Error) {
|
|
55
|
+
// If necessary, you may handle the error. Note session is no longer valid.
|
|
56
|
+
// You must create a new session to restart RF polling.
|
|
57
|
+
print( "tagReaderSession:didInvalidateWithError - \(error)" )
|
|
58
|
+
connectionCompleted?(error)
|
|
59
|
+
self.comSession = nil
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
func tagReaderSession(_ session: NFCTagReaderSession, didDetect tags: [NFCTag]) {
|
|
63
|
+
print( "tagReaderSession:didDectectTag" )
|
|
64
|
+
guard let session = self.comSession else {
|
|
65
|
+
return;
|
|
66
|
+
}
|
|
67
|
+
if tags.count > 1 {
|
|
68
|
+
// Restart polling in 500 milliseconds.
|
|
69
|
+
let retryInterval = DispatchTimeInterval.milliseconds(500)
|
|
70
|
+
session.alertMessage = "More than 1 Tap is detected. Please remove all tags and try again."
|
|
71
|
+
DispatchQueue.global().asyncAfter(deadline: .now() + retryInterval, execute: {
|
|
72
|
+
session.restartPolling()
|
|
73
|
+
})
|
|
74
|
+
return
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
guard let tag = tags.first else {
|
|
78
|
+
return;
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
// Connect to tag
|
|
82
|
+
|
|
83
|
+
session.connect(to: tag) { [weak self] (error: Error?) in
|
|
84
|
+
guard let strongSelf = self else {
|
|
85
|
+
return;
|
|
86
|
+
}
|
|
87
|
+
|
|
88
|
+
if error != nil {
|
|
89
|
+
let error = NFCReaderError( NFCReaderError.readerTransceiveErrorTagNotConnected )
|
|
90
|
+
strongSelf.invalidateSession( message: error.localizedDescription )
|
|
91
|
+
strongSelf.connectionCompleted?(error)
|
|
92
|
+
return
|
|
93
|
+
}
|
|
94
|
+
print( "connected to tag" )
|
|
95
|
+
strongSelf.tag = tag
|
|
96
|
+
strongSelf.connectionCompleted?(nil)
|
|
97
|
+
}
|
|
98
|
+
}
|
|
99
|
+
|
|
100
|
+
|
|
101
|
+
|
|
102
|
+
}
|
|
@@ -57,17 +57,18 @@ import CoreNFC
|
|
|
57
57
|
|
|
58
58
|
@objc(connect:)
|
|
59
59
|
func connect(command: CDVInvokedUrlCommand) {
|
|
60
|
+
print("CONNECT NFC")
|
|
60
61
|
guard #available(iOS 13.0, *) else {
|
|
61
62
|
sendError(command: command, result: "connect is only available on iOS 13+")
|
|
62
63
|
return
|
|
63
64
|
}
|
|
64
65
|
DispatchQueue.main.async {
|
|
65
|
-
print("Begin session \(self.nfcController)")
|
|
66
|
+
print("Begin session \(String(describing: self.nfcController))")
|
|
66
67
|
if self.nfcController == nil {
|
|
67
68
|
self.nfcController = ST25DVReader()
|
|
68
69
|
}
|
|
69
70
|
|
|
70
|
-
(self.nfcController as! ST25DVReader).initSession(alertMessage: "Bring your phone close to the Tap.", completed: {
|
|
71
|
+
(self.nfcController as! ST25DVReader).initSession(pollingOption: [.iso15693], alertMessage: "Bring your phone close to the Tap.", completed: {
|
|
71
72
|
(error: Error?) -> Void in
|
|
72
73
|
|
|
73
74
|
DispatchQueue.main.async {
|
|
@@ -93,13 +94,13 @@ import CoreNFC
|
|
|
93
94
|
return
|
|
94
95
|
}
|
|
95
96
|
|
|
96
|
-
(self.nfcController as!
|
|
97
|
+
(self.nfcController as! NFCTagReader).invalidateSession(message: "Sesssion Ended!")
|
|
97
98
|
self.nfcController = nil
|
|
98
99
|
}
|
|
99
100
|
}
|
|
100
101
|
|
|
101
|
-
@objc(
|
|
102
|
-
func
|
|
102
|
+
@objc(transceiveTap:)
|
|
103
|
+
func transceiveTap(command: CDVInvokedUrlCommand) {
|
|
103
104
|
guard #available(iOS 13.0, *) else {
|
|
104
105
|
sendError(command: command, result: "transceive is only available on iOS 13+")
|
|
105
106
|
return
|
|
@@ -140,6 +141,13 @@ import CoreNFC
|
|
|
140
141
|
})
|
|
141
142
|
}
|
|
142
143
|
}
|
|
144
|
+
|
|
145
|
+
@objc(registerTag:)
|
|
146
|
+
func registerTag(command: CDVInvokedUrlCommand) {
|
|
147
|
+
print("Registered NDEF Listener")
|
|
148
|
+
//isListeningNDEF = true // Flag for the AppDelegate
|
|
149
|
+
sendSuccess(command: command, result: "Tag Listener is on")
|
|
150
|
+
}
|
|
143
151
|
|
|
144
152
|
@objc(registerNdef:)
|
|
145
153
|
func registerNdef(command: CDVInvokedUrlCommand) {
|
|
@@ -248,4 +256,121 @@ import CoreNFC
|
|
|
248
256
|
let enabled = NFCReaderSession.readingAvailable
|
|
249
257
|
sendSuccess(command: command, result: enabled)
|
|
250
258
|
}
|
|
259
|
+
|
|
260
|
+
//full transparent mode
|
|
261
|
+
@objc(transceive:)
|
|
262
|
+
func transceive(command: CDVInvokedUrlCommand) {
|
|
263
|
+
guard #available(iOS 14.0, *) else {
|
|
264
|
+
sendError(command: command, result: "Tranparent transceive is only available in iOS 14+")
|
|
265
|
+
return
|
|
266
|
+
}
|
|
267
|
+
|
|
268
|
+
DispatchQueue.main.async {
|
|
269
|
+
print("sending ...")
|
|
270
|
+
if self.nfcController == nil {
|
|
271
|
+
self.sendError(command: command, result: "no session available")
|
|
272
|
+
return
|
|
273
|
+
}
|
|
274
|
+
|
|
275
|
+
// we need data to send
|
|
276
|
+
if command.arguments.count <= 0 {
|
|
277
|
+
self.sendError(command: command, result: "transceive parameter error")
|
|
278
|
+
return
|
|
279
|
+
}
|
|
280
|
+
|
|
281
|
+
guard let data: Data = command.arguments[0] as? Data else {
|
|
282
|
+
self.sendError(command: command, result: "Tried to transceive empty buffer")
|
|
283
|
+
return
|
|
284
|
+
}
|
|
285
|
+
|
|
286
|
+
(self.nfcController as! ST25DVReader).transceiveRaw(request: data, completed: {
|
|
287
|
+
(response: Data?, error: Error?) -> Void in
|
|
288
|
+
|
|
289
|
+
DispatchQueue.main.async {
|
|
290
|
+
if error != nil {
|
|
291
|
+
self.lastError = error
|
|
292
|
+
self.sendError(command: command, result: error!.localizedDescription)
|
|
293
|
+
} else {
|
|
294
|
+
print("responded \(response!.hexEncodedString())")
|
|
295
|
+
self.sendSuccess(command: command, result: response!.hexEncodedString())
|
|
296
|
+
}
|
|
297
|
+
}
|
|
298
|
+
})
|
|
299
|
+
}
|
|
300
|
+
}
|
|
301
|
+
|
|
302
|
+
@objc(beginSessionFromTech:)
|
|
303
|
+
func beginSessionFromTech(command: CDVInvokedUrlCommand) {
|
|
304
|
+
|
|
305
|
+
// self.nfcController = nil // Clear previous session, if any
|
|
306
|
+
|
|
307
|
+
guard #available(iOS 13.0, *) else {
|
|
308
|
+
sendError(command: command, result: "NFC Tag Session is only available in iOS 13+")
|
|
309
|
+
return
|
|
310
|
+
}
|
|
311
|
+
// we need data to send
|
|
312
|
+
if command.arguments.count <= 0 {
|
|
313
|
+
self.sendError(command: command, result: "beginSessionFromTech parameter error: missing tech")
|
|
314
|
+
return
|
|
315
|
+
}
|
|
316
|
+
|
|
317
|
+
guard let tech = command.argument(at: 0) as? String else {
|
|
318
|
+
self.sendError(command: command, result: "beginSessionFromTech parameter error: improper tech")
|
|
319
|
+
return
|
|
320
|
+
}
|
|
321
|
+
switch tech {
|
|
322
|
+
case "nfcV":
|
|
323
|
+
DispatchQueue.main.async {
|
|
324
|
+
print("Begin session \(String(describing: self.nfcController))")
|
|
325
|
+
if self.nfcController == nil {
|
|
326
|
+
self.nfcController = ST25DVReader()
|
|
327
|
+
}
|
|
328
|
+
|
|
329
|
+
(self.nfcController as! ST25DVReader).initSession(pollingOption: [.iso15693], alertMessage: "Begin nfcV Session.", completed: {
|
|
330
|
+
(error: Error?) -> Void in
|
|
331
|
+
|
|
332
|
+
DispatchQueue.main.async {
|
|
333
|
+
if error != nil {
|
|
334
|
+
print("onBeginSessionFromTech error \(error!.localizedDescription)")
|
|
335
|
+
self.sendError(command: command, result: error!.localizedDescription)
|
|
336
|
+
} else {
|
|
337
|
+
print("onBeginSessionFromTech sucess")
|
|
338
|
+
self.sendSuccess(command: command, result: "nfcV session started")
|
|
339
|
+
}
|
|
340
|
+
}
|
|
341
|
+
}, onDiscover: {(discovered: [AnyHashable: Any]?, error: Error?) -> Void in
|
|
342
|
+
DispatchQueue.main.async {
|
|
343
|
+
if error != nil {
|
|
344
|
+
print("onDiscover error \(error!.localizedDescription)")
|
|
345
|
+
self.sendError(command: command, result: error!.localizedDescription)
|
|
346
|
+
} else if (discovered != nil){
|
|
347
|
+
print("onDiscover success")
|
|
348
|
+
self.sendThroughChannel(jsonDictionary: discovered!)
|
|
349
|
+
}
|
|
350
|
+
}
|
|
351
|
+
})
|
|
352
|
+
}
|
|
353
|
+
return
|
|
354
|
+
default:
|
|
355
|
+
self.sendError(command: command, result: "Unsupported tech \(tech)")
|
|
356
|
+
}
|
|
357
|
+
}
|
|
358
|
+
|
|
359
|
+
@objc(endSession:)
|
|
360
|
+
func endSession(command: CDVInvokedUrlCommand) {
|
|
361
|
+
guard #available(iOS 11.0, *) else {
|
|
362
|
+
sendError(command: command, result: "close is only available on iOS 13+")
|
|
363
|
+
return
|
|
364
|
+
}
|
|
365
|
+
DispatchQueue.main.async {
|
|
366
|
+
guard let session = self.ndefController?.session else {
|
|
367
|
+
self.sendError(command: command, result: "no session to terminate")
|
|
368
|
+
return
|
|
369
|
+
}
|
|
370
|
+
|
|
371
|
+
session.invalidate()
|
|
372
|
+
self.nfcController = nil
|
|
373
|
+
self.sendSuccess(command: command, result: "Session Ended!")
|
|
374
|
+
}
|
|
375
|
+
}
|
|
251
376
|
}
|
|
@@ -9,10 +9,22 @@ export interface CordovaInterface {
|
|
|
9
9
|
/**
|
|
10
10
|
* Connect to current nfc tag
|
|
11
11
|
*/
|
|
12
|
-
connect(tech: string, timeout
|
|
12
|
+
connect(tech: string, timeout?: number): Promise<void>;
|
|
13
13
|
/**
|
|
14
|
-
* Transeive data using
|
|
14
|
+
* Transeive data using Tap NFC communication protocol
|
|
15
|
+
* @param data ArrayBuffer or string of hex data for transcieve
|
|
16
|
+
*/
|
|
17
|
+
transceiveTap(data: ArrayBuffer | string): Promise<string>;
|
|
18
|
+
/**
|
|
19
|
+
* Transeive raw data
|
|
15
20
|
* @param data ArrayBuffer or string of hex data for transcieve
|
|
16
21
|
*/
|
|
17
22
|
transceive(data: ArrayBuffer | string): Promise<string>;
|
|
23
|
+
setTapDeviceDiscoveryEnabled(value: boolean): Promise<void>;
|
|
24
|
+
/**
|
|
25
|
+
* Begins a reading session for the given technology.
|
|
26
|
+
* @param tech String representing the technology of the tap to discover.
|
|
27
|
+
*/
|
|
28
|
+
beginSessionFromTech(tech: string): Promise<void>;
|
|
29
|
+
endSession(): Promise<void>;
|
|
18
30
|
}
|