📄 v4l.c
字号:
memcpy( p_sys->p_header, ".v4l", 4 ); if( p_sys->fd_video >= 0 ) { p_sys->i_header_size += 20; p_sys->p_header = realloc( p_sys->p_header, p_sys->i_header_size ); SetDWBE( &p_sys->p_header[4], ++p_sys->i_streams ); memcpy( &p_sys->p_header[p_sys->i_header_pos], "vids", 4 ); memcpy( &p_sys->p_header[p_sys->i_header_pos+4], &p_sys->i_fourcc, 4 ); SetDWBE( &p_sys->p_header[p_sys->i_header_pos+8], p_sys->i_width ); SetDWBE( &p_sys->p_header[p_sys->i_header_pos+12], p_sys->i_height ); SetDWBE( &p_sys->p_header[p_sys->i_header_pos+16], 0 ); p_sys->i_header_pos = p_sys->i_header_size; } if( p_sys->fd_audio >= 0 ) { p_sys->i_header_size += 20; p_sys->p_header = realloc( p_sys->p_header, p_sys->i_header_size ); SetDWBE( &p_sys->p_header[4], ++p_sys->i_streams ); memcpy( &p_sys->p_header[p_sys->i_header_pos], "auds", 4 ); memcpy( &p_sys->p_header[p_sys->i_header_pos+4], "araw", 4 ); SetDWBE( &p_sys->p_header[p_sys->i_header_pos+8], p_sys->b_stereo ? 2 : 1 ); SetDWBE( &p_sys->p_header[p_sys->i_header_pos+12], p_sys->i_sample_rate ); SetDWBE( &p_sys->p_header[p_sys->i_header_pos+16], 16 ); p_sys->i_header_pos = p_sys->i_header_size; } p_sys->i_header_pos = 0; return VLC_SUCCESS;}/***************************************************************************** * ParseMRL: parse the options contained in the MRL *****************************************************************************/static void ParseMRL( input_thread_t *p_input ){ access_sys_t *p_sys = p_input->p_access_data; char *psz_dup = strdup( p_input->psz_name ); char *psz_parser = psz_dup; while( *psz_parser && *psz_parser != ':' ) { psz_parser++; } if( *psz_parser == ':' ) { /* read options */ for( ;; ) { *psz_parser++ = '\0'; if( !strncmp( psz_parser, "channel=", strlen( "channel=" ) ) ) { p_sys->i_channel = strtol( psz_parser + strlen( "channel=" ), &psz_parser, 0 ); } else if( !strncmp( psz_parser, "norm=", strlen( "norm=" ) ) ) { psz_parser += strlen( "norm=" ); if( !strncmp( psz_parser, "pal", strlen( "pal" ) ) ) { p_sys->i_norm = VIDEO_MODE_PAL; psz_parser += strlen( "pal" ); } else if( !strncmp( psz_parser, "ntsc", strlen( "ntsc" ) ) ) { p_sys->i_norm = VIDEO_MODE_NTSC; psz_parser += strlen( "ntsc" ); } else if( !strncmp( psz_parser, "secam", strlen( "secam" ) ) ) { p_sys->i_norm = VIDEO_MODE_SECAM; psz_parser += strlen( "secam" ); } else if( !strncmp( psz_parser, "auto", strlen( "auto" ) ) ) { p_sys->i_norm = VIDEO_MODE_AUTO; psz_parser += strlen( "auto" ); } else { p_sys->i_norm = strtol( psz_parser, &psz_parser, 0 ); } } else if( !strncmp( psz_parser, "frequency=", strlen( "frequency=" ) ) ) { p_sys->i_frequency = strtol( psz_parser + strlen( "frequency=" ), &psz_parser, 0 ); if( p_sys->i_frequency < 30000 ) { msg_Warn( p_input, "v4l syntax has changed : " "'frequency' is now channel frequency in kHz"); } } else if( !strncmp( psz_parser, "audio=", strlen( "audio=" ) ) ) { p_sys->i_audio = strtol( psz_parser + strlen( "audio=" ), &psz_parser, 0 ); } else if( !strncmp( psz_parser, "size=", strlen( "size=" ) ) ) { psz_parser += strlen( "size=" ); if( !strncmp( psz_parser, "subqcif", strlen( "subqcif" ) ) ) { p_sys->i_width = 128; p_sys->i_height = 96; } else if( !strncmp( psz_parser, "qsif", strlen( "qsif" ) ) ) { p_sys->i_width = 160; p_sys->i_height = 120; } else if( !strncmp( psz_parser, "qcif", strlen( "qcif" ) ) ) { p_sys->i_width = 176; p_sys->i_height = 144; } else if( !strncmp( psz_parser, "sif", strlen( "sif" ) ) ) { p_sys->i_width = 320; p_sys->i_height = 244; } else if( !strncmp( psz_parser, "cif", strlen( "cif" ) ) ) { p_sys->i_width = 352; p_sys->i_height = 288; } else if( !strncmp( psz_parser, "vga", strlen( "vga" ) ) ) { p_sys->i_width = 640; p_sys->i_height = 480; } else { /* widthxheight */ p_sys->i_width = strtol( psz_parser, &psz_parser, 0 ); if( *psz_parser == 'x' || *psz_parser == 'X') { p_sys->i_height = strtol( psz_parser + 1, &psz_parser, 0 ); } msg_Dbg( p_input, "WxH %dx%d", p_sys->i_width, p_sys->i_height ); } } else if( !strncmp( psz_parser, "brightness=", strlen( "brightness=" ) ) ) { p_sys->i_brightness = strtol( psz_parser + strlen( "brightness=" ), &psz_parser, 0 ); } else if( !strncmp( psz_parser, "colour=", strlen( "colour=" ) ) ) { p_sys->i_colour = strtol( psz_parser + strlen( "colour=" ), &psz_parser, 0 ); } else if( !strncmp( psz_parser, "hue=", strlen( "hue=" ) ) ) { p_sys->i_hue = strtol( psz_parser + strlen( "hue=" ), &psz_parser, 0 ); } else if( !strncmp( psz_parser, "contrast=", strlen( "contrast=" ) ) ) { p_sys->i_contrast = strtol( psz_parser + strlen( "contrast=" ), &psz_parser, 0 ); } else if( !strncmp( psz_parser, "tuner=", strlen( "tuner=" ) ) ) { p_sys->i_tuner = strtol( psz_parser + strlen( "tuner=" ), &psz_parser, 0 ); } else if( !strncmp( psz_parser, "adev=", strlen( "adev=" ) ) ) { int i_len; psz_parser += strlen( "adev=" ); if( strchr( psz_parser, ':' ) ) { i_len = strchr( psz_parser, ':' ) - psz_parser; } else { i_len = strlen( psz_parser ); } p_sys->psz_adev = strndup( psz_parser, i_len ); psz_parser += i_len; } else if( !strncmp( psz_parser, "samplerate=", strlen( "samplerate=" ) ) ) { p_sys->i_sample_rate = strtol( psz_parser + strlen( "samplerate=" ), &psz_parser, 0 ); } else if( !strncmp( psz_parser, "stereo", strlen( "stereo" ) ) ) { psz_parser += strlen( "stereo" ); p_sys->b_stereo = VLC_TRUE; } else if( !strncmp( psz_parser, "mono", strlen( "mono" ) ) ) { psz_parser += strlen( "mono" ); p_sys->b_stereo = VLC_FALSE; } else if( !strncmp( psz_parser, "mjpeg", strlen( "mjpeg" ) ) ) { psz_parser += strlen( "mjpeg" ); p_sys->b_mjpeg = VLC_TRUE; } else if( !strncmp( psz_parser, "decimation=", strlen( "decimation=" ) ) ) { p_sys->i_decimation = strtol( psz_parser + strlen( "decimation=" ), &psz_parser, 0 ); } else if( !strncmp( psz_parser, "quality=", strlen( "quality=" ) ) ) { p_sys->i_quality = strtol( psz_parser + strlen( "quality=" ), &psz_parser, 0 ); } else if( !strncmp( psz_parser, "fps=", strlen( "fps=" ) ) ) { p_sys->f_fps = strtof( psz_parser + strlen( "fps=" ), &psz_parser ); } else { msg_Warn( p_input, "unknown option" ); } while( *psz_parser && *psz_parser != ':' ) { psz_parser++; } if( *psz_parser == '\0' ) { break; } } } if( *psz_dup ) { p_sys->psz_device = strdup( psz_dup ); } if( psz_dup ) free( psz_dup );}/***************************************************************************** * OpenVideoDev: *****************************************************************************/int OpenVideoDev( input_thread_t *p_input, char *psz_device ){ access_sys_t *p_sys = p_input->p_access_data; int i_fd; struct video_channel vid_channel; struct mjpeg_params mjpeg; int i; if( ( i_fd = open( psz_device, O_RDWR ) ) < 0 ) { msg_Err( p_input, "cannot open device (%s)", strerror( errno ) ); goto vdev_failed; } if( ioctl( i_fd, VIDIOCGCAP, &p_sys->vid_cap ) < 0 ) { msg_Err( p_input, "cannot get capabilities (%s)", strerror( errno ) ); goto vdev_failed; } msg_Dbg( p_input, "V4L device %s %d channels %d audios %d < w < %d %d < h < %d", p_sys->vid_cap.name, p_sys->vid_cap.channels, p_sys->vid_cap.audios, p_sys->vid_cap.minwidth, p_sys->vid_cap.maxwidth, p_sys->vid_cap.minheight, p_sys->vid_cap.maxheight ); if( p_sys->i_channel < 0 || p_sys->i_channel >= p_sys->vid_cap.channels ) { msg_Dbg( p_input, "invalid channel, falling back on channel 0" ); p_sys->i_channel = 0; } if( p_sys->i_audio >= p_sys->vid_cap.audios ) { msg_Dbg( p_input, "invalid audio, falling back with no audio" ); p_sys->i_audio = -1; } if( p_sys->i_width < p_sys->vid_cap.minwidth || p_sys->i_width > p_sys->vid_cap.maxwidth ) { msg_Dbg( p_input, "invalid width %i", p_sys->i_width ); p_sys->i_width = 0; } if( p_sys->i_height < p_sys->vid_cap.minheight || p_sys->i_height > p_sys->vid_cap.maxheight ) { msg_Dbg( p_input, "invalid height %i", p_sys->i_height ); p_sys->i_height = 0; } if( !( p_sys->vid_cap.type & VID_TYPE_CAPTURE ) ) { msg_Err( p_input, "cannot grab" ); goto vdev_failed; } vid_channel.channel = p_sys->i_channel; if( ioctl( i_fd, VIDIOCGCHAN, &vid_channel ) < 0 ) { msg_Err( p_input, "cannot get channel infos (%s)", strerror( errno ) ); goto vdev_failed; } msg_Dbg( p_input, "setting channel %s(%d) %d tuners flags=0x%x type=0x%x norm=0x%x", vid_channel.name, vid_channel.channel, vid_channel.tuners, vid_channel.flags, vid_channel.type, vid_channel.norm ); if( p_sys->i_tuner >= vid_channel.tuners ) { msg_Dbg( p_input, "invalid tuner, falling back on tuner 0" ); p_sys->i_tuner = 0; } vid_channel.norm = p_sys->i_norm; if( ioctl( i_fd, VIDIOCSCHAN, &vid_channel ) < 0 ) { msg_Err( p_input, "cannot set channel (%s)", strerror( errno ) ); goto vdev_failed; } if( vid_channel.flags & VIDEO_VC_TUNER ) { /* set tuner */#if 0 struct video_tuner vid_tuner; if( p_sys->i_tuner >= 0 ) { vid_tuner.tuner = p_sys->i_tuner; if( ioctl( i_fd, VIDIOCGTUNER, &vid_tuner ) < 0 ) { msg_Err( p_input, "cannot get tuner (%s)", strerror( errno ) ); goto vdev_failed; } msg_Dbg( p_input, "tuner %s low=%d high=%d, flags=0x%x " "mode=0x%x signal=0x%x", vid_tuner.name, vid_tuner.rangelow, vid_tuner.rangehigh, vid_tuner.flags, vid_tuner.mode, vid_tuner.signal ); msg_Dbg( p_input, "setting tuner %s (%d)", vid_tuner.name, vid_tuner.tuner ); /* FIXME FIXME to be checked FIXME FIXME */ //vid_tuner.mode = p_sys->i_norm; if( ioctl( i_fd, VIDIOCSTUNER, &vid_tuner ) < 0 ) { msg_Err( p_input, "cannot set tuner (%s)", strerror( errno ) ); goto vdev_failed; } }#endif /* Show a warning if frequency is < than 30000. * User is certainly usint old syntax. */ /* set frequency */ if( p_sys->i_frequency >= 0 ) { int driver_frequency = p_sys->i_frequency * 16 /1000; if( ioctl( i_fd, VIDIOCSFREQ, &driver_frequency ) < 0 ) { msg_Err( p_input, "cannot set frequency (%s)", strerror( errno ) ); goto vdev_failed; } msg_Dbg( p_input, "frequency %d (%d)", p_sys->i_frequency, driver_frequency ); } } /* set audio */ if( vid_channel.flags & VIDEO_VC_AUDIO ) { struct video_audio vid_audio; /* XXX TODO volume, balance, ... */ if( p_sys->i_audio >= 0 ) { vid_audio.audio = p_sys->i_audio; if( ioctl( i_fd, VIDIOCGAUDIO, &vid_audio ) < 0 ) { msg_Err( p_input, "cannot get audio (%s)", strerror( errno ) ); goto vdev_failed; } /* unmute audio */ vid_audio.flags &= ~VIDEO_AUDIO_MUTE;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -