1. 程式人生 > >WPF屬性繫結測試(索引器方式)

WPF屬性繫結測試(索引器方式)

小結:

  如果屬性繫結路徑上的任何可通知變化屬性發生改變,其路徑及以下路徑都視為發生了變化,不管是否是可通知變化屬性,都會重新繫結新值。看來微軟對於繫結的機制是下了功夫的,如果採用簡單的反射,路徑尋找的方式,如果頁面元素比較多,層次比較多,效率肯定有問題的,看來有時間得反編譯,看看他們是如何搞的。下面是測試程式碼

1)VVM

using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Animation;
using System.Windows.Shapes;
using System.ComponentModel;

namespace SilverlightApplication3
{
    public partial class MainPage : UserControl
    {
        public MainPage()
        {
            InitializeComponent();
            this.DataContext = new VMDDD();
        }

        private void button1_Click(object sender, RoutedEventArgs e)
        {
            ((VMDDD)(this.DataContext)).SetVisible2(false);
        }

        private void button7_Click(object sender, RoutedEventArgs e)
        {
            ((VMDDD)(this.DataContext)).SetVisible(true);
        }
    }

    public class VMDDD : INotifyPropertyChanged
    {
        public event PropertyChangedEventHandler PropertyChanged;
        protected void RaisePropertyChanged(string PropertyName)
        {
            if (PropertyChanged != null)
            {
                PropertyChanged(this, new PropertyChangedEventArgs(PropertyName));
            }
        }
        Dictionary<string, CTRL> _Props = new Dictionary<string, CTRL>();
        public Dictionary<string, CTRL> Props
        {
            get
            {
                return _Props;
            }
            set
            {
                _Props = value;
                RaisePropertyChanged("Props");
            }
        }
        public VMDDD()
        {
            _Props.Add("button1", new CTRL() { Name = "hello" });
        }
        public void SetVisible(bool visible)
        {
            //改變屬性
            this.Props["button1"].Name = "Albert";
            this.Props["button1"].Visible = visible ? Visibility.Visible : Visibility.Collapsed;
        }
        public void SetVisible2(bool visible)
        {
            //改變更淺處屬性
            Dictionary<string, CTRL> theProps = new Dictionary<string, CTRL>();
            theProps.Add("button1", new CTRL() { Name = "good"+new Random().Next(1,10000).ToString() });
            theProps["button1"].Visible = visible ? Visibility.Visible : Visibility.Collapsed;
            this.Props = theProps;
        }
    }
    public class CTRL : INotifyPropertyChanged
    {
        public event PropertyChangedEventHandler PropertyChanged;
        protected void RaisePropertyChanged(string PropertyName)
        {
            if (PropertyChanged != null)
            {
                PropertyChanged(this, new PropertyChangedEventArgs(PropertyName));
            }
        }
        private Visibility _Visible;
        public Visibility Visible
        {
            get
            {
                return _Visible;
            }
            set
            {
                _Visible = value;
                RaisePropertyChanged("Visible");
            }
        }
        public string Name { get; set; }
    }
}

2)xaml

    <toolkit:DockPanel x:Name="LayoutRoot">
        <Grid Height="40" Name="grid1"  toolkit:DockPanel.Dock="Top" Visibility="{Binding Path=Props[button1].Visible,Mode=TwoWay}">
            <Button Content="Button1" Height="23" HorizontalAlignment="Left" Margin="258,11,0,0" Name="button4" VerticalAlignment="Top" Width="75" />
        </Grid>
        <Grid Height="59" Name="grid2"  toolkit:DockPanel.Dock="Top" >
            <Button Content="Button2" Height="23" HorizontalAlignment="Left" Margin="250,8,0,0" Name="button3" VerticalAlignment="Top" Width="75" />
        </Grid>
        <Grid Height="66" Name="grid3"  toolkit:DockPanel.Dock="Top" >
            <Button Content="Button3" Height="23" HorizontalAlignment="Left" Margin="6,23,0,0" Name="button2" VerticalAlignment="Top" Width="75" />
        </Grid>
        <Grid Height="24" Name="grid4"  toolkit:DockPanel.Dock="Top" VerticalAlignment="Center" UseLayoutRounding="False">
            <Button Content="{Binding Path=Props[button1].Name,Mode=TwoWay}" Height="23" HorizontalAlignment="Left" Margin="65,1,0,0" Name="button5" VerticalAlignment="Top" Width="75" />
        </Grid>
        <Grid Height="30" Name="grid5" toolkit:DockPanel.Dock="Bottom">
            <Button Content="hide" Height="23" Name="button1" Width="75" Margin="127,0,197,6" Click="button1_Click" />
            <Button Content="show" Height="23" Name="button7" Width="75" Margin="227,6,98,1" Click="button7_Click" />
        </Grid>
        <Button Content="Button5" Height="23" Name="button6" Width="75" />
    </toolkit:DockPanel>
</UserControl>