📄 winvideo.c
字号:
}#ifdef AMD_HACK2void * v4w_thread(void *arg){ V4wState *s=(V4wState*)arg; MSG msg; ms_mutex_lock(&s->thread_lock); _v4w_start(s, NULL); ms_cond_signal(&s->thread_cond); ms_mutex_unlock(&s->thread_lock); while(s->thread_running) { BOOL fGotMessage; if((fGotMessage = PeekMessage(&msg, (HWND) s->capvideo, 0, 0, PM_REMOVE)) != 0) { TranslateMessage(&msg); DispatchMessage(&msg); } else Sleep(10); } ms_mutex_lock(&s->thread_lock); _v4w_stop(s, NULL); ms_cond_signal(&s->thread_cond); ms_mutex_unlock(&s->thread_lock); ms_thread_exit(NULL); return NULL;}static int v4w_start(MSFilter *f, void *arg){ V4wState *s=(V4wState*)f->data; s->thread_running=TRUE; ms_thread_create(&s->thread,NULL,v4w_thread,s); ms_mutex_lock(&s->thread_lock); ms_cond_wait(&s->thread_cond,&s->thread_lock); ms_mutex_unlock(&s->thread_lock); s->started=TRUE; return 0;}static int v4w_stop(MSFilter *f, void *arg){ V4wState *s=(V4wState*)f->data; ms_mutex_lock(&s->thread_lock); s->thread_running=FALSE; //SendMessage(s->capvideo, WM_CLOSE, 0, 0); ms_cond_wait(&s->thread_cond,&s->thread_lock); ms_mutex_unlock(&s->thread_lock); ms_thread_join(s->thread,NULL); s->started=FALSE; return 0;}#elsestatic int v4w_start(MSFilter *f, void *arg){ V4wState *s=(V4wState*)f->data; _v4w_start(s, NULL); s->started=TRUE; return 0;}static int v4w_stop(MSFilter *f, void *arg){ V4wState *s=(V4wState*)f->data; _v4w_stop(s, NULL); s->started=FALSE; return 0;}#endifstatic void v4w_uninit(MSFilter *f){ V4wState *s=(V4wState*)f->data; int idx; flushq(&s->rq,0); ms_mutex_destroy(&s->mutex); for (idx=0;idx<10;idx++) { if (s->mire[idx]==NULL) break; freemsg(s->mire[idx]); } if (s->capvideo!=NULL) { ms_message("v4w: destroying capture window"); DestroyWindow(s->capvideo); ms_message("v4w: capture window destroyed"); s->capvideo=NULL; } if (s->reverted){ freemsg(s->reverted); }#ifdef AMD_HACK2 ms_cond_destroy(&s->thread_cond); ms_mutex_destroy(&s->thread_lock);#endif ms_free(s);}static mblk_t * v4w_make_nowebcam(V4wState *s){ int idx; int count; if (s->mire[0]==NULL && s->frame_ind==0){ /* load several images to fake a movie */ for (idx=0;idx<10;idx++) { s->mire[idx]=ms_load_nowebcam(&s->vsize, idx); if (s->mire[idx]==NULL) break; } if (idx==0) s->mire[0]=ms_load_nowebcam(&s->vsize, -1); } for (count=0;count<10;count++) { if (s->mire[count]==NULL) break; } s->frame_ind++; if (count==0) return NULL; idx = s->frame_ind%count; if (s->mire[idx]!=NULL) return s->mire[idx]; return s->mire[0];}static void v4w_preprocess(MSFilter * obj){ V4wState *s=(V4wState*)obj->data; if (!s->started) { ms_message("V4W auto-started."); v4w_start(obj,NULL); s->autostarted=TRUE; } s->running=TRUE; if (s->capvideo==NULL) s->fps=1;}static void v4w_postprocess(MSFilter * obj){ V4wState *s=(V4wState*)obj->data; s->running=FALSE; if (s->autostarted){ v4w_stop(obj,NULL); }}static void v4w_process(MSFilter * obj){ V4wState *s=(V4wState*)obj->data; mblk_t *m; uint32_t timestamp; int cur_frame; if (s->frame_count==-1){ s->start_time=obj->ticker->time; s->frame_count=0; } cur_frame=((obj->ticker->time-s->start_time)*s->fps/1000.0); if (cur_frame>s->frame_count){ mblk_t *om=NULL; ms_mutex_lock(&s->mutex); /*keep the most recent frame if several frames have been captured */ if (s->capvideo!=NULL){ while((m=getq(&s->rq))!=NULL){ if (om!=NULL) freemsg(om); om=m; } if (om!=NULL){ if (s->invert_rgb){ MSVideoSize roi; if (s->reverted==NULL){ s->reverted=allocb(om->b_wptr-om->b_rptr,0); s->reverted->b_wptr=s->reverted->b_datap->db_lim; } roi=s->vsize; rgb24_copy_revert(s->reverted->b_rptr,roi.width*3, om->b_rptr,roi.width*3,roi); freemsg(om); om=dupb(s->reverted); } } }else { mblk_t *nowebcam = v4w_make_nowebcam(s); if (nowebcam!=NULL){ om=dupmsg(nowebcam); mblk_set_precious_flag(om,1); } } ms_mutex_unlock(&s->mutex); if (om!=NULL){ timestamp=obj->ticker->time*90;/* rtp uses a 90000 Hz clockrate for video*/ mblk_set_timestamp_info(om,timestamp); ms_queue_put(obj->outputs[0],om); } s->frame_count++; }}static int v4w_set_fps(MSFilter *f, void *arg){ V4wState *s=(V4wState*)f->data; s->fps=*((float*)arg); return 0;}static int v4w_get_pix_fmt(MSFilter *f,void *arg){ V4wState *s=(V4wState*)f->data; if (!s->started) { ms_message("V4W auto-started in v4w_get_pix_fmt()"); v4w_start(f,NULL); s->autostarted=TRUE; } *((MSPixFmt*)arg) = (MSPixFmt)s->pix_fmt; return 0;}static int v4w_set_vsize(MSFilter *f, void *arg){ V4wState *s=(V4wState*)f->data; s->vsize=*((MSVideoSize*)arg); return 0;}static int v4w_get_vsize(MSFilter *f, void *arg){ V4wState *s=(V4wState*)f->data; MSVideoSize *vs=(MSVideoSize*)arg; vs->width=s->vsize.width; vs->height=s->vsize.height; return 0;}static MSFilterMethod methods[]={ { MS_FILTER_SET_FPS , v4w_set_fps }, { MS_FILTER_GET_PIX_FMT , v4w_get_pix_fmt }, { MS_FILTER_SET_VIDEO_SIZE, v4w_set_vsize }, { MS_FILTER_GET_VIDEO_SIZE, v4w_get_vsize }, { MS_V4L_START , v4w_start }, { MS_V4L_STOP , v4w_stop }, { 0 , NULL }};#ifdef _MSC_VERMSFilterDesc ms_v4w_desc={ MS_V4L_ID, "MSV4w", "A video4windows compatible source filter to stream pictures.", MS_FILTER_OTHER, NULL, 0, 1, v4w_init, v4w_preprocess, v4w_process, v4w_postprocess, v4w_uninit, methods};#elseMSFilterDesc ms_v4w_desc={ .id=MS_V4L_ID, .name="MSV4w", .text="A video4windows compatible source filter to stream pictures.", .ninputs=0, .noutputs=1, .category=MS_FILTER_OTHER, .init=v4w_init, .preprocess=v4w_preprocess, .process=v4w_process, .postprocess=v4w_postprocess, .uninit=v4w_uninit, .methods=methods};#endifMS_FILTER_DESC_EXPORT(ms_v4w_desc)static void ms_v4w_detect(MSWebCamManager *obj);static void ms_v4w_cam_init(MSWebCam *cam){}static MSFilter *ms_v4w_create_reader(MSWebCam *obj){ MSFilter *f= ms_filter_new_from_desc(&ms_v4w_desc); V4wState *s=(V4wState*)f->data; s->devidx=(int)obj->data; return f;}MSWebCamDesc ms_v4w_cam_desc={ "VideoForWindows grabber", &ms_v4w_detect, &ms_v4w_cam_init, &ms_v4w_create_reader, NULL};static void ms_v4w_detect(MSWebCamManager *obj){ int i; char dev[80]; char ver[80]; char name[160]; MSWebCam *cam; for (i = 0; i < 9; i++){ if (capGetDriverDescription(i, dev, sizeof (dev), ver, sizeof (ver))){ HWND hwnd=capCreateCaptureWindow("Capture Window",WS_CHILD /* WS_OVERLAPPED */ ,0,0,352,288,HWND_MESSAGE, 0) ; if (hwnd==NULL) break; if(!capDriverConnect(hwnd,i )){ ms_warning("v4w: could not connect to capture driver, no webcam connected."); DestroyWindow(hwnd); break; }else{ capDriverDisconnect(hwnd); DestroyWindow(hwnd); } capGetDriverDescription(i, dev, sizeof (dev),ver, sizeof (ver)); snprintf(name, sizeof(name), "%s/%s",dev,ver); cam=ms_web_cam_new(&ms_v4w_cam_desc); cam->data=(void*)i;/*store the device index */ cam->name=ms_strdup(name); ms_web_cam_manager_add_cam(obj,cam); } }}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -