I am working on a Robot Arm controlled by hand gestures. I am facing problem with the hand gestures part

I am working on a project since some time. The project is a Robot Arm controlled by hand gestures. I am trying to control it using a glove which will use 3 flex sensors and 2 MPU6050. I am using Bluetooth to transmit the information. The robot arm is controlled by six servos. I am also using a Servo driver to control the servos. The problem I m facing is about my code. I took some inspiration from this link here: Robot Arm + Glove Code. The codes are given below:
Robot Glove:

#include <Wire.h>
#include <Adafruit_MPU6050.h>
#include <Adafruit_Sensor.h>
#include <PCA9685.h>
#include <Servo.h>

Adafruit_MPU6050 mpu1;  // MPU6050 for base and wrist
Adafruit_MPU6050 mpu2;  // Second MPU6050 for wrist rotation and movement
PCA9685 pwm = PCA9685();

Servo servo1;  // Gripper Joint
Servo servo2;  // Wrist Joint Up/Down
Servo servo3;  // Wrist Rotation
Servo servo4;  // Elbow Joint
Servo servo5;  // Shoulder Joint
Servo servo6;  // Base Joint

// Flex sensor values (hypothetical pin numbers for flex sensors)
int flexThumb = A0;
int flexIndex = A1;
int flexPinky = A2;

// Variables to hold the readings
float accelX1, accelY1, accelZ1;
float accelX2, accelY2, accelZ2;

void setup() {
  Serial.begin(115200);
  
  // Initialize the PCA9685 for servo control
  pwm.begin();
  pwm.setPWMFreq(50);  // Set the PWM frequency to 50Hz for servos
  
  // Initialize the servos
  servo1.attach(0);
  servo2.attach(1);
  servo3.attach(2);
  servo4.attach(3);
  servo5.attach(4);
  servo6.attach(5);
  
  // Initialize the MPU6050 sensors
  if (!mpu1.begin()) {
    Serial.println("Failed to find MPU6050 #1");
    while (1);
  }
  if (!mpu2.begin()) {
    Serial.println("Failed to find MPU6050 #2");
    while (1);
  }
  
  // Initialize the flex sensors
  pinMode(flexThumb, INPUT);
  pinMode(flexIndex, INPUT);
  pinMode(flexPinky, INPUT);
}

void loop() {
  // MPU 1 Data (for base and wrist)
  sensors_event_t a1, g1, temp1;
  mpu1.getEvent(&a1, &g1, &temp1);
  accelX1 = a1.acceleration.x;
  accelY1 = a1.acceleration.y;
  accelZ1 = a1.acceleration.z;

  // MPU 2 Data (for wrist rotation and movement)
  sensors_event_t a2, g2, temp2;
  mpu2.getEvent(&a2, &g2, &temp2);
  accelX2 = a2.acceleration.x;
  accelY2 = a2.acceleration.y;
  accelZ2 = a2.acceleration.z;
  
  // Flex sensor readings
  int thumbFlexValue = analogRead(flexThumb);
  int indexFlexValue = analogRead(flexIndex);
  int pinkyFlexValue = analogRead(flexPinky);

  // Control Gripper Joint (Servo 1) - Index Finger Flex Sensor
  if (indexFlexValue > 500) {  // Adjust the threshold value as necessary
    servo1.write(180);  // Close gripper
  } else {
    servo1.write(0);    // Open gripper
  }

  // Control Wrist Joint Up/Down (Servo 2) - MPU2 X/Y-Axis
  if (accelY2 > 1) {
    servo2.write(180);  // Wrist Up
  } else if (accelY2 < -1) {
    servo2.write(0);    // Wrist Down
  }

  // Control Wrist Rotation (Servo 3) - MPU2 Z-Axis
  if (accelZ2 > 1) {
    servo3.write(180);  // Rotate Clockwise
  } else if (accelZ2 < -1) {
    servo3.write(0);    // Rotate Counterclockwise
  }

  // Control Elbow Joint (Servo 4) - Thumb Finger Flex Sensor
  if (thumbFlexValue > 500) {
    servo4.write(180);  // Bend elbow
  } else {
    servo4.write(0);    // Extend elbow
  }

  // Control Shoulder Joint (Servo 5) - Pinkie Finger Flex Sensor
  if (pinkyFlexValue > 500) {
    servo5.write(180);  // Move shoulder closer
  } else {
    servo5.write(0);    // Move shoulder further
  }

  // Control Base Joint (Servo 6) - MPU1 X-Axis
  if (accelX1 > 1) {
    servo6.write(180);  // Rotate base right
  } else if (accelX1 < -1) {
    servo6.write(0);    // Rotate base left
  }

  delay(50);  // Add a short delay to prevent too frequent updates
}

