Использование расширений разметки XAML
Расширения разметки XAML для многоплатформенных приложений .NET (.NET MAUI) помогают повысить мощность и гибкость XAML, позволяя задавать атрибуты элементов из различных источников.
Например, обычно вы задаете Color
свойство следующего BoxView вида:
<BoxView Color="Blue" />
Однако вместо этого можно задать Color
атрибут из значения, хранящегося в словаре ресурсов, или из значения статического свойства класса, созданного вами, или из свойства типа Color другого элемента на странице или из отдельных оттенков, насыщенности и значений светимости. Все эти параметры возможны с помощью расширений разметки XAML.
Расширение разметки отличается от способа выражения атрибута элемента. Расширения разметки XAML для .NET MAUI обычно можно определить по значению атрибута, заключенному в фигурные скобки:
<BoxView Color="{StaticResource themeColor}" />
Любое значение атрибута в фигурных скобках всегда является расширением разметки XAML. Однако расширения разметки XAML также можно ссылаться без использования фигурных скобок.
Примечание.
Несколько расширений разметки XAML являются частью спецификации XAML 2009. Они отображаются в XAML-файлах с префиксом обычного x
пространства имен и обычно называются этим префиксом.
Помимо расширений разметки, описанных в этой статье, следующие расширения разметки включены в .NET MAUI и рассматриваются в других статьях:
AppThemeBinding
— указывает ресурс, используемый на основе текущей системной темы. Дополнительные сведения см. в разделе Расширение разметки AppThemeBinding.Binding
— устанавливает связь между свойствами двух объектов. Дополнительные сведения см. в разделе "Привязка данных".DynamicResource
— реагирует на изменения объектов в словаре ресурсов. Дополнительные сведения см. в разделе "Динамические стили".FontImage
— отображает значок шрифта в любом представлении ImageSource, которое может отображаться. Дополнительные сведения см. в разделе "Загрузка значка шрифта".OnIdiom
— настраивает внешний вид пользовательского интерфейса на основе идиом устройства, на котором выполняется приложение. Дополнительные сведения см. в разделе "Настройка внешнего вида пользовательского интерфейса на основе идиома устройства".OnPlatform
— настраивает внешний вид пользовательского интерфейса на основе каждой платформы. Дополнительные сведения см. в разделе "Настройка внешнего вида пользовательского интерфейса на основе платформы".RelativeSource
— задает источник привязки относительно положения целевого объекта привязки. Дополнительные сведения см. в разделе "Относительные привязки".StaticResource
— ссылается на объекты из словаря ресурсов. Дополнительные сведения см . в словарях ресурсов.TemplateBinding
— выполняет привязку данных из шаблона элемента управления. Дополнительные сведения см. в разделе "Шаблоны элементов управления".
Расширение разметки x:Static
x:Static
Расширение разметки поддерживается классомStaticExtension. Класс имеет одно свойство с именем Member
типа string
, заданного именем общедоступной константы, статического свойства, статического поля или элемента перечисления.
Один из способов использования x:Static
— сначала определить класс с некоторыми константами или статическими переменными, такими как этот AppConstants
класс:
static class AppConstants
{
public static double NormalFontSize = 18;
}
Следующий код XAML демонстрирует наиболее подробный подход к созданию StaticExtension экземпляра класса между Label.FontSize
тегами элементов свойства:
<ContentPage xmlns="http://schemas.microsoft.com/dotnet/2021/maui"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
xmlns:sys="clr-namespace:System;assembly=netstandard"
xmlns:local="clr-namespace:MarkupExtensions"
x:Class="MarkupExtensions.StaticDemoPage"
Title="x:Static Demo">
<StackLayout Margin="10, 0">
<Label Text="Label No. 1">
<Label.FontSize>
<x:StaticExtension Member="local:AppConstants.NormalFontSize" />
</Label.FontSize>
</Label>
···
</StackLayout>
</ContentPage>
Средство синтаксического анализа XAML также позволяет StaticExtension классу быть сокращенным как x:Static
:
<Label Text="Label No. 2">
<Label.FontSize>
<x:Static Member="local:AppConstants.NormalFontSize" />
</Label.FontSize>
</Label>
Этот синтаксис можно упростить, поместив StaticExtension класс и параметр члена в фигурные скобки. Результирующее выражение устанавливается непосредственно атрибуту FontSize
:
<Label Text="Label No. 3"
FontSize="{x:StaticExtension Member=local:AppConstants.NormalFontSize}" />
В этом примере в фигурных скобках нет кавычек. Свойство Member
StaticExtension больше не является атрибутом XML. Он является частью выражения для расширения разметки.
Так же, как и при использовании его в качестве элемента объекта, его можно также сократить x:StaticExtension
x:Static
в выражении в фигурных скобках:
<Label Text="Label No. 4"
FontSize="{x:Static Member=local:AppConstants.NormalFontSize}" />
Класс StaticExtension имеет ContentProperty
атрибут, ссылающийся на свойство Member
, которое помечает это свойство как свойство содержимого по умолчанию класса. Для расширений разметки XAML, выраженных с фигурными скобками, можно исключить Member=
часть выражения:
<Label Text="Label No. 5"
FontSize="{x:Static local:AppConstants.NormalFontSize}" />
Это наиболее распространенная форма расширения разметки x:Static
.
Корневой тег примера XAML также содержит объявление пространства имен XML для пространства имен .NET System
. Это позволяет Label задать размер шрифта статическим полем Math.PI
. Это приводит к довольно маленькому тексту, поэтому Scale
для свойства задано значение Math.E
:
<Label Text="π × E sized text"
FontSize="{x:Static sys:Math.PI}"
Scale="{x:Static sys:Math.E}"
HorizontalOptions="Center" />
На следующем снимку экрана показаны выходные данные XAML:
Расширение разметки x:Reference
x:Reference
Расширение разметки поддерживается классомReferenceExtension. Класс имеет одно свойство с именем Name
типа string
, которое вы задаете имя элемента на странице с именем x:Name
. Это Name
свойство является свойством содержимого ReferenceExtension, поэтому Name=
не требуется при x:Reference
отображении в фигурных скобках. x:Reference
Расширение разметки используется исключительно с привязками данных. Дополнительные сведения о привязках данных см. в разделе "Привязка данных".
В следующем примере XAML показано два использования x:Reference
с привязками данных, первое, где оно используется для задания Source
свойства объекта, а второй — для задания BindingContext
свойства Binding
для двух привязок данных:
<ContentPage xmlns="http://schemas.microsoft.com/dotnet/2021/maui"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
x:Class="MarkupExtensions.ReferenceDemoPage"
x:Name="page"
Title="x:Reference Demo">
<StackLayout Margin="10, 0">
<Label Text="{Binding Source={x:Reference page},
StringFormat='The type of this page is {0}'}"
FontSize="18"
VerticalOptions="Center"
HorizontalTextAlignment="Center" />
<Slider x:Name="slider"
Maximum="360"
VerticalOptions="Center" />
<Label BindingContext="{x:Reference slider}"
Text="{Binding Value, StringFormat='{0:F0}° rotation'}"
Rotation="{Binding Value}"
FontSize="24"
HorizontalOptions="Center"
VerticalOptions="Center" />
</StackLayout>
</ContentPage>
В этом примере оба x:Reference
выражения используют сокращенную версию ReferenceExtension имени класса и устраняют Name=
часть выражения. В первом примере x:Reference
расширение разметки внедрено в Binding
расширение разметки, а Source
StringFormat
свойства разделяются запятыми.
На следующем снимку экрана показаны выходные данные XAML:
Расширение разметки x:Type
x:Type
Расширение разметки является эквивалентом XAML ключевое слово C# typeof
. Он поддерживается классом TypeExtension , который определяет свойство с именем TypeName
типа string
, которое должно быть присвоено имени класса или структуры. x:Type
Расширение разметки возвращает Type
объект этого класса или структуры. TypeName
— свойство содержимого TypeExtension, поэтому TypeName=
не требуется при x:Type
появлении фигурных скобок.
x:Type
Расширение разметки обычно используется с расширением x:Array
разметки. Дополнительные сведения см. в расширении разметки x:Array.
В следующем примере XAML демонстрируется использование x:Type
расширения разметки для создания экземпляров объектов .NET MAUI и их добавления в StackLayout. XAML состоит из трех Button элементов со своими Command
свойствами, равными a Binding
, и CommandParameter
свойства, заданные для типов трех представлений .NET MAUI:
<ContentPage xmlns="http://schemas.microsoft.com/dotnet/2021/maui"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
x:Class="MarkupExtensions.TypeDemoPage"
Title="x:Type Demo">
<StackLayout x:Name="stackLayout"
Padding="10, 0">
<Button Text="Create a Slider"
HorizontalOptions="Center"
VerticalOptions="Center"
Command="{Binding CreateCommand}"
CommandParameter="{x:Type Slider}" />
<Button Text="Create a Stepper"
HorizontalOptions="Center"
VerticalOptions="Center"
Command="{Binding CreateCommand}"
CommandParameter="{x:Type Stepper}" />
<Button Text="Create a Switch"
HorizontalOptions="Center"
VerticalOptions="Center"
Command="{Binding CreateCommand}"
CommandParameter="{x:Type Switch}" />
</StackLayout>
</ContentPage>
Файл программной части определяет и инициализирует CreateCommand
свойство:
public partial class TypeDemoPage : ContentPage
{
public ICommand CreateCommand { get; private set; }
public TypeDemoPage()
{
InitializeComponent();
CreateCommand = new Command<Type>((Type viewType) =>
{
View view = (View)Activator.CreateInstance(viewType);
view.VerticalOptions = LayoutOptions.Center;
stackLayout.Add(view);
});
BindingContext = this;
}
}
Button При нажатии нового экземпляра CommandParameter
аргумента создается и добавляется в нееStackLayout. Затем три Button объекта совместно используют страницу с динамически созданными представлениями:
Расширение разметки x:Array
Расширение x:Array
разметки позволяет определить массив в разметке. Он поддерживается классом ArrayExtension , который определяет два свойства:
Type
типType
, указывающий тип элементов в массиве. Это свойство должно иметь расширение разметкиx:Type
.Items
типIList
, который представляет собой коллекцию самих элементов. Это свойство содержимого ArrayExtension.
x:Array
Расширение разметки никогда не отображается в фигурных скобках. Вместо этого начальные x:Array
и конечные теги разделяют список элементов.
В следующем примере XAML показано, как добавлять x:Array
элементы в ListView массив, задав ItemsSource
свойство массиву:
<ContentPage xmlns="http://schemas.microsoft.com/dotnet/2021/maui"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
x:Class="MarkupExtensions.ArrayDemoPage"
Title="x:Array Demo Page">
<ListView Margin="10">
<ListView.ItemsSource>
<x:Array Type="{x:Type Color}">
<Color>Aqua</Color>
<Color>Black</Color>
<Color>Blue</Color>
<Color>Fuchsia</Color>
<Color>Gray</Color>
<Color>Green</Color>
<Color>Lime</Color>
<Color>Maroon</Color>
<Color>Navy</Color>
<Color>Olive</Color>
<Color>Pink</Color>
<Color>Purple</Color>
<Color>Red</Color>
<Color>Silver</Color>
<Color>Teal</Color>
<Color>White</Color>
<Color>Yellow</Color>
</x:Array>
</ListView.ItemsSource>
<ListView.ItemTemplate>
<DataTemplate>
<ViewCell>
<BoxView Color="{Binding}"
Margin="3" />
</ViewCell>
</DataTemplate>
</ListView.ItemTemplate>
</ListView>
</ContentPage>
В этом примере ViewCell создается простая BoxView для каждой записи цвета:
Примечание.
При определении массивов распространенных типов, таких как строки или числа, используйте теги языка XAML, перечисленные в аргументах Pass.
Расширение разметки x:NULL
x:Null
Расширение разметки поддерживается классомNullExtension. Он не имеет свойств и является просто эквивалентом XAML ключевое слово C# null
.
В следующем примере XAML показано, как использовать расширение разметки x:Null
:
<ContentPage xmlns="http://schemas.microsoft.com/dotnet/2021/maui"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
x:Class="MarkupExtensions.NullDemoPage"
Title="x:Null Demo">
<ContentPage.Resources>
<Style TargetType="Label">
<Setter Property="FontSize" Value="48" />
<Setter Property="FontFamily" Value="OpenSansRegular" />
</Style>
</ContentPage.Resources>
<StackLayout Padding="10, 0">
<Label Text="Text 1" />
<Label Text="Text 2" />
<Label Text="Text 3"
FontFamily="{x:Null}" />
<Label Text="Text 4" />
<Label Text="Text 5" />
</StackLayout>
</ContentPage>
В этом примере неявное Style определяется для Label этого, включающее Setter FontFamily
свойство в определенный шрифт. Однако третий Label избегает использования шрифта, определенного в неявном стиле, задав для нее значение FontFamily
x:Null
:
Расширение разметки DataTemplate
DataTemplate Расширение разметки позволяет преобразовать тип в типDataTemplate. Он поддерживается классомDataTemplateExtension, который определяет TypeName
свойство типаstring
, которое присваивается имени типа, преобразованного в .DataTemplate Свойство TypeName
является свойством содержимого DataTemplateExtension. Таким образом, для выражений разметки XAML с фигурными скобками можно исключить часть TypeName=
выражения.
Примечание.
Средство синтаксического анализа XAML позволяет сократить класс DataTemplateExtension как DataTemplate.
Обычное использование этого расширения разметки в приложении Shell, как показано в следующем примере:
<ShellContent Title="Monkeys"
Icon="monkey.png"
ContentTemplate="{DataTemplate views:MonkeysPage}" />
В этом примере MonkeysPage
преобразуется из объекта в ContentPage объект DataTemplate, который задается в качестве значения ShellContent.ContentTemplate
свойства. Это гарантирует, что MonkeysPage
создается только при переходе на страницу, а не при запуске приложения.
Дополнительные сведения о приложениях Оболочки см. в разделе Shell.