Add ContextMenu

This commit is contained in:
Jeremy Wu 2020-05-25 18:58:04 +10:00
parent 08a3215c9d
commit b737811bdc
2 changed files with 203 additions and 2 deletions

View file

@ -0,0 +1,199 @@
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Threading.Tasks;
using System.Windows;
using Flow.Launcher.Infrastructure.Logger;
using Flow.Launcher.Plugin.SharedCommands;
using Flow.Launcher.Plugin.Explorer.Search;
namespace Flow.Launcher.Plugin.Explorer
{
internal class ContextMenu : IContextMenu
{
public List<Result> LoadContextMenus(Result selectedResult)
{
var contextMenus = new List<Result>();
if (selectedResult.ContextData is SearchResult record)
{
if (record.Type == ResultType.File)
{
contextMenus.Add(CreateOpenWithEditorResult(record));
contextMenus.Add(CreateOpenContainingFolderResult(record));
}
var icoPath = (record.Type == ResultType.File) ? Constants.FileImagePath : Constants.FolderImagePath;
var fileOrFolder = (record.Type == ResultType.File) ? "file" : "folder";
contextMenus.Add(new Result
{
Title = "Copy path",
SubTitle = $"Copy the current {fileOrFolder} path to clipboard",
Action = (context) =>
{
try
{
Clipboard.SetText(record.FullPath);
return true;
}
catch (Exception e)
{
var message = "Fail to set text in clipboard";
LogException(message, e);
Main.Context.API.ShowMsg(message);
return false;
}
},
IcoPath = Constants.CopyImagePath
});
contextMenus.Add(new Result
{
Title = $"Copy {fileOrFolder}",
SubTitle = $"Copy the {fileOrFolder} to clipboard",
Action = (context) =>
{
try
{
Clipboard.SetFileDropList(new System.Collections.Specialized.StringCollection { record.FullPath });
return true;
}
catch (Exception e)
{
var message = $"Fail to set {fileOrFolder} in clipboard";
LogException(message, e);
Main.Context.API.ShowMsg(message);
return false;
}
},
IcoPath = icoPath
});
if (record.Type == ResultType.File || record.Type == ResultType.Folder)
contextMenus.Add(new Result
{
Title = $"Delete {fileOrFolder}",
SubTitle = $"Delete the selected {fileOrFolder}",
Action = (context) =>
{
try
{
if (record.Type == ResultType.File)
File.Delete(record.FullPath);
else
Directory.Delete(record.FullPath, true);
}
catch (Exception e)
{
var message = $"Fail to delete {fileOrFolder} at {record.FullPath}";
LogException(message, e);
Main.Context.API.ShowMsg(message);
return false;
}
return true;
},
IcoPath = Constants.DeleteFileFolderImagePath
});
if (record.Type == ResultType.File && CanRunAsDifferentUser(record.FullPath))
contextMenus.Add(new Result
{
Title = "Run as different user",
Action = (context) =>
{
try
{
Task.Run(() => ShellCommand.RunAsDifferentUser(record.FullPath.SetProcessStartInfo()));
}
catch (FileNotFoundException e)
{
var name = "Plugin: Folder";
var message = $"File not found: {e.Message}";
Main.Context.API.ShowMsg(name, message);
}
return true;
},
IcoPath = "Images/user.png"
});
}
return contextMenus;
}
private Result CreateOpenContainingFolderResult(SearchResult record)
{
return new Result
{
Title = "Open containing folder",
Action = _ =>
{
try
{
Process.Start("explorer.exe", $" /select,\"{record.FullPath}\"");
}
catch (Exception e)
{
var message = $"Fail to open file at {record.FullPath}";
LogException(message, e);
Main.Context.API.ShowMsg(message);
return false;
}
return true;
},
IcoPath = Constants.FolderImagePath
};
}
private Result CreateOpenWithEditorResult(SearchResult record)
{
string editorPath = "notepad.exe"; // TODO add the ability to create a custom editor
var name = "Open With Editor: " + Path.GetFileNameWithoutExtension(editorPath);
return new Result
{
Title = name,
Action = _ =>
{
try
{
Process.Start(editorPath, record.FullPath);
return true;
}
catch (Exception e)
{
var message = $"Fail to editor for file at {record.FullPath}";
LogException(message, e);
Main.Context.API.ShowMsg(message);
return false;
}
},
IcoPath = editorPath
};
}
public void LogException(string message, Exception e)
{
Log.Exception($"|Flow.Launcher.Plugin.Folder.ContextMenu|{message}", e);
}
private bool CanRunAsDifferentUser(string path)
{
switch (Path.GetExtension(path))
{
case ".exe":
case ".bat":
case ".msi":
return true;
default:
return false;
}
}
}
}

View file

@ -16,6 +16,8 @@ namespace Flow.Launcher.Plugin.Explorer
private SettingsViewModel _viewModel;
private IContextMenu _contextMenu;
public Control CreateSettingPanel()
{
return new ExplorerSettings();
@ -24,14 +26,14 @@ namespace Flow.Launcher.Plugin.Explorer
public void Init(PluginInitContext context)
{
Context = context;
_viewModel = new SettingsViewModel();
_settings = _viewModel.Settings;
_contextMenu = new ContextMenu();
}
public List<Result> LoadContextMenus(Result selectedResult)
{
return new List<Result>();
return _contextMenu.LoadContextMenus(selectedResult);
}
public List<Result> Query(Query query)