Robot Arm:

#include <Wire.h>
#include <Adafruit_PWMServoDriver.h>
#include <SoftwareSerial.h> // Include SoftwareSerial library

// Define Bluetooth TX and RX pins
SoftwareSerial bluetooth(3, 4); // RX | TX

// Create an instance of the Adafruit PWM Servo Driver
Adafruit_PWMServoDriver pwm = Adafruit_PWMServoDriver();

const int servo_min = 150; // Minimum pulse length count (for 0 degrees)
const int servo_max = 600; // Maximum pulse length count (for 180 degrees)

// Initial parking positions of the servos
const int servo_joint_L_parking_pos = 60;
const int servo_joint_R_parking_pos = 60;
const int servo_joint_1_parking_pos = 70;
const int servo_joint_2_parking_pos = 47;
const int servo_joint_3_parking_pos = 63;
const int servo_joint_4_parking_pos = 63;

// Degree of robot servo sensitivity - Intervals
int servo_joint_L_pos_increment = 20;
int servo_joint_R_pos_increment = 20;
int servo_joint_1_pos_increment = 20;
int servo_joint_2_pos_increment = 50;
int servo_joint_3_pos_increment = 60;
int servo_joint_4_pos_increment = 40;

// Current value of the motor positions
int servo_joint_L_parking_pos_i = servo_joint_L_parking_pos;
int servo_joint_R_parking_pos_i = servo_joint_R_parking_pos;
int servo_joint_1_parking_pos_i = servo_joint_1_parking_pos;
int servo_joint_2_parking_pos_i = servo_joint_2_parking_pos;
int servo_joint_3_parking_pos_i = servo_joint_3_parking_pos;
int servo_joint_4_parking_pos_i = servo_joint_4_parking_pos;

// Minimum and maximum angle of servo motor
int servo_joint_L_min_pos = 10;
int servo_joint_L_max_pos = 180;
int servo_joint_R_min_pos = 10;
int servo_joint_R_max_pos = 180;
int servo_joint_1_min_pos = 10;
int servo_joint_1_max_pos = 400;
int servo_joint_2_min_pos = 10;
int servo_joint_2_max_pos = 380;
int servo_joint_3_min_pos = 10;
int servo_joint_3_max_pos = 380;
int servo_joint_4_min_pos = 10;
int servo_joint_4_max_pos = 120;

char state = 0; // Changes value from ASCII to char
int response_time = 5;

void setup() {
  // Initialize Bluetooth communication
  bluetooth.begin(9600);  // Baud rate for Bluetooth module
  Serial.begin(9600); // For debugging

  // Initialize the PWM driver
  pwm.begin();
  pwm.setPWMFreq(60); // Analog servos run at ~60 Hz

  delay(3000);
}

