私はあなたが望むものを達成するためのコンバータを使用することをお勧め。
が
あなたのユーザーコントロールのXAMLは、次のようになります。
<UserControl x:Class="MyDateControl"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:my="clr-namespace:MyDateControl"
x:Name="root">
<UserControl.Resources>
<my:DatePartConverter x:Key="DatePartConverter"
Date="{Binding ElementName=root, Path=Date}"/>
</UserControl.Resources>
<StackPanel>
<StackPanel Orientation="Horizontal">
<TextBox Name="textbox_year" Text="{Binding ElementName=root, Path=Date, Converter={StaticResource DatePartConverter}, ConverterParameter=year, Mode=TwoWay}"/>
<TextBox Name="textbox_month" Text="{Binding ElementName=root, Path=Date, Converter={StaticResource DatePartConverter}, ConverterParameter=month, Mode=TwoWay}" />
<TextBox Name="textbox_day" Text="{Binding ElementName=root, Path=Date, Converter={StaticResource DatePartConverter}, ConverterParameter=day, Mode=TwoWay}" />
</StackPanel>
</StackPanel>
</UserControl>
をでコードビハインドあなただけがあります、あなたは、依存関係プロパティ:
public DateTime Date {
get { return (DateTime)GetValue(DateProperty); }
set { SetValue(DateProperty, value); }
}
public static readonly DependencyProperty DateProperty =
DependencyProperty.Register("Date", typeof(DateTime), typeof(MyDateControl),
new FrameworkPropertyMetadata(DateTime.Now, FrameworkPropertyMetadataOptions.BindsTwoWayByDefault));
、コンバータは、このようなものになります。
を
public class DatePartConverter : Freezable, IValueConverter
{
public DateTime Date {
get { return (DateTime)GetValue(DateProperty); }
set { SetValue(DateProperty, value); }
}
public static readonly DependencyProperty DateProperty =
DependencyProperty.Register("Date", typeof(DateTime), typeof(DatePartConverter), new UIPropertyMetadata(DateTime.Now));
public object Convert(object value, Type targetType, object parameter, CultureInfo culture) {
DateTime date = (DateTime)value;
string datePartType = (string)parameter;
string result;
switch (datePartType) {
case "year":
result = date.Year.ToString().PadLeft(4, '0');
break;
case "month":
result = date.Month.ToString().PadLeft(2, '0');
break;
case "day":
result = date.Day.ToString().PadLeft(2, '0');
break;
default:
throw new InvalidOperationException("Unknown date part type (ConverterParameter)");
}
return result;
}
public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture) {
string datePartValue = (string)value;
string datePartType = (string)parameter;
DateTime result;
switch (datePartType) {
case "year":
result = new DateTime(int.Parse(datePartValue), Date.Month, Date.Day);
break;
case "month":
result = new DateTime(Date.Year, int.Parse(datePartValue), Date.Day);
break;
case "day":
result = new DateTime(Date.Year, Date.Month, int.Parse(datePartValue));
break;
default:
throw new InvalidOperationException("Unknown date part type (ConverterParameter)");
}
return result;
}
protected override Freezable CreateInstanceCore() {
return new DatePartConverter();
}
}
私はそうは思わない、コンバータを使用すると、もっと多くの仕事のように見える - 私はそれが3つの余分なバインディングを作成する必要があるとは思っていない。バインディングを指定すると、時間の90%が日付を作ることに失敗します - 私の答えを参照してください。 – markmnl
これらのバインディングは "余分な"ものではありません。あなたのコードでは、これらのバインディングをコード内で手作業で行っています。私のケースでは、すべての変換ロジックは、メインのユーザーコントロールロジックを単純にしてコンバータにカプセル化されています。そして、これらのバインディングは、コンバータに適切な変換ロジックを置く限り、失敗しません。 –
主なユーザーコントロールロジックは、私が思うようなバインディングなしで簡単です。バインディングは、キーが押されるたびにコンバータを不必要に実行します。どんなことでも、探しているものではありません。 – markmnl