📄 cvvideo.cpp
字号:
#endif
// I don't need to rdlock lastframe, since I'm the one who writes it
//pthread_mutex_lock(&(camera->lastframemutex));
camera->vid_mmap.frame = (camera->lastframe + 1)%camera->mbuf.frames;
//pthread_mutex_unlock(&(camera->lastframemutex));
pthread_rwlock_wrlock(&(camera->framelock[camera->vid_mmap.frame]));
pthread_mutex_lock(&(camera->ioctlmutex));
if(ioctl(camera->device, VIDIOCMCAPTURE, &(camera->vid_mmap)) < 0)
{
fprintf(stderr, "icvVideoCaptureProc: ioctl VIDIOCMCAPTURE failed \n");
pthread_mutex_lock(&(camera->capturestatemutex));
camera->capturestate = FINISHED;
pthread_cond_signal(&(camera->capturestatecond));
pthread_mutex_unlock(&(camera->capturestatemutex));
}
if(ioctl(camera->device, VIDIOCSYNC, &(camera->vid_mmap.frame) ) < 0)
{
fprintf(stderr, "icvVideoCaptureProc: ioctl VIDIOCSYNC failed \n");
pthread_mutex_lock(&(camera->capturestatemutex));
camera->capturestate = FINISHED;
pthread_cond_signal(&(camera->capturestatecond));
pthread_mutex_unlock(&(camera->capturestatemutex));
}//if ioctl(..., VIDIOCSYNK, ...)
pthread_mutex_unlock(&(camera->ioctlmutex));
pthread_rwlock_unlock(&(camera->framelock[camera->vid_mmap.frame]));
pthread_mutex_lock(&(camera->lastframemutex));
camera->lastframe = camera->vid_mmap.frame;
pthread_mutex_unlock(&(camera->lastframemutex));
// if the camera is not rendered, call the callback myself
if (!camera->rendered && (camera->callback != NULL))
{
IplImage *image = icvVideoGetImage(cameraid);
if(image != NULL) {
camera->callback(image);
cvReleaseImage(&image);
} else {
fprintf(stderr, "icvVideoCaptureProc: icvVideoGetImage() returned NULL\n");
}
}
// signal that the rendering should be updated, since the image changed
if (camera->rendered)
{
pthread_mutex_lock(&(camera->updatedmutex));
if(camera->updated == 0)
{
pthread_cond_signal(&(camera->updatedcond));
camera->updated = 1;
}
pthread_mutex_unlock(&(camera->updatedmutex));
}
// stop here if we're paused
pthread_mutex_lock(&(camera->pausemutex));
pthread_mutex_unlock(&(camera->pausemutex));
pthread_mutex_lock(&(camera->capturestatemutex));
}
pthread_mutex_unlock(&(camera->capturestatemutex));
pthread_mutex_lock(&(camera->capturestatemutex));
camera->capturestate = FINISHED;
pthread_cond_signal(&(camera->capturestatecond));
pthread_mutex_unlock(&(camera->capturestatemutex));
pthread_exit(NULL);
}
////////////////////////////////////////////////////////////////////////////////
/* Frees all resources */
int cvcamExit()
{
int cameraid, frame;
#ifdef DEBUG_CVCAM
printf("cvcamExit(), ncameras = %d\n",ncameras);
#endif
cvcamStop();
for(cameraid=0; cameraid<ncameras; cameraid++) {
CvVideoCamera *const camera = &(cameras[cameraid]);
close(camera->device);
pthread_mutex_destroy(&(camera->ioctlmutex));
pthread_mutex_destroy(&(camera->pausemutex));
pthread_mutex_destroy(&(camera->capturestatemutex));
pthread_cond_destroy(&(camera->capturestatecond));
for(frame=0; frame< camera->mbuf.frames; frame++)
{
pthread_rwlock_destroy(&(camera->framelock[frame]));
}
free(camera->framelock);
pthread_mutex_destroy(&(camera->lastframemutex));
pthread_cond_destroy(&(camera->updatedcond));
pthread_mutex_destroy(&(camera->updatedmutex));
camera->initialised = 0;
}
free(cameras);
cameras = NULL;
ncameras = 0;
return 1;
}
////////////////////////////////////////////////////////////////////////////////
int icvVideoPauseCamera(int cameraid)
{
CvVideoCamera *const camera = &(cameras[cameraid]);
pthread_mutex_lock(&(camera->capturestatemutex));
if(!(camera->capturestate==CAPTURING))
{
pthread_mutex_unlock(&(camera->capturestatemutex));
return 1;
}
pthread_mutex_unlock(&(camera->capturestatemutex));
// taking this lock will stop grabbing
if(!camera->paused) {
pthread_mutex_lock(&(camera->pausemutex));
camera->paused = 1;
}
return 0;
}
////////////////////////////////////////////////////////////////////////////////
int icvVideoResumeCamera(int cameraid)
{
CvVideoCamera *const camera = &(cameras[cameraid]);
pthread_mutex_lock(&(camera->capturestatemutex));
if(!(camera->capturestate==CAPTURING))
{
pthread_mutex_unlock(&(camera->capturestatemutex));
return 1;
}
pthread_mutex_unlock(&(camera->capturestatemutex));
if(camera->paused) {
camera->paused = 0;
pthread_mutex_unlock(&(camera->pausemutex));
}
return 0;
}
////////////////////////////////////////////////////////////////////////////////
/* Pause the video; should be used for preventing data changes during frame reading
using "frame" and other properties */
int cvcamPause()
{
int i;
#ifdef DEBUG_CVCAM
printf("cvcamPause()\n");
#endif
for(i=0; i<ncameras; i++)
{
icvVideoPauseCamera(i);
}
return 0;
}
////////////////////////////////////////////////////////////////////////////////
/* Resume the video */
int cvcamResume()
{
int i;
#ifdef DEBUG_CVCAM
printf("cvcamResume()\n");
#endif
for(i=0; i<ncameras; i++)
{
icvVideoResumeCamera(i);
}
return 0;
}
////////////////////////////////////////////////////////////////////////////////
int icvVideoInit(int cameraid)
{
struct video_channel Channel;
struct video_capability VidCap;
CvVideoCamera *const camera = &(cameras[cameraid]);
#ifdef DEBUG_CVCAM
printf("icvVideoInit(%d)\n",cameraid);
#endif
char *rgbframe;
if(camera->initialised)
{
/*
fprintf(stderr, "icvVideoInit:camera %d is already "
"initialized\n",camera);*/
return 0;
}
if(camera->enabled)
{
pthread_mutex_lock(&(camera->ioctlmutex));
if(ioctl(camera->device,VIDIOCSPICT,
&(camera->videopp.picture) )==-1)
{
pthread_mutex_unlock(&(camera->ioctlmutex));
fprintf(stdout, "icvVideoInit: ioctl VIDIOCSPICT failed\n");
fprintf(stdout,"camera=%d,brightness=%d,hue=%d,colour=%d,contrast=%d,whiteness=%d,depth=%d,palette=%d\n",
camera,
camera->videopp.picture.brightness,
camera->videopp.picture.hue,
camera->videopp.picture.colour,
camera->videopp.picture.contrast,camera->videopp.picture.whiteness,camera->videopp.picture.depth,camera->videopp.picture.palette);
return 0;
}
pthread_mutex_unlock(&(camera->ioctlmutex));
Channel.norm = 1;
Channel.channel = camera->channel;
pthread_mutex_lock(&(camera->ioctlmutex));
if((ioctl(camera->device,VIDIOCSCHAN, &Channel) == -1)||
(ioctl(camera->device, VIDIOCGCAP, &VidCap)==-1))
{
fprintf(stderr,
"icvVideoInit: ioctl VIDIOCSCHAN or VIDIOCGCAP failed\n");
pthread_mutex_unlock(&(camera->ioctlmutex));
return 0;
}
pthread_mutex_unlock(&(camera->ioctlmutex));
pthread_mutex_lock(&(camera->ioctlmutex));
if(ioctl(camera->device, VIDIOCGMBUF,
&(camera->mbuf)) == -1)
{
pthread_mutex_unlock(&(camera->ioctlmutex));
fprintf(stdout, "icvVideoInit: ioctl VIDIOCGMBUF failed\n");
return 0;
}
pthread_mutex_unlock(&(camera->ioctlmutex));
pthread_mutex_lock(&(camera->ioctlmutex));
if(ioctl(camera->device,
VIDIOCSCHAN, &Channel)==-1)
{
fprintf(stderr, "icvVideoInit: couldn't set channel %d",
Channel.channel);
pthread_mutex_unlock(&(camera->ioctlmutex));
return 0;
}
pthread_mutex_unlock(&(camera->ioctlmutex));
camera->initialised = 1;
pthread_mutex_lock(&(camera->capturestatemutex));
camera->capturestate = READY;
pthread_cond_signal(&(camera->capturestatecond));
pthread_mutex_unlock(&(camera->capturestatemutex));
}//if(camera->IsEnabled)
return 1;
}
////////////////////////////////////////////////////////////
int icvVideoStop(int cameraid)
{
int i, frame;
CvVideoCamera *const camera = &(cameras[cameraid]);
#ifdef DEBUG_CVCAM
printf("icvVideoStop(%d)\n",cameraid);
#endif
pthread_mutex_lock(&(camera->capturestatemutex));
if(camera->capturestate != CAPTURING)
{
#ifdef DEBUG_CVCAM
printf("icvVideoStop: not capturing (state=%d), returning 0\n",camera->capturestate);
#endif
pthread_mutex_unlock(&(camera->capturestatemutex));
return 0;
}
camera->capturestate = STOPPING;
pthread_cond_signal(&(camera->capturestatecond));
pthread_mutex_unlock(&(camera->capturestatemutex));
if(camera->paused)
icvVideoResumeCamera(cameraid);
pthread_mutex_lock(&(camera->capturestatemutex));
// wait for the end of capture proc
while (camera->capturestate != FINISHED )
{
pthread_cond_wait(&(camera->capturestatecond),&(camera->capturestatemutex));
}
// wait for the end of rendering
while (camera->renderstate)
{
// the rendering loop may be waiting for an update
pthread_mutex_lock(&(camera->updatedmutex));
camera->updated = 1;
pthread_cond_signal(&(camera->updatedcond));
pthread_mutex_unlock(&(camera->updatedmutex));
pthread_cond_wait(&(camera->capturestatecond),&(camera->capturestatemutex));
}
pthread_mutex_unlock(&(camera->capturestatemutex));
munmap(camera->memorymap,
camera->mbuf.size);
pthread_mutex_lock(&(camera->capturestatemutex));
camera->capturestate = READY;
pthread_cond_signal(&(camera->capturestatecond));
pthread_mutex_unlock(&(camera->capturestatemutex));
#ifdef DEBUG_CVCAM
printf("icvVideoStop: returning 1\n",camera->capturestate);
#endif
return 1;
}
//////////////////////////////////////////////////////////////////
/* Stop the video */
int cvcamStop()
{
int camera;
#ifdef DEBUG_CVCAM
printf("cvcamStop()\n");
#endif
for(camera=0; camera<ncameras; camera++)
{
icvVideoStop(camera);
}//for(camera=0; camera<ncameras; camera++)
return 1;
}
////////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////////
int icvVideoFormat2Depth(int format)
{
switch (format)
{
case VIDEO_PALETTE_RGB24:
return 24;
case VIDEO_PALETTE_RGB32:
return 32;
case VIDEO_PALETTE_RGB565:
return 16;
case VIDEO_PALETTE_RGB555:
return 16;
default:
return 0;
}
}
////////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////////
int icvVideoSetDefaultValues(int cameraid, int device, int channel,
struct video_capability VidCap)
{
CvVideoCamera *const camera = &(cameras[cameraid]);
camera->device = device;
camera->channel = channel;
camera->description.channel = channel;
pthread_mutex_init(&(camera->ioctlmutex), NULL);
camera->enabled = 0;
camera->rendered = 0;
camera->initialised = 0;
camera->paused = 0;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -