![](http://blog.51cto.com/image/skin/artType01.jpg)
vlc的应用之三:动态调用vlc-0.9.4的libvlc.dll
2008-12-03 17:38:46
vlc-0.9.4提供的libvlc.dll是可以动态调用的,Jeremiah这一篇博客就介绍下如何用C#和WinForm框架调用libvlc.dll作个简易播放器。
1. vs2005新建工程,将vlc-0.9.4的libvlc.dll,libvlccore.dll,plugins目录全部拷贝到工程目录下面\bin\Debug中。
2. 创建异常结构体
using System;
using System.Collections.Generic;
using System.Text;
namespace MyOwnPlayer
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
//异常结构体
public
struct ExceptionStruct
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
private
int raised;
private
int code;
private
string message;
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
class MediaException
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
3. CoreHandle和Core类
using System;
using System.Runtime.InteropServices;
namespace MyOwnPlayer
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
class CoreHandle : SafeHandle
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
//构造方法
public CoreHandle()
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
:
base(IntPtr.Zero,
true)
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
//重写的方法
public
override
bool IsInvalid
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
get {
return handle == IntPtr.Zero; }
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
protected
override
bool ReleaseHandle()
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
if (!IsInvalid)
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
libvlc_release(
this);
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
handle = IntPtr.Zero;
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
return
true;
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
protected
override
void Dispose(
bool disposing)
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
ReleaseHandle();
base.Dispose(disposing);
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
//Dll动态导入
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
[DllImport(
"libvlc")]
private
static
extern
void libvlc_release(CoreHandle coreHandle);
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
using System;
using System.Runtime.InteropServices;
namespace MyOwnPlayer
{
class Core
{
//coreHandle字段和属性
private CoreHandle coreHandle;
public CoreHandle CoreHandle
{
get { return coreHandle; }
}
//构造方法
public Core(string[] argv, ref ExceptionStruct ex)
{
coreHandle = libvlc_new(argv.Length, argv, ref ex);
}
//Dll动态导入
[DllImport("libvlc")]
private static extern CoreHandle libvlc_new(int argc, string[] args, ref ExceptionStruct ex);
}
}
3. MediaHandle和Media类,注意里面的非英文路径处理方法。
using System;
using System.Runtime.InteropServices;
namespace MyOwnPlayer
{
class MediaHandle : SafeHandle
{
//构造方法
public MediaHandle()
: base(IntPtr.Zero, true)
{
}
//重写的方法
public override bool IsInvalid
{
get { return handle == IntPtr.Zero; }
}
protected override bool ReleaseHandle()
{
if (!IsInvalid)
{
libvlc_media_release(this);
handle = IntPtr.Zero;
}
return true;
}
protected override void Dispose(bool disposing)
{
ReleaseHandle();
base.Dispose(disposing);
}
//Dll动态导入
[DllImport("libvlc")]
private static extern void libvlc_media_release(MediaHandle mediaHandle);
}
}
using System;
using System.Text;
using System.Runtime.InteropServices;
namespace MyOwnPlayer
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
class Media
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
//mediaHandle字段和属性
private MediaHandle mediaHandle;
public MediaHandle MediaHandle
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
get {
return mediaHandle; }
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
//构造方法
public Media(CoreHandle coreHandle, String filename,
ref ExceptionStruct ex)
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
//c#为UTF-16编码, libvlc.dll为UTF-8编码, 需要转换.
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
UTF8Encoding utf8 =
new UTF8Encoding();
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
mediaHandle = libvlc_media_new(coreHandle, utf8.GetBytes(filename),
ref ex);
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
//Dll动态导入
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
[DllImport(
"libvlc")]
private
static
extern MediaHandle libvlc_media_new
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
(CoreHandle coreHandle, [MarshalAs(UnmanagedType.LPArray)]
byte[] link,
refExceptionStruct ex);
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
5. MediaPlayerHandle和MediaPlayer类
using System;
using System.Runtime.InteropServices;
namespace MyOwnPlayer
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
class MediaPlayerHandle : SafeHandle
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
//构造方法
public MediaPlayerHandle()
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
:
base(IntPtr.Zero,
true)
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
//重写的方法
public
override
bool IsInvalid
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
get {
return handle == IntPtr.Zero; }
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
protected
override
bool ReleaseHandle()
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
if (!IsInvalid)
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
libvlc_media_player_release(this);
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
handle = IntPtr.Zero;
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
return
true;
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
protected
override
void Dispose(
bool disposing)
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
ReleaseHandle();
base.Dispose(disposing);
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
//Dll动态导入
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
[DllImport(
"libvlc")]
private
static
extern
void libvlc_media_player_release(MediaPlayerHandle mediaPlayerHandle);
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
using System;
using System.Runtime.InteropServices;
namespace MyOwnPlayer
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
class MediaPlayer
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
//mediaPlayerHandle字段和属性
private MediaPlayerHandle mediaPlayerHandle;
public MediaPlayerHandle MediaPlayerHandle
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
get {
return mediaPlayerHandle; }
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
//构造方法
public MediaPlayer(MediaHandle mediaHandle,
ref ExceptionStruct ex)
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
mediaPlayerHandle = libvlc_media_player_new_from_media(mediaHandle,
ref ex);
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
//设置父窗口
public
void VedioSetParent(CoreHandle coreHandle, IntPtr hDT,
ref ExceptionStruct ex)
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
libvlc_video_set_parent(coreHandle, hDT,
ref ex);
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
//播放
public
void Play(
ref ExceptionStruct ex)
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
libvlc_media_player_play(mediaPlayerHandle,
ref ex);
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
//停止
public
void Stop(
ref ExceptionStruct ex)
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
{
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
libvlc_media_player_stop(mediaPlayerHandle,
ref ex);
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
//Dll动态导入
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
[DllImport(
"libvlc")]
private
static
extern MediaPlayerHandle libvlc_media_player_new_from_media(MediaHandle libvlc_media_handle,
ref ExceptionStruct ex);
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
[DllImport(
"libvlc")]
private
static
extern
void libvlc_video_set_parent(CoreHandle coreHandle, IntPtr hDT,
refExceptionStruct ex);
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
[DllImport(
"libvlc")]
private
static
extern
void libvlc_media_player_play(MediaPlayerHandle mediaPlayerHandle,
ref ExceptionStruct ex);
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
[DllImport(
"libvlc")]
private
static
extern
void libvlc_media_player_stop(MediaPlayerHandle mediaPlayerHandle,
ref ExceptionStruct ex);
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
}
6. 基本工作做好了。下一步建立一个Form,里面画一个Panel(播放容器),画一个Textbox(播放地址),画一个Button(播放按钮),Button的点击事件为:
private void button1_Click(object sender, EventArgs e)
{
//要播放的文件的uri
string uri = this.textBox1.Text;
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
//进行播放的控件的句柄
IntPtr hdl = this.panel1.Handle;
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
//播放参数
string[] argv = new string[] { "-I", "--ignore-config" };
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
//vlc对象的创建
ExceptionStruct ex = new ExceptionStruct();
Core core = new Core(argv, ref ex);
Media media = new Media(core.CoreHandle, uri, ref ex);
MediaPlayer player = new MediaPlayer(media.MediaHandle, ref ex);
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
//垃圾回收
GC.Collect();
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
//播放
player.VedioSetParent(core.CoreHandle, hdl, ref ex);
player.Play(ref ex);
![](https://i-blog.csdnimg.cn/blog_migrate/b4493fbe112bb7c4284e5d0787e512ef.png)
//继续回收垃圾等相关操作
GC.Collect();
GC.WaitForPendingFinalizers();
}
7. 基本的播放功能就是这样实现的。其他接口请参考源码下面的\include\vlc\libvlc.h文件,里面有比较详细的对外接口的说明。
8. 以上代码已经发送到附件中(MyOwnPlayer.rar),参考网址的楼主写的代码也在附件中(Marx_libvlc_wrapper(2).zip)。调试附件请注意第1步。
参考网址:
本文出自 “海狗哥的流媒体空间” 博客,请务必保留此出处http://jeremiah.blog.51cto.com/539865/116981
lbp0200、xc_shen、jiang421122 |
8人
| 了这篇文章 |