Submodule 18.1: Image in p5.js I

Site: ΕΛ/ΛΑΚ Moodle
Course: Study / Web Design and Web Development
Book: Submodule 18.1: Image in p5.js I
Printed by: Guest user
Date: Friday, 26 April 2024, 5:44 PM

Description

  • Images in p5.js
  • get() and set()
  • pixels array

Images in p5.js

There are two ways to include images in p5.js

The first way is to display an image after the image has been load.

In order to do that we go in the setup() function and we write the following code:

function setup() {
 createCanvas(width, height);
  loadImage('myfolder/myImage.jpg', function(myImg) {
    image(myImg, 0, 0);
  });
}

In the above code, inside the loadImage() we have the path to the folder and the function to display the image. The function parameter myImg, holds as value our image.

The image(myImg, 0, 0); is what displays the image. The 0,0 are the x and y coordinates where the image will be placed.

Using the above way, we may encounter some problems in our project because the image may not be immediately available for rendering.

If we want to first load the image and then start doing things with it, it is better to use the second way:

let myImg;
function preload() {
  myImg = loadImage('myfolder/myImage.jpg');
}
function setup() {
createCanvas(width, height); image(myImg, 0, 0); }

The  preload() function should always be used before the setup() function. When used, the setup() waits until the loading has completed in order to start running. 

get() and set()

In p5.js we can use get() in order to get a region of pixels from an image.

This function accepts 4 arguments:

get(x,y,w,h)

If it is used without arguments, the image stays as it was.

If it is used with only x,y arguments, a pixel is extracted.

If it is used with all parameters, a rectangular area is extracted.

set() is used together with createImage() and loadPixels(). The logic is that we first create a new image in the p5.js and we load its pixels. In continue we set the new image.

Let's see an example to understand better what these functions are doing.

Example 

Here is an example code which uses all of get() , set(), createImage() and loadPixels() :

// define two variables for the images
let choco1, choco2;
// use preload to load the image before setup
function preload() {
  choco1 = loadImage("images/choco.jpg");
}
function setup() {
  // create canvas with the same size as the images
  createCanvas(110,110);
  // create a new image
  choco2 = createImage(110, 110);
  // load the pixel array of the image in order to be able to manipulate them
  choco2.loadPixels();
  // go through each row of the choco1 image
  for (let y = 0; y < height; y++) {
    // go through each column of the choco1 image
    for (let x = 0; x < width; x++) {
      // use get() to take each pixel
      let myPixel = choco1.get(x, y);
      // set it to the opposite corner (turn image upside down)
      choco2.set(width - x, height - y, myPixel);
    }
  }
  // update the pixel array of the choco2 image
  choco2.updatePixels();
  // display the new image
  image(choco2, 0, 0);
}

You can see the result of the above code here

Exercise

  1. Open your Visual Studio editor and the p5yourName folder.
  2. Open the file ex812.js in your editor and save it as ex1012.js
  3. Open the file ex812.html in your editor and save it as ex1012.html
  4. In the ex1012.html file, update the link to ex1012.js  from exersice812.js
  5. Go to the index.html file and create, under Module 10, a link to the ex1012.html  file with the title "get() and set()".

Modify the ex1012.jsfile and use as a base the above example to create an image that starts from the middle of the x-axis and ends at the end of the width. You can see here an example.

Answer:

// define two variables for the images
let choco1, choco2;
// use preload to load the image before setup
function preload() {
  choco1 = loadImage("images/choco.jpg");
}
function setup() {
  // create canvas with the same size as the images
  createCanvas(110,110);
  // create a new image
  choco2 = createImage(110, 110);
  // load the pixel array of the image in order to be able to manipulate them
  choco2.loadPixels();
  // go through each row of the choco1 image
  for (let y = 0; y < height; y++) {
    // go through the middle of the choco1 image to the end
    for (let x = 25; x < width; x++) {
      // use get() to take each pixel
      let myPixel = choco1.get(x, y);
      // set the x and y of the image
      choco2.set(x, y, myPixel);
    }
  }
  // update the pixel array of the choco2 image
  choco2.updatePixels();
  // display the new image
  image(choco2, 0, 0);
}

Do a Git commit with the message "get() and set()".

pixels array

In the previous example, we show how we can display and manipulate an image in p5.js.

However, as you may have noticed, this method requires some time even for small images. If we had a bigger image, then the program would run very slow.

Using pixels to display an image, not only saves a lot of time, but also gives us a lot of manipulation options.

So, how do you access pixels of an image?

As you already know, each pixel has 4 values: R(red), G(green) B(blue) and A(alpha).

In p5.js we have an array called pixels array. This array holds the RGBA values for every single pixel of our canvas, thus 1 pixel will have 4 values in the array.

In order to manipulate the pixels, we need to be able to go through that array.

To do this we use the formula: (x+y*width)*4

In order to understand the formula, watch the video

.

Example 

Here is an example code which use the pixel array to manipulate the colors of an image according to mouseX and mouseY position. Note how we access the R and B values of each pixel:

// create a variable for the image
let chocos;
// preload image
function preload() {
  chocos = loadImage("images/chocos.jpg");
}

function setup() {
  // create canvas the same size as the image
  createCanvas(800,562);
}

function draw() {
  // show the 'initial image
  chocos.loadPixels();
  // go through each row
  for (let y = 0; y < height; y++) {
    // and each column
    for(let x = 0; x < width; x++) {
      // go through all pixels of image, R, G, B, and A
      let index = (x + y * width) * 4;
      // play with rgb values
        chocos.pixels[index] = mouseY; // red
        chocos.pixels[index + 2] = mouseX; // blue
      }
    }
    chocos.updatePixels();
    // display manipulated image
  image(chocos, 0, 0);
}

You can see the result of the above code here

Exercise

  1. Open your Visual Studio editor and the p5yourName folder.
  2. Open the file ex812.js in your editor and save it as ex1013.js
  3. Open the file ex812.html in your editor and save it as ex1013.html
  4. In the ex1013.html file, update the link to ex921.js  from exersice812.js
  5. Go to the index.html file and create, under Module 10, a link to the ex1013.html  file with the title "pixels array".

Modify the ex1013.jsfile and using as a base the above example, manipulate the image using random() to create an olds television "snow" effect. You can see here an example.

Answer:

// create a variable for the image
let chocos;
// preload image
function preload() {
  chocos = loadImage("images/chocos.jpg");
}

function setup() {
  // create canvas the same size as the image
  createCanvas(800,562);
}

function draw() {
  // show the 'initial image
  chocos.loadPixels();
  // go through each row
  for (let y = 0; y < height; y++) {
    // and each column
    for(let x = 0; x < width; x++) {
      // go through all pixels of image, R, G, B, and A
      let index = (x + y * width) * 4;
      // play with rgb values
      // create an old television effect
        chocos.pixels[index] = random(255); // red
        chocos.pixels[index + 2] = random(0,155); // blue
     
      }
    }
    chocos.updatePixels();
    // display manipulated image
  image(chocos, 0, 0);
}

Do a Git commit with the message "pixels array".

  • See more about the pixels array