2010-04-06 46 views
3

創建縮略圖我想要顯示我的網站上列出的視頻的縮略圖,我想從視頻(從特定時間)獲取單幀並將它們顯示爲縮略圖。如何從WMV視頻的

使用.Net可以嗎? (C#或VB)

回答

2

是的,這是可能的。你需要使用DirectShow.NET。我發現this有用。

編輯:

確定它看起來像,因爲我用它的庫已經改變了......詛咒開源:)

我剛翻譯成下面的代碼和測試,它爲我工作正常(注意,假定存在一個在C WMV:\ AAA稱爲C4.wmv和輸出將轉至c:\ AAA \ out.bmp)

IGraphBuilder graphbuilder = (IGraphBuilder)new FilterGraph(); 
     ISampleGrabber samplegrabber = (ISampleGrabber) new SampleGrabber(); 
     graphbuilder.AddFilter((IBaseFilter)samplegrabber, "samplegrabber"); 

     AMMediaType mt = new AMMediaType(); 
     mt.majorType = MediaType.Video; 
     mt.subType = MediaSubType.RGB24; 
     mt.formatType = FormatType.VideoInfo; 
     samplegrabber.SetMediaType(mt); 

     int hr = graphbuilder.RenderFile("C:\\aaa\\c4.wmv", null); 

     IMediaEventEx mediaEvt = (IMediaEventEx)graphbuilder; 
     IMediaSeeking mediaSeek = (IMediaSeeking)graphbuilder; 
     IMediaControl mediaCtrl = (IMediaControl)graphbuilder; 
     IBasicAudio basicAudio = (IBasicAudio)graphbuilder; 
     IVideoWindow videoWin = (IVideoWindow)graphbuilder; 

     basicAudio.put_Volume(-10000); 
     videoWin.put_AutoShow(OABool.False); 

     samplegrabber.SetOneShot(true); 
     samplegrabber.SetBufferSamples(true); 

     long d = 0; 
     mediaSeek.GetDuration(out d); 
     long numSecs = d/10000000; 

     long secondstocapture = (long)(numSecs * 0.10f); 


     DsLong rtStart, rtStop; 
     rtStart = new DsLong(secondstocapture * 10000000); 
     rtStop = rtStart; 
     mediaSeek.SetPositions(rtStart, AMSeekingSeekingFlags.AbsolutePositioning, rtStop, AMSeekingSeekingFlags.AbsolutePositioning); 

     mediaCtrl.Run(); 
     EventCode evcode; 
     mediaEvt.WaitForCompletion(-1, out evcode); 

     VideoInfoHeader videoheader = new VideoInfoHeader(); 
     AMMediaType grab = new AMMediaType(); 
     samplegrabber.GetConnectedMediaType(grab); 
     videoheader = 
     (VideoInfoHeader)Marshal.PtrToStructure(grab.formatPtr, 
     typeof(VideoInfoHeader)); 


     int width = videoheader.SrcRect.right; 
     int height = videoheader.SrcRect.bottom; 
     Bitmap b = new Bitmap(width, height, PixelFormat.Format24bppRgb); 

     uint bytesPerPixel = (uint)(24 >> 3); 
     uint extraBytes = ((uint)width * bytesPerPixel) % 4; 
     uint adjustedLineSize = bytesPerPixel * ((uint)width + extraBytes); 
     uint sizeOfImageData = (uint)(height) * adjustedLineSize; 


     BitmapData bd1 = b.LockBits(new Rectangle(0, 0, width, height), ImageLockMode.ReadWrite, PixelFormat.Format24bppRgb); 
     int bufsize = (int)sizeOfImageData; 
     int n = samplegrabber.GetCurrentBuffer(ref bufsize, bd1.Scan0); 
     b.UnlockBits(bd1); 
     b.RotateFlip(RotateFlipType.RotateNoneFlipY); 
     b.Save("C:\\aaa\\out.bmp"); 
     Marshal.ReleaseComObject(graphbuilder); 
     Marshal.ReleaseComObject(samplegrabber); 

另外要注意,DirectShow是somethign的框架中冷靜...... MS有點建議你去媒體基金會......我是一個老派的DirectX坦率地說,這個程序員不再那麼做了。

+0

嗨, 我引用的DirectShowLib-2005.dll,但我停留在你鏈接我的示例代碼2行:) 類型comtype = Type.GetTypeFromCLSID(Clsid.FilterGraph); ClsId會是什麼? – Michel 2010-04-06 12:39:30

+0

是啊!有用。非常感謝! – Michel 2010-04-07 20:25:30

+0

恩,恩,我幾乎不敢問......我更新了我的相機附帶的軟件,GRMBL軟件現在不會讓我輸出到WMV,但只能輸出到原始格式:MP4。我試圖理解代碼以使其適用於MP4文件(因爲它在MP4文件崩潰),但我真的不知道如何。 你能幫我解決這個問題嗎? – Michel 2010-04-10 19:47:27

相關問題