Final Project – Peacefulness in Green

a. The concept

My idea for the final project is to create a relaxing and interactive experience. While this idea can apply to many concepts, I decided to focus myself on recreating (albeit not 100% similar) the following figures:

A table on a park
Figure 1. The inspiration.
Figure 2. My other inspiration.

There is not too much of a specific reason as to why these two figures were selected for inspiration aside of me being a fan of rural areas. Not to imply that I hate cities, but there is a charm in living in a place where you can take a sit, appreciate and take care of nature.

Now, the idea was to implement everything that we have learned so far in class with these figures as concepts. Although, as mentioned, the most important detail to be added (at least in my opinion) was interaction. Since I am a fan of interactable experiences with physics, something along the lines was sought after. Likewise, the details that were going to fill the background were planned to be concepts taught in class modified to look in-place with the setting.

b. The sketch

Here is the final, completed draft with the corresponding instructions:

Controls:

Holding mouse left click: Grab body/element

Full-screen version: Go to the Full-screen version

c. The design

Since I have some skills when it comes to image manipulation (not that much of a design master if I am honest), I decided to use Figure 2 as a basis for the background. This was done by manipulating the image using the software GIMP:

Figure 3. Working with GIMP for the background.
Figure 4. Working some more for the background using GIMP.

The bench also had to be made handmade to complement the background. If I just happen to add rectangles or some images from the internet, it would end up looking weird.

Figure 5. Designing the table’s leg.

As for the audio, some clips were carefully selected to complement the experience, such as the audio background and feedback when the bodies collide with each other:

Figure 6. Editing audio with Audacity

This part did not take as much time as I expected. Nevertheless, preparing a graphic from zero, that takes into account a specific design, can be troublesome.

d. The features

The main feature of this sketch is the object manipulation with the help of the physics library matter.js. For more information, here is the complete list of features that this sketch possesses:

  • Interactable bottle and seeds: These are mostly done with the help of matter.js for the physics. The idea is that, the seeds will spawn inside the cups and that, once they fall into the grass with the help of the user manipulation, they will stop in where they landed. After this, a plant will grow using Perlin noise. As for the cups, new ones will spawn when a very low probability—getting the number 1 from 5000 possible numbers—is met with the help of random().
  • Ants moving from left to right: The ants moved from either the left or right side, following an established target.
  • Winds: They are displayed as sine waves, and are mostly there to provide an additional force for the matter.js bodies once they are under a specific range of the Y axis.
  • CRT effect: It is basically a combination of multiple cellular automata layered on top of each other with a specific value of opacity.

Here is a quick demonstration of all the systems mentioned in place:

e. Cut features

A quick sketch
Figure 7. The original sketch

Most of the ideas from the original sketch were implemented, although some needed reconsideration. For example, the cellular automata were originally intended to be for dirt patterns, but it proved to be difficult to get the result. While trying to figure out how to make it work, I came across a “CRT” effect that could add into a nostalgia factor.

Elements number 4 and 5 had to be cut due to not having enough time. The features were the following:

#4 Birds flying around: These will be done with the help of a flocking system.

#5 A tree with moving leaves: The moving leaves will be simulated with the help of some forces.
Figure 8. Developing the flow field.

f. Code I am still particularly proud of

Detecting the current position of each ball and then spawning a Perlin walker that moves linearly in the Y axis but randomly on the X axis, while leaving a trail, proved to be difficult. I had to readjust the positioning to match matter.js:

Code found in classes/walker.js. All the class is provided, since many elements are necessary for this to work.

class Walker {
  constructor(x, y, w, angle) {
    this.position = createVector(x, y);
    this.angle = angle;

    this.w = w;

    //Stop growing it in the Y axis.
    this.y_limit = int(random(400, 500));

    //Shows the trail. Made with the following help: https://www.youtube.com/watch?v=vqE8DMfOajk
    this.history = [];

    //Variables for the perlin movement.
    this.tx = this.position.x;
    this.ty = this.position.y;

    this.last_position = 0; //Tracks the last position for reference. This avoids that the Perlin movement moves everywhere.
    this.rise = 0; //Controls the map to allow the plant to grow.

    this.free_x = 0; //Frees X space
    this.free_y = 0; //Frees Y space.  Both of them helps to create the illusion of grow.
  }

  show() {
    //Show trail.
    push();
    for (let i = 0; i < this.history.length; i++) {
      let pos = this.history[i];
      ellipse(pos.x, pos.y, this.w);
      noStroke();
      fill(0, 200, 0);
    }
    pop();
  }

  move() {
    this.history.push(createVector(this.position.x, this.position.y));
    this.position.x = map(
      noise(this.tx),
      -30,
      30,
      this.position.x - 10,
      this.position.x + 10
    );
    this.tx += 0.1;
  }
}

The rest of the code, while expansive, did not feel really challenging aside from adapting some features to my sketch. I highlight the provided coded, since most of it came from my own logic and a lot of trial and error. It is impressive how some lines of codes can be seen as simple, but in reality, it takes a lot of time to write the correct code that gives the desired result.

g. User testing

I asked a friend to try out the sketch. Here is the video of it:

There are some issues highlighted, such as physics being glitched or initial confusion as to what to do, despite putting some (rather mysterious) instructions to let the user know what to do.  The instructions were left vague to let the user feel, possibly, more engage after figuring out the interaction.

