我正在尝试编写一个代码,模仿HTML画布中this video中发生的事情。
我的代码的不同之处在于,每次加载或刷新页面时,两个圆圈的半径都是随机生成的。我需要“行星”沿着各自圆圈的周长以相同的速度行进。
我正在使用p5.js绘制到画布。 p5.js中是否有根据路径绘制对象的东西,在我的例子中是一个圆形的路径?
我查看了参考资料并发现了矢量,但我不太明白他们做了什么。
到目前为止我的代码:
var w = window.innerWidth;
var h = window.innerHeight;
var r1, r1;
var d;
var x1, x2, y1, y2;
var angle = Math.PI / 4;
function setup() {
// canvas setup
createCanvas(w, h);
background(255);
angleMode(RADIANS);
// randomly generated radiuses
r1 = Math.floor(Math.random() * (h/2-300)) + 300;
r2 = Math.floor(Math.random() * (200-100)) + 100;
// drawing the two ellipses
ellipseMode(CENTER);
noFill();
ellipse(w/2, h/2, r1*2, r1*2);
ellipse(w/2, h/2, r2*2, r2*2);
}
function draw() {
// points on the circles
x1 = (r1 * (Math.cos(angle))) + (w/2);
y1 = (h/2) - (r1 * (Math.sin(angle)));
x2 = (r2 * (Math.cos(angle))) + (w/2);
y2 = (h/2) - (r2 * (Math.sin(angle)));
// drawing two circles at those points
ellipseMode(CENTER);
noStroke();
fill('rgb(140, 140, 140)');
ellipse(x1, y1, 20, 20);
ellipse(x2, y2, 20, 20);
// randomly generated color for the line
var r = random(0, 255);
var g = random(0, 255);
var b = random(0, 255);
stroke(r, g, b);
strokeWeight(1);
// drawing the line that connects the two points
line(x1, y1, x2, y2);
// animation????
angle = angle + (10 * (Math.PI / 180));
}
最后一行的问题是它会创建evenly spaces lines,而不是视频中创建的模式。
答案 0 :(得分:1)
如果两个行星以相同的角度增量移动,它们将始终保持一种关系,从而在它们之间产生均匀间隔的线。
为了使它们之间连接的线穿过中心,它们必须具有不同的增量值。您必须保持两个不同的角度值以及每个角度的步长(或速度)。
对于视频中的示例,速度比为1:2.247,基于地球和金星围绕太阳的日比例之间的真实世界关系。由于它们的速度不同,它们之间的界线现在会交叉并产生五角星形图案。
我不知道P5.js所以我在下面添加了一个简单的JavaScript示例,如果需要P5,可以将其视为伪代码。由此您将能够看到如何以可变速度计算两个位置。
var ctx = c.getContext("2d"),
ratio = 2.247, // earth:venus ratio 1:2.247
angle1 = 0, // planet 1 current angle
angle2 = 0, // planet 2 current angle
dlt = 0.05, // angle step (speed)
radius1 = 150, // radius path for planet 1
radius2 = 100, // radius path for planet 2
cx = c.width*0.5, // center canvas
cy = c.height*0.5,
t = 503; // abort animation per # of frames
ctx.strokeStyle = "rgba(0,120,255,0.5)";
(function loop() {
var x1, y1, x2, y2;
x1 = cx + Math.cos(angle1) * radius1; // current (x,y) for planet 1
y1 = cy + Math.sin(angle1) * radius1;
x2 = cx + Math.cos(angle2) * radius2; // current (x,y) for planet 2
y2 = cy + Math.sin(angle2) * radius2;
ctx.beginPath(); // draw line
ctx.moveTo(x1, y1);
ctx.lineTo(x2, y2);
ctx.stroke();
angle1 += dlt; // increase angle planet 1
angle2 += dlt * ratio; // increase angle planet 2 per ratio
if (t--) requestAnimationFrame(loop)
})()
<canvas id=c height=300></canvas>