WPF ListBox binding not showing up

2019-07-23 11:03发布

I'm new to WPF and am having problems binding data to a simple ListBox. I've set it up in MainWindow.XAML

<ListBox Name="lbxShows" />

then in the code behind, I set the ItemsSource property to be an ObservableCollection of Show objects called ShowList. This is actually a property of another class (Oasis) of which OasisInst is an instance (setup in the constructor of MainApplication).

InitializeComponent();
mainApp = new MainApplication();
lbxShows.ItemsSource = mainApp.OasisInst.ShowList;

At this point, there are no items in ShowList but later, some get added and they don't appear in the ListBox.

The code for the Oasis class implements the INotifyPropertyChanged interface and then has the textbook method that's called from the ShowList setter.

private void NotifyPropertyChanged([CallerMemberName] string propertyName = "")
{
    if (PropertyChanged != null)
    {
        PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
    }
}

PropertyChanged is my PropertyChangedEventHandler event.

When I step through in debug mode, PropertyChanged is null so it seems that nothing has subscribed to my event. Given that this would usually happen automatically through a binding (I think?), then I'm guessing the binding hasn't been setup properly.

Maybe setting the ItemsSource property alone isn't sufficient to setup the binding?

2条回答
Animai°情兽
2楼-- · 2019-07-23 11:43

All you need in the mainApp for ShowList is

public ObservableCollection<string> ShowList {get; set;}

You MUST have the getters and setters` for it to work.

查看更多
等我变得足够好
3楼-- · 2019-07-23 11:56

What you are doing should be enough to bind the ObservableCollection and have the U/I receive updates. I thought it was not so was going to suggest using a BindingObject but found it works. (So I too learned something). Here is a simple example that should work with the Xaml you provided. It adds an entry in the list once per second.

I am confused where you mention "PropertyChanged is my PropertyChangedEventHandler event." Note that the only PropertyChangedEventHandler required is inside the Oasis object.

Perhaps you mean you have other controls on your U/I that need a PropertyChangedEventHandler on your MainWindow but that should have no interaction with the PropertyChangedEventHandler inside the Oasis object.

---- code below ----

using System;
using System.Collections.ObjectModel;
using System.ComponentModel;
using System.Runtime.CompilerServices;
using System.Windows;
using System.Windows.Threading;

namespace ListBoxTest
{
    /// <summary>
    /// Interaction logic for MainWindow.xaml
    /// </summary>
    /// 

    public class OasisInstance : INotifyPropertyChanged
    {
        public event PropertyChangedEventHandler PropertyChanged;

        ObservableCollection<string> _items = new ObservableCollection<string>();
        public ObservableCollection<string> ShowList
        {
            get { return _items; }
            set {
                if (_items != value)
                {
                    _items = value; NotifyPropertyChanged();
                }
            }
        }

        private void NotifyPropertyChanged([CallerMemberName] string propertyName = "")
        {
            if (PropertyChanged != null)
            {
                PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
            }
        }
    }

    public class MainApplication
    {
        public OasisInstance OasisInst  = new OasisInstance();
    }

    public partial class MainWindow : Window
    {
        MainApplication mainApp = new MainApplication();
        DispatcherTimer timer = new DispatcherTimer();

        public MainWindow()
        {
            timer.Interval = TimeSpan.FromSeconds(1);
            timer.Tick += (s, e) => { mainApp.OasisInst.ShowList.Add(DateTime.Now.ToString()); };
            timer.Start();

            InitializeComponent();

            lbxShows.ItemsSource = mainApp.OasisInst.ShowList;
        }
    }
}
查看更多
登录 后发表回答