h. Interactive Media Showcase

Here are some videos of the Interactive Media showcase. What it is interesting from these videos is that some students actually understood what to do. Although, there was general confusion due to the physics glitching out and the (random) time that it took for new cups to arrive; they were sometimes waiting for something to happen. Aside from that, I feel that the instructions were mostly helpful for the amount of time the participants took.

Video 1:

Video 2:

i. Previous sketches

Here are the two previous sketches if you want to see the progress, or you can also click here to access the GitHub repo.

j. Reflection

This proved to be a difficult and very time-consuming final project. While could be understood as possibly annoying, it is the contrary: I enjoyed the process. I felt as I understood the concepts that were taught in class, and I could through without too much of an issue with what I wanted to add. Of course, some features had to be cut in order to complete the final project in time, but the difference this time is that I feel capable of adding them if enough time is provided.

As for the technicality of the project, I could not figure out the solution for the bodies going through bodies if they are at a high speed. This itself is a limitation of matter.js, although I wish there was a solution. Nevertheless, I feel satisfied with how the final project turned out and the new knowledge I possess now. I realized that there are a lot of uses outside p5.js I can use this for.

Thank you for the new knowledge, I deeply appreciate it.

k. Used sources

1. Cunningham, Andrew. “Today I Stumbled upon Microsoft’s 4K Rendering of the Windows XP Wallpaper.” Ars Technica, 8 June 2023, arstechnica.com/gadgets/2023/06/i-just-found-out-that-microsoft-made-a-4k-version-of-the-windows-xp-wallpaper/.

2. “Cursor.” P5js.org, 2024, p5js.org/reference/p5/cursor/. Accessed 2 Dec. 2024.

3. freesound_community. “Highland Winds FX | Royalty-Free Music.” Pixabay.com, 14 June 2023, pixabay.com/sound-effects/highland-winds-fx-56245/. Accessed 26 Nov. 2024.

4. flanniganable. “10b How to Make a Compound Body Matter.js.” YouTube, 4 Dec. 2021, www.youtube.com/watch?v=DR-iMDhUa-0. Accessed 25 Nov. 2024.

5. The Coding Train. “3.6 Graphing Sine Wave.” Thecodingtrain.com, 2016, thecodingtrain.com/tracks/the-nature-of-code-2/noc/3-angles/6-graphing-sine-wave. Accessed 2 Dec. 2024.

6. The Coding Train. “5.21: Matter.js: Mouse Constraints – the Nature of Code.” YouTube, 9 Mar. 2017, www.youtube.com/watch?v=W-ou_sVlTWk. Accessed 25 Nov. 2024.

7. The Coding Train. “9.7: Drawing Object Trails – P5.Js Tutorial.” YouTube, 9 Feb. 2016, www.youtube.com/watch?v=vqE8DMfOajk. Accessed 26 Nov. 2024.

Final Project Draft #2 – Peacefulness in Green

a. The concept

My idea for the final project is to create a relaxing and interactive experience. While this idea can apply to many concepts, I decided to focus myself on recreating (albeit not 100% similar) the following figure:

A table on a park
Figure 1. The inspiration.

And also, the following figure:

Figure 2. My other inspiration.

The idea was to implement everything that we have learned so far in class. Although, due to some concerns that will be shared below, this might be carefully considered depending on the quality outcome. In the following sections of this blog post, the interaction and goals of this sketch will be explained.

b. The current interaction

The interaction was possible to implement, which is mostly a physics interaction with the glass cup and the seeds to grow some plants. I have not thought about other interactions since I think it would be very time-consuming, since I feel that the current focus should be on finishing the visual details for the canvas.

c. The design

Since I have some skills when it comes to image manipulation (not that much of a design master if I am honest), I decided to use Figure 2 as a basis for the background. This was done by manipulating the image using the software GIMP:

Figure 3. Working with GIMP for the background.
Figure 4. Working some more for the background using GIMP.

Some audio background has also been added in order to complement the experience. Nevertheless, in future iterations, audio feedback for the physics objects will be implemented.

d. The difficulties encountered

A quick sketch
Figure 5. The original sketch

Taking into consideration the original sketch, there are some elements that have been added, such as the physics interaction with the bottle with seeds (number 1). Nevertheless, elements such as the generation of patterns for the terrain with cellular automata has proven to be difficult (number 6). Instead, this changed to be like an “old filter”. It is a very subtle effect, but noticeable.

Elements number 2, 3, 4 and 5 are still pending to be added, which are the following:

#2 Ants moving from left to right: The ants represented will be moving through the dirt randomly, although they will try to stay inside an established range with the help of a flow field.

#3 Winds: While they are going to be composed of a particle system, to highlight that winds do exist in the sketch, they are mostly there to provide an additional force for the matter.js bodies.

#4 Birds flying around: These will be done with the help of a flocking system.

#5 A tree with moving leaves: The moving leaves will be simulated with the help of some forces.

If difficulties are encountered again, the ideas for these elements will be rethought in order to have a complete final product.

e. Code I am particularly proud of

Detecting the current position of each ball and then spawning a Perlin walker that moves linearly in the Y axis but randomly on the X axis, while leaving a trail, proved to be difficult. I had to readjust the positioning to match Matter.js:

