WPF - set text to Window as TextBox - wpf

i would like catch text in WPF Window. For example, application window will focus and I am going to write without focus in some textbox. My application has input from barcode reader. I want users to be able read a barcode without click to some textbox - for faster work. It is possible? I tried event PreviewKeyDown but application catch only first char. My barcodes are in format #12000012546 and barcode reader emulate numeric keyboard (Shift + num) - for example instead of char # KeyEventArgs return only "System". This is my code:
static string text = string.Empty;
private void MainWindow_OnPreviewKeyDown(object sender, KeyEventArgs e)
{
text += e.Key.ToString();
if (text.Length == 12)
{
MessageBox.Show(text)
text = null;
}
}
Thanks for advice

If your Barcode reader is really doing key presses (Shift + number) to do your # character, then check this out. This was tested on an Spanish Keyboard, so the # character is on my 3 key (Key.D3)
private void Window_PreviewKeyDown(object sender, KeyEventArgs e)
{
var regex = new Regex("(#)|([0-9])");
var keystr = e.Key.ToString();
if ((Keyboard.Modifiers & ModifierKeys.Shift) == ModifierKeys.Shift)
{
if (regex.Match(keystr).Success)
if (e.Key == Key.D3) textBox1.Text += "#";
}
else if (regex.Match(keystr).Success)
textBox1.Text += keystr.Replace("D","");
}

Related

For Japanese Full Width Characters, WPF textbox interactivity behavior AttachedObject PreviewTextInput doesn't work

I have developed a WPF textbox which formats numbers as we keep typing numbers in textbox. This is using interactivity behavior. Now, It works fine with normal regular keyboard. But as we support globalization, textbox should support to Japanese characters(numbers) as well which are full width characters. So to test, when I select Japanese keyboard - Microsoft IME in (windows-controlpanel-region & langauage - keyboard and languages - change keyboards), and enter japanese numbers my interactivity behavior code (hookup) AssociatedObject_PreviewTextInput does not get called until I press 'Enter' Key which creates other issues for me. For regular keyboard, this function gets called as soon I type number.
Code looks as below
private void AssociatedObject_PreviewTextInput(object sender, TextCompositionEventArgs e)
{
TextBox tb = sender as TextBox;
// other stuff
}
protected override void OnAttached()
{
base.OnAttached();
AssociatedObject.PreviewTextInput += AssociatedObject_PreviewTextInput;
/// other stuff
}
Any help is appreciated. Thank you.
You can listen to PreviewKeyDown/PreviewKeyUp to get notified for each stroke.
Any you may want to take over input by manipulate TextBox's Text property directly, instead of waiting for the final input after pressing Enter.
AssociatedObject.PreviewKeyDown += AssociatedObject_PreviewKeyDown;
Here I just handle the case where user is using IME to input digits (0~9). I insert the digit at the caret. And by setting e.Handled = true;, IME will not input anything to the TextBox.
private void AssociatedObject_PreviewKeyDown(object sender, KeyEventArgs e)
{
if (e.ImeProcessedKey == Key.D0 ||
e.ImeProcessedKey == Key.D1 ||
e.ImeProcessedKey == Key.D2 ||
e.ImeProcessedKey == Key.D3 ||
e.ImeProcessedKey == Key.D4 ||
e.ImeProcessedKey == Key.D5 ||
e.ImeProcessedKey == Key.D6 ||
e.ImeProcessedKey == Key.D7 ||
e.ImeProcessedKey == Key.D8 ||
e.ImeProcessedKey == Key.D9 )
{
TextBox tb = sender as TextBox;
int index = tb.CaretIndex;
//stripe the leading 'D'
string d = e.ImeProcessedKey.ToString().Substring(1);
tb.Text = tb.Text.Insert(index, d);
tb.CaretIndex = index + 1; //I need to manually move the caret forward, since caret position was reset to 0.
e.Handled = true; //important, so IME does not input to the TextBox
}
}

how to use textChanged event when from barcode reader

