Giter VIP home page Giter VIP logo

ffmevideoplayer's Introduction

目录

这是一个WPF中播放rtsp等流视频文件的示例,使用的方式是使用ffmpeg封装MediaElement来实现的。封装的方法是unosquare做的,我只是把他的成果拿来用罢了,找了好久才找到在wpf中播放rtsp流(当然vlc、nvlc、winform控件和流转bitmap的方式也能实现,但都没有这个效率高而且它不依赖任何其他内容),封装的源码请查看:https://github.com/unosquare/ffmediaelement

如何使用我的Demo

说明

为了方遍别人和我以后更方便地使用demo,我将生成地dll文件和所需其他文件也传到了gihub上,这使得我的文件显得很臃肿,看起来很不专业,但方遍简洁最重要不是么,哈哈。

下载编译并运行

此次我使用Visual Stdio2015进行编程工作,只要你下载下这整个文件(zip或者clone),然后双击.sln文件打开解决方案,加载完成Rebuild一下,然后点击Start按钮即可,首先vs会先下载一些NuGet包,配置完成后会顺利运行,此时你就会看到展示了四个视频直播地窗口。

Demo的结构

这是一个非常简单的UserController的建立与使用的示例

MainWindow

MainWindow只是展示了四个PlayerControl用户控件而已,PlayerControl是我自己写好的播放器控件,它的SourceStr属性为依赖项属性,从父窗口获取要播放的rtsp流地址。

PlayerController

先贴出只实现播放功能的最简单的代码

PlayerControl.xaml:

<UserControl x:Class="FFMEVideoPlayer.Player.PlayerControl"
             xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
             xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
             xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
             xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
             xmlns:local="clr-namespace:FFMEVideoPlayer.Player" 
             Loaded="UserControl_Loaded"
             xmlns:player="clr-namespace:Unosquare.FFME;assembly=ffme"
             mc:Ignorable="d" Name="playerController">
    </UserControl.Resources>
    <Grid>
        <player:MediaElement Name="Media"/>
    </Grid>
</UserControl>

PlayerControl.xaml.cs

using Microsoft.Practices.Prism.Commands;
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;

namespace FFMEVideoPlayer.Player
{
    /// <summary>
    /// Interaction logic for PlayerControl.xaml
    /// </summary>
    public partial class PlayerControl : UserControl
    {
        public PlayerControl()
        {
                InitializeComponent();
                //必须在为播放器指定uri之前设置FFmpegDirectory的值
                //它引用一些依赖的.dll和.exe文件,该文件在../bin/DLL/中
                Unosquare.FFME.MediaElement.FFmpegDirectory = Directory.GetCurrentDirectory() + "\\DLL\\";
        }

        private void UserControl_Loaded(object sender, RoutedEventArgs e)
        {
            if (SourceStr != null)
            {
                //指定播放路径
                Media.Source = new Uri(SourceStr);
                //开始播放
                Media.Play();
            }
        }

        public static readonly DependencyProperty SourceStrProperty = DependencyProperty.Register("SourceStr", typeof(string), typeof(PlayerControl));
        public string SourceStr
        {
            get { return (string)GetValue(SourceStrProperty); }
            set { SetValue(SourceStrProperty, value); }
        }

    }
}

PlayerControl调用ffme封装好的MediaElement来实现播放功能。经过封装的MediaElement被集成到了我所引用的ffme.dll文件中,而ffmpeg.dll在本程序中也是不可缺少的引用。 所以引用MediaElement的方式如下:

PlayerControl_xaml

PlayerControl.xaml文件

  • 首先引入ffme.dll的命名空间:
   xmlns:player="clr-namespace:Unosquare.FFME;assembly=ffme"
  • 在Grid中添加MediaElementk控件:
<player:MediaElement Name="Media" HorizontalAlignment="Right" VerticalAlignment="Stretch"/>

xaml中定义的其他内容只是控制播放/停止等命令的按钮而已,若不需要可以删除掉,不影响播放功能。

PlayerControl_xaml_cs

