ShoulderGuardAI: Raspberry Pi Exercise Form Coach

by Yevhenii Murenko in Circuits > Raspberry Pi

19 Views, 0 Favorites, 0 Comments

ShoulderGuardAI: Raspberry Pi Exercise Form Coach

Logo_ShoulderGuardAI.jpg
2.jpg

Shoulder exercises look simple, but small mistakes such as shrugging, lifting unevenly, flaring the elbows, or leaning backward can place unnecessary stress on the body. I built ShoulderGuardAI to explore whether a small local AI system could recognise these movement patterns and provide immediate feedback without sending camera footage to a cloud service.

The finished prototype uses a Raspberry Pi 5, a USB camera, MediaPipe Pose, a trained classifier, and a Gradio web interface. It can analyse an uploaded video or a live exercise session. A valid RFID card identifies the user, while an RGB LED, LCD, and buzzer provide local feedback. Session and repetition results are stored in PostgreSQL. Everything is mounted in a laser-cut wooden enclosure.

This Instructable explains the complete process: designing the enclosure, collecting data, extracting body keypoints, training the model, wiring the modules, installing the software, and running the final system over Wi-Fi.

Supplies

4.jpg

Electronics

  1. Raspberry Pi 5
  2. Compatible USB-C power supply
  3. 64 GB microSD card
  4. Freenove Projects Board for Raspberry Pi
  5. Logitech USB webcam or another UVC-compatible USB camera
  6. MFRC522 RFID reader with cards/tags
  7. 16 x 2 I2C LCD
  8. RGB LED module
  9. Buzzer
  10. Momentary push button
  11. Female-to-female jumper wires
  12. Brass standoffs, nuts and screws

Enclosure materials

  1. 4 mm laser-cut plywood or MDF
  2. Brass Spacer M2.5 Male Female Hexagonal Copper Bolts Screws and Stainless Steel Nuts Assortment Kit

Software

  1. Raspberry Pi OS
  2. Python 3 virtual environment
  3. MediaPipe and OpenCV
  4. scikit-learn and joblib
  5. Gradio
  6. PostgreSQL and pgAdmin in Docker
  7. Github

Plan the System

photo_2026-06-17_23-19-23.jpg

I separated the project into five connected parts:

  1. Input: USB camera or uploaded exercise video.
  2. Pose processing: MediaPipe converts each frame into numerical body landmarks.
  3. Classification: the trained model and repetition logic classify the movement.
  4. Feedback: Gradio, LCD, RGB LED, and buzzer show the result.
  5. Storage: PostgreSQL stores the user, session, and repetition results.

The camera observes the upper body. The application focuses on shoulders, elbows, wrists, torso, and hips because these landmarks are most relevant to a lateral shoulder raise. Removing unrelated landmarks reduces noise and makes the model less dependent on a person's height or limb length.

The system runs locally on the Raspberry Pi. Only structured session results are stored in the database; raw training videos are kept as development data and are not required for normal use.

Collect and Label Exercise Videos

classes.jpg
videos example.jpg
folders.jpg

Create one folder for every class:

Data/
|-- neutral_or_rest/
|-- correct_form/
|-- flared_elbows/
|-- asymmetrical_lift/
|-- shrugged_shoulders/
`-- excessive_back_arching/

Record several repetitions for every class. I used both phone recordings and the same USB camera used by the prototype. USB-camera examples were important because camera position, mirroring, compression, clothing, lighting, and distance can change the landmark values.

Recording recommendations:

  1. Keep the upper body, hips, arms, and hands visible.
  2. Use a plain, well-lit area.
  3. Include different clothes and distances.
  4. Record clean examples of only one class per labelled clip.
  5. Remove failed or ambiguous repetitions before processing.
  6. Collect a reasonably balanced number of examples per class.

Short edited clips are acceptable when resolution, frame rate, and aspect ratio stay consistent. I exported MP4/H.264 at 720p and 30 fps.

Extract MediaPipe Keypoints

annotated.jpg

MediaPipe Pose detects body landmarks in every sampled frame. The processing script draws a skeleton preview and writes the landmark coordinates to CSV.

From the Raspberry Pi project directory, activate the virtual environment and process the labelled videos:

cd "your working directory" for me it was "~/2025-26-projectone-ctai-YevheniiMurenko/My_project/RPi"
source ~/.venv/bin/activate
python scripts/process_dataset_videos.py --input-dir ../Data --output-dir data

The generated structure contains:

data/
|-- raw_videos/
|-- keypoints_csv/
|-- annotated_previews/
`-- merged/

