2010-10-07 14 views
14

मैं निर्भरता गुणों के साथ बाध्य करने के लिए उपयोगकर्ता नियंत्रण बनाने की कोशिश कर रहा हूं। आंतरिक रूप से मेरे पास ComboBox है जो इन गुणों से जुड़ा हुआ है, लेकिन बाध्यकारी केवल एक ही तरीके से काम करता है। ComboBoxItemsSource से भरता है, लेकिन SelectedItem को उस दृश्यमान में वापस अपडेट नहीं किया गया है जिसे मैं बाध्यकारी हूं।मैं अपने WPF उपयोगकर्ता नियंत्रण की निर्भरता गुणों को अपने दृश्य मॉडल को कैसे अपडेट करूं?

एक सरल उदाहरण:

<UserControl x:Class="PeopleControlTest.PeopleControl" 
     xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
     xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
     xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
     xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
     mc:Ignorable="d" d:DesignHeight="56" d:DesignWidth="637"> 
<StackPanel > 
    <ComboBox Margin="11" 
       ItemsSource="{Binding BoundPeople, RelativeSource={RelativeSource AncestorType=UserControl}}" 
       SelectedItem="{Binding BoundSelectedPerson, RelativeSource={RelativeSource AncestorType=UserControl}}"/> 
</StackPanel> 

कोड के साथ

:

public class PeopleViewModel : INotifyPropertyChanged 
{ 
    public PeopleViewModel() 
    { 
     People = new List<string>(new [] {"John", "Alfred","Dave"}); 
     SelectedPerson = People.FirstOrDefault(); 
    } 

    public event PropertyChangedEventHandler PropertyChanged; 

    private IEnumerable<string> _people; 
    public IEnumerable<string> People 
    { 
     get { return _people; } 
     set 
     { 
      _people = value; 
      if (PropertyChanged != null) 
      { 
       PropertyChanged(this, new PropertyChangedEventArgs("People")); 
      } 
     } 
    } 

    private string _selectedPerson; 
    public string SelectedPerson 
    { 
     get { return _selectedPerson; } 
     set 
     { 
      _selectedPerson = value; 
      if (PropertyChanged != null) 
      { 
       PropertyChanged(this, new PropertyChangedEventArgs("SelectedPerson")); 
      } 
     } 
    } 
} 

यह उपयोगकर्ता नियंत्रण है:

इस उपयोगकर्ता नियंत्रण के साथ बाध्य करने के लिए दृश्य मॉडल है

के पीछे
public partial class PeopleControl : UserControl 
{ 
    public PeopleControl() 
    { 
     InitializeComponent(); 
    } 

    public static readonly DependencyProperty BoundPeopleProperty = 
     DependencyProperty.Register("BoundPeople", typeof(IEnumerable<string>), typeof(PeopleControl), new UIPropertyMetadata(null)); 

    public static readonly DependencyProperty BoundSelectedPersonProperty = 
     DependencyProperty.Register("BoundSelectedPerson", typeof(string), typeof(PeopleControl), new UIPropertyMetadata("")); 

    public IEnumerable<string> BoundPeople 
    { 
     get { return (IEnumerable<string>)GetValue(BoundPeopleProperty); } 
     set { SetValue(BoundPeopleProperty, value); } 
    } 

    public string BoundSelectedPerson 
    { 
     get { return (string)GetValue(BoundSelectedPersonProperty); } 
     set { SetValue(BoundSelectedPersonProperty, value); } 
    } 
} 

और यह है कि कैसे मैं मुख्य विंडो में उपयोगकर्ता नियंत्रण बाँध

<Window x:Class="PeopleControlTest.MainWindow" 
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
      xmlns:controls="clr-namespace:PeopleControlTest" 
    Title="MainWindow" Height="350" Width="525"> 
    <Grid> 
     <controls:PeopleControl 
      BoundPeople="{Binding People}" 
      BoundSelectedPerson="{Binding SelectedPerson}"/> 
    </Grid> 
</Window> 

उपयोगकर्ता नियंत्रण में बता गया नामों से भर जाता है (viewmodel का एक उदाहरण के लिए सेट खिड़कियों डेटा संदर्भ के साथ), लेकिन जब मैं एक अलग नाम का चयन करता हूं तो यह दृश्य मॉडल पर वापस अपडेट नहीं होता है। कोई विचार क्या मैं यहाँ याद कर रहा हूँ?

धन्यवाद!

उत्तर

19

कुछ गुण डिफ़ॉल्ट रूप से दो-तरफा बांधते हैं (SelectedItem सहित) लेकिन आपका BoundSelectedPerson नहीं है। आप बाध्यकारी की विधि सेट कर सकते हैं:

<controls:PeopleControl 
      BoundPeople="{Binding People}" 
      BoundSelectedPerson="{Binding SelectedPerson, Mode=TwoWay}"/> 

या आप DependencyProperty पर एक ध्वज की स्थापना करके यह डिफ़ॉल्ट रूप से TwoWay बना सकते हैं:

public static readonly DependencyProperty BoundSelectedPersonProperty = 
     DependencyProperty.Register("BoundSelectedPerson", typeof(string), typeof(PeopleControl), new FrameworkPropertyMetadata("",FrameworkPropertyMetadataOptions.BindsTwoWayByDefault)); 
+0

बढ़िया है, है, धन्यवाद है कि काम करता है !!! किसी कारण से मैंने सोचा कि मैं पढ़ूंगा कि सभी डीपी डिफ़ॉल्ट रूप से दो तरह से काम करते हैं। मैं UIPropertyMetadata का भी उपयोग कर रहा था, जिस पर मुझे वह विकल्प नहीं मिला। – Stefan

+0

_ (यह समाधान ठीक है। मैं सिर्फ उन लोगों के लिए एक नोट जोड़ना चाहता हूं जिनके पास एक ही समस्या हो सकती है और समाधान ढूंढने के दौरान यहां अपना रास्ता ढूंढ सकता है।) _ वह संपत्ति जो आप निर्भरता संपत्ति से बंधे हैं UserControl में एक सेट() विधि होनी चाहिए। – skst

संबंधित मुद्दे