Partager via


Principes de base du chemin d’accès dans SkiaSharp

Explorer l’objet SkPath SkiaSharp pour combiner des lignes connectées et des courbes

L’une des fonctionnalités les plus importantes du chemin graphique est la possibilité de définir quand plusieurs lignes doivent être connectées et quand elles ne doivent pas être connectées. La différence peut être significative, car les sommets de ces deux triangles illustrent :

Deux triangles montrant la différence entre les lignes connectées et déconnectées

Un chemin graphique est encapsulé par l’objet SKPath . Un tracé est une collection d’un ou plusieurs contours. Chaque contour est une collection de lignes droites et de courbes connectées. Les contours ne sont pas connectés les uns aux autres, mais ils peuvent se chevaucher visuellement. Parfois, un contour peut se chevaucher lui-même.

Un contour commence généralement par un appel à la méthode suivante :SKPath

  • MoveTo pour commencer un nouveau contour

L’argument de cette méthode est un point unique, que vous pouvez exprimer en tant que valeur ou en tant que SKPoint coordonnées X et Y distinctes. L’appel MoveTo établit un point au début du contour et un point actuel initial. Vous pouvez appeler les méthodes suivantes pour poursuivre le contour avec une ligne ou une courbe du point actuel à un point spécifié dans la méthode, qui devient ensuite le nouveau point actuel :

  • LineTo pour ajouter une ligne droite au chemin
  • ArcTo pour ajouter un arc, qui est une ligne sur la circonférence d’un cercle ou d’un ellipse
  • CubicTo pour ajouter une spline bezier cubique
  • QuadTo pour ajouter un spline de Bezier quadratique
  • ConicTo pour ajouter une spline de Bezier quadratique rationnelle, qui peut restituer avec précision des sections coniques (points de suspension, paraboles et hyperbolas)

Aucune de ces cinq méthodes ne contient toutes les informations nécessaires pour décrire la courbe ou la ligne. Chacune de ces cinq méthodes fonctionne conjointement avec le point actuel établi par l’appel de méthode immédiatement avant celui-ci. Par exemple, la LineTo méthode ajoute une ligne droite au contour en fonction du point actuel. Par conséquent, le paramètre n’est LineTo qu’un seul point.

La SKPath classe définit également les méthodes qui ont les mêmes noms que ces six méthodes, mais avec un R au début :

Il R s’agit d’un relatif. Ces méthodes ont la même syntaxe que les méthodes correspondantes sans les R méthodes, mais sont relatives au point actuel. Ils sont pratiques pour dessiner des parties similaires d’un chemin d’accès dans une méthode que vous appelez plusieurs fois.

Un contour se termine par un autre appel à MoveTo ou RMoveTo, qui commence un nouveau contour, ou un appel à Close, qui ferme le contour. La Close méthode ajoute automatiquement une ligne droite du point actuel au premier point du contour, et marque le chemin comme fermé, ce qui signifie qu’il sera rendu sans aucune limite de trait.

La différence entre les contours ouverts et fermés est illustrée dans la page Two Triangle Contours , qui utilise un SKPath objet avec deux contours pour afficher deux triangles. Le premier contour est ouvert et le second est fermé. Voici la classe TwoTriangleContoursPage :

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

    canvas.Clear();

    // Create the path
    SKPath path = new SKPath();

    // Define the first contour
    path.MoveTo(0.5f * info.Width, 0.1f * info.Height);
    path.LineTo(0.2f * info.Width, 0.4f * info.Height);
    path.LineTo(0.8f * info.Width, 0.4f * info.Height);
    path.LineTo(0.5f * info.Width, 0.1f * info.Height);

    // Define the second contour
    path.MoveTo(0.5f * info.Width, 0.6f * info.Height);
    path.LineTo(0.2f * info.Width, 0.9f * info.Height);
    path.LineTo(0.8f * info.Width, 0.9f * info.Height);
    path.Close();

    // Create two SKPaint objects
    SKPaint strokePaint = new SKPaint
    {
        Style = SKPaintStyle.Stroke,
        Color = SKColors.Magenta,
        StrokeWidth = 50
    };

    SKPaint fillPaint = new SKPaint
    {
        Style = SKPaintStyle.Fill,
        Color = SKColors.Cyan
    };

    // Fill and stroke the path
    canvas.DrawPath(path, fillPaint);
    canvas.DrawPath(path, strokePaint);
}