Code found in classes/walker.js

  show() {
    //Show trail.
    push();
    for (let i = 0; i < this.history.length; i++) {
      let pos = this.history[i];
      ellipse(pos.x, pos.y, this.w);
      noStroke();
      fill(0,200,0);
      /* fill(
        map(noise(seed1), 0, 1, 0, width),
        map(noise(seed2), 0, 1, 0, height),
        map(noise(seed1 + seed2), 0, 1, 0, seed1 + seed2)) Commented since it is not required at the moment. It also looks wrong. */ 
      ;
    }
    pop();
  }

  move() {
    this.history.push(createVector(this.position.x, this.position.y));
    this.position.x = map(
      noise(this.tx),
      -30,
      30,
      this.position.x - 10,
      this.position.x + 10
    );
    /* this.position.y = map(noise(this.ty), 0, 1, this.lastposition, 0); */
    this.tx += 0.1;
  }
}

f. The current progress so far

Here is my second draft, with the current progress, for the final project:

Controls:

Holding mouse left click: Grab body/element
C key: Spawn circle.

Full-screen version: Go to the Full-screen version

g. Reflection on current progress

This has proven to be a difficult task so far, since we have to implement everything we have seen in class. Not only that, but some features I want to add into the sketch requires some time in order to get the desired results. For example, the interaction with the seeds took a lot of time to add, since working in conjunction with Matter.js needs that I approach p5.js rather differently. Likewise, some physics values are still misaligned to properly represented the bodies seen in the sketch.

Still, the idea is to try, and if there are any issues, as mentioned, ideas will be replanned.

h. Used sources

1. Cunningham, Andrew. “Today I Stumbled upon Microsoft’s 4K Rendering of the Windows XP Wallpaper.” Ars Technica, 8 June 2023, arstechnica.com/gadgets/2023/06/i-just-found-out-that-microsoft-made-a-4k-version-of-the-windows-xp-wallpaper/.

2. freesound_community. “Highland Winds FX | Royalty-Free Music.” Pixabay.com, 14 June 2023, pixabay.com/sound-effects/highland-winds-fx-56245/. Accessed 26 Nov. 2024.

3. flanniganable. “10b How to Make a Compound Body Matter.js.” YouTube, 4 Dec. 2021, www.youtube.com/watch?v=DR-iMDhUa-0. Accessed 25 Nov. 2024.

4. The Coding Train. “5.21: Matter.js: Mouse Constraints – the Nature of Code.” YouTube, 9 Mar. 2017, www.youtube.com/watch?v=W-ou_sVlTWk. Accessed 25 Nov. 2024.

5. The Coding Train. “9.7: Drawing Object Trails – P5.Js Tutorial.” YouTube, 9 Feb. 2016, www.youtube.com/watch?v=vqE8DMfOajk. Accessed 26 Nov. 2024.

Final Project Draft #1 – Peacefulness in Green

a. The concept

My idea for the final project is to create a relaxing and interactive experience. While this idea can apply to many concepts, I decided to focus myself on recreating (albeit not 100% similar) the following figure:

A table on a park
Figure 1. The inspiration.

Now, the idea is to implement everything that we have learned in class. In the following sections of this blog post, the interaction and goals of this sketch will be explained.

b. The interaction

The interaction will be mostly done via the mouse input. I have not yet thought about other methods of interaction that can be interesting for the vision I try to approach. Nevertheless, if there is any new one, I will report it on the next draft.

c. Design of the canvas

Since my idea is to make something based on the concept, rather than an exact 1:1 copy, I imagined the following sketch for p5js:

A quick sketch
Figure 2. The sketch of the canvas.

If you noticed, there are some numbers dispersed around the sketch. These represent what key concepts from class they will play in this interactive experience. They are explained as it follows:

      1. Bottle with seeds: These are mostly done with the help of matter.js for the physics. The idea is that, once they fall into the ground, they will stop in where they landed and a plant will grow using Perlin noise. Likewise, the seeds can be affected by the winds that are represented in the number 3.
      2. Ants moving from left to right: The ants represented will be moving through the dirt randomly, although they will try to stay inside an established range with the help of a flow field.
      3. Winds: While they are going to be composed of a particle system, to highlight that winds do exist in the sketch, they are mostly there to provide an additional force for the matter.js bodies.
      4. Birds flying around: These will be done with the help of a flocking system.
      5. A tree with moving leaves: The moving leaves will be simulated with the help of some forces.
      6. Place to grow the seeds: It is basically a combination of grass and dirt. Although, the interesting part of this is that its pattern (to avoid a monotonous appearance) will be done with the help of cellular automata.

d. The current progress

Here is my current progress regarding the final project:

Controls:

Holding mouse left click: Grab body/element
C key: Spawn circle.

Full-screen version: Go to the Full-screen version

e. Used sources

1. flanniganable. “10b How to Make a Compound Body Matter.js.” YouTube, 4 Dec. 2021, www.youtube.com/watch?v=DR-iMDhUa-0. Accessed 25 Nov. 2024.

2. The Coding Train. “5.21: Matter.js: Mouse Constraints – the Nature of Code.” YouTube, 9 Mar. 2017, www.youtube.com/watch?v=W-ou_sVlTWk. Accessed 25 Nov. 2024.

