10 Eylül 2018 Pazartesi

C++ - OpenCV Nesne Takip Modülleri

Bu yazı kapsamında sizlere OpenCV içerisindeki nesne takip modüllerinden bahsedeceğim. 


Nesne takip bir videodaki herhangi bir nesneyi birbirini takip eden  görüntülerde bulma işlemidir. Nesne takip yöntemleri özellikle nesne tanıma yöntemleri ile birlikte kullanılarak, hedef nesnenin tespit edilemediği durumlarda takip yönteminin devreye girmesiyle son derece faydalı olabilir.
Görüntü işleme alanında son derece popüler olan OpenCV kütüphanesine ise, 3.0 sürümünden itibaren çeşitli nesne takip modülleri eklenmiştir. Buna göre bir videoda ilk görüntüde bir dikdörtgen alan seçerek, seçilen bu alanı (yani alanın içerisindeki nesneyi) takip etmek son derece kolay hale gelmiş oldu.

OpenCV 3.4.2 sürümü itibariyle BOOSTING, MIL, KCF, TLD, MEDIANFLOW, MOSSE, CSRT ve GOTURN gibi birçok takip modülü implemente edilmiş durumda. (detaylı bilgi için tıklayınız)

Bu yöntemlerin içerisinde GOTURN'e ayrıca değinmek istiyorum. Açılımı Generic Object Tracking Using Regression Networks  olan bu yöntem, adından da anlaşılacağı gibi sinir ağı yani popüler adıyla derin öğrenme temelli bir yöntem. Bu yöntemi kullanmak için diğerlerinden farklı olarak, eğitilmiş modeli indirip programı çalıştıracağımız dizine kopyalamamız gerekiyor. İndirmemiz gereken dosyalar; goturn.caffemodel ve goturn.prototxt . (detaylı bilgi ve dosyaları indirmek için tıklayınız)

Kodları paylaşmadan önce belirtmek istediğim önemli bir not: nesne takip yöntemlerini kullanabilmeniz için OpenCV'yi ekstra modülleri ile birlikte kurmanız gerekmekte. Bunun için opencv ve ekstra modüllerin olduğu opencv_contrib kaynak kodlarını indirip, OpenCV'yi ekstra modülleri ile birlikte derlemeniz gerekecek.

Mini girizgahtan sonra C++ ile yazılmış kodları paylaşıyorum.

include edeceğimiz dosyalar
#include<iostream>
#include <opencv2/opencv.hpp>
#include <opencv2/tracking.hpp>
using namespace std;
using namespace cv;

Dosya yolunu argüman olarak almak istersek;
 string str = "0";
 char* video_input = (char*)str.c_str();

 for (int argv_index = 1; argv_index < argc; argv_index++)
 {
  if (0 == strcmp("-v", argv[argv_index]))
  {
   if ((++argv_index) < argc)
   {
    video_input = argv[argv_index];
   }
  }
  else if (0 == strcmp("-c", argv[argv_index]))
  {
   if ((++argv_index) < argc)
   {
    video_input = argv[argv_index];
   }
  }
 }


Tracker nesnesini seçilen farklı yöntemlere göre oluşturmak için;
 Ptr<Tracker> tracker;
 string trackerTypes[8] = { "BOOSTING", "MIL", "KCF", "TLD","MEDIANFLOW", "GOTURN", "MOSSE", "CSRT" };
 string trackerType = trackerTypes[7];

 if (trackerType == "BOOSTING")
  tracker = TrackerBoosting::create();
 if (trackerType == "MIL")
  tracker = TrackerMIL::create();
 if (trackerType == "KCF")
  tracker = TrackerKCF::create();
 if (trackerType == "TLD")
  tracker = TrackerTLD::create();
 if (trackerType == "MEDIANFLOW")
  tracker = TrackerMedianFlow::create();
 if (trackerType == "GOTURN")
  tracker = TrackerGOTURN::create();
 if (trackerType == "MOSSE")
  tracker = TrackerMOSSE::create();
 if (trackerType == "CSRT")
  tracker = TrackerCSRT::create();

Eğer video yolu belirtilmemişse, kamerayı açmak istersek;
 VideoCapture *video;
 if (strlen(video_input) == 1 && (video_input[0] >= 48 || video_input[0] <= 57))
 {
  unsigned short x = video_input[0] - 48;
  video = new cv::VideoCapture(x);
 }
 else {
  video = new cv::VideoCapture(video_input);
 }


Ve artık selectROI ile bir dikdörtgen seçip takip işlemini başlatabiliriz.
 Mat frame;
 video->read(frame);
 Rect2d rect = selectROI(frame);


 // Initialize tracker with first frame and bounding box
 tracker->init(frame, rect);


Bir döngü içerisinde takip sonuçlarını ekranda görüntülemek için;
 while (video->read(frame))
 {
  // Update the tracking result
  bool ok = tracker->update(frame, rect);

  if (ok)
  {
   rectangle(frame, rect, Scalar(255, 0, 255), 2, 1);
  }
  else
  {
   putText(frame, "Tracking failure detected", Point(100, 80), FONT_HERSHEY_SIMPLEX, 0.75, Scalar(0, 0, 255), 2);
  }

  putText(frame, trackerType, Point(100, 20), FONT_HERSHEY_SIMPLEX, 0.75, Scalar(50, 170, 50), 2);

  // Display frame.
  imshow("Tracking", frame);

  // Exit if ESC pressed.
  if (waitKey(1) == 27) break;
 }




Her türlü görüş, öneri ve sorularınızı iletebilirsiniz...

Hiç yorum yok:

Yorum Gönder