先说下优缺点
优点:与电脑无关,能播放主流编码格式视频。
缺点:只能播放本地视频,网络视频播放不了。
下面是具体操作和代码
1. 安装Vlc.DotNet.Forms 和 VideoLAN.LibVLC.Windows
Vlc.DotNet.Forms 是播放库,VideoLAN.LibVLC.Windows用于播放显示
2. 界面布局
用到 vlcControl: 视频播放组件 ;滑块 TrackBar :自定义控件,用于显示视频播放进度和音量;button:视频播放和快进
我播放是网上的视频, 所以调用线程先将视频下载到本地,下载完成后在播放。
lTrackBar_vedio 和 lTrackBar_voice 是我自定义的滑块,可以直接用系统默认的滑块控件。
public partial class Form1 : Form{private string url = @"http://www.xxxxx.com/video/20240111155329.mp4";private string vedioPath = AppDomain.CurrentDomain.BaseDirectory + @"Vedio\123.mp4";private long vedioLength = 0;private string vedioTime;public Form1(){InitializeComponent();}private void Form1_Load(object sender, EventArgs e){if (!Directory.Exists(AppDomain.CurrentDomain.BaseDirectory + @"\Vedio"))Directory.CreateDirectory(AppDomain.CurrentDomain.BaseDirectory + @"\Vedio");if (!File.Exists(vedioPath)){VedioDownloader urlDownloader = new VedioDownloader(vedioPath, url);new Thread(new ThreadStart(urlDownloader.DownloadFileAsync)).Start(); ;}else{InitVedio(); }}private void InitVedio(){vlcControl1.Play(new FileInfo(vedioPath));button_play.BackgroundImage = Properties.Resources.audioPlay;vlcControl1.Audio.Volume = this.lTrackBar_voice.L_Value;lTrackBar_vedio.L_Maximum = this.lTrackBar_vedio.Width;lTrackBar_vedio.L_Minimum = 0;}//加载播放需要的库private void vlcControl1_VlcLibDirectoryNeeded(object sender, Vlc.DotNet.Forms.VlcLibDirectoryNeededEventArgs e){var currentAssembly = Assembly.GetEntryAssembly();var currentDirectory = new FileInfo(currentAssembly.Location).DirectoryName;if (currentDirectory != null){if (IntPtr.Size == 4){e.VlcLibDirectory = new DirectoryInfo(Path.GetFullPath(@".\libvlc\win-x86"));}else{e.VlcLibDirectory = new DirectoryInfo(Path.GetFullPath(@".\libvlc\win-x64"));}}if (!e.VlcLibDirectory.Exists){var folderBrowserDialog = new System.Windows.Forms.FolderBrowserDialog();folderBrowserDialog.Description = "Select Vlc libraries folder.";folderBrowserDialog.RootFolder = Environment.SpecialFolder.Desktop;folderBrowserDialog.ShowNewFolderButton = true;if (folderBrowserDialog.ShowDialog() == DialogResult.OK){e.VlcLibDirectory = new DirectoryInfo(folderBrowserDialog.SelectedPath);}}}private void vlcControl1_TimeChanged(object sender, Vlc.DotNet.Core.VlcMediaPlayerTimeChangedEventArgs e){vedioLength = vlcControl1.VlcMediaPlayer.Length;string allTime = ConvertTimeStampToDateTime(vedioLength);string current = ConvertTimeStampToDateTime(vlcControl1.VlcMediaPlayer.Time);this.lTrackBar_vedio.L_Value = Convert.ToInt32(1.0f * (lTrackBar_vedio.L_Maximum - lTrackBar_vedio.L_Minimum) * vlcControl1.VlcMediaPlayer.Time / vedioLength);vedioTime = current + " / " + allTime;SetVedioTime(vedioTime);}/// <summary>/// 使用委托显示视频时间/// </summary>/// <param name="text"></param>delegate void SetTextCallBack(string text);private void SetVedioTime(string vedioTime){if (this.label_vedioTime.InvokeRequired){SetTextCallBack stcb = new SetTextCallBack(SetVedioTime);this.BeginInvoke(stcb, new object[] { vedioTime });}else{this.label_vedioTime.Text = vedioTime;}}private string ConvertTimeStampToDateTime(long vedioLength){DateTime dt = new DateTime(vedioLength * 10000);return dt.Hour.ToString().PadLeft(2, '0') + ":" + dt.Minute.ToString().PadLeft(2, '0') + ":" + dt.Second.ToString().PadLeft(2, '0');}private void button_play_Click(object sender, EventArgs e){if (vlcControl1.State == Vlc.DotNet.Core.Interops.Signatures.MediaStates.Playing){vlcControl1.Pause();button_play.BackgroundImage = Properties.Resources.audioPause2;}else{if (vlcControl1.State == Vlc.DotNet.Core.Interops.Signatures.MediaStates.Ended){InitVedio();}else{button_play.BackgroundImage = Properties.Resources.audioPlay;vlcControl1.Play();}}}private void button_voice_Click(object sender, EventArgs e){if (lTrackBar_voice.L_Value != 0){lTrackBar_voice.L_Value = 0;button_voice.BackgroundImage = Properties.Resources.voice_close;}else{lTrackBar_voice.L_Value = 80;button_voice.BackgroundImage = Properties.Resources.voice_open;}}private void lTrackBar_voice_LValueChanged(object sender, LEventArgs e){vlcControl1.Audio.Volume = lTrackBar_voice.L_Value;}private void vlcControl1_Stopped(object sender, Vlc.DotNet.Core.VlcMediaPlayerStoppedEventArgs e){button_play.BackgroundImage = Properties.Resources.audioPause2;}private void lTrackBar_vedio_MouseMove(object sender, MouseEventArgs e){PlayInNewLocation(sender,e);}private void lTrackBar_vedio_MouseDown(object sender, MouseEventArgs e){PlayInNewLocation(sender,e);}private void PlayInNewLocation(object sender, MouseEventArgs e){if (e.Button == MouseButtons.Left){if (vlcControl1.State == Vlc.DotNet.Core.Interops.Signatures.MediaStates.Ended){InitVedio();}vlcControl1.VlcMediaPlayer.Time = this.lTrackBar_vedio.L_Value * vedioLength / (lTrackBar_vedio.L_Maximum - lTrackBar_vedio.L_Minimum);}}private void button1_MouseDown(object sender, MouseEventArgs e){if (e.Button == MouseButtons.Left)vlcControl1.Rate = 2.5f;}private void button1_MouseUp(object sender, MouseEventArgs e){vlcControl1.Rate = 1;}private void Form1_FormClosed(object sender, FormClosedEventArgs e){// vlcControl在stop的过程中可能会产生子窗口消息,然而子窗口消息是在主线程(UI线程)中处理的,而stop()方法也是在主线程中调用的,这就造成了竞争性死锁。所以先释放掉主窗体,在释放vlcControlthis.Dispose();if (vlcControl1.State != Vlc.DotNet.Core.Interops.Signatures.MediaStates.Stopped)vlcControl1.Stop();vlcControl1.Dispose();}}