Visualizzazione segmentata del bitmap di SkiaSharpSegmented display of SkiaSharp bitmaps

Scaricare l'esempio scaricare l'esempioDownload Sample Download the sample

Di SkiaSharp SKCanvas oggetto definisce un metodo denominato DrawBitmapNinePatch e due metodi denominati DrawBitmapLattice che sono molto simili.The SkiaSharp SKCanvas object defines a method named DrawBitmapNinePatch and two methods named DrawBitmapLattice that are very similar. Entrambi questi metodi eseguire il rendering di una bitmap per le dimensioni di un rettangolo di destinazione, ma invece di adattamento della bitmap in modo uniforme, visualizzare parti della bitmap in relative dimensioni in pixel e stretch altre parti della bitmap in modo che quest'ultima rientri il rettangolo:Both these methods render a bitmap to the size of a destination rectangle, but instead of stretching the bitmap uniformly, they display portions of the bitmap in its pixel dimensions and stretch other parts of the bitmap so that it fits the rectangle:

Segmentato campioniSegmented Samples

Questi metodi vengono in genere usati per il rendering di bitmap che fanno parte di oggetti dell'interfaccia utente, ad esempio i pulsanti.These methods are generally used for rendering bitmaps that form part of user-interface objects such as buttons. Quando si progetta un pulsante, in generale è consigliabile la dimensione di un pulsante deve essere basato sul contenuto del pulsante, ma è preferibile il bordo del pulsante per la stessa larghezza indipendentemente dal contenuto del pulsante.When designing a button, generally you want the size of a button to be based on the content of the button, but you probably want the button's border to be the same width regardless of the button's content. Che è un'applicazione ideale di DrawBitmapNinePatch.That's an ideal application of DrawBitmapNinePatch.

DrawBitmapNinePatch è un caso speciale di DrawBitmapLattice ma è il modo più semplice dei due metodi da utilizzare e comprendere.DrawBitmapNinePatch is a special case of DrawBitmapLattice but it is the easier of the two methods to use and understand.

La visualizzazione di nove-patchThe nine-patch display

Concettualmente DrawBitmapNinePatch divide una bitmap in nove rettangoli:Conceptually, DrawBitmapNinePatch divides a bitmap into nine rectangles:

Patch di noveNine Patch

I rettangoli nei quattro angoli vengono visualizzati nelle relative dimensioni in pixel.The rectangles at the four corners are displayed in their pixel sizes. Come le frecce indicano, le altre aree sui bordi della bitmap vengono allungate orizzontalmente o verticalmente all'area del rettangolo di destinazione.As the arrows indicate, the other areas on the edges of the bitmap are stretched horizontally or vertically to the area of the destination rectangle. Il rettangolo al centro è esteso sia orizzontalmente che verticalmente.The rectangle in the center is stretched both horizontally and vertically.

Se non vi è spazio sufficiente nel rettangolo di destinazione per visualizzare anche i quattro angoli nelle dimensioni in pixel, sono stati ridotti per le dimensioni disponibili e nothing ma vengono visualizzati i quattro angoli.If there is not enough space in the destination rectangle to display even the four corners in their pixel dimensions, then they are scaled down to the available size and nothing but the four corners are displayed.

Per dividere una bitmap in questi nove rettangoli, è necessario solo specificare il rettangolo al centro.To divide a bitmap into these nine rectangles, it is only necessary to specify the rectangle in the center. Questa è la sintassi del DrawBitmapNinePatch metodo:This is the syntax of the DrawBitmapNinePatch method:

canvas.DrawBitmapNinePatch(bitmap, centerRectangle, destRectangle, paint);

Il rettangolo centrale è relativo alla bitmap.The center rectangle is relative to the bitmap. Si tratta di un' SKRectI valore (la versione di numero intero di SKRect) e tutte le coordinate e le dimensioni sono espressi in unità di pixel.It is an SKRectI value (the integer version of SKRect) and all the coordinates and sizes are in units of pixels. Il rettangolo di destinazione è relativo alla superficie di visualizzazione.The destination rectangle is relative to the display surface. L'argomento paint è facoltativo.The paint argument is optional.

