none
Datenbindung von Listen an Controls (TwoWay) RRS feed

  • Frage

  • Hi,

    ich möchte die GUI an ein komplexes Objekt binden.
    Dieses Objekt ist Teil einer Instanz eines Singletons.
    Darin enthalten sind Strukturen wie z.B.
    data.listOfObjects[data.idOfObjectList].listOfProperties[data.listOfObjects[data.idOfObjectList].idOfPropertyList].myProperty

    Nun kann ich einfache Objekte, also welche aus "normalen" Klassen an meine GUI anbinden, das hat im Test gut funktioniert.
    Aber mit den komplexen Strukturen habe ich schon bei dem einfachsten Wert Probleme. Weder werden die Objektvariablen nach dem Start, noch nach einer Änderung des Wertes zur Laufzeit (ButtonClick) auf der GUI angezeigt.

    Hier der Code:

    <StackPanel>
        <TextBox Margin="10" Height="25" Name="txtName" Text="{Binding Path=idOfListUnterklassen, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" />
        <Button Height="30" Width="120" Name="btnChangeValue" Click="btnChangeValue_Click">Wert ändern</Button>
    </StackPanel>
    Codebehind:
        public partial class MainWindow : Window
        {
            private DataSingleton data;
            public MainWindow()
            {
                data = DataSingleton.Instance;
                data.HauptKlasse = new Hauptklasse();
                data.HauptKlasse.IdOfListUnterklassen = 2;
                InitializeComponent();
                this.DataContext = data.HauptKlasse;
            }
    
            private void btnChangeValue_Click(object sender, RoutedEventArgs e)
            {
                data.HauptKlasse.IdOfListUnterklassen = 4;
            }
        }
    DataSingleton:
        public class DataSingleton : INotifyPropertyChanged 
        {
            #region Instanz dieser Klasse erzeugen
            private static DataSingleton instance;
            private DataSingleton(){ }
            public static DataSingleton Instance
            {
                get
                {
                    if (instance == null)
                    {
                        instance = new DataSingleton();
                    }
                    return instance;
                }
            }
            #endregion
    
            private Hauptklasse hauptKlasse;
    
            public Hauptklasse HauptKlasse
            {
                get { return hauptKlasse; }
                set { hauptKlasse = value;
                OnPropertyChanged(new PropertyChangedEventArgs("ListID"));
                }
            }
    
            public event PropertyChangedEventHandler PropertyChanged;
            protected virtual void OnPropertyChanged(PropertyChangedEventArgs e)
            {
                if (PropertyChanged != null)
                    PropertyChanged(this, e);
            }
        }
    Hauptklasse:
        public class Hauptklasse : INotifyPropertyChanged
        {
            private int idOfListUnterklassen;
    
            public int IdOfListUnterklassen
            {
                get { return idOfListUnterklassen; }
                set
                {
                    idOfListUnterklassen = value;
                    OnPropertyChanged(new PropertyChangedEventArgs("IdOfListUnterklassen"));
                }
            }
    
            public event PropertyChangedEventHandler PropertyChanged;
            protected virtual void OnPropertyChanged(PropertyChangedEventArgs e)
            {
                if (PropertyChanged != null)
                    PropertyChanged(this, e);
            }
        }
    Warum werden die Werte aus data.Hauptklasse.IdOfListUnterklassen nicht in der TextBox angezeigt?

    Grüße, 
    Frank




    www.energiewende-mach-ich-selbst.de

    Dienstag, 24. Juni 2014 11:54

Antworten

  • Hallo,
    ein Buchstabe im XAML ist falsch:

    <TextBox ... Text="{Binding Path=IdOfListUnterklassen, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" />

    Sonst würdest du versuchen an das private Feld zu binden - das geht natürlich nicht.

    PS: Ab .NET 4.5 kannst du dir die OnPropertyChanged-Methode auch einfacher gestalten siehe dir dafür offizielle Beispiel an: http://msdn.microsoft.com/de-de/library/system.componentmodel.inotifypropertychanged.aspx

            // This method is called by the Set accessor of each property.
            // The CallerMemberName attribute that is applied to the optional propertyName
            // parameter causes the property name of the caller to be substituted as an argument.
            private void NotifyPropertyChanged([CallerMemberName] String propertyName = "")
            {
                if (PropertyChanged != null)
                {
                    PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
                }
            }




    Tom Lambert - C# MVP
    Bitte bewertet- und markiert Beiträge als Antwort. Danke.
    Nützliche Links: .NET Quellcode | C# ↔ VB.NET Konverter
    Ich: Webseite | Code Beispiele | Facebook | Twitter | Snippets

    • Als Antwort markiert frank me Dienstag, 24. Juni 2014 14:26
    Dienstag, 24. Juni 2014 14:22
    Moderator

Alle Antworten

  • Hallo,
    ein Buchstabe im XAML ist falsch:

    <TextBox ... Text="{Binding Path=IdOfListUnterklassen, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" />

    Sonst würdest du versuchen an das private Feld zu binden - das geht natürlich nicht.

    PS: Ab .NET 4.5 kannst du dir die OnPropertyChanged-Methode auch einfacher gestalten siehe dir dafür offizielle Beispiel an: http://msdn.microsoft.com/de-de/library/system.componentmodel.inotifypropertychanged.aspx

            // This method is called by the Set accessor of each property.
            // The CallerMemberName attribute that is applied to the optional propertyName
            // parameter causes the property name of the caller to be substituted as an argument.
            private void NotifyPropertyChanged([CallerMemberName] String propertyName = "")
            {
                if (PropertyChanged != null)
                {
                    PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
                }
            }




    Tom Lambert - C# MVP
    Bitte bewertet- und markiert Beiträge als Antwort. Danke.
    Nützliche Links: .NET Quellcode | C# ↔ VB.NET Konverter
    Ich: Webseite | Code Beispiele | Facebook | Twitter | Snippets

    • Als Antwort markiert frank me Dienstag, 24. Juni 2014 14:26
    Dienstag, 24. Juni 2014 14:22
    Moderator
  • Vielen Dank Tom,

    Du hast ein gutes Auge (kleines i / großes I)!

    Und danke auch für den Hinweis mit dem NotifyPropertyChanged-Event unter Ausnutzung des Runtime.CompilerServices. Das habe ich natürlich gleich umgesetzt. :)

    Jetzt habe ich mal an Komplexität zugelegt und dabei hackt es wieder, aber das eröffne ich in einem anderen Thread.

    Herzliche Grüße!
    Frank


    www.energiewende-mach-ich-selbst.de

    Dienstag, 24. Juni 2014 14:44