Přizpůsobení prvku ContentPage
ContentPage je vizuální prvek, který zobrazuje jedno zobrazení a zabírá většinu obrazovky. Tento článek ukazuje, jak vytvořit vlastní renderer pro stránku ContentPage, což vývojářům umožňuje přepsat výchozí nativní vykreslování vlastním vlastním přizpůsobením specifické pro platformu.
Každý Xamarin.Forms ovládací prvek má doprovodný renderer pro každou platformu, která vytvoří instanci nativního ovládacího prvku. ContentPage
Při vykreslení Xamarin.Forms aplikací se v iOSu PageRenderer
vytvoří instance třídy, která následně vytvoří instanci nativního UIViewController
ovládacího prvku. Na platformě Android třída PageRenderer
vytvoří ViewGroup
instanci ovládacího prvku. Na Univerzální platforma Windows (UPW) třída PageRenderer
vytvoří FrameworkElement
instanci ovládacího prvku. Další informace o rendereru a nativních tříd ovládacích prvcích, které Xamarin.Forms řídí mapování, naleznete v tématu Renderer Základní třídy a nativní ovládací prvky.
Následující diagram znázorňuje vztah mezi ContentPage
a odpovídajícími nativními ovládacími prvky, které ho implementují:
Proces vykreslování můžete využít k implementaci přizpůsobení specifických pro platformu vytvořením vlastního rendereru pro každou platformu ContentPage
. Postup je následující:
- Vytvořte Xamarin.Forms stránku.
- Využití stránky z Xamarin.Forms.
- Vytvořte vlastní renderer pro stránku na každé platformě.
Každá položka se teď bude probírat a implementovat CameraPage
tak živý kanál fotoaparátu a možnost zachytit fotku.
Xamarin.Forms Vytvoření stránky
Do sdíleného Xamarin.Forms projektu lze přidat nealterovaný ContentPage
objekt, jak je znázorněno v následujícím příkladu kódu XAML:
<ContentPage xmlns="http://xamarin.com/schemas/2014/forms"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
x:Class="CustomRenderer.CameraPage">
<ContentPage.Content>
</ContentPage.Content>
</ContentPage>
Podobně by měl soubor kódu pro soubor, který je za kódem ContentPage
, zůstat nezměněný, jak je znázorněno v následujícím příkladu kódu:
public partial class CameraPage : ContentPage
{
public CameraPage ()
{
// A custom renderer is used to display the camera UI
InitializeComponent ();
}
}
Následující příklad kódu ukazuje, jak lze stránku vytvořit v jazyce C#:
public class CameraPageCS : ContentPage
{
public CameraPageCS ()
{
}
}
Instance bude použita k zobrazení živého CameraPage
kanálu kamery na každé platformě. Přizpůsobení ovládacího prvku se provede ve vlastním rendereru, takže ve CameraPage
třídě není nutná žádná další implementace.
Xamarin.Forms Využívání stránky
Aplikace musí zobrazit prázdnou CameraPage
Xamarin.Forms . K tomu dochází při klepnutí na tlačítko na MainPage
instanci, které následně spustí metodu OnTakePhotoButtonClicked
, jak je znázorněno v následujícím příkladu kódu:
async void OnTakePhotoButtonClicked (object sender, EventArgs e)
{
await Navigation.PushAsync (new CameraPage ());
}
Tento kód jednoduše přejde na CameraPage
, na kterém vlastní renderery přizpůsobí vzhled stránky na každé platformě.
Vytvoření rendereru stránky na jednotlivých platformách
Proces vytvoření vlastní třídy rendereru je následující:
- Vytvořte podtřídu
PageRenderer
třídy. - Přepište metodu
OnElementChanged
, která vykreslí nativní stránku a logiku zápisu pro přizpůsobení stránky. MetodaOnElementChanged
je volána při vytvoření odpovídajícího Xamarin.Forms ovládacího prvku. ExportRenderer
Přidejte atribut do třídy vykreslovacího modulu stránky a určete, že se použije k vykreslení Xamarin.Forms stránky. Tento atribut se používá k registraci vlastního rendereru v Xamarin.Forms.
Poznámka:
V každém projektu platformy je volitelné zadat vykreslovací modul stránky. Pokud není vykreslení stránky zaregistrované, použije se výchozí vykreslovací modul pro stránku.
Následující diagram znázorňuje zodpovědnosti jednotlivých projektů v ukázkové aplikaci spolu s vztahem mezi nimi:
Instance CameraPage
je vykreslena třídami specifickými pro CameraPageRenderer
platformu, které jsou odvozeny od PageRenderer
třídy pro danou platformu. Výsledkem je vykreslení každé CameraPage
instance s živým kanálem fotoaparátu, jak je znázorněno na následujících snímcích obrazovky:
PageRenderer
Třída zveřejňuje metoduOnElementChanged
, která je volána při Xamarin.Forms vytvoření stránky pro vykreslení odpovídajícího nativního ovládacího prvku. Tato metoda přebírá ElementChangedEventArgs
parametr, který obsahuje OldElement
a NewElement
vlastnosti. Tyto vlastnosti představují Xamarin.Forms prvek, ke kterému byl renderer připojen, a Xamarin.Forms prvek, ke kterému je renderer připojen, v uvedeném pořadí. V ukázkové aplikaci OldElement
bude vlastnost a NewElement
vlastnost bude obsahovat odkaz na CameraPage
null
instanci.
Přepsáná verze OnElementChanged
metody ve CameraPageRenderer
třídě je místo pro provedení přizpůsobení nativní stránky. Odkaz na Xamarin.Forms instanci stránky, která se vykresluje, lze získat prostřednictvím Element
vlastnosti.
Každá vlastní třída rendereru je zdobena ExportRenderer
atributem, který registruje renderer s Xamarin.Forms. Atribut má dva parametry – název Xamarin.Forms typu vykreslené stránky a název typu vlastního rendereru. Předpona assembly
atributu určuje, že atribut se vztahuje na celé sestavení.
Následující části popisuje implementaci vlastního rendereru CameraPageRenderer
pro každou platformu.
Vytvoření rendereru stránky v iOSu
Následující příklad kódu ukazuje renderer stránky pro platformu iOS:
[assembly:ExportRenderer (typeof(CameraPage), typeof(CameraPageRenderer))]
namespace CustomRenderer.iOS
{
public class CameraPageRenderer : PageRenderer
{
...
protected override void OnElementChanged (VisualElementChangedEventArgs e)
{
base.OnElementChanged (e);
if (e.OldElement != null || Element == null) {
return;
}
try {
SetupUserInterface ();
SetupEventHandlers ();
SetupLiveCameraStream ();
AuthorizeCameraUse ();
} catch (Exception ex) {
System.Diagnostics.Debug.WriteLine (@" ERROR: ", ex.Message);
}
}
...
}
}
Volání metody základní třídy OnElementChanged
vytvoří instanci ovládacího prvku iOS UIViewController
. Stream živé kamery se vykresluje pouze za předpokladu, že renderer ještě není připojený k existujícímu Xamarin.Forms prvku, a za předpokladu, že existuje instance stránky, kterou vykresluje vlastní renderer.
Stránka se pak přizpůsobí řadou metod, které pomocí AVCapture
rozhraní API poskytují živý stream z fotoaparátu a schopnost zachytit fotku.
Vytvoření rendereru stránky v Androidu
Následující příklad kódu ukazuje renderer stránky pro platformu Android:
[assembly: ExportRenderer(typeof(CameraPage), typeof(CameraPageRenderer))]
namespace CustomRenderer.Droid
{
public class CameraPageRenderer : PageRenderer, TextureView.ISurfaceTextureListener
{
...
public CameraPageRenderer(Context context) : base(context)
{
}
protected override void OnElementChanged(ElementChangedEventArgs<Page> e)
{
base.OnElementChanged(e);
if (e.OldElement != null || Element == null)
{
return;
}
try
{
SetupUserInterface();
SetupEventHandlers();
AddView(view);
}
catch (Exception ex)
{
System.Diagnostics.Debug.WriteLine(@" ERROR: ", ex.Message);
}
}
...
}
}
Volání metody základní třídy OnElementChanged
vytvoří instanci ovládacího prvku Android ViewGroup
, což je skupina zobrazení. Stream živé kamery se vykresluje pouze za předpokladu, že renderer ještě není připojený k existujícímu Xamarin.Forms prvku, a za předpokladu, že existuje instance stránky, kterou vykresluje vlastní renderer.
Stránka se pak přizpůsobí vyvoláním řady metod, které používají Camera
rozhraní API k poskytování živého streamu z fotoaparátu a schopnost zachytit fotku před AddView
vyvoláním metody přidání uživatelského rozhraní živého streamu fotoaparátu do ViewGroup
rozhraní . Všimněte si, že v Androidu je také nutné přepsat metodu OnLayout
pro provádění operací měření a rozložení v zobrazení.
Vytvoření rendereru stránky v UPW
Následující příklad kódu ukazuje vykreslovací modul stránky pro UPW:
[assembly: ExportRenderer(typeof(CameraPage), typeof(CameraPageRenderer))]
namespace CustomRenderer.UWP
{
public class CameraPageRenderer : PageRenderer
{
...
protected override void OnElementChanged(ElementChangedEventArgs<Xamarin.Forms.Page> e)
{
base.OnElementChanged(e);
if (e.OldElement != null || Element == null)
{
return;
}
try
{
...
SetupUserInterface();
SetupBasedOnStateAsync();
this.Children.Add(page);
}
...
}
protected override Size ArrangeOverride(Size finalSize)
{
page.Arrange(new Windows.Foundation.Rect(0, 0, finalSize.Width, finalSize.Height));
return finalSize;
}
...
}
}
Volání metody základní třídy OnElementChanged
vytvoří FrameworkElement
instanci ovládacího prvku, na kterém je stránka vykreslena. Stream živé kamery se vykresluje pouze za předpokladu, že renderer ještě není připojený k existujícímu Xamarin.Forms prvku, a za předpokladu, že existuje instance stránky, kterou vykresluje vlastní renderer. Stránka se pak přizpůsobí vyvoláním řady metod, které používají MediaCapture
rozhraní API k poskytnutí živého streamu z fotoaparátu a možnosti zachytit fotku před přidáním přizpůsobené stránky do Children
kolekce pro zobrazení.
Při implementaci vlastního rendereru, který je odvozen z PageRenderer
UPW, ArrangeOverride
by se měla také implementovat metoda pro uspořádání ovládacích prvků stránky, protože základní renderer neví, co s nimi dělat. V opačném případě se zobrazí prázdné výsledky stránky. Proto v tomto příkladu ArrangeOverride
metoda volá metodu Arrange
v Page
instanci.
Poznámka:
Je důležité zastavit a odstranit objekty, které poskytují přístup ke kameře v aplikaci pro UPW. Pokud to neuděláte, může kolidovat s jinými aplikacemi, které se pokusí o přístup ke kameře zařízení. Další informace najdete v tématu Zobrazení náhledu fotoaparátu.
Shrnutí
Tento článek ukazuje, jak vytvořit vlastní vykreslovací modul pro ContentPage
stránku, který vývojářům umožňuje přepsat výchozí nativní vykreslování vlastními vlastními přizpůsobeními pro konkrétní platformu. A ContentPage
je vizuální prvek, který zobrazuje jedno zobrazení a zabírá většinu obrazovky.