void loop() {
  if (bluetooth.available() > 0) { // Check if data is coming from Bluetooth
    state = bluetooth.read();  // Read the data from Bluetooth
    Serial.print(state);  // Print to Serial Monitor for debugging

    // Move the servos based on received commands
    if (state == 'S') {
      baseRotateLeft();
      delay(response_time);
    }
    if (state == 'O') {
      baseRotateRight();
      delay(response_time);
    }
    if (state == 'c') {
      shoulderServoForward();
      delay(response_time);
    }
    if (state == 'C') {
      shoulderServoBackward();
      delay(response_time);
    }
    if (state == 'p') {
      elbowServoForward();
      delay(response_time);
    }
    if (state == 'P') {
      elbowServoBackward();
      delay(response_time);
    }
    if (state == 'U') {
      wristServo1Backward();
      delay(response_time);
    }
    if (state == 'G') {
      wristServo1Forward();
      delay(response_time);
    }
    if (state == 'R') {
      wristServoCW();
      delay(response_time);
    }
    if (state == 'L') {
      wristServoCCW();
      delay(response_time);
    }
    if (state == 'F') {
      gripperServoBackward();
      delay(response_time);
    }
    if (state == 'f') {
      gripperServoForward();
      delay(response_time);
    }
  }
}

// Boilerplate function to move the servo motors
void gripperServoForward() {
  if (servo_joint_4_parking_pos_i > servo_joint_4_min_pos) {
    pwm.setPWM(5, 0, map(servo_joint_4_parking_pos_i, 0, 180, servo_min, servo_max));
    delay(response_time);
    Serial.println(servo_joint_4_parking_pos_i);
    servo_joint_4_parking_pos_i = servo_joint_4_parking_pos_i - servo_joint_4_pos_increment;
  }
}

void gripperServoBackward() {
  if (servo_joint_4_parking_pos_i < servo_joint_4_max_pos) {
    pwm.setPWM(5, 0, map(servo_joint_4_parking_pos_i, 0, 180, servo_min, servo_max));
    delay(response_time);
    Serial.println(servo_joint_4_parking_pos_i);
    servo_joint_4_parking_pos_i = servo_joint_4_parking_pos_i + servo_joint_4_pos_increment;
  }
}

void wristServoCW() {
  if (servo_joint_3_parking_pos_i > servo_joint_3_min_pos) {
    pwm.setPWM(4, 0, map(servo_joint_3_parking_pos_i, 0, 180, servo_min, servo_max));
    delay(response_time);
    Serial.println(servo_joint_3_parking_pos_i);
    servo_joint_3_parking_pos_i = servo_joint_3_parking_pos_i - servo_joint_3_pos_increment;
  }
}

void wristServoCCW() {
  if (servo_joint_3_parking_pos_i < servo_joint_3_max_pos) {
    pwm.setPWM(4, 0, map(servo_joint_3_parking_pos_i, 0, 180, servo_min, servo_max));
    delay(response_time);
    Serial.println(servo_joint_3_parking_pos_i);
    servo_joint_3_parking_pos_i = servo_joint_3_parking_pos_i + servo_joint_3_pos_increment;
  }
}

void wristServo1Forward() {
  if (servo_joint_2_parking_pos_i < servo_joint_2_max_pos) {
    pwm.setPWM(3, 0, map(servo_joint_2_parking_pos_i, 0, 180, servo_min, servo_max));
    delay(response_time);
    Serial.println(servo_joint_2_parking_pos_i);
    servo_joint_2_parking_pos_i = servo_joint_2_parking_pos_i + servo_joint_2_pos_increment;
  }
}

void wristServo1Backward() {
  if (servo_joint_2_parking_pos_i > servo_joint_2_min_pos) {
    pwm.setPWM(3, 0, map(servo_joint_2_parking_pos_i, 0, 180, servo_min, servo_max));
    delay(response_time);
    Serial.println(servo_joint_2_parking_pos_i);
    servo_joint_2_parking_pos_i = servo_joint_2_parking_pos_i - servo_joint_2_pos_increment;
  }
}