Each CSV row contains the timestamp, class label, landmark values, and derived movement features. Coordinates are normalised relative to the body so the model depends less on camera distance and body proportions.

Build Repetitions and Train the Classifier

v5.jpg

A single frame is not always enough to distinguish similar classes. For example, most shoulder-raise classes look nearly identical during the first half of the movement. The project therefore also groups frames into repetitions and uses peak movement information.

Build the repetition-level dataset:

python scripts/build_repetition_dataset.py \
--input-dir data/keypoints_csv \
--output data/merged/shoulderguardai_repetition_dataset.csv

Train and validate the classifier:

python scripts/train_classifier.py \
--dataset data/merged/shoulderguardai_repetition_dataset.csv

The trained model is exported as a joblib file and loaded by the Gradio application:

models/shoulderguardai_form_classifier.joblib

I compared multiple tabular classifiers in Jupyter, including Random Forest, Logistic Regression, k-nearest neighbours, Gradient Boosting, and Support Vector Machine. Validation used held-out repetitions or videos rather than mixing neighbouring frames from the same recording across training and validation. This reduces data leakage.

For live use, the application analyses short rolling windows and summarises a completed repetition before changing the main feedback. Peak-angle rules help separate visually similar shoulder positions. Excessive back arching remains the most difficult class because a front-facing 2D camera sees depth changes less clearly than a human observer.

Create the PostgreSQL Database

table gradio.jpg
pgadmin.jpg
drawio.jpg

The database contains four main tables:

  1. users: RFID UID and user name
  2. devices: prototype information
  3. sessions: one exercise session per user
  4. production_repetition_results: one classified result per repetition

PostgreSQL and pgAdmin run in Docker. Start them from the database folder:

cd ~/2025-26-projectone-ctai-YevheniiMurenko/Milestone01b_Database_ERD
docker compose --env-file .env.example up -d

The Gradio application connects to PostgreSQL and saves the class, confidence, symmetry score, repetition number, timestamps, and linked RFID user.

Never publish real passwords. The repository contains only .env.example values.

Wire and Test the Hardware

4.jpg

The final prototype uses this pin map:

LCD: SDA, SCL, 5V, GND
RGB LED: GPIO5 red, GPIO6 green, GPIO13 blue, 5V common
Buzzer: GPIO12
Button: GPIO14 and GND, using the internal pull-up resistor
RFID: SPI connection; power the MFRC522 from 3.3V
Camera: USB

The RGB module is active-low. Its colours represent the six classes:

  1. Grey/off: neutral or waiting
  2. Green: correct form
  3. Yellow: flared elbows
  4. Orange: asymmetrical lift
  5. Red: shrugged shoulders
  6. Purple: excessive back arching

Test every module separately before combining them. Enable I2C and SPI in raspi-config. Check the RFID reader with:

python test_modules/test_rfid.py

Important electrical safety

  1. Power off the Raspberry Pi before changing wires.
  2. Do not connect 5V directly to a GPIO pin.
  3. Insulate each button terminal separately.
  4. Do not leave loose copper strands near neighbouring terminals.
  5. Add strain relief so moving the wooden lid cannot pull the wires together.
  6. Use a multimeter continuity test before closing the enclosure.


Laser-Cut the Enclosure

lazercut.jpg

The enclosure was designed around the Freenove project board and cut from 3 mm wood.

Approximate outside dimensions:

  1. Width: 253 mm
  2. Depth: 158 mm
  3. Height: 67 mm
  4. Finger-joint pitch: approximately 9 mm

The top panel has openings for the LCD, RGB LED, button, camera cable, and RFID scan area. The camera sits at the back edge so its angle can be adjusted while the USB cable passes into the enclosure.