Le premier contour se compose d’un appel à MoveTo l’utilisation des coordonnées X et Y plutôt qu’une SKPoint valeur, suivie de trois appels pour LineTo dessiner les trois côtés du triangle. Le deuxième contour n’a que deux appels, LineTo mais il termine le contour avec un appel à Close, qui ferme le contour. La différence est significative :

Capture d’écran triple de la page Deux contours triangles

Comme vous pouvez le voir, le premier contour est évidemment une série de trois lignes connectées, mais la fin ne se connecte pas avec le début. Les deux lignes se chevauchent en haut. Le deuxième contour est évidemment fermé et a été accompli avec un nombre inférieur LineTo d’appels, car la Close méthode ajoute automatiquement une ligne finale pour fermer le contour.

SKCanvas définit une seule DrawPath méthode, qui dans cette démonstration est appelée deux fois pour remplir et traiter le chemin. Tous les contours sont remplis, même ceux qui ne sont pas fermés. Pour remplir des chemins non fermés, une ligne droite est supposée exister entre les points de début et de fin des contours. Si vous supprimez le dernier LineTo du premier contour ou supprimez l’appel Close du deuxième contour, chaque contour n’aura que deux côtés, mais sera rempli comme s’il s’agissait d’un triangle.

SKPath définit de nombreuses autres méthodes et propriétés. Les méthodes suivantes ajoutent des contours entiers au chemin d’accès, qui peuvent être fermés ou non fermés en fonction de la méthode :

N’oubliez pas qu’un SKPath objet définit uniquement une géométrie : une série de points et de connexions. Uniquement lorsqu’un SKPath objet est combiné à un SKPaint objet est le chemin rendu avec une couleur particulière, une largeur de trait, etc. Gardez également à l’esprit que l’objet SKPaint passé à la DrawPath méthode définit les caractéristiques de l’intégralité du chemin. Si vous souhaitez dessiner quelque chose nécessitant plusieurs couleurs, vous devez utiliser un chemin distinct pour chaque couleur.

Tout comme l’apparence du début et de la fin d’une ligne est définie par une limite de trait, l’apparence de la connexion entre deux lignes est définie par une jointure de trait. Vous spécifiez cela en définissant la StrokeJoin propriété d’un SKPaint membre de l’énumération SKStrokeJoin :

  • Miter pour une jointure pointée
  • Round pour une jointure arrondie
  • Bevel pour une jointure hachée

La page Jointures de traits affiche ces trois jointures de traits avec du code similaire à la page Traits majuscules . Il s’agit du PaintSurface gestionnaire d’événements dans la StrokeJoinsPage classe :

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

    canvas.Clear();

    SKPaint textPaint = new SKPaint
    {
        Color = SKColors.Black,
        TextSize = 75,
        TextAlign = SKTextAlign.Right
    };

    SKPaint thickLinePaint = new SKPaint
    {
        Style = SKPaintStyle.Stroke,
        Color = SKColors.Orange,
        StrokeWidth = 50
    };

    SKPaint thinLinePaint = new SKPaint
    {
        Style = SKPaintStyle.Stroke,
        Color = SKColors.Black,
        StrokeWidth = 2
    };

    float xText = info.Width - 100;
    float xLine1 = 100;
    float xLine2 = info.Width - xLine1;
    float y = 2 * textPaint.FontSpacing;
    string[] strStrokeJoins = { "Miter", "Round", "Bevel" };

    foreach (string strStrokeJoin in strStrokeJoins)
    {
        // Display text
        canvas.DrawText(strStrokeJoin, xText, y, textPaint);

        // Get stroke-join value
        SKStrokeJoin strokeJoin;
        Enum.TryParse(strStrokeJoin, out strokeJoin);

        // Create path
        SKPath path = new SKPath();
        path.MoveTo(xLine1, y - 80);
        path.LineTo(xLine1, y + 80);
        path.LineTo(xLine2, y + 80);

        // Display thick line
        thickLinePaint.StrokeJoin = strokeJoin;
        canvas.DrawPath(path, thickLinePaint);

        // Display thin line
        canvas.DrawPath(path, thinLinePaint);
        y += 3 * textPaint.FontSpacing;
    }
}

Voici le programme en cours d’exécution :

Capture d’écran triple de la page Jointures de traits

La jointure mitreuse se compose d’un point aigu où les lignes se connectent. Lorsque deux lignes se joignent à un petit angle, la jointure mitreuse peut devenir assez longue. Pour éviter des jointures à mitre excessivement longues, la longueur de la jointure de mitreur est limitée par la valeur de la StrokeMiter propriété de SKPaint. Une jointure mitreuse qui dépasse cette longueur est hachée pour devenir une jointure de biseau.