一個用戶控件是一個完全可以接受的解決辦法,但我會更容易使用:1)自定義的控制,或2)RoutedUICommand。
建立一個自定義控制
創建自TextBox得出一個簡單的控制:
public class TextBoxWithFileDialog : TextBox
{
static TextBoxWithFileDialog()
{
DefaultStyleKeyProperty.OverrideMetadata(typeof(TextBoxWithFileDialog), new FrameworkPropertyMetadata(typeof(TextBoxWithFileDialog)));
CommandManager.RegisterClassCommandBinding(typeof(TextBoxWithFileDialog), new CommandBinding(
ApplicationCommands.Open,
(obj, e) => { e.Handled = true; ((TextBoxWithFileDialog)obj).ShowFileOpenDialog(); },
(obj, e) => { e.CanExecute = true; }));
}
void ShowFileOpenDialog()
{
var dialog = new Microsoft.Win32.OpenFileDialog
{
DefaultExt = ".txt"
};
if(dialog.ShowDialog()==true)
Text = dialog.FileName;
}
}
然後在主題/ Generic.xaml或資源從它包含字典添加含有適當的控件模板的樣式:
<Style TargetType="{x:Type TextBoxWithFileDialog}">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type TextBoxWithFileDialog}">
<DockPanel>
<Button Content="..." Command="Open" DockPanel.Dock="Right" />
<!-- copy original TextBox control template contents here -->
</DockPanel>
... close rest of tags ...
您可以使用Expression Blend複製TextBox的現有ControlTemplate或反射/ BamlViewer)。
對於我自己的項目,我寧願添加一個像這樣的解決方案到我的控制庫,這樣我就可以在任何我想要的地方使用它。不過,如果你只打算使用一次,這可能會過度。在這種情況下我也只是:
使用RoutedUICommand
public partial class MyWindow : Window
{
public Window()
{
InitializeComponent();
...
CommandManager.RegisterClassCommandBinding(typeof(TextBoxWithFileDialog), new CommandBinding(
ApplicationCommands.Open,
(obj, e) =>
{
e.Handled = true;
((MyWindow)obj).ShowFileOpenDialog((TextBox)e.Parameter);
},
(obj, e) => { e.CanExecute = true; }));
}
void ShowFileOpenDialog(TextBox textBox)
{
var dialog = new Microsoft.Win32.OpenFileDialog
{
DefaultExt = ".txt"
};
if(dialog.ShowDialog()==true)
textBox.Text = dialog.FileName;
}
}
這並不需要一個風格或額外的類。只需命名您的文本框,並將按鈕指向文本框作爲其命令參數:
<TextBox x:Name="Whatever" ... />
<Button Content="..." Command="Open" CommandParameter="{Binding ElementName=Whatever}" />
這就是它的全部。不幸的是,它只能在一個窗口中工作,並將其放在其他地方需要剪切和粘貼。這就是爲什麼我更喜歡自定義控件。
注意
如果你已經在其他地方你的應用程序使用ApplicationCommands.Open,您可以選擇不同的命令,或者創建自己:
public static readonly RoutedUICommand MyCommand = new RoutedUICommand(...)