Hi there,
I am very new to arduino coding and have been working on a code that displays a sound graph that reads the input from a microphone while 2 servos move according to my input. I have managed to get a bit map to display, some text and then the servos move but for some reason the graph stays frozen. If I remove the servos from loop the graph gets displayed perfectly.
any advice on how to get the graph to function properly while the servos move.
here is my code
#include <U8glib.h>
#include <Wire.h>
#include <Adafruit_GFX.h>
#include <Adafruit_SH110X.h>
#include <Servo.h>
// Set up the OLED display
#define OLED_MOSI 10
#define OLED_CLK 8
#define OLED_DC 7
#define OLED_CS 5
#define OLED_RST 9
Adafruit_SH1106G display = Adafruit_SH1106G(128, 64, OLED_MOSI, OLED_CLK, OLED_DC, OLED_RST, OLED_CS);
Servo servo1;
Servo servo2;
// Set up the sound sensor
const int sampleWindow = 50; // Sample window width in mS (50 mS = 20Hz)
unsigned int sample;
// Graph variables
// Graph variables
const int graphWidth = 128; // Width of the graph area
const int graphHeight = 60; // Height of the graph area
const int graphX = 0; // X-coordinate of the top-left corner of the graph area
const int graphY = 60; // Y-coordinate of the bottom-left corner of the graph area
const int graphResolution = 2; // Resolution of the graph (increase for a smoother line)
int graphData[graphWidth / graphResolution]; // Array to store graph data
int graphIndex = 0; // Index of the current graph data point
int openAngle1 = 60; // Open position angle for servo1 (0 degrees)
int closeAngle1 = 150; // Close position angle for servo1 (90 degrees)
int openAngle2 = 110; // Open position angle for servo2 (30 degrees)
int closeAngle2 = 30; // Close position angle for servo2 (100 degrees)
int stepDelay1 = 40; // Delay between steps for the first set of movements (milliseconds)
int stepDelay2 = 5; // Delay between steps for the second set of movements (milliseconds)
int stepDelay3 = 5; // Delay between steps for the third set of movements (milliseconds)
int holdDuration1 = 10000; // Hold duration after stepdelay 1 close movement (milliseconds)
int holdDuration2 = 2000; // Hold duration after stepdelay 3 close movement (milliseconds)
int numMovements1 = 1; // Number of movements for the first set of movements
int numMovements2 = 3; // Number of movements for the second set of movements
int numMovements3 = 4; // Number of movements for the third set of movements
int totalMovements = numMovements1 + numMovements2 + numMovements3; // Total number of movements to perform
// Set up the bitmap image
const unsigned char PROGMEM bitmap[] = {
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xbf, 0x0f, 0x80, 0x1c, 0x70, 0x3f, 0xdf, 0xc0, 0x3b, 0xfe, 0xe0, 0x70, 0xfa, 0x01, 0xff,
0xff, 0x3f, 0x0f, 0x00, 0x0c, 0x60, 0x1f, 0xcf, 0xc0, 0x19, 0xfe, 0xc0, 0x30, 0xf2, 0x00, 0xff,
0xff, 0x1f, 0x0f, 0x00, 0x0c, 0x60, 0x0f, 0x8f, 0xc0, 0x19, 0xfc, 0xc0, 0x10, 0xf2, 0x00, 0x7f,
0xfe, 0x1f, 0x0f, 0x03, 0x8c, 0x47, 0x0f, 0x87, 0xc7, 0x18, 0xfc, 0x87, 0x10, 0xf2, 0x38, 0x7f,
0xfe, 0x0f, 0x0f, 0x03, 0x84, 0x47, 0x8f, 0x07, 0xc7, 0x18, 0xf8, 0x87, 0x10, 0xf2, 0x38, 0x7f,
0xfc, 0x0f, 0x0f, 0x03, 0x84, 0x47, 0x8f, 0x03, 0xc4, 0x18, 0x70, 0x87, 0x10, 0xf2, 0x00, 0xff,
0xfd, 0x07, 0x0f, 0x03, 0x84, 0x47, 0x8e, 0x43, 0xc4, 0x18, 0x70, 0x87, 0x10, 0xf2, 0x00, 0xff,
0xf9, 0x87, 0x0f, 0x03, 0x84, 0x47, 0x8e, 0xc1, 0xc4, 0x38, 0x20, 0x87, 0x10, 0xf2, 0x21, 0xff,
0xfb, 0x83, 0x0f, 0x03, 0x84, 0x47, 0x8e, 0xe1, 0xc6, 0x38, 0x00, 0x87, 0x10, 0xf2, 0x31, 0xff,
0xfb, 0xc3, 0x0f, 0x03, 0x84, 0x47, 0x0d, 0xe0, 0xc6, 0x1a, 0x08, 0x87, 0x10, 0xf2, 0x30, 0xff,
0xf7, 0xc1, 0x0f, 0x03, 0x0c, 0x43, 0x0d, 0xf0, 0xc7, 0x1b, 0x08, 0xc7, 0x10, 0x72, 0x38, 0xff,
0xf0, 0x41, 0x80, 0x40, 0x0c, 0x60, 0x18, 0x10, 0x47, 0x0b, 0x18, 0xc0, 0x18, 0x06, 0x38, 0x7f,
0xe0, 0x61, 0x80, 0xc0, 0x1c, 0x70, 0x18, 0x18, 0x47, 0x03, 0x98, 0xe0, 0x38, 0x0e, 0x3c, 0x7f,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf0, 0x1f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x00, 0x01, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfc, 0x00, 0x00, 0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf8, 0x00, 0x00, 0x1f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xe0, 0x00, 0x00, 0x0f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xc0, 0x00, 0x00, 0x07, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xc0, 0x00, 0x00, 0x07, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xc0, 0x01, 0x00, 0x03, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x80, 0x06, 0x40, 0x03, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x84, 0x00, 0x00, 0x63, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xc7, 0xe0, 0x07, 0xc3, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xc0, 0xf8, 0x3f, 0x03, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xe0, 0x5c, 0x34, 0x0f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xe0, 0xdc, 0x32, 0x0f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xe0, 0x9c, 0x72, 0x0f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xe0, 0x8e, 0xf2, 0x0f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xe0, 0x0f, 0xf0, 0x0f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xe0, 0x1f, 0xf0, 0x0f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xe0, 0x1f, 0xf0, 0x0f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xe0, 0x1f, 0xf0, 0x0f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf8, 0x1f, 0xf0, 0x1f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfc, 0x1f, 0xf0, 0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfe, 0x1f, 0xf0, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x9f, 0xfb, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
};
void setup() {
servo1.attach(3); // Attach servo to pin 3
servo2.attach(6); // Attach servo to pin 6
servo1.write(openAngle1); // Set initial position of servo1
servo2.write(openAngle2); // Set initial position of servo2
Serial.begin(9600);
display.begin(0, true); // start OLED display
display.clearDisplay();
display.drawBitmap(0, 0, bitmap, 128, 64, 1);
display.display(); // show bitmap for 10 seconds
delay(5000); // delay for 10 seconds
display.clearDisplay(); // clear the display
display.setTextSize(2);
display.setTextColor(SH110X_WHITE);
display.setCursor(0,0);
display.println("TEST: 01");
display.display();
delay(5000);
display.setTextSize(1);
display.setTextColor(SH110X_WHITE);
// Initialize the sound sensor
pinMode(A0, INPUT);
sample = 0;
}
void loop() {
unsigned long startMillis = millis(); // Start of sample window
unsigned int peakToPeak = 0; // Peak-to-peak level
unsigned int signalMax = 0;
unsigned int signalMin = 1024;
// Collect data for the sample window
while (millis() - startMillis < sampleWindow) {
sample = analogRead(A0);
if (sample < 1024) { // Remove DC offset
if (sample > signalMax) {
signalMax = sample; // Find maximum value
} else if (sample < signalMin) {
signalMin = sample; // Find minimum value
}
}
}
peakToPeak = signalMax - signalMin; // Peak-to-peak level
// Update the graph data
graphData[graphIndex] = map(peakToPeak, 0, 1023, graphY, graphY - graphHeight);
// Display the sound level and graph on the OLED screen
display.clearDisplay();
display.setCursor(0, 0);
display.print("Sound Level: ");
display.print(peakToPeak);
// Draw the graph
for (int i = 0; i < graphWidth / graphResolution - 1; i++) {
display.drawLine(graphX + i * graphResolution, graphData[(graphIndex + i + 1) % (graphWidth / graphResolution)],
graphX + (i + 1) * graphResolution, graphData[(graphIndex + i + 2) % (graphWidth / graphResolution)], SH110X_WHITE);
}
display.display();
// Update the graph index
graphIndex = (graphIndex + 1) % (graphWidth / graphResolution);
// Delay for stability
delay(20);
for (int i = 0; i < totalMovements; i++) {
// Move servos from open to close position
for (int angle = openAngle1; angle <= closeAngle1; angle++) {
servo1.write(angle);
servo2.write(map(angle, openAngle1, closeAngle1, openAngle2, closeAngle2));
if (i < numMovements1) {
delay(stepDelay1);
} else if (i < (numMovements1 + numMovements2)) {
delay(stepDelay2);
} else if (i < totalMovements) {
delay(stepDelay3);
}
}
// Hold position after stepdelay 1 close movement
if (i == (numMovements1 - 1)) {
delay(holdDuration1);
}
// Move servos from close to open position
for (int angle = closeAngle1; angle >= openAngle1; angle--) {
servo1.write(angle);
servo2.write(map(angle, openAngle1, closeAngle1, openAngle2, closeAngle2));
if (i < numMovements1) {
delay(stepDelay1);
} else if (i < (numMovements1 + numMovements2)) {
delay(stepDelay2);
} else if (i < totalMovements) {
delay(stepDelay3);
}
}
// Hold position after stepdelay 3 close movement
if (i == (numMovements1 + numMovements2 - 1)) {
delay(holdDuration2);
}
}
// Stop the servos
servo1.detach();
servo2.detach();
// Stop the loop
while (true) {
// Do nothing
}
}```