Week #11 – Creative Bankruptcy

The concept

As the titles indicates, this sketch is about being creatively bankrupt. Why creatively bankrupt, might you ask? This mental state involves a constant black and white noise (as those seen in TV when there is no signal). It is a state in which no ideas flow, where ideas are not as good as you thought. Frustrating to say the least. Nevertheless, creative bankruptcy itself can be expressed as art.

Anybody remember rubbing your hand across the TV screen static? : r/nostalgia
Figure 1. CRT filled with static noise.

With this concept in mind, I wanted to do something similar with cellular automata. Therefore, I present you my newest sketch: “Creative Bankruptcy”

Controls:

Mouse Click: Start music.
Moving mouse while pressed: Rotate through the X, Y and Z axis.
Z key: Start from the beginning with a new rule value (new pattern).
X key: Stop generating scan lines
C key: Clear background.

Full-screen version: Creative Bankruptcy

Brief explanation of the code

The code work in the following manner:

1. Since we are working with cellular automata, a system needs to be in place in order to work. The vision I was seeking for required for me to create an array that hosts multiple classes for every cellular automata. So, the idea is to store multiple classes inside the array and then use the custom function of prepare() with each one of them.

//Prepare celular spawners.
//Parameters for spawning a celular spawner: (ruleValue, w, y, direction).
cells.push(new CelularSpawner(int(random(255)), 5, 0, 0));
cells.push(new CelularSpawner(int(random(255)), 5, 0, 0));
cells.push(new CelularSpawner(int(random(255)), 5, 0, 0));
cells.push(new CelularSpawner(int(random(255)), 5, 0, 0));

//Prepare the celular automata spawners.
for (let i = 0; i < cells.length; i++) {
  cells[i].prepare();
}

The function prepare() prepares the cellular automata spawner by analyzing the total width of the canvas and then filling each cell by the establish width in the parameters to properly fill it out and follow the pattern with calculateState(a, b, c):

prepare() {
  this.ruleSet = this.ruleValue.toString(2).padStart(8, "0");

  let total = width / this.w;
  for (let i = 0; i < total; i++) {
    this.cells[i] = 0;
  }
  this.cells[floor(total / 2)] = 1;
}
calculateState(a, b, c) {
  let ruleset_length = this.ruleSet.length;

  let neighborhood = "" + a + b + c;
  let value = ruleset_length - 1 - parseInt(neighborhood, 2);
  return parseInt(this.ruleSet[value]);
}

2. For reasons I will explain later, I decided to use WEBGL to generate a different effect on the canvas. This is due to the fact that, since the canvas was seeking to transmit a feeling of watching it on CRT, the shader support was limited to only WEBGL. Despite shaders not being used for this sketch, the rotation of it to generate different patterns was left with the function orbitControl(1,1,1).

3. Being inspired by “Following Uncertainty”, I decided to implement, again, audio spectrum visualizer. Although, this one is represented through an image that increases its sizes accordingly through a plane.

The creative bankruptcy behind it (A self reflection and what I could be proud of)

This section is more of a self-reflection on why this assignment was so hard for me, despite my other sketches being more complex. It seems that, at the end of the semester, the burnout catches up. It is frustrating since I had many ideas that I wanted to explore in this sketch:

      1. Boxes with physics done by matter.js that each location is generated by the patterns of cellular automata.
      2. A CRT like canvas done with the use of shaders.
      3. An image being filled by the patterns generated by cellular automata.
      4. An album like done with four sections divided in the screen that are filled by cellular automata.

All of these ideas (kind of) eventually arrived into one. Despite having artistic qualities, it is still not as creative as I wanted it to be. It is frustrating to not being able to implement new ideas due to the aforementioned creative bankruptcy. But as everything in life, we will not get the results we want in one try, and in my case, I should have tried more in other to get a more proper system going on.

For the final project, I will revise all of my previous ideas into something interesting. All of this knowledge I have accumulated into the class will not go unused.

Used sources:

1. Aesela. “𝒀𝒗𝒆𝒔 𝑻𝒖𝒎𝒐𝒓 • 𝑳𝒊𝒎𝒆𝒓𝒆𝒏𝒄𝒆 • 𝑨𝒏𝒈𝒆𝒍𝒊𝒄 𝑽𝒆𝒓𝒔𝒊𝒐𝒏.” YouTube, 24 Apr. 2022, www.youtube.com/watch?v=FfQoshkVChk. Accessed 22 Nov. 2024.

2. “Animated GIFs by Kjhollen -P5.Js Web Editor.” P5js.org, 2024, editor.p5js.org/kjhollen/sketches/S1bVzeF8Z. Accessed 22 Nov. 2024.

3. “CreateImage.” P5js.org, 2024, p5js.org/reference/p5/createImage/. Accessed 22 Nov. 2024.

4. “ShaderToy CRT by Keithohara -P5.Js Web Editor.” P5js.org, 2024, editor.p5js.org/keithohara/sketches/xGU1a8ty-. Accessed 22 Nov. 2024.

5. Tenor.com, 2024, media.tenor.com/88dnH_mHRLAAAAAM/static-tv-static.gif. Accessed 22 Nov. 2024.

6. The Coding Train. “Coding Challenge 179: Elementary Cellular Automata.” YouTube, 9 Jan. 2024, www.youtube.com/watch?v=Ggxt06qSAe4.

