You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
I am writing an implementation to make the motor run in PP pattern. I have followed the instruction from the servo motor's manual provided by the manufacturer. I send rpdos to set the control word and see the response in candump, mostly status word and target position. Here is the python code for the same:
import canopen
import logging
import time
# logging.basicConfig(level=logging.DEBUG)
network = canopen.Network()
network.connect(bustype='socketcan', channel='can0', bitrate=250000)
# Add some nodes with corresponding Object Dictionaries
node = canopen.BaseNode402(1, '~/zeroerr_zervos/eRobEDS.eds')
network.add_node(node)
# Reset network
node.nmt.state = 'RESET COMMUNICATION'
print('node state 0) = {0}'.format(node.nmt.state))
node.nmt.wait_for_bootup(15)
timeout = time.time() + 10
node.nmt.state = 'PRE-OPERATIONAL'
while node.nmt.state != 'PRE-OPERATIONAL':
if time.time() > timeout:
raise Exception('Timeout when trying to change state')
time.sleep(0.1)
print('node state 1) = {0}'.format(node.nmt.state))
#node initialization
print('node nmt state = {0}'.format(node.nmt.state))
#Set the profile position mode
node.sdo[0x6060].raw = 1
#Check operating mode to PP pattern
assert node.sdo[0x6061].raw ==1
# print("3. node in PP mode")
#Set the profile velocity to 5566 plus/s
node.sdo[0x6081].raw = 11132
#Set profile acceleration to 5566 plus/s²
node.sdo[0x6083].raw = 5566
#Set profile deceleration to 5566 plus/s²
node.sdo[0x6084].raw = 5566
# print('4. PV, PA, PD set to 5566')
#Disable sync
node.sdo[0x1005].raw = 128
assert node.sdo[0x1005].raw == 0x80
# network.sync.stop()
# print('5. sync disabled')
#Set communication cycle period (1000us)
node.sdo[0x1006].raw = 1000
assert node.sdo[0x1006].raw == 1000
# print('6. comms cycle period set to 1000us')
# node.nmt.state = 'OPERATIONAL
print('node nmt state before pdo mapping = {0}'.format(node.nmt.state))
#The TxPDO1 configuration process
node.tpdo_values[0x6041] = node.sdo[0x6041].raw #this is done only for the SW to be mapped to the tpdo otherwise theres a warning
node.tpdo[1].read()
node.tpdo[1].cob_id = 0x181
node.tpdo[1].enabled = False
node.tpdo[1].trans_type = 1 # Asynchronous
node.tpdo[1].clear() # Clear existing mapping
node.tpdo[1].add_variable('Status word') # Status word
node.tpdo[1].add_variable('Modes of operation')
node.tpdo[1].add_variable('Modes of operation display')
node.tpdo[1].add_variable('Actual position value') # Actual position
node.tpdo[1].enabled = True
node.tpdo[1].save()
#RPDO mapping configuration process
node.rpdo[1].read()
node.rpdo[1].cob_id = 0x201
node.rpdo[1].enabled = False
node.rpdo[1].trans_type = 1 # Asynchronous
node.rpdo[1].clear() # Clear existing mapping
node.rpdo[1].add_variable('Control word') # Control word
node.rpdo[1].add_variable('Target position') # Target position
node.rpdo[1].enabled = True
node.rpdo[1].save()
#Start the node
#NMT start remote node
print('node state = {0}'.format(node.nmt.state))
#Get the actual position
actual_position = node.sdo[0x6064].raw
print(f'actual_position: {actual_position}')
#Get the target position
target_position = node.sdo[0x607A].raw
print(f'target_position: {target_position}')
node.load_configuration()
node.setup_402_state_machine()
#Send sync frame
network.sync.start(0.1)
node.nmt.state = 'OPERATIONAL'
print(f'Control word 6 {node.state}')
node.rpdo[1]['Control word'].raw = 0x06
node.rpdo[1]['Target position'].raw =0
node.rpdo[1].transmit()
time.sleep(2)
print(f'Control word 7 {node.state}')
node.rpdo[1]['Control word'].raw = 0x07
node.rpdo[1]['Target position'].raw =0
node.rpdo[1].transmit()
time.sleep(2)
print(f'Control word F {node.state}')
node.rpdo[1]['Control word'].raw = 0x0F
node.rpdo[1]['Target position'].raw =0
node.rpdo[1].transmit()
time.sleep(2)
print(f'Control word 1F {node.state}')
node.rpdo[1]['Control word'].raw = 0x1F
node.rpdo[1]['Target position'].raw = 30000
node.rpdo[1].transmit()
time.sleep(2)
#Get the actual position
actual_position = node.sdo[0x6064].raw
print(f'actual_position after 1F: {actual_position}')
#Get the target position
target_position = node.sdo[0x607A].raw
print(f'target_position after 1F: {target_position}')
print(f'Error code: {node.sdo[0x603F].raw}')
node.nmt.stop_node_guarding()
network.sync.stop()
network.disconnect()
exit()
Following to this code, I monitor the candump msgs which go like: candump_can0.txt
As I understand, the candump msgs, after the control word goes can0 201 [6] 1F 00 10 27 00 00
the response from the motor as the status word is
Sorry this is only for bugs and not for support on how to use the library. But here are some hints:
You are receiving something, how do you know this is the position? It is very hard to read candumps. Does your script print the correct positions, if you request them by sdo? Also normally you need to set some device specific parameters (configuration) via sdo before you can use the device.
You have some possible errors in your code: You should be in PRE-OPERATIONAL Mode if you set the PDOs, maybe your device accepts PDOs in OPERATIONAL, but by the canopen standard you can only write PDOs in PRE-OPERATIONAL. Also the save() and read() commands are not on the subitem, but on the tpdo and rpdo maps directly.
Hi guys,
I am writing an implementation to make the motor run in PP pattern. I have followed the instruction from the servo motor's manual provided by the manufacturer. I send rpdos to set the control word and see the response in candump, mostly status word and target position. Here is the python code for the same:
Following to this code, I monitor the candump msgs which go like:
candump_can0.txt
As I understand, the candump msgs, after the control word goes
can0 201 [6] 1F 00 10 27 00 00
the response from the motor as the status word is
which i understand to mean that the motor is moving. But physically the motor doesnt move.
What am I missing or doing anything wrong?
I know it looks too bit of a code but it is quite basic.
Thanks
The text was updated successfully, but these errors were encountered: