Python ve OpenCV İle Yüz Algılama ve Sayma Uygulaması

0 4.140

Bu makalemizde Python ve OpenCV Görüntü işleme kütüphanesini kullanarak görüntülerdeki yüzleri algılama ve yüzleri sayma uygulaması nasıl yapılabileceğini yazacağız.

Python ve OpenCV kullanarak basit bir yüz tanıma uygulamasının nasıl yapıldığını anlatan bir makaleyi daha önce yazmıştık. Ayrıca OpenCV ile ilgili birçok yazı ve uygulama örneğini sitemizden bulabilirsiniz.

Python öğrenmeye yeni başladıysanız sitemizdeki Python Derslerini takip edebilirsiniz.

Giriş

Bu yazının amacı, OpenCV ve Python kullanarak bir görüntüdeki yüzlerin nasıl tespit edileceğini ve sayılacağını göstermektir. Bu basit örnekte, Haar özellik tabanlı bir basamaklı sınıflandırıcı kullanacağız .

Kod

Her zamanki gibi, görüntü işleme için gerekli modülleri ekleyerek başlayacağız. Bunlar OpenCV ve Numpy modülleridir.

import numpy as np
import cv2

Ardından, sınıflandırıcıyı , sınıflandırıcı dosyasının yolunu girdi olarak alan cv2 modülünün CascadeClassifier işleviyle yükleyeceğiz. Bu durumda, haarcascade_frontalface_default.xml sınıflandırıcı dosyasını kullanacağız. Bu xml dosyasını buradan indirebilirsiniz. 

Dosyaya doğru erişildiğini garanti etmek için, tüm dosya yolunu CascadeClassifier fonksiyonunun içine koymayı unutmayın. İsterseniz direk kodun olduğu klasöre xml dosyasını koyup altttaki kodu yazabilirsiniz. Kod ve xml dosyası aynı klaösrde olmalı veya xml dosyasının yolu tam olarak alttaki kodda belirtilmelidir. Bu fonksiyon bir CascadeClassifier nesnesi döndürür .

face_cascade = cv2.CascadeClassifier('haarcascade_frontalface_default.xml')

Sonra görüntüyü cv2 modülünün imread  fonksiyonu ile yükleyeceğiz. Bu işlev, görüntünün yolunu girdi olarak alır. İstediğimiz görüntüyü yüz algılamasına girdi olarak geçireceğiz.

Sınıflandırmayı uygulamak için görüntüyü gri tonlamaya da dönüştüreceğiz. Bunu yapmak için cvtColor işlevini kullanıyoruz. Bu, orijinal görüntüyü girdi olarak ve ikinci girdi olarak renk alanı dönüştürme kodunu alır. Bu durumda, RGB’den griye dönüştürmek için COLOR_BGR2GRAY kodunu kullanırız.

image = cv2.imread('Test.jpg')
grayImage = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)

Şimdi, gerçek yüz algılamayı yapmak için, face_cascade nesnesimiz üzerinde DetectMultiScale fonksiyonunu çağıracağız. Girdi olarak dönüştürülmüş gri görüntümüzü geçireceğiz. Ayrıca, bu fonksiyon gibi bazı ayar parametreleri alabilir. Nesnenin boyutunu değiştirmek için ScaleFactor veya boyutunu algılamak için minSize parametrelerini girebiliriz.  Bu parametreler hakkında daha fazla bilgiyi burada okuyabilirsiniz  , ancak basitlik açısından, görüntüyü girdi olarak geçeceğiz.

Bu yöntem algılanan nesneleri (bu örnekte yüzler) dikdörtgenler olarak döndürür, böylece bunları çıktı görüntüsünde kolayca bulduğumuz yüzleri işaretleyebiliriz.

Çıktının türünü onaylamak için, döndürülen nesnenin türünü kontrol etmek için Python’un tür işlevini kullanacağız. Numpy ndarray olacak.

Bu, orijinal eğitim kodunda dikkate alınmamıştı, bu nedenle yüzsüz görüntüler kullanılırken bir hata verirdi. Bunun düzeltmesi, döndürülen nesnenin uzunluğunu kontrol etmeye karşılık gelir ve sıfıra eşitse, yürütmeyi sonlandırırız. Bu koşul, bu bölümün sonuna, son koda eklenir.