I am using a Barcode reader to get bar code from products .
i get the code in a textfield . and i put textchanged event on that textbox .
but the problem is that when bar code puts it value ( for example if bar code is 5 digit ) then textchanged event is fired five times .
how to get ride of this thing ???
You should be able to program your Barcode reader to output a prefix character and a suffix character (one output before the scanned value and one afterwards). Let's say that you set it up to output an asterisk (*) before the scanned data value and output a carriage return (CR) afterwards. Attach a handler to the TextBox.PreviewTextInput Event and listen out for the asterisk character:
private void PreviewTextInput(object sender, TextCompositionEventArgs e)
{
if (e.Text == "*")
{
e.Handled = true;
// Data input has started
}
}
You can use this to pop up a message saying 'Scanning...', or anything else that you require. Next, attach a handler to the TextBox.KeyUp Event and listen out for the Enter key:
private void KeyUp(object sender, KeyEventArgs e)
{
if (e.Key == Key.Return)
{
string scannedValue = ScanTextBox.Text.Replace("*", string.Empty);
// Do something with scannedValue
}
}
Now the scannedValue variable should contain the scanned barcode value.

WPF TextBox AcceptsReturn = True

In WPF Application I have a textbox.
I set its AcceptsReturn Property to true.
So, I can enter data in multiple lines.
When user press enter in the textbox I want to check :
1) Is the cursor on the last line?
2) If cursor is on the last line then check if thatLine.Text = Nothing?
Something like this?
private void TextBoxOnTextChanged(object sender, TextChangedEventArgs e)
{
TextBox tb = sender as TextBox;
if (tb == null)
{
return;
}
string[] lines = tb.Text.Split(new[] { Environment.NewLine }, StringSplitOptions.None);
if (tb.CaretIndex >= tb.Text.Length - lines.Last().Length)
{
// cursor is on last line
if (string.IsNullOrEmpty(lines.Last()))
{
// cursor is on last line and line is empty
}
}
}
ok is in c# but i don't know the vb syntax..
if you need a translation to vb: http://www.developerfusion.com/tools/convert/csharp-to-vb/ ;-)

RichTextBox and Inserting at Caret Positions

