Happy new year| final project

A. Happy new year-Kelly Wu-Eric Parren
null


B.Conception and Design:

  As one of the traditional Chinese festivals, the Spring Festival has always been loved by a lot of Chinese people. And setting off fireworks is one of the customs. But as air pollution becomes more and more serious, many cities, including Shanghai, have banned fireworks. 2024 is just coming soon, and I want to make a project that can make everyone feel the traditional atmosphere of Chinese New Year again. That’s why I came up with the concept of Cyber Fireworks. Recalling my previous experience of setting off fireworks, I decided to simulate the process of ignition through a temperature sensor and finally the fireworks were presented on Processing. I received some advice during the user test period. First, people wanted me to increase the number of fireworks and sensors. Secondly, sound is also a must. Also, since it is difficult to control the distance between the sensors and the lighter to avoid the lighter burning the sensors, people want me to set a reasonable distance. Finally, some people also hope that I can increase the fun of ignition, such as using matches for ignition. After this session, I made a little adjustment. First, I increased the number of ” installations ” from one to two. Secondly, I added the sound when it is ignited. Third, I added matches. I was going to set up a device to hold the ignition position in order to control a reasonable distance, but finally it was not put into practice due to lack of time.

C. Fabrication and Production

  For the sensor selection, I chose a temperature sensor. The first thing to admit is that it is really conducive to interaction and because it is sensitive, I had a great success rate in my project. But at the same time, it has several unavoidable drawbacks. First, the temperature is not quite the same in different environments, so it’s hard to determine the value, and you need to keep adjusting it. Second, because the temperature sensor reads the temperature of the air around it, so when you heat it up with a lighter, that portion of the air will hold that temperature for a long time, leading to the possibility that you don’t have an ignition but the program is still running. At first I was thinking of using a match for ignition, but realized that the temperature sensor had a slight delay that would cause the match to burn too fast or even burn my hand. Therefore, I switched to using a lighter instead.

D. Conclusions:

  From the audience’s reaction, the project achieved what I expected. In particular, people said they were pleasantly surprised by the way I chose to use flames for the interaction. I gained a lot during the process of making this project. Fisrt, I knew how to use laser cutter correctly. Second, I improved my coding skills in the period of making the firework. What is more, I think the highlight of my project is using the neopixels to simulate the ignition. To be honest, I think the way that I think is more important than the project that I made. Because this project is not difficult in designing the circuit. However, the coding part and concept is very creative.

 

E. Appendix:

processing

import processing.serial.*;
import ddf.minim.*;

//Serial arduino;
Serial serialPort;
int NUM_OF_VALUES_FROM_ARDUINO = 4;
int arduino_values[] = new int[NUM_OF_VALUES_FROM_ARDUINO];
Firework firework1;
Firework firework2;

Minim minim;
AudioPlayer explosionSound;

void setup() {
// size(480,480);
fullScreen();
printArray(Serial.list());
minim = new Minim(this);
explosionSound = minim.loadFile(“firework.mp3”);

firework1 = new Firework(width / 2, height / 1.5);
firework2 = new Firework(width / 2.75, height / 1.5);

// String[] portList = Serial.list();
//if (portList.length > 0) {
// arduino = new Serial(this, “COM8”, 9600);
//} else {
// println(“No serial ports found!”);
//}

serialPort = new Serial(this, “COM8”, 9600);
}

void draw() {
background(0);
getSerialData();

firework1.update();
firework1.show();
firework2.update();
firework2.show();

if(arduino_values[2] == 1){
firework1 = new Firework(width / 2, height / 2.5);
explosionSound.rewind();
explosionSound.play();
}

if(arduino_values[3] == 1){
firework2 = new Firework(width / 4, height / 2);
explosionSound.rewind();
explosionSound.play();
}

//while (arduino != null && arduino.available() > 0) {
// char inChar = (char) arduino.read();

// if (inChar == ‘1’) {
// firework1 = new Firework(width / 2.5, height / 2.5);
// explosionSound.rewind();
// explosionSound.play();
// }
// if (inChar == ‘2’) {
// firework2 = new Firework(width / 2.75, height / 1.5);
// explosionSound.rewind();
// explosionSound.play();
// }
//}
}

class Firework {
PVector position;
PVector velocity;
PVector gravity;
boolean exploded;
ArrayList<Particle> particles;

Firework(float x, float y) {
position = new PVector(x, y);
velocity = new PVector(0, random(-12, -8));
gravity = new PVector(0, 0.2);
exploded = false;
particles = new ArrayList<Particle>();
}

void update() {
if (!exploded) {
position.add(velocity);
velocity.add(gravity);

if (velocity.y >= 0) {
exploded = true;
explode();
}
}

for (int i = particles.size() – 1; i >= 0; i–) {
Particle p = particles.get(i);
p.update();
if (p.isOffScreen()) {
particles.remove(i);
}
}
}

void show() {
if (!exploded) {
stroke(255);
strokeWeight(4);
point(position.x, position.y);
}

for (Particle p : particles) {
p.show();
}
}

void explode() {
for (int i = 0; i < 100; i++) {
Particle p = new Particle(position.x, position.y);
particles.add(p);
}
}
}