Week #10 – Sound of Triangle

Concept

I will be honest, I did not have that much of ideas for this week assignment… For some reason. Nevertheless, while experimenting with Matter.js I found myself with some interesting behaviors, such as gravity manipulation and collisions. Since I had a bit of interest in adding sound into my projects, I wondered how could I deliver something with at least a bit of creativity and interaction.

Sadly, most of the ideas that came into my mind were time-consuming, and thus, would be impossible to complete on time. Still, one was possible: A triangle which produces sound via the collision of circles.

Embedded sketch

Note: You can click on the Canva to spawn more circles.

Full-screen version: Go to the Full-screen version

Brief explanation of the code

The code itself is simple thanks to the use of Matter.js. That means that all the collision and interaction between bodies are managed by the library. Now, what is happening in this code is the following:

First, a set of circle bodies will be spawned and then attracted to the static circle in the middle:

//Draw circles.
for (let i = 0; i < circles.length; i++) {
  //Attract to attractor and then display.
  let force = attractor.attract(circles[i]);
  circles[i].applyForce(force);
  circles[i].show();
  //Check if there is any geometry outside the canvas.
  if (circles[i].isOffScreen()) {
    circles[i].removeFromWorld();
    circles.splice(i, 1);
    i--; //This fixes the flickering in the code.
  }
}

Secondly, while they are being pulled to the attractor, the circle bodies can move erratically around it due to the force applied. During this erratic movement, they can hit one of the three boundaries forming a triangle, or other circles. So, on hit, they will trigger an event in which a sound will reproduce (only when a boundary is hit) as well as change the color:

Collisions function:

//Done with help of the following material: https://nature-of-code-2nd-edition.netlify.app/physics-libraries/#collision-events
function handleCollisions(event) {
  for (let pair of event.pairs) {
    let bodyA = pair.bodyA;
    let bodyB = pair.bodyB;

    //Retrieve the particles associated with the colliding bodies via the plugin.
    let particleA = bodyA.plugin.particle;
    let particleB = bodyB.plugin.particle;

    if (particleA instanceof Circle && particleB instanceof Circle) {
      particleA.change();
      particleB.change();
    }

    if (particleA instanceof Boundary && particleB instanceof Circle) {
      particleA.change();
      particleB.change();
      bell.play();
    }
  }
}

change() function of boundary.js:

change() {
  this.col = color(random(100, 255));
}

circle() function of circle.js:

change() {
  this.col = color(random(100, 255));
  this.r = random(0, 10);
}

There is also some code that helps with optimization, such as in the case that the circles go out boundaries, as well as cleaning the array appropriately:

//Check if there is any geometry outside the canvas.
if (circles[i].isOffScreen()) {
  circles[i].removeFromWorld();
  circles.splice(i, 1);
  i--; //This fixes the flickering in the code.
}

Reflection and ideas for future work or improvements

I feel that this task end up being uninspiring. While simplistic and stylish in his own way, there are other interactions I would wish to implement. Such interactions include more “artistic” expressions once the circles hit the boundaries, or a more intricate physics simulation where the boundaries could be dynamically moved according to time (as in rotating in a 360 degree manner). I am confident that some ideas will be implemented in future projects, but at the moment, let’s conclude that this is still a phase of learning how to use Matter.js.

Used resources

a. “6. Physics Libraries.” Netlify.app, 2014, nature-of-code-2nd-edition.netlify.app/physics-libraries/#collision-events. Accessed 12 Nov. 2024.

b. “6.1 Matter.js – Introduction.” Thecodingtrain.com, thecodingtrain.com/tracks/the-nature-of-code-2/noc/6-physics-libraries/1-matterjs-introduction.

c. “6.2 Matter.js – Introduction, Continued.” Thecodingtrain.com, 2016, thecodingtrain.com/tracks/the-nature-of-code-2/noc/6-physics-libraries/2-matterjs-introduction-continued. Accessed 12 Nov. 2024.

d. “6.9 Matter.js Attraction by Natureofcode -P5.Js Web Editor.” P5js.org, 2024, editor.p5js.org/natureofcode/sketches/16sblEvax. Accessed 12 Nov. 2024.

e. “Freesound – BELL 0101.Wav by Zgump.” Freesound.org, 2024, freesound.org/people/zgump/sounds/83538/. Accessed 12 Nov. 2024.

Week #9 – Following uncertainty

Concept

I had a curious inspiration while I was going in a bus to campus. I was staring at the window, looking silently at the night, and this silent appreciation was then followed by the next music suggestion in my music app: DIIV – Taker.

It was a weirdly melancholic song, the type of beat I like: melancholic, but not to excessive levels to induce sadness, but rather, a peace calmness. And this is the type of feeling I got from listening to this music, calmness. Thus, for this week assignment, I wanted to share what I felt with a music visualization using flock systems.

Embedded sketch

Note: If the p5.js version is slow, it is suggested to try either this version or make a copy of the GitHub’s repo and run it locally on the computer.

Make sure to click on the Canva to start with the visualization!

Full-screen: Full-screen version

Brief explanation of the code

The flock system is divided on multiple parts, which are activated according to the time of the song; it is easily done with the value returned from the function song.currentTime(). Here is a quick example:

