Assignment 4: Generative Text

Concept & Inspiration

Aaron Sherwood’s portfolio website had me impressed since the past 2 years, and it had been on my to-do list of things to learn just because of how addictive its animations were. Therefore, I decided to pursue this assignment in p5js to produce something similar and learn something new.

The website I took inspiration from is linked here

Embedded Canvas

The assignment outcome is attached as an embedded sketch as follows:

Code

The methodology to convert the text to points:

function setup() {
  createCanvas(600, 400);
  textSize(64);
  textFont(font);

  for (let i = 0; i < texts.length; i++) {
    let points = font.textToPoints(texts[i], 50 + i * 150, height / 2,50, {sampleFactor: 0.75, simplifyThreshold: 0 });
    for (let j = 0; j < points.length; j++) {
      let p = new Particle(points[j].x, points[j].y);
      particles.push(p);
    }
  }
}

Object Oriented Nature of the Particles!

class Particle {
  constructor(x, y) {
    this.pos = createVector(x, y);
    this.vel = createVector(random(-1, 1), random(-1, 1));
    this.acc = createVector(0, 0);
    this.target = createVector(x, y);
    this.size = 2;
    this.maxSpeed = 2;
    this.maxForce = 0.1;
    this.attractRadius = 50;
    this.attractForce = 0.1;
    this.color = color(255, 255, 255);

  }

  behaviors() {
    let arrive = this.arrive(this.target);
    this.applyForce(arrive);
    this.repel();
  }

  repel() {
    let mouse = createVector(mouseX, mouseY);
    let distance = p5.Vector.dist(this.pos, mouse);
    if (distance < this.attractRadius) {
      let repelForce = p5.Vector.sub(this.pos, mouse).normalize().mult(this.attractForce);
      this.applyForce(repelForce);
    }
  }
    attract() {
    let mouse = createVector(mouseX, mouseY);
    let distance = p5.Vector.dist(this.pos, mouse);
    if (distance < this.attractRadius) {
      let attractForce = p5.Vector.sub(mouse, this.pos).normalize().mult(this.attractForce);
      this.applyForce(attractForce);
    }
  }

  applyForce(f) {
    this.acc.add(f);
  }

  arrive(target) {
    let desired = p5.Vector.sub(target, this.pos);
    let d = desired.mag();
    let speed = this.maxSpeed;
    if (d < 100) {
      speed = map(d, 0, 100, 0, this.maxSpeed);
    }
    desired.setMag(speed);
    let steer = p5.Vector.sub(desired, this.vel);
    steer.limit(this.maxForce);
    return steer;
  }

  update() {
    this.pos.add(this.vel);
    this.vel.add(this.acc);
    this.acc.mult(0);
  }

  show() {
    // Set the fill color based on the velocity of the particle
    let vel = this.vel.mag();
    if (vel < 0.5) {
      this.color = color(255, 0, 0); // red
    } else if (vel < 1) {
      this.color = color(255, 255, 0); // yellow
    } else {
      this.color = color(255, 255, 255); // white
    }

    fill(this.color);
    noStroke();
    ellipse(this.pos.x, this.pos.y, this.size, this.size);
  }
}

 

Problems

The primary issue I faced was to discover the font.textToPoints() function and its complex usage. The other difficult bits was to repel or attract the points and adjust the speed and colors of it!

Author: Zunair

Senior @ NYU Abu Dhabi

Leave a Reply