Convertendo uma ComboBox em uma AutoCompleteBox usando o WPF Toolkit
Estou tendo um pouco de dificuldade para conseguir a conversão de um ComboBox "complexo" em um AutoCompleteBox igualmente complexo. Meu objetivo é poder selecionar e definir um item do ShoppingCart para ser como um dos itens de uma lista. Aqui estão as três etapas a serem seguidas para reproduzir minha situação (estou usando o Stylet e seu método SetAndNotify () INPC) :
Crie dois objetos, um tendo apenas uma propriedade Name e o outro tendo apenas o outro objeto como propriedade
public class ItemModel : PropertyChangedBase { private string _name; public string Name { get => _name; set => SetAndNotify(ref _name, value); } } public class ShoppingCartModel : PropertyChangedBase { public ItemModel Item { get; set; } }
inicializar e preencher o ItemsList e o Shoppingcart no DataContext (já que estamos usando MVVM, é o ViewModel)
public ShoppingCartModel ShoppingCart { get; set; } public ObservableCollection<ItemModel> ItemsList { get; set; } public ShellViewModel() { ItemsList = new ObservableCollection<ItemModel>() { new ItemModel { Name = "T-shirt"}, new ItemModel { Name = "Jean"}, new ItemModel { Name = "Boots"}, new ItemModel { Name = "Hat"}, new ItemModel { Name = "Jacket"}, }; ShoppingCart = new ShoppingCartModel() { Item = new ItemModel() }; }
Crie a AutoCompleteBox, ComboBox e um pequeno TextBlock dentro da View para testar tudo:
<Window [...] xmlns:toolkit="clr-namespace:System.Windows.Controls;assembly=DotNetProjects.Input.Toolkit"> <!-- Required Template to show the names of the Items in the ItemsList --> <Window.Resources> <DataTemplate x:Key="AutoCompleteBoxItemTemplate"> <StackPanel Orientation="Horizontal" HorizontalAlignment="Center" Background="Transparent"> <Label Content="{Binding Name}"/> </StackPanel> </DataTemplate> </Window.Resources> <StackPanel> <!-- AutoCompleteBox: can see the items list but selecting doesn't change ShoppingCart.Item.Name --> <Label Content="AutoCompleteBox with ShoppingCart.Item.Name as SelectedItem:"/> <toolkit:AutoCompleteBox ItemsSource="{Binding ItemsList}" ValueMemberPath="Name" SelectedItem="{Binding Path=ShoppingCart.Item.Name}" ItemTemplate="{StaticResource AutoCompleteBoxItemTemplate}"/> <!-- ComboBox: can see the items list and selecting changes ShoppingCart.Item.Name value --> <Label Content="ComboBox with ShoppingCart.Item.Name as SelectedValue:"/> <ComboBox ItemsSource="{Binding ItemsList}" DisplayMemberPath="Name" SelectedValue="{Binding Path=ShoppingCart.Item.Name}" SelectedValuePath="Name" SelectedIndex="{Binding Path=ShoppingCart.Item}" /> <!-- TextBox: Typing "Jean" or "Jacket" updates the ComboBox, but not the AutoCompleteBox --> <Label Content="Value of ShoppingCart.Item.Name:"/> <TextBox Text="{Binding Path=ShoppingCart.Item.Name}"/> </StackPanel> </window>
Alterar o modo de vinculação do SelectedItem do AutoCompleteBox para TwoWay faz com que ele imprima " [ProjectName] .ItemModel ", o que significa (eu acho?) Que está obtendo ItemModels e não strings, mas não consigo fazer funcionar. Qualquer ajuda será apreciada, obrigado e fique à vontade para editar meu post se for possível torná-lo menor.
Respostas
Depois de muitas tentativas, finalmente encontrei os culpados:
INPC não implementado
ShoppingCartModel.Item
apesar daPropertyChangedBase
herança (implementando INPC ou removendo oPropertyChangedBase
trabalho de herança)public class ShoppingCartModel : PropertyChangedBase { private ItemModel _item; public ItemModel Item { get => _item; set => SetAndNotify(ref _item, value); } }
Os AutoCompleteBox's
SelectedItem
devem ser do mesmo tipoItemsSource
e ter umTwoWay
ModeBinding
<toolkit:AutoCompleteBox ItemsSource="{Binding ItemsList}" ValueMemberPath="Name" SelectedItem="{Binding Path=ShoppingCart.Item, Mode=TwoWay}" ItemTemplate="{StaticResource AutoCompleteBoxItemTemplate}"/>
E finalmente ... o mais misterioso é o ComboBox! Simplesmente por estar lá mexe com o
AutoCompleteBox
e não tenho ideia do porquê, só comentar o ComboBox inteiro faz com que tudo funcione. Se você sabe por que o ComboBox quebra a ligação do AutoCompleteBox, fique à vontade para ajudar.
Há outro problema, porém, ao usar um AutoCompleteBox dentro de um ListView, mas é melhor criar uma pergunta separada para esse problema aqui