2014-05-22 161 views
0

我知道關於依賴屬性的問題已經有很多問題了,但是我讀過的沒有一個解決了我的問題。WPF。設置自定義控件的依賴關係屬性

我有一個簡單的用戶控制按鈕和文本塊。文本塊包含一個我希望能夠從包含控件的窗口或視圖中設置的數字。我還需要能夠通過按下控件中的按鈕來增加值。

這裏是我的主窗口:

<Window x:Class="DependencyPropertiesTest.MainWindow" 
     xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
     xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
     Title="MainWindow" Height="350" Width="525" 
     xmlns:local="clr-namespace:DependencyPropertiesTest"> 
    <Grid> 
     <StackPanel Width="200" VerticalAlignment="Center"> 
      <local:UserControl1 Margin="10" UserControlNumber="{Binding Number}"/> 
      <TextBlock Text="{Binding Number}" Margin="10"/> 
      <Button Content="n" Click="Button_Click" Margin="10"/> 
     </StackPanel> 
    </Grid> 
</Window> 

背後的代碼:

using System; 
using System.Collections.Generic; 
using System.ComponentModel; 
using System.Linq; 
using System.Text; 
using System.Threading.Tasks; 
using System.Windows; 
using System.Windows.Controls; 
using System.Windows.Data; 
using System.Windows.Documents; 
using System.Windows.Input; 
using System.Windows.Media; 
using System.Windows.Media.Imaging; 
using System.Windows.Navigation; 
using System.Windows.Shapes; 

namespace DependencyPropertiesTest 
{ 
    /// <summary> 
    /// Interaction logic for MainWindow.xaml 
    /// </summary> 
    public partial class MainWindow : Window, INotifyPropertyChanged 
    { 
     public MainWindow() 
     { 
      InitializeComponent(); 
      DataContext = this; 
      Number = 1; 
     } 

     private int number; 
     public int Number 
     { 
      get { return number; } 
      set 
      { 
       number = value; 
       OnPropertyChanged("Number"); 
      } 
     } 


     public event PropertyChangedEventHandler PropertyChanged; 
     private void OnPropertyChanged(String info) 
     { 
      if (PropertyChanged != null) 
      { 
       PropertyChanged(this, new PropertyChangedEventArgs(info)); 
      } 
     } 

     private void Button_Click(object sender, RoutedEventArgs e) 
     { 
      Number++; 
     } 
    } 
} 

這裏是我的自定義控制:

<UserControl x:Class="DependencyPropertiesTest.UserControl1" 
      xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
      xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
      xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
      xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
      mc:Ignorable="d" 
      d:DesignHeight="300" d:DesignWidth="300"> 
    <Grid> 
     <Viewbox HorizontalAlignment="Center" VerticalAlignment="Center" Height="40" Width="100"> 
      <Border BorderBrush="Black" BorderThickness="1"> 
       <StackPanel Orientation="Horizontal"> 
        <TextBlock Text="{Binding UserControlNumber, TargetNullValue='nn', FallbackValue='ff'}" Margin="5"/> 
        <Button Content="+" Margin="5" Width="30" Click="Button_Click"/> 
       </StackPanel> 
      </Border> 
     </Viewbox> 

    </Grid> 
</UserControl> 

後面的代碼:

using System; 
using System.Collections.Generic; 
using System.ComponentModel; 
using System.Linq; 
using System.Text; 
using System.Threading.Tasks; 
using System.Windows; 
using System.Windows.Controls; 
using System.Windows.Data; 
using System.Windows.Documents; 
using System.Windows.Input; 
using System.Windows.Media; 
using System.Windows.Media.Imaging; 
using System.Windows.Navigation; 
using System.Windows.Shapes; 

namespace DependencyPropertiesTest 
{ 
    /// <summary> 
    /// Interaction logic for UserControl1.xaml 
    /// </summary> 
    public partial class UserControl1 : UserControl, INotifyPropertyChanged 
    { 
     public UserControl1() 
     { 
      InitializeComponent(); 
      DataContext = this; 
     } 



     public int UserControlNumber 
     { 
      get { return (int)GetValue(UserControlNumberProperty); } 
      set { SetValue(UserControlNumberProperty, value); } 
     } 

     // Using a DependencyProperty as the backing store for UserControlNumber. This enables animation, styling, binding, etc... 
     public static readonly DependencyProperty UserControlNumberProperty = 
      DependencyProperty.Register("UserControlNumber", typeof(int), typeof(UserControl1), new PropertyMetadata(0)); 



     public event PropertyChangedEventHandler PropertyChanged; 
     private void OnPropertyChanged(String info) 
     { 
      if (PropertyChanged != null) 
      { 
       PropertyChanged(this, new PropertyChangedEventArgs(info)); 
      } 
     } 

     private void Button_Click(object sender, RoutedEventArgs e) 
     { 
      UserControlNumber++; 
     } 
    } 
} 

主窗口中的兩個按鈕應分別增加用戶控件文本塊中的值,一個來自窗口,另一個來自控件本身。我可以設置從主窗口中的值作爲文字是這樣的:

<local:UserControl1 Margin="10" UserControlNumber="5"/> 

但是當我嘗試給它綁定的值,它不work.Checking與史努比的結合提供了以下錯誤:

消息:無法設置表達式。它被標記爲「NonShareable」並且已被使用。

UPDATE。

現在我已經試過,但它仍然不能正常工作:

 public int UserControlNumber 
    { 
     get { return (int)GetValue(UserControlNumberProperty); } 
     set { SetValue(UserControlNumberProperty, value); } 
    } 

    // Using a DependencyProperty as the backing store for UserControlNumber. This enables animation, styling, binding, etc... 
    public static readonly DependencyProperty UserControlNumberProperty = 
     DependencyProperty.Register("UserControlNumber", typeof(int), typeof(UserControl1), new PropertyMetadata(0, TextBlockPropertyChanged)); 

    private static void TextBlockPropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e) 
    { 
     UserControl1 uc1 = d as UserControl1; 
     int newNumber = (int)e.NewValue; 

     uc1.MyTextBlock.Text = newNumber.ToString(); 
    } 

在主窗口中:

在窗口中的XAML
<local:UserControl1 Margin="10" UserControlNumber="{Binding Number, Mode=TwoWay}"/> 
+0

我總是在元數據中設置屬性更改的回調,並使用它來設置回調中的文本塊。它從客戶端應用程序綁定。你有沒有考慮這種方法? –

+0

我給了它一個鏡頭。看到更新,這是你的意思? – ConnellOD

+0

是的,你釘了它。 –

回答

0

你chould在TwoWays模式綁定:

<local:UserControl1 Margin="10" UserControlNumber="{Binding Number, Mode=TwoWays}"/> 

否則在內部用戶控件的值會增加,但窗口中的綁定不會讓它改變。使用雙向綁定,窗口中的數字也會改變。

+0

我試過這個,但我恐怕沒有幫助。 – ConnellOD

相關問題