iOS पर ML Kit की मदद से, इमेज में मौजूद टेक्स्ट की पहचान करें

ML Kit का इस्तेमाल करके, इमेज या वीडियो में मौजूद टेक्स्ट की पहचान की जा सकती है. जैसे, सड़क पर लगे साइन बोर्ड का टेक्स्ट. इस सुविधा की मुख्य बातें ये हैं:

Text Recognition v2 API
ब्यौराइमेज या वीडियो में मौजूद टेक्स्ट को पहचानना. साथ ही, लैटिन, चाइनीज़, देवनागरी, जैपनीज़, और कोरियन स्क्रिप्ट के साथ-साथ कई भाषाओं में काम करता है.
SDK टूल के नामGoogleMLKit/TextRecognition
GoogleMLKit/TextRecognitionChinese
GoogleMLKit/TextRecognitionDevanagari
GoogleMLKit/TextRecognitionJapanese
GoogleMLKit/TextRecognitionKorean
लागू करनाऐसेट को बिल्ड टाइम पर, आपके ऐप्लिकेशन से स्टैटिक तौर पर लिंक किया जाता है
ऐप्लिकेशन के साइज़ पर असरहर स्क्रिप्ट एसडीके के लिए 38 एमबी के बारे में जानकारी
परफ़ॉर्मेंसलैटिन स्क्रिप्ट वाले एसडीके के लिए, ज़्यादातर डिवाइसों पर रीयल-टाइम में काम करता है. हालांकि, अन्य डिवाइसों पर यह सुविधा धीरे काम करती है.

इसे आज़माएं

शुरू करने से पहले

  1. अपने Podfile में, ML Kit के ये पॉड शामिल करें:
    # To recognize Latin script
    pod 'GoogleMLKit/TextRecognition', '8.0.0'
    # To recognize Chinese script
    pod 'GoogleMLKit/TextRecognitionChinese', '8.0.0'
    # To recognize Devanagari script
    pod 'GoogleMLKit/TextRecognitionDevanagari', '8.0.0'
    # To recognize Japanese script
    pod 'GoogleMLKit/TextRecognitionJapanese', '8.0.0'
    # To recognize Korean script
    pod 'GoogleMLKit/TextRecognitionKorean', '8.0.0'
    
  2. अपने प्रोजेक्ट के पॉड इंस्टॉल या अपडेट करने के बाद, Xcode प्रोजेक्ट को उसके .xcworkspace का इस्तेमाल करके खोलें. ML Kit, Xcode के 12.4 या इसके बाद के वर्शन पर काम करता है.

1. TextRecognizer का इंस्टेंस बनाना

TextRecognizer का इंस्टेंस बनाएं. इसके लिए, +textRecognizer(options:) को कॉल करें. साथ ही, एसडीके से जुड़े उन विकल्पों को पास करें जिन्हें आपने ऊपर डिपेंडेंसी के तौर पर घोषित किया है:

Swift

// When using Latin script recognition SDK
let latinOptions = TextRecognizerOptions()
let latinTextRecognizer = TextRecognizer.textRecognizer(options:options)

// When using Chinese script recognition SDK
let chineseOptions = ChineseTextRecognizerOptions()
let chineseTextRecognizer = TextRecognizer.textRecognizer(options:options)

// When using Devanagari script recognition SDK
let devanagariOptions = DevanagariTextRecognizerOptions()
let devanagariTextRecognizer = TextRecognizer.textRecognizer(options:options)

// When using Japanese script recognition SDK
let japaneseOptions = JapaneseTextRecognizerOptions()
let japaneseTextRecognizer = TextRecognizer.textRecognizer(options:options)

// When using Korean script recognition SDK
let koreanOptions = KoreanTextRecognizerOptions()
let koreanTextRecognizer = TextRecognizer.textRecognizer(options:options)

Objective-C

// When using Latin script recognition SDK
MLKTextRecognizerOptions *latinOptions = [[MLKTextRecognizerOptions alloc] init];
MLKTextRecognizer *latinTextRecognizer = [MLKTextRecognizer textRecognizerWithOptions:options];

// When using Chinese script recognition SDK
MLKChineseTextRecognizerOptions *chineseOptions = [[MLKChineseTextRecognizerOptions alloc] init];
MLKTextRecognizer *chineseTextRecognizer = [MLKTextRecognizer textRecognizerWithOptions:options];

// When using Devanagari script recognition SDK
MLKDevanagariTextRecognizerOptions *devanagariOptions = [[MLKDevanagariTextRecognizerOptions alloc] init];
MLKTextRecognizer *devanagariTextRecognizer = [MLKTextRecognizer textRecognizerWithOptions:options];

// When using Japanese script recognition SDK
MLKJapaneseTextRecognizerOptions *japaneseOptions = [[MLKJapaneseTextRecognizerOptions alloc] init];
MLKTextRecognizer *japaneseTextRecognizer = [MLKTextRecognizer textRecognizerWithOptions:options];

// When using Korean script recognition SDK
MLKKoreanTextRecognizerOptions *koreanOptions = [[MLKKoreanTextRecognizerOptions alloc] init];
MLKTextRecognizer *koreanTextRecognizer = [MLKTextRecognizer textRecognizerWithOptions:options];

2. इनपुट इमेज तैयार करना

इमेज को UIImage या CMSampleBufferRef के तौर पर, TextRecognizer के process(_:completion:) तरीके से पास करें:

UIImage या CMSampleBuffer का इस्तेमाल करके, VisionImage ऑब्जेक्ट बनाएं.

अगर UIImage का इस्तेमाल किया जाता है, तो यह तरीका अपनाएं:

  • UIImage का इस्तेमाल करके, VisionImage ऑब्जेक्ट बनाएं. पक्का करें कि आपने सही .orientation डाला हो.

    Swift

    let image = VisionImage(image: UIImage)
    visionImage.orientation = image.imageOrientation

    Objective-C

    MLKVisionImage *visionImage = [[MLKVisionImage alloc] initWithImage:image];
    visionImage.orientation = image.imageOrientation;

अगर CMSampleBuffer का इस्तेमाल किया जाता है, तो यह तरीका अपनाएं:

  • CMSampleBuffer में मौजूद इमेज डेटा का ओरिएंटेशन बताएं.

    इमेज का ओरिएंटेशन पाने के लिए:

    Swift

    func imageOrientation(
      deviceOrientation: UIDeviceOrientation,
      cameraPosition: AVCaptureDevice.Position
    ) -> UIImage.Orientation {
      switch deviceOrientation {
      case .portrait:
        return cameraPosition == .front ? .leftMirrored : .right
      case .landscapeLeft:
        return cameraPosition == .front ? .downMirrored : .up
      case .portraitUpsideDown:
        return cameraPosition == .front ? .rightMirrored : .left
      case .landscapeRight:
        return cameraPosition == .front ? .upMirrored : .down
      case .faceDown, .faceUp, .unknown:
        return .up
      }
    }
          

    Objective-C

    - (UIImageOrientation)
      imageOrientationFromDeviceOrientation:(UIDeviceOrientation)deviceOrientation
                             cameraPosition:(AVCaptureDevicePosition)cameraPosition {
      switch (deviceOrientation) {
        case UIDeviceOrientationPortrait:
          return cameraPosition == AVCaptureDevicePositionFront ? UIImageOrientationLeftMirrored
                                                                : UIImageOrientationRight;
    
        case UIDeviceOrientationLandscapeLeft:
          return cameraPosition == AVCaptureDevicePositionFront ? UIImageOrientationDownMirrored
                                                                : UIImageOrientationUp;
        case UIDeviceOrientationPortraitUpsideDown:
          return cameraPosition == AVCaptureDevicePositionFront ? UIImageOrientationRightMirrored
                                                                : UIImageOrientationLeft;
        case UIDeviceOrientationLandscapeRight:
          return cameraPosition == AVCaptureDevicePositionFront ? UIImageOrientationUpMirrored
                                                                : UIImageOrientationDown;
        case UIDeviceOrientationUnknown:
        case UIDeviceOrientationFaceUp:
        case UIDeviceOrientationFaceDown:
          return UIImageOrientationUp;
      }
    }
          
  • CMSampleBuffer ऑब्जेक्ट और ओरिएंटेशन का इस्तेमाल करके, VisionImage ऑब्जेक्ट बनाएं:

    Swift

    let image = VisionImage(buffer: sampleBuffer)
    image.orientation = imageOrientation(
      deviceOrientation: UIDevice.current.orientation,
      cameraPosition: cameraPosition)

    Objective-C

     MLKVisionImage *image = [[MLKVisionImage alloc] initWithBuffer:sampleBuffer];
     image.orientation =
       [self imageOrientationFromDeviceOrientation:UIDevice.currentDevice.orientation
                                    cameraPosition:cameraPosition];