Here is the deal: I have a RichTextBox control and it works fine. The problem is that there is a button "Insert Current DateTime" which adds/injects the current datetime into the RichTextBox. The user can enter the datetime anywhere where the caret is pointing. This involves complicated string manipulation and stuff.
Any ideas how to get the current caret position. Whenever I get RichTextBox.CaretPositon it seems it is pointing to the start of the RichTextBox and not where the actual caret is.
UPDATE 1:
The date time button click code:
private void DateTimeStampButton_Click(object sender, RoutedEventArgs e)
{
//TextRange tr = new TextRange(textBox.Selection.Start, textBox.Selection.End);
var tr = new TextRange(textBox.Document.ContentStart, textBox.Document.ContentEnd);
if(tr.Text.Length == 2)
{
if(tr.Text == "\r\n")
{
tr.Text = tr.Text.TrimStart(new[] { '\r', '\n' });
}
}
textBox.CaretPosition.InsertTextInRun(DateTime.Now.ToShortDateString() + " " + DateTime.Now.ToShortTimeString() + ": ");
DateTimeStampButton.Focusable = false;
}
private void SharpRichTextBox_LostFocus(object sender, RoutedEventArgs e)
{
SetValue(TextProperty, Text);
var binding = BindingOperations.GetBinding(this, TextProperty);
if (binding == null) return;
if (binding.UpdateSourceTrigger == UpdateSourceTrigger.Default || binding.UpdateSourceTrigger == UpdateSourceTrigger.LostFocus)
{
// if (TextProperty != null) BindingOperations.GetBindingExpression(this, TextProperty).UpdateSource();
}
}
public string Text
{
get
{
var newValue = new TextRange(Document.ContentStart, Document.ContentEnd).Text.RemoveNewLineAndReturn();
return newValue;
}
set
{
if (!String.IsNullOrEmpty(value))
{
SetValue(TextProperty, value.RemoveNewLineAndReturn());
Document.Blocks.Clear();
Document.Blocks.Add(new Paragraph(new Run(value)));
OnPropertyChanged("Text");
}
}
}
UPDATE 2:
Turned out the problem was with the DateTime button being Focusable. I turned it to be not focusable and it worked as expected. When focus was lost on the RichTextBox it was resetting the caret position. It happened only once since in the code the btn_DateTime was dynamically being set as Focusable = false. I placed Focusable = false in XAML and everything worked fine from the start.
I'm using this code to successfully do what you are attempting:
private void insertNowButton_Click(object sender, RoutedEventArgs e)
{
//NOTE: The caret position does not change.
richTextBox1.CaretPosition.InsertTextInRun(DateTime.Now.ToString());
}
EDIT: Addressing Update 1
private void DateTimeStampButton_Click(object sender, RoutedEventArgs e)
{
var tr = new TextRange(textBox.Document.ContentStart, textBox.Document.ContentEnd);
if (tr.Text.Length == 2)
{
if (tr.Text == "\r\n")
{
tr.Text = tr.Text.TrimStart(new[] { '\r', '\n' });
}
}
/* Changing the text is the only way I can get the date to insert at the beginning */
tr.Text = "I need a beer at ";
textBox.CaretPosition.InsertTextInRun(DateTime.Now.ToString());
}
It looks like SetValue is changing the text so based on my test that actually changing the text resets the caret, I would agree with you that SetValue is causing the problem...
I tried this solution with WPFToolkit.Extended RichTextBox and it didn't work for me.
However I found another one and thought it would be good to post it in here in case someone else could use it.
My problem was also that the after I clicked a button that is supposed to append text at the caret location, it instead adds it at the beginning of the RichTextBox.
So The solution I found is similar to the one in here -
RichTextBox CaretPosition physical location
Instead of using CaretPosition I used RichTextBox.Selection.Start.InsertTextInRun("SomeText").
It considered the selection's start as the caret position even though no selection was made and therefore was good enough for me.
I hope someone will find this useful :)
This worked for me:
private void InsertText(String text, RichTextBox rtb)
{
rtb.CaretPosition = rtb.CaretPosition.GetPositionAtOffset(0, LogicalDirection.Forward);
rtb.CaretPosition.InsertTextInRun(text);
}
I found the code here:
How do I move the caret a certain number of positions in a WPF RichTextBox?

Why doesn't the MaxLength property on a RichTextBox work in WPF?

I am trying to set the MaxLength property on a RichTextBox but it does not seem to work.
Any ideas what might be happening?
The fundamental problem is that the WPF RichTextBox doesn't have a MaxLength property - unlike the Windows.Forms one.
Here's an improvement on #jhony's anwser. If you catch the PreviewKeyDown event and check the length, you also need to allow the user to press Delete and BackSpace after hitting the limit.
// In constructor
this.RichTextBox.PreviewKeyDown += this.EditBox_KeyDown;
private void EditBox_KeyDown(object sender, KeyEventArgs e)
{
if (e.Key != Key.Delete && e.Key != Key.Back)
{
var range = new TextRange(this.RichTextBox.Document.ContentStart, this.RichTextBox.Document.ContentEnd);
if (range.Text.Length > this.MaxLength)
{
e.Handled = true;
return;
}
}
}
You should also allow the arrow keys, because you wouldn't expect them to be disabled.
To disable pasting, put this in the constructor DataObject.AddPastingHandler(this.RichTextBox, this.EditBox_Paste); and
private void EditBox_Paste(object sender, DataObjectPastingEventArgs e)
{
e.CancelCommand();
}
However, you might want to allow pasting unless it breaks the MaxLength, in which case you'll need to check the text being inserted, and the text it is replacing. At that point I decided not to implement a MaxLength in the control, but to handle it with the rest of the validation in the form.
Add this code in yout KeyDown Event.
private void rLetter_KeyDown(object sender, KeyEventArgs e)
{
TextRange tr= new TextRange(rLetter.Document.ContentStart, rLetter.Document.ContentEnd);
if (tr.Text.Length > 4000 || e.Key == Key.Space || e.Key == Key.Enter)
{
e.Handled = true;
return;
}
}
I have some problem, The bug is :
Test this code using copy and paste text max 4000.
Sorry for my English ..

Resources