wtorek, 2 czerwca 2009

Mysz w OpenCV


Kolejny post niezwiązany stricte z wizją komputerową, ale opisujący przydatną w pracy nad programem/algorytmem funkcjonalność. W OpenCV brakuje zaawansowanych elementów GUI, biblioteka ma inny cel. Jednak interakcja pozwala na znaczne przyspieszenie testowania programu. OpenCV udostępnia kilka podstawowych operacji w części zwanej HighGUI (związany z nią jest plik highgui.h). Jedną z nich jest tworzenie okien. Dzisiaj opiszę inną: obsługę myszy.

Obsługa myszki rozwiązana jest czymś na wzór "callbacku". Aby jej użyć musimy napisać funkcję o określonym nagłówku (ważna jest tylko kolejność i typ parametrów):
void obsluga_myszki(int zdarzenie, int x, int y, int flagi, void* parametry);

Proste jej użycie pokzauje poniższy przykład:
// czy przycisk jest wcisniety
bool wcisniety = false;
// kolor ktorym rysujemy
CvScalar kolor;
// nazwa okna
char* nazwa = "Rysowanie";

void obsluga_myszki(int e, int x, int y, int fl, void* par)
{
// rzutujemy parametr na wskaznik na obraz
IplImage * obraz = (IplImage*) par;

switch (e)
{
case CV_EVENT_LBUTTONDOWN:
cvSet2D(obraz, y, x, kolor);
wcisniety = true;
break;
case CV_EVENT_LBUTTONUP:
wcisniety = false;
break;
case CV_EVENT_MOUSEMOVE:
if (wcisniety)
{
cvSet2D(obraz, y, x, kolor);
}
break;
}
}

void program_gl()
{

// tworzymy okno
cvNamedWindow(nazwa, CV_WINDOW_AUTOSIZE);

// wyswietlany obraz
IplImage* wys = cvCreateImage(cvSize(500, 500), 8, 3);
cvZero(wys);

// ustawiamy funkcje obslugi myszy
// kolejno podajemy nazwe okna, nazwe funkcji obslugi
// nasze dane (jako wskaznik), ktore otrzymamy w funkcji
// obslugi w parametrze void* par
cvSetMouseCallback(nazwa,obsluga_myszki,wys);

while(true)
{

cvShowImage(nazwa,wys);

if(cvWaitKey(10) == 'k')
break;
}

cvReleaseImage(&wys);
cvDestroyWindow(nazwa);

}

/*
* Rysowanie
* autor: ratixu.blogspot.com
*/
int main(int argc, char** argv)
{
kolor = cvScalarAll(255.0);
program_gl();
return (EXIT_SUCCESS);
}

Po uruchomieniu możemy rysować białym kolorem na czarnym tle.

Oczywiście zastosowań jest tyle, ile wyobraźnia podpowie :)

4 komentarze:

Anonimowy pisze...

Bardzo pomocne wydaję mi się te wpisy o openCV. :)
Niedługo mam zamiar coś w tym porobić, i sądzę, ze mi się przydadzą.

Tak trzymać :)

Anonimowy pisze...

mam pytanie. dlaczego gdy wyswietlam obraz IplImage w PictureBoxie w VisualC++ to jednoczesnie musze miec wlaczone cvWindow? czy mozna wyswietlic obraz IplImage w PictureBoxie bez koniecznosci wlaczania cvWindow?? z gory dziekuje

Łukasz pisze...

Ja niestety nie wiem, w VisualC++ nie miałem ostatnio okazji popisać. Jeżeli ktoś ma jakiś pomysł, to śmiało!

Anonimowy pisze...

Jak można wyświetlnić IplImage w PictureBoxie w VisualC++ ?