1. Vision SDK
  2. iOS

Vision SDK

iOS

Barcode and QR Code scanner framework for iOS. VisionSDK provides a way to detect barcodes and qr codes. It also provides the functionality for information extraction from different kind of logistic labels like shipping labels, inventory labels, bill of ladings, receipts & invoices

Development Requirements

  • iOS 13.0+
  • Swift: 5.4.2+
  • Xcode Version: 13.0+

Installation

CocoaPods

CocoaPods is a dependency manager for Cocoa projects. For usage and installation instructions, visit their website. To integrate VisionSDK into your Xcode project using CocoaPods, specify it in your Podfile:

        pod 'VisionSDK'

      

Usage

Update Info.plist

Add Privacy - Camera Usage Description to Info.plist file

PermissionSettings

Initialization

In order to use the OCR API for information extraction, you have to set following parameters

  • Constants.apiKey to your API key.
  • Constants.apiEnvironment you also need to specify the API environment that you have the API key for (sandbox or production).
NOTE

Please note that these have to be set before using the API call. You can generate your own API key at cloud.packagex.io. You can find the instruction guide here.

        Constants.apiKey = "your_api_key"
Constants.apiEnvironment = .production

      

Code Samples

You can find the sample code for using the vision-sdk on our github.

Functional Description

Configuration Method

        scannerView.configure(delegate: VisionSDK.CodeScannerViewDelegate, input: VisionSDK.CodeScannerView.Input = .default, scanMode: VisionSDK.CodeScannerMode = .qrCode)


      

Parameters

  • delegate
    This class should conform to the CodeScannerViewDelegate protocol.

