.NET讀取視訊資訊、視訊截圖
在.NET中處理視訊是一件痛苦的事情,.NET並沒有提供視訊處理的類。於是咱們只能找一些第三方的類庫或者自己實現,在專案時間比較趕的情況下,自己實現是不可能的了,而且說不定會留下很多坑。所以一般情況下,咱們都是找一些靠譜的第三方類庫,畢竟別人確實實現得蠻好的。
這次的專案是一個資訊釋出APP,其中一個模組功能有些類似微信朋友圈,釋出內容需要支援圖片、音訊、視訊等。其他的都很好處理,但視訊的處理著實讓我費了一番勁兒,之前也沒有接觸過視訊處理的專案,甚至對視訊處理的瞭解也挺少的。於是我Google了大半天(國內搜尋引擎很少相關資料,此處建議使用Google Code),找到了一些解決方案,我選取了其中的2個。
1、AVBlocks
不得不說AVBlocks確實是做得挺不錯的,其主要功能是處理視訊、音訊、圖片等多媒體檔案;AVBlocks官網提供了非常詳細的Demo,比較可惜的是Demo的註釋跟說明比較少(或者只是我沒有發現),我在開始工作前把這個Demo裡面38個專案通讀了一遍(基本每個專案只包含一種功能,程式碼簡潔)。
a)功能簡介 主要包括視訊的格式、流、位元率、顏色格式(Color Format)、寬高比、解析度、幀率、掃描方式(Scan Type;這個引數我是真的不認識); 獲取音訊、圖片資訊我還沒用到,不過據官網的介紹看起來還是挺好用的,AVBlocks支援的格式很多,值得一用。 b)使用方法 使用AVBlocks的方法很簡單,直接在你的專案中引用 AVBlocks.clr4.x64.dll ,然後複製 AVBlocks64.dll 到你的專案生成目錄下(如果是 WinForm,則複製到輸出目錄根目錄;如果是 ASP.NET,則複製到輸出目錄 bin 目錄)就可以了。 如果執行時報以下錯誤: “無法載入 DLL“AVBlocks64.dll”: 找不到指定的模組。 (異常來自 HRESULT:0x8007007E)。” 不用懷疑,肯定是你沒有把AVBlocks64.dll複製到輸出目錄下。 c)上線注意事項 之所以寫這部分是因為我在上線的時候就傻乎乎跳進了一個坑,Windows Server 2008/2008 R2/2012/2012 R2等伺服器預設是沒有安裝wmvcore.dll。這需要我們手動安裝Media Foundation(媒體基礎)或者Desktop Experience(桌面體驗)功能。我選擇安裝“桌面體驗”功能。 大概操作是這樣:伺服器管理器->功能->新增,然後找到“桌面體驗”,勾選、確定,安裝完成後重啟就可以了。 不然會一直報錯“未將物件引用設定到物件的例項”。其實官網有說明,只是我一開始沒留意。
下面是這部分的程式碼:
public class VideoInfo
{
//public StreamType Container { get; set; }
//public int Streams { get; set; }
public string FileName { get; set; }
public string CaptureFile { get; set; }
public MediaType MediaType { get ; set; }
public StreamType StreamType { get; set; }
public StreamSubType StreamSubType { get; set; }
public int Id { get; set; }
public double Duration { get; set; }
public int Bitrate { get; set; }
public BitrateMode BitrateMode { get; set; }
public ColorFormat ColorFormat { get; set; }
public int DisplayRatioWidth { get; set; }
public int DisplayRatioHeight { get; set; }
public bool FrameBottomUp { get; set; }
public int FrameWidth { get; set; }
public int FrameHeight { get; set; }
public double FrameRate { get; set; }
public ScanType ScanType { get; set; }
}
public static VideoInfo GetVideoInfo(string inputFile)
{
VideoInfo videoInfo = new VideoInfo();
using (MediaInfo info = new MediaInfo())
{
info.Inputs[0].File = inputFile;
if (!info.Open())
{
return null;
}
videoInfo = GetStreams(info)[0];
}
// videoInfo.CaptureFile = CatchImg(inputFile, videoInfo.FrameWidth, videoInfo.FrameHeight);
return videoInfo;
}
private static List<VideoInfo> GetStreams(MediaInfo mediaInfo)
{
List<VideoInfo> videoInfos = new List<VideoInfo>();
foreach (var socket in mediaInfo.Outputs)
{
VideoInfo videoInfo = new VideoInfo();
for (int streamIndex = 0; streamIndex < socket.Pins.Count; streamIndex++)
{
StreamInfo si = socket.Pins[streamIndex].StreamInfo;
videoInfo.MediaType = si.MediaType;
videoInfo.StreamType = si.StreamType;
videoInfo.StreamSubType = si.StreamSubType;
videoInfo.Id = si.ID;
videoInfo.Duration = si.Duration;
if (MediaType.Video == si.MediaType)
{
VideoStreamInfo vsi = si as VideoStreamInfo;
videoInfo.Bitrate = vsi.Bitrate;
videoInfo.BitrateMode = vsi.BitrateMode;
videoInfo.ColorFormat = vsi.ColorFormat;
videoInfo.DisplayRatioWidth = vsi.DisplayRatioWidth;
videoInfo.DisplayRatioHeight = vsi.DisplayRatioHeight;
videoInfo.FrameBottomUp = vsi.FrameBottomUp;
videoInfo.FrameWidth = vsi.FrameWidth;
videoInfo.FrameHeight = vsi.FrameHeight;
videoInfo.FrameRate = vsi.FrameRate;
videoInfo.ScanType = vsi.ScanType;
}
videoInfos.Add(videoInfo);
}
}
return videoInfos;
}
2、FFMpeg
在專案中,我需要隨機擷取視訊中其中一幀的圖片作為視訊封面,所以我找到了FFMpeg只是簡單的做個截圖功能。
其實FFMpeg功能很強大,想轉換視訊格式什麼的,推薦大家有興趣讀一下這篇文章:
我簡單介紹下我專案中的使用:
a)複製ffMpeg.exe到系統目錄下,目錄隨意,在第二步進行配置;
b)需在Web.config的appSettings節點中配置ffmpeg.exe的路徑,<add key="ffmpeg" value="plugins\ffmpeg.exe" />;
c)上程式碼;
/// <summary>
/// 使用ffMpeg.exe擷取視訊圖片(第一幀)
/// *需在Web.config的appSettings節點中配置ffmpeg.exe的路徑*
/// *<add key="ffmpeg" value="plugins\ffmpeg.exe" />*
/// </summary>
/// <param name="vedioPath">視訊路徑</param>
/// <param name="saveImgWidth">儲存的圖片寬度</param>
/// <param name="saveImgHeight">儲存的圖片高度</param>
/// <returns>儲存後的圖片路徑(去除基路徑)</returns>
public static string CatchImg(string vedioPath, int saveImgWidth, int saveImgHeight)
{
string ffmpeg = AppDomain.CurrentDomain.BaseDirectory + "\\" + System.Configuration.ConfigurationSettings.AppSettings["ffmpeg"];
if ((!System.IO.File.Exists(ffmpeg)) || (!System.IO.File.Exists(vedioPath)))
{
return "";
}
string saveImgPath = System.IO.Path.ChangeExtension(vedioPath, ".jpg");
string saveImgSize = string.Format("{0}x{1}", saveImgWidth, saveImgHeight);
ProcessStartInfo startInfo = new ProcessStartInfo(ffmpeg);
startInfo.WindowStyle = System.Diagnostics.ProcessWindowStyle.Hidden;
startInfo.Arguments = string.Format(" -i \"{0}\" -y -f image2 -t 0.001 -s \"{1}\" \"{2}\"", vedioPath, saveImgSize, saveImgPath);
System.Diagnostics.Process.Start(startInfo);
return saveImgPath.Replace(AppDomain.CurrentDomain.BaseDirectory, "");
}
以上就是這次我關於.NET視訊處理的一些經驗。
最後附上這個類的完整程式碼:
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Text;
using PrimoSoftware.AVBlocks;
namespace JHD.Utils
{
public class AvInfoUtil
{
public class VideoInfo
{
//public StreamType Container { get; set; }
//public int Streams { get; set; }
public string FileName { get; set; }
public string CaptureFile { get; set; }
public MediaType MediaType { get; set; }
public StreamType StreamType { get; set; }
public StreamSubType StreamSubType { get; set; }
public int Id { get; set; }
public double Duration { get; set; }
public int Bitrate { get; set; }
public BitrateMode BitrateMode { get; set; }
public ColorFormat ColorFormat { get; set; }
public int DisplayRatioWidth { get; set; }
public int DisplayRatioHeight { get; set; }
public bool FrameBottomUp { get; set; }
public int FrameWidth { get; set; }
public int FrameHeight { get; set; }
public double FrameRate { get; set; }
public ScanType ScanType { get; set; }
}
public static VideoInfo GetVideoInfo(string inputFile)
{
VideoInfo videoInfo = new VideoInfo();
using (MediaInfo info = new MediaInfo())
{
info.Inputs[0].File = inputFile;
if (!info.Open())
{
return null;
}
videoInfo = GetStreams(info)[0];
}
videoInfo.CaptureFile = CatchImg(inputFile, videoInfo.FrameWidth, videoInfo.FrameHeight);
return videoInfo;
}
private static List<VideoInfo> GetStreams(MediaInfo mediaInfo)
{
List<VideoInfo> videoInfos = new List<VideoInfo>();
foreach (var socket in mediaInfo.Outputs)
{
VideoInfo videoInfo = new VideoInfo();
for (int streamIndex = 0; streamIndex < socket.Pins.Count; streamIndex++)
{
StreamInfo si = socket.Pins[streamIndex].StreamInfo;
videoInfo.MediaType = si.MediaType;
videoInfo.StreamType = si.StreamType;
videoInfo.StreamSubType = si.StreamSubType;
videoInfo.Id = si.ID;
videoInfo.Duration = si.Duration;
if (MediaType.Video == si.MediaType)
{
VideoStreamInfo vsi = si as VideoStreamInfo;
videoInfo.Bitrate = vsi.Bitrate;
videoInfo.BitrateMode = vsi.BitrateMode;
videoInfo.ColorFormat = vsi.ColorFormat;
videoInfo.DisplayRatioWidth = vsi.DisplayRatioWidth;
videoInfo.DisplayRatioHeight = vsi.DisplayRatioHeight;
videoInfo.FrameBottomUp = vsi.FrameBottomUp;
videoInfo.FrameWidth = vsi.FrameWidth;
videoInfo.FrameHeight = vsi.FrameHeight;
videoInfo.FrameRate = vsi.FrameRate;
videoInfo.ScanType = vsi.ScanType;
}
videoInfos.Add(videoInfo);
}
}
return videoInfos;
}
/// <summary>
/// 使用ffMpeg.exe擷取視訊圖片(第一幀)
/// *需在Web.config的appSettings節點中配置ffmpeg.exe的路徑*
/// *<add key="ffmpeg" value="plugins\ffmpeg.exe" />*
/// </summary>
/// <param name="vedioPath">視訊路徑</param>
/// <param name="saveImgWidth">儲存的圖片寬度</param>
/// <param name="saveImgHeight">儲存的圖片高度</param>
/// <returns>儲存後的圖片路徑(去除基路徑)</returns>
public static string CatchImg(string vedioPath, int saveImgWidth, int saveImgHeight)
{
string ffmpeg = AppDomain.CurrentDomain.BaseDirectory + "\\" + System.Configuration.ConfigurationSettings.AppSettings["ffmpeg"];
if ((!System.IO.File.Exists(ffmpeg)) || (!System.IO.File.Exists(vedioPath)))
{
return "";
}
string saveImgPath = System.IO.Path.ChangeExtension(vedioPath, ".jpg");
string saveImgSize = string.Format("{0}x{1}", saveImgWidth, saveImgHeight);
ProcessStartInfo startInfo = new ProcessStartInfo(ffmpeg);
startInfo.WindowStyle = System.Diagnostics.ProcessWindowStyle.Hidden;
startInfo.Arguments = string.Format(" -i \"{0}\" -y -f image2 -t 0.001 -s \"{1}\" \"{2}\"", vedioPath, saveImgSize, saveImgPath);
System.Diagnostics.Process.Start(startInfo);
return saveImgPath.Replace(AppDomain.CurrentDomain.BaseDirectory, "");
}
}
}
相關推薦
.NET讀取視訊資訊、視訊截圖
在.NET中處理視訊是一件痛苦的事情,.NET並沒有提供視訊處理的類。於是咱們只能找一些第三方的類庫或者自己實現,在專案時間比較趕的情況下,自己實現是不可能的了,而且說不定會留下很多坑。所以一般情況下,咱們都是找一些靠譜的第三方類庫,畢竟別人確實實現得蠻好的。
ADO.Net中DataSet的應用(知識點描述、思維導圖、示例程式碼、效果截圖)
一.知識點描述 ADO.NET是Microsoft公司推出的.NET框架中用於資料訪問的元件,ADO. NET是.Net FrameWork SDK 中用以操作資料庫的類庫的總稱。而DataSet 類則是ADO. NET中最核心的成員之一,也是各種開發基於.Net平臺程式語言開發資料庫應用程式最常接觸的類。
ffmpeg處理視訊獲取第一幀截圖
<?php //使用PHP SDK,並且使用自定義配置檔案 require app_path().'/include/BaiduBce.phar'; require app_path().'/include/SampleConf.php'; require app_path().'
ADO.Net中DataTable的應用(知識點描述、思維導圖、示例程式碼、效果截圖)
SqlConnection sqlConnection = new SqlConnection(); //宣告並例項化SQL連線; sqlConnection.ConnectionString
【JAVA】JAVA使用ffmpeg進行視訊格式轉換以及截圖
JAVA 處理視訊檔案,需要用到 ffmpeg 這個工具。不需要依賴jar包。無論是在windows伺服器還是linux伺服器,想要使用 ffmpeg 都需要先安裝。 附上Linux下 *.tar.gz/*.tgz、*.bz2形式的原始碼軟體包 安裝方法:
使用AForge.NET Framework打開攝像頭並截圖 C#
int mon info bit sta pla red 說了 player videoDevices = new FilterInfoCollection(FilterCategory.VideoInputDevice); if
【Tools】macOS 截圖工具推薦xnip(滾動截圖&截長圖、步驟截圖)
20181113截圖工具先用了騰訊的snip,滾動截圖我在chrome和別的軟體下測試下沒成功。而且需要修改輔助功能。 xnip實現的原理似乎是滑鼠滾動時軟體自己拼接圖片。 此外,xnip的步驟截圖非常驚豔。 這兩個功能是很多截圖軟體都沒有的。 參考:https://
微信視訊應用、視訊直播、流媒體服務、視訊教學、線上教育類原創文章彙總
原創文章 / 阿酷TONY / 更新:2018-12-12 長沙 / 陽光明媚 / yáng guāng míng mèi / 2 ~ 6℃ 微信視訊應用、視訊直播、流媒體服務、視訊教學、線上教育類原創文章彙總 (2017-2018年度) &nbs
基於WebRtc在H5視訊聊天、視訊教學、視訊會議、視訊直播、白板互動低延時方案
隨移動互聯應用加快,4G,5G網路上馬,低延時網路視訊應改越來越走近生活,在教學,會議,線上醫療,招聘交友及時視訊要求高等場景需求越來越大,傳統基於rtmp直播應用已經大量應用在各個方向,由於rtmp基於TCP延時上可控較差,有積累延時,互動效能差,而新興的Webrtc技術,
安卓獲取視訊時間、視訊寬高
private String getPlayTime(String mUri) { android.media.MediaMetadataRetriever mmr = new android.media.MediaMetadataRetriever(); tr
Spring Boot + MyBatis 電商專案 -04- 使用 Spring MVC 讀取使用者資訊、篩選欄位
Spring Boot + MyBatis 電商專案 -04- 使用 Spring MVC 讀取使用者資訊、篩選欄位 前幾篇文章: (如果不是新手,建議至少看完第 3 篇,因為整個專案是基於第三篇建立的很多檔案進行的) Spring Boot + MyBatis 電商
java 視訊會議、視訊溝通、遠端教育、java視訊會議系統
以下都是基於webrtc的實現 方案1:簡單版 基於js框架 http://www.rtcmulticonnection.org/ 只要安裝好後臺的服務即可 體驗地址:https://github.com/muaz-khan/RTCMultiConnection#v3-de
springboot讀取配置資訊、環境變數
2、讀取配置檔案2.1 讀取核心配置檔案核心配置檔案是指在resources根目錄下的application.properties或application.yml配置檔案,讀取這兩個配置檔案的方法有兩種,都比較簡單。核心配置檔案application.properties內容
視訊互動、視訊會議、語音對講、IM、開戶等軟體的基本流程和開發指南
視訊呼叫業務邏輯主要實現兩個終端(PC、手機、Pad等)之間的通話請求流程控制,包括請求(Request)、回覆(Reply)、開始(Start)以及結束(Finish)等過程,可以形象理解為打電話的流程:撥號、等待、通話、結束通話。 以下以AnyChat視訊
小程式填坑之路—讀取使用者資訊、快取其資料、讀取其資料(button、wx.setStorage、wx.getStorage)
深深以為,遇見一個好的文章不容易,希望自己也能用心填坑。 首先來說讀取使用者資訊,之前是用getUserInfo(),但在2018年4月30日之後,該介面不適用於開發版和測試版,正式上線的小程式不受影響。很不幸,我就是4月30後後的這批。出於
PHP後臺自動獲取視訊資訊並截圖功能例項
名稱:php自動獲取視訊資訊並截圖 描述:PHP後臺自動獲取視訊資訊並截圖功能例項,包含ffmpeg的安裝步驟。 版本:所有版本 步驟1:確保 shell_exec() 函式是否可用!,php.ini中修改下方禁用函式。 disable_functions = pa
Android中如何獲取視訊檔案的截圖、縮圖
背景 公司最近要求給我負責的APP加上視訊錄製和釋出的功能,我簡單的完成了基本的錄製和視訊壓縮功能,後來發現釋出介面需要上傳視訊的截圖,網上搜索了一下資料,在這裡整理一下。 程式碼實現 ? 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
使用ffmpeg視訊格式轉換、視訊截圖、視訊採集、螢幕錄製
ffmpeg.exe-i F:閃客之家閃客之歌.mp3 -ab 56 -ar 22050 -b 500 -r 15 -s 320x240 f:11.flv ffmpeg -i F:01.wmv -ab 56 -ar 22050 -b 500 -r 15 -s 320x240 f:test.flv 使用-ss引
7、實現指令碼執行失敗 時自動截圖並儲存出錯資訊到檔案中
自動化指令碼如果失敗了,憑藉什麼去快速定位呢?當然是截圖和出錯資訊了,這裡就來實現這兩個功能。 方法是重寫TestListenerAdapter中的onTestFailure和onTestSkipped方法,在方法中新增截圖和儲存出錯資訊到文字的方法。 新建一個webtestListener.j
springboot中配置addResourceHandler和addResourceLocations,使得可以從磁碟中讀取圖片、視訊、音訊等
磁碟目錄 WebMvcConfig的程式碼 //對靜態資源的配置 @Override public void addResourceHandlers(ResourceHandlerRegistry registry) { String os = System.ge