Conditional prevention of the textbox change - c#

I have a TextBox, and a TextBlock within the Border. The TextBlock's Text property is bound to TextBox's value. When I type into the TextBox, the Border changes its width according to the TextBlock's new size.
There is an event handler for TextBox.TextChanged in which I test whether the size of the border exceeds a certain number. If it does, I want to prevent the TextBox from making the change that caused the handler.
If a character was always added to an end, I would be able just to substring the text, but all other sorts of changing can occur, for example pasting a large amount of text into the TextBox.
So, what would be the way of preventing the change from the handler? I remember in some WindowsForms e.Cancel property which when set would ignore the action, but haven't seen that in WPF and the TextChangedEventArgs obviously does not have one.
Thanks

You can listen to the PreviewTextInput event and set e.Handled to true to prevent the change from taking effect.

Related

How to find WPF TextBox's changed text?

Suppose we inherit from WPF TextBox and then try to get text changes through overriding OnTextChanged.
Then we would notice when changes occurred, but the only information that we would have is:
Offset that this change occurred
Removed Length
Added Length
Can we get the accurate added text by using,
Text.Substring(Change.Offset, Change.AddedLength)
in OnTextChanged?
Text Change occurs in different conditions (such as user input, pasting text, or setting Text property in-code). Is there any possibility of conflicting changes coming into e.Changes?
Is this approach a trust way? If answer is No, Is there any other standard way(s) to get accurate changed text?
For a TextBox, this event occurs when its text changes; for a RichTextBox, this event occurs when any content or formatting changes (for example, images, table, or background color).
Can we get the accurate added text by using ... ?
Yes, you will always get accurate text in case of TextBox. You can make use of e.UndoAction to check for addition/deletion of text.
Read documentation here.
Is there any possibility of conflicting changes coming into e.Changes?
There won't be conflicting changes.
In general, the following will always be true:
The changes that occur result in the document being in a valid state.
The collection is ordered consecutively, related to where the change occurred in the control. For example, a TextChange object
that represents a change at position 2 is before a TextChange
object that represents a change at position 10.
Two TextChange objects do not represent an overlapping area. The value of Offset plus the value of AddedLength of one TextChange
object is always less than or equal to the value of Offset of the
next TextChange object in the collection. Likewise, the value of
Offset plus the value of RemovedLength of one TextChange object is
always less than or equal to the value of Offset of the next
TextChange object in the collection.
The collection reflects whatever changes occurred, even if there seems to be no net change. In the preceding example, neither the
first or fourth change results in a net change, because each simply
removed and re-added the and symbols, respectively. But
the symbols were actually removed and added, so they are included in
the collection.
More can be read here.
I made a short test program with one TextBox and one Label and I could not find the problems you describe. If I implement an TextChanged event for the TextBox like the following it works even if I paste something.The checking for null is needed because if the Textbox has an initial value the Initilialize method will trigger the change event before the label is created.
private void TextBox_TextChanged(object sender, TextChangedEventArgs e)
{
TextBox tbSource = (sender as TextBox);
if (lblOutput == null)
return;
lblOutput.Content = tbSource.Text;
}

WPF TextBox focus "sticking" after disabling and enabling

I have a TextBox in a Grid that has InputBindings such that when I hit return, a search is performed in a background thread.
The IsEnabled property of the TextBox is bound to a bool property in my ViewModel called IsSearching, which is true while the background thread is running (I use a converter to negate the value).
I type in TextBox and hit enter, starting the search and disabling the TextBox. When the background thread completes, the TextBox is enabled, however the focus is messed up:
The caret is still inside the TextBox however it does not blink, and I am unable to type. I believe the TextBox has focus, but not "KeyboardFocus".
Can anyone tell me how to resolve this?
Look at that answer:
TextBox Cursor is NOT blinking
Like you said maybe you must set the focus to the keyboard

In Winforms, why is validation not being fired after leaving TextBox and entering a DataGridView?

I'm overriding the OnValidating event in a custom Winforms text box. I'm finding that if the text box (which is bound to an object) has focus and then I give a grid focus using the mouse, the OnValidating event doesn't always get fired. When I first give the grid focus, it gets fired fine. But, if put one of the grid's cell in edit (blinking cursor), from there on out it seems to not get fired when I go back between the text box and grid using the mouse. If I change focus using the tab key, the validating always gets fired. If I give focus to a non-grid control using the mouse, the validation is always getting fired.
I tried to recreate this functionality from scratch in a simple form and I can't recreate the problem. The grid I'm using in the setup where I'm getting the problem is a custom DataGridView with custom column types. I'm wondering if the grid is the problem. But, I don't see how it could affect the text box events. Any ideas?
It probably has to do with the CausesValidation property.
A control's validation is suppressed if focus is going to a control that has CausesValidation set to false. It's just a wild guess, but I'm thinking some control inside the grid has CausesValidation = false;
This property is meant for things like "Cancel" buttons, but can cause lots of confusion.

Is TextBox behavior correct

Why TextBox is using e.Handled = true in order to prevent specific characters from being typed.
Don't we have a better way?
Isn't this a wrong design?
Currently I want to not receive KeyDown event if specific TextBox is in focus is there a good way to do this?Or I'll have to check is the OriginalSource the TextBox I want...
Edit:
As It seems that my original question is a bit confusing Let me reform it.
Lets suppose we have a Canvas and textbox as a child of canvas.
I registered for keyDown event of canvas to do something very interesting there.
I don't want to receive keydown events when user is typing in textBox though.
Is there a way to do this without involving e.OriginalSource?
If you want to prevent any input you can (in fact, should) also set ReadOnly = true instead of listening to the KeyDown event.
If you want to selectively prevent key strokes, listening to KeyDown and setting e.Handled is the only way.
However, selectively preventing keystrokes is bad for usability; don’t do it. Instead, use the Validating event of the text box control to validate the user input.

Read-only textbox in C#

In C#, I am creating a form window for a LAN messenger with two textboxes. I need to create a particular textbox as read-only, but any text submitted to it is appearing grey which is not desirable. Is there any way that can be prevented?
I would use a Textbox and set ReadOnly to true, ForeColor to Color.Black, and BackColor to Color.White. This way you can still select the text and copy it with Ctrl-C.
You could replace it with a label or on the text box in the KeyPress event, set handled to true:
void textBox1_KeyPress(object sender, KeyPressEventArgs e)
{
e.Handled = true;
}
You can set the colour of the text by setting the Textbox ForeColor property.
For example:
myTextBox.ForeColor = Color.Black
In order to keep the textbox white (or Window) when it's read-only, you must explicitly set the BackColor property to Window. To do this, you must first set the BackColor to some other value, then back to Window. The backcolor property should become bold indicating it is no longer the default value.
The grey color is indicative of the ReadOnly state of the textbox. It is a visual indication to the user who will not need to enter text to discover that the textbox is in fact, disabled.
If you need only the readonly behaviour, you would be better off using a Label instead.

Categories

Resources