3. इमेज को प्रोसेस करना

इसके बाद, इमेज को process(_:completion:) तरीके से पास करें:

Swift

textRecognizer.process(visionImage) { result, error in
  guard error == nil, let result = result else {
    // Error handling
    return
  }
  // Recognized text
}

Objective-C

[textRecognizer processImage:image
                  completion:^(MLKText *_Nullable result,
                               NSError *_Nullable error) {
  if (error != nil || result == nil) {
    // Error handling
    return;
  }
  // Recognized text
}];

4. पहचाने गए टेक्स्ट के ब्लॉक से टेक्स्ट निकालना

अगर टेक्स्ट की पहचान करने की प्रोसेस पूरी हो जाती है, तो यह Text ऑब्जेक्ट दिखाता है. Text ऑब्जेक्ट में, इमेज में पहचाना गया पूरा टेक्स्ट और शून्य या उससे ज़्यादा TextBlock ऑब्जेक्ट शामिल होते हैं.

हर TextBlock, टेक्स्ट के रेक्टेंगुलर ब्लॉक को दिखाता है. इसमें शून्य या उससे ज़्यादा TextLine ऑब्जेक्ट होते हैं. हर TextLine ऑब्जेक्ट में शून्य या उससे ज़्यादा TextElement ऑब्जेक्ट होते हैं. ये ऑब्जेक्ट, शब्दों और शब्द जैसी इकाइयों को दिखाते हैं. जैसे, तारीखें और संख्याएं.

हर TextBlock, TextLine, और TextElement ऑब्जेक्ट के लिए, आपको क्षेत्र में पहचाना गया टेक्स्ट और क्षेत्र के बाउंडिंग कोऑर्डिनेट मिल सकते हैं.

उदाहरण के लिए:

Swift

let resultText = result.text
for block in result.blocks {
    let blockText = block.text
    let blockLanguages = block.recognizedLanguages
    let blockCornerPoints = block.cornerPoints
    let blockFrame = block.frame
    for line in block.lines {
        let lineText = line.text
        let lineLanguages = line.recognizedLanguages
        let lineCornerPoints = line.cornerPoints
        let lineFrame = line.frame
        for element in line.elements {
            let elementText = element.text
            let elementCornerPoints = element.cornerPoints
            let elementFrame = element.frame
        }
    }
}

Objective-C

NSString *resultText = result.text;
for (MLKTextBlock *block in result.blocks) {
  NSString *blockText = block.text;
  NSArray<MLKTextRecognizedLanguage *> *blockLanguages = block.recognizedLanguages;
  NSArray<NSValue *> *blockCornerPoints = block.cornerPoints;
  CGRect blockFrame = block.frame;
  for (MLKTextLine *line in block.lines) {
    NSString *lineText = line.text;
    NSArray<MLKTextRecognizedLanguage *> *lineLanguages = line.recognizedLanguages;
    NSArray<NSValue *> *lineCornerPoints = line.cornerPoints;
    CGRect lineFrame = line.frame;
    for (MLKTextElement *element in line.elements) {
      NSString *elementText = element.text;
      NSArray<NSValue *> *elementCornerPoints = element.cornerPoints;
      CGRect elementFrame = element.frame;
    }
  }
}

