Распознавание образов для программистов

ВНИМАНИЕ! БЛОГ ПЕРЕЕХАЛ ПО АДРЕСУ
RECOG.RU

27 Январь 2011

Поворот изображений

написано в рубрике: OpenCV — Кручинин Александр @ 12:54 ПП

Для поворота изображений существует следующая функция (нашёл где-то в Интернете):
Mat rotateImage(const Mat& source, double angle)
{
Point2f src_center(source.cols/2.0F, source.rows/2.0F);
Mat rot_mat = getRotationMatrix2D(src_center, angle, 1.0);
Mat dst;
warpAffine(source, dst, rot_mat, source.size());
return dst;
}

Её использование:

Mat image_12=rotateImage(image_11,angle_);
IplImage image_2=image_12;

Ну а после  image_2 можно обычными средствами использовать.

25 Январь 2011

36. Прозрачный цвет в OpenCV

написано в рубрике: OpenCV — Кручинин Александр @ 1:57 ПП

При разработке различных систем наложения изображений часто бывает необходимо сделать один из цветов прозрачным. Такая возможность поддерживается функцией cvCopy. Для этого третьим параметром необходимо передать маску изображения, которую можно получить, переведя исходное изображение в изображение в градациях серого. Пусть у нас есть некоторое изображение в 24 битном формате в IplImage – Image1. Тогда для копирования изображения туда, куда надо (Image2)с прозрачным цветом необходимо выполнить следующие действия:

cvSetImageROI(Image2,Rect); //Rect – размеры области

IplImage* image=cvCreateImage(cvGetSize(Image1), 8, 1);

cvCvtColor(Image1,image, CV_BGR2GRAY );

cvCopy(Image1,Image2,image);

cvResetImageROI(Image2);

cvReleaseImage(image);

В результате цвет с яркостью 0 – будет прозрачным. Такой метод подходит для прозрачного чёрного цвета.

24 Январь 2011

Трекинг лица

написано в рубрике: OpenCV, Распознавание образов — Кручинин Александр @ 9:32 ПП

Существует много задач, где необходимо детктировать лицо на видеопотоке, а затем следить за ним. При использовании средств OpenCV простейшую программу можно написать за короткое время. Ниже приведён пример слежения за лицом.

1. Есть не однородный фон
2. Стандартные средства OpenCV работы с камерой
3. После детектирования лица и глаз сразу определяются точки для трекинга
4. Детектирование лица человека
5. Определение точек
6. Трекинг
7. Программно детектирование лиц делается достаточно просто
8. Можно наложить чьё-то фото на лицо человека
9. Наклонение оси и положение центра лица человека
10. И ещё раз слежение

1. There are not a homogeneous background
2. Standard tools OpenCV to work with camera
3. After detecting the face and eyes immediately determined point for tracking
4. Detection of a human face
5. Definition points
6. Tracking
7. Software detection faces is simply
8. Possible to impose someone else’s photo on the face of a man
9. Inclination of the axis and the center of the human face
10. And once again tracking

25 Декабрь 2010

35. Подсчёт объектов (людей), пересекающих линию (People counting)

написано в рубрике: OpenCV, Распознавание образов — Кручинин Александр @ 12:35 ПП

Самый простейший путь при подсчёте объектов – это использование детектирования движений. Например, используя ту же функцию update_mhi из примеров OpenCV. Собственно решение напрашивается само – следить за выделяемыми областями движения, и как только происходит пересечение заданной линии, то увеличивать значение счётчика. Однако функция update_mhi не предназначена для слежения за объектами, поэтому эту часть придётся делать самостоятельно. На рисунке 35.1 показано обнаруженные центра движений (а), и изменения положений центров движений (б).

Рис. 35. 1. Центры движений в кадре (а), изменение движений (b)

Рис. 35. 1. Центры движений в кадре (а), изменение движений (b)

Красные центры – старое местоположение, чёрные – новое. Одной из красных точек не соответствует чёрной, т.к. объект остановился и не двигается. R – максимальное расстояние, на которое может сместиться объект за один кадр.

Для наблюдения за объектами будет использоваться следующая структура:

struct _OBJECT_

{

int x,y; //Координаты центра объекта

int w,h; //Ширина, высота объекта

int timer; //Задержка, позволяющая следить за объектом после остановки

int num; //Номер объекта

int object;//Соответствие с новым объектом

int inn; //Переменная, показывающая где находится объект относительно линии пересечения

}VObject[MAX_OBJECTS],BVObject[MAX_OBJECTS];

VObject – текущий массив объектов, BVObject – предыдущий массив объектом. При каждом анализе детектируемых зон, необходимо сначала сохранить предыдущий массив, например так:

