XAML マークアップ拡張の作成
開発者レベルでは、.NET マルチプラットフォーム アプリ UI (.NET MAUI) XAML マークアップ拡張は、IMarkupExtension<T> または IMarkupExtension インターフェイスを実装するクラスです。 IMarkupExtension または IMarkupExtension<T> から独自のカスタム XAML マークアップ拡張を定義することもできます。 マークアップ拡張機能が特定の型の値を取得する場合は、ジェネリック フォームを使用します。 これは、複数の .NET MAUI マークアップ拡張機能がある場合です。
TypeExtension
は、IMarkupExtension<Type>
から派生しますArrayExtension
は、IMarkupExtension<Array>
から派生しますDynamicResourceExtension
は、IMarkupExtension<DynamicResource>
から派生しますBindingExtension
は、IMarkupExtension<BindingBase>
から派生します
IMarkupExtension または IMarkupExtension<T> を実装するすべてのクラスには、RequireServiceAttribute または AcceptEmptyServiceProviderAttribute で注釈を付ける必要があります。 詳細については、「サービス プロバイダー」をご覧ください。
2 つの IMarkupExtension インターフェイスは、ProvideValue
という名前のそれぞれ 1 つのメソッドのみを定義します。
public interface IMarkupExtension
{
object ProvideValue(IServiceProvider serviceProvider);
}
public interface IMarkupExtension<out T> : IMarkupExtension
{
new T ProvideValue(IServiceProvider serviceProvider);
}
IMarkupExtension<T> は IMarkupExtension から派生し、ProvideValue
の new
キーワードが含まれているので、両方の ProvideValue
メソッドが含まれます。
多くの場合、XAML マークアップ拡張は戻り値に寄与するプロパティを定義し、 ProvideValue
メソッドには IServiceProvider
型の 1 つの引数があります。 サービス プロバイダーの詳細については、「サービス プロバイダー」を参照してください。
マークアップ拡張を作成する
次の XAML マークアップ拡張機能は、独自のマークアップ拡張を作成する方法を示しています。 これにより、色相、彩度、および光度の各コンポーネントを使用して Color 値を構築できます。 これは、色の 4 つのコンポーネントの 4 つのプロパティを定義します。1 に初期化されるアルファ コンポーネントも含まれます。 このクラスは、IMarkupExtension<Color>
から派生し、Color 戻り値を示します。
public class HslColorExtension : IMarkupExtension<Color>
{
public float H { get; set; }
public float S { get; set; }
public float L { get; set; }
public float A { get; set; } = 1.0f;
public Color ProvideValue(IServiceProvider serviceProvider)
{
return Color.FromHsla(H, S, L, A);
}
object IMarkupExtension.ProvideValue(IServiceProvider serviceProvider)
{
return (this as IMarkupExtension<Color>).ProvideValue(serviceProvider);
}
}
[AcceptEmptyServiceProvider]
public class HslColorExtension : IMarkupExtension<Color>
{
public float H { get; set; }
public float S { get; set; }
public float L { get; set; }
public float A { get; set; } = 1.0f;
public Color ProvideValue(IServiceProvider serviceProvider)
{
return Color.FromHsla(H, S, L, A);
}
object IMarkupExtension.ProvideValue(IServiceProvider serviceProvider)
{
return (this as IMarkupExtension<Color>).ProvideValue(serviceProvider);
}
}
このマークアップ拡張機能は、サービス プロバイダーからのサービスを使用しないため、AcceptEmptyServiceProviderAttribute で注釈を付けられます。 詳細については、「サービス プロバイダー」をご覧ください。
IMarkupExtension<T> は IMarkupExtension から派生するため、クラスには 2 つの ProvideValue
メソッドを含める必要があります。1 つは Color を返し、もう 1 つは object
を返しますが、2 番目のメソッドは最初のメソッドを呼び出すことができます。
マークアップ拡張を使用する
次の XAML は、BoxView の色を指定するために HslColorExtension
の呼び出しで使用できるさまざまな方法を示しています。
<ContentPage xmlns="http://schemas.microsoft.com/dotnet/2021/maui"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
xmlns:local="clr-namespace:MarkupExtensions"
x:Class="MarkupExtensions.HslColorDemoPage"
Title="HSL Color Demo">
<ContentPage.Resources>
<Style TargetType="BoxView">
<Setter Property="WidthRequest" Value="80" />
<Setter Property="HeightRequest" Value="80" />
<Setter Property="HorizontalOptions" Value="Center" />
<Setter Property="VerticalOptions" Value="Center" />
</Style>
</ContentPage.Resources>
<StackLayout>
<BoxView>
<BoxView.Color>
<local:HslColorExtension H="0" S="1" L="0.5" A="1" />
</BoxView.Color>
</BoxView>
<BoxView>
<BoxView.Color>
<local:HslColor H="0.33" S="1" L="0.5" />
</BoxView.Color>
</BoxView>
<BoxView Color="{local:HslColorExtension H=0.67, S=1, L=0.5}" />
<BoxView Color="{local:HslColor H=0, S=0, L=0.5}" />
<BoxView Color="{local:HslColor A=0.5}" />
</StackLayout>
</ContentPage>
この例では、HslColorExtension
が XML タグで、4 つのプロパティが属性として設定されているものの、中かっこの間に表示される場合、4 つのプロパティは引用符なしでコンマで区切られます。 H
の既定値は S
、L
は 0、A
は 1 なので、既定値に設定する場合は、これらのプロパティを省略できます。 最後の例では、光度が 0 で、通常は黒になりますが、アルファ チャネルが 0.5 なので半分透明になり、ページの白い背景に対して灰色で表示されています。
サービス プロバイダー
IServiceProvider
引数を ProvideValue
に対して使用すると、XAML マークアップ拡張機能は、使用されている XAML ファイルに関するデータにアクセスできるようになります。 たとえば、IProvideValueTarget
サービスを使用すると、マークアップ拡張機能が適用されているオブジェクトに関するデータを取得できます。
IProvideValueTarget provideValueTarget = serviceProvider.GetService(typeof(IProvideValueTarget)) as IProvideValueTarget;
IProvideValueTarget
インターフェイスは 2 つのプロパティ、TargetObject
と TargetProperty
を定義します。 この情報が HslColorExtension
クラスで取得される場合、TargetObject
は BoxView で、TargetProperty
は BoxView のColor
プロパティです。 これは、XAML マークアップ拡張機能が設定されているプロパティです。
IMarkupExtension または IMarkupExtension<T> を実装するすべてのクラスには、RequireServiceAttribute または AcceptEmptyServiceProviderAttribute で注釈を付ける必要があります。
ProvideValue
メソッドでserviceProvider.GetService(typeof(T))
を使用するたびに、クラスに[RequireService(typeof(T))]
で注釈を付ける必要があります。[RequireService([typeof(IReferenceProvider), typeof(IProvideValueTarget)])] public class MyMarkupExtension : IMarkupExtension { public object ProvideValue(IServiceProvider serviceProvider) { ... var referenceProvider = serviceProvider.GetService<IReferenceProvider>(); var valueProvider = serviceProvider.GetService<IProvideValueTarget>() as IProvideParentValues ?? throw new ArgumentException("serviceProvider does not provide an IProvideValueTarget"); ... } }
マークアップ拡張機能でサービス プロバイダーのサービスが使用されていない場合は、クラスに
[AcceptEmptyServiceProvider]
で注釈を付ける必要があります。
これらの注釈は、より効率的なコードの生成を可能にする XAML コンパイラを最適化するために必要です。これにより、アプリのサイズを小さくし、実行時のパフォーマンスを向上させることができます。
.NET MAUI