2013-02-18 12 views
6

Problem polega na tym, że RelativeSource nie działa w następującym przypadku. Używam Silverlight 5.RelativeSource and Popup

//From MainPage.xaml 
<Grid x:Name="LayoutRoot" Background="White" Height="100" Width="200"> 
    <Popup IsOpen="True"> 
     <TextBlock Text="{Binding Path=DataContext, RelativeSource={RelativeSource AncestorType=Grid}}" /> 
    </Popup> 
</Grid> 

//From MainPage.xaml.cs 
public MainPage() 
{ 
    InitializeComponent(); 
    DataContext = "ololo"; 
} 

Jeżeli ustawić punkt przerwania na wiązaniu, będę się błąd:

System.Exception: BindingExpression_CannotFindAncestor.

Jeśli używam ElementName=LayoutRoot zamiast RelativeSource, wszystko będzie OK.

Dlaczego powiązanie źródła względnego nie działa?

Odpowiedz

6

Popup jest jak ContextMenu, kontrolki ToolTip, nie są dodawane do VisualTree. W tym celu trzeba będzie zrobić jak

<Grid x:Name="LayoutRoot" Height="100" Width="200" Background="Black"> 
    <Popup Grid.Row="0" x:Name="popup" DataContext="{Binding PlacementTarget.DataContext, RelativeSource={RelativeSource Mode=Self}}"> 
     <TextBlock Text="{Binding DataContext, ElementName=popup}" Background="Red" Width="30" Height="30" /> 
    </Popup> 
</Grid> 

public MainWindow() 
    { 
     InitializeComponent(); 
     DataContext = "abcd"; 
     popup.PlacementTarget = LayoutRoot; 
    } 

Mam nadzieję, że będzie to help.Not jak w przypadku ContextMenu lub Tooltip, tutaj będzie trzeba także określić PlacementTarget.

+1

Ok. Jest to jasne w przypadku kontrolek wyskakujących okienek Czy istnieje sposób użycia źródła względnego w ComboBoxItemTemplate? –

-1

Wyskakujące okienka nie są częścią wizualnego drzewa.

Źródło względne "Pobiera lub ustawia źródło wiązania, podając jego położenie względem pozycji wiążącego celu (MSDN)". Ponieważ wyskakujące okienka nie są częścią wizualnego drzewa kontrolki, która je pokazuje, nie będzie w stanie rozwiązać niczego poza wyskakującym okienkiem.

1

Możesz dokonać małego hacka: ustaw DataContext za pomocą zasobów.

<Grid.Resources> 
    <Style TargetType="TextBlock"> 
     <Setter Property="DataContext" Value="{Binding ElementName=myGrid, Path=DataContext}" /> 
    </Style> 
</Grid.Resources> 
2

Jak wspomnieli inni, dzieje się tak, ponieważ wyskakujące okienko nie jest częścią wizualnego drzewa. Zamiast tego można użyć PlacementTarget mienia podręcznego, aby wrócić do drzewa wizualnej:

<Grid x:Name="LayoutRoot" Background="White" Height="100" Width="200"> 
    <Popup IsOpen="True"> 
     <TextBlock Text="{Binding RelativeSource={RelativeSource Mode=FindAncestor, AncestorType={x:Type Popup}}, 
            Path=PlacementTarget.DataContext}" /> 
    </Popup> 
</Grid>