Il nove Patch Display nella pagina il SkiaSharpFormsDemos esempio Usa prima di tutto un costruttore statico per creare una proprietà statica pubblica di tipo SKBitmap:The Nine Patch Display page in the SkiaSharpFormsDemos sample first uses a static constructor to create a public static property of type SKBitmap:

public partial class NinePatchDisplayPage : ContentPage
{
    static NinePatchDisplayPage()
    {
        using (SKCanvas canvas = new SKCanvas(FiveByFiveBitmap))
        using (SKPaint paint = new SKPaint
        {
            Style = SKPaintStyle.Stroke,
            Color = SKColors.Red,
            StrokeWidth = 10
        })
        {
            for (int x = 50; x < 500; x += 100)
                for (int y = 50; y < 500; y += 100)
                {
                    canvas.DrawCircle(x, y, 40, paint);
                }
        }
    }

    public static SKBitmap FiveByFiveBitmap { get; } = new SKBitmap(500, 500);
    ···
}

Due altre pagine in questo articolo usano la stessa bitmap.Two other pages in this article use that same bitmap. La bitmap è 500 pixel quadrati ed è costituito da una matrice di 25 cerchi, le stesse dimensioni, ogni che occupa un'area di quadrati di 100 pixel:The bitmap is 500 pixels square, and consists of an array of 25 circles, all the same size, each occupying a 100-pixel square area:

Cerchio grigliaCircle Grid

Costruttore di istanza del programma crea un' SKCanvasView con un PaintSurface gestore che usa DrawBitmapNinePatch per visualizzare la bitmap allungata sulla sua superficie schermo intero:The program's instance constructor creates an SKCanvasView with a PaintSurface handler that uses DrawBitmapNinePatch to display the bitmap stretched to its entire display surface:

public class NinePatchDisplayPage : ContentPage
{
    ···
    public NinePatchDisplayPage()
    {
        Title = "Nine-Patch Display";

        SKCanvasView canvasView = new SKCanvasView();
        canvasView.PaintSurface += OnCanvasViewPaintSurface;
        Content = canvasView;
    }

    void OnCanvasViewPaintSurface(object sender, SKPaintSurfaceEventArgs args)
    {
        SKImageInfo info = args.Info;
        SKSurface surface = args.Surface;
        SKCanvas canvas = surface.Canvas;

        canvas.Clear();

        SKRectI centerRect = new SKRectI(100, 100, 400, 400);
        canvas.DrawBitmapNinePatch(FiveByFiveBitmap, centerRect, info.Rect);
    }
}

Il centerRect rettangolo comprende la matrice centrale dei 16 cerchi.The centerRect rectangle encompasses the central array of 16 circles. I cerchi negli angoli vengono visualizzati nelle dimensioni in pixel e tutto il resto viene adattata conseguenza:The circles in the corners are displayed in their pixel dimensions, and everything else is stretched accordingly:

Visualizzazione di nove-PatchNine-Patch Display

La pagina UWP è 500 pixel di larghezza e pertanto vengono visualizzate le righe superiore e inferiore come una serie di cerchi le stesse dimensioni.The UWP page happens to be 500 pixels wide, and hence displays the top and bottom rows as a series of circles of the same size. In caso contrario, tutti i cerchi che non sono presenti negli angoli vengono adattati in ellissi form.Otherwise, all the circles that are not in the corners are stretched to form ellipses.

Per una visualizzazione strano di oggetti costituiti da una combinazione di cerchi e sui puntini di sospensione, provare a eseguire che definisce il rettangolo di center in modo che si sovrappone a righe e colonne di cerchi:For a strange display of objects consisting of a combination of circles and ellipses, try defining the center rectangle so that it overlaps rows and columns of circles:

SKRectI centerRect = new SKRectI(150, 150, 350, 350);

La visualizzazione reticoloThe lattice display

I due DrawBitmapLattice metodi sono simili a DrawBitmapNinePatch, ma sono generalizzati per qualsiasi numero di divisioni orizzontali o verticali.The two DrawBitmapLattice methods are similar to DrawBitmapNinePatch, but they are generalized for any number of horizontal or vertical divisions. Queste divisioni sono definite da matrici di interi corrispondenti a pixel.These divisions are defined by arrays of integers corresponding to pixels.

