mirror of
https://github.com/linyqh/NarratoAI.git
synced 2025-12-12 19:52:48 +00:00
优化 ffmpeg 硬件加速兼容性
This commit is contained in:
parent
6356a140aa
commit
47cd4f145d
@ -13,6 +13,7 @@ from app.config import config
|
|||||||
from app.models.exception import HttpException
|
from app.models.exception import HttpException
|
||||||
from app.router import root_api_router
|
from app.router import root_api_router
|
||||||
from app.utils import utils
|
from app.utils import utils
|
||||||
|
from app.utils import ffmpeg_utils
|
||||||
|
|
||||||
|
|
||||||
def exception_handler(request: Request, e: HttpException):
|
def exception_handler(request: Request, e: HttpException):
|
||||||
@ -80,3 +81,10 @@ def shutdown_event():
|
|||||||
@app.on_event("startup")
|
@app.on_event("startup")
|
||||||
def startup_event():
|
def startup_event():
|
||||||
logger.info("startup event")
|
logger.info("startup event")
|
||||||
|
|
||||||
|
# 检测FFmpeg硬件加速
|
||||||
|
hwaccel_info = ffmpeg_utils.detect_hardware_acceleration()
|
||||||
|
if hwaccel_info["available"]:
|
||||||
|
logger.info(f"FFmpeg硬件加速检测结果: 可用 | 类型: {hwaccel_info['type']} | 编码器: {hwaccel_info['encoder']} | 独立显卡: {hwaccel_info['is_dedicated_gpu']} | 参数: {hwaccel_info['hwaccel_args']}")
|
||||||
|
else:
|
||||||
|
logger.warning(f"FFmpeg硬件加速不可用: {hwaccel_info['message']}, 将使用CPU软件编码")
|
||||||
|
|||||||
@ -16,6 +16,8 @@ from loguru import logger
|
|||||||
from typing import Dict, List, Optional
|
from typing import Dict, List, Optional
|
||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
|
|
||||||
|
from app.utils import ffmpeg_utils
|
||||||
|
|
||||||
|
|
||||||
def parse_timestamp(timestamp: str) -> tuple:
|
def parse_timestamp(timestamp: str) -> tuple:
|
||||||
"""
|
"""
|
||||||
@ -79,40 +81,8 @@ def check_hardware_acceleration() -> Optional[str]:
|
|||||||
Returns:
|
Returns:
|
||||||
Optional[str]: 硬件加速参数,如果不支持则返回None
|
Optional[str]: 硬件加速参数,如果不支持则返回None
|
||||||
"""
|
"""
|
||||||
# 检查NVIDIA GPU支持
|
# 使用集中式硬件加速检测
|
||||||
try:
|
return ffmpeg_utils.get_ffmpeg_hwaccel_type()
|
||||||
nvidia_check = subprocess.run(
|
|
||||||
["ffmpeg", "-hwaccel", "cuda", "-i", "/dev/null", "-f", "null", "-"],
|
|
||||||
stderr=subprocess.PIPE, stdout=subprocess.PIPE, text=True, check=False
|
|
||||||
)
|
|
||||||
if nvidia_check.returncode == 0:
|
|
||||||
return "cuda"
|
|
||||||
except Exception:
|
|
||||||
pass
|
|
||||||
|
|
||||||
# 检查MacOS videotoolbox支持
|
|
||||||
try:
|
|
||||||
videotoolbox_check = subprocess.run(
|
|
||||||
["ffmpeg", "-hwaccel", "videotoolbox", "-i", "/dev/null", "-f", "null", "-"],
|
|
||||||
stderr=subprocess.PIPE, stdout=subprocess.PIPE, text=True, check=False
|
|
||||||
)
|
|
||||||
if videotoolbox_check.returncode == 0:
|
|
||||||
return "videotoolbox"
|
|
||||||
except Exception:
|
|
||||||
pass
|
|
||||||
|
|
||||||
# 检查Intel Quick Sync支持
|
|
||||||
try:
|
|
||||||
qsv_check = subprocess.run(
|
|
||||||
["ffmpeg", "-hwaccel", "qsv", "-i", "/dev/null", "-f", "null", "-"],
|
|
||||||
stderr=subprocess.PIPE, stdout=subprocess.PIPE, text=True, check=False
|
|
||||||
)
|
|
||||||
if qsv_check.returncode == 0:
|
|
||||||
return "qsv"
|
|
||||||
except Exception:
|
|
||||||
pass
|
|
||||||
|
|
||||||
return None
|
|
||||||
|
|
||||||
|
|
||||||
def clip_video(
|
def clip_video(
|
||||||
@ -152,12 +122,11 @@ def clip_video(
|
|||||||
# 确保输出目录存在
|
# 确保输出目录存在
|
||||||
Path(output_dir).mkdir(parents=True, exist_ok=True)
|
Path(output_dir).mkdir(parents=True, exist_ok=True)
|
||||||
|
|
||||||
# 检查硬件加速支持
|
# 获取硬件加速支持
|
||||||
hwaccel = check_hardware_acceleration()
|
hwaccel = check_hardware_acceleration()
|
||||||
hwaccel_args = []
|
hwaccel_args = []
|
||||||
if hwaccel:
|
if hwaccel:
|
||||||
hwaccel_args = ["-hwaccel", hwaccel]
|
hwaccel_args = ffmpeg_utils.get_ffmpeg_hwaccel_args()
|
||||||
logger.info(f"使用硬件加速: {hwaccel}")
|
|
||||||
|
|
||||||
# 存储裁剪结果
|
# 存储裁剪结果
|
||||||
result = {}
|
result = {}
|
||||||
|
|||||||
@ -14,6 +14,7 @@ from moviepy.video.io.VideoFileClip import VideoFileClip
|
|||||||
from app.config import config
|
from app.config import config
|
||||||
from app.models.schema import VideoAspect, VideoConcatMode, MaterialInfo
|
from app.models.schema import VideoAspect, VideoConcatMode, MaterialInfo
|
||||||
from app.utils import utils
|
from app.utils import utils
|
||||||
|
from app.utils import ffmpeg_utils
|
||||||
|
|
||||||
requested_count = 0
|
requested_count = 0
|
||||||
|
|
||||||
@ -314,40 +315,9 @@ def _detect_hardware_acceleration() -> Optional[str]:
|
|||||||
Returns:
|
Returns:
|
||||||
Optional[str]: 硬件加速参数,如果不支持则返回None
|
Optional[str]: 硬件加速参数,如果不支持则返回None
|
||||||
"""
|
"""
|
||||||
# 检查NVIDIA GPU支持
|
# 使用集中式硬件加速检测
|
||||||
try:
|
hwaccel_type = ffmpeg_utils.get_ffmpeg_hwaccel_type()
|
||||||
nvidia_check = subprocess.run(
|
return hwaccel_type
|
||||||
["ffmpeg", "-hwaccel", "cuda", "-i", "/dev/null", "-f", "null", "-"],
|
|
||||||
stderr=subprocess.PIPE, stdout=subprocess.PIPE, text=True, check=False
|
|
||||||
)
|
|
||||||
if nvidia_check.returncode == 0:
|
|
||||||
return "cuda"
|
|
||||||
except Exception:
|
|
||||||
pass
|
|
||||||
|
|
||||||
# 检查MacOS videotoolbox支持
|
|
||||||
try:
|
|
||||||
videotoolbox_check = subprocess.run(
|
|
||||||
["ffmpeg", "-hwaccel", "videotoolbox", "-i", "/dev/null", "-f", "null", "-"],
|
|
||||||
stderr=subprocess.PIPE, stdout=subprocess.PIPE, text=True, check=False
|
|
||||||
)
|
|
||||||
if videotoolbox_check.returncode == 0:
|
|
||||||
return "videotoolbox"
|
|
||||||
except Exception:
|
|
||||||
pass
|
|
||||||
|
|
||||||
# 检查Intel Quick Sync支持
|
|
||||||
try:
|
|
||||||
qsv_check = subprocess.run(
|
|
||||||
["ffmpeg", "-hwaccel", "qsv", "-i", "/dev/null", "-f", "null", "-"],
|
|
||||||
stderr=subprocess.PIPE, stdout=subprocess.PIPE, text=True, check=False
|
|
||||||
)
|
|
||||||
if qsv_check.returncode == 0:
|
|
||||||
return "qsv"
|
|
||||||
except Exception:
|
|
||||||
pass
|
|
||||||
|
|
||||||
return None
|
|
||||||
|
|
||||||
|
|
||||||
def save_clip_video(timestamp: str, origin_video: str, save_dir: str = "") -> str:
|
def save_clip_video(timestamp: str, origin_video: str, save_dir: str = "") -> str:
|
||||||
@ -422,12 +392,11 @@ def save_clip_video(timestamp: str, origin_video: str, save_dir: str = "") -> st
|
|||||||
duration = end - start
|
duration = end - start
|
||||||
# logger.info(f"开始剪辑视频: {format_timestamp(start)} - {format_timestamp(end)},时长 {format_timestamp(duration)}")
|
# logger.info(f"开始剪辑视频: {format_timestamp(start)} - {format_timestamp(end)},时长 {format_timestamp(duration)}")
|
||||||
|
|
||||||
# 检测可用的硬件加速选项
|
# 获取硬件加速选项
|
||||||
hwaccel = _detect_hardware_acceleration()
|
hwaccel = _detect_hardware_acceleration()
|
||||||
hwaccel_args = []
|
hwaccel_args = []
|
||||||
if hwaccel:
|
if hwaccel:
|
||||||
hwaccel_args = ["-hwaccel", hwaccel]
|
hwaccel_args = ffmpeg_utils.get_ffmpeg_hwaccel_args()
|
||||||
logger.info(f"使用硬件加速: {hwaccel}")
|
|
||||||
|
|
||||||
# 转换为FFmpeg兼容的时间格式(逗号替换为点)
|
# 转换为FFmpeg兼容的时间格式(逗号替换为点)
|
||||||
ffmpeg_start_time = start_str.replace(',', '.')
|
ffmpeg_start_time = start_str.replace(',', '.')
|
||||||
|
|||||||
@ -15,6 +15,8 @@ from enum import Enum
|
|||||||
from typing import List, Optional, Tuple
|
from typing import List, Optional, Tuple
|
||||||
from loguru import logger
|
from loguru import logger
|
||||||
|
|
||||||
|
from app.utils import ffmpeg_utils
|
||||||
|
|
||||||
|
|
||||||
class VideoAspect(Enum):
|
class VideoAspect(Enum):
|
||||||
"""视频宽高比枚举"""
|
"""视频宽高比枚举"""
|
||||||
@ -62,60 +64,8 @@ def get_hardware_acceleration_option() -> Optional[str]:
|
|||||||
Returns:
|
Returns:
|
||||||
Optional[str]: 硬件加速参数,如果不支持则返回None
|
Optional[str]: 硬件加速参数,如果不支持则返回None
|
||||||
"""
|
"""
|
||||||
try:
|
# 使用集中式硬件加速检测
|
||||||
# 检测操作系统
|
return ffmpeg_utils.get_ffmpeg_hwaccel_type()
|
||||||
is_windows = os.name == 'nt'
|
|
||||||
|
|
||||||
# 检查NVIDIA GPU支持
|
|
||||||
nvidia_check = subprocess.run(
|
|
||||||
['ffmpeg', '-hide_banner', '-hwaccels'],
|
|
||||||
stdout=subprocess.PIPE, stderr=subprocess.PIPE, text=True
|
|
||||||
)
|
|
||||||
output = nvidia_check.stdout.lower()
|
|
||||||
|
|
||||||
# 首先尝试获取系统信息,Windows系统使用更安全的检测方法
|
|
||||||
if is_windows:
|
|
||||||
try:
|
|
||||||
# 尝试检测显卡信息
|
|
||||||
gpu_info = subprocess.run(
|
|
||||||
['wmic', 'path', 'win32_VideoController', 'get', 'name'],
|
|
||||||
stdout=subprocess.PIPE, stderr=subprocess.PIPE, text=True, check=False
|
|
||||||
)
|
|
||||||
gpu_info_output = gpu_info.stdout.lower()
|
|
||||||
|
|
||||||
# 检测是否为AMD显卡
|
|
||||||
if 'amd' in gpu_info_output or 'radeon' in gpu_info_output:
|
|
||||||
logger.info("检测到AMD显卡,为避免兼容性问题,将使用软件编码")
|
|
||||||
return None
|
|
||||||
|
|
||||||
# 检测是否为集成显卡
|
|
||||||
if 'intel' in gpu_info_output and ('hd graphics' in gpu_info_output or 'uhd graphics' in gpu_info_output):
|
|
||||||
# 在Windows上,Intel集成显卡可能不稳定,建议使用软件编码
|
|
||||||
logger.info("检测到Intel集成显卡,为避免兼容性问题,将使用软件编码")
|
|
||||||
return None
|
|
||||||
except Exception as e:
|
|
||||||
logger.warning(f"获取显卡信息失败: {str(e)},将谨慎处理硬件加速")
|
|
||||||
|
|
||||||
# 根据ffmpeg支持的硬件加速器决定使用哪种
|
|
||||||
if 'cuda' in output and not is_windows:
|
|
||||||
# 在非Windows系统上使用CUDA
|
|
||||||
return 'cuda'
|
|
||||||
elif 'nvenc' in output and not is_windows:
|
|
||||||
# 在非Windows系统上使用NVENC
|
|
||||||
return 'nvenc'
|
|
||||||
elif 'qsv' in output and not (is_windows and ('amd' in gpu_info_output if 'gpu_info_output' in locals() else False)):
|
|
||||||
# 只有在非AMD系统上使用QSV
|
|
||||||
return 'qsv'
|
|
||||||
elif 'videotoolbox' in output: # macOS
|
|
||||||
return 'videotoolbox'
|
|
||||||
elif 'vaapi' in output and not is_windows: # Linux VA-API
|
|
||||||
return 'vaapi'
|
|
||||||
else:
|
|
||||||
logger.info("没有找到支持的硬件加速器或系统不兼容,将使用软件编码")
|
|
||||||
return None
|
|
||||||
except Exception as e:
|
|
||||||
logger.warning(f"检测硬件加速器时出错: {str(e)},将使用软件编码")
|
|
||||||
return None
|
|
||||||
|
|
||||||
|
|
||||||
def check_video_has_audio(video_path: str) -> bool:
|
def check_video_has_audio(video_path: str) -> bool:
|
||||||
@ -231,15 +181,9 @@ def process_single_video(
|
|||||||
# 添加硬件加速参数(根据前面的安全检查可能已经被禁用)
|
# 添加硬件加速参数(根据前面的安全检查可能已经被禁用)
|
||||||
if hwaccel:
|
if hwaccel:
|
||||||
try:
|
try:
|
||||||
if hwaccel == 'cuda' or hwaccel == 'nvenc':
|
# 使用集中式硬件加速参数
|
||||||
command.extend(['-hwaccel', 'cuda'])
|
hwaccel_args = ffmpeg_utils.get_ffmpeg_hwaccel_args()
|
||||||
elif hwaccel == 'qsv':
|
command.extend(hwaccel_args)
|
||||||
command.extend(['-hwaccel', 'qsv'])
|
|
||||||
elif hwaccel == 'videotoolbox':
|
|
||||||
command.extend(['-hwaccel', 'videotoolbox'])
|
|
||||||
elif hwaccel == 'vaapi':
|
|
||||||
command.extend(['-hwaccel', 'vaapi', '-vaapi_device', '/dev/dri/renderD128'])
|
|
||||||
logger.info(f"应用硬件加速: {hwaccel}")
|
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
logger.warning(f"应用硬件加速参数时出错: {str(e)},将使用软件编码")
|
logger.warning(f"应用硬件加速参数时出错: {str(e)},将使用软件编码")
|
||||||
# 重置命令,移除可能添加了一半的硬件加速参数
|
# 重置命令,移除可能添加了一半的硬件加速参数
|
||||||
|
|||||||
419
app/utils/ffmpeg_utils.py
Normal file
419
app/utils/ffmpeg_utils.py
Normal file
@ -0,0 +1,419 @@
|
|||||||
|
"""
|
||||||
|
FFmpeg 工具模块 - 提供 FFmpeg 相关的工具函数,特别是硬件加速检测
|
||||||
|
"""
|
||||||
|
import os
|
||||||
|
import platform
|
||||||
|
import subprocess
|
||||||
|
from typing import Dict, List, Optional, Tuple, Union
|
||||||
|
from loguru import logger
|
||||||
|
|
||||||
|
# 全局变量,存储检测到的硬件加速信息
|
||||||
|
_FFMPEG_HW_ACCEL_INFO = {
|
||||||
|
"available": False,
|
||||||
|
"type": None,
|
||||||
|
"encoder": None,
|
||||||
|
"hwaccel_args": [],
|
||||||
|
"message": "",
|
||||||
|
"is_dedicated_gpu": False
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
def check_ffmpeg_installation() -> bool:
|
||||||
|
"""
|
||||||
|
检查ffmpeg是否已安装
|
||||||
|
|
||||||
|
Returns:
|
||||||
|
bool: 如果安装则返回True,否则返回False
|
||||||
|
"""
|
||||||
|
try:
|
||||||
|
subprocess.run(['ffmpeg', '-version'], stdout=subprocess.PIPE, stderr=subprocess.PIPE, check=True)
|
||||||
|
return True
|
||||||
|
except (subprocess.SubprocessError, FileNotFoundError):
|
||||||
|
logger.error("ffmpeg未安装或不在系统PATH中,请安装ffmpeg")
|
||||||
|
return False
|
||||||
|
|
||||||
|
|
||||||
|
def detect_hardware_acceleration() -> Dict[str, Union[bool, str, List[str], None]]:
|
||||||
|
"""
|
||||||
|
检测系统可用的硬件加速器,并存储结果到全局变量
|
||||||
|
|
||||||
|
Returns:
|
||||||
|
Dict: 包含硬件加速信息的字典
|
||||||
|
"""
|
||||||
|
global _FFMPEG_HW_ACCEL_INFO
|
||||||
|
|
||||||
|
# 如果已经检测过,直接返回结果
|
||||||
|
if _FFMPEG_HW_ACCEL_INFO["type"] is not None:
|
||||||
|
return _FFMPEG_HW_ACCEL_INFO
|
||||||
|
|
||||||
|
# 检查ffmpeg是否已安装
|
||||||
|
if not check_ffmpeg_installation():
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["message"] = "FFmpeg未安装或不在系统PATH中"
|
||||||
|
return _FFMPEG_HW_ACCEL_INFO
|
||||||
|
|
||||||
|
# 检测操作系统
|
||||||
|
system = platform.system().lower()
|
||||||
|
logger.debug(f"检测硬件加速 - 操作系统: {system}")
|
||||||
|
|
||||||
|
# 获取FFmpeg支持的硬件加速器列表
|
||||||
|
try:
|
||||||
|
hwaccels_cmd = subprocess.run(
|
||||||
|
['ffmpeg', '-hide_banner', '-hwaccels'],
|
||||||
|
stdout=subprocess.PIPE, stderr=subprocess.PIPE, text=True
|
||||||
|
)
|
||||||
|
supported_hwaccels = hwaccels_cmd.stdout.lower()
|
||||||
|
except Exception as e:
|
||||||
|
logger.error(f"获取FFmpeg硬件加速器列表失败: {str(e)}")
|
||||||
|
supported_hwaccels = ""
|
||||||
|
|
||||||
|
# 根据操作系统检测不同的硬件加速器
|
||||||
|
if system == 'darwin': # macOS
|
||||||
|
_detect_macos_acceleration(supported_hwaccels)
|
||||||
|
elif system == 'windows': # Windows
|
||||||
|
_detect_windows_acceleration(supported_hwaccels)
|
||||||
|
elif system == 'linux': # Linux
|
||||||
|
_detect_linux_acceleration(supported_hwaccels)
|
||||||
|
else:
|
||||||
|
logger.warning(f"不支持的操作系统: {system}")
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["message"] = f"不支持的操作系统: {system}"
|
||||||
|
|
||||||
|
# 记录检测结果已经在启动时输出,这里不再重复输出
|
||||||
|
|
||||||
|
return _FFMPEG_HW_ACCEL_INFO
|
||||||
|
|
||||||
|
|
||||||
|
def _detect_macos_acceleration(supported_hwaccels: str) -> None:
|
||||||
|
"""
|
||||||
|
检测macOS系统的硬件加速
|
||||||
|
|
||||||
|
Args:
|
||||||
|
supported_hwaccels: FFmpeg支持的硬件加速器列表
|
||||||
|
"""
|
||||||
|
global _FFMPEG_HW_ACCEL_INFO
|
||||||
|
|
||||||
|
if 'videotoolbox' in supported_hwaccels:
|
||||||
|
# 测试videotoolbox
|
||||||
|
try:
|
||||||
|
test_cmd = subprocess.run(
|
||||||
|
["ffmpeg", "-hwaccel", "videotoolbox", "-i", "/dev/null", "-f", "null", "-"],
|
||||||
|
stderr=subprocess.PIPE, stdout=subprocess.PIPE, text=True, check=False
|
||||||
|
)
|
||||||
|
if test_cmd.returncode == 0:
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["available"] = True
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["type"] = "videotoolbox"
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["encoder"] = "h264_videotoolbox"
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["hwaccel_args"] = ["-hwaccel", "videotoolbox"]
|
||||||
|
# macOS的Metal GPU加速通常是集成GPU
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["is_dedicated_gpu"] = False
|
||||||
|
return
|
||||||
|
except Exception as e:
|
||||||
|
logger.debug(f"测试videotoolbox失败: {str(e)}")
|
||||||
|
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["message"] = "macOS系统未检测到可用的videotoolbox硬件加速"
|
||||||
|
|
||||||
|
|
||||||
|
def _detect_windows_acceleration(supported_hwaccels: str) -> None:
|
||||||
|
"""
|
||||||
|
检测Windows系统的硬件加速
|
||||||
|
|
||||||
|
Args:
|
||||||
|
supported_hwaccels: FFmpeg支持的硬件加速器列表
|
||||||
|
"""
|
||||||
|
global _FFMPEG_HW_ACCEL_INFO
|
||||||
|
|
||||||
|
# 在Windows上,首先检查显卡信息
|
||||||
|
gpu_info = _get_windows_gpu_info()
|
||||||
|
|
||||||
|
# 检查是否为AMD显卡
|
||||||
|
if 'amd' in gpu_info.lower() or 'radeon' in gpu_info.lower():
|
||||||
|
logger.info("检测到AMD显卡,为避免兼容性问题,将使用软件编码")
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["message"] = "检测到AMD显卡,为避免兼容性问题,将使用软件编码"
|
||||||
|
return
|
||||||
|
|
||||||
|
# 检查是否为Intel集成显卡
|
||||||
|
is_intel_integrated = False
|
||||||
|
if 'intel' in gpu_info.lower() and ('hd graphics' in gpu_info.lower() or 'uhd graphics' in gpu_info.lower()):
|
||||||
|
logger.info("检测到Intel集成显卡")
|
||||||
|
is_intel_integrated = True
|
||||||
|
|
||||||
|
# 检测NVIDIA CUDA支持
|
||||||
|
if 'cuda' in supported_hwaccels and 'nvidia' in gpu_info.lower():
|
||||||
|
try:
|
||||||
|
test_cmd = subprocess.run(
|
||||||
|
["ffmpeg", "-hwaccel", "cuda", "-i", "/dev/null", "-f", "null", "-"],
|
||||||
|
stderr=subprocess.PIPE, stdout=subprocess.PIPE, text=True, check=False
|
||||||
|
)
|
||||||
|
if test_cmd.returncode == 0:
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["available"] = True
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["type"] = "cuda"
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["encoder"] = "h264_nvenc"
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["hwaccel_args"] = ["-hwaccel", "cuda"]
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["is_dedicated_gpu"] = True
|
||||||
|
return
|
||||||
|
except Exception as e:
|
||||||
|
logger.debug(f"测试CUDA失败: {str(e)}")
|
||||||
|
|
||||||
|
# 检测Intel QSV支持(如果是Intel显卡)
|
||||||
|
if 'qsv' in supported_hwaccels and 'intel' in gpu_info.lower():
|
||||||
|
try:
|
||||||
|
test_cmd = subprocess.run(
|
||||||
|
["ffmpeg", "-hwaccel", "qsv", "-i", "/dev/null", "-f", "null", "-"],
|
||||||
|
stderr=subprocess.PIPE, stdout=subprocess.PIPE, text=True, check=False
|
||||||
|
)
|
||||||
|
if test_cmd.returncode == 0:
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["available"] = True
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["type"] = "qsv"
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["encoder"] = "h264_qsv"
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["hwaccel_args"] = ["-hwaccel", "qsv"]
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["is_dedicated_gpu"] = not is_intel_integrated
|
||||||
|
return
|
||||||
|
except Exception as e:
|
||||||
|
logger.debug(f"测试QSV失败: {str(e)}")
|
||||||
|
|
||||||
|
# 检测D3D11VA支持
|
||||||
|
if 'd3d11va' in supported_hwaccels:
|
||||||
|
try:
|
||||||
|
test_cmd = subprocess.run(
|
||||||
|
["ffmpeg", "-hwaccel", "d3d11va", "-i", "/dev/null", "-f", "null", "-"],
|
||||||
|
stderr=subprocess.PIPE, stdout=subprocess.PIPE, text=True, check=False
|
||||||
|
)
|
||||||
|
if test_cmd.returncode == 0:
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["available"] = True
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["type"] = "d3d11va"
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["encoder"] = "h264" # D3D11VA只用于解码,编码仍使用软件编码器
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["hwaccel_args"] = ["-hwaccel", "d3d11va"]
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["is_dedicated_gpu"] = not is_intel_integrated
|
||||||
|
return
|
||||||
|
except Exception as e:
|
||||||
|
logger.debug(f"测试D3D11VA失败: {str(e)}")
|
||||||
|
|
||||||
|
# 检测DXVA2支持
|
||||||
|
if 'dxva2' in supported_hwaccels:
|
||||||
|
try:
|
||||||
|
test_cmd = subprocess.run(
|
||||||
|
["ffmpeg", "-hwaccel", "dxva2", "-i", "/dev/null", "-f", "null", "-"],
|
||||||
|
stderr=subprocess.PIPE, stdout=subprocess.PIPE, text=True, check=False
|
||||||
|
)
|
||||||
|
if test_cmd.returncode == 0:
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["available"] = True
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["type"] = "dxva2"
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["encoder"] = "h264" # DXVA2只用于解码,编码仍使用软件编码器
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["hwaccel_args"] = ["-hwaccel", "dxva2"]
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["is_dedicated_gpu"] = not is_intel_integrated
|
||||||
|
return
|
||||||
|
except Exception as e:
|
||||||
|
logger.debug(f"测试DXVA2失败: {str(e)}")
|
||||||
|
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["message"] = f"Windows系统未检测到可用的硬件加速,显卡信息: {gpu_info}"
|
||||||
|
|
||||||
|
|
||||||
|
def _detect_linux_acceleration(supported_hwaccels: str) -> None:
|
||||||
|
"""
|
||||||
|
检测Linux系统的硬件加速
|
||||||
|
|
||||||
|
Args:
|
||||||
|
supported_hwaccels: FFmpeg支持的硬件加速器列表
|
||||||
|
"""
|
||||||
|
global _FFMPEG_HW_ACCEL_INFO
|
||||||
|
|
||||||
|
# 获取Linux显卡信息
|
||||||
|
gpu_info = _get_linux_gpu_info()
|
||||||
|
is_nvidia = 'nvidia' in gpu_info.lower()
|
||||||
|
is_intel = 'intel' in gpu_info.lower()
|
||||||
|
is_amd = 'amd' in gpu_info.lower() or 'radeon' in gpu_info.lower()
|
||||||
|
|
||||||
|
# 检测NVIDIA CUDA支持
|
||||||
|
if 'cuda' in supported_hwaccels and is_nvidia:
|
||||||
|
try:
|
||||||
|
test_cmd = subprocess.run(
|
||||||
|
["ffmpeg", "-hwaccel", "cuda", "-i", "/dev/null", "-f", "null", "-"],
|
||||||
|
stderr=subprocess.PIPE, stdout=subprocess.PIPE, text=True, check=False
|
||||||
|
)
|
||||||
|
if test_cmd.returncode == 0:
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["available"] = True
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["type"] = "cuda"
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["encoder"] = "h264_nvenc"
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["hwaccel_args"] = ["-hwaccel", "cuda"]
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["is_dedicated_gpu"] = True
|
||||||
|
return
|
||||||
|
except Exception as e:
|
||||||
|
logger.debug(f"测试CUDA失败: {str(e)}")
|
||||||
|
|
||||||
|
# 检测VAAPI支持
|
||||||
|
if 'vaapi' in supported_hwaccels:
|
||||||
|
# 检查是否存在渲染设备
|
||||||
|
render_devices = ['/dev/dri/renderD128', '/dev/dri/renderD129']
|
||||||
|
render_device = None
|
||||||
|
for device in render_devices:
|
||||||
|
if os.path.exists(device):
|
||||||
|
render_device = device
|
||||||
|
break
|
||||||
|
|
||||||
|
if render_device:
|
||||||
|
try:
|
||||||
|
test_cmd = subprocess.run(
|
||||||
|
["ffmpeg", "-hwaccel", "vaapi", "-vaapi_device", render_device,
|
||||||
|
"-i", "/dev/null", "-f", "null", "-"],
|
||||||
|
stderr=subprocess.PIPE, stdout=subprocess.PIPE, text=True, check=False
|
||||||
|
)
|
||||||
|
if test_cmd.returncode == 0:
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["available"] = True
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["type"] = "vaapi"
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["encoder"] = "h264_vaapi"
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["hwaccel_args"] = ["-hwaccel", "vaapi", "-vaapi_device", render_device]
|
||||||
|
# 根据显卡类型判断是否为独立显卡
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["is_dedicated_gpu"] = is_nvidia or (is_amd and not is_intel)
|
||||||
|
return
|
||||||
|
except Exception as e:
|
||||||
|
logger.debug(f"测试VAAPI失败: {str(e)}")
|
||||||
|
|
||||||
|
# 检测Intel QSV支持
|
||||||
|
if 'qsv' in supported_hwaccels and is_intel:
|
||||||
|
try:
|
||||||
|
test_cmd = subprocess.run(
|
||||||
|
["ffmpeg", "-hwaccel", "qsv", "-i", "/dev/null", "-f", "null", "-"],
|
||||||
|
stderr=subprocess.PIPE, stdout=subprocess.PIPE, text=True, check=False
|
||||||
|
)
|
||||||
|
if test_cmd.returncode == 0:
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["available"] = True
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["type"] = "qsv"
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["encoder"] = "h264_qsv"
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["hwaccel_args"] = ["-hwaccel", "qsv"]
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["is_dedicated_gpu"] = False # Intel QSV通常是集成GPU
|
||||||
|
return
|
||||||
|
except Exception as e:
|
||||||
|
logger.debug(f"测试QSV失败: {str(e)}")
|
||||||
|
|
||||||
|
_FFMPEG_HW_ACCEL_INFO["message"] = f"Linux系统未检测到可用的硬件加速,显卡信息: {gpu_info}"
|
||||||
|
|
||||||
|
|
||||||
|
def _get_windows_gpu_info() -> str:
|
||||||
|
"""
|
||||||
|
获取Windows系统的显卡信息
|
||||||
|
|
||||||
|
Returns:
|
||||||
|
str: 显卡信息字符串
|
||||||
|
"""
|
||||||
|
try:
|
||||||
|
gpu_info = subprocess.run(
|
||||||
|
['wmic', 'path', 'win32_VideoController', 'get', 'name'],
|
||||||
|
stdout=subprocess.PIPE, stderr=subprocess.PIPE, text=True, check=False
|
||||||
|
)
|
||||||
|
return gpu_info.stdout
|
||||||
|
except Exception as e:
|
||||||
|
logger.warning(f"获取Windows显卡信息失败: {str(e)}")
|
||||||
|
return "Unknown GPU"
|
||||||
|
|
||||||
|
|
||||||
|
def _get_linux_gpu_info() -> str:
|
||||||
|
"""
|
||||||
|
获取Linux系统的显卡信息
|
||||||
|
|
||||||
|
Returns:
|
||||||
|
str: 显卡信息字符串
|
||||||
|
"""
|
||||||
|
try:
|
||||||
|
# 尝试使用lspci命令
|
||||||
|
gpu_info = subprocess.run(
|
||||||
|
['lspci', '-v', '-nn', '|', 'grep', '-i', 'vga\\|display'],
|
||||||
|
stdout=subprocess.PIPE, stderr=subprocess.PIPE, text=True, shell=True, check=False
|
||||||
|
)
|
||||||
|
if gpu_info.stdout:
|
||||||
|
return gpu_info.stdout
|
||||||
|
|
||||||
|
# 如果lspci命令失败,尝试使用glxinfo
|
||||||
|
gpu_info = subprocess.run(
|
||||||
|
['glxinfo', '|', 'grep', '-i', 'vendor\\|renderer'],
|
||||||
|
stdout=subprocess.PIPE, stderr=subprocess.PIPE, text=True, shell=True, check=False
|
||||||
|
)
|
||||||
|
if gpu_info.stdout:
|
||||||
|
return gpu_info.stdout
|
||||||
|
|
||||||
|
return "Unknown GPU"
|
||||||
|
except Exception as e:
|
||||||
|
logger.warning(f"获取Linux显卡信息失败: {str(e)}")
|
||||||
|
return "Unknown GPU"
|
||||||
|
|
||||||
|
|
||||||
|
def get_ffmpeg_hwaccel_args() -> List[str]:
|
||||||
|
"""
|
||||||
|
获取FFmpeg硬件加速参数
|
||||||
|
|
||||||
|
Returns:
|
||||||
|
List[str]: FFmpeg硬件加速参数列表
|
||||||
|
"""
|
||||||
|
# 如果还没有检测过,先进行检测
|
||||||
|
if _FFMPEG_HW_ACCEL_INFO["type"] is None:
|
||||||
|
detect_hardware_acceleration()
|
||||||
|
|
||||||
|
return _FFMPEG_HW_ACCEL_INFO["hwaccel_args"]
|
||||||
|
|
||||||
|
|
||||||
|
def get_ffmpeg_hwaccel_type() -> Optional[str]:
|
||||||
|
"""
|
||||||
|
获取FFmpeg硬件加速类型
|
||||||
|
|
||||||
|
Returns:
|
||||||
|
Optional[str]: 硬件加速类型,如果不支持则返回None
|
||||||
|
"""
|
||||||
|
# 如果还没有检测过,先进行检测
|
||||||
|
if _FFMPEG_HW_ACCEL_INFO["type"] is None:
|
||||||
|
detect_hardware_acceleration()
|
||||||
|
|
||||||
|
return _FFMPEG_HW_ACCEL_INFO["type"] if _FFMPEG_HW_ACCEL_INFO["available"] else None
|
||||||
|
|
||||||
|
|
||||||
|
def get_ffmpeg_hwaccel_encoder() -> Optional[str]:
|
||||||
|
"""
|
||||||
|
获取FFmpeg硬件加速编码器
|
||||||
|
|
||||||
|
Returns:
|
||||||
|
Optional[str]: 硬件加速编码器,如果不支持则返回None
|
||||||
|
"""
|
||||||
|
# 如果还没有检测过,先进行检测
|
||||||
|
if _FFMPEG_HW_ACCEL_INFO["type"] is None:
|
||||||
|
detect_hardware_acceleration()
|
||||||
|
|
||||||
|
return _FFMPEG_HW_ACCEL_INFO["encoder"] if _FFMPEG_HW_ACCEL_INFO["available"] else None
|
||||||
|
|
||||||
|
|
||||||
|
def get_ffmpeg_hwaccel_info() -> Dict[str, Union[bool, str, List[str], None]]:
|
||||||
|
"""
|
||||||
|
获取FFmpeg硬件加速信息
|
||||||
|
|
||||||
|
Returns:
|
||||||
|
Dict: 包含硬件加速信息的字典
|
||||||
|
"""
|
||||||
|
# 如果还没有检测过,先进行检测
|
||||||
|
if _FFMPEG_HW_ACCEL_INFO["type"] is None:
|
||||||
|
detect_hardware_acceleration()
|
||||||
|
|
||||||
|
return _FFMPEG_HW_ACCEL_INFO
|
||||||
|
|
||||||
|
|
||||||
|
def is_ffmpeg_hwaccel_available() -> bool:
|
||||||
|
"""
|
||||||
|
检查是否有可用的FFmpeg硬件加速
|
||||||
|
|
||||||
|
Returns:
|
||||||
|
bool: 如果有可用的硬件加速则返回True,否则返回False
|
||||||
|
"""
|
||||||
|
# 如果还没有检测过,先进行检测
|
||||||
|
if _FFMPEG_HW_ACCEL_INFO["type"] is None:
|
||||||
|
detect_hardware_acceleration()
|
||||||
|
|
||||||
|
return _FFMPEG_HW_ACCEL_INFO["available"]
|
||||||
|
|
||||||
|
|
||||||
|
def is_dedicated_gpu() -> bool:
|
||||||
|
"""
|
||||||
|
检查是否使用独立显卡进行硬件加速
|
||||||
|
|
||||||
|
Returns:
|
||||||
|
bool: 如果使用独立显卡则返回True,否则返回False
|
||||||
|
"""
|
||||||
|
# 如果还没有检测过,先进行检测
|
||||||
|
if _FFMPEG_HW_ACCEL_INFO["type"] is None:
|
||||||
|
detect_hardware_acceleration()
|
||||||
|
|
||||||
|
return _FFMPEG_HW_ACCEL_INFO["is_dedicated_gpu"]
|
||||||
@ -19,6 +19,8 @@ from typing import List, Dict
|
|||||||
from loguru import logger
|
from loguru import logger
|
||||||
from tqdm import tqdm
|
from tqdm import tqdm
|
||||||
|
|
||||||
|
from app.utils import ffmpeg_utils
|
||||||
|
|
||||||
|
|
||||||
class VideoProcessor:
|
class VideoProcessor:
|
||||||
def __init__(self, video_path: str):
|
def __init__(self, video_path: str):
|
||||||
@ -115,14 +117,8 @@ class VideoProcessor:
|
|||||||
|
|
||||||
# 确定硬件加速器选项
|
# 确定硬件加速器选项
|
||||||
hw_accel = []
|
hw_accel = []
|
||||||
if use_hw_accel:
|
if use_hw_accel and ffmpeg_utils.is_ffmpeg_hwaccel_available():
|
||||||
# 尝试检测可用的硬件加速器
|
hw_accel = ffmpeg_utils.get_ffmpeg_hwaccel_args()
|
||||||
hw_accel_options = self._detect_hw_accelerator()
|
|
||||||
if hw_accel_options:
|
|
||||||
hw_accel = hw_accel_options
|
|
||||||
logger.info(f"使用硬件加速: {' '.join(hw_accel)}")
|
|
||||||
else:
|
|
||||||
logger.warning("未检测到可用的硬件加速器,使用软件解码")
|
|
||||||
|
|
||||||
# 提取帧
|
# 提取帧
|
||||||
frame_numbers = []
|
frame_numbers = []
|
||||||
@ -173,119 +169,9 @@ class VideoProcessor:
|
|||||||
Returns:
|
Returns:
|
||||||
List[str]: 硬件加速器ffmpeg命令参数
|
List[str]: 硬件加速器ffmpeg命令参数
|
||||||
"""
|
"""
|
||||||
# 检测操作系统
|
# 使用集中式硬件加速检测
|
||||||
import platform
|
if ffmpeg_utils.is_ffmpeg_hwaccel_available():
|
||||||
system = platform.system().lower()
|
return ffmpeg_utils.get_ffmpeg_hwaccel_args()
|
||||||
|
|
||||||
# 测试不同的硬件加速器
|
|
||||||
accelerators = []
|
|
||||||
|
|
||||||
if system == 'darwin': # macOS
|
|
||||||
# 测试 videotoolbox (Apple 硬件加速)
|
|
||||||
test_cmd = [
|
|
||||||
"ffmpeg",
|
|
||||||
"-hide_banner",
|
|
||||||
"-loglevel", "error",
|
|
||||||
"-hwaccel", "videotoolbox",
|
|
||||||
"-i", self.video_path,
|
|
||||||
"-t", "0.1",
|
|
||||||
"-f", "null",
|
|
||||||
"-"
|
|
||||||
]
|
|
||||||
try:
|
|
||||||
subprocess.run(test_cmd, capture_output=True, check=True)
|
|
||||||
return ["-hwaccel", "videotoolbox"]
|
|
||||||
except subprocess.CalledProcessError:
|
|
||||||
pass
|
|
||||||
|
|
||||||
elif system == 'linux':
|
|
||||||
# 测试 VAAPI
|
|
||||||
test_cmd = [
|
|
||||||
"ffmpeg",
|
|
||||||
"-hide_banner",
|
|
||||||
"-loglevel", "error",
|
|
||||||
"-hwaccel", "vaapi",
|
|
||||||
"-i", self.video_path,
|
|
||||||
"-t", "0.1",
|
|
||||||
"-f", "null",
|
|
||||||
"-"
|
|
||||||
]
|
|
||||||
try:
|
|
||||||
subprocess.run(test_cmd, capture_output=True, check=True)
|
|
||||||
return ["-hwaccel", "vaapi"]
|
|
||||||
except subprocess.CalledProcessError:
|
|
||||||
pass
|
|
||||||
|
|
||||||
# 尝试 CUDA
|
|
||||||
test_cmd = [
|
|
||||||
"ffmpeg",
|
|
||||||
"-hide_banner",
|
|
||||||
"-loglevel", "error",
|
|
||||||
"-hwaccel", "cuda",
|
|
||||||
"-i", self.video_path,
|
|
||||||
"-t", "0.1",
|
|
||||||
"-f", "null",
|
|
||||||
"-"
|
|
||||||
]
|
|
||||||
try:
|
|
||||||
subprocess.run(test_cmd, capture_output=True, check=True)
|
|
||||||
return ["-hwaccel", "cuda"]
|
|
||||||
except subprocess.CalledProcessError:
|
|
||||||
pass
|
|
||||||
|
|
||||||
elif system == 'windows':
|
|
||||||
# 测试 CUDA
|
|
||||||
test_cmd = [
|
|
||||||
"ffmpeg",
|
|
||||||
"-hide_banner",
|
|
||||||
"-loglevel", "error",
|
|
||||||
"-hwaccel", "cuda",
|
|
||||||
"-i", self.video_path,
|
|
||||||
"-t", "0.1",
|
|
||||||
"-f", "null",
|
|
||||||
"-"
|
|
||||||
]
|
|
||||||
try:
|
|
||||||
subprocess.run(test_cmd, capture_output=True, check=True)
|
|
||||||
return ["-hwaccel", "cuda"]
|
|
||||||
except subprocess.CalledProcessError:
|
|
||||||
pass
|
|
||||||
|
|
||||||
# 测试 D3D11VA
|
|
||||||
test_cmd = [
|
|
||||||
"ffmpeg",
|
|
||||||
"-hide_banner",
|
|
||||||
"-loglevel", "error",
|
|
||||||
"-hwaccel", "d3d11va",
|
|
||||||
"-i", self.video_path,
|
|
||||||
"-t", "0.1",
|
|
||||||
"-f", "null",
|
|
||||||
"-"
|
|
||||||
]
|
|
||||||
try:
|
|
||||||
subprocess.run(test_cmd, capture_output=True, check=True)
|
|
||||||
return ["-hwaccel", "d3d11va"]
|
|
||||||
except subprocess.CalledProcessError:
|
|
||||||
pass
|
|
||||||
|
|
||||||
# 测试 DXVA2
|
|
||||||
test_cmd = [
|
|
||||||
"ffmpeg",
|
|
||||||
"-hide_banner",
|
|
||||||
"-loglevel", "error",
|
|
||||||
"-hwaccel", "dxva2",
|
|
||||||
"-i", self.video_path,
|
|
||||||
"-t", "0.1",
|
|
||||||
"-f", "null",
|
|
||||||
"-"
|
|
||||||
]
|
|
||||||
try:
|
|
||||||
subprocess.run(test_cmd, capture_output=True, check=True)
|
|
||||||
return ["-hwaccel", "dxva2"]
|
|
||||||
except subprocess.CalledProcessError:
|
|
||||||
pass
|
|
||||||
|
|
||||||
# 如果没有找到可用的硬件加速器
|
|
||||||
return []
|
return []
|
||||||
|
|
||||||
def process_video_pipeline(self,
|
def process_video_pipeline(self,
|
||||||
|
|||||||
@ -1,5 +1,5 @@
|
|||||||
[app]
|
[app]
|
||||||
project_version="0.6.1"
|
project_version="0.6.2"
|
||||||
# 支持视频理解的大模型提供商
|
# 支持视频理解的大模型提供商
|
||||||
# gemini (谷歌, 需要 VPN)
|
# gemini (谷歌, 需要 VPN)
|
||||||
# siliconflow (硅基流动)
|
# siliconflow (硅基流动)
|
||||||
|
|||||||
8
webui.py
8
webui.py
@ -7,6 +7,7 @@ from webui.components import basic_settings, video_settings, audio_settings, sub
|
|||||||
review_settings, merge_settings, system_settings
|
review_settings, merge_settings, system_settings
|
||||||
# from webui.utils import cache, file_utils
|
# from webui.utils import cache, file_utils
|
||||||
from app.utils import utils
|
from app.utils import utils
|
||||||
|
from app.utils import ffmpeg_utils
|
||||||
from app.models.schema import VideoClipParams, VideoAspect
|
from app.models.schema import VideoClipParams, VideoAspect
|
||||||
|
|
||||||
|
|
||||||
@ -193,6 +194,13 @@ def main():
|
|||||||
init_log()
|
init_log()
|
||||||
init_global_state()
|
init_global_state()
|
||||||
|
|
||||||
|
# 检测FFmpeg硬件加速
|
||||||
|
hwaccel_info = ffmpeg_utils.detect_hardware_acceleration()
|
||||||
|
if hwaccel_info["available"]:
|
||||||
|
logger.info(f"FFmpeg硬件加速检测结果: 可用 | 类型: {hwaccel_info['type']} | 编码器: {hwaccel_info['encoder']} | 独立显卡: {hwaccel_info['is_dedicated_gpu']} | 参数: {hwaccel_info['hwaccel_args']}")
|
||||||
|
else:
|
||||||
|
logger.warning(f"FFmpeg硬件加速不可用: {hwaccel_info['message']}, 将使用CPU软件编码")
|
||||||
|
|
||||||
# 仅初始化基本资源,避免过早地加载依赖PyTorch的资源
|
# 仅初始化基本资源,避免过早地加载依赖PyTorch的资源
|
||||||
# 检查是否能分解utils.init_resources()为基本资源和高级资源(如依赖PyTorch的资源)
|
# 检查是否能分解utils.init_resources()为基本资源和高级资源(如依赖PyTorch的资源)
|
||||||
try:
|
try:
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user