faces = face_cascade.detectMultiScale(grayImage)
print type(faces)
print faces

Ayrıca, dizimizde  boyutlarını döndürecek shape  fonksiyonunu çağırarak çıktımız hakkında daha fazla bilgi edinebiliriz . Göreceğimiz gibi, N satır ve 4 sütunluk bir matris elde edeceğiz, tespit edilen yüz sayısı N ve her yüzün dikdörtgeninin 4 boyutu.

Yani, N satırını alırsak, şimdi aşağıda belirtildiği gibi kaç yüz tespit edildi.

print faces.shape
print "Number of faces detected: " + str(faces.shape[0])

Böylelikle görüntü dosyamızda kaç tane yüz bulunduğu terminal ekranına yazdırabiliyoruz.

Şimdi, sonuçları tekrarlayacağız ve orijinal görüntümüzdeki yüzlerin etrafına dikdörtgenler çizeceğiz. Bunu yapmak  için, cv2 modülündeki rectangle fonksiyonunu çağırıyoruz. Bu fonksiyon görüntüyü, dikdörtgenin başlangıç ​​ve son tepe noktalarını, dikdörtgenin RGB rengini ve dikdörtgenin kalınlığını alır . Tüm dikdörtgenleri almak ve çizmek için bunu bir for-in  döngüsünde yapacağız.

for (x,y,w,h) in faces:
    cv2.rectangle(image,(x,y),(x+w,y+h),(0,255,0),1)

Ayrıca algılanan yüz sayısını görüntümüzün sol alt kısmına koyacağız. İlk olarak, metni üstüne koymak için başka bir dikdörtgen çizeceğiz, çünkü görüntülerin rengini bilmiyoruz. Bu, metnin her zaman kolayca okunabileceğini garanti eder.

Başlangıç ​​tepe noktası koordinatlarda (x = 0, y = görüntü yüksekliği – 25) ve bitiş tepe noktası (x = 270, görüntü yüksekliği) olacaktır. Daha karmaşık kodlardan kaçınmak için, bunun belirteceğimiz metnin boyutu için sabit kodlandığını unutmayın.

Görüntünün yüksekliğini elde etmek için, daha önce ndarray ile yaptığımız aynı numarayı yapabileceğimizi unutmayın. Görüntü bir matris olduğundan, şekil yöntemini çağırır ve satır sayısını alırız.

Dikdörtgen fonksiyonuna beyaz rengi ve -1 kalınlığını geçeceğiz, yani dikdörtgen doldurulacaktır.

Metni yazmak için görüntüyü, metni, metnin nereye yerleştirileceği sol alt köşeyi, yazı tipini , metnin ölçeğini, rengi ve kalınlığı girerek geçiren putText işlevini çağırırız.

cv2.rectangle(image, ((0,image.shape[0] -25)),(270, image.shape[0]), (255,255,255), -1)
cv2.putText(image, "Number of faces detected: " + str(faces.shape[0]), (0,image.shape[0] -10), cv2.FONT_HERSHEY_TRIPLEX, 0.5, (0,0,0), 1)

Bunun sadece bir eklenti olduğunu unutmayın, ancak isterseniz basitlik için yüzlerin sayısı konsolda yazdırılacağı için kodu koddan kaldırabilirsiniz.

Son olarak, düzenlenmiş görüntüyü dikdörtgenler ve metinle gösteririz ve pencereleri yok etmek için bir tuşa basılmasını bekleriz.

cv2.imshow('Image with faces',image)
cv2.waitKey(0)
cv2.destroyAllWindows()

Aşağıdaki çalışma kodunun tamamını kontrol edebilirsiniz. Belirtildiği gibi, detMultiScale yöntemi bu durumda şekil yöntemine sahip olmayan bir demet döndürdüğünden , yüz nesnesi bulunmadığında hata almamak için faces nesnesinin uzunluğunu kontrol ettiğimizi unutmayın .

import numpy as np
import cv2

