Advanced Level • Lesson 11

🎛️ Integrating Display and Controls

⏱️ 60 minutes 📚 Advanced 🎯 System Integration
🎛️

Integrating Display and Controls

Learn how to combine everything - add a display to show status and a button to start/stop tracking!

State Management

Your tracking system needs to remember its current state - is it tracking or stopped? We use variables to track this!

Tracking State:

# State variables tracking_active = False # Is tracking on or off? face_detected = False # Is a face currently detected? servo_angle = 90 # Current servo position # States your system can be in: # 1. Stopped - not tracking, waiting for button press # 2. Tracking - actively following face # 3. No Face - tracking active but no face detected

Button to Start/Stop Tracking

Add a button that toggles tracking on and off. When pressed, it changes the tracking state!

Button Control Code:

import RPi.GPIO as GPIO import time # Set up button GPIO.setmode(GPIO.BCM) GPIO.setup(2, GPIO.IN, pull_up_down=GPIO.PUD_UP) # Tracking state tracking_active = False last_button_state = GPIO.HIGH def check_button(): """Check if button was pressed (toggle tracking)""" global tracking_active, last_button_state current_state = GPIO.input(2) # Detect button press (transition from HIGH to LOW) if last_button_state == GPIO.HIGH and current_state == GPIO.LOW: tracking_active = not tracking_active # Toggle state print(f"Tracking: {'ON' if tracking_active else 'OFF'}") time.sleep(0.3) # Debounce last_button_state = current_state return tracking_active # Use in main loop try: while True: is_tracking = check_button() if is_tracking: print("Tracking is active!") # Do tracking here else: print("Tracking stopped - waiting...") time.sleep(0.1) except KeyboardInterrupt: GPIO.cleanup()

Displaying Status on Screen

Use an LCD display to show the current status - is tracking on? Is a face detected? What's the servo angle?

Status Display Code:

from RPLCD.i2c import CharLCD import time # Initialize LCD lcd = CharLCD(i2c_expander='PCF8574', address=0x27, port=1, cols=16, rows=2, dotsize=8) def update_display(tracking_active, face_detected, servo_angle): """Update LCD with current status""" lcd.clear() # First line: Tracking status if tracking_active: status = "Tracking: ON" else: status = "Tracking: OFF" lcd.write_string(status) # Second line: Face and angle info lcd.cursor_pos = (1, 0) if face_detected: lcd.write_string(f"Face: YES {int(servo_angle)}°") else: lcd.write_string("Face: NO") # Use in main loop try: while True: # Get current state tracking = check_button() face_found = detect_face() # Your face detection function angle = get_servo_angle() # Your servo angle function # Update display update_display(tracking, face_found, angle) time.sleep(0.5) # Update display every 0.5 seconds except KeyboardInterrupt: lcd.clear() lcd.write_string("Stopped") time.sleep(2) lcd.clear()

Project: Full Control Interface

Let's combine everything - face detection, servo tracking, display, and button control!

Materials Needed:

  • Raspberry Pi
  • Raspberry Pi Camera Module
  • Servo motor (for pan/tilt)
  • 16x2 LCD Display (I2C)
  • Push button
  • Jumper wires
  • Breadboard

Complete Integrated System Code:

