Capture a Custom Data Field with iOS

Documentation Menu

This section contains a step-by-step guide to creating an application that captures a single custom data field.

How it Works

With Real-Time Recognition SDK you can create custom data capture profiles for documents that are not supported out-of-the-box. In corresponding result schemes you define custom data fields. (Currently, only one scheme per profile is supported, and only one field may be defined in the scheme). To tell the recognition engine that some text string is a data value (a field value), you will have to specify a regular expression that should match the strings you are looking for. The value may be a date, some code with a known format, and so on: the more specific the data is, the easier it would be to capture it.

This guide uses an alphanumeric code as an example of data that can be captured. Code format is the following: it contains 15 characters that are either digits or capital letters, and the first two characters are always digits. Example: 69KL46D7WF2AR5U.


note Note: Before you begin, see Build your application with the OCR library for iOS.

Implementing the delegates

  1. Implement a delegate conforming to the RTRDataCaptureServiceDelegate protocol. The delegate will handle messages from the data capture service. Here are the recommendations on what its methods should do:
  2. Implement a delegate that adopts the AVCaptureVideoDataOutputSampleBufferDelegate protocol. Instantiate an AVCaptureSession object, add video input and output and set the video output delegate. When the delegate receives a video frame via the captureOutput:didOutputSampleBuffer:fromConnection: method, pass this frame on to the data capture service by calling the addSampleBuffer: method of the RTRDataCaptureService object.
    We recommend using the AVCaptureSessionPreset1280x720 preset for your AVCaptureSession.
    Also note that your video output must be configured to use the kCVPixelFormatType_32BGRA video pixel format.

Loading the library and setting up the service

  1. Create an RTREngine object using the sharedEngineWithLicenseData: method. The method requires an NSData object containing your license data. For example, you can use dataWithContentsOfFile: to create a data object, then pass this object to the sharedEngineWithLicenseData: method.
  2. Use the createDataCaptureServiceWithDelegate:profile: method of the RTREngine object to create a background recognition service. The profile parameter should be left empty.
    Only one instance of the service per application is necessary: multiple threads will be started internally.
  3. Call the configureDataCaptureProfile method of the RTRDataCaptureService object to create an RTRDataCaptureProfileBuilder object. Create a data scheme builder using the addScheme: method. The scheme builder will allow you to specify a human-readable name for the scheme and to add field definitions.
  4. Use the addField: method to create a new field builder. Use setName: to add a human-readable field name and setRegEx: to specify the regular expression that should match the field text. The regEx parameter @"[0-9]{2}[0-9A-Z]{13}" — match 2 digits followed by 13 characters which are digits or capital letters.
  5. note Note: For details on regular expression syntax supported in ABBYY Real-Time Recognition SDK, see the Regular Expressions section.
    An alphanumeric code needs no additional check besides the regular expression. However, there is the option of implementing a block which would perform additional validation after the data has passed the regular expression check, for example, calculate the field's checksum (see the setPredicateBlock: method).

  6. Call the checkAndApply method of the RTRDataCaptureProfileBuilder object to submit the profile for use in the data capture service. If an error is returned at this stage, it is probable the regular expression has mistakes in the syntax, please check it again.
  7. We recommend also calling the setAreaOfInterest: method to specify the rectangular area on the frame where the field is likely to be found. For example, your application may show a highlighted rectangle in the UI into which the end user will try to fit the page they are capturing. The best result is achieved when the area of interest does not touch the boundaries of the frame but has a margin of at least half the size of a typical printed character.


  1. Process the messages sent by the service to the RTRDataCaptureServiceDelegate delegate object. The result will be delivered via the onBufferProcessedWithDataScheme:dataFields:resultStatus: method:
    • An RTRDataScheme object. Its id property should return the same identifier you specified in the custom profile.

    warning Important! If nil is passed instead of a valid RTRDataScheme object, the data scheme has not yet been matched, which may mean that there is no data of the required type in the area of interest. In this case, the results are not usable.

    • An array containing, in this case, one RTRDataField object which represents the extracted field. It provides the identifier and the human-readable name for the field, the field text, and its location.
    • The result stability status, which indicates if the result is available and if it is likely to be improved by adding further frames. Use it to determine whether the application should stop processing and display the result to the user. We do not recommend using the result until the stability level has reached at least RTRResultStabilityAvailableand the data scheme has been matched.
  2. Save the results. Call the stopTasks method to stop processing and clean up image buffers. The data capture service keeps its configuration settings (the custom profile, the area of interest) and necessary resources. The processing will start automatically on the new call to the addSampleBuffer: method.

See the description of classes and methods in the API Reference section.