Подтвердить что ты не робот

Каким должен быть параметр преобразователя для этой привязки

Я пытаюсь реализовать пользовательский элемент управления wpf, который связывает текстовое поле с списком удвоений с использованием конвертера. Как я могу настроить экземпляр пользовательского элемента управления как параметр преобразователя?

код для управления показан ниже

Спасибо

<UserControl x:Class="BaySizeControl.BaySizeTextBox"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"  
    xmlns:local="clr-namespace:BaySizeControl"
    >
    <UserControl.Resources>
        <local:BayListtoStringConverter x:Key="BaySizeConverter"/>
    </UserControl.Resources>
    <Grid>

        <TextBox  Name="Textbox_baysizes" 
                  Text="{Binding RelativeSource={RelativeSource self},
                                Path=Parent.Parent.BaySizeItemsSource, 
                                Converter={StaticResource BaySizeConverter}}"
                  />
    </Grid>
</UserControl>
4b9b3361

Ответ 1

Параметры для констант, необходимых вашему конвертеру. Чтобы предоставить экземпляр объекта вашему конвертеру, вы можете использовать MultiBinding.

Примечание. Чтобы это решение работало, вам также необходимо изменить свой конвертер для реализации IMultiValueConverter вместо IValueConverter. К счастью, внесенных изменений довольно мало. Вы можете добавить подтверждение для количества значений, предоставленных вашему конвертеру, 2 в вашем случае.

<TextBox Name="Textbox_baysizes">
    <TextBox.Text>
        <MultiBinding Converter="{StaticResource BaySizeConverter}">
            <Binding RelativeSource="{RelativeSource self}" Path="Parent.Parent.BaySizeItemsSource"/>
            <Binding ElementName="Textbox_baysizes"/>
        </MultiBinding>
    </TextBox.Text>
</TextBox>

Ответ 2

Другим способом является преобразование вашего конвертера из DependencyObject (или FrameworkElement). Это позволяет объявлять свойства зависимостей, позволяя устанавливать его значения из XAML, даже привязки.

Пример. Преобразователь для умножения значения, определяющего коэффициент, который получается из свойства (FactorValue) в пользовательском элементе управления (MyControl).

Конвертер:

public class MyConverter : DependencyObject, IValueConverter
{
    // The property used as a parameter
    public double Factor
    {
        get { return (double) GetValue(FactorProperty); }
        set { SetValue(FactorProperty, value); }
    }

    // The dependency property to allow the property to be used from XAML.
    public static readonly DependencyProperty FactorProperty =
        DependencyProperty.Register(
        "Factor",
        typeof(double),
        typeof(MyConverter),
        new PropertyMetadata(1.15d));

    #region IValueConverter Members

    object IValueConverter.Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
    {
        // Use the property in the Convert method instead of "parameter"
        return (double) value * Factor;
    }

    object IValueConverter.ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
    {
        throw new NotImplementedException();
    }

    #endregion
}

Использование в XAML:

<MyConverter x:Key="MyConv"
             Factor={Binding ElementName=MyControl, Path=FactorValue}
/>

Итак, теперь вы можете объявить свойство зависимостей для каждого параметра, который вам нужен в конвертере, и связать его.

Ответ 3

Я бы назвал элемент управления, а затем связал его с помощью ElementName:

<UserControl x:Class="BaySizeControl.BaySizeTextBox"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"  
    xmlns:local="clr-namespace:BaySizeControl"
    Name="Foobar"
    >
    <UserControl.Resources>
        <local:BayListtoStringConverter x:Key="BaySizeConverter"/>
    </UserControl.Resources>
    <Grid>

        <TextBox  Name="Textbox_baysizes" 
                  Text="{Binding RelativeSource={RelativeSource self},
                                Path=Parent.Parent.BaySizeItemsSource, 
                                Converter={StaticResource BaySizeConverter,
                                ConverterParameter={Binding ElementName=Foobar} }}"
                  />
    </Grid>
</UserControl>

Нет, подождите, это не сработает, потому что ConverterParameter не является свойством зависимостей и не привязывает объект DependencyObject. Расширение разметки ReleaseativeSource должно делать то, что вы хотите, хотя я не использовал его вложенным внутри другого MarkupExtension - возможно, он не очень хорошо себя ведет в этом случае:

<TextBox  Name="Textbox_baysizes" 
                      Text="{Binding RelativeSource={RelativeSource self},
                                    Path=Parent.Parent.BaySizeItemsSource, 
                                    Converter={StaticResource BaySizeConverter,
                                    ConverterParameter={RelativeSource self} }}"
                      />

Ответ 4

У меня была такая же проблема, но я не могу использовать MultiBindings, так как мне нужно правильно реализовать метод ConvertBack. Вот решение, которое я закончил реализовать для свойства CheckBox IsChecked:

<CheckBox>
    <CheckBox.IsChecked>
        <Binding Converter="{StaticResource myConverter}" Path="Value">
            <Binding.ConverterParameter>
                <FrameworkElement DataContext="{TemplateBinding DataContext}" />
            </Binding.ConverterParameter>
        </Binding>
    </CheckBox.IsChecked>
</CheckBox>

Я не очень хорошо знаком с TemplateBindings (или что-то вроде WPF в этом отношении), так что, возможно, это работает только потому, что мой CheckBox находится в DataTemplate...