Heim  >  Artikel  >  Web-Frontend  >  HTML5-Leinwand-Zeichnungs-Tutorial (11) – Verwenden Sie lineTo/arc/bezierCurveTo, um ein Oval zu zeichnen._HTML5-Tutorial-Fähigkeiten

HTML5-Leinwand-Zeichnungs-Tutorial (11) – Verwenden Sie lineTo/arc/bezierCurveTo, um ein Oval zu zeichnen._HTML5-Tutorial-Fähigkeiten

WBOY
WBOYOriginal
2016-05-16 15:50:051647Durchsuche

In Canvas können Sie problemlos die Bogenmethode verwenden, um einen Kreis zu zeichnen. Ursprünglich kann ein Kreis auch als Ellipse mit gleicher Breite und Höhe betrachtet werden, es gibt jedoch keine Möglichkeit, eine Ellipse in Canvas zu zeichnen um es zu simulieren.
Wir müssen zunächst klären, welche Parameter zum Zeichnen einer Ellipse benötigt werden. Aus den geometrischen Grundkenntnissen geht hervor, dass eine Ellipse Mittelpunktskoordinaten, Breite, Höhe – oder Drehwinkel – benötigt. Dies kann jedoch vorerst weggelassen werden, die Drehung ist einfacher.
1. Verwenden Sie lineTo, um Ellipsen zu zeichnen
Sie haben richtig gelesen, lineTo, eine Methode, die ausschließlich zum Zeichnen gerader Linien verwendet wird, kann tatsächlich zum Zeichnen von Ellipsen verwendet werden! ? Aber es gibt ihn, aber die Schreibmethode ist wirklich unglaublich:

Kopieren Sie den Code
Der Code lautet wie folgt:

function DrawEllipse(Canvas,O,OA,OB){
//Zeichne eine Ellipse, Beispiel: var B=new Array(150,150); DrawEllipse(hb,B,50,30) ;
with ( Canvas){
var x=O[0] OA;
moveTo(x,y); 0;i<=360 ;i ){
var ii=i*Math.PI/180;
var x=O[0] OA*Math.cos(ii); [1]-OB* Math.sin(ii);
lineTo(x,y);
}
}


Das Prinzip dieser Methode ist dass ein Kreis 360 Grad hat. Verwenden Sie dann lineTo, um eine 360-fache Schleife zu durchlaufen, zeichnen Sie Liniensegmente für jeden Grad und verbinden Sie sie schließlich zu einer Ellipse. Zur Berechnung werden die trigonometrischen Funktionen Sinus und Cosinus benötigt.
Beachten Sie, dass der zweite Parameter dieser Methode ein Array ist, das die Mittelkoordinate der Ellipse ist
Die Idee ist sehr seltsam und die gezeichnete Ellipse ist relativ glatt. Aber es lohnt sich nicht, es für jeden zu verwenden – diese Methode durchläuft jedes Mal, wenn eine Ellipse gezeichnet wird, 360 Mal und zeichnet nur geringfügig mehr Ellipsen, was einen Test für die Leistung des Browsers darstellt.
Wir müssen nur seine Ideen verstehen

2. Zeichnen Sie mit einem Bogen einen Kreis und skalieren Sie ihn dann in eine Ellipse

Der Originaltext dieser Methode und der Kern sind hier Die Funktion lautet wie folgt:



Code kopieren
Der Code lautet wie folgt: var canvas = document.getElementById('myCanvas');
var context = canvas.getContext('2d');
var centerY = 0;
var radius = 50;
// Status speichern
context.save();
// Kontext übersetzen
context.translate(canvas.width / 2, canvas.height / 2);
// Kontext skalieren horizontal
context.scale( 2, 1);
// Kreis zeichnen, der in ein Oval gestreckt wird
context.beginPath();
context.arc(centerX, centerY, radius, 0 , 2 * Math.PI, false );
// Wiederherstellung des ursprünglichen Zustands
context.restore()


Diese Methode verwendet eine Canvas-Funktion, über die ich zuvor noch nicht gesprochen habe , nämlich Skalierung, die Leinwand-Zoom implementieren kann. Es gibt zwei Skalierungsrichtungen: horizontal und vertikal. Im Code wird die Leinwand in horizontaler Richtung vergrößert, die vertikale Richtung bleibt jedoch unverändert. Der durch einen Bogen gezeichnete Kreis wird also zu einer Ellipse.
Diese Methode sieht auf den ersten Blick sehr gut aus, mit weniger Code und das Prinzip ist leicht zu verstehen. Aber nach der Analyse können Sie seine offensichtlichen Mängel finden, nämlich Ungenauigkeit! Ich benötige zum Beispiel eine Ellipse mit einer Breite von 171 und einer Höhe von 56. Wenn wir den Bogenradius auf 28 einstellen, werden wir von der schmerzhaften und unverständlichen Zahl 171/28/2 deprimiert.

Aber ein Kompromiss besteht darin, den Bogenradius immer auf 100 einzustellen und ihn dann zu vergrößern, wenn er nicht ausreicht, und ihn zu verkleinern, wenn er größer ist. Allerdings ist es immer noch nicht präzise.

