1

わかりました... 私は、WPF とそのすべての素晴らしさを理解しようとしている VB.NET WinForms の男です。私は学習体験として基本的なアプリを作成しており、多くの情報を読んだり、チュートリアル ビデオを見たりしていますが、単純な DataBinding を使い始めることができず、いくつかの基本的な概念が欠けていることがわかっています。いくら好きでも、「あはは!」というのはありませんでした。まだソースコードをレビューしている瞬間。

だから... 私の Window クラスでは、カスタム文字列プロパティを定義しました。Blend に入ると、TextBox の Text をこのプロパティにデータバインドしようとしましたが、プロパティがバインドに使用できるものとして Blend に表示されません。

以下のコード/XAMLに何を追加する必要があるか教えてもらえますか...そして最も重要なのはその理由ですか?

私のXAML:

<Window x:Class="Window1"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    Title="Window1" Height="300" Width="300">
    <Grid>
        <TextBox Text="How do I Bind my SomeText property here?"></TextBox>
    </Grid>
</Window>

私のウィンドウコード:

Class Window1 

    Private _sometext As String = "Hello World"

    Public Property SomeText() As String
        Get
            Return _sometext
        End Get
        Set(ByVal value As String)
            _sometext = value
        End Set
    End Property

End Class
4

4 に答える 4

6

XAML を変更する必要がある方法は次のとおりです (コードは問題ありません)。

<Window x:Class="Window1"    
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"    
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"    
            Title="Window1" Height="300" Width="300" 
            DataContext="{Binding RelativeSource={RelativeSource Self}}">    
      <Grid>        
          <TextBox Text="{Binding SomeText}">
          </TextBox>    
      </Grid>
    </Window>

WPF のバインドを理解するには、DataContext を理解する必要があります。すべての要素には DataContext プロパティがあり、そのプロパティに配置したオブジェクトは、明示的なデータ ソースが指定されていないバインディングのデータ ソースになります。DataContext の値は、親オブジェクトから継承されます (したがって、この場合、TextBox は、ウィンドウの DataContext を継承するグリッドの DataContext を継承します)。ウィンドウのプロパティを参照したいので、DataContext が Window インスタンスを指すように設定する必要があります。これは、Window の DataContext 属性で行うことです。

{Binding } 要素で Source= または RelativeSource= 構文を使用して、個々のバインドのデータ ソースを変更することもできます。

于 2008-10-17T12:52:02.757 に答える
5

データ バインディングでは、いくつかのことを考えると役に立ちます。

  1. ソース オブジェクト
  2. ターゲット オブジェクト (DependencyObject である必要があります)
  3. ソース プロパティ (バインディングに参加しているソース オブジェクトのプロパティ)
  4. ターゲット プロパティ (依存プロパティである必要があります)

あなたのサンプルコードで:

  1. ソース オブジェクト = Window1
  2. ターゲット オブジェクト = TextBox
  3. ソース プロパティ = SomeText プロパティ
  4. ターゲット プロパティ = テキスト

Binding マークアップ拡張機能は、Target オブジェクトの Target プロパティに適用されます。

上記を説明する図は次のとおりです。

代替テキスト

次のコードを確認してください (この問題を解決する 1 つの方法)。

<Window
    x:Class="WpfApplication2.Window1"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    x:Name="theWindow"
    Title="Window1"
    Height="300"
    Width="300"
>
    <Grid>
        <StackPanel>
            <TextBox Text="{Binding ElementName=theWindow, Path=SomeText}"/>
            <Button
                Width="100"
                Height="25"
                Content="Change Text"
                Click="Button_Click"
            />
        </StackPanel>
    </Grid>
</Window>

Binding マークアップ拡張機能では、ElementName を使用してソースを定義しました。これにより、ビジュアル ツリー内の別の要素をソースとして使用できます。その際、x:Name 属性を使用してウィンドウに名前を付ける必要もありました。

Binding を使用してソースを定義する方法はいくつかあります (つまり、Source、ElementName、DataContext)。ElementName は 1 つの方法にすぎません。

注意すべきことの 1 つは、Source プロパティが依存関係プロパティである必要はないということですが、そうでない場合、Target プロパティは更新されません ... 特別な助けがなければ。次のコードを確認してください (C# で申し訳ありませんが、C# の方が速かったです)。その中で、INotifyPropertyChanged を実装していることがわかります。これにより、ソース オブジェクトは何かが変更されたことを示すことができます ... データ バインディングはそれを監視するのに十分スマートです。したがって、ボタンをクリックすると (ここのコード例から)、TextBox が更新されます。このインターフェイスを実装しないと (そしてボタンをクリックしても)、TextBox は更新されません。

それが役立つことを願っています。

/// <summary>
/// Interaction logic for Window1.xaml
/// </summary>
public partial class Window1 : Window, INotifyPropertyChanged
{
    public Window1()
    {
        InitializeComponent();
    }

    private string _someText = "Hello World!";
    public string SomeText
    {
        get { return _someText; }
        set
        {
            _someText = value;
            OnNotifyPropertyChanged("SomeText");
        }
    }

    #region INotifyPropertyChanged Members

    public event PropertyChangedEventHandler PropertyChanged;
    private void OnNotifyPropertyChanged(string propertyName)
    {
        if (PropertyChanged != null)
        {
            PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
        }
    }

    #endregion

    private void Button_Click(object sender, RoutedEventArgs e)
    {
        this.SomeText = "Goodbye World!";
    }
}
于 2008-10-17T13:01:47.543 に答える
1

WPF DataBinding は非常に強力な機能です。次のような、ウェブ上の既存の記事を読むことをお勧めします。

Beatrix Costa の Data Binding に関するブログも非常に役に立ちました。

于 2008-10-17T13:02:05.360 に答える
0

CLRプロパティを使用したデータバインディングには、追加の手順が必要です。INotifyPropertyChangedを実装し、そのCLRプロパティが変更されるたびにPropertyChangedイベントを発生させる必要があります。これではBlendに表示されませんが、Text = "{Binding SomeText}"を使用してプロパティにバインドし、ウィンドウのDataContextをオブジェクトに設定できます。

別の方法があります。.NETデータバインディングを使用する代わりに、UpdateControls.NETを検討してください。これは、データバインディングを置き換えるオープンソースプロジェクトであり、INotifyPropertyChangedを必要としません。アップデートコントロールの優れている点は、中間のビジネスロジックを透視できることです。INotifyPropertyChangedを使用すると、イベントをキャッチして再起動する必要があります。

于 2008-12-29T14:26:33.780 に答える