Autor Beitrag
Määx
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Beiträge: 123



BeitragVerfasst: Di 25.02.14 13:58 
Hallo zusammen,

ich habe mir einige Models gebaut, die ua Kunden repräsenteiren. Nun würde ich diese gerne bearbeiten und somit an eine ComboBox binden. Leider habe ich dabei Probleme mit der Synchronisierung...
Folgendes habe ich jetzt:
Meine beiden Models:
ausblenden volle Höhe C#-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
17:
18:
19:
20:
21:
22:
23:
24:
25:
26:
27:
28:
29:
30:
31:
32:
33:
34:
35:
36:
37:
38:
39:
40:
41:
42:
43:
44:
45:
46:
47:
48:
49:
50:
51:
52:
53:
public class StoreModel
    {
        public int Storenum{ get; set; }
        public BindingList<PersonModel> Kunden{ get; set; }
        public PersonModel CurrentPerson { get; private set; }

        public StoreModel()
        {
            Storenum= -1;
            Kunden= new BindingList<PersonModel>();
            CurrentPerson = null;            
        }
        public void SetCurrentKunde(PersonModel newKunde)
        {
            if (!Kunden.Contains(newKunde))
                Kunden.Add(newKunde);
            CurrentPerson = newKunde;
        }
    }
public class PersonModel 
    {
        public int Id { get; set; }
        public string Firstname { get; set; }
        public string Lastname { get; set; }
        public DateTime Birthday { get; set; }

        public PersonModel ()
        {
            Id = -1;
            Firstname = string.Empty;
            Lastname = string.Empty;
            Birthday = DateTime.MinValue;
        }
        public PersonModel (int id, string lastname, string firstname)
            :this()
        {
            Id = id;
            Lastname = lastname;
            Firstname = firstname;
        }

        public override bool Equals(object obj)
        {
            if (obj == null)
                return false;

            PersonModel p = obj as PersonModel;
            if (p == null)
                return false;

            return (p.Id == this.Id);
        }
    }


Und in der xaml habe ich dann folgende Bindungen (den DataContext setzte ich Anfangs auf ein Objekt von StoreModel):
ausblenden C#-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
<ComboBox x:Name="ComboBoxKunde" 
                  ItemsSource="{Binding Kunden}" 
                  DisplayMemberPath="Lastname" 
                  SelectedValuePath="Id" 
                  SelectedValue="{Binding CurrentPerson.Id}"
                  IsSynchronizedWithCurrentItem="True" 
                  SelectionChanged="ComboBoxKunde_SelectionChanged" />
<Label Content="{Binding CurrentPerson.Firstname}"/>
<TextBox Text="{Binding Kunden/Firstname, Mode=TwoWay}"/>


In dem SelectionChanged-Event der ComboBox rufe ich dann noch die SetCurrentKunde-Methode auf. Beim starten der Anwendung wird in der ComboBox auch der aktuelle Kundeausgewählt und im Textfeld und Label angezeigt. Ändere ich nun die ComboBox, so wird das TextFeld ebenfalls verändert, das Label behält jedoch den alten Eintrag und die ComboBox springt ebenfalls zurück auf den ursprünglichen Wert. Das Objekt CurrentKunde wird jedoch aktualisiert...

Was mach eich denn da nun falsch?
Vielen Dank
Määx
Christian S.
ontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic starofftopic star
Beiträge: 20451
Erhaltene Danke: 2264

Win 10
C# (VS 2019)
BeitragVerfasst: Di 25.02.14 14:23 
Hallo!

Wenn Du bei der Combobox ein TwoWay-Binding auf SelectedItem (nicht SelectedValue, das funktioniert nicht) machst, brauchst Du das Ereignis schonmal nicht mehr.
ausblenden XML-Daten
1:
2:
3:
4:
5:
6:
    <ComboBox x:Name="ComboBoxKunde"  ItemsSource="{Binding Kunden}" 
                  DisplayMemberPath="Firstname" 
                  SelectedItem="{Binding CurrentPerson,Mode=TwoWay}"
                  IsSynchronizedWithCurrentItem="True" 
                  Height="36" VerticalAlignment="Top"
          />


Dann musst Du nur noch INotifyPropertyChanged implementieren und das entsprechende Ereignis "feuern", wenn CurrentPerson geändert wird:
ausblenden C#-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
17:
18:
    private Kunde currentPerson;
    public Kunde CurrentPerson
    {
      get
      {
        return currentPerson;
      }
      set
      {
        if (currentPerson != value)
        {
          currentPerson = value;
          var tmp = PropertyChanged;
          if (tmp != null)
            tmp.Invoke(thisnew PropertyChangedEventArgs("CurrentPerson"));
        }
      }
    }

Dann bekommen auch alle Komponenten das mit und können drauf reagieren.


Grüße
Christian


//Edit: Das mit dem Ereignis stimmt wahrscheinlich nicht, weil Du in SetCurrentPerson ja mehr tust, als nur auszuwählen ...
//Edit2: Andererseits kannst Du das dann im Setter erledigen, es dürfte als doch stimmen :nut:

_________________
Zwei Worte werden Dir im Leben viele Türen öffnen - "ziehen" und "drücken".

Für diesen Beitrag haben gedankt: Määx
Määx Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Beiträge: 123



BeitragVerfasst: Di 25.02.14 17:23 
Wunderbar, funktioniert perfekt :)
Vielen Dank!