class Particle {
PVector position;
PVector velocity;
PVector gravity;
int col;
float lifespan;

Particle(float x, float y) {
position = new PVector(x, y);
velocity = PVector.random2D().mult(random(2, 10));
gravity = new PVector(0, 0.2);
col = color(random(255), random(255), random(255));
lifespan = 255;
}

void update() {
velocity.add(gravity);
position.add(velocity);
lifespan -= 2;
}

void show() {
noStroke();
fill(col, lifespan);
ellipse(position.x, position.y, 16, 16);
}

boolean isOffScreen() {
return position.y > height || position.x < 0 || position.x > width;
}
}

void getSerialData() {
while (serialPort.available() > 0) {
String in = serialPort.readStringUntil( 10 ); // 10 = ‘\n’ Linefeed in ASCII
if (in != null) {
print(“From Arduino: ” + in);
String[] serialInArray = split(trim(in), “,”);
if (serialInArray.length == NUM_OF_VALUES_FROM_ARDUINO) {
for (int i=0; i<serialInArray.length; i++) {
arduino_values[i] = int(serialInArray[i]);
}
}
}
}
}

arduino

#include <Adafruit_NeoPixel.h>
#define PIN_NEOPIXEL_1 3
#define PIN_NEOPIXEL_2 8
#define PIN_TEMPERATURE_1 A0
#define PIN_TEMPERATURE_2 A3
#define NUMPIXELS 60  // Number of pixels in each Neopixel strip
#define TEMPERATURE_THRESHOLD 27.0
Adafruit_NeoPixel strip1 = Adafruit_NeoPixel(NUMPIXELS, PIN_NEOPIXEL_1, NEO_GRB + NEO_KHZ800);
Adafruit_NeoPixel strip2 = Adafruit_NeoPixel(NUMPIXELS, PIN_NEOPIXEL_2, NEO_GRB + NEO_KHZ800);
bool sequenceTriggered1 = false;
bool sequenceTriggered2 = false;
void setup() {
  Serial.begin(9600);
  strip1.begin();
  strip1.show();  // Initialize all pixels to ‘off’
  strip2.begin();
  strip2.show();  // Initialize all pixels to ‘off’
}
void loop() {
  // Read temperature value from the first sensor
  int temperatureValue1 = analogRead(PIN_TEMPERATURE_1);
  float temperatureCelsius1 = (temperatureValue1 / 1023.0) * 5.0 * 100.0;
  // Read temperature value from the second sensor
  int temperatureValue2 = analogRead(PIN_TEMPERATURE_2);
  float temperatureCelsius2 = (temperatureValue2 / 1023.0) * 5.0 * 100.0;
 
  int val3 = 0;
  int val4 = 0;
  // Check if temperature from the first sensor is higher than the threshold and sequence has not been triggered
  if (temperatureCelsius1 > TEMPERATURE_THRESHOLD && !sequenceTriggered1) {
    fireNeopixelSequence(strip1);
    sequenceTriggered1 = true;
    val3 = 1;
   
  } else if (temperatureCelsius1 <= TEMPERATURE_THRESHOLD) {
    sequenceTriggered1 = false;  // Reset the flag if temperature drops below the threshold
  }
  // Check if temperature from the second sensor is higher than the threshold and sequence has not been triggered
  if (temperatureCelsius2 > TEMPERATURE_THRESHOLD && !sequenceTriggered2) {
    fireNeopixelSequence(strip2);
    sequenceTriggered2 = true;
    val4 = 1;
   
  } else if (temperatureCelsius2 <= TEMPERATURE_THRESHOLD) {
    sequenceTriggered2 = false;  // Reset the flag if temperature drops below the threshold
  }
  Serial.print(temperatureCelsius1);
  Serial.print(“,”);
  Serial.print(temperatureCelsius2);
  Serial.print(“,”);
  Serial.print(val3);  // Send a signal to Processing for the first set oNeopixels
  Serial.print(“,”);
  Serial.print(val4);  // Send a signal to Processing for the second set of Neopixels
  Serial.println();
  delay(100);  // Delay between temperature readings (adjust as needed)
}
void fireNeopixelSequence(Adafruit_NeoPixel &strip) {
  for (int i = 0; i < NUMPIXELS; i++) {
    strip.setPixelColor(i, strip.Color(255, 0, 0));  // Red color, you can change the color as per your preference
    strip.show();
    delay(70);                                     // Adjust the delay between pixels as needed
    strip.setPixelColor(i, strip.Color(0, 0, 0));  // Turn off the current pixel
  }
  strip.show();
}

Leave a Reply

Your email address will not be published. Required fields are marked *