一、多媒体设备
多媒体设备是指本机中的音频输入设备(如麦克风)、音频输出设备(如音箱、头戴耳机)和视频输入设备(如摄像头)。多媒体设备通过 QMediaDevices 类提供的方法来获取,音频输入输出设备类是 QAudioDevice,视频输入设备类是 QCameraDevice。
我们可以在终端中使用 pip 安装 pyside6 模块。
pip install pyside6
用 QMediaDevices、QAudioDevice 和 QCameraDevice 创建设备实例的方法如下所示。
QMediaDevices(parent:QObject=None)
QAudioDevice()
QCameraDevice()
QMediaDevices 类的常用方法如下:
# 静态方法
audioInputs() -> List[QAudioDevice] # 获取音频输入设备
defaultAudioInput() -> QAudioDevice # 获取默认音频输入设备audioOutputs() -> List[QAudioDevice] # 获取音频输出设备
defaultAudioOutput() -> QAudioDevice # 获取默认音频输出设备videoInputs() -> List[QCameraDevice] # 获取视频输入设备
defaultVideoInput() -> QCameraDevice # 获取默认的视频输入设备
QMediaDevices 类的信号方法如下:
audioInputsChanged() # 当音频输入设备发生改变时发射信号
audioOutputsChanged() # 当音频输出设备发生改变时发射信号
videoInputsChanged() # 当视频输入设备发生改变时发射信号
QAudioDevice 类的常用方法如下:
description() -> str # 获取音频设备的信息
id() -> QQByteArray # 获取音频设备的识别号
isDefault() -> bool # 获取是否是默认的音频设备
isFormatSupported(format:QAudioFormat) -> bool # 获取音频设备是否支持某种音频格式
isNull() -> bool # 获取设备是否有效
minimumChannelCount() -> int # 获取音频设备支持的最小通道数
maximumChannelCount() -> int # 获取音频设备支持的最大通道数
minimumSampleRate() -> int # 获取音频设备支持的最小采样率
maximumSampleRate() -> int # 获取音频设备支持的最大采样率
mode() -> QAudioDevice.Mode # 获取音频设备是输入还是输出设备
preferredFormat() -> QAudioFormat # 获取音频设备的默认音频格式
supportedSampleFormats() -> List[QAudioFormat.SampleFormat] # 获取音频设备支持的采样格式
mode()
的方法获取音频设备是输入还是输出设备,返回值是 QAudioDevice.Mode 枚举值,返回的值可以是:
QAudioDevice.Mode.Null # 无效设备
QAudioDevice.Mode.Input # 输入设备
QAudioDevice.Mode.Output # 输出设备
supportedSampleFormats()
方法获取音频设备支持的采样格式,返回值是 QAudioFormat.SampleFormat 的列表,QAudioFormat.SampleFormat 枚举值如下:
QAudioFormat.SampleFormat.UInt8
QAudioFormat.SampleFormat.Int16
QAudioFormat.SampleFormat.Int32
QAudioFormat.SampleFormat.Float
QAudioFormat.SampleFormat.Unknown
QCameraDevice 类的常用方法如下:
description() -> str # 获取视频输入设备的信息
id() -> QQByteArray # 获取视频输入设备的识别号
isDefault() -> bool # 获取是否是默认的视频输入设备
isNull() -> bool # 获取视频输入设备是否有效
photoResolutions() -> List[QSize] # 获取视频输入设备的分辨率
position() -> QCameraDevice.Position # 获取视频输入的位置
videoFormats() -> List[QCameraFormat] # 获取视频输入设备支持的格式
position()
方法获取视频输入的位置,返回值是 QCameraDevice.Position 枚举值,返回值可以是:
QCameraDevice.Position.BackFace # 后置摄像头
QCameraDevice.Position.FrontFace # 前置摄像头
QCameraDevice.Position.UnspecifiedPosition # 位置不确定
二、音频接口与视频接口
要录制音频和视频,需要定义音频设备的接口 QAudioInput 和视频设备的接口 QCamera 后,才能调用音频设备和视频设备进行录制,QAudioInput 和 QCamera 相当于音频和视频输入通道。QAudioInput 是机器上的音频输入,例如内置麦克风或头戴麦克风,而 QCamera 是机器上的摄像头或外接相机。
利用 QAudioInput 和 QCamera 创建音频设备和视频设备接口的方法如下所示。
QAudioInput(parent:QObject=None)
QAudioInput(deviceInfo:QAudioDevice, parent:QObject=None)QCamera(parent:QObject=None)
QCamera(position:QCameraDevice.Position, parent:QObject=None)
2.1、音频接口
音频接口 QAudioInput 类的常用方法如下:
# 实例方法
device() -> QAudioDeicve # 获取音频设备
isMuted() -> bool # 获取是否静音
volume() -> bool # 获取音量# 槽函数
setDevice(device:QAudioDevice) -> None # 设置音频设备
setMuted(muted:bool) -> None # 设置是否静音
setVolume(volume:float) -> float # 设置音量
音频接口 QAudioInput 类的常用信号如下:
deviceChanged() # 当设备发生改变时发射信号
mutedChanged(muted:bool) # 当静音状态发生改变时发射信号
volumeChanged(volume:float) # 当音量发生改变时发射信号
2.2、视频接口
视频接口 QCamera 类的常用方法如下:
# 实例方法
setCameraDevice(cameraDevice:QCameraaDevice) -> None # 设置视频设备
cameraDevice() -> QCameraDevice # 获取视频设备isActive() -> bool # 获取相机是否启用
isAvailable() -> bool # 获取相机是否可用setCameraFormat(format:QCameraFormat) -> None # 设置视频格式
captureSession() -> QMediaCaptureSession # 获取与QCamera关联的媒体捕获器
supportedFeatures() -> QCamera.Features # 获取支持的特征isExposureModeSupported(mode:QCamera.ExposureMode) -> None # 获取是否支持某种曝光
exposureTime() -> float # 获取曝光时间
manualExposureTime() -> float -> float # 获取自定义曝光时间
isoSensitivity() -> int # 获取光敏感值
exposureCompensation() -> float # 获取曝光补偿(EV值) flashMode() -> QCamera.FlashMode # 获取快闪模式
isFlashModeSupported(mode:QCamera.FlashMode) -> bool # 获取是否支持某种快闪模式
isFlashReady() -> bool # 获取是否可以用快闪setFocusMode(mode:QCamera.FocusMode) -> None # 设置对焦模式
isFlashModeSupported(mode:QCamera.FocusMode) -> bool # 获取是否支持某种焦点模式
setFocusDistance(d:float) -> None # 设置自定义焦距,0表示最近的点,1表示无限远
focusDistance() -> float # 获取自定义焦距
setCustomFocusPoint(point:Union[QPoint, QPointF]) -> None # 设置自定义焦点位置
customFocusPoint() -> QPointF # 获取自定义焦点
focusPoint() -> QPointF # 获取焦点torchMode() -> QCamera.TorchMode # 获取辅助光源模式
isTorchModeSupported(mode:QCamera.TorchMode) -> bool # 获取是否支持某种辅助光源模式whiteBalanceMode() -> QCamera.WhiteBalanceMode # 获取白平衡模式
isWhiteBalanceModeSupported(mode:QCamera.WhiteBalanceMode) -> bool # 获取是否支持某种白平衡模式 colorTemperature() -> int # 获取颜色温度setZoomFactor(factor:float) -> None # 设置缩放系数
zoomFactor() -> float # 获取缩放系数minimumExposureTime() -> float # 获取最小的曝光时间
maximumExposureTime() -> float # 获取最大的曝光时间minimumIsoSensitivity() -> int # 获取最小的光敏感值
maximumIsoSensitivity() -> int # 获取最大的光敏感值minimumZoomFactor() -> float # 获取最小的方法系数
maximumZoomFactor() -> float # 获取最大的放大系数error() -> QCamera.Error # 获取出错类型
errorString() -> str # 获取出错信息# 槽函数
start() -> None # 开启相机
stop() -> None # 关闭相机
setActive(active:bool) -> None # 获取相机是否启用setExposureMode(mode:QCamera.ExposureMode) -> None # 设置曝光模式
setAutoExposureTime() -> None # 打开自动计算曝光时间
setManualExposureTime(seconds:float) -> None # 设置曝光时间
setAutoIsoSensitivity() -> None # 根据曝光值开启自动选择光敏感值
setExposureCompensation(ev:float) -> None # 设置曝光补偿(EV值)setFlashMode(mode:QCamera.FlashMode) -> bool # 设置是否可以用快闪
setTorchMode(mode:QCamera.TorchMode) -> None # 设置辅助光源模式
setWhiteBalanceMode(mode:QCamera.WhiteBalanceMode) -> None # 设置白平衡模式setColorTemperature(colorTemperature:int) -> None # 设置颜色温度zoomTo(zoom:float, rate:float) -> None # 根据速率设置缩放系数
用 setCameraDevice(cameraDevice:QCameraDevice)
方法为视频接口设置视频设备;用 start()
方法或 setActive(true)
方法开启视频设备;用 stop()
方法或 setActive(false)
方法停止视频设备。
用 supportedFeatures()
方法获取相机支持的特征,返回值如下所示。
QCamera.Feature.ColorTemperature # 相机支持色温
QCamera.Feature.ExposureCompensation # 相机支持补偿曝光
QCamera.Feature.IsoSensitivity # 相机支持自定义敏感值
QCamera.Feature.ManualExposureTime # 相机支持自定义曝光时间
QCamera.Feature.CustomFocusPoint # 相机支持自定义焦点
QCamera.Feature.FocusDistance # 相机支持自定义焦距
用 setExposureMode(mode:QCamera.ExposureMode)
方法设置相机的曝光模式,参数 mode 的取值是 QCamera.ExposureMode 的枚举值,可取的值如下所示;
QCamera.ExposureMode.ExposureAuto # 自动
QCamera.ExposureMode.ExposureManual # 手动
QCamera.ExposureMode.ExposurePortrait # 人物
QCamera.ExposureMode.ExposureNight # 夜晚
QCamera.ExposureMode.ExposureSports # 运动
QCamera.ExposureMode.ExposureSnow # 雪景
QCamera.ExposureMode.ExposureBeach # 海景
QCamera.ExposureMode.ExposureAction # 动作
QCamera.ExposureMode.ExposureLandscape # 风景
QCamera.ExposureMode.ExposureNightPortrait # 夜晚
QCamera.ExposureMode.ExposureTheatre # 剧院
QCamera.ExposureMode.ExposureSunset # 傍晚
QCamera.ExposureMode.ExposureSteadyPhoto # 固定
QCamera.ExposureMode.ExposureFireworks # 火景
QCamera.ExposureMode.ExposureParty # 宴会
QCamera.ExposureMode.ExposureCandlelight # 烛光
QCamera.ExposureMode.ExposureBarcode # 条码
用 setFlashMode(mode:QCamera.FlashMode)
方法设置相机的快闪模式,参数 mode 的取值是 QCamera.FlashMode 的枚举值,可取值如下:
QCamera.FlashMode.FlashOff
QCamera.FlashMode.FlashOn
QCamera.FlashMode.FlashAuto
用 setFocusMode(mode:QCamera.FocusMode)
方法设置对焦模式,参数 mode 的取值是 QCamera.FocusMode 的枚举值,可取的值如下所示。
QCamera.FocusMode.FocusModeAuto # 连续自动对焦模式
QCamera.FocusMode.FocusModeAutoNear # 对近处物体连续自动对焦模式
QCamera.FocusMode.FocusModeAutoFar # 对远处物体连续自动对焦模式
QCamera.FocusMode.FocusModeHyperfocal # 对超过焦距范围的物体采用最大景深值
QCamera.FocusMode.FocusModeInfinity # 对无限远对焦模式
QCamera.FocusMode.FocusModeManual # 手动或固定对焦模式
用 setTorchMode(mode:QCamera.TorchMode)
方法设置辅助光源模式,在光线不强时可以设置该模式,并会覆盖快闪模式,参数 mode 可取值如下:
QCamera.TorchMode.TorchOff
QCamera.TorchMode.TorchOn
QCamera.TorchMode.TorchAuto
用 setWhiteBalanceMode(mode:QCamera.WhiteBalanceMode)
方法设置白平衡模式,白平衡是描述红、绿、蓝三基色混合生成后白色精确度的一项指标。在房间里的日光灯下拍摄的影像会显得发绿,在室内钨丝灯光下拍摄出来的景物会偏黄,而在日光阴影处拍摄到的照片则偏蓝,白平衡的作用是不管在任何光源下都能将白色物体还原为白色。参数 mode 是 QCamera.WhiteBalanceMode 的枚举值,可取的值如下所示。
QCamera.WhiteBalanceMode.WhiteBalanceAuto # 自动
QCamera.WhiteBalanceMode.WhiteBalanceManual # 手动
QCamera.WhiteBalanceMode.WhiteBalanceShade # 阴影
QCamera.WhiteBalanceMode.WhiteBalanceTungsten # 钨灯
QCamera.WhiteBalanceMode.WhiteBalanceFluorescent # 荧光灯
QCamera.WhiteBalanceMode.WhiteBalanceSunlight # 阳光
QCamera.WhiteBalanceMode.WhiteBalanceCloudy # 云
QCamera.WhiteBalanceMode.WhiteBalanceFlash # 快闪
QCamera.WhiteBalanceMode.WhiteBalanceSunset # 日落
在手动模式下,需要用 setColorTemperature(colorTemperature:int)
方法设置色温。
视频接口 QCamera 类的常用信号如下:
activeChanged(arg__1:bool) # 照相机启动或停止时发射信号
cameraDeviceChanged() # 照相设备发生改变时发射信号
cameraFormatChanged() # 格式发生改变时发射信号focusModeChanged() # 焦点模式发生改变时发射信号
focusDistanceChanged(d:float) # 焦距发生改变时发射信号
focusPointChanged() # 聚焦点发生改变时发射信号
customFocusPointChanged() # 自定义聚焦点发生改变时发射信号exposureModeChanged() # 曝光模式发生改变时发射信号
exposureCompensationChanged(value:float) # 曝光补偿发生改变时发射信号
exposureTimeChanged(speed:float) # 曝光时间发生改变时发射信号
manualExposureTimeChanged(speed:float) # 自动曝光时间发生改变时发射信号flashModeChanged() # 快闪模式发生改变时发射信号
flashReady(ready:bool) # 可以快闪时发射信号isoSensitivityChanged(value:int) # 光敏感值发生改变时发射信号
manualIsoSensitivityChanged(value:int) # 自定义光敏感值发生改变时发射信号minimumZoomFactorChanged(value:float) # 最小缩放系数发生改变时发射信号
maximumZoomFactorChanged(value:float) # 最大缩放系数发生改变时发射信号
zoomFactorChanged(value:int) # 缩放系数发生改变时发射信号saturationChanged()
supportedFeaturesChanged() # 支持的功能发生改变时发射信号
torchModeChanged() # 辅助光源模式发生改变时发射信号
whiteBalanceModeChanged() # 白平衡模式发生改变时发射信号
colorTemperatureChanged() # 色温发生改变时发射信号errorChanged() # 错误状态发生改变时发射信号
errorOccurred(error:QCamera.Error, errorString:str) # 出现错误时发射信号
三、媒体捕获器
媒体捕获器 QMediaCaptureSession 是音频数据和视频数据的集散地,它接收从 QAudioInput 和 QCamera 传递过来的音频和视频,然后将音频转发给 QAudioOutput 播放音频,将视频转发给 QVideoWidegt 或 QGraphicsVideoItem 播放视频,或者将音频和视频转发给 QMdiaRecorder 录制音频和视频,转发给 QImageCapture 实现拍照功能。
用 QMediaCaptureSession 创建实例对象的方法如下所示。
QMediaCaptureSession(parent:QObject=None)
QMediaCaptureSession 类的常用方法如下:
setAudioInput(input:QAudioInput) -> None # 设置音频输入
audioInput() -> QAudioInput # 获取音频输入
setAudioOutput(output:QAudioOutput) -> None # 设置音频输出
audioOutput() -> QAudioOutput # 获取音频输出setCamera(camera:QCamera) -> None # 设置视频接口
camera() -> QCamera # 获取视频接口setVideoOutput(output:QObject) -> None # 设置视频输出
videoOutput() -> QObject # 获取视频输出
setVideoSink(sink:QVideoSink) -> None # 设置视频接收器
videoSink() -> QVideoSink # 获取视频接收器setImageCapture(imageCapture:QImageCapture) -> None # 设置图像捕获器
imageCapture() -> QImageCapture # 获取图像捕获器setRecorder(recorder:QMidiaRecorder) -> None # 设置媒体记录器
recorder() -> QMeidaRecorder # 获取媒体记录器
QMediaCaptureSession 类的常用信号如下:
audioInputChanged() # 当音频输入发生改变时发射信号
audioOutputChanged() # 当视频输出发生改变时发射信号
cameraChanged() # 当视频输入发生改变时发射信号
videoOutputChanged() # 当视频输出发生改变时发射信号imageCaptureChanged() # 当图像捕获器发生改变时发射信号
screenCaptureChanged() # 当屏幕捕获器发生改变时发射信号
windowCaptureChanged() # 当窗口捕获器发生改变时发射信号recorderChanged() # 当记录器发生改变时发射信号
import sysfrom PySide6.QtWidgets import QApplication, QWidget
from PySide6.QtWidgets import QPushButton
from PySide6.QtWidgets import QVBoxLayout, QHBoxLayout
from PySide6.QtMultimedia import QMediaDevices, QCamera, QMediaCaptureSession
from PySide6.QtMultimediaWidgets import QVideoWidgetclass MyWidget(QWidget):def __init__(self):# 1、调用父类的__init__()方法super().__init__()self.setup_ui()def setup_ui(self):# 1、设置窗口对象大小self.resize(700, 500)layout_v = QVBoxLayout()self.setLayout(layout_v)# 2、显示视频的控件self.videoWidget = QVideoWidget()layout_v.addWidget(self.videoWidget)# 3、打开和停止摄像头的按钮self.button_open = QPushButton("打开摄像头")self.button_stop = QPushButton("关闭摄像头")layout_h = QHBoxLayout()layout_h.addWidget(self.button_open)layout_h.addWidget(self.button_stop)layout_v.addLayout(layout_h)# 3、媒体设备self.mediaDevice = QMediaDevices(self)# 4、获取默认的视频输入设备self.cameraDevice = self.mediaDevice.defaultVideoInput()# 5、根据视频输入设备定义视频接口self.camera = QCamera(self.cameraDevice)# 6、媒体捕获器self.mediaCaptureSession = QMediaCaptureSession(self)# 7、设备媒体捕获器的视频接口self.mediaCaptureSession.setCamera(self.camera)# 8、设置媒体捕获器的视频输出控件self.mediaCaptureSession.setVideoOutput(self.videoWidget)# 9、定义信号与槽的连接self.button_open.clicked.connect(self.camera.start)self.button_stop.clicked.connect(self.camera.stop)if __name__ == "__main__":# 1、创建一个QApplication类的实例app = QApplication(sys.argv)# 2、创建一个窗口window = MyWidget()# 3、展示窗口window.show()# 4、进入程序的主循环并通过exit()函数确保主循环安全结束sys.exit(app.exec())
四、媒体格式
在进行音频和视频的录制时,需要指定音频和视频的记录格式,以及媒体文件的存储格式,这些格式通过 QMediaFormat 类来定义。
用 QMediaFormat 类创建媒体格式实例的方法如下所示。
QMediaFormat(format:QMediaFormat.FileFormat=QQMediaFormant.UnspecifiedFormat)
QMediaFormat(other:Union[QMediaFotmat, QMediaFotmant.FileFormat])
QMediaFormat 类的常用方法如下:
# 实例方法
setFileFormat(f:QMediaFormat.FileFormat) -> None # 设置文件格式
fileFormat() -> QMediaFormat.FileFormat # 获取文件格式
setAudioCodec(codec:QMediaFormat.AudioCode) -> None # 设置音频编码格式
audioCodec() -> QMediaFormat.AudioCodec # 获取音频编码格式
setVideoCodec(codec:QMediaFormat.VideoCodec) -> None # 设置视频编码格式
videoCodec() -> QMediaFormat.VideoCodec # 获取视频编码格式supportedFileFormats(m:QMediaFormat.ConversionMode) -> List[QMediaFormat.FileFormat] # 获取支持的文件编码格式列表
supportedAudioCodecs(m:QMediaFormat.ConversionMode) -> List[QMediaFormat.AudioCode] # 获取支持的音频编码格式列表
supportedVideoCodecs(m:QMediaFormat.ConversionMode) -> List[QMediaFormat.VideoCode] # 获取支持的视频编码格式列表
isSupported(mode:QMediaFormat.ConversionMode) -> bool # 获取是否可以对某种编码格式编码或解码# 静态方法
fileFormatName(fileFormat:QMediaFormat.FileFormat) -> str # 获取文件格式名称
fileFormatDescription(fileFormat:QMediaFormat.FileFormat) -> str # 获取文件格式信息
audioCodecName(codec:QMediaFormat.AudioCode) -> str # 获取音频格式名称
audioCodecDescription(codec:QMediaFormat.AudioCode) -> str # 获取音频格式信息
videoCodecName(codec:QMediaFormat.VideoCode) -> str # 获取视频格式名称
videoCodecDescription(codec:QMediaFormat.VideoCode) -> str # 获取视频格式信息
分别用 supportedFileFormats(QMediaFormat.ConversionMode)
方法、supportedAudioCodecs(QMediaFormat.ConversionMode)
方法和 supportedVideoCodecs(QMediaFormat.ConversionMode)
方法获取编码或解码时支持的文件格式列表、音频编码格式列表和视频编码格式列表,参数 QMediaFormat.ConversionMode 可取值如下:
QMediaFormat.ConversionMode.Encode
QMediaFormat.ConversionMode.Decode
五、图像捕获
用媒体捕获器 QMediaCaptureSession 的 setImageCapture(imageCapture:QImageCapture)
方法将 QImageCapture 与 QMediaCatureSession 关联,可以捕获图像,实现拍照功能。
用 QImageCapture 类定义图像捕获的方法如下所示。
QImageCapture(parent:QObject=None)
QImageCapture 类常用方法如下:
# 实例方法
isReadyForCapture() -> bool # 获取是否可以拍照
captureSession() -> QMediaCaptureSession # 获取关联的捕捉器setFileFormat(format:QImageCapture.FileFormat) -> None # 设置文件格式
fileFormat() -> QImageCapture.FileFormat # 获取文件格式setQuality(quality:QImageCapture.Quality) -> None # 设置图像质量
quality() -> QImageCapture.Quality # 获取图像质量setResolution(size:QSize) -> None # 设置分辨率
setResolution(width:int, height:int) -> None # 设置分辨率
resolution() -> QSize # 获取分辨率setMetaData(metaData:QMediaMetaData) -> None # 设置元数据
metaData() -> QMediaMetaData # 获取元数据
addMetaData(metaData:QMediaMetaData) -> None # 添加元数据error() -> QImageCapture.Error # 获取出错信息
errorString() -> str # 获取出错信息# 槽函数
capture() -> int # 进行拍照
captureToFile(location="") -> int # 拍照到文件# 静态方法
fileFormatDescription(c:QImageCapture.FileFormat) -> str # 获取格式的信息
fileFormatName(c:QImageCapture.FileFormat) -> str # 获取格式的名称
supportedFormats() -> List[QImageCapture.FileFormat] # 获取支持的格式
当 isReadyForCapture()
的返回值是 True 时,可以进行拍照;用 capture()
方法进行拍照,返回值是拍照的识别号 ID,同时会发送 imageCaptured(id:int,preview:QImage)
信号和 imageExposed(id:int)
信号,可以获取拍摄的图像;也可以用 captureToFile(location:str='')
方法直接将拍摄的图像保存到文件中,同时发送 imageCaptured(id:int,preview:QImage)
信号、imageExposed(id:int)
信号和 imageSaved(id:int,fileName:str)
信号,如果没有给出保存的文件名和路径,则使用默认的路径和文件名,如果只给出文件名,则保存到默认路径下,完整路径可以通过 imageSaved(id:int,fileName:str)
信号的参数获取。
用 error()
方法获取拍照时的出错状态,返回值是 QImageCapture.Error 枚举值,可取值如下:
QImageCapture.NoError # 没有错误
QImageCapture.NotReadyError # 设备没准备好
QImageCapture.ResourceError # 设备没准备好或不可用
QImageCapture.OutOfSpaceError # 存储空间不够
QImageCapture.NotSupportedFeatureError # 设备不支持拍照
QImageCapture.FormatError # 格式出错
用 setFileFormat(format:QImageCapture.FileFormat)
方法设置拍照的格式,参数是 QImageCapture.FileFormat 的枚举值,可取值如下:
QImageCapture.FileFormat.JPEG
QImageCapture.FileFormat.PNG
QImageCapture.FileFormat.Tiff
QImageCapture.FileFormat.WebP
QImageCapture.FileFormat.UnspecifiedFormat
QImageCapture.FileFormat.LastFileFormat
用 setQuality(quality:QImageCapture.Quality)
方法设置图像质量,参数是 QImageCapture.Quality 的枚举值,可取值如下:
QImageCapture.Quality.VeryLowQuality
QImageCapture.Quality.LowQuality
QImageCapture.Quality.NormalQuality
QImageCapture.Quality.HighQuality
QImageCapture.Quality.VeryHighQuality
QImageCapture 类常用信号如下:
readyForCaptureChanged(ready:bool) # 准备状态发生改变时发射信号
imageCaptured(id:int, preview:QImage) # 捕捉到图象时发射信号
imageExposed(id:int) # 图像曝光时发射信号
imageSaved(id:int, fileName:str) # 保存图像时发射信号
imageAvailable(id:int, frame:QVideoFrame) # 可以获取图像时发射信号
metaDataChanged() # 元数据发生改变时发射信号
qualityChanged() # 图像质量发生改变时发射信号
errorOccurred(id:int, error:QImageCapture.Error, errorString:str) # 出现错误时发射信号
errorChanged() # 错误状态发生改变时发射信号
fileFormatChanged() # 文件格式发生改变时发射信号
其中 imageAvailable(id:int,frame:QVideoFrame)
信号的参数 QVideoFrame 是视频帧,利用 QVideoFrame 的 toImage()
方法可以得到 QImage。
import sys
import os, timefrom PySide6.QtWidgets import QApplication, QWidget
from PySide6.QtWidgets import QPushButton
from PySide6.QtWidgets import QVBoxLayout, QHBoxLayout
from PySide6.QtMultimedia import QMediaDevices, QCamera
from PySide6.QtMultimedia import QMediaCaptureSession, QImageCapture
from PySide6.QtMultimediaWidgets import QVideoWidgetclass MyWidget(QWidget):def __init__(self):# 1、调用父类的__init__()方法super().__init__()self.imageCapture = Noneself.setup_ui()def setup_ui(self):# 1、设置窗口对象大小self.resize(700, 500)layout_v = QVBoxLayout()self.setLayout(layout_v)# 2、显示视频的控件self.videoWidget = QVideoWidget()layout_v.addWidget(self.videoWidget)# 3、打开和停止摄像头的按钮self.button_camera_action = QPushButton("打开摄像头")self.button_camera_take_photo = QPushButton("拍照")layout_h = QHBoxLayout()layout_h.addWidget(self.button_camera_action)layout_h.addWidget(self.button_camera_take_photo)layout_v.addLayout(layout_h)# 3、媒体设备self.mediaDevice = QMediaDevices(self)# 4、获取默认的视频输入设备self.cameraDevice = self.mediaDevice.defaultVideoInput()# 5、根据视频输入设备定义视频接口self.camera = QCamera(self.cameraDevice)# 6、媒体捕获器self.mediaCaptureSession = QMediaCaptureSession(self)# 7、设备媒体捕获器的视频接口self.mediaCaptureSession.setCamera(self.camera)# 8、设置媒体捕获器的视频输出控件self.mediaCaptureSession.setVideoOutput(self.videoWidget)# 9、定义信号与槽的连接self.button_camera_action.clicked.connect(self.camera_action)self.button_camera_take_photo.clicked.connect(self.take_photo)def camera_action(self):if self.button_camera_action.text() == "打开摄像头":# 打开摄像头self.camera.start()# 摄像头操作按钮文本显示为关闭摄像头self.button_camera_action.setText("关闭摄像头")# 创建图片捕获对象,并关联摄像头self.imageCapture = QImageCapture()# 设置图像图示self.imageCapture.setFileFormat(QImageCapture.FileFormat.JPEG)# 设置分辨率self.imageCapture.setResolution(1920, 1080)# 设置图片质量self.imageCapture.setQuality(QImageCapture.Quality.HighQuality)# 设置捕获器self.mediaCaptureSession.setImageCapture(self.imageCapture)elif self.button_camera_action.text() == "关闭摄像头":# 关闭摄像头self.camera.stop()# 摄像头操作按钮文本显示为打开摄像头self.button_camera_action.setText("打开摄像头")self.imageCapture = Nonedef take_photo(self):if self.imageCapture:fileName = f"{os.getcwd()}/{time.strftime('%Y%m%d%H%M%S', time.localtime())}.jpeg"self.imageCapture.captureToFile(fileName)if __name__ == "__main__":# 1、创建一个QApplication类的实例app = QApplication(sys.argv)# 2、创建一个窗口window = MyWidget()# 3、展示窗口window.show()# 4、进入程序的主循环并通过exit()函数确保主循环安全结束sys.exit(app.exec())
六、媒体录制
QMediaRecorder 可以录制从 QMediaCaptureSession 获取的音频和视频,并对音频和视频进行编码,需要用 QMediaCaptureSession的setRecorder(recorder:QMediaRecorder)
方法设置关联的捕获器。
用 QMediaRecorder 创建实例的方法如下所示。
QMediaRecorder(parent:QObject=None)
QMediaRecorder 类的常用方法如下:
# 实例方法
isAvailable() -> bool # 获取是否可以录制duration() -> int # 获取录制时间
recorderState() -> QMediaRecorder.recorderState # 获取录制状态error() -> QMediaRecorder.Error # 获取出错内容
errorString() -> str # 获取错误信息setAudioBitRate(bitRate:int) -> None # 设置音频比特率
audioBitRate() -> int # 获取音频比特率
setAudioChannelCount(channels:int) -> None # 设置音频通道数
audioChannelCount() -> int # 获取音频通道数
setAudioSampleRate(sampleRate:int) -> None # 设置音频采样率
audioSampleRate() -> int # 获取音频采样率setEncodingMode(mode:QMediaRecorder.EncodingMode) -> None # 设置编码格式
encodingMode() -> QMeidaRecorder.encodingMode # 获取编码格式
setMediaFormat(format:Union[QMediaFormat, QMediaFormat.FileFotmat]) -> None # 设置媒体格式setQuality(quality:QMediaRecorder.Quality) -> None # 设置录制质量
quality() -> QMediaRecorder.Quality # 获取录制质量
setVideoBitRate(bitRate:int) -> None # 设置视频比特率
videoBitRate() -> int # 获取视频比特率
setVideoFrameRate(frameRate:float) -> None # 设置视频帧速
videoFrameRate() -> float # 获取视频帧速setVideoResolution(size:QSize) -> None # 设置视频分辨率
setVideoResolution(width:int, height:int) -> None # 设置视频分辨率
videoResolution() -> QSize # 获取视频分辨率setMetaData(metaData:QMediaMetaData) -> None # 设置媒体元数据
metaData() -> QMediaMeta # 获取媒体元数据
addMetaData(metaData:QMediaMetaData) -> None # 添加媒体元数据setOutputLocation(location:QUrl) -> None # 设置媒体输出位置
outputLocation() -> QUrl # 获取输出位置
actualLocation() -> QUrl # 获取实际的输出位置 # 槽方法
record() -> None # 开始录制
pause() -> None # 暂停录制
stop() -> None # 停止录制
用 recorderState()
方法获取录制状态,返回值是 QMediaRecorder.RecorderState 的枚举值,可取值如下:
QMediaRecorder.RecorderState.StoppedState
QMediaRecorder.RecorderState.RecordingState
QMediaRecorder.RecorderState.PausedState
录制过程中如果出错,可以用 error()
方法获取出错内容,返回值是 QMediaRecorder.Error 的枚举值,可取值如下:
QMediaRecorder.Error.NoError # 没有问题
QMediaRecorder.Error.ResourceError # 设备没有准备好
QMediaRecorder.Error.FormatError # 不支持该格式
QMediaRecorder.Error.OutOfSpaceError # 存储空间不足
QMediaRecorder.Error.LocationNotWritable # 输出位置不可写
用 setEncodingMode(QMediaRecorder.EncodingMode)
方法设置编码模式,参数是 QMediaRecorder.EncodingMode 的枚举值,可取值如下:
QMediaRecorder.EncodingMode.ConstantQualityEncoding # 常质量编码
QMediaRecorder.EncodingMode.ConstantBitRateEncoding # 常比特率编码
QMediaRecorder.EncodingMode.AverageBitRateEncoding # 平均比特率编码
QMediaRecorder.EncodingMode.TwoPassEncoding # 二次编码
用 setQuality(quality:QMediaRecorder.Quality)
方法设置录制质量,参数是 QMediaRecorder.Quality 的枚举值,可取如下:
QMediaRecorder.Quality.VeryLowQuality
QMediaRecorder.Quality.LowQuality
QMediaRecorder.Quality.NormalQuality
QMediaRecorder.Quality.HighQuality
QMediaRecorder.Quality.VeryHighQuality
QMediaRecorder 类的常用信号如下:
actualLocationChanged(location:QUrl) # 存储位置发生改变时发射信号
durationChanged(duration:int) # 录制时间发生改变时发射信号
errorChanged() # 错误状态发生改变时发射信号
errorOccurred(error:QMediaRecorder.Error, errorString:str) # 出现错误时发射信号
mediaFormatChanged() # 格式发生改变时发射信号
metaDataChanged() # 元数据发生改变时发射信号
recorderStateChanged(state:QMediaRecorder.RecorderState) # 录制状态发生改变时发射信号
import sys
import os, timefrom PySide6.QtWidgets import QApplication, QWidget
from PySide6.QtWidgets import QPushButton
from PySide6.QtWidgets import QVBoxLayout, QHBoxLayout
from PySide6.QtMultimedia import QMediaDevices, QCamera
from PySide6.QtMultimedia import QMediaCaptureSession, QAudioInput
from PySide6.QtMultimedia import QMediaRecorder, QMediaFormat
from PySide6.QtMultimediaWidgets import QVideoWidget
from PySide6.QtCore import QUrlclass MyWidget(QWidget):def __init__(self):# 1、调用父类的__init__()方法super().__init__()self.mediaRecorder = Noneself.setup_ui()def setup_ui(self):# 1、设置窗口对象大小self.resize(700, 500)layout_v = QVBoxLayout()self.setLayout(layout_v)# 2、显示视频的控件self.videoWidget = QVideoWidget()layout_v.addWidget(self.videoWidget)# 3、打开和停止摄像头的按钮self.button_camera_action = QPushButton("打开摄像头")self.button_camera_recorder_action = QPushButton("开始录像")self.button_camera_recorder_stop = QPushButton("停止录像")layout_h = QHBoxLayout()layout_h.addWidget(self.button_camera_action)layout_h.addWidget(self.button_camera_recorder_action)layout_h.addWidget(self.button_camera_recorder_stop)layout_v.addLayout(layout_h)# 3、媒体设备self.mediaDevice = QMediaDevices(self)# 4、获取默认的视频输入设备self.cameraDevice = self.mediaDevice.defaultVideoInput()# 5、根据视频输入设备定义视频接口self.camera = QCamera(self.cameraDevice)# 6、媒体捕获器self.mediaCaptureSession = QMediaCaptureSession(self)# 7、设备媒体捕获器的视频接口self.mediaCaptureSession.setCamera(self.camera)# 8、设置媒体捕获器的视频输出控件self.mediaCaptureSession.setVideoOutput(self.videoWidget)# 9、定义信号与槽的连接self.button_camera_action.clicked.connect(self.camera_action)self.button_camera_recorder_action.clicked.connect(self.camera_recorder_action)self.button_camera_recorder_stop.clicked.connect(self.camera_recorder_stop)def camera_action(self):if self.button_camera_action.text() == "打开摄像头":# 打开摄像头self.camera.start()# 摄像头操作按钮文本显示为关闭摄像头self.button_camera_action.setText("关闭摄像头")# 创建媒体录制对象,并关联摄像头self.mediaRecorder = QMediaRecorder(self.camera)# 设置输出视频的格式self.mediaRecorder.setMediaFormat(QMediaFormat.FileFormat.AVI)# 设置分辨率self.mediaRecorder.setVideoResolution(1920, 1080)# 设置输出视频的质量self.mediaRecorder.setQuality(QMediaRecorder.Quality.HighQuality)# 设置媒体输出位置fileName = f"{os.getcwd()}/{time.strftime('%Y%m%d%H%M%S', time.localtime())}.avi"self.mediaRecorder.setOutputLocation(QUrl.fromLocalFile(fileName))# 设置音频输出self.audioInput = QAudioInput()self.mediaCaptureSession.setAudioInput(self.audioInput)# 设置捕获器self.mediaCaptureSession.setRecorder(self.mediaRecorder)self.mediaRecorder.errorOccurred.connect(self.error)elif self.button_camera_action.text() == "关闭摄像头":# 关闭摄像头self.camera.stop()# 摄像头操作按钮文本显示为打开摄像头self.button_camera_action.setText("打开摄像头")# 结束录制if self.mediaRecorder:self.mediaRecorder.stop()self.button_camera_recorder_action.setText("开始录像")self.mediaRecorder = Nonedef camera_recorder_action(self):if self.mediaRecorder:if self.button_camera_recorder_action.text() == "开始录像":# 开始录像self.mediaRecorder.record()# 录制操作按钮文本显示为暂停录像self.button_camera_recorder_action.setText("暂停录像")elif self.button_camera_recorder_action.text() == "暂停录像":# 暂停录像self.mediaRecorder.pause()# 录制操作按钮文本显示为开始录像self.button_camera_recorder_action.setText("开始录像")def camera_recorder_stop(self):if self.mediaRecorder:# 结束录像self.mediaRecorder.stop()# 录制操作按钮文本显示为开始录像self.button_camera_recorder_action.setText("开始录像")# 关闭摄像头self.camera.stop()# 摄像头操作按钮文本显示为打开摄像头self.button_camera_action.setText("打开摄像头")self.mediaRecorder = Nonedef error(self, error, errorString):print(error)print(errorString)if __name__ == "__main__":# 1、创建一个QApplication类的实例app = QApplication(sys.argv)# 2、创建一个窗口window = MyWidget()# 3、展示窗口window.show()# 4、进入程序的主循环并通过exit()函数确保主循环安全结束sys.exit(app.exec())