Input struct
Input struct defines the properties of scanner view. These properties are:

  • FocusSettings
    The FocusSettings struct defines the focus-related properties of the scanner view. These properties include:

    • focusImage: UIImage?
      The image will be displayed at the center of the view. If no image is provided, VisionSDK will use the default image. Please note that the focus rectangle frame may vary depending on the scan mode.

    • focusImageRect: CGRect
      You can provide a custom rectangle for the focus image. Specify your preferred rectangle, or use .zero to apply the default settings. Note that the default focus rectangle frame may vary depending on the scan mode.

    • shouldDisplayFocusImage: Bool
      set true if you need focused region to be drawn.

    • shouldScanInFocusImageRect: Bool
      set true if you want to detect codes visible in focused region only. This will discard the codes detected to be outside of the focus image.

    • showCodeBoundariesInMultipleScan: Bool
      set true if you want to display boundaries around detected codes in multiple code scan. Default value is 'true'

    • validCodeBoundryBorderColor: UIColor
      Color of border drawn around detected valid code. Default value is .green

    • validCodeBoundryBorderWidth: CGFloat
      Width of border drawn around detected valid code. Default value is 1.0

    • validCodeBoundryFillColor: UIColor
      Fill color of border drawn around detected valid code. Default value is .green.withAlphaComponent(0.3)

    • inValidCodeBoundryBorderColor: UIColor
      Color of border drawn around detected invalid code. Default value is .red

    • inValidCodeBoundryBorderWidth: CGFloat
      Width of border drawn around detected invalid code. Default value is 1.0

    • inValidCodeBoundryFillColor: UIColor
      Fill color of border drawn around detected invalid code. Default value is .red.withAlphaComponent(0.3)

    • showDocumentBoundries: Bool
      Set true if you want to display boundaries around document detected in camera view.

    • documentBoundryBorderColor: UIColor
      Set the border color of boundaries drawn around detected document in camera stream.

    • documentBoundryFillColor: UIColor
      Set the fill color of boundaries drawn around detected document in camera stream.

    • focusImageTintColor: UIColor
      Set the color you want the focus image to be displayed in when no code is detected.

    • focusImageHighlightedColor: UIColor
      Set the color you want the focus image to be displayed in when code is detected.

  • ObjectDetectionConfiguration
    ObjectDetectionConfiguration struct defines the object detection properties of scanner view. These properties are:

    • isTextIndicationOn: Bool
      Set false if you do not want to detect text in live camera feed. If set false codeScannerViewDidDetect(_ text: Bool, barCode: Bool, qrCode: Bool, document: Bool) method will send text parameter as false.



    • isBarCodeOrQRCodeIndicationOn: Bool
      Set false if you do not want to detect barcode or QR codes in live camera feed. Using this proerty my be helpful in cases if you want to perform manual capture based on code detection.

    • isDocumentIndicationOn: Bool
      Set false if you do not want to detect document in live camera feed.



    • codeDetectionConfidence: Float
      You can set the minimum confidence level for codes detected. Those below the given value will be discarded. Value must be set on the scale of 0 - 1. Default is 0.5.

    • documentDetectionConfidence: Float
      You can set the minimum confidence level for document detection. Those below the given value will be discarded. Value must be set on the scale of 0 - 1. Default is 0.9.

    • secondsToWaitBeforeDocumentCapture: Double
      Time threshold to wait before capturing a document automatically in OCR mode. VisionSDK only captures the document if it is continuously detected for the n(value of this property) seconds. Default is 3.0.

    • selectedTemplateId: String?
      Set this value using the template id if you want to detect multiple codes using a specific template. To use a specific template, set the captureType to .multiple as well.



  • CameraSettings
    CameraSettings struct defines the camera related properties of scanner view. These properties are:

    • sessionPreset: Session.Preset
      You can set session preset as per your requirement. Default is .high.



    • nthFrameToProcess: Int
      This is the nth number of the frame that is processed for detection of text, barcodes, and qrcodes in live camera feed if enabled by isTextIndicationOn or isBarCodeOrQRCodeIndicationOn. Processing every single frame may be costly in terms of CPU usage and battery consumption. Default value is 10 which means that from camera stream of usual 30 fps, every 10 frame is processed. Its value should be set between 1 - 30.



    • shouldAutoSaveCapturedImage: Bool
      Set true if you want captured image to be saved and get its URL. Upon true func codeScannerView(_ scannerView: VisionSDK.CodeScannerView, didCaptureOCRImage image: UIImage, withCroppedImge croppedImage: UIImage?, withbarCodes barcodes: [String], savedImageURL: URL?) will respond with URL of the saved image as well. To clear stored images, you can use CodeScannerView.removeAllSavedImages() instance method.

  • PriceTagDetectionSettings
    PriceTagDetectionSettings struct defines the price tag related properties of scanner view. These properties are:

    • shouldDisplayOnScreenIndicators: Bool
      Set true if you want to display price tag verification indicators on screen after detection.



    • validTagImage: UIImage
      Set the image you want to be displayed on camera stream when a price tag has been detected and verified as valid.



    • invalidTagImage: UIImage
      Set the image you want to be displayed on camera stream when a price tag has been detected and is invalid.

  • captureMode
    Defines whether the VisionSDK should capture codes automatically or not. If you want to capture code on user action, then set it to .manual. Default value is .auto. If otherwise, you will have to manually trigger scanning using capturePhoto() method.

  • captureType
    Set it to .multiple if you want to allow multiple results from scan. In .manual case, you will have to manually trigger scanning using capturePhoto() method.

  • scanMode
    Defines the scan mode. It has following options

    • .barCode
      Detects barcodes only in this mode
    • .qrCode
      Detects qr codes only in this mode
    • .autoBarCodeOrQRCode
      Detects both bar codes and qr codes
    • .ocr
      Use this mode to capture photos for later user in OCR API call.
    • .photo
      Use this mode to capture regular photos without the need for OCR
    • .priceTag
      Use this mode for scanning price tags. This mode is only available for authenticated users.

Set Scan Mode

  • Sets the scan mode to desired mode. i.e
    • .barCode
    • .qrcode
    • .ocr
    • .autoBarCodeOrQRCode
        scannerView.setScanModeTo(_ mode: VisionSDK.CodeScannerMode)

      

