Passing Text value from TextChanged event

Jun 17, 2011 at 9:46 AM
Edited Jun 17, 2011 at 9:48 AM

I have a TextBox and I'm trying to bind a method to an action and pass in the Text from the TextChanged event. I tried

cal:Message.Attach="[Event TextChanged] = [Action SearchTextChanged($this)]"

and

cal:Message.Attach="[Event TextChanged] = [Action SearchTextChanged(MyTextBox.Text)]"

But I only get the value of the Text before the change. The only way I can get it to give me the changed value is to change my method to take in a TextBox, use TextBox.Text value in the method and change the action to this:

cal:Message.Attach="[Event TextChanged] = [Action SearchTextChanged($source)]"

Is there a way to pass the changed Text value to the method? What's the best way to achieve this?


Jun 17, 2011 at 12:18 PM

One way is to bind the Text property and attach a behavior that will update the binding on TextChanged event

xaml
		<TextBox x:Name="SearchText"
				 Text="{Binding MySearchText,Mode=TwoWay}">
			<i:Interaction.Behaviors>
				<Hello:UpdateSourceOnTextChangedBehavior />
			</i:Interaction.Behaviors>
		</TextBox>

viewmodel

        private string _mySearchText = string.Empty;
        public string MySearchText { get { return _mySearchText; } set { _mySearchText = value;NotifyOfPropertyChange(() => MySearchText); } }
        public void SearchText()
        {
            MessageBox.Show(MySearchText);
        }

behavior

    public class UpdateSourceOnTextChangedBehavior : Behavior<TextBox>
    {
        protected override void OnAttached()
        {
            base.OnAttached();
            AssociatedObject.TextChanged += OnTextChanged;
        }

        protected override void OnDetaching()
        {
            AssociatedObject.TextChanged -= OnTextChanged;
            base.OnDetaching();
        }

        private void OnTextChanged(object sender, TextChangedEventArgs args)
        {
            var textBox = (sender as TextBox);
            if (textBox != null)
            {
                BindingExpression binding = textBox.GetBindingExpression(TextBox.TextProperty);
                if (binding != null)
                    binding.UpdateSource();
            }
        }
    }

Coordinator
Jun 17, 2011 at 12:35 PM

Try adding this in your bootstrapper:

MessageBinder.SpecialValues["$text"] = context => {
    var textBox = (TextBox)context.Source;
    return textBox.Text;
};

Then, add this to your text box:

cal:Message.Attach="SearchTextChanged($text)"

 

Jun 17, 2011 at 2:24 PM

Nice to know these options. I actually just switched the event to KeyUp and it worked fine.

Jan 5, 2012 at 1:02 PM
EisenbergEffect wrote:

Try adding this in your bootstrapper:

MessageBinder.SpecialValues["$text"] = context => {
    var textBox = (TextBox)context.Source;
    return textBox.Text;
};

This all works really fine, but what if I additionally have a custom textbox control MyTextBox for which I will do the same as above? I.e. bind twice to MessageBinder.SpecialValues["$text"], in first case with TextBox and second case with MyTextBox?

 





 

Coordinator
Jan 5, 2012 at 3:07 PM

In this case, it's best to just use the KeyUp event. SpecialValues are really not the best solution...they are sort of a last resort because you can do just about anything with them.