PlayerControl.xaml.cs

  • 注册一个依赖项属性,获取父窗体提供的播放地址
 public static readonly DependencyProperty SourceStrProperty = DependencyProperty.Register("SourceStr", typeof(string), typeof(PlayerControl));
        public string SourceStr
        {
            get { return (string)GetValue(SourceStrProperty); }
            set { SetValue(SourceStrProperty, value); }
        }
  • 在构造函数中首先添加一句:
 Unosquare.FFME.MediaElement.FFmpegDirectory = Directory.GetCurrentDirectory() + "\\DLL\\";

这是为了要添加一些播放所需的dll和exe文件,位置在/bin/Debug/DLL,它必须在设置播放器Source属性之前执行。

  • 而后在控件的Loaded事件里为Media控件的Source属性赋值并令其播放。
  private void UserControl_Loaded(object sender, RoutedEventArgs e)
        {
            if (SourceStr != null)
            {
                //指定播放路径
                Media.Source = new Uri(SourceStr);
                //开始播放
                Media.Play();
            }
        }

此时就可以实现最简单的播放功能了。

MediaElement

MediaElement有Play()Close()Dispose()Pause()Stop()等方法,有IsPlayingIsOpenIsOpeningMediaStateHasAudio等属性,我们可以通过他们来判断和控制播放状态。

demo中其他内容

定义DelegateCommand命令实现停止、播放功能,定义公有属性监控当前播放状态,当MediaElement播放状态发生改变时Media_PropertyChanged事件被触发来更新监控状态的属性的值。 知道了这些内容,如何定义自已的界面以及功能就随君所欲了。

如何使用FFME

如果想要按照unosquare的指引来做播放器的话,首先要做的就是下载并安装Visual Stuido 2017来使用C#7.0,否则是无法编译成功的。

下载所需内容

下载源码

这里下载unosquare/ffmediaelement整个项目源码,里面有使用FFmpeg封装MediaElemnt的源码,也有使用封装得到的dll的Exmaple,我便是按照他的教程来做的。

下载一个压缩包

这里下载文件并解压。

新建一个WPF应用程序

在VS中新建一个你的播放器WPF程序,我取的名字为FFMEVideoPlayer。建立完成之后打开其所在文件夹,依次导航到FFMEVideoPlayer\FFMEVideoPlayer\bin\Debug下,新建一个文件夹命名为DLL,当然你也可以取别的名字。而后将刚才下载并解压得到的ffmpeg-3.3.2-win32-shared文件夹中bin文件夹下的3个exe文件和8个dll文件全部复制到DLL下。

编译下载的源码

下载下载unosquare/ffmediaelemen完成之后使用VS2017打开Unosquare.FFME.sln解决方案,重新生Unosquare.FFME项目,生成成功之后打开其所在文件夹,找到bin/Debug或者bin/Release下生成的ffme.dllffmpeg.dll文件,复制到你的WPF应用程序的bin/DLL文件夹下。

在新的WPF应用程序中添加引用

在刚才新建的WPF应用程序中添加引用,引用刚刚复制到bin/DLL文件夹中的ffme.dllffmpeg.dll文件。

编辑MainWindow

在MainWindow.xaml中:

  • 添加命名空间:
xmlns:player="clr-namespace:Unosquare.FFME;assembly=ffme"
  • 注册Loaded事件:
Loaded="Window_Loaded"
  • 添加MediaElement控件
<player:MediaElement Name="Media"/>

在MainWindow.xaml.cs中:

  • 修改Loaded事件:
  private void Window_Loaded(object sender, RoutedEventArgs e)
        {
         	//必须在为播放器指定uri之前设置FFmpegDirectory的值
            //它引用一些依赖的.dll和.exe文件,文件在../bin/DLL/中
            Unosquare.FFME.MediaElement.FFmpegDirectory = Directory.GetCurrentDirectory() + "\\DLL\\";
        	//http://ivi.bupt.edu.cn/hls/cctv1hd.m3u8是cctv1直播地址
 			Media.Source = new Uri("http://ivi.bupt.edu.cn/hls/cctv1hd.m3u8);
             //开始播放
            Media.Play();
		}

此时运行你的程序,稍等一会就回看到cctv1的直播节目了。

MediaElement其他方法与属性

这里简要说了下MediaElement的几个方法,具体内容可以在 Media.Play(); Play上右键转到定义查看其他属性、方法和事件。

感谢

感谢Unosquare Labs提供的解决方案

ffmevideoplayer's People

Contributors

dg-wangtao avatar

Watchers

James Cloos avatar  avatar

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.