WPF核心的技術--資料繫結

來源:互聯網
上載者:User
WPF最核心的技術優勢之一就是資料繫結。資料繫結,可以通過對資料的操作來更新介面。

資料繫結最經常用到的是ObservableCollection<T> 和 Dictionary<T, T> 這兩個類。

ObservableCollection表示一個動態資料集合,在添加項、移除項或重新整理整個列表時,此集合將提供通知,可以通過更新集合資料來更新介面顯示。

Dictionary字典類,檢索和資料操作效能極性,所以一些配置項的集合都使用它來儲存。

因此,大家就想到的,有沒有ObservableCollection和Dictionary相結合的類呢,於是就形成的ObservableDictionary類。

網上有很多版本的ObservableDictionary類,據我瞭解到的,最早且最經典的就是Dr.WPF裡面的ItemsControl to a dictionary,其他的版本多數是參考這個來修改的(不對的那就是我孤陋寡聞了)。

今天我提供的這個版本,也是參考了網上的其他版本和Dr.WPF裡的。

Dr.WPF裡的定義是這樣的:

public class ObservableDictionary <TKey, TValue> :        IDictionary<TKey, TValue>,        ICollection<KeyValuePair<TKey, TValue>>,        IEnumerable<KeyValuePair<TKey, TValue>>,        IDictionary,        ICollection,        IEnumerable,        ISerializable,        IDeserializationCallback,        INotifyCollectionChanged,        INotifyPropertyChanged

大家細心點就會發現,這裡繼承的介面和Dictionary<TKey, TValue>所繼承的大部分相同,只是多了INotifyCollectionChanged, INotifyPropertyChanged

於是,今天我提供的版本,就直接繼承於Dictionary<TKey, TValue>和INotifyCollectionChanged, INotifyPropertyChanged。

本人測試過,無BUG,效能也極佳,下面上代碼:

    public class ObservableDictionary<TKey, TValue> : Dictionary<TKey, TValue>, INotifyCollectionChanged, INotifyPropertyChanged    {        public ObservableDictionary()            : base()        { }        private int _index;        public event NotifyCollectionChangedEventHandler CollectionChanged;        public event PropertyChangedEventHandler PropertyChanged;        public new KeyCollection Keys        {            get { return base.Keys; }        }        public new ValueCollection Values        {            get { return base.Values; }        }        public new int Count         {            get { return base.Count; }        }        public new TValue this[TKey key]        {            get { return this.GetValue(key); }            set { this.SetValue(key, value); }        }        public TValue this[int index]        {            get { return this.GetIndexValue(index); }            set { this.SetIndexValue(index, value); }        }        public new void Add(TKey key, TValue value)        {            base.Add(key, value);            this.OnCollectionChanged(new NotifyCollectionChangedEventArgs(NotifyCollectionChangedAction.Add, this.FindPair(key), _index));            OnPropertyChanged("Keys");            OnPropertyChanged("Values");            OnPropertyChanged("Count");        }        public new void Clear()        {            base.Clear();            this.OnCollectionChanged(new NotifyCollectionChangedEventArgs(NotifyCollectionChangedAction.Reset));            OnPropertyChanged("Keys");            OnPropertyChanged("Values");            OnPropertyChanged("Count");        }        public new bool Remove(TKey key)        {            var pair = this.FindPair(key);            if (base.Remove(key))            {                this.OnCollectionChanged(new NotifyCollectionChangedEventArgs(NotifyCollectionChangedAction.Remove, pair, _index));                OnPropertyChanged("Keys");                OnPropertyChanged("Values");                OnPropertyChanged("Count");                return true;            }            return false;        }        protected void OnCollectionChanged(NotifyCollectionChangedEventArgs e)        {            if (this.CollectionChanged != null)            {                this.CollectionChanged(this, e);            }        }        protected void OnPropertyChanged(string propertyName)        {            if (this.PropertyChanged != null)            {                this.PropertyChanged(this, new PropertyChangedEventArgs(propertyName));            }        }        #region private方法        private TValue GetIndexValue(int index)        {            for (int i = 0; i < this.Count; i++)            {                if (i == index)                {                    var pair = this.ElementAt(i);                    return pair.Value;                }            }            return default(TValue);        }        private void SetIndexValue(int index, TValue value)        {            try            {                var pair = this.ElementAtOrDefault(index);                SetValue(pair.Key, value);                            }            catch (Exception)            {                            }        }        private TValue GetValue(TKey key)        {            if (base.ContainsKey(key))            {                return base[key];            }            else            {                return default(TValue);            }        }        private void SetValue(TKey key, TValue value)        {            if (base.ContainsKey(key))            {                var pair = this.FindPair(key);                int index = _index;                base[key] = value;                var newpair = this.FindPair(key);                this.OnCollectionChanged(new NotifyCollectionChangedEventArgs(NotifyCollectionChangedAction.Replace, newpair, pair, index));                OnPropertyChanged("Values");                OnPropertyChanged("Item[]");            }            else            {                this.Add(key, value);            }        }        private KeyValuePair<TKey, TValue> FindPair(TKey key)        {            _index = 0;            foreach (var item in this)            {                if (item.Key.Equals(key))                {                    return item;                }                _index++;            }            return default(KeyValuePair<TKey, TValue>);        }        private int IndexOf(TKey key)        {            int index = 0;            foreach (var item in this)            {                if (item.Key.Equals(key))                {                    return index;                }                index++;            }            return -1;        }        #endregion    }

擴充方面,大家可以以Dr.WPF版本來修改,那個更加有技術含量和可擴充性更強!

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.