Skip to content

Instantly share code, notes, and snippets.

@altrive
Last active May 23, 2023 13:51
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save altrive/7253135 to your computer and use it in GitHub Desktop.
Save altrive/7253135 to your computer and use it in GitHub Desktop.
PowerShell ISE don't support multi-sequence keyboard shortcuts like Ctrl+K,Ctrl+D by default. It need to create MultiKeyGesture class inherited from KeyGesture.
$ErrorActionPreference = "Stop"
function Main
{
if ($Host.Name -ne "Windows PowerShell ISE Host"){
return
}
$menus = $psISE.CurrentPowerShellTab.AddOnsMenu.Submenus
#Note: Can't use "Ctrl+C" shortcut in key sequences. because it's used to cancel executing script, and can't override.
$title = "Format Document"
$gesture = New-Object MultiKeyGesture(@(
New-Object Windows.Input.KeyGesture([Windows.Input.Key]::K, [Windows.Input.ModifierKeys]::Control)
New-Object Windows.Input.KeyGesture([Windows.Input.Key]::D, [Windows.Input.ModifierKeys]::Control)
), "Ctrl+K, Ctrl+D")
$sb = { Invoke-FormatDocument }
$item = $menus | where DisplayName -eq $title
if ($item -ne $null){
$menus.Remove($item) > $null
}
$menus.Add($title, $sb, $gesture) > $null
}
function Invoke-FormatDocument
{
Write-Host "Invoke-FormatDocument(Ctrl+K, Ctrl+D)"
}
Add-Type -ReferencedAssemblies @("WindowsBase", "PresentationCore") -TypeDefinition @'
using System;
using System.Linq;
using System.Windows.Input;
public class MultiKeyGesture : KeyGesture
{
private readonly KeyGesture[] _gestures;
private int _index;
public MultiKeyGesture(KeyGesture[] gestures, string displayString)
: base(gestures.First().Key, gestures.First().Modifiers, displayString)
{
this._gestures = gestures;
}
public override bool Matches(object targetElement, InputEventArgs inputEventArgs)
{
var args = inputEventArgs as KeyEventArgs;
if (args == null)
{
return false;
}
//Test current gesuture
if (!TestCurrentGesture(args))
{
//Reset status
_index = 0;
return false;
}
++_index;
System.Diagnostics.Debug.WriteLine(_index);
if (_index < _gestures.Length)
{
return false; //wait next gesture
}
//Match all gesture sequence
_index = 0;
return true;
}
private bool TestCurrentGesture(KeyEventArgs args)
{
var currentGesture = _gestures[_index];
if (currentGesture.Modifiers == args.KeyboardDevice.Modifiers && currentGesture.Key == args.Key)
{
args.Handled = true;
return true;
}
return false;
}
}
'@
. Main
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment