Why do Enter and Space keys behave differently for buttons? - c#

As far as I know, these are the only keys that react when a button has focus.
Pressing Enter instantly 'clicks' the button, even if you keep it the key down. (So the 'click' happens on KeyDown).
Pressing Space acts more like a normal mouse click; holding it down doesn't activate the Click event, but it does once you release it. (So the 'click' happens on KeyUp or KeyPressed.)
Why the difference? I'd like a good article on the subject or simply a logical explanation as to why those two keys have different behavior. Surely there's an explanation out there!

I can't find any articles explaining this and it's a really good question. I personally think that it's for functionality purposes
Enter Key the classic AcceptButton acts like a FullClick (Click/ClickReleased) that's why if you hold it you will have the effect of clicking multiple times.
Space however is a SingleClick (No click release until you release the key) so it can accomplish task where only a Click is required without a ClickRelease and actions where only the selection of a control is required to activate it. Like the CheckBox or RadioButtons which can't be activate with the Enter but can be activated with the Space like if you click on it.
In conclusion, the Space would be the official MouseClick since it has the same effects of a MouseClick uppon pressing or releasing. Enter would be sort of a shortcut for a One click full click. All, of course, in the idea of giving more possibilities to the keyboard itself.

You're seeing two different behaviors, which aren't associated except that they both deal with keyboard events on a winform.
Enter is special because it's the keypress to activate the acceptButton of a form. In fact, you missed another key that can affect buttons: Esc is the cancelButton, and will throw events as well.
As PhaDaPhunk explained, Space is a MouseClick for any component that accepts a MouseClick, but I haven't found a detailed explanation for it. I'd assume it's the default behavior of all controls. The Microsoft guide to accessibility seems to imply that is so in their section on keyboard-based navigation
Incidentally, this Microsoft support knowledge base entry seems to show that the spacebar implementation went from Button.Click to Button.MouseClick. Perhaps that's the reason for it's different behavior.

This functionality seems to have been removed in Big Sur. I came here looking for how I could get it back. It can be very efficient to click enter to proceed or spacebar usually to cancel, to pick the two primary options on most dialog buttons.

Related

Cannot read held state of key in WPF inside mouse event handler - Inconsistent behaviour in Windows guest on VMWare Fusion for Mac