import cv2 import RPi.GPIO as GPIO from RPLCD.i2c import CharLCD import time # ===== SETUP ===== # Face detection face_cascade = cv2.CascadeClassifier(cv2.data.haarcascades + 'haarcascade_frontalface_default.xml') # Servo motor GPIO.setmode(GPIO.BCM) GPIO.setup(18, GPIO.OUT) servo_pwm = GPIO.PWM(18, 50) servo_pwm.start(0) # Button GPIO.setup(2, GPIO.IN, pull_up_down=GPIO.PUD_UP) # LCD Display lcd = CharLCD(i2c_expander='PCF8574', address=0x27, port=1, cols=16, rows=2, dotsize=8) # Camera cap = cv2.VideoCapture(0) cap.set(cv2.CAP_PROP_FRAME_WIDTH, 320) cap.set(cv2.CAP_PROP_FRAME_HEIGHT, 240) # ===== STATE VARIABLES ===== tracking_active = False current_servo_angle = 90 last_button_state = GPIO.HIGH last_display_update = 0 # ===== FUNCTIONS ===== def set_servo_angle(angle): """Move servo to angle""" global current_servo_angle duty = 2 + (angle / 180) * 10 servo_pwm.ChangeDutyCycle(duty) time.sleep(0.1) servo_pwm.ChangeDutyCycle(0) current_servo_angle = angle def check_button(): """Check button and toggle tracking""" global tracking_active, last_button_state current_state = GPIO.input(2) if last_button_state == GPIO.HIGH and current_state == GPIO.LOW: tracking_active = not tracking_active time.sleep(0.3) # Debounce last_button_state = current_state return tracking_active def update_display(tracking, face_detected, angle): """Update LCD display""" lcd.clear() # Line 1: Status if tracking: lcd.write_string("Tracking: ON") else: lcd.write_string("Tracking: OFF") # Line 2: Face info lcd.cursor_pos = (1, 0) if face_detected: lcd.write_string(f"Face:YES {int(angle)}°") else: lcd.write_string("Face: NO") def calculate_servo_angle(face_x, frame_width): """Convert face X to servo angle""" angle = (face_x / frame_width) * 180 return max(0, min(180, angle)) # ===== MAIN LOOP ===== print("System started! Press button to toggle tracking.") lcd.write_string("Press button") time.sleep(2) try: while True: # Check button is_tracking = check_button() if is_tracking: # Read camera frame ret, frame = cap.read() if ret: gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY) faces = face_cascade.detectMultiScale(gray, 1.1, 4) if len(faces) > 0: # Face detected - track it x, y, w, h = faces[0] face_center_x = x + w // 2 # Calculate target angle target_angle = calculate_servo_angle(face_center_x, 320) # Smooth movement angle_diff = target_angle - current_servo_angle if abs(angle_diff) > 2: step = 5 if angle_diff > 0 else -5 new_angle = current_servo_angle + step new_angle = max(0, min(180, new_angle)) set_servo_angle(new_angle) # Update display update_display(True, True, current_servo_angle) else: # No face detected update_display(True, False, current_servo_angle) else: # Tracking stopped update_display(False, False, current_servo_angle) time.sleep(0.1) except KeyboardInterrupt: cap.release() servo_pwm.stop() lcd.clear() lcd.write_string("Stopped") time.sleep(2) lcd.clear() GPIO.cleanup() print("System stopped!")

Understanding the Complete System:

  • Button Control: Press button to start/stop tracking
  • Face Detection: Continuously detects faces when tracking is active
  • Servo Tracking: Moves servo to follow detected face
  • Status Display: Shows tracking status, face detection, and servo angle
  • State Management: System remembers if tracking is on/off

Summary

You've learned:

  • ✅ State management tracks system status (tracking on/off)
  • ✅ Button can toggle tracking on and off
  • ✅ LCD display shows current system status
  • ✅ All components work together in one system
  • ✅ Display updates in real-time to show what's happening
  • ✅ Button provides user control over the system
🎉 Almost There! You've integrated all the components! In the final lesson, you'll assemble everything into the complete human-tracking fan project.

🎮 Try It: Practice Integration!

Practice combining components. Try these challenges:

📝 Challenge 1: State Toggle

Write code that toggles a state variable when button is pressed:

📝 Challenge 2: Status Display

Write a function that displays status on LCD:

💡 Tip: Remember to update the display regularly (every 0.5-1 second), and always clear the display before writing new content!

🎯 Activity: Full Control Interface

What You'll Build:

Create a complete control interface with display and button for your tracking system!

Step-by-Step Instructions:

  1. Connect Components: Wire button, LCD, servo, and camera
  2. Write Button Function: Create function to toggle tracking state
  3. Write Display Function: Create function to update LCD status
  4. Integrate Everything: Combine all components in main loop
  5. Test: Press button to start/stop, watch display update
  6. Refine: Adjust display update frequency and button debounce

Display Information:

  • ✅ Line 1: "Tracking: ON" or "Tracking: OFF"
  • ✅ Line 2: "Face: YES 90°" or "Face: NO"
  • ✅ Updates every 0.5-1 second
  • ✅ Shows current servo angle when face detected
🏆 Bonus Challenge: Can you add a second button that resets the servo to center position (90 degrees)?

💪 Practice Challenges

Challenge 1: Enhanced Display

Add more information to the display:

  • Show frame count or detection rate
  • Show time since tracking started
  • Show number of faces detected

Challenge 2: Multiple Buttons

Add a second button for different functions:

  • Button 1: Start/Stop tracking
  • Button 2: Reset servo to center

Challenge 3: Status LED

Add an LED that indicates system status:

  • Green LED: Tracking active, face detected
  • Yellow LED: Tracking active, no face
  • Red LED: Tracking stopped