AForge.Video.FFMPEG.dll 加载失败解决指南
问题现象

使用 AForge.NET 做摄像头录制时,调用 VideoFileWriter 或点击"开始录制"按钮后,程序报错:
未能加载文件或程序集 "AForge.Video.FFMPEG.dll" 或它的某一个依赖项。找不到指定的模块。
程序能正常打开摄像头显示画面,但无法录制视频。
错误原因
AForge.Video.FFMPEG.dll 是一个 C++/CLI 混合模式程序集,它的依赖链如下:
AForge.Video.FFMPEG.dll (.NET 包装层)
├── MSVCR100.dll (VC++ 2010 运行库)
├── avformat-58.dll (FFmpeg)
├── avcodec-58.dll (FFmpeg)
├── avutil-56.dll (FFmpeg)
└── swscale-5.dll (FFmpeg)
加载失败通常有三个原因:
原因 1:原生 FFmpeg DLL 缺失
avcodec-58.dll、avformat-58.dll 等 FFmpeg 原生 DLL 没有被复制到程序输出目录。这些 DLL 通常放在项目的 Lib\x64\ 或 Lib\x86\ 目录下,但构建时不会自动复制。
原因 2:VC++ 运行库缺失(最常见)
AForge.Video.FFMPEG.dll 是使用 Visual Studio 2010 编译的,依赖 MSVCR100.dll(Release 版)或 MSVCR100D.dll(Debug 版)。如果目标机器没有安装 VC++ 2010 可再发行组件包,就会报错。
区分 Release/Debug 版本:
用 dumpbin /dependents AForge.Video.FFMPEG.dll 查看:
MSVCR100.dll--- Release 版,可随程序分发MSVCR100D.dll--- Debug 版,不可分发(需要安装 VS 2010)
原因 3:平台架构不匹配
.NET 项目平台目标(x86/x64)与 AForge.Video.FFMPEG.dll 的实际架构不一致。在 .csproj 的引用声明中如果标记了错误的 processorArchitecture,Fusion 加载器在运行时可能会跳过该程序集。
解决方案
第一步:诊断问题
用 VS 自带的 dumpbin 检查 DLL 的架构和依赖:
bash
# 检查架构(8664 = x64, 14C = x86)
dumpbin /headers AForge.Video.FFMPEG.dll | findstr machine
# 查看依赖的 CRT
dumpbin /dependents AForge.Video.FFMPEG.dll | findstr MSVCR
第二步:确保原生 DLL 复制到输出目录
在 .csproj 中添加构建后事件(Target),根据平台自动复制对应的原生 DLL:
xml
<Target Name="CopyFFmpegNativeDlls" AfterTargets="Build">
<ItemGroup>
<_FFmpegDlls Include="Lib\$(PlatformTarget)\*.dll" />
</ItemGroup>
<Copy SourceFiles="@(_FFmpegDlls)"
DestinationFolder="$(OutputPath)"
Condition="Exists('Lib\$(PlatformTarget)')" />
</Target>
要求项目目录结构如下:
Project/
├── Lib/
│ ├── x64/ # x64 版所有 DLL(含 MSVCR100.dll)
│ │ ├── AForge.Video.FFMPEG.dll
│ │ ├── avcodec-58.dll
│ │ ├── avformat-58.dll
│ │ ├── MSVCR100.dll ← 关键!
│ │ └── ...
│ ├── x86/ # x86 版所有 DLL
│ │ └── ...
│ ├── AForge.dll
│ └── ...
第三步:修复 processorArchitecture
在 .csproj 的 <Reference> 中,确保 processorArchitecture 与实际架构一致:
| 实际架构 | processorArchitecture |
|---|---|
| x64 | amd64 或留空 |
| x86 | x86 或留空 |
| AnyCPU | MSIL 或留空 |
第四步:补充 VC++ 运行库
方式 A:随程序分发 MSVCR100.dll(推荐)
从 VC++ 2010 可再发行组件包中提取 MSVCR100.dll,放入 Lib\x64\ 目录,由构建事件自动复制。
提取方法:
- 下载 vcredist_x64.exe
- 解压:
vcredist_x64.exe /x:extract_dir - 解压
vc_red.cab:expand vc_red.cab -F:* output_dir - 找到
F_CENTRAL_msvcr100_x64,重命名为MSVCR100.dll
方式 B:安装 VC++ 2010 可再发行组件包
让客户安装 Microsoft Visual C++ 2010 Redistributable (x64)。
第五步:验证
构建后检查输出目录是否包含以下全部文件:
bin\Debug\
├── Fountain.WinForm.VideoDemo.exe
├── AForge.Video.FFMPEG.dll ← .NET 包装层
├── MSVCR100.dll ← VC++ 运行库
├── avcodec-58.dll ← FFmpeg 原生库
├── avformat-58.dll
├── avutil-56.dll
├── swscale-5.dll
├── avdevice-58.dll
├── avfilter-7.dll
├── swresample-3.dll
├── postproc-55.dll
└── 其他托管 DLL...
常见问答
Q:为什么 Debug 版会依赖 MSVCR100D.dll?
A:Lib\x86\ 中提供的 x86 版 AForge.Video.FFMPEG.dll 是 Debug 编译的,依赖 MSVCR100D.dll(仅开发机有)。建议改用 Release 编译的 x64 版本(依赖 MSVCR100.dll)。
Q:一定要用 x64 吗?
A:x64 更通用,且能处理大内存。如果摄像头驱动只支持 32 位,则需要用 x86 版本并确保 MSVCR100D.dll 可用。
Q:安装 VC++ 2010 报错"无法访问网络位置"怎么办?
A:Win10/11 上这是已知问题。直接用提取 MSVCR100.dll 随程序分发的方式即可解决。