-
This commit is contained in:
29
README.md
29
README.md
@@ -70,6 +70,17 @@ https://github.com/stax76/mpv.net/wiki/Scripting-(CSharp,-Python,-JavaScript,-Lu
|
||||
|
||||
### Changelog
|
||||
|
||||
### 2.3 (2019-04-04)
|
||||
|
||||
- dragging a youtube URL on mpv.net would still break something, it should work now
|
||||
- when the main window gets focus/activation it will check the clibboard for a YouTube video and ask to play it
|
||||
- libmpv updated
|
||||
- changing to normal size from fullscreen resulted in a too large window in some circumstances
|
||||
- some default key bindings and menu structure have changed and the input.conf file has a description added on top <https://github.com/stax76/mpv.net/blob/master/mpv.net/Resources/input.conf.txt>
|
||||
- the file association code was completely rewriten, it's now contained within mpvnet.exe instead of a separate application and it adds a few more keys
|
||||
- various new info added to the wiki: <https://github.com/stax76/mpv.net/wiki>
|
||||
- On Top feature was implemented using mpv's native property 'ontop', default bindings at: <https://github.com/stax76/mpv.net/blob/master/mpv.net/Resources/input.conf.txt>
|
||||
|
||||
### 2.2 (2019-04-01)
|
||||
|
||||
- messages boxes had always the info icon even if a different icon (error, warning, question) was intended
|
||||
@@ -77,20 +88,4 @@ https://github.com/stax76/mpv.net/wiki/Scripting-(CSharp,-Python,-JavaScript,-Lu
|
||||
- there was a problem fixed that made the cursor hidden when it should be visible
|
||||
- dragging a youtube URL on mpv.net would break certain input related features
|
||||
- there is now an installer with file extension registration (limited on Win 10) available
|
||||
- WM_APPCOMMAND media keys were not working in the input (shortcut) editor and there were no defaults for prev and next defined
|
||||
|
||||
### 2.1 (2019-03-30)
|
||||
|
||||
- new input editor added, default key binding is here: <https://github.com/stax76/mpv.net/blob/master/mpv.net/Resources/input.conf.txt#L89>
|
||||
|
||||
### 2.0 (2019-03-28)
|
||||
|
||||
- setting track-auto-selection added to settings editor (<https://mpv.io/manual/master/#options-track-auto-selection>)
|
||||
- setting loop-playlist added to settings editor (<https://mpv.io/manual/master/#options-loop-playlist>)
|
||||
- setting audio-file-auto added to settings editor (<https://mpv.io/manual/master/#options-audio-file-auto>)
|
||||
- setting video-sync added to settings editor (<https://mpv.io/manual/master/#options-video-sync>)
|
||||
- command execute-mpv-command added to menu: Tools > Enter a mpv command for execution
|
||||
- added youtube-dl.exe, please note this will only work when a certain Visual C++ runtime is installed
|
||||
- added drag & drop support to drag & drop a youtube URL on mpv.net
|
||||
- added support to open a youtube URL from command line
|
||||
- added support for opening a URL from the menu: Open > Open URL
|
||||
- WM_APPCOMMAND media keys were not working in the input (shortcut) editor and there were no defaults for prev and next defined
|
||||
@@ -1,2 +0,0 @@
|
||||
"C:\Program Files (x86)\Inno Setup 6\ISCC.exe" setup\mpvnet.iss
|
||||
pause
|
||||
@@ -5,7 +5,6 @@ using System.Runtime.InteropServices;
|
||||
using System.Threading;
|
||||
using System.Windows.Forms;
|
||||
using System.Linq;
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace mpvnet
|
||||
{
|
||||
@@ -26,6 +25,7 @@ namespace mpvnet
|
||||
|
||||
try
|
||||
{
|
||||
AppDomain.CurrentDomain.UnhandledException += CurrentDomain_UnhandledException;
|
||||
Application.ThreadException += Application_ThreadException;
|
||||
Instance = this;
|
||||
Hwnd = Handle;
|
||||
@@ -43,7 +43,7 @@ namespace mpvnet
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
MainForm.Instance.ShowMsgBox(e.ToString(), MessageBoxIcon.Error);
|
||||
ShowMsgBox(e.ToString(), MessageBoxIcon.Error);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -81,6 +81,7 @@ namespace mpvnet
|
||||
if (IsFullscreen || mp.VideoSize.Width == 0) return;
|
||||
Screen screen = Screen.FromControl(this);
|
||||
int height = ClientSize.Height;
|
||||
if (height > screen.Bounds.Height * 0.8) height = Convert.ToInt32(screen.Bounds.Height * 0.6);
|
||||
int width = Convert.ToInt32(height * mp.VideoSize.Width / (double)mp.VideoSize.Height);
|
||||
Point middlePos = new Point(Left + Width / 2, Top + Height / 2);
|
||||
var rect = new Native.RECT(new Rectangle(screen.Bounds.X, screen.Bounds.Y, width, height));
|
||||
@@ -88,15 +89,9 @@ namespace mpvnet
|
||||
int left = middlePos.X - rect.Width / 2;
|
||||
int top = middlePos.Y - rect.Height / 2;
|
||||
Screen[] screens = Screen.AllScreens;
|
||||
|
||||
if (left < screens[0].Bounds.Left)
|
||||
left = screens[0].Bounds.Left;
|
||||
|
||||
if (left < screens[0].Bounds.Left) left = screens[0].Bounds.Left;
|
||||
int maxLeft = screens[0].Bounds.Left + screens.Select((sc) => sc.Bounds.Width).Sum() - rect.Width - SystemInformation.CaptionHeight;
|
||||
|
||||
if (left > maxLeft)
|
||||
left = maxLeft;
|
||||
|
||||
if (left > maxLeft) left = maxLeft;
|
||||
Native.SetWindowPos(Handle, IntPtr.Zero /* HWND_TOP */, left, top, rect.Width, rect.Height, 4 /* SWP_NOZORDER */);
|
||||
}
|
||||
|
||||
@@ -156,7 +151,7 @@ namespace mpvnet
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
MainForm.Instance.ShowMsgBox(e.ToString(), MessageBoxIcon.Error);
|
||||
ShowMsgBox(e.ToString(), MessageBoxIcon.Error);
|
||||
}
|
||||
});
|
||||
|
||||
@@ -165,10 +160,7 @@ namespace mpvnet
|
||||
}
|
||||
}
|
||||
|
||||
private void CMS_Opened(object sender, EventArgs e)
|
||||
{
|
||||
CursorHelp.Show();
|
||||
}
|
||||
private void CMS_Opened(object sender, EventArgs e) => CursorHelp.Show();
|
||||
|
||||
private string LastHistory;
|
||||
|
||||
@@ -191,16 +183,18 @@ namespace mpvnet
|
||||
BeginInvoke(new Action(() => { Text = "mpv.net " + Application.ProductVersion; }));
|
||||
}
|
||||
|
||||
private void CM_Popup(object sender, EventArgs e)
|
||||
{
|
||||
CursorHelp.Show();
|
||||
}
|
||||
private void CM_Popup(object sender, EventArgs e) => CursorHelp.Show();
|
||||
|
||||
private void Application_ThreadException(object sender, ThreadExceptionEventArgs e)
|
||||
{
|
||||
ShowMsgBox(e.Exception.ToString(), MessageBoxIcon.Error);
|
||||
}
|
||||
|
||||
private void CurrentDomain_UnhandledException(object sender, UnhandledExceptionEventArgs e)
|
||||
{
|
||||
ShowMsgBox(e.ExceptionObject.ToString(), MessageBoxIcon.Error);
|
||||
}
|
||||
|
||||
private void mp_VideoSizeChanged()
|
||||
{
|
||||
BeginInvoke(new Action(() => SetFormPositionAndSizeKeepHeight()));
|
||||
@@ -213,7 +207,7 @@ namespace mpvnet
|
||||
|
||||
public bool IsFullscreen => WindowState == FormWindowState.Maximized;
|
||||
|
||||
void mp_ChangeFullscreen(bool value)
|
||||
void mpPropChangeFullscreen(bool value)
|
||||
{
|
||||
BeginInvoke(new Action(() => ChangeFullscreen(value)));
|
||||
}
|
||||
@@ -288,7 +282,6 @@ namespace mpvnet
|
||||
m.Result = new IntPtr(1);
|
||||
return;
|
||||
}
|
||||
|
||||
base.WndProc(ref m);
|
||||
}
|
||||
|
||||
@@ -301,12 +294,11 @@ namespace mpvnet
|
||||
|
||||
protected override void OnDragDrop(DragEventArgs e)
|
||||
{
|
||||
base.OnDragDrop(e);
|
||||
if (e.Data.GetDataPresent(DataFormats.FileDrop))
|
||||
mp.LoadFiles(e.Data.GetData(DataFormats.FileDrop) as String[]);
|
||||
if (e.Data.GetDataPresent(DataFormats.Text))
|
||||
mp.LoadURL(e.Data.GetData(DataFormats.Text).ToString());
|
||||
|
||||
base.OnDragDrop(e);
|
||||
}
|
||||
|
||||
protected override void OnMouseDown(MouseEventArgs e)
|
||||
@@ -371,13 +363,16 @@ namespace mpvnet
|
||||
{
|
||||
base.OnLoad(e);
|
||||
mp.Init();
|
||||
mp.observe_property_bool("fullscreen", mp_ChangeFullscreen);
|
||||
mp.observe_property_bool("fullscreen", mpPropChangeFullscreen);
|
||||
mp.observe_property_bool("ontop", mpPropChangeOnTop);
|
||||
mp.Shutdown += mp_Shutdown;
|
||||
mp.VideoSizeChanged += mp_VideoSizeChanged;
|
||||
mp.PlaybackRestart += mp_PlaybackRestart;
|
||||
mp.Idle += Mp_Idle;
|
||||
}
|
||||
|
||||
void mpPropChangeOnTop(bool value) => BeginInvoke(new Action(() => TopMost = value));
|
||||
|
||||
protected override void OnShown(EventArgs e)
|
||||
{
|
||||
base.OnShown(e);
|
||||
@@ -386,6 +381,7 @@ namespace mpvnet
|
||||
ContextMenuStrip = CMS;
|
||||
BuildMenu();
|
||||
IgnoreDpiChanged = false;
|
||||
CheckYouTube();
|
||||
}
|
||||
|
||||
protected override void OnFormClosed(FormClosedEventArgs e)
|
||||
@@ -400,5 +396,24 @@ namespace mpvnet
|
||||
base.OnLostFocus(e);
|
||||
CursorHelp.Show();
|
||||
}
|
||||
|
||||
protected override void OnActivated(EventArgs e)
|
||||
{
|
||||
base.OnActivated(e);
|
||||
CheckYouTube();
|
||||
}
|
||||
|
||||
private string LastURL;
|
||||
|
||||
void CheckYouTube()
|
||||
{
|
||||
string clipboard = Clipboard.GetText();
|
||||
if (clipboard.StartsWith("https://www.youtube.com/watch?") && LastURL != clipboard && Visible)
|
||||
{
|
||||
LastURL = clipboard;
|
||||
if (ShowMsgBox("Play YouTube URL?", MessageBoxIcon.Question) == DialogResult.OK)
|
||||
mp.LoadURL(clipboard);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,6 +1,9 @@
|
||||
using System;
|
||||
using Microsoft.Win32;
|
||||
using System;
|
||||
using System.Collections;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
using System.Runtime.InteropServices;
|
||||
using System.Windows.Forms;
|
||||
|
||||
@@ -34,4 +37,91 @@ namespace mpvnet
|
||||
|
||||
public static float Current => Environment.OSVersion.Version.Major + Environment.OSVersion.Version.Minor / 10f;
|
||||
}
|
||||
|
||||
public class FileAssociation
|
||||
{
|
||||
static string ExePath = Application.ExecutablePath;
|
||||
static string ExeFilename = Path.GetFileName(Application.ExecutablePath);
|
||||
static string ExeFilenameNoExt = Path.GetFileNameWithoutExtension(Application.ExecutablePath);
|
||||
static string[] Types;
|
||||
public static string[] VideoTypes = "mpg avi vob mp4 mkv avs 264 mov wmv flv h264 asf webm mpeg mpv y4m avc hevc 265 h265 m2v m2ts vpy mts webm m4v".Split(" ".ToCharArray());
|
||||
public static string[] AudioTypes = "mp2 mp3 ac3 wav w64 m4a dts dtsma dtshr dtshd eac3 thd thd+ac3 ogg mka aac opus flac mpa".Split(" ".ToCharArray());
|
||||
|
||||
public static void Register(string[] types)
|
||||
{
|
||||
Types = types;
|
||||
|
||||
RegistryHelp.SetValue(@"HKCU\SOFTWARE\Microsoft\Windows\CurrentVersion\App Paths\" + ExeFilename, null, ExePath);
|
||||
RegistryHelp.SetValue($"HKCR\\Applications\\{ExeFilename}", "FriendlyAppName", "mpv.net media player");
|
||||
RegistryHelp.SetValue($"HKCR\\Applications\\{ExeFilename}\\shell\\open\\command", null, $"\"{ExePath}\" \"%1\"");
|
||||
RegistryHelp.SetValue(@"HKLM\SOFTWARE\Clients\Media\mpv\Capabilities", "ApplicationDescription", "mpv.net media player");
|
||||
RegistryHelp.SetValue(@"HKLM\SOFTWARE\Clients\Media\mpv\Capabilities", "ApplicationName", "mpv.net");
|
||||
RegistryHelp.SetValue($"HKCR\\SystemFileAssociations\\video\\OpenWithList\\{ExeFilename}", null, "");
|
||||
RegistryHelp.SetValue($"HKCR\\SystemFileAssociations\\audio\\OpenWithList\\{ExeFilename}", null, "");
|
||||
|
||||
foreach (string ext in Types)
|
||||
{
|
||||
RegistryHelp.SetValue($"HKCR\\Applications\\{ExeFilename}\\SupportedTypes", "." + ext, "");
|
||||
RegistryHelp.SetValue($"HKCR\\" + "." + ext, null, ExeFilenameNoExt + "." + ext);
|
||||
RegistryHelp.SetValue($"HKCR\\" + "." + ext + "\\OpenWithProgIDs", ExeFilenameNoExt + "." + ext, "");
|
||||
if (VideoTypes.Contains(ext))
|
||||
RegistryHelp.SetValue($"HKCR\\" + "." + ext, "PerceivedType", "video");
|
||||
if (AudioTypes.Contains(ext))
|
||||
RegistryHelp.SetValue($"HKCR\\" + "." + ext, "PerceivedType", "audio");
|
||||
RegistryHelp.SetValue($"HKCR\\" + ExeFilenameNoExt + "." + ext + "\\shell\\open", null, "Play with " + Application.ProductName);
|
||||
RegistryHelp.SetValue($"HKCR\\" + ExeFilenameNoExt + "." + ext + "\\shell\\open\\command", null, $"\"{ExePath}\" \"%1\"");
|
||||
RegistryHelp.SetValue(@"HKLM\SOFTWARE\Clients\Media\mpv.net\Capabilities\FileAssociations", "." + ext, ExeFilenameNoExt + "." + ext);
|
||||
}
|
||||
}
|
||||
|
||||
public static void Unregister()
|
||||
{
|
||||
RegistryHelp.RemoveKey(@"HKCU\SOFTWARE\Microsoft\Windows\CurrentVersion\App Paths\" + ExeFilename);
|
||||
RegistryHelp.RemoveKey($"HKCR\\Applications\\{ExeFilename}");
|
||||
RegistryHelp.RemoveKey(@"HKLM\SOFTWARE\Clients\Media\mpv.net");
|
||||
RegistryHelp.RemoveKey($"HKCR\\SystemFileAssociations\\video\\OpenWithList\\{ExeFilename}");
|
||||
RegistryHelp.RemoveKey($"HKCR\\SystemFileAssociations\\audio\\OpenWithList\\{ExeFilename}");
|
||||
|
||||
foreach (string id in Registry.ClassesRoot.GetSubKeyNames())
|
||||
{
|
||||
if (id.StartsWith(ExeFilenameNoExt + "."))
|
||||
Registry.ClassesRoot.DeleteSubKeyTree(id);
|
||||
|
||||
RegistryHelp.RemoveValue($"HKCR\\Software\\Classes\\" + id + "\\OpenWithProgIDs", ExeFilenameNoExt + id);
|
||||
RegistryHelp.RemoveValue($"HKLM\\Software\\Classes\\" + id + "\\OpenWithProgIDs", ExeFilenameNoExt + id);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public class RegistryHelp
|
||||
{
|
||||
public static void SetValue(string path, string name, string value)
|
||||
{
|
||||
using (RegistryKey rk = GetRootKey(path).CreateSubKey(path.Substring(5), RegistryKeyPermissionCheck.ReadWriteSubTree))
|
||||
rk.SetValue(name, value);
|
||||
}
|
||||
|
||||
public static void RemoveKey(string path)
|
||||
{
|
||||
GetRootKey(path).DeleteSubKeyTree(path.Substring(5), false);
|
||||
}
|
||||
|
||||
public static void RemoveValue(string path, string name)
|
||||
{
|
||||
using (RegistryKey rk = GetRootKey(path).OpenSubKey(path.Substring(5), true))
|
||||
if (!(rk is null))
|
||||
rk.DeleteValue(name, false);
|
||||
}
|
||||
|
||||
static RegistryKey GetRootKey(string path)
|
||||
{
|
||||
switch (path.Substring(0, 4))
|
||||
{
|
||||
case "HKLM": return Registry.LocalMachine;
|
||||
case "HKCU": return Registry.CurrentUser;
|
||||
case "HKCR": return Registry.ClassesRoot;
|
||||
default: throw new Exception();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -8,6 +8,24 @@ namespace mpvnet
|
||||
[STAThread]
|
||||
static void Main()
|
||||
{
|
||||
try
|
||||
{
|
||||
string[] args = Environment.GetCommandLineArgs();
|
||||
|
||||
if (args.Length == 3 && args[1] == "--reg-file-assoc")
|
||||
{
|
||||
if (args[2] == "audio") FileAssociation.Register(FileAssociation.AudioTypes);
|
||||
if (args[2] == "video") FileAssociation.Register(FileAssociation.VideoTypes);
|
||||
if (args[2] == "unregister") FileAssociation.Unregister();
|
||||
return;
|
||||
}
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
MessageBox.Show(ex.ToString(), Application.ProductName, MessageBoxButtons.OK, MessageBoxIcon.Error);
|
||||
return;
|
||||
}
|
||||
|
||||
Application.EnableVisualStyles();
|
||||
Application.SetCompatibleTextRenderingDefault(false);
|
||||
Application.Run(new MainForm());
|
||||
|
||||
@@ -10,7 +10,7 @@ using System.Runtime.InteropServices;
|
||||
[assembly: AssemblyConfiguration("")]
|
||||
[assembly: AssemblyCompany("")]
|
||||
[assembly: AssemblyProduct("mpv.net")]
|
||||
[assembly: AssemblyCopyright("Copyright © stax76")]
|
||||
[assembly: AssemblyCopyright("Copyright © 2017 stax76")]
|
||||
[assembly: AssemblyTrademark("")]
|
||||
[assembly: AssemblyCulture("")]
|
||||
|
||||
@@ -32,5 +32,5 @@ using System.Runtime.InteropServices;
|
||||
// You can specify all the values or you can default the Build and Revision Numbers
|
||||
// by using the '*' as shown below:
|
||||
// [assembly: AssemblyVersion("1.0.*")]
|
||||
[assembly: AssemblyVersion("2.2.0.0")]
|
||||
[assembly: AssemblyFileVersion("2.2.0.0")]
|
||||
[assembly: AssemblyVersion("2.3.0.0")]
|
||||
[assembly: AssemblyFileVersion("2.3.0.0")]
|
||||
|
||||
@@ -1,3 +1,29 @@
|
||||
|
||||
# This file defines the input (keys and mouse) bindings of mpv and mpv.net
|
||||
# and it also defines the context menu of mpv.net. mpv.net has a input
|
||||
# editor and a conf editor as alternatives to editing this file via texteditor.
|
||||
# The input and conf editors can be found in mpv.net's context menu at:
|
||||
|
||||
# Settings > Show Config Editor
|
||||
# Settings > Show Input Editor
|
||||
|
||||
# The defaults of this file can be found at:
|
||||
|
||||
# https://github.com/stax76/mpv.net/blob/master/mpv.net/Resources/input.conf.txt
|
||||
|
||||
# the defaults of mpv can be found at:
|
||||
|
||||
# https://github.com/mpv-player/mpv/blob/master/etc/input.conf
|
||||
|
||||
# mpv.net's defaults of mpv.conf contain: 'input-default-bindings = no'
|
||||
# which disables mpv's input defaults. Every line in this file begins with a
|
||||
# space character to make it easier to do a text search, so if you want to know
|
||||
# if 'o' has already a binding you can make a text search on ' o '.
|
||||
|
||||
# mpv input commands: https://github.com/stax76/mpv.net/wiki/mpv-input-commands
|
||||
|
||||
# mpv input keys: https://github.com/stax76/mpv.net/wiki/mpv-input-keys
|
||||
|
||||
o script-message mpv.net open-files #menu: Open > Open Files...
|
||||
u script-message mpv.net open-url #menu: Open > Open URL...
|
||||
_ ignore #menu: -
|
||||
@@ -83,30 +109,36 @@
|
||||
KP3 script-message rate-file 3 #menu: Addons > Rating > 3stars
|
||||
KP4 script-message rate-file 4 #menu: Addons > Rating > 4stars
|
||||
KP5 script-message rate-file 5 #menu: Addons > Rating > 5stars
|
||||
_ script-message mpv.net set-setting hwdec yes #menu: Settings > Hardware Decoding > Enable
|
||||
_ script-message mpv.net set-setting hwdec no #menu: Settings > Hardware Decoding > Disable
|
||||
e script-message mpv.net show-conf-editor #menu: Settings > Show Config Editor
|
||||
Ctrl+i script-message mpv.net show-input-editor #menu: Settings > Show Input Editor
|
||||
c script-message mpv.net open-config-folder #menu: Settings > Open Config Folder
|
||||
i script-message mpv.net show-info #menu: Tools > Info
|
||||
t script-binding stats/display-stats #menu: Tools > Show Statistics
|
||||
T script-binding stats/display-stats-toggle #menu: Tools > Toggle Statistics
|
||||
_ ignore #menu: Tools > -
|
||||
h script-message mpv.net show-history #menu: Tools > Show History
|
||||
l ab-loop #menu: Tools > Set/clear A-B loop points
|
||||
L cycle-values loop-file "inf" "no" #menu: Tools > Toggle Infinite Looping
|
||||
Del script-binding osc/visibility #menu: Tools > Toggle OSC Visibility
|
||||
Ctrl+h cycle-values hwdec "auto" "no" #menu: Tools > Cycle Hardware Decoding
|
||||
F8 show-text ${playlist} 5000 #menu: Tools > Show Playlist
|
||||
F9 show-text ${track-list} 5000 #menu: Tools > Show Audio/Video/Subtitle List
|
||||
_ script-message mpv.net execute-mpv-command #menu: Tools > Execute mpv command...
|
||||
|
||||
Ctrl+t set ontop yes #menu: View > On Top > Enable
|
||||
Ctrl+T set ontop no #menu: View > On Top > Disable
|
||||
i script-message mpv.net show-info #menu: View > File Info
|
||||
t script-binding stats/display-stats #menu: View > Show Statistics
|
||||
T script-binding stats/display-stats-toggle #menu: View > Toggle Statistics
|
||||
|
||||
_ script-message mpv.net set-setting hwdec yes #menu: Settings > Hardware Decoding > Enable
|
||||
_ script-message mpv.net set-setting hwdec no #menu: Settings > Hardware Decoding > Disable
|
||||
Ctrl+c script-message mpv.net show-conf-editor #menu: Settings > Show Config Editor
|
||||
Ctrl+i script-message mpv.net show-input-editor #menu: Settings > Show Input Editor
|
||||
Ctrl+f script-message mpv.net open-config-folder #menu: Settings > Open Config Folder
|
||||
|
||||
h script-message mpv.net show-history #menu: Tools > Show History
|
||||
l ab-loop #menu: Tools > Set/clear A-B loop points
|
||||
L cycle-values loop-file "inf" "no" #menu: Tools > Toggle Infinite Looping
|
||||
Del script-binding osc/visibility #menu: Tools > Toggle OSC Visibility
|
||||
Ctrl+h cycle-values hwdec "auto" "no" #menu: Tools > Cycle Hardware Decoding
|
||||
F8 show-text ${playlist} 5000 #menu: Tools > Show Playlist
|
||||
F9 show-text ${track-list} 5000 #menu: Tools > Show Audio/Video/Subtitle List
|
||||
_ script-message mpv.net execute-mpv-command #menu: Tools > Execute mpv command...
|
||||
|
||||
_ script-message mpv.net shell-execute https://mpv.io/manual/stable/ #menu: Help > Show mpv manual
|
||||
_ script-message mpv.net shell-execute https://github.com/mpv-player/mpv/blob/master/etc/input.conf #menu: Help > Show mpv default keys
|
||||
_ script-message mpv.net shell-execute https://github.com/stax76/mpv.net/blob/master/mpv.net/Resources/input.conf.txt #menu: Help > Show mpv.net default keys
|
||||
_ script-message mpv.net shell-execute https://github.com/stax76/mpvnet #menu: Help > Show mpv.net web site
|
||||
_ ignore #menu: -
|
||||
Esc quit #menu: Exit
|
||||
Q quit-watch-later #menu: Exit Watch Later
|
||||
|
||||
_ ignore #menu: -
|
||||
Esc quit #menu: Exit
|
||||
Q quit-watch-later #menu: Exit Watch Later
|
||||
> playlist-next
|
||||
< playlist-prev
|
||||
Enter cycle pause
|
||||
@@ -123,4 +155,4 @@
|
||||
Wheel_Up add volume 10
|
||||
Wheel_Down add volume -10
|
||||
Prev playlist-prev
|
||||
Next playlist-next
|
||||
Next playlist-next
|
||||
|
||||
@@ -1,11 +1,12 @@
|
||||
# mpv manual: https://mpv.io/manual/master/
|
||||
|
||||
# mpv manual: https://mpv.io/manual/master/
|
||||
|
||||
# mpv.net mpv.conf defaults: https://github.com/stax76/mpv.net/blob/master/mpv.net/Resources/mpv.conf.txt
|
||||
|
||||
input-ar-delay = 500
|
||||
input-ar-rate = 20
|
||||
volume = 50
|
||||
hwdec = yes
|
||||
vo = direct3d
|
||||
keep-open = yes
|
||||
keep-open-pause = no
|
||||
osd-playing-msg = ${filename}
|
||||
|
||||
232
mpv.net/mp.cs
232
mpv.net/mp.cs
@@ -142,130 +142,137 @@ namespace mpvnet
|
||||
|
||||
//Debug.WriteLine(evt.event_id.ToString());
|
||||
|
||||
switch (evt.event_id)
|
||||
try
|
||||
{
|
||||
case mpv_event_id.MPV_EVENT_SHUTDOWN:
|
||||
Shutdown?.Invoke();
|
||||
AutoResetEvent.Set();
|
||||
return;
|
||||
case mpv_event_id.MPV_EVENT_LOG_MESSAGE:
|
||||
LogMessage?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_GET_PROPERTY_REPLY:
|
||||
GetPropertyReply?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_SET_PROPERTY_REPLY:
|
||||
SetPropertyReply?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_COMMAND_REPLY:
|
||||
CommandReply?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_START_FILE:
|
||||
StartFile?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_END_FILE:
|
||||
var end_fileData = (mpv_event_end_file)Marshal.PtrToStructure(evt.data, typeof(mpv_event_end_file));
|
||||
EndFile?.Invoke((EndFileEventMode)end_fileData.reason);
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_FILE_LOADED:
|
||||
FileLoaded?.Invoke();
|
||||
LoadFolder();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_TRACKS_CHANGED:
|
||||
TracksChanged?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_TRACK_SWITCHED:
|
||||
TrackSwitched?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_IDLE:
|
||||
Idle?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_PAUSE:
|
||||
Pause?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_UNPAUSE:
|
||||
Unpause?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_TICK:
|
||||
Tick?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_SCRIPT_INPUT_DISPATCH:
|
||||
ScriptInputDispatch?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_CLIENT_MESSAGE:
|
||||
if (ClientMessage != null)
|
||||
{
|
||||
try
|
||||
switch (evt.event_id)
|
||||
{
|
||||
case mpv_event_id.MPV_EVENT_SHUTDOWN:
|
||||
Shutdown?.Invoke();
|
||||
AutoResetEvent.Set();
|
||||
return;
|
||||
case mpv_event_id.MPV_EVENT_LOG_MESSAGE:
|
||||
LogMessage?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_GET_PROPERTY_REPLY:
|
||||
GetPropertyReply?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_SET_PROPERTY_REPLY:
|
||||
SetPropertyReply?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_COMMAND_REPLY:
|
||||
CommandReply?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_START_FILE:
|
||||
StartFile?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_END_FILE:
|
||||
var end_fileData = (mpv_event_end_file)Marshal.PtrToStructure(evt.data, typeof(mpv_event_end_file));
|
||||
EndFile?.Invoke((EndFileEventMode)end_fileData.reason);
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_FILE_LOADED:
|
||||
FileLoaded?.Invoke();
|
||||
LoadFolder();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_TRACKS_CHANGED:
|
||||
TracksChanged?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_TRACK_SWITCHED:
|
||||
TrackSwitched?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_IDLE:
|
||||
Idle?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_PAUSE:
|
||||
Pause?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_UNPAUSE:
|
||||
Unpause?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_TICK:
|
||||
Tick?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_SCRIPT_INPUT_DISPATCH:
|
||||
ScriptInputDispatch?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_CLIENT_MESSAGE:
|
||||
if (ClientMessage != null)
|
||||
{
|
||||
var client_messageData = (mpv_event_client_message)Marshal.PtrToStructure(evt.data, typeof(mpv_event_client_message));
|
||||
string[] args = NativeUtf8StrArray2ManagedStrArray(client_messageData.args, client_messageData.num_args);
|
||||
|
||||
if (args != null && args.Length > 1 && args[0] == "mpv.net")
|
||||
try
|
||||
{
|
||||
bool found = false;
|
||||
var client_messageData = (mpv_event_client_message)Marshal.PtrToStructure(evt.data, typeof(mpv_event_client_message));
|
||||
string[] args = NativeUtf8StrArray2ManagedStrArray(client_messageData.args, client_messageData.num_args);
|
||||
|
||||
foreach (var i in mpvnet.Command.Commands)
|
||||
if (args != null && args.Length > 1 && args[0] == "mpv.net")
|
||||
{
|
||||
if (args[1] == i.Name)
|
||||
bool found = false;
|
||||
|
||||
foreach (var i in mpvnet.Command.Commands)
|
||||
{
|
||||
found = true;
|
||||
i.Action.Invoke(args.Skip(2).ToArray());
|
||||
if (args[1] == i.Name)
|
||||
{
|
||||
found = true;
|
||||
i.Action.Invoke(args.Skip(2).ToArray());
|
||||
}
|
||||
}
|
||||
if (!found)
|
||||
{
|
||||
List<string> names = mpvnet.Command.Commands.Select((item) => item.Name).ToList();
|
||||
names.Sort();
|
||||
MainForm.Instance.ShowMsgBox($"No command '{args[1]}' found. Available commands are:\n\n{string.Join("\n", names)}\n\nHow to bind these commands can be seen in the default input bindings and menu definition located at:\n\nhttps://github.com/stax76/mpv.net/blob/master/mpv.net/Resources/input.conf.txt", MessageBoxIcon.Error);
|
||||
}
|
||||
}
|
||||
if (!found)
|
||||
{
|
||||
List<string> names = mpvnet.Command.Commands.Select((item) => item.Name).ToList();
|
||||
names.Sort();
|
||||
MainForm.Instance.ShowMsgBox($"No command '{args[1]}' found. Available commands are:\n\n{string.Join("\n", names)}\n\nHow to bind these commands can be seen in the default input bindings and menu definition located at:\n\nhttps://github.com/stax76/mpv.net/blob/master/mpv.net/Resources/input.conf.txt", MessageBoxIcon.Error);
|
||||
}
|
||||
ClientMessage?.Invoke(args);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
MainForm.Instance.ShowMsgBox(ex.GetType().Name + "\n\n" + ex.ToString(), MessageBoxIcon.Error);
|
||||
}
|
||||
ClientMessage?.Invoke(args);
|
||||
}
|
||||
catch (Exception ex)
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_VIDEO_RECONFIG:
|
||||
VideoReconfig?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_AUDIO_RECONFIG:
|
||||
AudioReconfig?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_METADATA_UPDATE:
|
||||
MetadataUpdate?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_SEEK:
|
||||
Seek?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_PROPERTY_CHANGE:
|
||||
var event_propertyData = (mpv_event_property)Marshal.PtrToStructure(evt.data, typeof(mpv_event_property));
|
||||
|
||||
if (event_propertyData.format == mpv_format.MPV_FORMAT_FLAG)
|
||||
foreach (var i in BoolPropChangeActions)
|
||||
if (i.Key== event_propertyData.name)
|
||||
i.Value.Invoke(Marshal.PtrToStructure<int>(event_propertyData.data) == 1);
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_PLAYBACK_RESTART:
|
||||
PlaybackRestart?.Invoke();
|
||||
Size s = new Size(get_property_int("dwidth"), get_property_int("dheight"));
|
||||
|
||||
if (VideoSize != s && s != Size.Empty)
|
||||
{
|
||||
MainForm.Instance.ShowMsgBox(ex.GetType().Name + "\n\n" + ex.ToString(), MessageBoxIcon.Error);
|
||||
VideoSize = s;
|
||||
VideoSizeChanged?.Invoke();
|
||||
}
|
||||
}
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_VIDEO_RECONFIG:
|
||||
VideoReconfig?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_AUDIO_RECONFIG:
|
||||
AudioReconfig?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_METADATA_UPDATE:
|
||||
MetadataUpdate?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_SEEK:
|
||||
Seek?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_PROPERTY_CHANGE:
|
||||
var event_propertyData = (mpv_event_property)Marshal.PtrToStructure(evt.data, typeof(mpv_event_property));
|
||||
|
||||
if (event_propertyData.format == mpv_format.MPV_FORMAT_FLAG)
|
||||
foreach (var i in BoolPropChangeActions)
|
||||
if (i.Key== event_propertyData.name)
|
||||
i.Value.Invoke(Marshal.PtrToStructure<int>(event_propertyData.data) == 1);
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_PLAYBACK_RESTART:
|
||||
PlaybackRestart?.Invoke();
|
||||
Size s = new Size(get_property_int("dwidth"), get_property_int("dheight"));
|
||||
|
||||
if (VideoSize != s && s != Size.Empty)
|
||||
{
|
||||
VideoSize = s;
|
||||
VideoSizeChanged?.Invoke();
|
||||
}
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_CHAPTER_CHANGE:
|
||||
ChapterChange?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_QUEUE_OVERFLOW:
|
||||
QueueOverflow?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_HOOK:
|
||||
Hook?.Invoke();
|
||||
break;
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_CHAPTER_CHANGE:
|
||||
ChapterChange?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_QUEUE_OVERFLOW:
|
||||
QueueOverflow?.Invoke();
|
||||
break;
|
||||
case mpv_event_id.MPV_EVENT_HOOK:
|
||||
Hook?.Invoke();
|
||||
break;
|
||||
}
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
MainForm.Instance.ShowMsgBox(ex.ToString(), MessageBoxIcon.Error);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -489,6 +496,7 @@ namespace mpvnet
|
||||
{
|
||||
string[] types = "264 265 3gp aac ac3 avc avi avs bmp divx dts dtshd dtshr dtsma eac3 evo flac flv h264 h265 hevc hvc jpg jpeg m2t m2ts m2v m4a m4v mka mkv mlp mov mp2 mp3 mp4 mpa mpeg mpg mpv mts ogg ogm opus pcm png pva raw rmvb thd thd+ac3 true-hd truehd ts vdr vob vpy w64 wav webm wmv y4m".Split(' ');
|
||||
string path = get_property_string("path");
|
||||
if (!Directory.Exists(Path.GetDirectoryName(path))) return;
|
||||
List<string> files = Directory.GetFiles(Path.GetDirectoryName(path)).ToList();
|
||||
files = files.Where((file) => types.Contains(Path.GetExtension(file).TrimStart(".".ToCharArray()).ToLower())).ToList();
|
||||
files.Sort(new StringLogicalComparer());
|
||||
|
||||
@@ -168,6 +168,9 @@
|
||||
<SubType>Designer</SubType>
|
||||
<LastGenOutput>Resources.Designer.cs</LastGenOutput>
|
||||
</EmbeddedResource>
|
||||
<None Include="..\README.md">
|
||||
<Link>README.md</Link>
|
||||
</None>
|
||||
<None Include="app.manifest" />
|
||||
<None Include="packages.config" />
|
||||
<None Include="Properties\Settings.settings">
|
||||
|
||||
17
mpvnet.iss
17
mpvnet.iss
@@ -1,6 +1,7 @@
|
||||
#define MyAppName "mpv.net"
|
||||
#define MyAppVersion GetFileVersion("mpv.net\bin\mpvnet.exe")
|
||||
#define MyAppExeName "mpvnet.exe"
|
||||
#define MyAppSourceDir "mpv.net\bin"
|
||||
|
||||
[Setup]
|
||||
AppId={{9AA2B100-BEF3-44D0-B819-D8FC3C4D557D}}
|
||||
@@ -10,18 +11,20 @@ AppPublisher=stax76
|
||||
ArchitecturesInstallIn64BitMode=x64
|
||||
Compression=lzma2
|
||||
DefaultDirName={commonpf}\{#MyAppName}
|
||||
DisableProgramGroupPage=yes
|
||||
OutputBaseFilename=mpvnet-{#MyAppVersion}
|
||||
OutputDir=C:\Users\frank\Desktop
|
||||
ChangesAssociations=yes
|
||||
DefaultGroupName={#MyAppName}
|
||||
|
||||
[Icons]
|
||||
Name: "{group}\{#MyAppName}"; Filename: "{app}\{#MyAppExeName}"
|
||||
|
||||
[Files]
|
||||
Source: "C:\Users\frank\Daten\Projekte\CS\mpv.net\mpv.net\bin\mpvnet.exe"; DestDir: "{app}"; Flags: ignoreversion
|
||||
Source: "C:\Users\frank\Daten\Projekte\CS\mpv.net\mpv.net\bin\*"; DestDir: "{app}"; Flags: ignoreversion recursesubdirs createallsubdirs; Excludes: "System.Management.Automation.xml"
|
||||
Source: "{#MyAppSourceDir}\{#MyAppExeName}"; DestDir: "{app}"; Flags: ignoreversion
|
||||
Source: "{#MyAppSourceDir}\*"; DestDir: "{app}"; Flags: ignoreversion recursesubdirs createallsubdirs; Excludes: "System.Management.Automation.xml"
|
||||
|
||||
[Run]
|
||||
Filename: "{app}\defapp.exe"; Description: "Associate video file extensions?"; Flags: postinstall unchecked runascurrentuser runhidden nowait; Parameters: """{app}\{#MyAppExeName}"" mpg avi vob mp4 mkv avs 264 mov wmv flv h264 asf webm mpeg mpv y4m avc hevc 265 h265 m2v m2ts vpy mts webm m4v"
|
||||
Filename: "{app}\defapp.exe"; Description: "Associate audio file extensions?"; Flags: postinstall unchecked runascurrentuser runhidden nowait; Parameters: """{app}\{#MyAppExeName}"" mp2 mp3 ac3 wav w64 m4a dts dtsma dtshr dtshd eac3 thd thd+ac3 ogg mka aac opus flac mpa"
|
||||
Filename: "{app}\{#MyAppExeName}"; Description: "Associate video file extensions?"; Flags: postinstall unchecked runascurrentuser runhidden nowait; Parameters: "--reg-file-assoc video"
|
||||
Filename: "{app}\{#MyAppExeName}"; Description: "Associate audio file extensions?"; Flags: postinstall unchecked runascurrentuser runhidden nowait; Parameters: "--reg-file-assoc audio"
|
||||
|
||||
[UninstallRun]
|
||||
Filename: "{app}\defapp.exe"; Flags: runascurrentuser runhidden nowait; Parameters: """{app}\{#MyAppExeName}"""
|
||||
Filename: "{app}\{#MyAppExeName}"; Flags: runascurrentuser runhidden; Parameters: "--reg-file-assoc unregister"
|
||||
Reference in New Issue
Block a user