Teleoperation Robots with Acrome SMD: Advanced Motion Control
What is Teleoperation?
Definition of Teleoperation
Teleoperation, also known as remote robot control, is the process of operating a robotic system from a distance using wired or wireless communication. Unlike fully autonomous robots, which operate based on pre-programmed logic and artificial intelligence, teleoperated robots rely on human input to execute commands in real time. This enables precise control and intervention, making it a valuable technology for a wide range of applications.
How Teleoperation Works
Teleoperation consists of three key components:
1. User Interface (UI): The control medium that allows operators to send commands. This can be a mobile application, a keyboard interface, a joystick, VR controllers, or even EEG (brain-computer interface) systems.
2. Communication System: The network through which control commands are sent to the robot and feedback is received. This can be WiFi, Bluetooth, radio waves, satellite communication, or cellular networks.
3. Robotic System: The hardware and software components that execute commands and provide movement or actions. This includes sensors, actuators, controllers, safety systems, and feedback mechanisms.
Why is Teleoperation Important?
Teleoperation is essential in robotics because it enables human intervention in situations where automation alone is not sufficient. Some key benefits include:
- Remote Accessibility: Operators can control robots from different locations, reducing the need for physical presence in dangerous or inaccessible areas.
- Enhanced Safety: Reduces human exposure to hazardous environments such as high-radiation zones, deep-sea exploration, and outer space.
- Precision Control: Provides real-time human decision-making and adjustments, leading to higher accuracy than fully automated systems.
- Scalability: A single operator can control multiple robots simultaneously, improving efficiency in industrial and research settings.
- Versatility: Teleoperation can be applied across various fields, including healthcare, agriculture, defense, logistics, and research.
Applications of Teleoperation
Teleoperation has been successfully implemented in various industries, proving its flexibility and effectiveness:
- Industrial Robotics: Factories use teleoperated robotic arms for assembly, welding, material handling, and quality control.
- Autonomous Vehicles: Warehouse robots, delivery drones, and self-driving forklifts can be remotely managed.
- Medical Robotics: Remote-controlled robotic arms perform telesurgery, enabling doctors to operate on patients from thousands of kilometers away.
- Defense and Security: Bomb disposal robots, surveillance drones, and robotic reconnaissance units help security forces in high-risk areas.
- Space Exploration: NASA’s rovers on Mars, such as Perseverance, are controlled remotely from Earth to explore and analyze planetary surfaces.
- Search and Rescue: Teleoperated robots navigate collapsed buildings and hazardous environments to locate and assist survivors.
- Agriculture and Farming: Remote-controlled tractors, robotic planters, and harvesting machines optimize agricultural productivity.
- Hazardous Material Handling: Robots manage toxic chemicals and nuclear waste, reducing human risk exposure.
Methods for Teleoperating Acrome SMD Robots
Acrome SMD systems provide a robust platform for teleoperation. Depending on the application, different control methods can be used:
Teleoperation via Mobile Application: Using an Android APK for wireless robot control, allowing for flexibility and ease of use.
Teleoperation via PC Keyboard: Utilizing keyboard commands to control robots, ideal for manual operation and research.
Teleoperation via Joystick or Game Controller: Offering an intuitive control method for applications requiring precise movements.
Robot with Acrome SMD
Teleoperation Using a Mobile Application (APK)
Why Use a Mobile Application?
A mobile application provides an easy-to-use, wireless control system for Acrome SMD-powered robots. Advantages include:
- Wireless Connectivity: Eliminates the need for physical cables, enhancing mobility and range.
- User-Friendly Interface: Touchscreen interfaces provide intuitive control, reducing the learning curve for new operators.
- Remote Access: Allows operators to control robots from different locations via an internet connection.
- Real-Time Responsiveness: Ensures instant feedback and execution of commands, providing a seamless experience.
- Multi-Device Support: Multiple users can control or monitor robots from different devices simultaneously.
System Architecture
1. User Input: The operator interacts with the mobile app to send movement commands.
2. Wireless Communication: The app transmits control signals to a Flask API running on a Raspberry Pi via WiFi.
3. Command Processing: The Flask API processes the received signals and transmits them to the Acrome SMD motor controllers.
4. Motor Execution: Acrome SMD controllers adjust motor speeds and directions accordingly.
5. Safety Mechanism: A monitoring system continuously checks motor performance and stops the robot if any issues arise.
Python Code for Mobile Application-Controlled Robot Movement:
1from flask import Flask, request
2from smd.red import *
3from serial.tools.list_ports import comports
4from platform import system
5import threading
6import time
78app = Flask(__name__)
9classPIDController:10def__init__(self, kp, ki, kd):11 self.kp = kp
12 self.ki = ki
13 self.kd = kd
14 self.previous_error = 015 self.integral = 01617defcalculate(self, error, delta_time):18 self.integral += error * delta_time
19 derivative = (error - self.previous_error) / delta_time if delta_time > 0else020 output = (self.kp * error) + (self.ki * self.integral) + (self.kd * derivative)
21 self.previous_error = error
22returnmax(min(output, 100), -100) # Clamp output to motor speed range23# Robot Setup24defUSB_Port():25 ports = list(comports())
26 usb_names = {
27"Windows": ["USB Serial Port"],
28"Linux": ["/dev/ttyUSB"],
29"Darwin": [
30"/dev/tty.usbserial",
31"/dev/tty.usbmodem",
32"/dev/tty.SLAB_USBtoUART",
33"/dev/tty.wchusbserial",
34"/dev/cu.usbserial",
35"/dev/cu.usbmodem",
36"/dev/cu.SLAB_USBtoUART",
37"/dev/cu.wchusbserial",
38 ],
39 }
40 os_name = system()
41if ports:
42for port, desc, hwid insorted(ports):
43ifany(name in port or name in desc for name in usb_names.get(os_name, [])):
44return port
45print("Current ports:")
46for port, desc, hwid in ports:
47print(f"Port: {port}, Description: {desc}, Hardware ID: {hwid}")
48else:
49print("No port found")
50returnNone5152port = USB_Port()
53smd = Master(port) if port elseNone54if smd:
55 smd.attach(Red(0)) # Left motor56 smd.attach(Red(1)) # Right motor57 smd.set_operation_mode(0, OperationMode.PWM)
58 smd.set_operation_mode(1, OperationMode.PWM)
59 smd.set_shaft_rpm(0, 100)
60 smd.set_shaft_rpm(1, 100)
61 smd.set_shaft_cpr(0, 6533)
62 smd.set_shaft_cpr(1, 6533)
63 smd.enable_torque(0, 1)
64 smd.enable_torque(1, 1)
65 left_pid = PIDController(kp=23.55, ki=0.00, kd=18.65)
66 right_pid = PIDController(kp=21.37, ki=0.00, kd=18.15)
67 base_speed = 6068 turning_speed = 4069defstop_robot():70"""Stop the robot by setting duty cycle to 0."""71 smd.set_duty_cycle(0, 0)
72 smd.set_duty_cycle(1, 0)
7374defwatchdog_check():75"""Check periodically if the motors are stuck or not working."""76whileTrue:
77# Logic to check if motors are stuck (e.g., if duty cycle hasn't changed for a while)78# You can implement a simple check based on time or position feedback.79# For now, we just print a simple message.80print("Watchdog: Checking motor status.")
81 time.sleep(5) # Periodically check every 5 seconds8283# Start a separate thread for watchdog monitoring84watchdog_thread = threading.Thread(target=watchdog_check, daemon=True)
85watchdog_thread.start()
8687@app.route('/control', methods=['POST'])88defcontrol():89global last_command_time
90 data = request.get_json()
91 direction = data.get('direction', '')
92 target_speed = 60# Hedef hız93 turning_speed = 40# Dönüş sırasında kullanılacak hız94 left_speed = 095 right_speed = 09697if smd:
98 last_command_time = time.time()
99 current_time = time.time()
100 delta_time = current_time - last_command_time
101102if direction == '1': # Move forward103 error = target_speed
104 left_speed = left_pid.calculate(error, delta_time)
105 right_speed = right_pid.calculate(error, delta_time)
106 smd.set_duty_cycle(0, -left_speed) # Left motor forward107 smd.set_duty_cycle(1, right_speed)
108elif direction == '4': # Move backward109 error = -target_speed
110 left_speed = left_pid.calculate(error, delta_time)
111 right_speed = right_pid.calculate(error, delta_time)
112 smd.set_duty_cycle(0, -left_speed) # Left motor backward113 smd.set_duty_cycle(1, right_speed) # Right motor backward114elif direction == '3': # Turn right115 smd.set_duty_cycle(0, -turning_speed) # Left motor forward116 smd.set_duty_cycle(1, 0)
117118elif direction == '2': # Turn left119 smd.set_duty_cycle(0, 0)
120 smd.set_duty_cycle(1, turning_speed)
121122elif direction == '0': # Stop123 stop_robot()
124return {"status": "success", "direction": direction}
125126127return {"status": "error", "message": "Robot not connected"}
128129if __name__ == '__main__':
130 app.run(host='0.0.0.0', port=5005, debug=True)
Teleoperation via PC Keyboard
Why Use a Keyboard for Teleoperation?
A PCkeyboard can be used to send commands to AcromeSMDrobots, providing a simple and effective way to control movements. This method is ideal for research, industrial applications, and testing environments where precise control is required.
- High Precision Control: Useful for manual operation requiring fine movement adjustments.
- Reliable Performance: No dependency on wireless connections, ensuring uninterrupted operation.
- Easy Integration: Simple to implement using Python and other programming languages.
Python Code for Keyboard-Controlled Robot Movement:
1from pynput import keyboard
2import time
3from smd.red import *
4from serial.tools.list_ports import comports
5from platform import system
6classPIDController:7def__init__(self, kp, ki, kd):8 self.kp = kp
9 self.ki = ki
10 self.kd = kd
11 self.previous_error = 012 self.integral = 01314defcalculate(self, error, delta_time):15 self.integral += error * delta_time
16 derivative = (error - self.previous_error) / delta_time if delta_time > 0else017 output = (self.kp * error) + (self.ki * self.integral) + (self.kd * derivative)
18 self.previous_error = error
19returnmax(min(output, 100), -100)
202122defUSB_Port():23 ports = list(comports())
24 usb_names = {
25"Windows": ["USB Serial Port"],
26"Linux": ["/dev/ttyUSB"],
27"Darwin": [
28"/dev/tty.usbserial",
29"/dev/tty.usbmodem",
30"/dev/tty.SLAB_USBtoUART",
31"/dev/tty.wchusbserial",
32"/dev/cu.usbserial",
33 ]
34 }
35 os_name = system()
36if ports:
37for port, desc, hwid insorted(ports):
38ifany(name in port or name in desc for name in usb_names.get(os_name, [])):
39print("Connected!")
40return port
41print("Available ports:")
42for port, desc, hwid in ports:
43print(f"Port: {port}, Description: {desc}, HWID: {hwid}")
44else:
45print("No ports detected!")
46returnNone474849defteleoperate_smd():50print("Use W/A/S/D to control the robot. Press Q to quit.")
5152 port = USB_Port()
53ifnot port:
54print("No suitable port found. Exiting...")
55return5657try:
58 smd = Master(port)
59 smd.attach(Red(0)) # Left motor (ID 0)60 smd.attach(Red(1)) # Right motor (ID 1)6162 smd.enable_torque(0, 1)
63 smd.enable_torque(1, 1)
6465 left_pid = PIDController(kp=24.96, ki=0.00, kd=19.10)
66 right_pid = PIDController(kp=46.97, ki=0.00, kd=18.96)
6768 base_speed = 10069 turning_speed = 100# Speed for turning70 last_time = time.time()
7172defon_press(key):73nonlocal last_time
7475try:
76# Calculate time difference77 current_time = time.time()
78 delta_time = current_time - last_time
79 last_time = current_time
8081ifhasattr(key, 'char'):
82if key.char == 'w': # Move forward83print("Move Forward")
84 error = base_speed
85 left_speed = left_pid.calculate(error, delta_time)
86 right_speed = right_pid.calculate(error, delta_time)
87# Send commands to both motors simultaneously88 smd.set_duty_cycle(0, -left_speed) # Left motor forward89 smd.set_duty_cycle(1, right_speed) # Right motor forward90elif key.char == 's': # Move backward91print("Move Backward")
92 error = -base_speed
93 left_speed = left_pid.calculate(error, delta_time)
94 right_speed = right_pid.calculate(error, delta_time)
95# Send commands to both motors simultaneously96 smd.set_duty_cycle(0, -left_speed) # Left motor backward97 smd.set_duty_cycle(1, right_speed) # Right motor backward98elif key.char == 'a': # Turn left99print("Turn Left")
100# Send commands to both motors simultaneously101 smd.set_duty_cycle(0, 0) # Left motor stopped102 smd.set_duty_cycle(1, turning_speed) # Right motor forward103elif key.char == 'd': # Turn right104print("Turn Right")
105# Send commands to both motors simultaneously106 smd.set_duty_cycle(0, -turning_speed) # Left motor forward107 smd.set_duty_cycle(1, 0) # Right motor stopped108elif key.char == 'q': # Quit109print("Exiting...")
110returnFalse111except AttributeError:
112pass113114defon_release(key):115# Stop both motors simultaneously116 smd.set_duty_cycle(0, 0)
117 smd.set_duty_cycle(1, 0)
118119# Start keyboard listener120with keyboard.Listener(on_press=on_press, on_release=on_release) as listener:
121 listener.join()
122123except Exception as e:
124print(f"Error: {e}")
125finally:
126# Stop both motors simultaneously during cleanup127 smd.set_duty_cycle(0, 0)
128 smd.set_duty_cycle(1, 0)
129 smd.enable_torque(0, 0)
130 smd.enable_torque(1, 0)
131 smd.close()
132print("SMD connection closed.")
133134teleoperate_smd()
Teleoperation via Joystick or Game Controller
Why Use a Joystick or Game Controller?
Using a joystick or game controller for teleoperation provides a more intuitive and precise control method, especially for applications requiring real-time movement and fine adjustments. Compared to keyboard-based control, joysticks offer smooth transitions, making them ideal for robot navigation, industrial automation, and gaming-related robotics projects
Advantages of Joystick-Based Teleoperation
• Analog Control: Unlike keyboards with discrete inputs, joysticks provide a range of motion, enabling gradual speed and direction adjustments.
• Ergonomic Design: Game controllers are comfortable and easy to use, reducing fatigue for long teleoperation sessions.
• Dual-Axis Movement: The ability to control both X and Y axes simultaneously enhances maneuverability.
• Multi-Button Functions: Additional buttons can be assigned for robotic arm control, mode switching, or emergency stops.
• Wireless Options: Many joysticks and game controllers support Bluetooth or RF connections, allowing remote control without physical constraints.
System Architecture
1. User Input: The operator uses a joystick or game controller to provide movement commands.
2. Signal Processing: The joystick transmits X and Y axis values, and button presses are detected for additional actions.
3. Communication System: Signals are transmitted to the Acrome SMD controller via USB, Bluetooth, or WiFi.
4. Motor Execution: The Acrome SMD motor controllers adjust motor speeds and directions based on joystick input.
5. Safety Mechanism: The system monitors joystick drift and connection stability, ensuring smooth and safe operation.
Python Code for Joystick-Controlled Robot Movement:
1import time
2from smd.red import Master, Red
3from serial.tools.list_ports import comports
4from platform import system
56# Detect USB Port7defdetect_usb_port():8"""Detects the connected USB port for communication."""9 ports = list(comports())
10 usb_names = {
11"Windows": ["USB Serial Port"],
12"Linux": ["/dev/ttyUSB"],
13"Darwin": [
14"/dev/tty.usbserial", "/dev/tty.usbmodem",
15"/dev/tty.SLAB_USBtoUART", "/dev/tty.wchusbserial",
16"/dev/cu.usbserial", "/dev/cu.usbmodem",
17"/dev/cu.SLAB_USBtoUART", "/dev/cu.wchusbserial",
18 ]
19 }
20 os_name = system()
21if ports:
22for port in ports:
23ifany(name in port.device or name in port.description for name in usb_names.get(os_name, [])):
24return port.device
25returnNone2627# Initialize USB connection28serial_port = detect_usb_port()
29ifnot serial_port:
30print("No valid USB port detected. Check the connection.")
31 exit()
3233# Initialize SMD Red Motors34master = Master(serial_port)
3536MOTOR_LEFT_ID = 0# Left Motor37MOTOR_RIGHT_ID = 1# Right Motor38JOYSTICK_ID = 5# Joystick module ID3940motor_left = master.attach(Red(MOTOR_LEFT_ID)) # Attach Left Motor41motor_right = master.attach(Red(MOTOR_RIGHT_ID)) # Attach Right Motor4243# Set motors to PWM mode and enable torque44master.set_operation_mode(MOTOR_LEFT_ID, 0)
45master.set_operation_mode(MOTOR_RIGHT_ID, 0)
46master.enable_torque(MOTOR_LEFT_ID, True)
47master.enable_torque(MOTOR_RIGHT_ID, True)
4849# Define Dead Zone for Joystick50DEAD_ZONE = 15# Ignore small movements51previous_state = None# Store the last printed joystick state5253# Motor Control with Joystick (Fixed Four Directions, Corrected Motor Directions)54defcontrol_motors():55global previous_state
5657print("Motor control via joystick is active...")
58print("Waiting for joystick movement...")
5960whileTrue:
61 joystick = master.get_joystick(MOTOR_LEFT_ID, JOYSTICK_ID)
62if joystick isNone:
63print("Joystick data could not be read. Check the connection.")
64 time.sleep(0.1)
65continue6667 x_axis, y_axis, button_pressed = joystick[0], joystick[1], joystick[2]
6869# Ignore small movements (Dead Zone)70ifabs(x_axis) < DEAD_ZONE:
71 x_axis = 072ifabs(y_axis) < DEAD_ZONE:
73 y_axis = 07475# Determine movement direction (Only 4 Directions)76 movement = "Stopped"77 left_motor_speed = 078 right_motor_speed = 07980if y_axis > 0: # Forward81 movement = "Moving Forward"82 left_motor_speed = -10083 right_motor_speed = 10084elif y_axis < 0: # Backward85 movement = "Moving Backward"86 left_motor_speed = 10087 right_motor_speed = -10088elif x_axis > -20: # Right Turn89 movement = "Turning Right"90 left_motor_speed = -10091 right_motor_speed = -10092elif x_axis < -20: # Left Turn93 movement = "Turning Left"94 left_motor_speed = 10095 right_motor_speed = 1009697# Send PWM values to the motors98 master.set_duty_cycle(MOTOR_LEFT_ID, left_motor_speed)
99 master.set_duty_cycle(MOTOR_RIGHT_ID, right_motor_speed)
100101# Print only if the state has changed102 current_state = (movement, x_axis, y_axis, left_motor_speed, right_motor_speed)
103if current_state != previous_state:
104print(f"{movement} | X: {x_axis}, Y: {y_axis} | Left Motor: {left_motor_speed}, Right Motor: {right_motor_speed}")
105 previous_state = current_state # Update the last printed state106107# Stop motors if the joystick button is pressed108if button_pressed:
109 master.set_duty_cycle(MOTOR_LEFT_ID, 0)
110 master.set_duty_cycle(MOTOR_RIGHT_ID, 0)
111print("Joystick button pressed, motors stopped.")
112break113114 time.sleep(0.05)
115116# Start Motor Control117control_motors()
Teleoperation plays a critical role in modern robotics, enabling remote, real-time control of robotic systems in various industries. By integrating Acrome SMD motor controllers with mobile applications and keyboard-based teleoperation, users can achieve flexible and precise robotic motion control.
As robotics continues to advance, emerging technologies such as AI-powered automation, real-time video streaming, and cloud robotics will further enhance teleoperation capabilities. Acrome SMD-powered robots provide a reliable, scalable, and intelligent solution for industrial and research applications, paving the way for the next generation of remote-controlled robotic systems.
Oops! Something went wrong while submitting the form.
Discover Acrome
Acrome was founded in 2013. Our name stands for ACcessible RObotics MEchatronics. Acrome is a worldwide provider of robotic experience with software & hardware for academia, research and industry.