TwoWayモードを使用して、ListView selectedItemをテキストボックスにバインドするにはどうすればよいですか?
-
13-10-2019 - |
質問
私はWPFを非常に初めてであり、取り組んでいるアプリケーションに含めたいものをいくつかテストしています。 Scott GuthrieとJon Skeetという名前の2行のListView(テキストボックスにバインドされています)があります。 ListViewで「Scott Guthrie」を選択して、テキストボックスに入力しようとしています。テキストとタブを編集して、ListViewを更新できるようにしたいと思います。
編集:それが本当に質問に何も追加しなかったので、コードを削除しました。
解決
うわー、それはあなたがそこに持っているものを本当に複雑です。
これは非常に簡単な方法で達成できます。プログラマーを表すモデル、プログラマーのリストを保持するビューモデル、および残りの世話をするための簡単なバインディングが必要です。
モデル:
public sealed class Programmer
{
public string Name { get; set; }
}
その非常にシンプルです。名前のプログラマーを表すオブジェクト。文字列は.NETで不変であるため、オブジェクト内の名前をカプセル化する必要があります。文字列のリストで単一の文字列にバインディングしようとした場合、変更は伝播しません。
プログラマーのコレクションはビューモデルに保持されます。この場合、想像力がないので、私はそれをviewmodelと呼びます。このビューモデルには、ビューが拘束するすべてのものが含まれています。この場合、プログラマーのリスト。
public sealed class ViewModel
{
public ObservableCollection<Programmer> Programmers { get; private set; }
public ViewModel()
{
Programmers = new ObservableCollection<Programmer>();
}
}
ViewModelは、ビューのデータコンテキストとして設定されています。 Datacontextは視覚ツリーを流れ、いつでも視覚ツリーにバインドできます。
public MainWindow()
{
var vm = new ViewModel();
vm.Programmers.Add(new Programmer { Name = "Jon Skeet" });
vm.Programmers.Add(new Programmer { Name = "Scott Guthrie" });
DataContext = vm;
InitializeComponent();
}
DataContextを必要な方法で設定できます。私はここでシンプルさのためにそれをやっています。
UIでは、ViewModelのプログラマーのリストに対してListViewを単純にバインドします(DataContextは、特に明記しない限り、バインディングパスのルートです)。次に、テキストボックスをリストボックスのselectedItemにバインドします。リストからプログラマーを選択し、それがselectedItemになり、その名前を変更できます。
<Window
x:Class="Programmers.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:t="clr-namespace:Programmers"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition />
<ColumnDefinition />
</Grid.ColumnDefinitions>
<ListBox
x:Name="list"
ItemsSource="{Binding Programmers}"
DisplayMemberPath="Name" />
<TextBox
Grid.Column="1"
VerticalAlignment="Top"
Text="{Binding SelectedItem.Name, ElementName=list}" />
</Grid>
</Window>
シンプル、一度それを手に入れたら。
他のヒント
これは機能します(テキストを入力できるため、テキストボックスを検証する必要があります。ドロップダウンがより良い選択かもしれません)。
意見:
<TabItem x:Name="RightTabPage" Header="RightModel" DataContext="{Binding Right}">
<StackPanel>
<TextBox Text="{Binding SelectedGuru}"/>
<ListView SelectedItem="{Binding SelectedGuru}" ItemsSource="{Binding Gurus}"/>
</StackPanel>
</TabItem>
ViewModel:
public class RightViewModel
{
public RightViewModel()
{
Gurus = new[] {"Scott Guthrie", "Jon Skeet"};
SelectedGuru = Gurus.First();
}
public string SelectedGuru { get; set; }
public IEnumerable<string> Gurus{ get; set; }
}