Error de WPF: No se puede encontrar el framework de gobierno para el elemento de destino


Tengo una cuadrícula de datos con una fila que tiene una imagen. Esta imagen está enlazada con un disparador a un cierto estado. Cuando el estado cambia quiero cambiar la imagen.

La Plantilla en sí se establece en el estilo de encabezado de una DataGridTemplateColumn. Esta plantilla tiene algunos enlaces. El primer día de enlace muestra qué día es y el Estado cambia la imagen con un disparador.

Estas propiedades se establecen en un ViewModel.

Propiedades:

public class HeaderItem
{
    public string Day { get; set; }
    public ValidationStatus State { get; set; }
}

this.HeaderItems = new ObservableCollection<HeaderItem>();
        for (int i = 1; i < 15; i++)
        {
            this.HeaderItems.Add(new HeaderItem()
            {
                Day = i.ToString(),
                State = ValidationStatus.Nieuw,
            });
        }

Datagrid:

<DataGrid x:Name="PersoneelsPrestatiesDataGrid" HorizontalAlignment="Stretch" VerticalAlignment="Stretch"
              AutoGenerateColumns="False" SelectionMode="Single" ItemsSource="{Binding CaregiverPerformances}" FrozenColumnCount="1" >

    <DataGridTemplateColumn HeaderStyle="{StaticResource headerCenterAlignment}" Header="{Binding HeaderItems[1]}" Width="50">

                <DataGridTemplateColumn.CellEditingTemplate>
                    <DataTemplate>
                        <TextBox Text="{ Binding Performances[1].Duration,Converter={StaticResource timeSpanConverter},Mode=TwoWay}"/>
                    </DataTemplate>
                </DataGridTemplateColumn.CellEditingTemplate>
                <DataGridTemplateColumn.CellTemplate>
                    <DataTemplate>
                        <TextBlock TextAlignment="Center" Text="{ Binding Performances[1].Duration,Converter={StaticResource timeSpanConverter}}"/>
                    </DataTemplate>
                </DataGridTemplateColumn.CellTemplate>
            </DataGridTemplateColumn> </DataGrid>

Datagrid HeaderStyleTemplate:

  <Style x:Key="headerCenterAlignment"
          TargetType="{x:Type DataGridColumnHeader}">
        <Setter Property="HorizontalContentAlignment" Value="Center"/>

        <Setter Property="Template">
            <Setter.Value>
                <ControlTemplate TargetType="{x:Type DataGridColumnHeader}">
                    <Grid>
                        <Grid.RowDefinitions>
                            <RowDefinition />
                            <RowDefinition />
                        </Grid.RowDefinitions>

                        <TextBlock Grid.Row="0" Text="{Binding Day}" />
                        <Image x:Name="imageValidation" Grid.Row="1" Width="16" Height="16" Source="{StaticResource imgBevestigd}" />
                    </Grid>

                    <ControlTemplate.Triggers>
                        <MultiDataTrigger >
                            <MultiDataTrigger.Conditions>
                                <Condition Binding="{Binding State}" Value="Nieuw"/>                                 
                            </MultiDataTrigger.Conditions>
                            <Setter TargetName="imageValidation" Property="Source" Value="{StaticResource imgGeenStatus}"/>
                        </MultiDataTrigger>
                    </ControlTemplate.Triggers>
                </ControlTemplate>
            </Setter.Value>
        </Setter>
    </Style>

Ahora, cuando inicio el proyecto, las imágenes no se muestran y obtengo este error:

Sistema.Windows.Error de datos: 2: No se puede encontrar FrameworkElement o FrameworkContentElement para el elemento de destino. BindingExpression: Path = HeaderItems[0]; DataItem = null; el elemento de destino es ' DataGridTemplateColumn '(hashCode=26950454); la propiedad de destino es 'Header' (type "Objeto")

¿Por qué se muestra este error?

Author: Cœur, 2011-10-05

1 answers

Tristemente cualquier DataGridColumn alojado bajo DataGrid.Columns no es parte del árbol Visual y por lo tanto no está conectado al contexto de datos de la cuadrícula de datos. Por lo tanto, los enlaces no funcionan con sus propiedades como Visibility o Header, etc. (¡aunque estas propiedades son propiedades de dependencia válidas!).

Ahora usted puede preguntarse ¿cómo es eso posible? ¿No se supone que su propiedad Binding está vinculada al contexto de datos? Bueno, simplemente es un truco. La encuadernación no funciona realmente. En realidad, son las celdas de cuadrícula de datos las que copiar / clona este objeto de enlace y úsalo para mostrar su propio contenido!

Así que ahora volviendo a resolver su problema, asumo que HeaderItems es una propiedad del objeto que se establece como DataContext de su vista padre. Nosotros podemos conectar el DataContext de la vista a cualquier DataGridColumn a través de algo que llamamos un ProxyElement.

El siguiente ejemplo ilustra cómo conectar un hijo lógico como ContextMenu o DataGridColumn a la vista padre DataContext

 <Window x:Class="WpfApplicationMultiThreading.Window5"
         xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
         xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"        
         xmlns:vb="http://schemas.microsoft.com/wpf/2008/toolkit"
         Title="Window5" Height="300" Width="300" >
  <Grid x:Name="MyGrid">
    <Grid.Resources>
        <FrameworkElement x:Key="ProxyElement" DataContext="{Binding}"/>
    </Grid.Resources>
    <Grid.DataContext>
         <TextBlock Text="Text Column Header" Tag="Tag Columne Header"/>
    </Grid.DataContext>
    <ContentControl Visibility="Collapsed"
             Content="{StaticResource ProxyElement}"/>
    <vb:DataGrid AutoGenerateColumns="False" x:Name="MyDataGrid">
        <vb:DataGrid.ItemsSource>
            <x:Array Type="{x:Type TextBlock}">
                <TextBlock Text="1" Tag="1.1"/>
                <TextBlock Text="2" Tag="1.2"/>
                <TextBlock Text="3" Tag="2.1"/>
                <TextBlock Text="4" Tag="2.2"/>
            </x:Array>
        </vb:DataGrid.ItemsSource>
        <vb:DataGrid.Columns>
            <vb:DataGridTextColumn
                       Header="{Binding DataContext.Text,
                                     Source={StaticResource ProxyElement}}"
                       Binding="{Binding Text}"/>
            <vb:DataGridTextColumn
                       Header="{Binding DataContext.Tag,
                                     Source={StaticResource ProxyElement}}"
                       Binding="{Binding Tag}"/>
        </vb:DataGrid.Columns>
    </vb:DataGrid>
  </Grid>
</Window>

La vista anterior encontró el mismo error de enlace que ha encontrado si no he implementado el hack ProxyElement. El ProxyElement es cualquier framework que roba el DataContext de la Vista principal y lo ofrece al hijo lógico como ContextMenu o DataGridColumn. Para eso debe ser alojado como un Content en un ContentControl invisible que está bajo la misma vista.

Espero que esto te guíe en la dirección correcta.

 130
Author: WPF-it,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2011-11-10 09:21:42