Jenn Wonjung Choi

 NYU ITP 2026  




Welcome !

This is Jenn’s blog.
Let’s talk, record, archive. 

 Intro to Comp Media

– Week1 –––––––––––––––––––––––––––––––––––––––––––  
  • Worksheet assignment


<Statement>  

  I believe that art is a means of expanding a person's experience and thinking. Over the past few centuries, many artworks and sculptures have inspired, entertained, and even comforted people. In the era we live in now, most people are used to the web and mobile environment. The internet is a constant part of their daily lives. As designers and artists, we need to think about how to communicate inspiration in new ways in spaces that are part of their lives.

  I aspire to become a UX designer. Through this class, I hope to understand web environments and computation and become a bridge between technology and human experience. I hope to combine physical computing and ICM classes this semester to create new experiences for people.





Start with this sketch. 
Where should createCanvas() go?


function setup() {                  
createCanvas(400,400);
}function draw() {
background(400);
}
Start with this sketch.  Move the commented code at the top to where you think it should go: setup(), draw()or leave it where it is.


 // Code that describes the starting position of a shape that will move
let x = 50;
let y = 50;function setup() {
createCanvas(400, 400);
}
function draw() {
background(220);
 // Code that changes the position of the shape over time
x++;
 y++; // Prevent the rectangle from moving off the canvas
 if (x > width) {
 x = -50; // go back to left when it gets out of screen }
 if (y > height) {
 y = -50; // go up when it gets out of screen }
 }// Code to draw the shape
rect(x, y, 50, 50); // Code that describes mouse interaction
 if (mouseX > x && mouseX < x + 50 && mouseY > y && mouseY < y + 50) {
 x = mouseX - 25;
}
}


Reproduce the above image with code. Be as accurate and precise as possible.



// Canvas drawing
function setup() {
createCanvas(800, 600);
 }// background
function draw() {
background(3,255,255); // blue background
 
 // red line
 stroke(255,0,0); // red color
 strokeWeight(45); // line weignt
 line(0,0, 800, 600); // line position
 
 
 //draw the ellipse with no stroke
 noStroke()
fill(0,200,2) //ellipse color
ellipse(400,300,380,290)
 
 //draw the square with no stroke
 noStroke()
 fill(0,0,128) //square color
 square(540,240,50)
}

  • Drawing my portraitdrawing mechanism



function setup() {                          
   createCanvas(400, 400);
   background(100); // grey
   angleMode(DEGREES);


 // bottom hair shape
     fill(139, 69, 19); // brown hair
     noStroke();
     beginShape();
     vertex(350, 350); 
     vertex(50, 350);
     vertex(110, 90);
     vertex(290, 90); 
    endShape(CLOSE);                        

// face shape
     fill(252,243,220); // face tone
     noStroke();
     ellipse(200, 190, 220, 250);


  // right top hair shape
  push();//rotate only hair
  rotate(45);
  fill(139, 69, 19); // brown hair
  ellipse(260, -110, 170, 70);
  pop();

  // left top hair shape
  push();//rotate only hair
  rotate(135);
  fill(139, 69, 19); // brown hair
  ellipse(-20, -170, 170, 70);
  pop();


// left hand-eye
 fill(0, 191, 255); // blue
           
 beginShape();
 vertex(120, 160); // wrist  start
 vertex(110, 130); // finger start
 vertex(115, 110); // first finger
 vertex(125, 115);
 vertex(130, 100); // second  finger
 vertex(140, 110);
 vertex(145, 95);  // third finger
 vertex(155, 110);
 vertex(160, 100); // fourth finger
 vertex(165, 115);
 vertex(170, 130); // fifth finger
 vertex(160, 160); // wrist  end
 endShape(CLOSE);





  // right hand-eye
  beginShape();
 vertex(240, 160); // wrist  start
 vertex(230, 130); // finger start
 vertex(235, 110); // first finger
  vertex(245, 115);
 vertex(250, 100); // second  finger
  vertex(260, 110);
 vertex(265, 95);  // third finger
  vertex(275, 110);
 vertex(280, 100); // fourth finger
  vertex(285, 115);
 vertex(290, 130); // fifth finger
 vertex(280, 160); // wrist  end
  endShape(CLOSE);

  // left eye
  fill(0); // black
  ellipse(140, 140, 20, 20);
  // right eye
  ellipse(260, 140, 20, 20);

  // eyelash
  stroke(0); //black
  strokeWeight(3); 
  //left
  line(135, 130, 130, 120);
  line(140, 130, 140, 120);
  line(145, 130, 150, 120);
  //right
  line(255, 130, 250, 120);
  line(260, 130, 260, 120);                   line(265, 130, 270, 120);

 
// nose
  fill(255, 204, 0); // yellow
  triangle(205, 165, 215, 210, 195, 210); // shape

  // mouth
 fill(255, 0, 0); // red
  noStroke();
 arc(200, 260, 80, 60, 0, 180);


}




– Week2 –––––––––––––––––––––––––––––––––––––––––––


  • Worksheet assignment


  1. Start with this sketch. The default p5 arguments for the rect() function are: x, y, w, h where x, y are the coordinate for the top left corner and w, h are the width and height of the rectangle. What are other ways to define a rectangle? Make up your own arguments for rect()? Come up with at least 2 sets. 


     - First test to make rotating rectangle

     
   
- Findings -> to applicate WEBGL, I had to put all the 
width and height of the rectangle even if they are same.


      Final!

     





  •      2. Draw a rectangle in the middle of the screen that is half the width and half the height of the canvas. Write it so that you can change the size of the canvas and the rectangle will stay in the center and maintain its size relationship to the canvas.


         
   



  •      3. Draw a rectangle in the middle of the screen that is half the width and half the height of the canvas. Write it so that you can change the size of the canvas and the rectangle will stay in the center and maintain its size relationship to the canvas.

       
   
    


  •       4. Move a circle from the middle of the screen to the right side of the screen. 
    •       a. Add 3 more, 1 moving left, 1 moving up, 1 moving down.
    •       b. Add 4 more, each moving towards each of the 4 corners of the canvas.
    •       c. Make one of your circles move 10 times faster than the other circles.
    •       d. Challenge: Re-write 4b. so if I change the width of the canvas, the circles still go to the corners without having to change any other code.

function setup() {
 createCanvas(600, 600);
 circleX = width / 2;
 circleY = height / 2;
 circleFastX = width / 2;
 circleY = height / 2;
}

function draw() {
 background(220);
 circleX = circleX + speed;
 circleFastX = circleFastX + speed*10;

 //go back to middle
 if (circleX > width) {
   circleX = width / 2;
 }

 // Circle 1 - moves to the right
 fill(myBlue);
 ellipse(circleFastX, height / 2, 50, 50);

 // Circle 2 - moves to the left
 fill(myMint);
 ellipse(width - circleX, height / 2, 50, 50);

 // Circle 3 - moves up
 fill(myMint);
 ellipse(width / 2, height - circleX, 50, 50);

 // Circle 4 - moves down
 fill(myMint);
 ellipse(width / 2, circleX, 50, 50);

 // Four corners movement (relative to canvas size)
 fill(myPurple);
 ellipse(circleX, circleX, 50, 50); // Top-left
 ellipse(width - circleX, circleX, 50, 50); // Top-right
 ellipse(circleX, height - circleX, 50, 50); // Bottom-left
 ellipse(width - circleX, height - circleX, 50, 50); // Bottom-right
}




        5. Move a circle towards the mouse. Hint: Use mouseX + mouseY.


I had to understand the examples about ‘cos,sin’ in p5js page.
 

 
1. I used ‘translate’ to fix the center of rotation to (mouseX,mouseY)

2. Using cos(angle) and sin(angle), the x and y coordinates of the circle were set based on the current angle. By multiplying with the radius, the distance of the circle's rotation was established.

3.The angle is continuously changed, causing the x and y coordinates to vary, creating the effect of the circle rotating around the mouse cursor.



        6. Move your rectangle from Q3 towards the mouse. 




let myPinkple = "#9F2042";
let rectX = 400; //starting point
let rectY = 400; //starting point
let speed = 2; 

function setup() {
  createCanvas(800, 800);
}

function draw() { 
let gColor = random(200, 255);
    fill(0, gColor, 10);
    move();
    background(220); 









  // rectangle
  push();
  rectMode(CENTER);
  rect(rectX, rectY, 200, 200);
  pop();

  // line
  stroke(myPinkple);
  strokeWeight(5);

  // line moving with rect
  let lineX1 = rectX - 100;
  let lineY1 = rectY - 100;
  let lineX2 = rectX + 100;
  let lineY2 = rectY + 100;

  line(lineX1, lineY2, lineX2, lineY2);
  line(lineX1, lineY1, lineX1, lineY2);
  line(lineX2, lineY2, lineX2, lineY1);
  line(lineX1, lineY1, lineX2, lineY1);
}

// move
function move() {
  // follow the mouse! 
  if (mouseX > rectX) {          
    rectX += speed;
 }
else if (mouseX < rectX) {
    rectX -= speed;
  }

  if (mouseY > rectY) {
    rectY += speed;
 }
else if (mouseY < rectY) {
    rectY -= speed;
  }


}










  • Create an animated sketch!

    • As an exercise include all of the following.
      1. One element controlled by the mouse.
      2. One element that changes over time, independently of the mouse.
      3. One element that is different every time you run the sketch.
    • See if you can eliminate all (or as much as you can) hard-coded* numbers from the sketch. A hard coded number is something like fill(150). Better practice is to save 150 in a variable, for example myGreyColour, then use fill(myGreyColour)



I could not use circle in WEBGL mode. -> changed to sphere
I used bugs from example (https://p5js.org/tutorials/custom-geometry/)

-> First try..



let myBlue = "#0075F2"; // setting my color
let myPear = "#D1D646";
let myGreen = "#798071";
let bug;

function setup() {
  createCanvas(800, 800, WEBGL); 
  describe('Bugs randomly moving around');

  // bug
  bug = createBugGeometry(); // bug 3d
}

function draw() {
  background(220);

  // Sphere 
  push();
  fill(myPear);
  rotate(frameCount * 0.1);
  sphere(30);
  pop();

  orbitControl();
  rotateX(PI * -0.1);

  noStroke();
  lights();

 

 // Draw a bunch of bugs
  for (let i = 0; i < 20; i++) {
    push();
    // Move each bug to a random position and rotation using noise
    translate(
      map(
        noise(frameCount * 0.001, i, 0), // Map this value...
        0, 1, // ...from this range...
        -150, 150 // ...into this range
      ),
      0,
      map(
        noise(frameCount * 0.001, i, 100),  // Map this value...
        0, 1, // ...from this range...
        -200, 300 // ...into this range
      )
    );
    rotateY(noise(frameCount * 0.01, i, 200) * TWO_PI);
    scale(0.1);

    // Bug drawing
    bug();
    pop();
  }
}
// making bugs
function createBugGeometry() {
  return function() {
    // Head
    push();
    translate(-50, 0, 0);
    sphere(70);

    // Draw symmetrical parts of the head that come in pairs
    for (let side of [-1, 1]) {
      // Eye
      push();
      translate(-20, -60, side * 30);
      sphere(20);
      pop();

      // Antenna
      push();
      translate(0, -100, side * 30);
      rotateX(PI * -0.1 * side);
      cylinder(5, 100);
      pop();
    }
    pop();

    // Body
    push();
    translate(50, 0, 0);
    scale(1.5, 0.8, 1);
    sphere(100);
    pop();
  };
}



-> Second changing the bugs move toward the yellow snack ( mouse )





let myBlue = "#0075F2"; // setting my color
let myPear = "#D1D646";
let myGreen = "#798071";
let bug;
let circleX = 0; // for making snack to follow mouse
let circleY = 0;
let bugs = []; // Array to store bugs' positions

function setup() {
 createCanvas(800, 800, WEBGL);

 // Initialize bugs' positions
 for (let i = 0; i < 50; i++) {
   bugs.push({
     x: random(-300, 300),
     z: random(-300, 300)
   });
 }

 // Create bug geometry
 bug = createBugGeometry(); // bug 3d
}

function draw() {
 background(220);

 // Snack following mouse
 if (circleX < mouseX - width / 2) {
   circleX += 5; // follow right
 } else if (circleX > mouseX - width / 2) {
   circleX -= 5; // follow left
 }

 if (circleY < mouseY - height / 2) {
   circleY += 5; // follow down
 } else if (circleY > mouseY - height / 2) {
   circleY -= 5; // follow up
 }



 
// Draw snack
 push();
 fill(myPear);
 translate(circleX, circleY);
 sphere(30);
 pop();

 orbitControl();
 rotateX(PI * -0.2);

 noStroke();
 lights();

 // Draw bugs
 for (let i = 0; i < bugs.length; i++) {
   let bugX = bugs[i].x;
   let bugZ = bugs[i].z;

   // Move bug towards the snack
   if (bugX < circleX) {
     bugs[i].x += 0.5; // Move right
   } else if (bugX > circleX) {
     bugs[i].x -= 0.5; // Move left
   }

   if (bugZ < circleY) {
     bugs[i].z += 0.5; // Move down
   } else if (bugZ > circleY) {
     bugs[i].z -= 0.5; // Move up
   }

   push();
   translate(bugs[i].x, 0, bugs[i].z);
   rotateY(noise(frameCount * 0.01, i, 200) * TWO_PI);
   scale(0.1);
   bug();
   pop();
 }
}
// making bugs
function createBugGeometry() {
 return function() {
   // Head
   push();
   translate(-50, 0, 0);
   sphere(70);

   // Draw symmetrical parts of the head that come in pairs
   for (let side of [-1, 1]) {
     // Eye
     push();
     translate(-20, -60, side * 30);
     sphere(20);
     pop();

     // Antenna
     push();
     translate(0, -100, side * 30);
     rotateX(PI * -0.1 * side);
     cylinder(5, 100);
     pop();
   }
   pop();

   // Body
   push();
   translate(50, 0, 0);
   scale(1.5, 0.8, 1);
   sphere(100);
   pop();
 };
}

-> Third make bug’s location random every run, and change it’s color every second in random green.





let myBlue = "#0075F2"; // setting my color
let myPear = "#D1D646";
let myGreen = "#798071";
let bug;
let circleX = 0; // for making snack to follow mouse
let circleY = 0;
let bugs = []; // Array to store bugs' positions

function setup() {
  createCanvas(800, 800, WEBGL); 

  // Initialize bugs' positions
  for (let i = 0; i < 10; i++) {
    bugs.push({
      x: random(-400, 400),
      z: random(-400, 400)
    });
   // fill(random(255),20,20);
  }

  // Create bug geometry
  bug = createBugGeometry(); // bug 3d
}

function draw() {
  background(220);

  // Snack following mouse
  if (circleX < mouseX - width / 2) {
    circleX += 5; // follow right
  } else if (circleX > mouseX - width / 2) {
    circleX -= 5; // follow left
  }

  if (circleY < mouseY - height / 2) {
    circleY += 5; // follow down
  } else if (circleY > mouseY - height / 2) {
    circleY -= 5; // follow up
  }


 // Draw snack
 push();
 fill(myPear);
 translate(circleX, circleY);
 sphere(30);
 pop();

 orbitControl();
 rotateX(PI * -0.2);

 noStroke();
 lights();

 // Draw bugs
 for (let i = 0; i < bugs.length; i++) {
   let bugX = bugs[i].x;
   let bugZ = bugs[i].z;

   // Move bug towards the snack
   if (bugX < circleX) {
     bugs[i].x += 0.5; // Move right
   } else if (bugX > circleX) {
     bugs[i].x -= 0.5; // Move left
   }

   if (bugZ < circleY) {
     bugs[i].z += 0.5; // Move down
   } else if (bugZ > circleY) {
     bugs[i].z -= 0.5; // Move up
   }

   push();
   translate(bugs[i].x, 0, bugs[i].z);
   rotateY(noise(frameCount * 0.01, i, 200) * TWO_PI);
   scale(0.1);
   bug();
   pop();
 }
}
// making bugs
function createBugGeometry() {
 return function() {
    let gColor=random(100,255);
 print (gColor);
 fill(0,gColor,10);
   // Head
   push();
   translate(-50, 0, 0);
   sphere(70);

   // Draw symmetrical parts of the head that come in pairs
   for (let side of [-1, 1]) {
     // Eye
     push();
     translate(-20, -60, side * 30);
     sphere(20);
     pop();

     // Antenna
     push();
     translate(0, -100, side * 30);
     rotateX(PI * -0.1 * side);
     cylinder(5, 100);
     pop();
   }
   pop();

   // Body
   push();
   translate(50, 0, 0);
   scale(1.5, 0.8, 1);
   sphere(100);
   pop();
 };
}

– Week 4 –––––––––––––––––––––––––––––––––––––––––––


  • W4 assignment



Try1












Try 2








Try 3







– Week 6 –––––––––––––––––––––––––––––––––––––––––––


  • worksheet


  1. Create 10 columns that toggle on and off when you click on them. You click on the column and the column turns red and stays red. You click on the column again and it turns white and stays white. Challenge: Make this work for a grid of cells.







         2. Make 2 bouncing balls.





       3. Make 20 bouncing balls.





         4. Add a feature: Create a new ball when you click the canvas.


         5. Add a feature: Make the new balls move slowly towards the mouse.
         6. Add a feature: Make the new balls move slowly towards the mouse.
         7. Add a feature: Add the ability to zap (delete) a ball if you mouse over it.
    • Assignment













    – Finals  –––––––––––––––––––––––––––––––––––––––––––


    • Team Jenn Sky Plan


    • 1. Concept

    This experience invites participants to embark on a warm journey of gift-giving and connection. As snowflakes gently fall on a serene winter landscape, Santa Claus becomes their collaborative partner in spreading joy and light.

    The journey begins with a deeply personal moment: each participant chooses a single, meaningful word that represents the gift they most want to share with a loved one this Christmas. This word becomes more than just language—it transforms into a vessel of emotion, intention, and connection.

    Once the word is selected, Santa Claus steps in as a messenger, preparing a gift package that embodies that word. Each package is imbued with a distinctive color that resonates with the random palette of the chosen word.

    Participants then become essential helpers in Santa's mission, assisting in delivering these special packages to various homes. These are not ordinary houses, but dark, waiting spaces yearning for warmth and illumination. As each gift is received, something magical happens: the house begins to glow from within, filled with the vibrant color of the present's emotional spectrum.

    The process is a metaphorical journey of spreading light, love, and personal meaning—transforming dark, silent spaces into radiant sanctuaries of connection and hope, one carefully chosen word at a time.

    2. Coding Plan

    - There will be 3 layers, one is on the foreground with houses, but the houses will have transparent windows so that the layer with another image on the next layer can be seen through the window when interaction happens. Then background video will be placed on the third layer.
    Code type : Image, Video, Video on/off, Opacity.

    - If the box radius overlaps with the house radius - video on.
    There will be an input box on the bottom of the screen where users can type a word for ‘gift’. As input successfully returns a word, Santa sleigh will show up from the top left corner of the screen. As the Santa sleigh reaches to the middle of the screen, it will drop the word written in a gift box with different colors per each time.
    Code type : Input box, array.

    - If Santa sleigh’s position reaches to the middle of the screen, drop the gift box.
    The users can deliver the gift to any house they want to give to. A parachute will follow where the hands are, and when it overlaps with the gift box, they will stick together and the users can move the gift box from the moment.
    Code type : ML5 bodyPose.

    - If hand position overlaps with the box radius, stick together and update the position based on where the hand is.
    When the box overlaps with a house, it will make a sound effect and the image behind the house will be activated. And the lights in the window will turn on and the color of the lights will be different based on the color of gift box.
    Code type : image, sound.

    - If the box radius overlaps with a house, the house activates the image and the light turns on based on the color of the gift box.
    - One round ends.



    3. Interaction

    In this experience, participants embark on a journey of gift-giving by entering a word that encapsulates their heartfelt message.

    As the word is input, the scene transforms dramatically. High above in the wintry sky, Santa Claus and Rudolph's sleigh appear. The participant's chosen word materializes as a unique gift package within the sleigh, ready to be delivered.

    The gift box descends from the sky, suspended in mid-air and awaiting the participant's touch. There's a moment of interactive art as the participant must physically reach out and catch the falling package—a symbolic connection between digital intention and physical action.

    The final step requires the participant to select a specific chimney representing their chosen home. They must deliver the gift, guiding it perfectly into the chimney. Each chimney represents a potential destination, a home waiting to be touched by the warmth of the participant's carefully chosen word.


    This experience transforms gift-giving from a simple transaction into an immersive, almost ceremonial process. It's not merely about sending a present, but creating a moment of genuine connection where words become tangible gifts of love, hope, and meaning.



    • 4. Visual effect 

     The entire scene unfolds against a softly blurred background, reminiscent of a frosted winter landscape. Layered atop this dreamy backdrop are delicate line drawings that transform the visual experience. These precise, minimalist lines create a striking contrast—much like looking through a frost-covered window, offering a sense of both distance and intimate observation.

     Each participant's chosen word becomes more than just language; it transforms into a uniquely colored gift package. This personalized packaging is not merely decorative but deeply symbolic. When the gift arrives at its destination, something magical occurs: the receiving house is illuminated by a corresponding glow of the same color as the gift.

     This chromatic synchronization is profound in its simplicity. The matching color represents more than visual harmony—it symbolizes a successful emotional transmission. Each lit house signifies that the participant's carefully chosen word has not just been delivered, but has truly been received, bringing with it a sense of happiness, warmth, and connection.

    The line-drawn aesthetic and color-infused illumination create a visual metaphor for communication, suggesting that words—when shared with intention and love—can transform spaces and touch hearts, especially during the season of giving.