diff --git a/mRemoteV1/App/NativeMethods.cs b/mRemoteV1/App/NativeMethods.cs index c9250671d..595046262 100644 --- a/mRemoteV1/App/NativeMethods.cs +++ b/mRemoteV1/App/NativeMethods.cs @@ -382,12 +382,12 @@ namespace mRemoteNG.App public const int WM_KEYUP = 0x101; /// - /// + /// Posted to the window with the keyboard focus when a WM_KEYDOWN message is translated by the TranslateMessage function. The WM_CHAR message contains the character code of the key that was pressed. /// public const int WM_CHAR = 0x102; /// - /// + /// Sent when the user selects a command item from a menu, when a control sends a notification message to its parent window, or when an accelerator keystroke is translated. /// public const int WM_COMMAND = 0x111; diff --git a/mRemoteV1/Tools/MultiSSHController.cs b/mRemoteV1/Tools/MultiSSHController.cs new file mode 100644 index 000000000..60384e6b7 --- /dev/null +++ b/mRemoteV1/Tools/MultiSSHController.cs @@ -0,0 +1,134 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Windows.Forms; +using System.Collections; +using mRemoteNG.App; +using mRemoteNG.Connection; +using mRemoteNG.Connection.Protocol; + +namespace mRemoteNG.Tools +{ + class MultiSSHController + { + private ArrayList processHandlers = new ArrayList(); + private ArrayList previousCommands = new ArrayList(); + private int previousCommandIndex = 0; + + public int CommandHistoryLength { get; set; } = 100; + + public MultiSSHController(TextBox txtBox) + { + DecorateTextBox(txtBox); + } + + public MultiSSHController(ToolStripTextBox txtBox) + { + DecorateTextBox(txtBox.TextBox); + } + + private void DecorateTextBox(TextBox toBeDecorated) + { + toBeDecorated.Enter += refreshActiveConnections; + toBeDecorated.KeyDown += processKeyPress; + toBeDecorated.KeyUp += processKeyRelease; + } + + private void SendAllKeystrokes(int keyType, int keyData) + { + if (processHandlers.Count == 0) + { + return; + } + foreach (PuttyBase proc in processHandlers) + { + NativeMethods.PostMessage(proc.PuttyHandle, keyType, new IntPtr(keyData), new IntPtr(0)); + } + } + +#region Event Processors + private void refreshActiveConnections(object sender, EventArgs e) + { + var previouslyOpenedConnections = Runtime.ConnectionTreeModel.GetRecursiveChildList().Where(item => item.OpenConnections.Count > 0); + + processHandlers.Clear(); + foreach (ConnectionInfo connection in previouslyOpenedConnections) + { + foreach (ProtocolBase _base in connection.OpenConnections) + { + if (_base.GetType().IsSubclassOf(typeof(PuttyBase))) + { + processHandlers.Add((PuttyBase)_base); + } + } + } + } + + private void processKeyPress(object sender, KeyEventArgs e) + { + TextBox txtMultiSSH = sender as TextBox; + if (txtMultiSSH == null) return; + + if (processHandlers.Count == 0) + { + e.SuppressKeyPress = true; + return; + } + + if (e.KeyCode == Keys.Up || e.KeyCode == Keys.Down) + { + e.SuppressKeyPress = true; + if (e.KeyCode == Keys.Up && previousCommandIndex - 1 >= 0) + { + previousCommandIndex -= 1; + } + + if (e.KeyCode == Keys.Down && previousCommandIndex + 1 < previousCommands.Count) + { + previousCommandIndex += 1; + } + + txtMultiSSH.Text = previousCommands[previousCommandIndex].ToString(); + txtMultiSSH.Select(txtMultiSSH.TextLength, 0); + } + + if (e.Control == true && e.KeyCode != Keys.V && e.Alt == false) + { + SendAllKeystrokes(NativeMethods.WM_KEYDOWN, e.KeyValue); + } + + if (e.KeyCode == Keys.Enter) + { + string strLine = txtMultiSSH.Text; + foreach (char chr1 in strLine) + { + SendAllKeystrokes(NativeMethods.WM_CHAR, Convert.ToByte(chr1)); + } + SendAllKeystrokes(NativeMethods.WM_KEYDOWN, 13); // Enter = char13 + } + } + + private void processKeyRelease(object sender, KeyEventArgs e) + { + TextBox txtMultiSSH = sender as TextBox; + if (txtMultiSSH == null) return; + + if (e.KeyCode == Keys.Enter) + { + if (txtMultiSSH.Text.Trim() != "") + { + previousCommands.Add(txtMultiSSH.Text.Trim()); + } + if (previousCommands.Count >= CommandHistoryLength) + { + previousCommands.RemoveAt(0); + } + + previousCommandIndex = previousCommands.Count - 1; + txtMultiSSH.Clear(); + } + } +#endregion + } +} diff --git a/mRemoteV1/UI/Forms/frmMain.Designer.cs b/mRemoteV1/UI/Forms/frmMain.Designer.cs index 7d8b6ca86..6f05da256 100644 --- a/mRemoteV1/UI/Forms/frmMain.Designer.cs +++ b/mRemoteV1/UI/Forms/frmMain.Designer.cs @@ -808,9 +808,6 @@ namespace mRemoteNG.UI.Forms this.txtMultiSSH.Name = "txtMultiSSH"; this.txtMultiSSH.Size = new System.Drawing.Size(300, 25); this.txtMultiSSH.ToolTipText = "Press ENTER to send. Ctrl+C is sent immediately."; - this.txtMultiSSH.Enter += new System.EventHandler(this.txtMultiSSH_Enter); - this.txtMultiSSH.KeyDown += new System.Windows.Forms.KeyEventHandler(this.txtMultiSSH_KeyDown); - this.txtMultiSSH.KeyUp += new System.Windows.Forms.KeyEventHandler(this.txtMultiSSH_KeyUp); // // tmrAutoSave // diff --git a/mRemoteV1/UI/Forms/frmMain.cs b/mRemoteV1/UI/Forms/frmMain.cs index 9b085fc40..25f34aa80 100644 --- a/mRemoteV1/UI/Forms/frmMain.cs +++ b/mRemoteV1/UI/Forms/frmMain.cs @@ -45,6 +45,7 @@ namespace mRemoteNG.UI.Forms private SystemMenu _systemMenu; private ConnectionTreeWindow ConnectionTreeWindow { get; set; } private readonly IConnectionInitiator _connectionInitiator = new ConnectionInitiator(); + private MultiSSHController _multiSSHController ; private frmMain() { @@ -52,7 +53,8 @@ namespace mRemoteNG.UI.Forms InitializeComponent(); _fullscreen = new Fullscreen(this); pnlDock.Theme = new VS2012LightTheme(); - } + _multiSSHController = new MultiSSHController(txtMultiSSH); + } static frmMain() { @@ -977,106 +979,6 @@ namespace mRemoteNG.UI.Forms } #endregion - #region Multi SSH - private ArrayList processHandlers = new ArrayList(); - private ArrayList previousCommands = new ArrayList(); - private int previousCommandIndex = 0; - - private void txtMultiSSH_Enter(object sender, EventArgs e) - { - var previouslyOpenedConnections = Runtime.ConnectionTreeModel.GetRecursiveChildList().Where(item => item.OpenConnections.Count > 0); - - processHandlers.Clear(); - foreach (ConnectionInfo connection in previouslyOpenedConnections) - { - foreach (ProtocolBase _base in connection.OpenConnections) - { - if (_base.GetType().IsSubclassOf(typeof(PuttyBase))) - { - processHandlers.Add((PuttyBase)_base); - } - } - } - } - - private void txtMultiSSH_KeyDown(object sender, KeyEventArgs e) - { - if (processHandlers.Count == 0) - { - e.SuppressKeyPress = true; - return; - } - - if (e.KeyCode == Keys.Up || e.KeyCode == Keys.Down) - { - e.SuppressKeyPress = true; - if (e.KeyCode == Keys.Up && previousCommandIndex - 1 >= 0) - { - previousCommandIndex -= 1; - } - - if (e.KeyCode == Keys.Down && previousCommandIndex + 1 < previousCommands.Count) - { - previousCommandIndex += 1; - } - - txtMultiSSH.Text = previousCommands[previousCommandIndex].ToString(); - txtMultiSSH.Select(txtMultiSSH.TextLength, 0); - } - - if (e.Control == true && e.KeyCode != Keys.V && e.Alt == false) - { - sendAllKey(NativeMethods.WM_KEYDOWN, e.KeyValue); - } - - if (e.KeyCode == Keys.Enter) - { - string strLine = txtMultiSSH.Text; - foreach (char chr1 in strLine) - { - sendAllKey(NativeMethods.WM_CHAR, Convert.ToByte(chr1)); - } - sendAllKey(NativeMethods.WM_KEYDOWN, 13); // Enter = char13 - } - } - - private void saveLastCommand() - { - if (txtMultiSSH.Text.Trim() != "") - { - previousCommands.Add(txtMultiSSH.Text.Trim()); - } - if (previousCommands.Count >= 100) - { - // Don't keep too many. TODO: make this configurable - previousCommands.RemoveAt(0); - } - - previousCommandIndex = previousCommands.Count - 1; - txtMultiSSH.Clear(); - } - - private void sendAllKey(int keyType, int keyData) - { - if (processHandlers.Count == 0) - { - return; - } - foreach (PuttyBase proc in processHandlers) - { - NativeMethods.PostMessage(proc.PuttyHandle, keyType, new IntPtr(keyData), new IntPtr(0)); - } - } - - private void txtMultiSSH_KeyUp(object sender, KeyEventArgs e) - { - if (e.KeyCode == Keys.Enter) - { - saveLastCommand(); - } - } - #endregion - #region Info private void mMenInfoHelp_Click(object sender, EventArgs e) { diff --git a/mRemoteV1/mRemoteV1.csproj b/mRemoteV1/mRemoteV1.csproj index 22f9436f9..895bc606d 100644 --- a/mRemoteV1/mRemoteV1.csproj +++ b/mRemoteV1/mRemoteV1.csproj @@ -220,6 +220,7 @@ +