2017-06-06 27 views
0

是否有可能從(ResourceDictionary的)後面的代碼訪問到一個指定的控件?我可以從(ResourceDictionary的)後面的代碼訪問到一個指定的控件嗎?

E.g.對我來說,有必要創建大量文件夾選取對話框。一個對話框可能包含需要選擇的每個文件夾的多行。 每行包含:標籤(名稱),文本框(選擇路徑)和按鈕(打開FileBrowserDialog)。

所以現在我想在FileBrowserDialog完成時訪問TextBox。但是我無法從CodeBehind訪問「SelectedFolderTextBox」。

有沒有更好的方法來實現我想要做的事情?

XAML

<ResourceDictionary ...> 
    ... 

    <StackPanel x:Key="FolderSearchPanel" 
       x:Shared="False"> 
     <Label Content="Foldername"/> 
     <TextBox x:Name="SelectedFolderTextBox" 
       Text="C:\Folder\Path\"/> 
     <Button Content="..." 
       Click="Button_Click"/> 
    </StackPanel> 
</ResourceDictionary> 

代碼隱藏

private void Button_Click(object sender, RoutedEventArgs e) 
{ 
    // Initialize and show 
    var dialog = new System.Windows.Forms.FolderBrowserDialog(); 
    System.Windows.Forms.DialogResult result = dialog.ShowDialog(); 

    // Process result 
    if (result == System.Windows.Forms.DialogResult.OK) 
    { 
     string selectedPath = dialog.SelectedPath; 

     SelectedFolderTextBox.Text = selectedPath; // THIS DOES NOT WORK 
                // since I don't have access to it 
                // but describes best, what I want to do 
    } 
} 

回答

0

當你有控制重複組和一點點關聯的功能是有意義的創建可重用的控制:

通過項目添加用戶控件「添加項目」對話框,並使用該XAML和代碼:

<UserControl x:Class="WpfDemos.FolderPicker" 
      x:Name="folderPicker" 
      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="75" d:DesignWidth="300"> 
    <StackPanel> 
     <Label Content="{Binding Path=Title, ElementName=folderPicker}"/> 
     <TextBox x:Name="SelectedFolderTextBox" 
       Text="{Binding Path=FullPath, ElementName=folderPicker, 
           UpdateSourceTrigger=PropertyChanged}"/> 
     <Button Content="..." Click="PickClick"/> 
    </StackPanel> 
</UserControl> 
public partial class FolderPicker : UserControl 
{ 
    public FolderPicker() 
    { 
     InitializeComponent(); 
    } 

    public static readonly DependencyProperty TitleProperty = DependencyProperty.Register(
     "Title", typeof (string), typeof (FolderPicker), new PropertyMetadata("Folder")); 

    public string Title 
    { 
     get { return (string) GetValue(TitleProperty); } 
     set { SetValue(TitleProperty, value); } 
    } 

    public static readonly DependencyProperty FullPathProperty = DependencyProperty.Register(
     "FullPath", typeof (string), typeof (FolderPicker), new FrameworkPropertyMetadata(@"C:\", FrameworkPropertyMetadataOptions.BindsTwoWayByDefault)); 

    public string FullPath 
    { 
     get { return (string) GetValue(FullPathProperty); } 
     set { SetValue(FullPathProperty, value); } 
    } 

    private void PickClick(object sender, RoutedEventArgs e) 
    { 
     using (var dialog = new System.Windows.Forms.FolderBrowserDialog()) 
     { 
      if (dialog.ShowDialog() == System.Windows.Forms.DialogResult.OK) 
       FullPath = dialog.SelectedPath; 
     } 
    } 
} 

文本框是從後臺代碼訪問。依賴屬性TitleFullPath允許爲不同用途定製控件,並創建與視圖模型的綁定(控制組聲明爲資源時無法執行的操作)。例如

視圖模型:

public class MyViewModel 
{ 
    public string Src { get; set; } 
    public string Target { get; set; } 
} 

觀點:

public MyWindow() 
{ 
    InitializeComponent(); 
    this.DataContext = new MyViewModel { Src = "C:", Target = "D:" } 
} 
<StackPanel> 
    <wpfDemos:FolderPicker Title="Source"  FullPath="{Binding Path=Src}" /> 
    <wpfDemos:FolderPicker Title="Destination" FullPath="{Binding Path=Target}"/> 
</StackPanel> 
+0

謝謝,你回答我遇到的下一個問題!所以UserControl是我下一步需要創建的:)所以ResourceDictionary只是用於「愚蠢的」漂亮的東西...... – BarbecueSIlver

0

你應該能夠在sender參數轉換爲Button再投的ButtonParent屬性設置爲StackPanel,找到的Children集合中的控件。事情是這樣的:

private void Button_Click(object sender, RoutedEventArgs e) 
{ 
    // Initialize and show 
    var dialog = new System.Windows.Forms.FolderBrowserDialog(); 
    System.Windows.Forms.DialogResult result = dialog.ShowDialog(); 

    // Process result 
    if (result == System.Windows.Forms.DialogResult.OK) 
    { 
     string selectedPath = dialog.SelectedPath; 

     Button clickedButton = sender as Button; 
     StackPanel sp = clickedButton.Parent as StackPanel; 
     if (sp != null) 
     { 
      TextBox SelectedFolderTextBox = sp.Children.OfType<TextBox>().FirstOrDefault(x => x.Name == "SelectedFolderTextBox"); 
      if (SelectedFolderTextBox != null) 
       SelectedFolderTextBox.Text = selectedPath; 
     } 
    } 
} 
+0

大,它的工作!感謝您的快速回復。 :) – BarbecueSIlver

相關問題