इनपुट इमेज के लिए दिशा-निर्देश

  • एमएल किट को टेक्स्ट की सही पहचान करने के लिए, इनपुट इमेज में ऐसा टेक्स्ट होना चाहिए जिसे दिखाने के लिए पिक्सल का सही डेटा इस्तेमाल किया गया हो. आदर्श रूप से, हर वर्ण कम से कम 16x16 पिक्सल का होना चाहिए. आम तौर पर, वर्णों को 24x24 पिक्सल से बड़ा करने पर, सटीक होने का कोई फ़ायदा नहीं मिलता.

    इसलिए, उदाहरण के लिए, 640x480 इमेज का इस्तेमाल करके, ऐसे बिज़नेस कार्ड को स्कैन किया जा सकता है जो इमेज की पूरी चौड़ाई में हो. लेटर साइज़ के पेपर पर प्रिंट किए गए दस्तावेज़ को स्कैन करने के लिए, 720x1280 पिक्सल की इमेज की ज़रूरत पड़ सकती है.

  • इमेज का फ़ोकस सही न होने से, टेक्स्ट को पहचानने की सुविधा की सटीकता पर असर पड़ सकता है. अगर आपको सही नतीजे नहीं मिल रहे हैं, तो उपयोगकर्ता से इमेज को फिर से कैप्चर करने के लिए कहें.

  • अगर आपको किसी रीयल-टाइम ऐप्लिकेशन में टेक्स्ट की पहचान करनी है, तो आपको इनपुट इमेज के कुल डाइमेंशन पर ध्यान देना चाहिए. छोटी इमेज को तेज़ी से प्रोसेस किया जा सकता है. लेटेंसी कम करने के लिए, पक्का करें कि इमेज में ज़्यादा से ज़्यादा टेक्स्ट हो. साथ ही, इमेज को कम रिज़ॉल्यूशन पर कैप्चर करें. हालांकि, ऊपर बताई गई सटीक जानकारी देने की ज़रूरी शर्तों को ध्यान में रखें. ज़्यादा जानकारी के लिए, परफ़ॉर्मेंस को बेहतर बनाने के लिए सुझाव लेख पढ़ें.

परफ़ॉर्मेंस को बेहतर बनाने के लिए सुझाव

  • वीडियो फ़्रेम प्रोसेस करने के लिए, डिटेक्टर के results(in:) सिंक्रोनस एपीआई का इस्तेमाल करें. दिए गए वीडियो फ़्रेम से नतीजे पाने के लिए, इस तरीके को AVCaptureVideoDataOutputSampleBufferDelegate के captureOutput(_, didOutput:from:) फ़ंक्शन से कॉल करें. डिटेक्टर को कॉल करने की फ़्रीक्वेंसी कम करने के लिए, AVCaptureVideoDataOutput के alwaysDiscardsLateVideoFrames को true के तौर पर सेट करें. अगर डिटेक्टर के चालू होने के दौरान कोई नया वीडियो फ़्रेम उपलब्ध होता है, तो उसे छोड़ दिया जाएगा.
  • अगर आपको इनपुट इमेज पर ग्राफ़िक ओवरले करने के लिए, डिटेक्टर के आउटपुट का इस्तेमाल करना है, तो पहले ML Kit से नतीजे पाएं. इसके बाद, इमेज को रेंडर करें और एक ही चरण में ओवरले करें. ऐसा करने से, आपको हर प्रोसेस किए गए इनपुट फ़्रेम के लिए, डिसप्ले सर्फ़ेस पर सिर्फ़ एक बार रेंडर करना होता है. उदाहरण के लिए, ML Kit के क्विकस्टार्ट सैंपल में updatePreviewOverlayViewWithLastFrame देखें.
  • इमेज को कम रिज़ॉल्यूशन में कैप्चर करें. हालांकि, इस एपीआई के इमेज डाइमेंशन से जुड़ी ज़रूरी शर्तों का भी ध्यान रखें.
  • परफ़ॉर्मेंस में गिरावट से बचने के लिए, अलग-अलग स्क्रिप्ट विकल्पों के साथ एक साथ कई TextRecognizer इंस्टेंस न चलाएं.