This issue is caused by an inconsistent setting in vmware fusion - the secondary mouse function of MacOS (ie, right click) was being triggered by the control-left click, in spite of being configured in vmware fusion settings to send control through as a separate key.
I am leaving this here as it outlines the diagnostic steps taken to isolate the issue.
This behaviour might be present in other virtualisation solutions on MacOS.
This is not a duplicate - I have tried the approaches suggested - They Do Not Work. Genuine help is required please.
I am trying to implement a multiple select function in a WPF canvas, and need to be able to detect when either control key is held while clicking on an item.
I have already tried using the documented and accepted methods of getting the key (Keyboard.IsKeyDown and Keyboard.Modifiers) and although they are supposed to work, they do not in this case.
I cannot place a key handler in the main window of the application as this solution is implemented in a component, and as such, I do not have access to the main window.
I cannot create a keyboard OnKeyDown override, as it does not register the event. I do not know why this is, but suffice to say, I have tried all the methods I can find after an extensive search on Stack Overflow, and am currently out of ideas.
In the current logic, clicking an item in my canvas will clear any selected items already. If the control key is held, I will not clear selected items.
The structure of my application is as follows:
Main Window -> Dock Panel -> ScrollViewer -> Main Custom Component (extends Canvas) -> ChildCanvas objects (multiple instances, all also extend Canvas).
The component will not have any reference back to the main window - this is absolutely not negotiable.
The component must not require a reference to the main window to be passed in to it.
The component cannot rely on any logic, properties, methods or other functional code being placed in the MainWindow - it must be totally reusable.
Multiple instances of a custom object (ChildCanvas) which itself derives from Canvas are placed onto a base custom object (ExtendedCanvas) which also extends Canvas.
I am detecting the mouse click in a mouse event handler within my custom item.
Although I can in theory handle the key event and set a bool flag when the key goes down and clear it when the key goes up, this is not a reliable way to do things as it would require the focus to be on whichever component is handling the key.
All the examples I have looked at require a specific event handler for the key press, but I cannot apply that approach in this case as it simply does not seem to register the key press, even if the component where the event handler is implemented has focus at the time.
I would like to find a way to check if a key is held down in the mouse click handler if this is possible in WPF.
EDIT: I have tried using the Keyboard.Modifiers approach, but this returns no result.
EDIT: I have also tried Keyboard.IsKeyDown(Key.LeftCtrl), which does not return any values.
EDIT: I have tried to handle the key event globally by registering on the EventManager as shown. What I have found is that key up and key down events are triggered in quick succession. The first event has the property e.IsRepeat as false, and all subsequent event occurrences have e.IsRepeat set as true. Using these events, I have set a bool which is set to true in the first keyDown event is e.IsRepeat is false (the first initial key press), and set to false in the keyUp event if e.IsRepeat is false (the keyUp event fire when the key is physically released).
This does not work - clicking the item on the canvas when the key is held altered the state of the bool setting it to false.
This behaviour is totally inconsistent with what Microsoft document for the way the keyboard handling should work.
EventManager.RegisterClassHandler(typeof(Control),
Keyboard.KeyDownEvent,new KeyEventHandler(keyDown),true);
I can call Keyboard.IsKeyToggled(Key.LeftCtrl) which does show the toggled state, but it changes with every key press, and does not show me whether the key is held down at the time of the mouse click.
public class ExtendedCanvas:Canvas {
public ExtendedCanvas() {
MouseUp += thisMouseUp;
}
void thisMouseUp(object sender,MouseButtonEventArgs e) {
if ((Keyboard.Modifiers & ModifierKeys.Control) > 0) {
//This does not work - no key is registered, as for some reason, Keyboard.Modifiers does not register that the key is held.
}
//If CONTROL is held down
if (!ControlKeyHeldDown) {
ClearSelectedItems();
}
IsSelected = true;
}
}
The inconsistent behaviour is the result of a VMWare option.
This VM is being run on MacOS and in spite of VMWare Fusion being configured to send the Control key straight through, Control Click was still triggering the secondary mouse button (ie, right click in this case).
The solution is:
1) Shut down the VM.
2) In VMWare Fusion Preferences -> Keyboard And Mouse -> Mouse Shortcuts, ENABLE (Check) the "Secondary Button" option if it is not checked.
3) Close the preferences window to save the settings.
4) Close VMWare Fusion
5) Reboot the host system
6) In VMWare Fusion Preferences -> Keyboard And Mouse -> Mouse Shortcuts, DISABLE (UnCheck) the "Secondary Button" option.
7) Start the VM, and confirm that Control Click no longer triggers the secondary click.
This option had been configured to send Control straight through prior to upgrading VMWare Fusion from 8 to 10.
It appears that although the Secondary Function checkbox was unchecked, the property was set to true, and it was behaving inconsistently from the way the settings suggested it should.

limiting tabbing to a custom in-window message box

I have made a custom MessageBox for my application and it launches as a UserControl. I have two buttons inside it and I would like to allow users to press Tab to switch between Buttons. However, since it's a UserControl overlaying the content, Pressing tab more than twice makes the focus go in the background on elements that aren't supposed to be tabbed at.
I can't figure out a good idea how to prevent this, I've thought of making a method that will select all elements and make their IsTabStop values to false and then restore them later, but I think that would be more of a problem then a solution.
Is there a way around this to limit tabbing only to the UserControl?
I would also appreciate advice on working with the message box.. the whole messagebox is an async function that has an infinitive loop until the answer is given. Is there another way to stop the application until one of the message box options was selected?
Crowcoder's reference has lead to correct MSDN page where I found my solution:
dialog = new UCMessageBox("Are you sure you want to exit the application?", MBType.YesNo);
AppMessageBox.Children.Add(dialog);
KeyboardNavigation.SetTabNavigation(dialog, KeyboardNavigationMode.Cycle);
The key was to call .SetTabNavigation function and direct it to my dialog (custom UserControl for the message box) and setting the KeyboardNavigationMode to Cycle.
After closing the UC rest of the application continued normally regarding navigation.

Backspace not working for IE Toolbar

