Merhabalar. Bugünkü yayında, webcam görüntüsü üzerinde yüz tespiti örneği yapacağız. Yayının amacı size doğrudan OpenCv öğretmek değil. Yani OpenCv hakkında bir şeyler biliyorsanız ama OpenCv'yi C# ile kullanmak için OpenCvSharp hakkında örneklere ihtiyacınız varsa, bu yayın sizin için uygundur.
Öncelikle bir WindowsFormsApplication projesi oluşturun.
Sonralıkla NuGet Manager'den OpenCvSharp3-AnyCPU bulup kurun. :)
Projemizde yüz tipi nesneleri bulabimek için gerekli verileri içeren ve internetten kolaylıkla bulup indirebileceğiniz bir XML dosyasına ihtiyacımız var: haarcascade_frontalface_default.xml
Örnek olarak şu linkten bilgisayarınıza indirebilirsiniz: Şu Link :)
İndirdikten sonra, proje dosyalarınızın içine bunu yapıştırmanız gerekiyor. Visual Studio'da, Solution Explorer'den projenizin adına (WindowsFormsApplication1) sağ tıklayıp Open Folder in File Explorer seçin. Projenizin olduğu klasör açılınca bin klasörü altında Debug klasörü altına haarcascade_frontalface_default.xml dosyanızı yapıştırın. Bu dosyanın ille de burada olmasına gerek yok tabii ki ama bu örnekte ben bu dosyayı bu yoldan çağırıyorum. :)
Form tasarımı için şunlara ihtiyacımız olacak
Button ( Name: button1 | Text: Başlat | Click: button1_Click )
PictureBox ( Name: pictureBox1 | Size: 640;480 )
Timer ( Name: timer1 | Enable: false | Interval: 33 | Tick: timer1_Tick )
Kod sayfamızda da, sınıfımızın içinde şu metotlarımız olacak:
Senaryo:
Başlangıçta hiçbir görüntü yok. Başlat yazan butona tıkladığımızda webcam görüntüsü PictureBox nesnemizde akmaya başlayacak ve butonda Durdur yazacak. Durdur dediğimizde görüntü donacak ve butonda yine Başlat yazacak.
Butona basıldığında, durum_Kamera adlı bool bir değişkenimizin değeri true|false olarak değişecek.
Görüntünün akması işini Timer nesnemiz yapacak. 33 milisaniyede bir çalışan timer1 nesnemiz, eğer durum_Kamera değişkeninin değeri true ise webcam'den alınan görüntüyü pictureBox1'de gösterecek; false ise timer1 nesnemiz çalışmayacak. :)
Görüntü webcam'dan kare kare (Mat türünde) okunup sunulurken, her görüntüde yüz aranacak. Yüz bulunursa, etrafına sarı bir kare çizilecek. Oluşan son görüntü de Mat (matris) türünden Bitmap türüne dönüştürülerek pictureBox1'de gösterilecek.
Kodlamaya geçelim:
Projemize dahil edeceğimiz OpenCv sınıflarını çağıralım. Gerçi bunları yazmasak da Visual Studio bize bunları çağırmamızı önerecektir ama olsun:
Bazı değişkenlerimiz birden çok metot içinde kullanılacağından, onları global olarak tanımlayacağız. Sınıfımız içinde tanımladığımız global değişkenler:
Global değişkenlerin başlangıç değerlerini Form1_Load() fonksiyonumuzda vereceğiz.
button1 nesnemize tıklandığında üzerindeki yazı değişecek (Başlat | Durdur), durum_Kamera değişkeninin değeri değişecek (false | true) ve timer1 nesnemizin enable özelliği değişerek çalışması veya durması sağlanacak ( true | false ). button1_Click() metodumuz şu şekilde:
timer1 nesnemiz asıl işi yapacak. Webcam'in o anki görüntüsünü alıp, frame adlı Mat nesnesine atacak. Görüntü içinde 40x40 ile 300x300 piksel boyutları arasında yüz var mı diye bakacak. Yüz tespit ederse, frame görüntüsündeki yüzün etrafına sarı bir kare şekli çizecek. Oluşan son hali de Bitmap türüne dönüştürüp pictureBox1 nesnesinde gösterecek.
Başka bir yayında görüşmek üzere...
Öncelikle bir WindowsFormsApplication projesi oluşturun.
Sonralıkla NuGet Manager'den OpenCvSharp3-AnyCPU bulup kurun. :)
Projemizde yüz tipi nesneleri bulabimek için gerekli verileri içeren ve internetten kolaylıkla bulup indirebileceğiniz bir XML dosyasına ihtiyacımız var: haarcascade_frontalface_default.xml
Örnek olarak şu linkten bilgisayarınıza indirebilirsiniz: Şu Link :)
İndirdikten sonra, proje dosyalarınızın içine bunu yapıştırmanız gerekiyor. Visual Studio'da, Solution Explorer'den projenizin adına (WindowsFormsApplication1) sağ tıklayıp Open Folder in File Explorer seçin. Projenizin olduğu klasör açılınca bin klasörü altında Debug klasörü altına haarcascade_frontalface_default.xml dosyanızı yapıştırın. Bu dosyanın ille de burada olmasına gerek yok tabii ki ama bu örnekte ben bu dosyayı bu yoldan çağırıyorum. :)
Form tasarımı için şunlara ihtiyacımız olacak
Button ( Name: button1 | Text: Başlat | Click: button1_Click )
PictureBox ( Name: pictureBox1 | Size: 640;480 )
Timer ( Name: timer1 | Enable: false | Interval: 33 | Tick: timer1_Tick )
Kod sayfamızda da, sınıfımızın içinde şu metotlarımız olacak:
public Form1() { InitializeComponent(); }
private void Form1_Load(object sender, EventArgs e) { ... }
private void timer1_Tick(object sender, EventArgs e) { ... }
private void button1_Click(object sender, EventArgs e) { ... }
private void Form1_Load(object sender, EventArgs e) { ... }
private void timer1_Tick(object sender, EventArgs e) { ... }
private void button1_Click(object sender, EventArgs e) { ... }
Senaryo:
Başlangıçta hiçbir görüntü yok. Başlat yazan butona tıkladığımızda webcam görüntüsü PictureBox nesnemizde akmaya başlayacak ve butonda Durdur yazacak. Durdur dediğimizde görüntü donacak ve butonda yine Başlat yazacak.
Butona basıldığında, durum_Kamera adlı bool bir değişkenimizin değeri true|false olarak değişecek.
Görüntünün akması işini Timer nesnemiz yapacak. 33 milisaniyede bir çalışan timer1 nesnemiz, eğer durum_Kamera değişkeninin değeri true ise webcam'den alınan görüntüyü pictureBox1'de gösterecek; false ise timer1 nesnemiz çalışmayacak. :)
Görüntü webcam'dan kare kare (Mat türünde) okunup sunulurken, her görüntüde yüz aranacak. Yüz bulunursa, etrafına sarı bir kare çizilecek. Oluşan son görüntü de Mat (matris) türünden Bitmap türüne dönüştürülerek pictureBox1'de gösterilecek.
Kodlamaya geçelim:
Projemize dahil edeceğimiz OpenCv sınıflarını çağıralım. Gerçi bunları yazmasak da Visual Studio bize bunları çağırmamızı önerecektir ama olsun:
using OpenCvSharp;
using OpenCvSharp.Extensions;
using OpenCvSharp.Extensions;
Bazı değişkenlerimiz birden çok metot içinde kullanılacağından, onları global olarak tanımlayacağız. Sınıfımız içinde tanımladığımız global değişkenler:
private VideoCapture capture;
private Mat frame;
private Bitmap bitmapFrame;
private bool durum_Kamera;
private CascadeClassifier haarCascade;
private Mat frame;
private Bitmap bitmapFrame;
private bool durum_Kamera;
private CascadeClassifier haarCascade;
Global değişkenlerin başlangıç değerlerini Form1_Load() fonksiyonumuzda vereceğiz.
private void Form1_Load(object sender, EventArgs e)
{
capture = new VideoCapture(0);
frame = new Mat();
string xml_dosyasi = "haarcascade_frontalface_default.xml";
haarCascade = new CascadeClassifier(Application.StartupPath+"\\"+xml_dosyasi);
kameraDurum = false;
}
{
capture = new VideoCapture(0);
frame = new Mat();
string xml_dosyasi = "haarcascade_frontalface_default.xml";
haarCascade = new CascadeClassifier(Application.StartupPath+"\\"+xml_dosyasi);
kameraDurum = false;
}
button1 nesnemize tıklandığında üzerindeki yazı değişecek (Başlat | Durdur), durum_Kamera değişkeninin değeri değişecek (false | true) ve timer1 nesnemizin enable özelliği değişerek çalışması veya durması sağlanacak ( true | false ). button1_Click() metodumuz şu şekilde:
private void button1_Click(object sender, EventArgs e)
{
if(kameraDurum)
{
durum_Kamera= false;
button1.Text = "Başlat";
timer1.Enabled = false;
}
else
{
durum_Kamera= true;
button1.Text = "Durdur";
timer1.Enabled = true;
}
}
{
if(kameraDurum)
{
durum_Kamera= false;
button1.Text = "Başlat";
timer1.Enabled = false;
}
else
{
durum_Kamera= true;
button1.Text = "Durdur";
timer1.Enabled = true;
}
}
timer1 nesnemiz asıl işi yapacak. Webcam'in o anki görüntüsünü alıp, frame adlı Mat nesnesine atacak. Görüntü içinde 40x40 ile 300x300 piksel boyutları arasında yüz var mı diye bakacak. Yüz tespit ederse, frame görüntüsündeki yüzün etrafına sarı bir kare şekli çizecek. Oluşan son hali de Bitmap türüne dönüştürüp pictureBox1 nesnesinde gösterecek.
private void timer1_Tick(object sender, EventArgs e)
{
capture.Read(frame);
Cv2.Flip(frame, frame, FlipMode.Y);
OpenCvSharp.Size minBoyut = new OpenCvSharp.Size(40, 40);
OpenCvSharp.Size maxBoyut = new OpenCvSharp.Size(300, 300);
Rect[] faces = haarCascade.DetectMultiScale(frame, 1.1, 10, 0, minBoyut, maxBoyut);
if (faces.Length > 0)
for (int i = 0; i <= faces.Length - 1; i++)
{
int x1 = faces[i].Location.X;
int y1 = faces[i].Location.Y;
int x2 = faces[i].Location.X + faces[i].Width;
int y2 = faces[i].Location.Y + faces[i].Height;
OpenCvSharp.Point pt1 = new OpenCvSharp.Point(x1, y1);
OpenCvSharp.Point pt2 = new OpenCvSharp.Point(x2, y2);
Cv2.Rectangle(frame, pt1, pt2, new Scalar(0, 255, 255));
}
bitmapFrame = BitmapConverter.ToBitmap(frame);
pictureBox1.Image = bitmapFrame;
}
{
capture.Read(frame);
Cv2.Flip(frame, frame, FlipMode.Y);
OpenCvSharp.Size minBoyut = new OpenCvSharp.Size(40, 40);
OpenCvSharp.Size maxBoyut = new OpenCvSharp.Size(300, 300);
Rect[] faces = haarCascade.DetectMultiScale(frame, 1.1, 10, 0, minBoyut, maxBoyut);
if (faces.Length > 0)
for (int i = 0; i <= faces.Length - 1; i++)
{
int x1 = faces[i].Location.X;
int y1 = faces[i].Location.Y;
int x2 = faces[i].Location.X + faces[i].Width;
int y2 = faces[i].Location.Y + faces[i].Height;
OpenCvSharp.Point pt1 = new OpenCvSharp.Point(x1, y1);
OpenCvSharp.Point pt2 = new OpenCvSharp.Point(x2, y2);
Cv2.Rectangle(frame, pt1, pt2, new Scalar(0, 255, 255));
}
bitmapFrame = BitmapConverter.ToBitmap(frame);
pictureBox1.Image = bitmapFrame;
}
Başka bir yayında görüşmek üzere...
Yorumlar
Yorum Gönder