以下の単純化されたアプリケーションを考えてみましょう。このアプリケーションでは、2 つの要素から選択できます。各要素には、ラジオ ボタンにバインドされた A および B ブール プロパティがあります。アイデアは、要素ごとに独立して A/B を設定できる必要があり、要素を切り替えると、ラジオ ボタンはその要素のフラグを反映する必要があるということです。しかし、これは起こることではありません。
ビューモデル:
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
using System.Runtime.CompilerServices;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Documents;
namespace SandboxWpf
{
public sealed class Element : INotifyPropertyChanged
{
private bool _memberA;
public bool MemberA
{
get { return _memberA; }
set
{
if (value != _memberA)
{
_memberA = value;
OnPropertyChanged();
}
}
}
private bool _memberB;
public bool MemberB
{
get { return _memberB; }
set
{
if (value != _memberB)
{
_memberB = value;
OnPropertyChanged();
}
}
}
public event PropertyChangedEventHandler PropertyChanged;
private void OnPropertyChanged([CallerMemberName] string propertyName = null)
{
PropertyChangedEventHandler handler = PropertyChanged;
if (handler != null) handler(this, new PropertyChangedEventArgs(propertyName));
}
}
public sealed class MainViewModel : INotifyPropertyChanged
{
private readonly List<Element> _elements;
public MainViewModel()
{
_elements = new List<Element>();
_elements.Add(new Element());
_elements.Add(new Element());
}
public IEnumerable<Element> Elements
{
get { return _elements; }
}
private Element _selectedElement;
public Element SelectedElement
{
get { return _selectedElement; }
set
{
if (value != _selectedElement)
{
_selectedElement = value;
OnPropertyChanged();
}
}
}
public event PropertyChangedEventHandler PropertyChanged;
private void OnPropertyChanged([CallerMemberName] string propertyName = null)
{
PropertyChangedEventHandler handler = PropertyChanged;
if (handler != null) handler(this, new PropertyChangedEventArgs(propertyName));
}
}
}
ウィンドウ XAML (コード ビハインドなし):
<Window x:Class="SandboxWpf.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:SandboxWpf="clr-namespace:SandboxWpf"
Title="MainWindow" Height="350" Width="525">
<Window.DataContext>
<SandboxWpf:MainViewModel/>
</Window.DataContext>
<StackPanel Orientation="Horizontal">
<ListBox ItemsSource="{Binding Elements}"
SelectedItem="{Binding SelectedElement, Mode=TwoWay}" />
<ContentPresenter Content="{Binding SelectedElement}">
<ContentPresenter.Resources>
<DataTemplate DataType="{x:Type SandboxWpf:Element}">
<StackPanel Orientation="Horizontal">
<RadioButton Content="A" IsChecked="{Binding MemberA, Mode=TwoWay}"/>
<RadioButton Content="B" IsChecked="{Binding MemberB, Mode=TwoWay}"/>
</StackPanel>
</DataTemplate>
</ContentPresenter.Resources>
</ContentPresenter>
</StackPanel>
</Window>
各要素のラジオ ボタンを使用して、A 値と B 値を切り替えることができます。ただし、最初の要素と 2 番目の要素を異なる値 (1 つの A と 1 つの B) に設定してから、選択した他の要素に戻ると、他の要素では A と B の両方が false に設定されます。SelectedElement プロパティが ContentPresenter で変更され、TwoWay バインディングが何らかの形でトリガーされ、プロパティ値が上書きされると思われるときに、何かおかしなことが起こっていますが、なぜこれが起こるのか、またはそれを解決する方法がわかりません。これは、より大きなアプリケーションで見られるものを意図的に簡略化したものです。
ここで何が起こっているか分かりますか?