مكتبة OpenCV (الجزء الرابع) : إستخدام الـ Thresholding مع الصور

339

سنتعرف علي ال thresholding في هذا الدرس ونقوم بتطبيقها بمعالجة الصور والفيديوهات. الفكرة هي تبسيط البيانات أكثر قبل المعالجة. في البداية، يمكن تحويل الصورة الملونة إلى صورة رمادية لكن عليك أن تعلم أنه بعد ذلك ستبقي الصورة الرمادية بها على الأقل 255 قيمة. في أبسط الأمور، يعمل ال thresholding علي تحويل الصورة إلي binary أي صورة أبيض وأسود بإستخدام قيمة ل threshold. إذا كانت الصورة تتكون من 255 قيمة وتم استخدام قيمة 125 لـ threshold، فأي شيء يساوي 125 أو أقل يتم تحويل قيمته إلى 0 وأي شيئ أكبر من 125 يتم استبدالها بقيمة 255 أو اللون الأبيض. إذا كانت الصورة رمادية قبل تطبيق ال threshold، فبهذا الشكل سيتم الحصول على صورة أبيض وأسود. إذا لم تكون الصورة رمادية وتم تطبيق ال threshold على صورة ملونة، سيتم الحصول ايضاً على صورة ملونة بعد تطبيق ال threshold.

سيتم تطبيق أكثر من مثال على ال thresholding للتوضيح أكثر. سنستخدم الصورة التالية في المثال لكن يمكنك إستخدام أي صورة أخرى.

D:\Work\Jisr Labs\3.OpenCV\6\jisrlabs-opencvtut6-fig-1.jpg

هذه الصورة مثال جيد لتطبيق ال threshold بسبب وجود طبقة سوداء على الكلام. فكل شيئ غامق مع أن الخلفية في الأصل بيضاء. بعض الأجزاء يمكن قراءتها لكن البعض الآخر صعب جداً قراءته ويلزم تركيز عالي. لنبدأ تطبيق threshold بسيط:

 

retval, threshold = cv2.threshold(img, 10, 255, cv2.THRESH_BINARY)

 

ال threshold المستخدم يعتبر binary وذلك لأن ناتجه يكون فقط 0 أو 255. سنقوم بتطبيق ال threshold بغير تحويل الصورة إلي gray ولذلك الناتج سيظل صورة ملونة. العامل الأول هنا هو الصورة. العامل الثاني هو ال threshold والذي سيتم اختيار قيمته ب 10. القيمة العظمى سيتم إختيارها ب 255. قيمة 10 ليست أفضل القيم لكننا يمكننا مشاهدة ما سيجري حين إستخدامها. تم إستخدامها لأن الصورة تميل اللون الغامق وبإستخدام قيمة صغيرة سيتم تحويل أكبر عدد من ال pixels للون الفاتح. غالباً قيمة بين 125 إلى 150 ستكون جيدة في العديد من الأحيان.

import cv2

import numpy as np

img = cv2.imread('bookpage.jpg')

retval, threshold = cv2.threshold(img, 12, 255, cv2.THRESH_BINARY)

cv2.imshow('original',img)

cv2.imshow('threshold',threshold)

cv2.waitKey(0)

cv2.destroyAllWindows()

الناتج:

D:\Work\Jisr Labs\3.OpenCV\6\jisrlabs-opencvtut6-fig-2.pngالصورة الآن بحالة أفضل للقراءة عن السابق لكن يظل هناك تحسين. في البداية سيتم تحويل الصورة إلى صورة رمادية عن طريق إستخدام threshold كالتالي:

 

import cv2

import numpy as np

grayscaled = cv2.cvtColor(img,cv2.COLOR_BGR2GRAY)

retval, threshold = cv2.threshold(grayscaled, 10, 255, cv2.THRESH_BINARY)

cv2.imshow('original',img)

cv2.imshow('threshold',threshold)

cv2.waitKey(0)

cv2.destroyAllWindows()

D:\Work\Jisr Labs\3.OpenCV\6\jisrlabs-opencvtut6-fig-3.png

الآن الناتج أفضل عن ما كان عليه. يمكننا بعد ذلك استخدام adaptive thresholding والفكرة هنا هو التعامل مع الأجزاء المنحنية من الصفحات.

 

import cv2

import numpy as np

th = cv2.adaptiveThreshold(grayscaled, 255, cv2.ADAPTIVE_THRESH_GAUSSIAN_C, cv2.THRESH_BINARY, 115, 1)

cv2.imshow('original',img)

cv2.imshow('Adaptive threshold',th)

cv2.waitKey(0)

cv2.destroyAllWindows()

D:\Work\Jisr Labs\3.OpenCV\6\jisrlabs-opencvtut6-fig-4.png

النسخة الجديدة من الناتج تعتبر أفضل بكثير عن السابق. لكن هناك نوع آخر من ال thresholding يُسمي Otsu`s threshold:

retval2,threshold2 = cv2.threshold(grayscaled,125,255,cv2.THRESH_BINARY+cv2.THRESH_OTSU)

cv2.imshow('original',img)

cv2.imshow('Otsu threshold',threshold2)

cv2.waitKey(0)

cv2.destroyAllWindows()

تم ترجمة هذا الدرس بواسطة أحمد جاد.

المقال الأصلي:

https://pythonprogramming.net/thresholding-image-analysis-python-opencv-tutorial/

 

تعليقات