Set Capture Mode

  • Sets the capture mode to desired mode. i.e
    • .manual
    • .auto
        scannerView.setCaptureModeTo(_ mode: VisionSDK.CaptureMode)

      

Set Capture Type

  • Sets the capture type to desired type.
        scannerView.setCaptureTypeTo(_ type: VisionSDK.CaptureType)

      

Start the scanning

  • Needs configure() method to be called before it. It starts the camera session and scanning.
        scannerView.startRunning()

      

Stop the scanning

  • Stops camera session and scanning.
        scannerView.stopRunning()

      

Rerstart the camera & scanning

  • Use this function to resume scanning
        scannerView.rescan()

      

Deconfigure the configurations

  • Removes all the configurations of scannerView and stops scanning.
        scannerView.deConfigure()

      

Capture the photo/image

  • Use this method to trigger code scan or photo capture when you are scanning for multiple codes, in manual capture or OCR mode.
        scannerView.capturePhoto()

      

Delegate Methods / Callbacks

  • This method returns with the codes scanned after successful scan
        func codeScannerView(_ scannerView: VisionSDK.CodeScannerView, didSuccess codes: [String])

      
  • This method is called when text, barcode or qr code is detected in the camera stream. Values depend on whether text or code indication is enabled while configuring the scanner view.
        func codeScannerViewDidDetect(_ text: Bool, barCode: Bool, qrCode: Bool)

      
  • This method is called when capturePhoto() method is called in OCR Mode. It return with the captured image and all the detected codes in it.
        func codeScannerView(_ scannerView: VisionSDK.CodeScannerView, didCaptureOCRImage image: UIImage, with barcodes barcodes: [String])

      
  • This method is called when an error occurs in any stage of initializing or capturing the codes when there is none detected.
        func codeScannerView(_ scannerView: VisionSDK.CodeScannerView, didFailure error: VisionSDK.CodeScannerError)

      

Custom Template Scanning Methods

In order to use custom templates for code scanning. It is necessary to create a template first. You can create templates using the following code

        
    func openTemplateController() {
    
        let scanController = GenerateTemplateController.instantiate()
        scanController.delegate = self
        
        if let sheet = scanController.sheetPresentationController {
            sheet.prefersGrabberVisible = true
        }
        
        self.present(scanController, animated: true)
    }
    

      

Listen to the GenerateTemplateControllerDelegate methods to get response.

        
    extension BarcodeViewController: GenerateTemplateControllerDelegate {
    
        // This function provides you with the ID of the template that has been created
        func templateScanController(_ controller: GenerateTemplateController, didFinishWith result: String) {
            print(result)
        }
    
        func templateScanController(_ controller: GenerateTemplateController, didFailWithError error: any Error) {
            controller.dismiss(animated: true)
        }
    
        func templateScanControllerDidCancel(_ controller: GenerateTemplateController) {
            print("Template creation cancelled")
        }
    }
    

      

NOTE: VisionSDK automatically saves created templates into its secure storage. You can access those saved template using methods below

            
    // This method returns all the ids of the saved templates
    CodeScannerView.getAllTemplates()

    // This method deletes the template with the specified ID
    CodeScannerView.deleteTemplateWithId(_ id: String)
    
    // This method deletes all saved templates
    CodeScannerView.deleteAllTemplates()
    

      

On-Device OCR Methods

This method must be called first before using offline device OCR. Preparation should complete first without any errors. For that, listen to completion block in the params.

        
    // This method must be provided with `apiKey` or `token`.
    // modelClass: VSDKModelClass - Select required Model Class. Currently supported is .shippingLabel only
    // modelSize: VSDKModelSize - Select the model size for the above selected Model Class. Currently supported sizes are .micro and .large only.
    
    func prepareOfflineOCR(withApiKey apiKey: String? = nil, andToken token: String? = nil, forModelClass modelClass: VSDKModelClass, withModelSize modelSize: VSDKModelSize = .micro, withProgressTracking progress: ((_ currentProgress: Float, _ totalSize: Float)->())?, withCompletion completion:((_ error: NSError?)->())?)


      