memcpy(BVObject,VObject,sizeof(_OBJECT_)*MAX_OBJECTS);

Если в предыдущем массиве нет ни одного объекта, то при анализе детектируемых зон можно вызвать следующий листинг:

if (all_object<MAX_OBJECTS){

VObject[all_object].num=end_object;

VObject[all_object].timer=timer_1;

VObject[all_object].x=xx;

VObject[all_object].y=yy;

VObject[all_object].w=comp_rect.width;

VObject[all_object].h=comp_rect.height;

VObject[all_object].object=-1;

VObject[all_object].inn=2;

cur_object=all_object;

all_object++;

end_object++;

}

Здесь, end_object – глобальный счётчик номеров объектов (всегда увеличивается); timer_1 – максимальное время задержки, после которого объект, которому не соответствия движения, уничтожается; xx, yy – текущие координаты центра движения; comp_rect – размер зоны движения.

Если от предыдущего кадра сохранились объекты, то необходимо проверять соответствие со старыми объектами:

min=-1;

for(j=0;j<local_all_object;j++)

if (BVObject[j].object==-1)

{

dd=LengthLine(xx,yy,BVObject[j].x,BVObject[j].y);

if (dd<maxdist && (min==-1 || dd1>dd))

{

min=j;

dd1=dd;

}

}

if (min==-1) {

VObject[all_object].num=end_object;

VObject[all_object].inn=2;

end_object++;

}

else {

VObject[all_object].num=BVObject[min].num;

VObject[all_object].inn=BVObject[min].inn;

BVObject[min].object=0;

}

VObject[all_object].timer=timer_1;

VObject[all_object].x=xx;

VObject[all_object].y=yy;

VObject[all_object].w=comp_rect.width;

VObject[all_object].h=comp_rect.height;

VObject[all_object].object=-1;

cur_object=all_object;

all_object++;

Здесь, local_all_object – общее количество старых объектов. Если указатель ссылки на новый объект (BVObject[j].object) равен -1, то сравнивается его удалённость с текущим объектом, если она минимальна и меньше расстояния R, заданного переменной maxdist, то соответствие найдено. Если соответствие не было найдено, то создаётся новый объект, иначе текущему объекту присваиваются номера и положения относительно граничной линии старого объекта.

Определение пересечения линии достаточно просто – необходимо сравнивать значения inn текущего и старого объекта. Определить inn относительно положения текущей линии можно по следующему листингу:

float ang=MakePolarF(center.x-Center.x,center.y-Center.y);//Из библиотеки ImagePak

byte inn=0;

if ((ang>In_ && ang<In_+PI) || (In_>PI  && ang<PI-In_)) {

inn=1;

}

if (VObject[cur_object].inn==0 && inn==1) All_In++;

if (VObject[cur_object].inn==1 && inn==0) {

All_Out++;

}

VObject[cur_object].inn=inn;

Здесь, center – это центр области движения; Center – центр заданной нами линии; In_ – угол в радианах вектора из центра линии в одну из сторон линии.

Этот метод прост и не лишён недостатков, возможно он не всегда работает, но я не нашёл подходящих видео для тестирования. Если у вас есть видео с камеры, расположенный сверху в коридоре (выходе/входе), через которые проходят много людей, и вам несложно передать эти видео мне для тестирования, то свяжитесь со мной!

14 Декабрь 2010

34. Создание программы детектирования движения на нескольких камерах с использованием OpenCV. Часть III

написано в рубрике: OpenCV — Кручинин Александр @ 10:56 ДП

Текст результирующей программы детектирования движений вы можете скачать здесь:

Multiple Motion Detect http://vidikon.com/download/multimd.zip

На рисунке 34.1 представлена система для тестирования программы с 4 камерами (1 встроенная).

Рис. 34.1 Система для тестирования

Рис. 34.1 Система для тестирования

Программа реализует самый простейший способ управления процессом распознавания образов в реальном времени, о котором вы можете почитать здесь:

http://blog.vidikon.com/?p=423

http://blog.vidikon.com/?p=157

http://blog.vidikon.com/?p=103

Когда на камерах нет движения, то частота кадров снижается до минимальной (т.е. максимальная задержка. В противном случае увеличивается. Результаты смотрите в таблице и на рисунке 34.2.

Таблица

Количество камер, на которых обнаружено движение

Процент загруженности CPU

0

4-8%

1

10-16%

2

17-21%

3

22-29%

4

31-34%

Рис. 34.2. Загруженность CPU

Рис. 34.2. Загруженность CPU

Понятно, что если не управлять детектированием движения загрузка будет постоянно максимальной, что для описываемого случая приемлемо, но в ситуации, когда максимальная загрузка колеблется около 100% – это необходимое решение.

« Новые записиСтарые записи »

Работает на WordPress