I am developing the Internet Explorer Toolbar in c#.net using the band objects.
Now in my toolbar, I am using the textbox field to make the search enable, but in this textbox field, I am not able to use the backspace, delete, arrow keys and many other such button.
I am not sure about y I am not able to use this. Please help me about this. I found many question posted over like this, but none of them was having the specific answer.
Thanks
The problem is that the browser is eating the events for those keystrokes, so the solution is to force focus to the toolbar when the text box receives focus.
To fix it add this line to your toolbar's constructor:
yourTextBox.GotFocus += (sender, args) => OnGotFocus(args);
Also make sure you have implemented TranslateAcceleratorIO() per this example.
Compare your code to this one and see what's missing.

How can I remove the input focus from textbox?

I'm making simple C# Winform application. There is a Form having a textbox. I want to change the location of textbox by arrow key but textbox has the input focus so form's KeyDown event is not called. How can I remove that input focus?
Typing on the textbox should still be possible. I try to make a dummy label and give the focus, but It doesn't work. If I press any key, the cursor go back to the textbox. please help me. How can I solve this problem?
Handle the TextBox.KeyDown event. And set e.Handled = true; in your handler after you move the TextBox, but before you return. And, yeah, only handle the arrow keys.
Hmm, not sure if I understand. If the user can type into the edit box, then it can have focus. If he clicks outside of it, on a blank are of the form, then it loses focus.
If you want to be able to 1) type into the edit box and 2) move the edit box, then you need a separate mechanism to enter "move mode".
I would suggest either a "click here to move selected control" button, or a right-click context menu on the control with a "move control option".
You would also have to conisder how the user indicates that moving has ended.
Hope this helps.
NOTE: I just realized this is not even an in-browser C# app. I guess disregard all of this. Serves me right for not reading carefully enough.
Use Javascript, in particular, I'd personally recommend jQuery.
They have pretty nicely documented their library: http://docs.jquery.com/Main_Page
For this particular task, you are going to want to bind some sort of key event (ie. keypress) and make sure to stop event propagation (so that you prevent the default response which is to be sent to be simply handled by the textbox element's default listener).
So, to give you an idea, if you want to change the location of the textbox using keypresses (maybe arrow keys), do something like this:
/* link the jQuery source to the HTML page with script tag */
<script src="jquery.js" type="text/javascript"></script>
<script type="text/javascript">
/* short hand for $(document).ready(function() { ... */
$(function() {
$("#textbox_id").keypress(function(e) {
var $this = $(this); // store the #textbox_id element in $this
e.preventDefault();
switch (e.keyCode) {
// find the actual integer code for the up arrow
case UP_ARROW:
$this.animate({
top : '-=10px'
}, 100); // time in milliseconds to complete the animation
/* fill in the cases */
}
}
});
Okay, I hope you get the picture. Find out more about animate() and other jQuery functions at in the documentation at the link I provided above. Hope that helps!
NOTE: Obviously, preventing the default handling of events is a terrible idea in this case for accessibility reasons. Use your best judgement when selecting keypresses to trigger these moving events -- whatever you do, don't disallow users from moving around within the text they have in input fields.

Is there a way to press or fireup the keys in key board using c# code?

I want the 'Alt' to be pressed by code. It is like firing key-press event with key 'Alt' by the code, not hitting it manually. The need is, I have set 'ShortCut keys for menu, but it (the single underline on key letter) is not visible to the user unless he presses 'alt'. So i need to make the Alt be pressed by default.
Is there a way to 'press' or 'fireup' the keys in key board using c# code?
Check out the System.Windows.Forms.SendKeys class.
You can use the static Send method to send keystrokes to the active window. If you're trying to send keystrokes to another window, you'll need to use the Windows API to activate the other window first.
If you have any control over the operating system on which the program is being deployed, apparently you can force the underlined shortcut letter to always be displayed by going to Control Panel -> Display -> Appearance -> Effects -> Hide underlined letters for keyboard navigation.
(http://www.chinhdo.com/20080902/underlined-letters-windows/)
here is a complete article on use of SendKeys on codeproject
Here is how you simulate input (both mouse and keyboard).
http://msdn.microsoft.com/en-us/library/ms171548.aspx
If you look at the System.Windows.Forms.SendKeys class you will see that it provides you with what you want.
http://msdn.microsoft.com/en-us/library/system.windows.forms.sendkeys.aspx

Categories

Resources