首页 > 解决方案 > 如何从 WPF 中的 CS 文件中调用 Grid

问题描述

无法再调用列表框中的网格了……我的 xaml 如下。

<UserControl x:Class="WPFPurpleButtonTest.InstrumentUserControl"
             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:WPFPurpleButtonTest"
             mc:Ignorable="d" 
             d:DesignHeight="750" d:DesignWidth="900">
    <Grid>
        <Grid.RowDefinitions>
            <RowDefinition Height="Auto"/>
            <RowDefinition Height="Auto"/>
        </Grid.RowDefinitions>
        <TabControl x:Name="tabControl" HorizontalAlignment="Left" Height="706" Margin="24,34,0,-212" VerticalAlignment="Top" Width="850" Grid.RowSpan="2">
            <TabItem Header="TabItem" Name="mainTab">
                <Grid Background="#FFE5E5E5" Margin="0,0,-396,-255">
                    <Label x:Name="colourName" Content="PURPLE" HorizontalAlignment="Left" Height="93" Margin="284,88,0,0" VerticalAlignment="Top" Width="243" FontWeight="Bold" HorizontalContentAlignment="Center" VerticalContentAlignment="Center" FontSize="50" Foreground="#FFDC00FF"/>
                    <Button x:Name="testButton" Content="Button" HorizontalAlignment="Left" Margin="365,181,0,0" VerticalAlignment="Top" Width="75" Click="TestButton_Click"/>
                    <Label x:Name="label" Content="Row Size" HorizontalAlignment="Left" Margin="198,211,0,0" VerticalAlignment="Top" Foreground="#FFDC00FF"/>
                    <Label x:Name="label_Copy" Content="Column Size" HorizontalAlignment="Left" Margin="432,211,0,0" VerticalAlignment="Top" Foreground="#FFDC00FF"/>
                    <Button x:Name="createGrid" Content="Create Grid" HorizontalAlignment="Left" Margin="365,273,0,0" VerticalAlignment="Top" Width="75" Click="CreateGrid_Click"/>
                    <TextBox x:Name="rowSizeText" HorizontalAlignment="Left" Height="23" Margin="278,214,0,0" TextWrapping="Wrap" Text="" VerticalAlignment="Top" Width="62"/>
                    <TextBox x:Name="columnSizeText" HorizontalAlignment="Left" Height="23" Margin="522,215,0,0" TextWrapping="Wrap" Text="" VerticalAlignment="Top" Width="62"/>
                </Grid>
            </TabItem>
            <TabItem Header="TabItem" Name="gridTab">
                <ListBox x:Name="listbox1" ScrollViewer.VerticalScrollBarVisibility="Disabled">
                    <ListBox.ItemsPanel>
                        <ItemsPanelTemplate>
                            <WrapPanel IsItemsHost="True" Orientation="Vertical" />
                        </ItemsPanelTemplate>
                    </ListBox.ItemsPanel>
                    <ListBox.ItemTemplate>
                        <DataTemplate>
                            <StackPanel Margin="20" HorizontalAlignment="Center">
                                <Viewbox>
                                    <Grid x:Name="wellGrid" Grid.Row="1" ShowGridLines="True"
                      local:GridHelpers.RowCount="{Binding RowCount}"
                      local:GridHelpers.ColumnCount="{Binding ColumnCount}" Margin="15,15,15,15" />
                                </Viewbox>
                            </StackPanel>
                        </DataTemplate>
                    </ListBox.ItemTemplate>
                </ListBox>
            </TabItem>
        </TabControl>
    </Grid>
</UserControl>

我希望能够像以前网格不在列表框中时那样调用 wellGrid.Children,但现在网格在列表框中时不完全确定如何执行此操作。

标签: wpfxamlgrid

解决方案


Grid is part of the应用DataTemplate that is assigned to theListBoxItem . You need to get theContentPresenter of the item. This is where theDataTemplate` 。

private void Button_Click(object sender, RoutedEventArgs e)
{
  int selectedItemIndex = this.listbox1.SelectedIndex;
  if (selectedItemIndex == -1)
  {
    return;
  }

  var itemContainer = this.listbox1.ItemContainerGenerator.ContainerFromIndex(selectedItemIndex) as ListBoxItem;

  if (TryFindChildElement(itemContainer, out ContentPresenter contentPresenter))
  {
    // Get the Grid
    var grid = contentPresenter.ContentTemplate.FindName("wellGrid", myContentPresenter) as Grid;    
  }
}

// Helper to traverse the visual tree
private bool TryFindChildElement<TElement>(DependencyObject parent, out TElement resultElement) where TElement : DependencyObject
{
  resultElement = null;
  for (var childIndex = 0; childIndex < VisualTreeHelper.GetChildrenCount(parent); childIndex++)
  {
    DependencyObject childElement = VisualTreeHelper.GetChild(parent, childIndex);

    if (childElement is Popup popup)
    {
      childElement = popup.Child;
    }

    if (childElement is TElement)
    {
      resultElement = childElement as TElement;
      return true;
    }

    if (TryFindChildElement(childElement, out resultElement))
    {
      return true;
    }
  }

  return false;
}

推荐阅读