void elbowServoForward() {
  if (servo_joint_L_parking_pos_i < servo_joint_L_max_pos) {
    pwm.setPWM(0, 0, map(servo_joint_L_parking_pos_i, 0, 180, servo_min, servo_max));
    pwm.setPWM(1, 0, map(servo_joint_L_max_pos - servo_joint_L_parking_pos_i, 0, 180, servo_min, servo_max));
    delay(response_time);
    Serial.println(servo_joint_L_parking_pos_i);
    servo_joint_L_parking_pos_i = servo_joint_L_parking_pos_i + servo_joint_L_pos_increment;
  }
}

void elbowServoBackward() {
  if (servo_joint_L_parking_pos_i > servo_joint_L_min_pos) {
    pwm.setPWM(0, 0, map(servo_joint_L_parking_pos_i, 0, 180, servo_min, servo_max));
    pwm.setPWM(1, 0, map(servo_joint_L_max_pos - servo_joint_L_parking_pos_i, 0, 180, servo_min, servo_max));
    delay(response_time);
    Serial.println(servo_joint_L_parking_pos_i);
    servo_joint_L_parking_pos_i = servo_joint_L_parking_pos_i - servo_joint_L_pos_increment;
  }
}

void shoulderServoForward() {
  if (servo_joint_1_parking_pos_i < servo_joint_1_max_pos) {
    pwm.setPWM(2, 0, map(servo_joint_1_parking_pos_i, 0, 180, servo_min, servo_max));
    delay(response_time);
    Serial.println(servo_joint_1_parking_pos_i);
    servo_joint_1_parking_pos_i = servo_joint_1_parking_pos_i + servo_joint_1_pos_increment;
  }
}

void shoulderServoBackward() {
  if (servo_joint_1_parking_pos_i > servo_joint_1_min_pos) {
    pwm.setPWM(2, 0, map(servo_joint_1_parking_pos_i, 0, 180, servo_min, servo_max));
    delay(response_time);
    Serial.println(servo_joint_1_parking_pos_i);
    servo_joint_1_parking_pos_i = servo_joint_1_parking_pos_i - servo_joint_1_pos_increment;
  }
}

void baseRotateLeft() {
  if (servo_joint_R_parking_pos_i > servo_joint_R_min_pos) {
    pwm.setPWM(1, 0, map(servo_joint_R_parking_pos_i, 0, 180, servo_min, servo_max));
    delay(response_time);
    Serial.println(servo_joint_R_parking_pos_i);
    servo_joint_R_parking_pos_i = servo_joint_R_parking_pos_i - servo_joint_R_pos_increment;
  }
}

void baseRotateRight() {
  if (servo_joint_R_parking_pos_i < servo_joint_R_max_pos) {
    pwm.setPWM(1, 0, map(servo_joint_R_parking_pos_i, 0, 180, servo_min, servo_max));
    delay(response_time);
    Serial.println(servo_joint_R_parking_pos_i);
    servo_joint_R_parking_pos_i = servo_joint_R_parking_pos_i + servo_joint_R_pos_increment;
  }
}

Please help if you can.

What is the issue? Describe what happens and how that compares with what you want. All I can say now is that the code does exactly what is written.

From the looks of the arbitrary if conditions in this code, you may need to spend more time studying the details of how the sensors report your movements, and revise the conditions for specific gesture recognition.

  // Control Shoulder Joint (Servo 5) - Pinkie Finger Flex Sensor
  if (pinkyFlexValue > 500) {
    servo5.write(180);  // Move shoulder closer
  } else {
    servo5.write(0);    // Move shoulder further
  }

How you can Get the Right Help Faster:

You can spend weeks spinning your wheels, or you might get lucky and solve your problem quickly. To avoid unnecessary delays, it’s crucial to provide an annotated schematic of your circuit as you have it wired, showing all connections, including power, ground, and supplies.

Why Detailed Information Matters:

  • Annotated Schematics: These are essential because they show exactly how your circuit is set up. Without them, it's difficult for anyone to understand what you’ve done, which makes troubleshooting nearly impossible. Fritzing diagrams or unclear pictures are not enough.

Did you even check if these files you downloaded compile? Why are you using different servo libraries in each sketch? ChatGPT.

