W3docs

Canvas-Koordinaten

Nützliche Informationen über das HTML-Canvas-Koordinatensystem sowie Codebeispiele zum Zeichnen von Kreisen und Linien.

HTML Canvas ist ein leistungsstarkes Element in HTML5, mit dem Sie mithilfe von JavaScript Grafiken auf einer Webseite erstellen und bearbeiten können. Das <canvas>-Element stellt eine zweidimensionale Zeichenfläche bereit, die man sich als ein Raster oder ein Koordinatensystem vorstellen kann.

Diese Seite erklärt, wie das Canvas-Koordinatensystem funktioniert, wie man Punkte darin liest und schreibt, und wie man dieses System mit Transformationen verschieben, skalieren und drehen kann. Wenn Sie neu mit dem Element sind, beginnen Sie zuerst mit der Canvas-Einführung.

Das Koordinatensystem

Das Canvas-Raster beginnt in der oberen linken Ecke, die die Koordinaten (0, 0) hat. Von dort aus gilt:

  • Die x-Achse wächst nach rechts.
  • Die y-Achse wächst nach unten (das ist das Gegenteil der Mathematik, an die sich die meisten erinnern, wo y nach oben zeigt).

Jeder Punkt auf dem Canvas ist ein Paar (x, y), gemessen in Pixeln vom oberen linken Ursprung.

(0,0)──────── x increases → ────────►
  │  ┌───────────────────────────────┐
  │  │ (0,0)                  (300,0) │
  y  │                               │
  │  │            (150,75)           │
  ▼  │                               │
     │ (0,150)              (300,150)│
     └───────────────────────────────┘

Bei einem 300 × 150-Canvas ist (0, 0) die obere linke Ecke, (300, 0) die obere rechte Ecke, (0, 150) die untere linke Ecke, und (150, 75) ist der genaue Mittelpunkt.

Der 2D-Rendering-Kontext

Sie zeichnen nie direkt auf das <canvas>-Element. Stattdessen fordern Sie einen Rendering-Kontext davon an — ein Objekt, das die Zeichenmethoden bereitstellt (moveTo, lineTo, arc, fillRect usw.):

const canvas = document.getElementById("myCanvas");
const ctx = canvas.getContext("2d");

getContext("2d") gibt den 2D-Kontext zurück, der für alle nachfolgenden Beispiele verwendet wird. (Es gibt auch andere Kontexttypen, wie "webgl" für 3D, aber "2d" ist das, was beim Canvas-Zeichnen verwendet wird.) Jede Koordinate, die Sie an eine Kontextmethode übergeben, wird im oben beschriebenen Raster interpretiert.

Eine Linie zeichnen

Die folgenden Methoden werden verwendet, um eine gerade Linie auf einem Canvas zu zeichnen:

  • moveTo(x,y), das den Startpunkt der Linie angibt
  • lineTo(x,y), das den Endpunkt der Linie angibt

Verwenden Sie eine der „Tinten"-Methoden, um eine Linie zu zeichnen, beispielsweise stroke().

Beispiel des HTML-<canvas>-Elements zum Zeichnen einer Linie:

<!DOCTYPE html>
<html>
  <head>
    <title>Title of the document</title>
  </head>
  <body>
    <canvas width="300" height="150" style="border:1px solid #cccccc;" id="canvasExample">
      Your browser does not support the HTML5 canvas tag.
    </canvas>
    <script>
      const c = document.getElementById("canvasExample");
      const ctx = c.getContext("2d");
      // Starting point (0,0) is the top-left corner
      ctx.moveTo(0, 0);
      // Ending point (300,150) matches the canvas width and height
      ctx.lineTo(300, 150);
      ctx.strokeStyle = '#359900';
      ctx.stroke();
    </script>
  </body>
</html>

Im obigen Beispiel wird die Linie diagonal von (0, 0) (oben links) nach (300, 150) (unten rechts) gezeichnet. Beachten Sie, dass diese einzelne Linie kein beginPath() benötigte: Wenn noch nichts anderes gezeichnet wurde, starten moveTo/lineTo automatisch einen neuen Pfad. Der Kreis unten verwendet beginPath(), weil er eine separate Form ist — siehe die Erläuterung in jenem Abschnitt.

Weitere Formen und Füllungen, die auf demselben Koordinatensystem aufbauen, finden Sie unter Canvas-Zeichnen.

Einen Kreis zeichnen

Die folgenden Methoden werden verwendet, um einen Kreis auf einem Canvas zu zeichnen:

  • beginPath(), das einen neuen Pfad startet, damit der Kreis nicht mit zuvor Gezeichnetem verbunden ist.
  • arc(x, y, r, startAngle, endAngle), das dem aktuellen Pfad einen Bogen (einen Teil eines Kreises) hinzufügt.

Die arc()-Parameter

ParameterBedeutung
x, yDie Koordinaten des Mittelpunkts des Kreises.
rDer Radius in Pixeln.
startAngleWo der Bogen beginnt, in Bogenmaß.
endAngleWo der Bogen endet, in Bogenmaß.