Before cutting the final material:

  1. Print or cut a cardboard test layer.
  2. Check every module opening.
  3. Measure the real material thickness with callipers.
  4. Apply the laser cutter's kerf compensation.
  5. Keep metal screws away from the RFID antenna area.
  6. Add ventilation around the Raspberry Pi.


Assemble the Prototype

4.jpg
3.jpg
  1. Mount the Raspberry Pi and Freenove board on the base using standoffs.
  2. Install the internal support layer.
  3. Mount the LCD, RGB LED, RFID reader, buzzer, and button.
  4. Route cables through the internal openings.
  5. Attach the USB camera at the rear edge.
  6. Confirm that no wire is pinched by the lid.
  7. Check continuity and power rails before powering the Pi.
  8. Test the system with the lid open.
  9. Gently move the lid and cables while powered to check for intermittent connections.
  10. Close the enclosure only after every module is stable.

The LCD is used for local status and network information. It is not the main coaching display because a 16 x 2 screen is difficult to read from several metres away. Detailed feedback appears in Gradio.

Install and Run the Application

gradio.jpg

Clone the project, create a virtual environment, and install the Python packages:

git clone <repository_name>.git
cd 2025-26-projectone-ctai-YevheniiMurenko/My_project/RPi
python3 -m venv ~/.venv
source ~/.venv/bin/activate
pip install -r requirements.txt

Enable I2C, SPI, SSH, and Wi-Fi. Connect the Pi and the user's phone or laptop to the same network.

Start the user-friendly application manually:

python app_friendly.py

Open:

http://<raspberry-pi-ip>:7861

The production setup uses systemd so the database and Gradio start automatically after boot. The service templates are in My_project/RPi/deployment/.

sudo cp deployment/shoulderguardai-database.service /etc/systemd/system/
sudo cp deployment/shoulderguardai-gradio.service /etc/systemd/system/
sudo systemctl daemon-reload
sudo systemctl enable shoulderguardai-database.service
sudo systemctl enable shoulderguardai-gradio.service
sudo systemctl start shoulderguardai-database.service
sudo systemctl start shoulderguardai-gradio.service

Repository: https://github.com/howest-mct/2025-26-projectone-ctai-YevheniiMurenko


Use ShoulderGuardAI

  1. Plug in the prototype and wait for the LCD to show its network address.
  2. Open the Gradio address from a phone or laptop on the same Wi-Fi.
  3. Place an authorised RFID card on the reader.
  4. Choose video upload or real-time filming.
  5. For live recording, press the on-screen control or the physical button.
  6. Move into position during the countdown.
  7. Perform lateral shoulder raises while keeping the full upper body visible.
  8. Observe the LCD, RGB LED, buzzer, and web interface.
  9. Stop recording or wait for the automatic limit.
  10. Open the Data tab to review saved repetitions.
  11. Remove or rescan the RFID card to end the user's access.

The model is a coaching prototype, not a medical device. Its output should support awareness and discussion, not replace professional medical or physiotherapy advice.

Troubleshooting and Improvements

debug.jpg

Camera is not detected

  1. Check the USB connection.
  2. Confirm the camera index in the configuration.
  3. Close other programs that may already use the camera.

Pose landmarks are unstable

  1. Improve lighting.
  2. Keep the upper body and hands inside the frame.
  3. Avoid a busy background.
  4. Use a similar camera height to the training setup.

RFID does not read

  1. Enable SPI.
  2. Power the MFRC522 from 3.3V.
  3. Keep the card close and parallel to the antenna.
  4. Keep metal parts away from the reader.

The Raspberry Pi resets or flickers

  1. Disconnect power immediately.
  2. Inspect for exposed copper, loose strands, or pinched wiring.
  3. Test modules one at a time.
  4. Check supply quality and vcgencmd get_throttled.
  5. Improve ventilation if the enclosure becomes hot.

Future improvements

  1. Collect data from more people and camera positions.
  2. Add a side or depth camera for more reliable back-arching detection.
  3. Use a smaller custom PCB instead of a development board.
  4. Add model confidence calibration and clearer uncertainty feedback.
  5. Add a removable, serviceable lid instead of permanently sealing electronics.


Downloads and References