123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491 |
- using System;
- using System.Text.RegularExpressions;
- using System.Windows;
- using System.Windows.Input;
- using System.Windows.Threading;
-
- namespace XHWK.WKTool
- {
- using system;
-
- /// <summary>
- /// 视频剪辑
- /// VideoClipWindow.xaml 的交互逻辑
- /// </summary>
- public partial class VideoClipWindow
- {
- /// <summary>
- /// 视频地址
- /// </summary>
- string _videoPath;
-
- /// <summary>
- /// 视频剪辑
- /// </summary>
- public VideoClipWindow()
- {
- InitializeComponent();
- Width = App.W_XHMicroLessonSystemWindow.ActualWidth;
- Height = App.W_XHMicroLessonSystemWindow.ActualHeight;
- }
-
- public bool InitClipVideo(string mVideoPath)
- {
- if (FileToolsCommon.IsExistFile(mVideoPath))
- {
- _videoPath = mVideoPath;
- QsMovie.Source = new Uri(_videoPath);
- double prop = QsMovie.NaturalVideoHeight / (double)QsMovie.NaturalVideoWidth;
- double gridWidth = GridMovie.ActualHeight / prop;
- if (gridWidth <= GridMovie.ActualWidth)
- {
- QsMovie.Width = gridWidth;
- QsMovie.Height = GridMovie.ActualHeight;
- }
- else
- {
- QsMovie.Height = GridMovie.ActualWidth * prop;
- QsMovie.Width = GridMovie.ActualWidth;
- }
- DataContext = App.PageContextData;
- }
- else
- {
- return false;
- }
- return true;
- }
-
- /// <summary>
- /// 计时器
- /// </summary>
- DispatcherTimer _dispatcherTimer = new System.Windows.Threading.DispatcherTimer(); // 定义一个DT
-
- /// <summary>
- /// 播放/暂停
- /// </summary>
- /// <param name="sender"></param>
- /// <param name="e"></param>
- private void Play_Click(object sender, RoutedEventArgs e)
- {
- if (_isPlay)
- {
- MoviePause();
- }
- else
- {
- MoviePlay();
- }
- }
-
- /// <summary>
- /// 正在播放
- /// </summary>
- bool _isPlay;
-
- /// <summary>
- /// 播放
- /// </summary>
- public void MoviePlay()
- {
- _isPlay = true;
- ImgPlay.Visibility = Visibility.Collapsed;
- ImgPause.Visibility = Visibility.Visible;
- QsMovie.Play();
- }
-
- /// <summary>
- /// 暂停
- /// </summary>
- public void MoviePause()
- {
- _isPlay = false;
- ImgPlay.Visibility = Visibility.Visible;
- ImgPause.Visibility = Visibility.Collapsed;
- QsMovie.Pause();
- }
-
- /// <summary>
- /// slider滑动值随播放内容位置变化
- /// </summary>
- /// <param name="sender"></param>
- /// <param name="e"></param>
- private void dispatcherTimer_Tick(object sender, EventArgs e)
- {
- TimelineSlider.Value = QsMovie.Position.TotalMilliseconds; //slider滑动值随播放内容位置变化
- LblProgress.Content = new TimeSpan(
- 0,
- 0,
- 0,
- 0,
- (int)QsMovie.Position.TotalMilliseconds
- ).ToString(@"hh\:mm\:ss");
- }
-
- /// <summary>
- /// 拖动进度条
- /// </summary>
- /// <param name="sender"></param>
- /// <param name="e"></param>
- private void TimelineMDown(object sender, EventArgs e)
- {
- _dispatcherTimer.Stop();
- }
-
- /// <summary>
- /// 拖动进度条
- /// </summary>
- /// <param name="sender"></param>
- /// <param name="e"></param>
- private void TimelineMUp(object sender, EventArgs e)
- {
- QsMovie.Position = new TimeSpan(
- 0,
- 0,
- 0,
- 0,
- (int)TimelineSlider.Value
- );
- _dispatcherTimer.Start();
- MoviePlay();
- }
-
- /// <summary>
- /// 加载视频
- /// </summary>
- /// <param name="sender"></param>
- /// <param name="e"></param>
- private void QS_Movie_Loaded(object sender, RoutedEventArgs e)
- {
- //GridMovie.Height
- UcSlider.SilderWidth = (int)TimelineSlider.ActualWidth;
- MoviePlay();
- while (QsMovie.NaturalVideoWidth == 0)
- {
- System.Threading.Thread.Sleep(50);
- }
- MoviePause();
-
- //new Thread(new ThreadStart(new Action(() =>
- //{
- // Dispatcher.Invoke(() =>
- // {
- //});
- //}))).Start();
- }
-
- /// <summary>
- /// 关闭
- /// </summary>
- /// <param name="sender"></param>
- /// <param name="e"></param>
- private void Button_Click(object sender, RoutedEventArgs e)
- {
- //this.Close();
- QsMovie.Stop();
- _isPlay = false;
- ImgPlay.Visibility = Visibility.Visible;
- ImgPause.Visibility = Visibility.Collapsed;
- UcSlider.StartValue = 0;
- TimelineSlider.Value = 0;
- _dispatcherTimer.Stop();
- Hide();
- }
-
- double _statime;
-
- private void UcSlider_PreviewMouseLeftButtonDown(object sender, MouseButtonEventArgs e)
- {
- //dispatcherTimer.Stop();
- _statime = UcSlider.StartValue;
- }
-
- private void UcSlider_PreviewMouseLeftButtonUp(object sender, MouseButtonEventArgs e)
- {
- if (Math.Abs(UcSlider.StartValue - _statime) > 100)
- {
- _dispatcherTimer.Stop();
- TimelineSlider.Value = UcSlider.StartValue;
- QsMovie.Position = new TimeSpan(
- 0,
- 0,
- 0,
- 0,
- (int)TimelineSlider.Value
- );
- _dispatcherTimer.Start();
- UcSlider_PreviewMouseMove(null, null);
- MoviePlay();
- }
- }
-
- private void UcSlider_PreviewMouseMove(object sender, MouseEventArgs e)
- {
- TxbStartTime.Text = new TimeSpan(
- 0,
- 0,
- 0,
- 0,
- (int)UcSlider.StartValue
- ).ToString(@"hh\:mm\:ss\.fff");
- TxbEndTime.Text = new TimeSpan(
- 0,
- 0,
- 0,
- 0,
- (int)UcSlider.EndValue
- ).ToString(@"hh\:mm\:ss\.fff");
- LblVideoTime.Content = new TimeSpan(
- 0,
- 0,
- 0,
- 0,
- ((int)UcSlider.EndValue - (int)UcSlider.StartValue)
- ).ToString(@"hh\:mm\:ss\.fff");
- //LblStartTime.Content = new TimeSpan(0, 0, 0, 0, (int)UcSlider.StartValue).ToString(@"hh\:mm\:ss");
- //LblEndTime.Content = new TimeSpan(0, 0, 0, 0, (int)UcSlider.EndValue).ToString(@"hh\:mm\:ss");
- //LblVideoTime.Content = new TimeSpan(0, 0, 0, 0, ((int)(UcSlider.EndValue - (UcSlider.EndValue % 1000)) - (int)(UcSlider.StartValue - (UcSlider.StartValue % 1000)))).ToString(@"hh\:mm\:ss");
- }
-
- /// <summary>
- /// 剪辑
- /// </summary>
- /// <param name="sender"></param>
- /// <param name="e"></param>
- private void BtnClip_Click(object sender, RoutedEventArgs e)
- {
- if ((UcSlider.EndValue - UcSlider.StartValue) < 1000)
- {
- MessageWindow.Show("剪辑时间不得小于1秒!");
- return;
- }
- _dispatcherTimer.Stop();
- MoviePause();
- string extension = FileToolsCommon.GetIoExtension(_videoPath);
- string fileName = FileToolsCommon.GetIoFileNameNoExtension(_videoPath);
- System.Windows.Forms.SaveFileDialog saveDg = new System.Windows.Forms.SaveFileDialog();
- saveDg.Filter = @"(*" + extension + @")|*" + extension; // + "|(*.MP4)|*.MP4";
- //saveDg.FileName = tableName + DateTime.Now.ToString("yyyy-MM-dd_hh-mm-ss") + "";
- saveDg.FileName = fileName + "剪辑";
- saveDg.AddExtension = true;
- saveDg.RestoreDirectory = true;
- if (saveDg.ShowDialog() == System.Windows.Forms.DialogResult.OK)
- {
- string filePath = saveDg.FileName;
- //duration.ToString(@"dd\.hh\:mm\:ss");
- TimeSpan startTp = new TimeSpan(
- 0,
- 0,
- 0,
- 0,
- (int)UcSlider.StartValue
- );
- string startTime = startTp.ToString(@"hh\:mm\:ss\.fff");
- TimeSpan endTp = new TimeSpan(
- 0,
- 0,
- 0,
- 0,
- (int)UcSlider.EndValue
- );
- string endTime = endTp.ToString(@"hh\:mm\:ss\.fff");
- App.FFmpeg.ClipVideo(
- _videoPath,
- startTime,
- endTime,
- filePath
- );
- MessageBoxResult br = MessageWindow.Show(
- "剪辑完成是否打开文件夹?",
- "剪辑",
- MessageBoxButton.OKCancel
- );
- if (br == MessageBoxResult.OK)
- {
- //System.Diagnostics.Process.Start(FileToolsCommon.GetDirectoryName(filePath));
- System.Diagnostics.Process.Start("explorer.exe", "/select," + filePath);
- }
- }
- }
-
- /// <summary>
- /// 输入开始时间
- /// </summary>
- /// <param name="sender"></param>
- /// <param name="e"></param>
- private void TxbStartTime_LostFocus(object sender, RoutedEventArgs e)
- {
- //判断是否为时间格式
- if (!TimeStrRegularJudg(TxbStartTime.Text))
- {
- MessageWindow.Show("请输入正确的时间格式:hh:mm:ss.fff");
- return;
- }
- TimeSpan time = ConvertToTimeSpan(TxbStartTime.Text);
- if (time.TotalMilliseconds > UcSlider.EndValue)
- {
- MessageWindow.Show("开始时间不能大于结束时间!");
- return;
- }
- if (time.TotalMilliseconds > QsMovie.NaturalDuration.TimeSpan.TotalMilliseconds - 1000 || time.TotalMilliseconds > UcSlider.EndValue - 1000)
- {
- MessageWindow.Show("剪辑时间不能小于1秒!");
- return;
- }
- UcSlider.StartValue = time.TotalMilliseconds;
- UcSlider_PreviewMouseLeftButtonUp(null, null);
- }
-
- /// <summary>
- /// 输入结束时间
- /// </summary>
- /// <param name="sender"></param>
- /// <param name="e"></param>
- private void TxbEndTime_LostFocus(object sender, RoutedEventArgs e)
- {
- //判断是否为时间格式
- if (!TimeStrRegularJudg(TxbEndTime.Text))
- {
- MessageWindow.Show("请输入正确的时间格式:hh:mm:ss.fff");
- return;
- }
- TimeSpan time = ConvertToTimeSpan(TxbEndTime.Text);
- if (time.TotalMilliseconds < UcSlider.StartValue)
- {
- MessageWindow.Show("结束时间不能小于开始时间!");
- return;
- }
- if (time.TotalMilliseconds < UcSlider.StartValue + 1000)
- {
- MessageWindow.Show("剪辑时间不能小于1秒!");
- return;
- }
- if (time.TotalMilliseconds > QsMovie.NaturalDuration.TimeSpan.TotalMilliseconds)
- {
- MessageWindow.Show("结束时间不能超出视频总时长!");
- return;
- }
- UcSlider.EndValue = time.TotalMilliseconds;
- UcSlider_PreviewMouseLeftButtonUp(null, null);
- }
-
- /// <summary>
- /// string转TimeSpan
- /// </summary>
- /// <param name="str"></param>
- /// <returns></returns>
- public TimeSpan ConvertToTimeSpan(string str)
- {
- int day = 0;
- int hour = 0;
- int min = 0;
- int sec = 0;
- int mil = 0;
- string[] strArray1 = str.Split(':');
- try
- {
- if (strArray1[0].Contains("."))
- {
- string[] strArray2 = strArray1[0].Split('.');
- day = Convert.ToInt32(strArray2[0]);
- hour = Convert.ToInt32(strArray2[1]);
- }
- else
- {
- day = 0;
- hour = Convert.ToInt32(strArray1[0]);
- }
- min = Convert.ToInt32(strArray1[1]);
- if (strArray1[2].Contains("."))
- {
- string[] strArray3 = strArray1[2].Split('.');
- sec = Convert.ToInt32(strArray3[0]);
- mil = Convert.ToInt32(strArray3[1]);
- }
- else
- {
- sec = Convert.ToInt32(strArray1[2]);
- }
- }
- catch (Exception)
- {
- // ignored
- }
- return new TimeSpan(
- day,
- hour,
- min,
- sec,
- mil
- );
- }
-
- /// <summary>
- /// 判断是否为时间格式
- /// </summary>
- /// <param name="str"></param>
- /// <returns></returns>
- public bool TimeStrRegularJudg(string str)
- {
- try
- {
- Regex reg = new Regex(@"^((20|21|22|23|[0-1]?\d):[0-5]?\d:[0-5]?\d.\d\d\d)$");
- return reg.IsMatch(str);
- }
- catch (Exception)
- {
- return false;
- }
- }
-
- /// <summary>
- /// 鼠标点击移动
- /// </summary>
- /// <param name="sender"></param>
- /// <param name="e"></param>
- private void Title_MouseLeftButtonDown(object sender, MouseButtonEventArgs e)
- {
- DragMove();
- }
-
- /// <summary>
- /// 启动定时器 同步进度条和视频进度
- /// </summary>
- /// <param name="sender"></param>
- /// <param name="e"></param>
- private void Element_MediaOpened(object sender, RoutedEventArgs e)
- {
- TimelineSlider.Maximum = QsMovie.NaturalDuration.TimeSpan.TotalMilliseconds; //设置slider最大值
- UcSlider.Maximum = QsMovie.NaturalDuration.TimeSpan.TotalMilliseconds;
- UcSlider.StartValue = 0;
- UcSlider.EndValue = QsMovie.NaturalDuration.TimeSpan.TotalMilliseconds;
- UcSlider_PreviewMouseMove(null, null);
- _dispatcherTimer.Tick += dispatcherTimer_Tick; //超过计时间隔时发生
- _dispatcherTimer.Interval = new TimeSpan(
- 0,
- 0,
- 0,
- 0,
- 500
- ); //DT间隔
- _dispatcherTimer.Start(); //DT启动
-
- #region 调整视频大小
-
- double prop = QsMovie.NaturalVideoHeight / (double)QsMovie.NaturalVideoWidth;
- double gridWidth = GridMovie.ActualHeight / prop;
- if (gridWidth <= GridMovie.ActualWidth)
- {
- QsMovie.Width = gridWidth;
- QsMovie.Height = GridMovie.ActualHeight;
- }
- else
- {
- QsMovie.Height = GridMovie.ActualWidth * prop;
- QsMovie.Width = GridMovie.ActualWidth;
- }
-
- #endregion
- }
- }
- }
|