Let’s say that I want to generate the wave effect that appears at the beginning, for this, I create the following parameters inside a custom function called startPart(value):

The wave code is located in the second if condition (value == 2).

function startPart(value) {
  if (value == 1) {
    for (let boid of flock) {
      //Reset value.
      boid.velocity.mult(0);
      boid.maxForce = 0.0;
      //Avoid boids from going out from the borders of the screen.
      boid.transparency = 1;
      boid.acceleration.add(random(-2, 2), random(-0.5, 0.5));
      boid.update_values(1); //Updates the boundaries to the first phase values.
      part = 1;
    }
  }

  //THIS IS THE WAVE CODE
  if (value == 2) {
    for (let boid of flock) {
      //Reset value.
      boid.velocity.mult(0);

      //Assign maxForce
      boid.maxForce = 0.01;

      //Avoid boids from going out from the borders of the screen.
      boid.transparency = 10;
      boid.acceleration.add(random(1, 3), random(-1, 1));
      boid.update_values(2); //Updates the boundaries to the first phase values.
      part = 2;
    }
  }

And then, the specific part is called with the following custom function checkAudioTime() on the second 14 of the song:

function checkAudioTime() {
  if (round(audio.currentTime(), 0) == 6) {
    startPart(1);
  }

  if (round(audio.currentTime(), 0) == 14) {
    startPart(2);
  }

It is important to note that checkAudioTime()is called continuously under draw().

Highlight of some code that I am particularly proud of

I am mostly proud of the patterns I created for this visualization. In total, there are 11 variations which are divided between two flocking systems. I will not paste all the variations here, since it is almost 300 lines of code, but I will share three examples of it:

if (value == 9) {
  for (let boid of flock_outside) {
    //Reset value.
    boid.velocity.mult(0);

    //Assign maxForce
    boid.maxForce = 0.01;
    boid.maxSpeed = 1;
    boid.perception_radius = 50;

    //Avoid boids from going out from the borders of the screen.
    boid.transparency = 50;
    boid.acceleration.add(random(-1, 1), random(-1, 1));
    boid.update_values(6); //Updates the boundaries to the first phase values.
    part = 3;
  }
}

if (value == 10) {
  for (let boid of flock_outside) {
    //Reset value.
    boid.velocity.mult(0);
    boid.maxForce = 1;
    boid.transparency = 5;
    boid.acceleration.add(random(0), random(10));
  }

  for (let boid of flock) {
    //Reset value.
    boid.velocity.mult(0);
    boid.maxForce = 1;
    boid.transparency = 5;
    boid.acceleration.add(random(0), random(10));
  }
}

if (value == 11) {
  for (let boid of flock_outside) {
    //Reset value.
    boid.update_values(7);
  }

  for (let boid of flock) {
    //Reset value.
    boid.update_values(7);
  }
  part = 6;
}

Reflection and ideas for future work or improvements

I am mostly proud of this work. It is by far the assignment I have spent the most time on (or probably the second one). It was an enjoyable challenge, which I felt really curious about what kind of results I could get with the flocking systems. Although, I felt that some patterns in the visualization are rather simplistic and should have been reacting to the sound.

Not to imply that I did not try to implement more reactions that are based on the frequencies of the song, but after some attempts, it was best to disregard the idea since it would consume a lot of time.

Used resources

17.11: Sound Visualization: Frequency Analysis with FFT – p5.js Sound Tutorial

Coding Challenge 124: Flocking Simulation

DIIV // Taker (Official Audio)

Week #8 – Ants want to go to their home

Concept

For this assignment, I wanted to implement something rather simple, but entertaining to play with. So, to come with some ideas, I reflected upon the material given in class and had a sudden realization that the autonomous agents concepts and examples looked like how ants behave.

So with this realization in mind, I decided to code ants trying to reach their home, while they try to avoid the flashlights.

Embedded sketch

Link to full-screen version: Full-screen version of the sketch

Brief explanation of the code

The code possess three main characteristics:

      • Arrival
      • Evade
      • Randomized movement across the Canva with the help of a flowfield.

At the beginning of the program, an ant will spawn, which will make the final destination the nest. After the ant has moved a certain distance, another ant will spawn. Although, the ants can have some troubles getting into the nest if the flashlights are switched on, since they would have to avoid them. Likewise, to avoid a monotonous movement, the concept of flow fields (using Perlin Noise to help with the random generation) was added into the Canva to let ants move more naturally; their movements are more unpredictable.

Highlight of some code that I am particularly proud of

The hardest part, at least for this code, was to find a way to properly toggle ON and OFF the flashlights, as well as moving them across the Canva. While this seemed like an easy task at first, I forgot that sometimes coding can be hard for no reason. For example, the first flashlight would work, but the second not. Although, if you moved the second flashlight closer to the left side of the canvas, suddenly it worked!

It was confusing, but at the end, this was the code that worked:

First part of the logic (mouse is being pressed on a flashlight to move it):

 for (let i = 0; i < flashlights.length; i++) {
   flashlights[i].display();

   if(mouseIsPressed == true){
     if (
       mouseX > flashlights[i].position.x &&
       mouseX < flashlights[i].position.x + flashlights[i].r + 60 &&
       mouseY > flashlights[i].position.y &&
       mouseY < flashlights[i].position.y + flashlights[i].r + 180
     ) {
 
       //Check just in case if clicked element exists.
       let index = flashlights.indexOf(flashlights[i]);
       if (index > -1) {
         flashlights[index].position.x = mouseX-30;
         flashlights[index].position.y = mouseY-95;
       }
     }
   }
}

Second part of the logic (mouse is pressed over a flashlight to turn ON or OFF the light):

function mousePressed() {
    for (let i = 0; i < flashlights.length; i++) {
      if (
        mouseX > flashlights[i].position.x &&
        mouseX < flashlights[i].position.x + flashlights[i].r + 60 &&
        mouseY > flashlights[i].position.y &&
        mouseY < flashlights[i].position.y + flashlights[i].r + 180
      ) {
  
        //Check just in case if clicked element exists.
        let index = flashlights.indexOf(flashlights[i]);
        if (index > -1) {
          if (flashlights[index].state == 0) {
            flashlights[index].state = 1;
          } else if (flashlights[index].state == 1) {
            flashlights[index].state = 0;
          }
          flashlight_button_sound.play();
        }
      }
   }
}

Reflection and ideas for future work or improvements

I feel that there could be more original ideas and experimentation implemented in this program, since I feel that I only use class material in a very copy and paste fashion. Not to imply that I feel that I did not put effort into this assignment, rather, how I should have gone more outside the box.

Now, regarding the code itself, some improvements are:

      • Ants spawn in different points in the Y axis.
      • Ants avoid the flashlights in a more believable manner.
      • Flashlights can not be overlapped between each other.

Used resources

SOme extra Concepts:

a. https://stackoverflow.com/questions/5767325/how-can-i-remove-a-specific-item-from-an-array-in-javascript

Images:

a. https://www.shutterstock.com/search/dirt-ground-grass

b. https://www.freepik.com/premium-vector/large-worker-ant-top-view-vector-illustration-isolated-white-background_21352776.htm

c. https://media.istockphoto.com/id/1486076388/photo/anthill-top-view.jpg?s=612×612&w=0&k=20&c=rcpRqTgk4lHhqFg_qssf9Qoi4s_UshYTToeKmOH18bI=

Audio:

a. https://freesound.org/people/Sjonas88/sounds/538554/

b. https://freesound.org/people/baidonovan/sounds/187335/

c. https://freesound.org/people/naturesoundspa/sounds/163597/

Week #8 – Reflection on lecture by guest artists

While listening to the lecture, I found myself reflecting on how coding concepts can blend seamlessly with real life. By this I mean that, if we apply some real-life principles to our programs, and then demonstrate them with visual references, the result can be interesting.

One example mentioned in the lecture was the illusion of sand falling in a gradual, realistic way. This is only possible thanks to the knowledge accumulated over the years and a creative approach to projecting it using sand as the medium. This made me realize that coding is not just about solving logical problems; it is also about tackling creative ones.

Midterm Project – Generative Clock

Concept

This was a sketch that took some time to fully realize what my final concept was. First, I thought about being inspired by my sketch “2000s qwerty” and integrate key caps into the midterm with a clock. Although, when I finished a quick draft of it, I did not like the end result: It was very uninspired.

Figure 1. Initial sketch.

However, the clock functionality was giving promising results and more ideas.

After deleting the key caps out of the sketch, I started experimenting with the clock I made, trying to understand what kind of creative variations I could do with it. After some time of thinking, I decided that it was best to add certain functionalities to each hand, but at the same time, that each function somehow helps in filling the background to generate the silhouette of a clock. The end result can be seen in the following sketch.

Sketch

Note: By clicking on the canvas, it will generate a .svg file of what is currently seen on screen. Likewise, by pressing the space bar, the color scheme will toggle between either colorful (the default) or black and white.

Full-screen version: Fullscreen version of “Generative Clock v1.0”

The functionality

Since the idea of the midterm was to implement different concepts we have seen so far in class, I decided to add each one in a “natural” manner. The functionalities are the following:

      1. Vectors: Everything is composed by vectors.
      2. Clock hands using angles: These, according to the system’s time, will move accordingly as if it was a real analog clock. The way that the position of the hands is determined is by, first, catching the current time of the system, to then translate and map the vector values of each hand to an angle (with the help of theta).
      3. Physics: The sketch possesses gravity, acceleration, and attraction. For example, every time a second passes, a tiny particle will spawn in the X and Y coordinates of the millisecond hand. After than, they will get attracted to the seconds hand and fly around it using the aforementioned physics.
      4. Perlin Noise: The particles that fly around the seconds hand will have their colors changed using the Perlin noise, which grabs the current system time to move smoothly in the RGB values.
      5. Particles system: Each particle that loops around the seconds hand will get deleted after some time, to avoid consuming more resources of the computer.

Highlight of the code I am proud of

The hardest part of this code was translating the system time to the accurate position of the clock’s hand, since it needed precise values in order to be properly represented using angles:

//Move the hands in a circular motion, according to system time.
update(hours, minutes, seconds, milliseconds){


    // Convert polar to cartesian  (Taken from an example from class).
    this.position = p5.Vector.fromAngle(this.theta);
    this.position.mult(this.r);

    if (this.type_of_hand == "hours"){
        this.theta = map(hours, 0, 198, -51.8, 51.8);   //-51.8 seems to be the value to simulate a clock.

    } else if (this.type_of_hand == "minutes"){
        this.theta = map(minutes, 0, 1000, -51.8, 51.8);
    }

    else if (this.type_of_hand == "seconds"){
        this.theta = map(seconds, 0, 1000, -51.8, 51.8);
    }
    
    else if (this.type_of_hand == "milliseconds”){
        this.theta = map(milliseconds, 0, 15800, -51.8, 51.8);
    }
}

Images

Figure 2. Clock without the generative background.
Figure 3. Clock with the generative background in colorful mode.
Figure 4. Clock with generative background in black and white mode.

Pen Plotting

For the pen plotting in a A3 paper, I had to create a different version in order to be easily drawn, since the original version would create a .svg file that would take too much time to plot. This involved taking some artistic decisions, such as altering the pattern and physics to avoid creating many circles.

Figure 5. Generative Clock made with pen plotter.

Printed version

For the printed version, the  was used to develop the following:

Figure 6. Black and white version of the Generative Clock printed on a A3 paper.
Figure 7. Colorful version of the Generative Clock printed on a A3 paper.

Reflection and future improvements

I am happy with the progress so far for this midterm. The concepts that I applied from class (in my opinion) seem to integrate seamlessly with the concept of the project. Although, one thing that I would like to implement is a functionality for the hours hand, although it would seem a bit unnecessary since it will take too long to move. Likewise, I would like to implement another feature which could help the Canva appear more interesting visually, but I have yet to come with new ideas.

Used Sources

Week #5 – Midterm Report #1

Concept & Design

For the midterm, I had various ideas. Although, most of them were a variation from week 4’s assignment. The brainstorming process was one that took me time, since I was thinking to myself: “How do I blend everything that we have learned so far?”. And this is where a bit of a realization came to me.

In my last week assignment, I commented how I wanted to create like a “face”, composed by two eyes represented as a spiral of key caps. Although, the end result would have been weird. Still, with this idea, I continued brainstorming until I realized the following draft:

Quick sketch of an analog clock composed of key caps.
Figure 1. Quick sketch of an analog clock composed of key caps.

Basically, my idea is to create an analog clock, composed of multiple hands that indicate time, as well as being surrounded by key caps that will define most of the features and interactions for this generative art. So, once I arrived with the idea, it was time to develop it and determine the key features.

Key features

      1. Time accurate: The clock seen in the Canva is accurate to the time present in the computer.
      2. Sound: As seen in my week 4’s assignment, I will integrate sound into this project to complement the experience. It will be triggered once the keycaps touch any of the hands from the analog clock. While I am still thinking about this feature, what is clear is that it will be mainly composed of mechanical keyboard sounds.
      3. Physics: I have not yet defined how physics will play a mayor role in this sketch, but what I want to feature the most is key caps falling and disappearing with a proper particle system.
      4. Magnetism: Using the mouse as an attractor, I plan to make the key caps falling be collected with the mouse if it is pressed.
      5. Perlin noise for color: This is yet another feature I am thinking how it will be integrated, but it could be for all the entities in the canva. In other words, according to their position, the color will change smoothly.

Current Progress

Here is my current progress:

Frightening parts

At the moment, the most frightening parts are the interaction with the key caps and sound. This is due to the nature of this code: The key caps move too fast, and it will overlap the sounds.

Another frightening part, although it is already done, was the integration of the system’s time with the Canva. This was done using the JavaScript default class Date and its functions and adjusting the value of theta via the function map();

Here is the feature code of the moving hands, of the analog clock, which took me the most time:

update(hours, minutes, seconds, milliseconds){
        // Convert polar to cartesian  (Taken from an example from class).
        this.position = p5.Vector.fromAngle(this.theta);
        this.position.mult(this.r);

        if (this.type_of_hand == "hours"){
            this.theta = map(hours, 0, 390, -51.8, 51.8);   //-51.8 seems to be the value to simulate a clock.

        } else if (this.type_of_hand == "minutes"){
            this.theta = map(minutes, 0, 1000, -51.8, 51.8);
        }

        else if (this.type_of_hand == "seconds"){
            this.theta = map(seconds, 0, 1000, -51.8, 51.8);
        }
        
        else if (this.type_of_hand == "milliseconds"){
            this.theta = map(milliseconds, 0, 15800, -51.8, 51.8);
        }
    }

Finding the correct values to map each hand took a lot of time since, most attempts, resulted in the hands being desynchronized with the system’s time.

Reducing risks

To avoid delivering an uncompleted midterm project, I plan to do the following:

      • If a certain part of the code is too hard to develop, I will refer to the class material as well as the multiple examples in order to understand how something works.
      • If there are some unclear details in how to proceed, I should arrange office hours with the professor.
      • Spend between 1–2 hours a day developing the key features.

Future improvements

I would like to improve this sketch by doing the following:

      • Adding better aesthetics and with a more of a “generative” touch. Like, for example, if a key cap is touch then generate a series of letters around it following Perlin noise.
      • Add the mechanical keyboard sound.
      • Develop a background and not from an external source.
      • Define better what kind of interaction will the user have with the mouse.

Used sources

      1. How to get current time in JavaScript by geeksforgeeks