@xfpd I got the code online, but I am having trouble adjusting it to my requirements. I didn't know where to start, as it is my first time dealing with sensors, so I just put it in GPT and it gave me this (only for the Robot Glove). I had trouble understanding it so I put it here, and yes the code for the Robot arm compiles, but I didn't check for the glove because it looked sketchy. I am using a servo driver as well, PCA9685 to be exact. The problem I have is that the code for the glove is used to control a 7-axis robot arm, but I want to modify it to control a 6-axis robot arm. This is the first time I have been dealing with sensors and hence don't know where to start. If you know anything or see anything unusual about my code please share it and tell me how to fix it or where to start.

@jremington Thank you for this example. I will try it out and see how it goes. If you see anything unusual please notify me. Thank you for your time and effort.

@Delta_G I have this code ready. I just need someone to verify this and tell me if I am missing out on something

Verify what? Load it to your board and see what happens.

The purpose of this forum is to help you fix code that you've written. So, our recommendation and general practice for GPT-written code is that you go back to GPT for an explanation of its code and request to fix it.

Both sketches must work. Why would you not test both? The "glove" does not compile, part of the reason is chatGPT's guess at creating an instance. i stopped there.

Do you have the hardware to build this, including skeleton? Have you tested all the hardware individually? Have you tested the SoftwareSerial communication between the two boards/sketches?

You should be the active player in building this, with a few questions along the way, not bringing a bucket of parts and random code for someone else to fix. You can not start with this project. You must learn to program, then learn to program the Arduino, then try this.

@xfpd I know how to program the Arduino, and I certainly have everything including the skeleton and arm all assembled and have also tested each and every one of my hardware. I have also tested the SoftwareSerial communication between the two boards. I am not asking someone to fix this, I am asking someone to tell me whether I am doing it right or wrong. Like I said before, it's my first time dealing with sensors and this entire experience has been a huge learning curve for me. I don't want someone to come and fix this for me, I want someone to tell me where I am wrong. I know that what code I came here with isn't correct, it's a place I wanted to start with. And I came here thinking that I might get a few suggestions to correct this code and learn. So please, instead of assuming things about me just because the place I started with is lousy, just try and help me out here. I will respect all of your inputs.

You are doing it right... just not the chatGPT part... Start with a master drawing. "Connect" everything. Then, write a description of how every component in the finished product will interact. Then start with a blank sketch.

Make one sketch for each device to test and learn how they work. Next you will combine these sketches (so, when you are writing each mini-sketch, keep in mind the overall sketch).

Understand that your working robot depends on all devices' ability to operate when needed, not waiting to get input or give output. For that, you will want to learn about "multiple events" occurring (really, just a mini version of time-sharing a processor).

An excellent (free, online) simulator: wokwi.com

On that simulator you can choose your MCU, add all your components, code and libraries, and "run" your robot. You will need to allow for some components not being available, for example, your flex sensor is analog so you would substitute an adjustable analog input, like a potentiometer.

Keep asking questions. Throw chatGPT out the window.

Thank you for your advice, but there still is one more problem. I wanted to run a simulation for my arm but I can't find a simulator which has a Servo Driver. Do you know any simulators which has a PCA9685 in their devices?

Wokwi has Servo.h... look under the "Libraries" tab, then "Add a library" then type "Servo" and select the "Servo" library.

If you want to add a special library, copy the raw code of your .H and .CPP file and add them under the "libraries" tab... "add a file" and give your library filenames.

I just checked... wokwi has this... use the library tab, then click the + button and add that number and you will be given a list... choose the exact library.

I can't find the PCA9685 driver here in the parts list

Yes, wokwi does not have every part... or every library... you have to fake that part and use the Serial Monitor (or a similar device) for output or input. You can also use GPIO pins for multiple servos alongside the Serial Monitor. Like this...

The user knows the library exists... they were looking for a part/device/component.

Ah, yes. I see that now.