ইমেজ বিশ্লেষণ
ব্যবহারের ক্ষেত্রে আপনার অ্যাপকে একটি CPU-অ্যাক্সেসযোগ্য ছবি প্রদান করে যার উপর আপনি
ইমেজ প্রসেসিং, কম্পিউটার ভিশন বা মেশিন লার্নিং ইনফারেন্স পারফর্ম করতে পারবেন। অ্যাপ্লিকেশনটি
একটি
analyze()
পদ্ধতি প্রয়োগ করে যা প্রতিটি ফ্রেমে রান করে।
আপনার CameraX অ্যাপের সাথে Google-এর ML Kit কীভাবে ইন্টিগ্রেট করবেন তা জানতে, ML Kit Analyzer দেখুন।
অপারেটিং মোড
অ্যাপ্লিকেশনের বিশ্লেষণ পাইপলাইন CameraX-এর ফ্রেম রেটের প্রয়োজনীয়তা পূরণ করতে না পারলে, CameraX-কে নিম্নলিখিত উপায়ে ফ্রেম ড্রপ করার জন্য কনফিগার করা যেতে পারে:
নন-ব্লকিং (ডিফল্ট): এই মোডে, এক্সিকিউটর সবসময় লেটেস্ট ছবিকে ইমেজ বাফারে (এক গভীরতার সারি) ক্যাশে করে, যখন অ্যাপ্লিকেশন আগের ছবি বিশ্লেষণ করে। অ্যাপ্লিকেশন প্রসেস করা শেষ করার আগে CameraX নতুন ছবি পেলে, নতুন ছবিটি একই বাফারে সেভ করা হয়, আগের ছবিটি ওভাররাইট করে। মনে রাখবেন যে এই পরিস্থিতিতে
ImageAnalysis.Builder.setImageQueueDepth()-এর কোনও প্রভাব নেই এবং বাফার কন্টেন্ট সবসময় ওভাররাইট করা হয়। আপনিSTRATEGY_KEEP_ONLY_LATEST-এর সাথেsetBackpressureStrategy()কল করে এই নন-ব্লকিং মোড চালু করতে পারবেন। এক্সিকিউটর ইমপ্লিকেশন সম্পর্কে আরও তথ্যের জন্য,STRATEGY_KEEP_ONLY_LATEST-এর রেফারেন্স ডকুমেন্টেশন দেখুন।ব্লকিং: এই মোডে, ইন্টার্নাল এক্সিকিউটর ইন্টার্নাল ইমেজ কিউতে একাধিক ছবি যোগ করতে পারে এবং কিউ সম্পূর্ণ হয়ে গেলে তবেই ফ্রেম ড্রপ করা শুরু করে। ব্লকিং পুরো ক্যামেরা ডিভাইস স্কোপ জুড়ে ঘটে: যদি ক্যামেরা ডিভাইসে একাধিক বাউন্ড ব্যবহারের কেস থাকে, তাহলে CameraX এই ছবিগুলি প্রসেস করার সময় সেই ব্যবহারের কেসগুলি সব ব্লক করা হবে। যেমন, প্রিভিউ ও ছবি বিশ্লেষণ, দুটিই ক্যামেরা ডিভাইসের সাথে যুক্ত থাকলে, CameraX ছবি প্রসেস করার সময় প্রিভিউও ব্লক হয়ে যাবে। আপনি
STRATEGY_BLOCK_PRODUCERথেকেsetBackpressureStrategy()-এ পাস করার মাধ্যমে ব্লকিং মোড চালু করতে পারবেন। এছাড়াও, আপনি ImageAnalysis.Builder.setImageQueueDepth() ব্যবহার করে ইমেজ কিউ ডেপথ কনফিগার করতে পারবেন।
কম লেটেন্সি ও উচ্চ পারফর্ম্যান্স অ্যানালাইজার সহ, যেখানে একটি ছবি বিশ্লেষণ করার মোট সময় CameraX ফ্রেমের সময়কালের চেয়ে কম (উদাহরণস্বরূপ, ৬০fps-এর জন্য ১৬ms), যেকোনও অপারেটিং মোড একটি মসৃণ সামগ্রিক অভিজ্ঞতা প্রদান করে। কিছু পরিস্থিতিতে ব্লকিং মোড এখনও সহায়ক হতে পারে, যেমন খুব সংক্ষিপ্ত সিস্টেম জিটার নিয়ে কাজ করার সময়।
উচ্চ লেটেন্সি ও উচ্চ পারফর্ম্যান্স অ্যানালাইজার সহ, লেটেন্সি কমানোর জন্য দীর্ঘ কিউ সহ ব্লকিং মোড প্রয়োজন। তবে মনে রাখবেন, অ্যাপ্লিকেশনটি এখনও সমস্ত ফ্রেম প্রসেস করতে পারে।
বেশি লেটেন্সি ও সময়সাপেক্ষ অ্যানালাইজার (অ্যানালাইজার সব ফ্রেম প্রসেস করতে পারে না) থাকলে, নন-ব্লকিং মোড আরও উপযুক্ত বিকল্প হতে পারে, কারণ অ্যানালিসিস পাথের জন্য ফ্রেম ড্রপ করতে হয়, তবে অন্যান্য কনকারেন্ট বাউন্ড ব্যবহারের ক্ষেত্রে এখনও সব ফ্রেম দেখা যায়।
প্রয়োগ
আপনার অ্যাপ্লিকেশনে ইমেজ অ্যানালিসিস ব্যবহার করতে, এইসব ধাপ অনুসরণ করুন:
ImageAnalysisব্যবহারিক ক্ষেত্র তৈরি করুন।ImageAnalysis.Analyzerতৈরি করুন।- আপনার
ImageAnalysis-এ অ্যানালাইজার সেট করুন। - লাইফসাইকেলে
আপনার লাইফসাইকেল মালিক, ক্যামেরা সিলেক্টর ও
ImageAnalysisব্যবহারের কেস বাইন্ড করুন।
বাইন্ডিংয়ের ঠিক পরেই, CameraX আপনার রেজিস্টার করা অ্যানালাইজারে ছবি পাঠায়।
বিশ্লেষণ সম্পূর্ণ করার পরে,
ImageAnalysis.clearAnalyzer()
কল করুন অথবা বিশ্লেষণ বন্ধ করতে ImageAnalysis ব্যবহারের কেস আনবাইন্ড করুন।
ImageAnalysis ব্যবহারের উদাহরণ তৈরি করুন
ImageAnalysis আপনার
অ্যানালাইজারকে (একটি ইমেজ কনজিউমার) CameraX-এর সাথে কানেক্ট করে, যা একটি ইমেজ প্রোডিউসার।
অ্যাপ্লিকেশন
ImageAnalysis.Builder
ব্যবহার করে ImageAnalysis অবজেক্ট তৈরি করতে পারে। ImageAnalysis.Builder-এর মাধ্যমে,
অ্যাপ্লিকেশন নিম্নলিখিতগুলি কনফিগার করতে পারে:
- ইমেজ আউটপুট প্যারামিটার:
- ফর্ম্যাট: CameraX-এ
YUV_420_888এবংRGBA_8888setOutputImageFormat(int)-এর মাধ্যমে কাজ করে। ডিফল্ট ফর্ম্যাট হলYUV_420_888। - রেজোলিউশন এবং অ্যাসপেক্ট রেশিও: আপনি এই প্যারামিটারগুলির মধ্যে যেকোনও একটি সেট করতে পারেন, তবে মনে রাখবেন যে আপনি একই সময়ে দুটি মান সেট করতে পারবেন না।
- রোটেশন।
- টার্গেটের নাম: ডিবাগিংয়ের উদ্দেশ্যে এই প্যারামিটার ব্যবহার করুন।
- ফর্ম্যাট: CameraX-এ
- ইমেজ ফ্লো কন্ট্রোল:
অ্যাপ্লিকেশন রেজোলিউশন বা অ্যাস্পেক্ট রেশিওর মধ্যে যেকোনও একটি সেট করতে পারে, কিন্তু
দুটিই নয়। আউটপুটের সঠিক রেজোলিউশন নির্ভর করে অ্যাপ্লিকেশনের অনুরোধ করা সাইজ
(বা অ্যাস্পেক্ট রেশিও) এবং হার্ডওয়্যার ক্ষমতার উপর এবং অনুরোধ করা সাইজ বা রেশিওর থেকে
আলাদা হতে পারে। রেজোলিউশন ম্যাচিং অ্যালগরিদম সম্পর্কে তথ্যের জন্য,
setTargetResolution()-এর
ডকুমেন্টেশন দেখুন
কোনও অ্যাপ্লিকেশন আউটপুট ইমেজ পিক্সেলকে YUV (ডিফল্ট)
বা RGBA কালার স্পেসে কনফিগার করতে পারে। RGBA আউটপুট ফর্ম্যাট সেট করার সময়, CameraX ইন্টার্নালি
YUV থেকে RGBA কালার স্পেসে ছবি কনভার্ট করে এবং ছবির বিট
ImageProxy-র প্রথম প্লেনের ByteBuffer-এ
নিম্নলিখিত ক্রমে প্যাক করে (অন্য দুটি প্লেন ব্যবহার করা হয় না):
ImageProxy.getPlanes()[0].buffer[0]: alpha
ImageProxy.getPlanes()[0].buffer[1]: red
ImageProxy.getPlanes()[0].buffer[2]: green
ImageProxy.getPlanes()[0].buffer[3]: blue
...
জটিল ইমেজ বিশ্লেষণ করার সময়, ডিভাইস ফ্রেম রেট বজায় রাখতে না পারলে, আপনি CameraX কনফিগার করতে পারেন যাতে এই বিষয়ের অপারেটিং মোড বিভাগে বর্ণিত স্ট্র্যাটেজি অনুযায়ী ফ্রেম ড্রপ করা যায়।
আপনার অ্যানালাইজার তৈরি করুন
অ্যাপ্লিকেশন
ImageAnalysis.Analyzer
ইন্টারফেস প্রয়োগ করে এবং
analyze(ImageProxy image)
ওভাররাইড করে অ্যানালাইজার তৈরি করতে পারে।
প্রতিটি অ্যানালাইজারে, অ্যাপ্লিকেশন একটি
ImageProxy পায়, যা Media.Image-এর
জন্য একটি র্যাপার।
ছবির ফর্ম্যাট
ImageProxy.getFormat()-এর মাধ্যমে কোয়েরি করা যেতে পারে।
ফর্ম্যাটটি নিম্নলিখিত মানগুলির মধ্যে একটি যা অ্যাপ্লিকেশনটি
ImageAnalysis.Builder-এর সাথে প্রদান করে:
ImageFormat.RGBA_8888যদি অ্যাপটিOUTPUT_IMAGE_FORMAT_RGBA_8888-এর জন্য অনুরোধ করে।ImageFormat.YUV_420_888যদি অ্যাপটিOUTPUT_IMAGE_FORMAT_YUV_420_888-এর জন্য অনুরোধ করে।
কালার স্পেস কনফিগারেশন এবং পিক্সেল বাইট কোথায় পাওয়া যাবে তা জানতে ImageAnalysis ব্যবহারের কেস তৈরি করুন দেখুন।
অ্যানালাইজারের মধ্যে, অ্যাপ্লিকেশনকে নিম্নলিখিত কাজগুলি করতে হবে:
- যত দ্রুত সম্ভব প্রদত্ত ফ্রেম বিশ্লেষণ করুন, বিশেষত প্রদত্ত ফ্রেম রেটের সময়সীমার মধ্যে (যেমন, ৩০ fps-এর ক্ষেত্রে ৩২ms-এর কম)। অ্যাপ্লিকেশনটি যদি যথেষ্ট দ্রুত ফ্রেম বিশ্লেষণ করতে না পারে, তাহলে ফ্রেম ড্রপ করার জন্য কাজ করে এমন মেকানিজম-এর মধ্যে একটি ব্যবহার করার কথা বিবেচনা করুন।
ImageProxy.close()কল করেImageProxy-কে CameraX-এ রিলিজ করুন। মনে রাখবেন, আপনার র্যাপ করা Media.Image-এর close ফাংশন (Media.Image.close()) কল করা উচিত নয়।
অ্যাপ্লিকেশন সরাসরি ImageProxy-এর মধ্যে র্যাপ করা Media.Image ব্যবহার করতে পারে।
র্যাপ করা ছবিতে Media.Image.close() কল করবেন না, কারণ এটি CameraX-এর মধ্যে
ছবি শেয়ার করার মেকানিজমকে ভেঙে দেবে; এর পরিবর্তে,
CameraX-এ অন্তর্নিহিত Media.Image রিলিজ করতে
ImageProxy.close() ব্যবহার করুন।
ImageAnalysis-এর জন্য আপনার অ্যানালাইজার কনফিগার করুন
আপনি অ্যানালাইজার তৈরি করার পরে, বিশ্লেষণ শুরু করার জন্য এটি রেজিস্টার করতে
ImageAnalysis.setAnalyzer()
ব্যবহার করুন। বিশ্লেষণ করা হয়ে গেলে, রেজিস্টার করা বিশ্লেষক সরাতে
ImageAnalysis.clearAnalyzer()
ব্যবহার করুন।
ছবি বিশ্লেষণের জন্য শুধুমাত্র একটি অ্যাক্টিভ বিশ্লেষক কনফিগার করা যেতে পারে। ImageAnalysis.setAnalyzer() কল করা
রেজিস্টার করা অ্যানালাইজার আগে থেকেই থাকলে, সেটি পরিবর্তন করে। অ্যাপ্লিকেশন যেকোনও সময়, ব্যবহারের কেস বাইন্ড করার আগে বা পরে, নতুন বিশ্লেষক সেট করতে পারে।
ImageAnalysis-কে লাইফসাইকেলের সাথে বাইন্ড করুন
ProcessCameraProvider.bindToLifecycle()
ফাংশনের মাধ্যমে আপনার ImageAnalysis-কে আগে থেকে থাকা
AndroidX লাইফসাইকেলের সাথে বাইন্ড করার জন্য বিশেষভাবে সাজেস্ট করা হয়। মনে রাখবেন যে bindToLifecycle() ফাংশন বেছে নেওয়া
Camera ডিভাইস ফিরিয়ে দেয়, যা এক্সপোজার ও অন্যান্য উন্নত সেটিংস
ফাইন টিউন করতে ব্যবহার করা যেতে পারে। ক্যামেরা আউটপুট নিয়ন্ত্রণ করা সম্পর্কে আরও তথ্যের জন্য এই নির্দেশিকা দেখুন।
নিচে দেওয়া উদাহরণে আগের ধাপের সবকিছু একত্রিত করা হয়েছে, CameraX ImageAnalysis এবং Preview ব্যবহারের কেস lifeCycle মালিকের সাথে বাইন্ড করা হয়েছে:
val imageAnalysis = ImageAnalysis.Builder() // enable the following line if RGBA output is needed. // .setOutputImageFormat(ImageAnalysis.OUTPUT_IMAGE_FORMAT_RGBA_8888) .setTargetResolution(Size(1280, 720)) .setBackpressureStrategy(ImageAnalysis.STRATEGY_KEEP_ONLY_LATEST) .build() imageAnalysis.setAnalyzer(executor, ImageAnalysis.Analyzer { imageProxy -> val rotationDegrees = imageProxy.imageInfo.rotationDegrees // insert your code here. ... // after done, release the ImageProxy object imageProxy.close() }) cameraProvider.bindToLifecycle(this as LifecycleOwner, cameraSelector, imageAnalysis, preview)
অতিরিক্ত রিসোর্স
CameraX সম্পর্কে আরও জানতে, নিম্নলিখিত অতিরিক্ত রিসোর্স দেখুন।
কোডল্যাব
কোডের স্যাম্পেল