今朝私はhereという質問をしました。単純な作業サンプルを実行すると、予想外の動作が起こりました。なぜDataBindingがUserControlに伝播しないのですか
GitHubで全作業サンプル。下の主な部分コード。
この場合、UserControlがWindowの子として直接使用されている場合でも、このコマンドはどのUserControlにも伝播されません。 UserControlがListBox ItemTemplateのDataTemplateとして使用されている場合、これも機能しません。
また、CommandがUserControlsに到達する問題を解決するためのハックボタンが含まれています。ハックはStackOverflowです。
しかし、なぜUserControlが(それなしで)コマンドを受け取っていないし、このハックを使用して良いコーディングの最初のルールを破る: "こんにちは凝集力と低結合"ハックを説明しません。ハックは、UserControlでコマンドを管理するために、ウィンドウコードで使用する必要があります、私の考えは、デフォルトで起こるはずです。
コマンドがデフォルトでUserControlに伝播していないのはなぜですか。コマンドを明確にUserControlに伝播するにはどうすればよいですか?
注:UserControlでCommandBindingを1つだけ使用すると、いずれかを削除しても問題は解決されません。
部分コード:
<Window x:Class="CommandRoutingIntoItemTemplate.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:local="clr-namespace:CommandRoutingIntoItemTemplate"
xmlns:system="clr-namespace:System;assembly=mscorlib"
mc:Ignorable="d"
Title="MainWindow" Height="350" Width="525">
<Grid>
<Grid.RowDefinitions>
<RowDefinition></RowDefinition>
<RowDefinition></RowDefinition>
<RowDefinition Height="Auto"></RowDefinition>
</Grid.RowDefinitions>
<local:UserControlTest></local:UserControlTest>
<ListBox Grid.Row="1">
<ListBox.ItemTemplate>
<DataTemplate>
<Border BorderBrush="Aqua" BorderThickness="2">
<local:UserControlTest></local:UserControlTest>
</Border>
</DataTemplate>
</ListBox.ItemTemplate>
<ListBox.Items>
<system:String>1</system:String>
<system:String>2</system:String>
</ListBox.Items>
</ListBox>
<StackPanel Grid.Row="2" Orientation="Horizontal">
<Button Command="local:Commands.CommandTest">Put focus on TestBlock and click here to see if command occurs</Button>
<Button Click="AddHack">Hack</Button>
</StackPanel>
</Grid>
</Window>
ユーザーコントロール:あなたのユーザーコントロール上で呼び出されたコマンドを取得されていません
<UserControl x:Class="CommandRoutingIntoItemTemplate.UserControlTest"
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"
xmlns:local="clr-namespace:CommandRoutingIntoItemTemplate"
mc:Ignorable="d"
d:DesignHeight="300" d:DesignWidth="300">
<UserControl.CommandBindings>
<CommandBinding Command="local:Commands.CommandTest" CanExecute="CommandTestCanExecuteUserControl" Executed="CommandTestExecuteUserControl"></CommandBinding>
</UserControl.CommandBindings>
<Grid>
<TextBox Text="UserControlTest">
<TextBox.CommandBindings>
<CommandBinding Command="local:Commands.CommandTest" CanExecute="CommandTestCanExecuteTextBox" Executed="CommandTestExecuteTextBox"></CommandBinding>
</TextBox.CommandBindings>
</TextBox>
</Grid>
</UserControl>
すばらしい説明!どうもありがとうございます!完璧に動作します。 UserControl側で何かを行うことができるかどうかを知っていますか?今は問題なく動作しますが、私はUserControlを別の場所で使用したいと思っています。すべての状況で適切な使用を保証するために、1つの共通の場所(UserControl)にコードを書くより良い解決策と聞こえますか? –
私もmenuItemでテストしましたが、これはおそらくMenu要素が私に提案した修正を持っているためうまくいきます:FocusManager.IsFocusScopeがtrueに設定されていますか?それは私が知って覚えなければならないものです;-)? –
@EricOuelletそれはまさに正しいことです。 MenuItemsは、独自のフォーカススコープを持つポップアップで表示されます。 – ghord