3, verwenden Sie die Bezier-Kurve bezierCurveTo

Da ich der Meinung war, dass die obige Skalierungsmethode ungenau war, wollte ich eine genaue Methode zum Zeichnen einer Ellipse finden und fand sie schließlich im Stackoverflow:



Code kopieren
Der Code lautet wie folgt: Funktion drawEllipse(ctx, x, y , w, h) { var kappa = 0,5522848;
ox = (w / 2) * kappa, // Kontrollpunkt-Offset horizontal
oy = (h / 2) * kappa, // Kontrollpunkt Versatz vertikal
xe = x w, // x-Ende
ye = y h, // y-Ende
xm = x w / 2, // x-Mitte
ym = y h / 2; / y-middle
ctx.beginPath();
ctx.moveTo(x, ym);
ctx.bezierCurveTo(x, ym - oy, xm - ox, y, xm, y); 🎜 >ctx.bezierCurveTo(xm ox, y, xe, ym - oy, xe, ym);
ctx.bezierCurveTo(xe, ym oy, xm ox, ye, xm, ye); ( xm - ox, ye, x, ym oy, x, ym);
Diese Methode kann als perfekt angesehen werden. Er teilte eine Ellipse in vier Bezier-Kurven und verband sie zu einer Ellipse. Schließlich sind Breite und Höhe genauer und der Overhead ist geringer.
Aber diese Methode weist immer noch Mängel auf. Schauen Sie sich den Kappa-Parameter an, er hat einen ganz besonderen Wert. Ich glaube, viele Leute verstehen nicht, warum er diesen Wert haben muss, bis Ihnen ein Geometrieexperte sagt, warum er diesen Wert haben muss – ich weiß es immer noch nicht. Und ich habe den starken Drang, es zu ändern und zu sehen, was die Konsequenzen sein werden.

Natürlich kann man nicht sagen, dass mein Impuls, der dem eines Zwangsstörungspatienten ähnelt, ein Mangel dieser Methode ist. Der eigentliche Mangel ist: Warum 4 Bezier-Kurven verwenden? Ich persönlich bin der Meinung, dass eine Ellipse offensichtlich aus zwei statt vier Bezier-Kurven besteht. Diese Idee führte mich schließlich zur perfekten Möglichkeit, eine Ellipse zu zeichnen.
4, verwenden Sie zwei Bezier-Kurven, um eine Ellipse zu zeichnen
Um zu verstehen, ob die vorherige Methode vereinfacht werden kann, habe ich speziell ein Stackoverflow-Konto registriert, um Fragen zu stellen Frage, ich hatte nicht genügend Punkte zum Übertragen, also musste ich mein kaum ausreichendes Englisch nutzen, um Fragen von Ausländern zu beantworten, um Punkte zu sammeln. Aber schließlich kam das Glück und mein Punkteproblem wurde durch die Beantwortung einer Frage gelöst.
Die Frage, die ich zur Beziehung zwischen Bezier-Kurven und Ellipsen gestellt habe, ist hier
Um ehrlich zu sein, habe ich die meisten Antworten des Ausländers unten nicht verstanden, aber glücklicherweise hat er eine Codebeispielseite bereitgestellt, die mir das Verständnis vermittelt hat . Prinzip, ich möchte ihm noch einmal meinen Dank aussprechen. Laut seiner Antwort lautet die Methode, die ich zum Zeichnen einer Ellipse gefunden habe, wie folgt:

Kopieren Sie den Code
Der Code ist wie folgt:

//Ellipse
CanvasRenderingContext2D.prototype.oval = function (x, y, width, height) {
var k = (width/0.75)/2,
w = width/ 2,
h = height/2;
this.moveTo(x, y-h);
this.bezierCurveTo(x k, y-h, x k , y h, x, y h );
this.bezierCurveTo(x-k, y h, x-k, y-h, x, y-h);
return this;

Diese Methode ist präzise, ​​erfordert weniger Code und weist keine seltsamen Macken auf. Denken Sie daran: Das Verhältnis der Breite der Ellipse zu den Koordinaten der Kontrollpunkte der Bezier-Kurve, die die Ellipse zeichnet, ist wie folgt:
Bezier-Kontrollpunkt x=(Ellipsenbreite/0,75)/2 Das ist schon so im Code widergespiegelt in.
Sie können die oben genannten 4 Methoden ausprobieren, um eine Ellipse zu zeichnen.
Wenn Sie eine einfachere Methode finden, teilen Sie sie uns bitte zur Diskussion mit.
Stellungnahme:
Der Inhalt dieses Artikels wird freiwillig von Internetnutzern beigesteuert und das Urheberrecht liegt beim ursprünglichen Autor. Diese Website übernimmt keine entsprechende rechtliche Verantwortung. Wenn Sie Inhalte finden, bei denen der Verdacht eines Plagiats oder einer Rechtsverletzung besteht, wenden Sie sich bitte an admin@php.cn