2015-09-15 15 views
5

spędziłem lepsze od pół dnia próbując dokonać ItemTemplate o ListView z UserControl konfigurowalny za pomocą środków o charakterze DependencyProperty na wspomnianej UserControl . Natknąłem się na kilka dziwnych niespójności dotyczących dwóch różnych metod dostępnych na platformie Windows 10 UAP (Binding i x:Bind).Wiązanie vs. x: Bind, używając StaticResource jako domyślne i ich różnice w DataContext

Wygląda to tak: jest to część niestandardowego komponentu kalendarza.

<UserControl 
    x:Class="FlowDesigner.UserControls.CalendarDayView" 
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
    xmlns:local="using:FlowDesigner.UserControls" 
    xmlns:vw="using:FlowDesigner.ViewModels" 
    xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
    xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
    xmlns:uc="using:FlowDesigner.UserControls" 
    mc:Ignorable="d" 
    d:DesignHeight="300" 
    d:DesignWidth="400" 
    x:Name="DateControl"> 
    <UserControl.Resources> 
     <DataTemplate x:Key="DefaultDataTemplate" x:DataType="vw:Event" > 
      <uc:EventListTemplate IsToday="{Binding Date, Converter={StaticResource IsTodayConverter}}" 
           Date="{Binding Date, Mode=OneWay}" 
           Summary="{Binding Path=Summary, Mode=OneWay}" /> 
     </DataTemplate> 
    </UserControl.Resources> 
    <RelativePanel Background="White" BorderBrush="Black" BorderThickness="1" DataContext="{Binding ElementName=DateControl}"> 
     <TextBlock x:Name="DayText" TextAlignment="Center" VerticalAlignment="Center" /> 
     <TextBlock x:Name="MonthText" TextAlignment="Center" VerticalAlignment="Center" RelativePanel.RightOf="DayText" /> 
     <ListView x:Name="EventList" ItemsSource="{x:Bind Events, Mode=OneWay}" 
       ItemTemplate="{Binding Path=EventItemTemplate, Mode=OneWay, FallbackValue={StaticResource DefaultDataTemplate}, TargetNullValue={StaticResource DefaultDataTemplate}}" 
       RelativePanel.Below="DayText" RelativePanel.AlignLeftWithPanel="True" RelativePanel.AlignRightWithPanel="True"> 

     </ListView> 
    </RelativePanel> 
</UserControl> 

EventItemTemplate jest DependencyProperty z UserControl.

public DataTemplate EventItemTemplate 
{ 
    get { return (DataTemplate)GetValue(EventItemTemplateProperty); } 
    set { SetValue(EventItemTemplateProperty, value); } 
} 

public static readonly DependencyProperty EventItemTemplateProperty = 
     DependencyProperty.Register("EventItemTemplate", typeof(DataTemplate), typeof(CalendarDayView), new PropertyMetadata(null)); 

który został zmieniony na jednej ze stron głównych stylizowania się ListView w taki czy inny, jak tak.

<Style TargetType="uc:CalendarDayView"> 
    <Setter Property="EventItemTemplate"> 
     <Setter.Value> 
      <DataTemplate x:DataType="vw:Event" > 
       <TextBlock Text="{Binding Summary, Mode=OneWay}" /> 
      </DataTemplate> 
     </Setter.Value> 
    </Setter> 
</Style> 

To jest faktycznie działająca wersja, ale musiałem trochę nią majstrować. Pierwsze próby zostały wykonane przeze mnie z x:Bind i Binding i bez DataContext na RelativePanel jako jest teraz. x:Bind byłby użyteczny podczas ustawiania wartości na EventItemTemplate na stronie głównej, ale nie byłby w stanie użyć domyślnej wartości DataTemplate określonej przez StaticResource, gdy strona główna nic nie określiła. Binding z drugiej strony używałby domyślnie DataTemplate przez cały czas, nawet jeśli strona główna miała zestaw innej wartości niż EventItemTemplate.

Ustawienie DataContext na RelativePanel na UserControl zaczęło działać tak, jak chciał tego również. x:Bind nadal pokazuje to samo zachowanie.

Teraz rozumiem, że Binding nie domyślnie wiążą się z UserControl „s DataContext, ale nadal nie jestem do końca pewien, dlaczego x:Bind nie działa. Czy to zamierzone zachowanie, czy też jest coś nie tak z moim całym planem i czy wymyśliłem tylko szczęśliwy hack?

Odpowiedz

8

Od {x:Bind} markup extension:

Opcja {x: Bind} markup przedłużenie nowe dla Windows 10 jest alternatywą dla {Binding}. {x: Bind} nie ma niektórych funkcji {Binding}, ale działa w krótszym czasie i mniej pamięci niż {Binding} i obsługuje lepsze debugowanie.

W czasie ładowania XAML, {x: Bind} jest konwertowany na coś, co można uznać za obiekt wiążący, a ten obiekt otrzymuje wartość z właściwości w źródle danych. Obiekt wiążący może być opcjonalnie skonfigurowany do obserwowania zmian wartości właściwości źródła danych i odświeżania na podstawie tych zmian. Opcjonalnie może być skonfigurowany do przesyłania zmian we własnej wartości z powrotem do właściwości źródłowej. Obiekty wiązania utworzone przez {x: Bind} i {Binding} są w dużej mierze równoważne funkcjonalnie. Ale {x: Bind} wykonuje kod specjalnego przeznaczenia, który generuje podczas kompilacji, a {Binding} używa inspekcji obiektów środowiska wykonawczego ogólnego przeznaczenia. W konsekwencji wiązania {x: Bind} (często nazywane połączonymi kompilacjami) mają dużą wydajność, zapewniają sprawdzanie poprawności wyrażeń wiążących w czasie kompilacji oraz obsługują debugowanie, umożliwiając ustawianie punktów przerwań w plikach kodowych generowanych jako częściowe. klasa dla twojej strony.Pliki te można znaleźć w folderze obj, o nazwach takich jak (dla C#) .g.cs.