2016-01-16 2 views
2

Мой класс содержит свойство address (тип строки), но мое окно WPF содержит несколько текстовых полей для адреса (номер дома, название улицы и дополнительная вторая строка адреса - город и почтовый индекс имеют отдельные поля в классе) , Я хотел бы получить их все в одну строку address в классе, через запятую (например, «43, Уайтфилд-роуд, Принцесса»). Есть ли способ сделать это путем привязки или только вручную в коде?Есть ли способ привязать 2 (или более) элемента WPF к одному свойству в C#?

enter image description here

+2

Вам гораздо лучше, если ваша модель отражает то, как вам нужны эти ограничения. Вы можете использовать отдельный класс, который раскрывает каждый из них как свойства, тогда он может сделать перевод объединения свойств в одну строку. –

+0

Согласен. Вы можете использовать конвертер, как показано ниже, но это действительно то, что вы должны уметь тестировать без предварительного просмотра. Если вам приходится использовать конвертеры для реализации чего-либо, кроме самой основной логики, то обычно это хороший знак того, что модель, с которой вы связываетесь (например, модель представления в случае mvvm), не выполняет свою работу должным образом. –

ответ

1

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

public class AddressSeparatorConverter : IValueConverter 
{ 
    ///<summary> 
    /// Index of the substring element of the address to be manipulated (read/edited). 
    ///</summary> 
    public int SubStringIdx { get; set; } 

    ... 
} 

Тогда при выполнении преобразования, вы просто разделить строку, используя, разделитель и возвращает подстроку, как указано в SubStringIdx:

address.Split(',')[SubStringIdx] 

Поскольку вы привязываетесь к редактируемому элементу управления, вам необходимо убедиться, что вы предоставляете реализации как для методов IValueConverter.Convert, так и для IValueConverter.ConvertBack.

Для того, чтобы это еще один шаг вперед, вы можете предоставить различные определения преобразователя в вашем Converters.xaml файла обрабатывать различные подкомпоненты адреса:

<converters:AddressSeparatorConverter x:Key="AddressToHouseNumberConverter" SubStringIdx="0"/> 
<converters:AddressSeparatorConverter x:Key="AddressToStreetNameConverter" SubStringIdx="1"/> 
... 

Тогда при связывании с вашим контролем вы могли бы назвать соответствующий преобразователь ее ключом:

<TextBox Text="{Binding Address, Converter={StaticResource AddressToStreetNameConverter}}"/> 

у меня нет доступа к IDE прямо сейчас, так пожалуйста, примите фрагменты кода не может быть 100% правы, но вы должны получить суть.

+1

Чтобы быть честным, хотя я предложил решение иметь адрес как одно поле, так как это действительно сложное поле, было бы намного проще разделить его на отдельные свойства. –

0

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

Синтаксис адрес текстового поля текста связывания будет:

<TextBox Width="100" > 
     <TextBox.Text> 
      <MultiBinding Converter="{StaticResource YourAddressConverter}"> 
       //order below bindings as you want them in the array passed to converter 
       <Binding ElementName="Houseblock" Path="Text"/> 
       <Binding ElementName="streetblock" Path="Text"/> 
       ....................... 
       <Binding ElementName="townblock" Path="Text"/> 
      </MultiBinding> 
     </TextBox.Text> 
    </TextBox> 

, где использование elementbinding текст других текстовых полей является переплетены с finaltextbox (адрес) и YourAddressConverter является конвертер, который будет содержать логин конкатенации адресных компонентов, как показано ниже в его методе преобразования.

public class YourAddressConverter : IMultiValueConverter 
{ 

    public object Convert(object[] values, Type targetType, object parameter, System.Globalization.CultureInfo culture) 
    { 
     return values[0].ToString() + " " + values[1].ToString(); 
    } 

    public object[] ConvertBack(object value, Type[] targetTypes, object parameter, System.Globalization.CultureInfo culture) 
    { 
     throw new NotImplementedException(); 
    } 
} 

Это самое простое и лучшее решение.

0

Если вы создаете объект Address с отдельными полями для номера дома, названия улицы, почтового индекса и т. Д., Вы можете привязываться к каждому отдельно.

Если вы хотите распечатать весь адрес, а затем создать только для чтения свойство, которое сочетает в себе различные части адреса в одну строку:

public string SingleLineFormat 
{ 
    get 
    { 
     return string.Format("{0} {1}, {2}, {3}", this.Number, this.Street, this.Town, this.PostCode); 
    } 
} 

Вы можете даже иметь различные версии, которые возвращают строку отформатировано в нескольких строках или с различными комбинациями адреса по мере необходимости.

public string MultiLineFormat 
{ 
    get 
    { 
     return string.Format("{0} {1}{4} {2}{4} {3}", this.Number, this.Street, this.Town, this.PostCode, Environment.NewLine); 
    } 
} 
Смежные вопросы