Il DrawBitmapLattice metodo con parametri per le matrici di interi non sembra funzionare.The DrawBitmapLattice method with parameters for these arrays of integers does not seem to work. Il DrawBitmapLattice metodo con un parametro di tipo SKLattice funziona, e che corrisponde a quella usata negli esempi illustrati di seguito.The DrawBitmapLattice method with a parameter of type SKLattice does work, and that's the one used in the samples shown below.

Il SKLattice struttura definisce quattro proprietà:The SKLattice structure defines four properties:

  • XDivs, una matrice di interiXDivs, an array of integers
  • YDivs, una matrice di interiYDivs, an array of integers
  • Flags, una matrice di SKLatticeFlags, un tipo di enumerazioneFlags, an array of SKLatticeFlags, an enumeration type
  • Bounds di tipo Nullable<SKRectI> per specificare un rettangolo di origine facoltativa della bitmapBounds of type Nullable<SKRectI> to specify an optional source rectangle within the bitmap

Il XDivs matrice divide la larghezza della bitmap in strisce verticali.The XDivs array divides the width of the bitmap into vertical strips. La prima striscia si estende dal pixel da 0 a sinistra per XDivs[0].The first strip extends from pixel 0 at the left to XDivs[0]. Questo elenco viene visualizzato in larghezza in pixel.This strip is rendered in its pixel width. Elenco di secondo compreso tra XDivs[0] a XDivs[1]e viene ridimensionato.The second strip extends from XDivs[0] to XDivs[1], and is stretched. Il terzo elenco compreso tra XDivs[1] a XDivs[2] e viene eseguito il rendering nella relativa larghezza in pixel.The third strip extends from XDivs[1] to XDivs[2] and is rendered in its pixel width. Striscia di ultima compreso tra l'ultimo elemento della matrice e il bordo destro della bitmap.The last strip extends from the last element of the array to the right edge of the bitmap. Se la matrice ha un numero pari di elementi, viene visualizzato nel relativo larghezza in pixel.If the array has an even number of elements, then it's displayed in its pixel width. In caso contrario, viene estesa.Otherwise, it's stretched. Il numero totale di Sfoglia verticale è una maggiore del numero di elementi nella matrice.The total number of vertical strips is one more than the number of elements in the array.

Il YDivs matrice è simile.The YDivs array is similar. Divide l'altezza della matrice in strisce orizzontali.It divides the height of the array into horizontal strips.

Insieme, il XDivs e YDivs matrice consentono di dividere la bitmap in rettangoli.Together, the XDivs and YDivs array divide the bitmap into rectangles. Il numero di rettangoli è uguale al prodotto del numero di strisce orizzontali e il numero di strisce verticali.The number of rectangles is equal to the product of the number of horizontal strips and the number of vertical strips.

In base alla documentazione, Skia il Flags matrice contiene un elemento per ogni rettangolo, prima di tutto la riga superiore dei rettangoli, quindi la seconda riga e così via.According to Skia documentation, the Flags array contains one element for each rectangle, first the top row of rectangles, then the second row, and so forth. Il Flags matrice è di tipo SKLatticeFlags , un'enumerazione con i membri seguenti:The Flags array is of type SKLatticeFlags, an enumeration with the following members:

  • Default con il valore 0Default with value 0
  • Transparent con valore 1Transparent with value 1

Tuttavia, questi flag non sembrano funzionare come che sono autorizzati a e si consiglia di ignorarli.However, these flags don't seem to work as they are supposed to, and it's best to ignore them. Ma non vengono impostate le Flags proprietà null.But don't set the Flags property to null. Impostarla su una matrice di SKLatticeFlags valori sufficientemente ampio da contenere il numero totale di rettangoli.Set it to an array of SKLatticeFlags values large enough to encompass the total number of rectangles.

Il reticolo nove Patch pagina Usa DrawBitmapLattice simulare DrawBitmapNinePatch.The Lattice Nine Patch page uses DrawBitmapLattice to mimic DrawBitmapNinePatch. Usa la stessa bitmap creata in NinePatchDisplayPage:It uses the same bitmap created in NinePatchDisplayPage:

public class LatticeNinePatchPage : ContentPage
{
    SKBitmap bitmap = NinePatchDisplayPage.FiveByFiveBitmap;

