SDK reference · iOS SDK / iOS Individual Modules

ID Capture

The ID Capture module captures the front and back of a government-issued ID, with auto-capture and quality checks, and produces clean images for processing. It is the entry point for most identity-capture flows.

For an overview of this module and how it works, see ID Capture.

How you use this module depends on your integration pattern. When the app defines the steps in code, you add the module to an IncdOnboardingFlowConfiguration as shown below; when the flow is defined in Dashboard, you reference it by session token and let the back end drive the steps. See Integration Approaches.

Availability: All variants.

Add ID Capture

  1. Add the module with addIdScan().
    flowConfig.addIdScan(
        idType: nil,                              // .id or .passport; nil shows the chooser
        scanStep: .both,                          // .front / .back / .both
        idCategory: .primary,                     // .primary or .secondary
        showTutorials: true,
        showRetakeScreenForManualCapture: nil,
        showRetakeScreenForAutoCapture: nil,
        autocaptureUxMode: nil,                   // .countdown or .holdStill(duration:)
        showIDOverlay: nil,
        streamFrames: nil,
        initialOrientation: nil,
        enableAudioStream: nil,
        showIdTypeChooser: nil,
        digitalIdsUpload: false,
        motion: false                             // collect motion data + run local motion-behavior calc
    )
    
  2. Add ID OCR/Process after ID Capture. ID Capture captures the document images, and processing then runs validation and OCR on what was captured. When scanStep == .both, processing runs automatically afterward.

Configuration Options

Configure the module with addIdScan().

Option Type Description
idType IdType? Sets the type of document: .id or .passport. nil lets the user select.
scanStep ScanStep Selects which sides are captured: .front, .back, or .both. Default: .both.
idCategory IDCategory .primary or .secondary.
showTutorials Bool? Shows the tutorial screen that explains how to scan an ID.
showIdTypeChooser Bool? Shows or hides the document type selector.
showRetakeScreenForAutoCapture Bool? Controls whether the review/retake screen appears after auto-capture.
showRetakeScreenForManualCapture Bool? Controls whether the review/retake screen appears after manual capture.
autocaptureUxMode AutocaptureUxMode? Specifies auto-capture behavior: .countdown or .holdStill(duration:).
showIDOverlay Bool? Shows a visual overlay/frame guide on the camera preview to help the user align the ID within the capture area. Does not impact UI v2. Default: false.
streamFrames Bool? Turns on frame streaming during capture. Only applies for the Video Conference (-vc) variant.
initialOrientation IDOrientation? Sets the orientation of the on-screen ID template: .vertical or .horizontal. Does not impact device rotation.
enableAudioStream Bool? Enables audio capture alongside the video/image stream during scanning. Only applies if streamFrames is true.
digitalIdsUpload Bool? Allows uploading an existing digital ID (PDF).
motion Bool Enables motion data collection and local motion-behavior calculation for the capture. Default: false.

ID Capture ships both a v1 (legacy) and a v2 (smart-capture) screen. The one that runs is not controlled by an addIdScan parameter; the SDK selects it automatically based on a remote UX experiment and, for the v2 US smart-capture back-scan path, the active flow's Workflow configuration in Dashboard. Neither condition is directly settable by the integrating app.

There is also a non-UI variant for headless capture: addIdScanNonUI(scanStep:idCategory:streamFrames:enableAudioStream:).

The overload taking showRetakeScreen, showAutoCaptureRetakeScreen, and enableRotationOnRetakeScreen is deprecated. Use the renamed parameters shown above for showRetakeScreen (showRetakeScreenForManualCapture) and showAutoCaptureRetakeScreen (showRetakeScreenForAutoCapture). enableRotationOnRetakeScreen has no replacement; it was removed instead of renamed, and is retained in the deprecated overload only as an unused parameter.

Result

ID Capture reports through the IncdOnboardingDelegate callbacks, with one pair per captured side plus the lifecycle and per-attempt variants:

func onIdFrontStarted(_ controller: any IDCaptureController)
func onIdFrontCompleted(_ result: IdScanResult)
func onIdFrontAttemptCompleted(_ result: IdScanResult)
func onIdBackStarted(_ controller: any IDCaptureController)
func onIdBackCompleted(_ result: IdScanResult)
func onIdBackAttemptCompleted(_ result: IdScanResult)

onIdFrontCompleted(_:) and onIdBackCompleted(_:) each deliver an IdScanResult for that side. Check error first: a non-nil value indicates a fatal, pre-upload failure (for example, the scan never reached the server) and takes precedence over the other fields. Otherwise, treat scanStatus as the authoritative validation outcome for the capture. failReason provides supplementary detail and is not derived from scanStatus. Both are independently reported from the same upload response.

IdScanResult fields:

  • image: The captured ID or passport image.
  • base64Image: The Base64-encoded string of the captured image.
  • encryptedBase64Image: The encrypted Base64-encoded image, when encryption is enabled.
  • croppedFace: The face photo cropped from the ID; nil when no face can be extracted.
  • chosenIdType: The document type the user chose (IdType).
  • classifiedIdType: The document type returned by the server.
  • idCategory: Whether the document is a primary or secondary identification document (IDCategory: .primary or .secondary).
  • scanStatus: The scan outcome; an IncdIdScanStatus: unknown, ok, errorClassification, errorGlare, errorSharpness, errorReadability, errorInCapture, errorUnacceptableID, or wrongSide.
  • failReason: The reason the scan failed; nil when the scan succeeds.
  • issueName: The legal name on the document.
  • issueYear: The year the document was issued.
  • countryCode: The country code of the document's issuing country.
  • allAttemptsExhausted: true if all retry attempts are used up. This reflects the current side, front or back, independently.
  • metadata: The proprietary capture metadata required by the SDK; populated only in Capture-Only mode.
  • idealCaptureEnvironmentTestResult: The result of the ideal-capture-environment test.
  • deviceStats: A DeviceStats snapshot of the device state when the result was produced. Its motionStatus (MotionStatus) reports device motion during capture. MotionStatus is a CustomStringConvertible enum (not a string-backed/RawRepresentable enum) with three cases; its description, and the value serialized to the wire, is the uppercase string shown in parentheses:
    • .unclear"UNCLEAR": Motion could not be determined; this is the fallback used when no motion result is available.
    • .pass"PASS": Device motion was within acceptable limits.
    • .fail"FAIL": Excessive device motion was detected.
  • error: An IncdIdScanError when the capture failed; otherwise, nil.

Errors also surface through IncdOnboardingDelegate.onError(_:). There is no ID-Capture-specific delegate error callback beyond the per-result error field.

Errors

IncdIdScanError cases:

  • error
  • cameraSetupFailed
  • permissionsDenied
  • fakePermissionsDenied
  • skipped
  • streamAudioPermissionsDenied

Was this page helpful?