For extraction of data using Offline OCR use the following method.

        
    func extractDataFromImage(_ image: CIImage, withBarcodes barcodes: [String], _ completion: @escaping ((Data?, NSError?) -> Void))


      

It returns with the OCR Response based on PackageX Platform API Response.

These methods are called on the shared instance of OnDeviceOCRManager. It can be accessed using OnDeviceOCRManager.shared syntax.

OCR Methods

        
func checkPriceTagAuthenticationWithKey(_ apiKey: String?, _ completion: @escaping ((_ error: NSError?) -> Void))

func callScanAPIWith(_ image: UIImage, andBarcodes barcodes: [String], andApiKey apiKey: String? = nil, andToken token: String? = nil, andLocationId locationId: String? = nil, andOptions options: [String: String], withImageResizing shouldResizeImage: Bool = true, _ completion: @escaping ((_ data: Data?, _ response: URLResponse?, _ error: NSError?)-> Void))

func callManifestAPIWith(_ image: UIImage, andBarcodes barcodes: [String], andApiKey apiKey: String? = nil, withImageResizing shouldResizeImage: Bool = true, _ completion: @escaping ((_ data: Data?, _ response: URLResponse?, _ error: NSError?) -> Void))


      

These methods are called on the shared instance of VisionAPIManager. It can be accessed using VisionAPIManager.shared syntax.

To use price tag scanning, you need to authenticate first using checkPriceTagAuthenticationWithKey method. Upon successful completion block calling without error, you can use price tag mode of scanner view.

callScanAPIWith method receives the captured image and the API Key or AuthToken as parameters. It returns with the OCR Response from PackageX Platform API Response.

callManifestAPIWith method receives the captured image and the API Key as parameters.

Error Handling

Please ensure that error cases are handled appropriately. The provided error cases can be used as a reference to track any errors that may occur. Keep in mind that some errors might be related to functionality you're not using, so you might not encounter those specific issues.

        public enum CodeScannerError: Int {
    case cameraUsageNotAuthorized = 0
    case noTextDetected = 1
    case noBarCodeDetected = 2
    case noQRCodeDetected = 3
    case noBarCodeORQRCodeDetected = 4
    case noDocumentDetected = 5
    case readFailure = 6
    case unknowns = 7
    case videoUnavailable = 8
    case inputInvalid = 9
    case metadataOutputFailure = 10
    case videoDataOutputFailure = 11
    case authenticationNeededForPriceTagScanning = 12
    case priceTagDelegateNotImplemented = 13
    case templateNotFound = 14
    case noTemplateCodesFound = 15
}

      

Report an issue

VisionSDK contains internal error reporting mechanism if it faces any issue. Furthermore, if you get a response from On-Device models, that you consider to be incorrect, then you can report it using the following function:

        
    // This method must be provided with `apiKey` or `token`.
    // modelClass: VSDKModelClass - Select required Model Class. e.g .shippingLabel
    // modelSize: VSDKModelSize - Select the model size for the above selected Model Class. e.g. .micro
    // image: CIImage? - Optional captured image
    // reportText: String - Description of issue you are facing
    // response: Data? - Optional response object you received from On-device extraction on the given image

    func reportErrorWith(_ apiKey: String? = nil, andToken token: String? = nil, forModelClass modelClass: VSDKModelClass, withModelSize modelSize: VSDKModelSize = .micro, image: CIImage?, withBarcodes barcodes: [String], reportText: String, response: Data?, withCompletion completion: ((_ response: Int)->())?)

    // Completion block returns an integer indicating response action on reported error. 
    /// 1 = Error reported successfully
    /// 2 = Error saved. Will be automatically posted later by VisionSDK.


      

This method is called on the shared instance of OnDeviceOCRManager. It can be accessed using OnDeviceOCRManager.shared syntax.