Winkel werden in Bogenmaß gemessen, nicht in Grad, und 0 zeigt nach rechts (die positive x-Achse), wobei die Drehung im Uhrzeigersinn erfolgt. Eine vollständige Umdrehung entspricht 2 * Math.PI Bogenmaß (360°), ein vollständiger Kreis geht also von 0 bis 2 * Math.PI.

Um Grad in Bogenmaß umzurechnen, multiplizieren Sie mit Math.PI / 180:

const radians = degrees * (Math.PI / 180);

Teilbögen

Sie müssen keinen vollständigen Kreis zeichnen. Verwenden Sie einen kleineren Endwinkel, um nur einen Teil davon zu zeichnen. Ein Bogen von 0 bis Math.PI (eine halbe Umdrehung) zeichnet beispielsweise die untere Hälfte eines Kreises, da y nach unten wächst:

// A half-circle (bottom half) centered at (100, 75) with radius 50
ctx.beginPath();
ctx.arc(100, 75, 50, 0, Math.PI);
ctx.stroke();

Beispiel des HTML-<canvas>-Elements zum Zeichnen eines Kreises:

<!DOCTYPE html>
<html>
  <head>
    <title>Title of the document</title>
  </head>
  <body>
    <canvas id="exampleCanvas" width="250" height="200" style="border:1px solid #dddddd;">
      The canvas tag is not supported by your browser.
    </canvas>
    <script>
      const canvas = document.getElementById("exampleCanvas");
      const ctx = canvas.getContext("2d");
      ctx.beginPath();
      // Center at (125, 95), radius 70. 125 is half of the 250 width.
      ctx.arc(125, 95, 70, 0, 2 * Math.PI);
      ctx.strokeStyle = '#1c87c9';
      ctx.closePath();
      ctx.stroke();
    </script>
  </body>
</html>

Im obigen Beispiel ist der Kreis bei (125, 95) mit einem Radius von 70 zentriert.

beginPath() und closePath()

Diese beiden Methoden führen häufig zu Verwirrung:

  • beginPath() verwirft jeden bisher aufgebauten Pfad und beginnt einen völlig neuen. Rufen Sie diese Methode vor jeder eigenständigen Form auf — andernfalls wird die neue Form mit der vorherigen verbunden, und ein einziges stroke()/fill() gestaltet beide zusammen.
  • closePath() zeichnet eine gerade Linie vom aktuellen Punkt zurück zum Startpunkt des Pfades und „schließt" damit die Kontur. Bei einem vollständigen Kreis trifft das Ende bereits auf den Anfang, sodass closePath() hier keine sichtbare Wirkung hat — es wird aus Gewohnheit eingefügt und ist relevant, wenn man offene Formen wie ein Polygon erstellt.

Das frühere Linienbeispiel benötigte keine dieser Methoden, da es sich um einen einzelnen, eigenständigen Pfad handelte. Sobald Sie eine zweite Form zeichnen, greifen Sie auf beginPath() zurück.

Koordinatentransformationen

Statt jede Koordinate manuell neu zu berechnen, können Sie das gesamte Koordinatensystem verschieben, skalieren oder drehen. Transformationen wirken sich auf alles aus, was Sie danach zeichnen.

Ein gängiges Muster ist es, transformiertes Zeichnen in save() und restore() einzuwickeln, damit das Raster danach wieder in den Normalzustand zurückkehrt:

ctx.save();      // remember the current coordinate system
// ...transform and draw...
ctx.restore();   // put the coordinate system back

translate(x, y)

Verschiebt den Ursprung (0, 0) an eine neue Position. Nach translate(50, 30) erscheint das Zeichnen bei (0, 0) tatsächlich an der Stelle (50, 30):

ctx.translate(50, 30);
ctx.fillRect(0, 0, 80, 40); // top-left corner now sits at (50, 30)

scale(x, y)

Multipliziert die Größe jeder Koordinate und Dimension. scale(2, 2) macht alles doppelt so groß; scale(1, 0.5) behält die Breite bei, halbiert aber die Höhe:

ctx.scale(2, 2);
ctx.fillRect(10, 10, 30, 30); // drawn at (20, 20), 60×60 in real pixels

rotate(angle)

Dreht das Koordinatensystem im Uhrzeigersinn um den aktuellen Ursprung. Der Winkel wird in Bogenmaß angegeben, wie bei arc(). Da die Drehung um (0, 0) erfolgt, verwenden Sie üblicherweise zuerst translate(), um zum gewünschten Drehpunkt zu wechseln:

ctx.translate(100, 75);          // move origin to the pivot point
ctx.rotate(45 * Math.PI / 180);  // rotate 45° clockwise
ctx.fillRect(-25, -25, 50, 50);  // a square centered on the pivot

Transformationen halten Ihre Koordinaten im selben Raster, das Sie die ganze Zeit verwendet haben — sie verschieben oder verändern lediglich dieses Raster. Informationen zum Positionieren von Text in diesem System finden Sie unter Canvas-Text.

Übungen

Übung
Was sind die Eigenschaften der HTML5-<canvas>-Element-Koordinaten?
Was sind die Eigenschaften der HTML5-<canvas>-Element-Koordinaten?
Was this page helpful?