如何使用 JS 和 p5.js 使 class 中的对象物理移动

How to make a Object in a class physically move using JS and p5.js

到目前为止,我已经创建了一个 class 来生成一个圆圈。我一直在尝试使这个圆 move/vibrate 不断变化,但我不确定使用 OOP 添加移动功能的最佳方法是什么。此外,当我在绘制函数中创建 'face' 对象时,我的页面崩溃了。

function setup() {
  createCanvas(350, 350, WEBGL);
  background('white')
  let face = new Face();
}

class Face {
  constructor() {
    this.basicFace(100, random(10,30),0,0);
  }


  basicFace(radius, steps, centerX, centerY) {
  var xValues = [];
  var yValues = [];
  for (var i = 0; i < steps; i++) {
    let rad = radius + random(-radius / 50, radius / 50) 
    xValues[i] = (centerX + rad * cos(2 * PI * i / steps));
    yValues[i] = (centerY + rad * sin(2 * PI * i / steps));
  }
  beginShape();
  strokeWeight(4)
    for (let i = 0; i < xValues.length; i++) {
      curveVertex(xValues[i], yValues[i]);
    }
  endShape(CLOSE);

}
}
<script src="https://cdn.jsdelivr.net/npm/p5@1.4.0/lib/p5.js"></script>

首先,在 draw() 函数中创建新的 Face 实例可能导致页面挂起的一个原因是 draw() 函数每秒运行多次,并且在 JavaScript 中,大量分配(例如创建 class 的新实例)可能对性能不利。但是,每次调用 draw() 时简单地分配一个 class 实例通常不会导致问题。另一方面,如果您将这些实例添加到数据结构(例如数组)中,这可能会导致您的页面使用过多的内存并最终挂起。没有看到导致挂起的确切代码,很难说。

如果你想以面向对象的方式实现上面的草图,那么你应该采取以下步骤:

  1. 为您的 class 提供一些定义其属性的构造函数参数,例如位置和大小,并将它们存储为实例字段。
  2. 将您的 class 行为与构造函数分开(即给它一个方法使其显示。
  3. 实例化一次,然后在draw()中调用该实例方法,以便每一帧显示它。

let face;

function setup() {
  createCanvas(350, 350, WEBGL);
  face = new Face(100, random(10, 30), 0, 0);
}

function draw() {
  background('white');
  face.show();
}

class Face {
  constructor(radius, steps, centerX, centerY) {
    this.radius = radius;
    this.steps = steps;
    this.centerX = centerX;
    this.centerY = centerY;
  }

  show() {
    var xValues = [];
    var yValues = [];
    for (var i = 0; i < this.steps; i++) {
      let rad = this.radius + random(-this.radius / 50, this.radius / 50)
      xValues[i] = (this.centerX + rad * cos(2 * PI * i / this.steps));
      yValues[i] = (this.centerY + rad * sin(2 * PI * i / this.steps));
    }
    
    strokeWeight(4);
    beginShape();
    for (let i = 0; i < xValues.length; i++) {
      curveVertex(xValues[i], yValues[i]);
    }
    
    endShape(CLOSE);
  }
}
<script src="https://cdn.jsdelivr.net/npm/p5@1.4.0/lib/p5.js"></script>

此外,当您显示曲线时,不必在一个循环中为 x 和 y 值创建数组,然后在单独的循环中调用 curveVertex()。相反,您可以组合这些循环并避免不必要的数组分配。

      show() {
        strokeWeight(4);
        beginShape();
        for (let i = 0; i < this.steps; i++) {
          let rad = this.radius + random(-this.radius / 50, this.radius / 50);
          curveVertex(
            this.centerX + rad * cos(2 * PI * i / this.steps),
            this.centerY + rad * sin(2 * PI * i / this.steps)
          );
        }
        
        endShape(CLOSE);
      }