Application Level ================= The Application Level regroups the features that are required for the application to operate in an optimum way. One piece of information that is useful, especially in case of an anomaly, is to retrieve the version of Capture and the version of the Scanner connected to the host. In the event multiple scanners are used on a single device, there is then a way to identify them by assigning a friendly name. Also in the case of contactless reader/writer, that uses Bluetooth Low Energy (BLE) to connect to the host and in the event the deployment has multiple contactless reader/writer, it is possible to discover them and let the user picking the appropriate one. Another useful feature is the scenario where the host computer is out of range from where the scan happens, and to confirm the barcode was actually received by the application. Display the Capture Version ^^^^^^^^^^^^^^^^^^^^^^^^^^^ This feature is useful when an issue arises in a deployment in order to help identify the version of Capture SDK actually in use. Here is a sample of code for retrieving the Capture Version:: // retrieve the version of Capture SKTCaptureHelper* capture = [SKTCaptureHelper sharedInstance]; [capture getVersionWithCompletionHandler:^(SKTResult result, SKTCaptureVersion *version) { dispatch_async(dispatch_get_main_queue(), ^{ if(result == SKTCaptureE_NOERROR){ NSString* versionStr = [NSString stringWithFormat:@"Version: %ld.%ld.%ld.%ld", version.Major, version.Middle, version.Minor, version.Build]; self.infoTextView.text = versionStr; } }); }]; .. note:: The completion handler of this ``getVersionWithCompletionHandler`` is updating the UI, this could be done only in the main UI thread context. This is accomplished by using the code: ``dispatch_async(dispatch_get_main_queue(), ^{...});`` In this sample code, ``capture`` is set to ``[CaptureHelper shareInstance]``. Here is an example for getting the device version:: [device getFirmwareVersionWithCompletionHandler:^(SKTResult result, SKTCaptureVersion *version) { dispatch_async(dispatch_get_main_queue(), ^{ if(result == SKTCaptureE_NOERROR){ NSString* versionStr = [NSString stringWithFormat:@"Version: %ld.%ld.%ld.%ld", version.Major, version.Middle, version.Minor, version.Build]; self.infoTextView.text = versionStr; } }); }]; .. note:: The completion handler of this ``getFirmwareVersionWithCompletionHandler`` is updating the UI, this could be done only in the main UI thread context. This is accomplished by using the code: ``dispatch_async(dispatch_get_main_queue(), ^{...});`` In this example, ``device`` is an instance of a ``CaptureHelperDevice`` that could be initialized in the ``didNotifyArrivalForDevice`` delegate. Give a Friendly Name to a Scanner ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ In a deployment where multiple scanners are present, it is helpful to identify them with a friendly name that makes sense (e.g. ''Register1Scanner''). Here is a sample code to change the friendly name:: NSString* friendlyName = @"Register1Scanner"; [device setFriendlyName:friendlyName completionHandler:^(SKTResult result) { NSLog(@"Setting Friendly Name returns: %ld", (long)result); }]; Here ``device`` is a ``CaptureHelperDevice`` instance. Contactless Reader/Writer Discovery And Selection ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Please refer to :ref:`Contactless Reader/Writer discovery`. .. _dataconfirmationappobjclabel: Data confirmation from the Application ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ For some deployments where the user might be unable to see the screen of the host when scanning a barcode, there is a way to have the application confirm receipt of the barcode. In this case the trigger button will be disabled until the application confirms the decoded data or until the trigger lock out timer elapses. First, Capture needs to be configured with Data Confirmation Mode set to ''App''. This mode is persistent in Capture. If a scanner is connected then it will be configured to App mode as well at this time, otherwise, when a scanner connects it will be automatically configured to App mode during the connection process. The following example shows how to set the confirmation to the application:: SKTCaptureHelper* capture = [SKTCaptureHelper sharedInstance]; [capture setConfirmationMode:SKTCaptureDataConfirmationModeApp completionHandler:^(SKTResult result) { NSLog(@"Confirmation set to App returns: %ld", (long)result); }]; If the Data Confirmation Mode is configured to ''App'', then the application is responsible for acknowledging the decoded data to the scanner. Here is example code showing how an application can acknowledge the decoded data:: -(void)didReceiveDecodedData:(SKTCaptureDecodedData*) decodedData fromDevice:(SKTCaptureHelperDevice*) device withResult:(SKTResult) result{ NSLog(@"receive decoded data: %@", [decodedData stringFromDecodedData]); dispatch_async(dispatch_get_main_queue(), ^{ self.decodedDataTextView.text = [self.decodedDataTextView.text stringByAppendingString: [decodedData stringFromDecodedData]]; self.decodedDataTextView.text = [self.decodedDataTextView.text stringByAppendingString: @"\n"]; }); [device setDataConfirmationWithLed:SKTCaptureDataConfirmationLedGreen withBeep:SKTCaptureDataConfirmationBeepGood withRumble:SKTCaptureDataConfirmationRumbleGood completionHandler:^(SKTResult result) { NSLog(@"Data Confirmation returns: %ld", (long)result); }]; } .. note:: The Data Confirmation Mode set to ''App'' is the slowest way of scanning barcodes. Another way to handle cases where the barcode might be incorrect, is to have the application sending a Bad Beep, Bad Rumble and Red LED to the scanner and disabling the trigger button until the user acknowledges a message on the host screen explaining the issue. Please refer to :ref:`Wrong Barcode Indication ` and :ref:`Disabling the Scanner Trigger Button `