    public LatticeNinePatchPage ()
    {
        Title = "Lattice Nine-Patch";

        SKCanvasView canvasView = new SKCanvasView();
        canvasView.PaintSurface += OnCanvasViewPaintSurface;
        Content = canvasView;
    }
    `
    void OnCanvasViewPaintSurface(object sender, SKPaintSurfaceEventArgs args)
    {
        SKImageInfo info = args.Info;
        SKSurface surface = args.Surface;
        SKCanvas canvas = surface.Canvas;

        SKLattice lattice = new SKLattice();
        lattice.XDivs = new int[] { 100, 400 };
        lattice.YDivs = new int[] { 100, 400 };
        lattice.Flags = new SKLatticeFlags[9]; 

        canvas.DrawBitmapLattice(bitmap, lattice, info.Rect);
    }
}

Sia la XDivs e YDivs proprietà vengono impostate su matrici di due numeri interi, dividere la bitmap in tre strisce sia orizzontalmente che verticalmente: dal pixel 0 a 100 (con rendering le dimensioni in pixel), in pixel dal pixel 100 a 400 pixel (esteso), e dal pixel 400 e 500 (le dimensioni in pixel).Both the XDivs and YDivs properties are set to arrays of just two integers, dividing the bitmap into three strips both horizontally and vertically: from pixel 0 to pixel 100 (rendered in the pixel size), from pixel 100 to pixel 400 (stretched), and from pixel 400 to pixel 500 (pixel size). Insieme, XDivs e YDivs definiscono un totale di 9 rettangoli, ovvero le dimensioni del Flags matrice.Together, XDivs and YDivs define a total of 9 rectangles, which is the size of the Flags array. È sufficiente creare la matrice è sufficiente per creare una matrice di SKLatticeFlags.Default valori.Simply creating the array is sufficient to create an array of SKLatticeFlags.Default values.

La visualizzazione è identica al precedente programma:The display is identical to the previous program:

Reticolo nove-PatchLattice Nine-Patch

Il reticolo visualizzazione pagina divide la bitmap in 16 rettangoli:The Lattice Display page divides the bitmap into 16 rectangles:

public class LatticeDisplayPage : ContentPage
{
    SKBitmap bitmap = NinePatchDisplayPage.FiveByFiveBitmap;

    public LatticeDisplayPage()
    {
        Title = "Lattice Display";

        SKCanvasView canvasView = new SKCanvasView();
        canvasView.PaintSurface += OnCanvasViewPaintSurface;
        Content = canvasView;
    }

    void OnCanvasViewPaintSurface(object sender, SKPaintSurfaceEventArgs args)
    {
        SKImageInfo info = args.Info;
        SKSurface surface = args.Surface;
        SKCanvas canvas = surface.Canvas;

        canvas.Clear();

        SKLattice lattice = new SKLattice();
        lattice.XDivs = new int[] { 100, 200, 400 };
        lattice.YDivs = new int[] { 100, 300, 400 };

        int count = (lattice.XDivs.Length + 1) * (lattice.YDivs.Length + 1);
        lattice.Flags = new SKLatticeFlags[count];

        canvas.DrawBitmapLattice(bitmap, lattice, info.Rect);
    }
}

Il XDivs e YDivs le matrici sono piuttosto diverse, causando la visualizzazione a non essere abbastanza come simmetrico come negli esempi precedenti:The XDivs and YDivs arrays are somewhat different, causing the display to be not quite as symmetrical as the previous examples:

Visualizzazione reticoloLattice Display

In iOS e Android immagini a sinistra, vengono visualizzati solo i più piccoli cerchi nelle relative dimensioni in pixel.In the iOS and Android images on the left, only the smaller circles are rendered in their pixel sizes. Tutto il resto viene adattata.Everything else is stretched.

Il reticolo Display pagina generalizza la creazione delle Flags matrice, che consente di sperimentare XDivs e YDivs più facilmente.The Lattice Display page generalizes the creation of the Flags array, allowing you to experiment with XDivs and YDivs more easily. In particolare, è opportuno vedere cosa accade quando si imposta il primo elemento della XDivs o YDivs array su 0.In particular, you'll want to see what happens when you set the first element of the XDivs or YDivs array to 0.