face_cascade = cv2.CascadeClassifier('haarcascade_frontalface_default.xml')

image = cv2.imread('millitakim.jpg')
grayImage = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)

faces = face_cascade.detectMultiScale(grayImage)

print(type(faces))

if len(faces) == 0:
    print("No faces found")

else:
    print(faces)
    print(faces.shape)
    print("Number of faces detected: " + str(faces.shape[0]))

    for (x, y, w, h) in faces:
        cv2.rectangle(image, (x, y), (x + w, y + h), (0, 255, 0), 1)

    cv2.rectangle(image, ((0, image.shape[0] - 25)), (270, image.shape[0]), (255, 255, 255), -1)
    cv2.putText(image, "Number of faces detected: " + str(faces.shape[0]), (0, image.shape[0] - 10),
                cv2.FONT_HERSHEY_TRIPLEX, 0.5, (0, 0, 0), 1)

    cv2.imshow('Image with faces', image)
    cv2.waitKey(0)
    cv2.destroyAllWindows()

Sonuç

Kodumuzu çalıştırdığımızda kod ile aynı klasörde yer alan test.jpg dosyasını açığ içindeki yüzleri tespit edecek ve bulduğu yüz sayısını ekranın sol alt köşesine yazdıracaktır.

Milli takımımızın resmini çalıştırdığımızda yüzleri buluyor ve en alta bulduğu yüzlerin sayısını yazıyor.

Konsol ekranında da bulduğu yüzlerin konumlarını yazdırdık.

Tek kişinin bir kişinin bulunduğu bir görüntü dosyası.

 

Webcam’den Yüz Algılama ve Sayma

İsterseniz kodda ufak bir kaç değişiklik ile webcamden alınan görüntüdeki yüzleri bulma ve sayma uygulaması da yapılabilir. bu işlem için kodlarımız alttaki gibi olacaktır.

import numpy as np
import cv2

face_cascade = cv2.CascadeClassifier('haarcascade_frontalface_default.xml')
capture = cv2.VideoCapture(1)

while(True):
    ret, image = capture.read()
    grayImage = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)

    faces = face_cascade.detectMultiScale(grayImage)

    print(type(faces))

    if len(faces) == 0:
        cv2.putText(image, "Number of faces detected: 0" , (0, image.shape[0] - 10),
                    cv2.FONT_HERSHEY_TRIPLEX, 0.5, (0, 0, 0), 1)

    else:


        for (x, y, w, h) in faces:
            cv2.rectangle(image, (x, y), (x + w, y + h), (0, 255, 0), 1)

        cv2.rectangle(image, ((0, image.shape[0] - 25)), (270, image.shape[0]), (255, 255, 255), -1)
        cv2.putText(image, "Number of faces detected: " + str(faces.shape[0]), (0, image.shape[0] - 10),
                    cv2.FONT_HERSHEY_TRIPLEX, 0.5, (0, 0, 0), 1)

        cv2.imshow('Image with faces', image)
        if (cv2.waitKey(1) == 27):
            break

capture.release()
cv2.destroyAllWindows()

Sonuç olarak videoda izlediğiniz gibi görüntüdeki yüzleri algılanıyor ve yüz sayısı pencerenin altında yazdırılıyor.

Sonuç

Haar Cascade yöntemi ile yüz tanıma işlemini yaptığımız bu uygulama sonucunda yüzde 100 lük bir başarı elde etmek zordur. Resimdeki tüm yüzleri bulamaması veya yüz olmayan bazı durumları yüz olarak işaretlemesi olasıdır. Ancak bu eğitimimiz sayesinde opencv ve python kullanarak yüz tanıma uygulaması geliştirmenin mantığını, ekranda bulunan yüzleri saydırma işlemi yapmayı ve ekrana yazı yazdırma işlemini uygulamış olduk.

Yorumlarınızı bekliyoruz.

Cevap bırakın

E-posta hesabınız yayımlanmayacak.

Bu web sitesi deneyiminizi geliştirmek için çerezleri kullanır. Bununla iyi olduğunuzu varsayacağız, ancak isterseniz vazgeçebilirsiniz. Kabul etmek Mesajları Oku