我的页面上有一个ListBox,其中包含一些项目的名称。 ListBox右侧是一个显示所选项目信息的区域。
当用户单击“添加项目”按钮时,将使用自动生成的名称创建新项目,例如“新项目”。我希望能够立即将项目添加到ListBox后,关注TextBox并选择所有选定的文本,这样如果他们开始输入它会立即替换自动生成的文本。
以下是对它的外观的概念:
我创建了一个附加到ListBox的行为,它在创建新项目时给出了TextBox焦点。但是,我在尝试选择文本时遇到问题。在我的行为执行时,新名称尚未绑定。因此,例如,如果我选择了“第三项”,然后单击“添加项目”按钮,当行为执行时,文本框的文本仍然是“第三项”,我选择了所有这些,但随后TextBox更新的绑定并将其更改为“新项目”,并且不再选择该文本。
这是我的行为:
public class ListBoxFocusAnotherControlOnAddBehavior : Behavior<ListBox>
{
public static readonly DependencyProperty AttachedTextBoxProperty = DependencyProperty.Register("AttachedTextBox", typeof (TextBox),
typeof (ListBoxFocusAnotherControlOnAddBehavior), new PropertyMetadata(default(TextBox)));
public TextBox AttachedTextBox
{
get { return (TextBox)GetValue(AttachedTextBoxProperty); }
set { SetValue(AttachedTextBoxProperty, value); }
}
protected override void OnAttached()
{
((INotifyCollectionChanged)AssociatedObject.Items).CollectionChanged += onListBoxCollectionChanged;
}
private void onListBoxCollectionChanged(object sender, NotifyCollectionChangedEventArgs e)
{
if (e.Action == NotifyCollectionChangedAction.Add)
{
AttachedTextBox.Focus();
AttachedTextBox.SelectAll();
// The problem being that at the time of this SelectAll, the TextBox's Text binding hasn't updated yet.
}
}
}
相关XAML:
<ListBox Name="ThingsList" ItemsSource="{Binding Things}" SelectedItem="{Binding SelectedThing}">
<i:Interaction.Behaviors>
<behaviors:ListBoxFocusAnotherControlOnAddBehavior AttachedTextBox="{Binding ElementName=ThingNameTextBox}" />
</i:Interaction.Behaviors>
<ListBox.ItemTemplate>
<DataTemplate DataType="{x:Type ThingViewModel}">
<TextBlock Text="{Binding Path=Name, UpdateSourceTrigger=PropertyChanged}" />
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>
<TextBox Name="ThingNameTextBox" Text="{Binding Path=SelectedThing.Name, UpdateSourceTrigger=PropertyChanged}" />
我能做些什么来获得我正在寻找的行为?
答案 0 :(得分:1)
我确实找到了一个可行的解决方案,涉及从处理程序订阅TextChanged事件,选择处理后的所有文本,然后删除事件,但这感觉非常糟糕,我喜欢某事这不是一个黑客攻击。
private void onListBoxCollectionChanged(object sender, NotifyCollectionChangedEventArgs e)
{
if (e.Action == NotifyCollectionChangedAction.Add)
{
AttachedTextBox.Focus();
AttachedTextBox.TextChanged += AttachedTextBox_TextChanged;
}
}
private void AttachedTextBox_TextChanged(object sender, TextChangedEventArgs e)
{
AttachedTextBox.SelectAll();
AttachedTextBox.TextChanged -= AttachedTextBox_TextChanged;
}