Hello software developers. I am new in programming and ROS. I am working now with servo motors and want to make the controlling node to rotate motor into some degrees like from 0 --> 90--> 180-->0 degrees. there is a main code and I would like to add def function into the main node:
#!/usr/bin/env python
import os
import rospy
from std_msgs.msg import String
from controller_motor.msg import Motor
from controller_motor.srv import Motor2
if os.name == 'nt':
import msvcrt
def getch():
return msvcrt.getch().decode()
else:
import sys, tty, termios
fd = sys.stdin.fileno()
old_settings = termios.tcgetattr(fd)
def getch():
try:
tty.setraw(sys.stdin.fileno())
ch = sys.stdin.read(1)
finally:
termios.tcsetattr(fd, termios.TCSADRAIN, old_settings)
return ch
from dynamixel_sdk import * # Uses Dynamixel SDK library
class DynamixelController(object):
def __init__(self):
#print("1")
self.motor_sub = rospy.Subscriber("/motor_topic", Motor, self.motor_callback)
self.test_motor_client(1) #here we can put request order as 1 for the using id=14 and position= 1500; or as 2 is id same and position is 2500. The cases could be found in the server.py node
def motor_callback(self, data):
_id = data.id
_position = data.position
print("_id : {0}, _position : {1}".format(_id, _position))
self.read_write(_id, _position)
def test_motor_client(self, request):
print("2")
rospy.wait_for_service('test_motor_service')
try:
proxy = rospy.ServiceProxy('test_motor_service', Motor2)
response = proxy(request)
print("response is id : {} position : {}".format(response.id, response.position))
self.read_write(response.id, response.position)
except rospy.ServiceException as e:
print("Service call failed: %s"%e)
def new_rotation(self, response):
print("3")
rospy.wait_for_service('test_mototr_rotation')
try:
proxy = rospy.ServiceProxy('test_motor_rotation', Motor2)
response = proxy(request)
self.read_write(response.id, response.position(arg[0]))
sleep(2)
self.read_write(response.id, response._position(arg[1]))
sleep(2)
self.read_write(response.id, response._position(arg[2]))
sleep(2)
except rospy.ServiceException as e:
print("Service call failed: %s"%e)
def read_write(self, _id, _position):
print("Start the node")
# Control table address
ADDR_PRO_TORQUE_ENABLE = 64 # Control table address is different in Dynamixel model
ADDR_PRO_GOAL_POSITION = 116
ADDR_PRO_PRESENT_POSITION = 132
# Protocol version
PROTOCOL_VERSION = 2.0 # See which protocol version is used in the Dynamixel
# Default setting
DXL_ID = _id # Dynamixel ID : 14
BAUDRATE = 1000000 # Dynamixel default baudrate : 1000000
DEVICENAME = '/dev/ttyUSB0' # Check which port is being used on your controller
# ex) Windows: "COM1" Linux: "/dev/ttyUSB0" Mac: "/dev/tty.usbserial-*"
TORQUE_ENABLE = 1 # Value for enabling the torque
TORQUE_DISABLE = 0 # Value for disabling the torque
DXL_MINIMUM_POSITION_VALUE = 10 # Dynamixel will rotate between this value
DXL_MAXIMUM_POSITION_VALUE = _position # The position here is already in the degree measurement; and this value (note that the Dynamixel would not move when the position value is out of movable range. Check e-manual about the range of the Dynamixel you use.)
DXL_MOVING_STATUS_THRESHOLD = 20 # Dynamixel moving status threshold
index = 0
dxl_goal_position = [DXL_MINIMUM_POSITION_VALUE, DXL_MAXIMUM_POSITION_VALUE] # Goal position
# Initialize PortHandler instance
# Set the port path
# Get methods and members of PortHandlerLinux or PortHandlerWindows
portHandler = PortHandler(DEVICENAME)
# Initialize PacketHandler instance
# Set the protocol version
# Get methods and members of Protocol1PacketHandler or Protocol2PacketHandler
packetHandler = PacketHandler(PROTOCOL_VERSION)
# Open port
if portHandler.openPort():
print("Succeeded to open the port")
else:
print("Failed to open the port")
print("Press any key to terminate...")
getch()
quit()
# Set port baudrate
if portHandler.setBaudRate(BAUDRATE):
print("Succeeded to change the baudrate")
else:
print("Failed to change the baudrate")
print("Press any key to terminate...")
getch()
quit()
# Enable Dynamixel Torque
dxl_comm_result, dxl_error = packetHandler.write1ByteTxRx(portHandler, DXL_ID, ADDR_PRO_TORQUE_ENABLE, TORQUE_ENABLE)
if dxl_comm_result != COMM_SUCCESS:
print("%s" % packetHandler.getTxRxResult(dxl_comm_result))
elif dxl_error != 0:
print("%s" % packetHandler.getRxPacketError(dxl_error))
else:
print("Dynamixel has been successfully connected")
while 1:
print("Press any key to continue! (or press ESC to quit!)")
if getch() == chr(0x1b):
break
# Write goal position
dxl_comm_result, dxl_error = packetHandler.write4ByteTxRx(portHandler, DXL_ID, ADDR_PRO_GOAL_POSITION, dxl_goal_position[index])
if dxl_comm_result != COMM_SUCCESS:
print("%s" % packetHandler.getTxRxResult(dxl_comm_result))
elif dxl_error != 0:
print("%s" % packetHandler.getRxPacketError(dxl_error))
while 1:
# Read present position
dxl_present_position, dxl_comm_result, dxl_error = packetHandler.read4ByteTxRx(portHandler, DXL_ID, ADDR_PRO_PRESENT_POSITION)
if dxl_comm_result != COMM_SUCCESS:
print("%s" % packetHandler.getTxRxResult(dxl_comm_result))
elif dxl_error != 0:
print("%s" % packetHandler.getRxPacketError(dxl_error))
print("[ID:%03d] GoalPos:%03d PresPos:%03d" % (DXL_ID, dxl_goal_position[index], dxl_present_position))
if not abs(dxl_goal_position[index] - dxl_present_position) > DXL_MOVING_STATUS_THRESHOLD:
break
# Change goal position
if index == 0:
index = 1
else:
index = 0
# Disable Dynamixel Torque
dxl_comm_result, dxl_error = packetHandler.write1ByteTxRx(portHandler, DXL_ID, ADDR_PRO_TORQUE_ENABLE, TORQUE_DISABLE)
if dxl_comm_result != COMM_SUCCESS:
print("%s" % packetHandler.getTxRxResult(dxl_comm_result))
elif dxl_error != 0:
print("%s" % packetHandler.getRxPacketError(dxl_error))
# Close port
portHandler.closePort()
if __name__ == '__main__':
rospy.init_node('read_write', anonymous=True)
controller = DynamixelController()
and here is the server node:
#!/usr/bin/env python
import rospy
from controller_motor.srv import Motor2, Motor2Response
def motor_info(req):
print("receive the request : {}".format(req.order))
if req.order == 1:
_id = 14
#_position = 1500
_positiondegree = 180 # change it degree value
_position = (11.4 * (_positiondegree)) # here is using there 11.4 the number which helps rotate the motor in the correct degree; We get the number encoder number/degree we want to rotate the motor.
elif req.order == 2:
_id = 14
#_position = 2047.5
_positiondegree = 180
_position = (11.4 * (_positiondegree))
print("Response to this request id : {} and postiion : {}".format(_id, _position))
return Motor2Response(_id, _position)
def motor_info_server():
rospy.init_node('test_motor_service')
s = rospy.Service('test_motor_service', Motor2, motor_info)
print("Ready to response some id and position")
# spin() simply keeps python from exiting until this node is stopped
rospy.spin()
if __name__ == '__main__':
motor_info_server()
Now when running the motor it rotates to the degree I would like it to rotate. And now I would like to know how could I give some degrees to make motor rotates from 0 to some other degrees and go back to the 0 degree position again.
I guess there might be applied the list and args for some degrees. But I am not well-known how I could do this :) I would like to get some advice from professionals like you ,guys :)
I know my question could be obvious for professionals. I would like to get experience in the programming and ROS as much as I can :)
I will be so thankful for any help and advise how I could do this :)
Thank to everyone who will share his/her idea:)
I wish you have a good day :)