-
Notifications
You must be signed in to change notification settings - Fork 428
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Two motors move at the same time #563
Comments
Hi @Alberto-D If you use the Broadcast ID Please see below eManual for more details. Thanks! |
I assing different ID to each motor with dxl_comm_result = packetHandler->write1ByteTxRx( I have commented // if (dxl_comm_result != COMM_SUCCESS) { But when i try to sent messages with rostopic pub -1 /set_position dynamixel_sdk_examples/SetPosition "{id: 1, position: 100}" |
@Alberto-D // Copyright 2020 ROBOTIS CO., LTD.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
/*******************************************************************************
* This example is written for DYNAMIXEL X(excluding XL-320) and MX(2.0) series with U2D2.
* For other series, please refer to the product eManual and modify the Control Table addresses and other definitions.
* To test this example, please follow the commands below.
*
* Open terminal #1
* $ roscore
*
* Open terminal #2
* $ rosrun dynamixel_sdk_examples read_write_node
*
* Open terminal #3 (run one of below commands at a time)
* $ rostopic pub -1 /set_position dynamixel_sdk_examples/SetPosition "{id: 1, position: 0}"
* $ rostopic pub -1 /set_position dynamixel_sdk_examples/SetPosition "{id: 1, position: 1000}"
* $ rosservice call /get_position "id: 1"
* $ rostopic pub -1 /set_position dynamixel_sdk_examples/SetPosition "{id: 2, position: 0}"
* $ rostopic pub -1 /set_position dynamixel_sdk_examples/SetPosition "{id: 2, position: 1000}"
* $ rosservice call /get_position "id: 2"
*
* Author: Zerom
*******************************************************************************/
#include <ros/ros.h>
#include "std_msgs/String.h"
#include "dynamixel_sdk_examples/GetPosition.h"
#include "dynamixel_sdk_examples/SetPosition.h"
#include "dynamixel_sdk/dynamixel_sdk.h"
using namespace dynamixel;
// Control table address
#define ADDR_TORQUE_ENABLE 24
#define ADDR_GOAL_POSITION 30
#define ADDR_PRESENT_POSITION 36
// Protocol version
#define PROTOCOL_VERSION 1.0 // Default Protocol version of DYNAMIXEL X series.
// Default setting
#define DXL1_ID 1 // DXL1 ID
#define DXL2_ID 2 // DXL2 ID
#define BAUDRATE 57600 // Default Baudrate of DYNAMIXEL X series
#define DEVICE_NAME "/dev/ttyUSB0" // [Linux] To find assigned port, use "$ ls /dev/ttyUSB*" command
PortHandler * portHandler;
PacketHandler * packetHandler;
bool getPresentPositionCallback(
dynamixel_sdk_examples::GetPosition::Request & req,
dynamixel_sdk_examples::GetPosition::Response & res)
{
uint8_t dxl_error = 0;
int dxl_comm_result = COMM_TX_FAIL;
// Position Value of X series is 4 byte data. For AX & MX(1.0) use 2 byte data(int16_t) for the Position Value.
int16_t position = 0;
// Read Present Position (length : 4 bytes) and Convert uint32 -> int32
// When reading 2 byte data from AX / MX(1.0), use read2ByteTxRx() instead.
dxl_comm_result = packetHandler->read2ByteTxRx(
portHandler, (uint8_t)req.id, ADDR_PRESENT_POSITION, (uint16_t *)&position, &dxl_error);
if (dxl_comm_result == COMM_SUCCESS) {
ROS_INFO("getPosition : [ID:%d] -> [POSITION:%d]", req.id, position);
res.position = position;
return true;
} else {
ROS_INFO("Failed to get position! Result: %d", dxl_comm_result);
return false;
}
}
void setPositionCallback(const dynamixel_sdk_examples::SetPosition::ConstPtr & msg)
{
uint8_t dxl_error = 0;
int dxl_comm_result = COMM_TX_FAIL;
// Position Value of X series is 4 byte data. For AX & MX(1.0) use 2 byte data(uint16_t) for the Position Value.
uint16_t position = (unsigned int)msg->position; // Convert int32 -> uint32
// Write Goal Position (length : 4 bytes)
// When writing 2 byte data to AX / MX(1.0), use write2ByteTxRx() instead.
dxl_comm_result = packetHandler->write2ByteTxRx(
portHandler, (uint8_t)msg->id, ADDR_GOAL_POSITION, position, &dxl_error);
if (dxl_comm_result == COMM_SUCCESS) {
ROS_INFO("setPosition : [ID:%d] [POSITION:%d]", msg->id, msg->position);
} else {
ROS_ERROR("Failed to set position! Result: %d", dxl_comm_result);
}
}
int main(int argc, char ** argv)
{
uint8_t dxl_error = 0;
int dxl_comm_result = COMM_TX_FAIL;
portHandler = PortHandler::getPortHandler(DEVICE_NAME);
packetHandler = PacketHandler::getPacketHandler(PROTOCOL_VERSION);
if (!portHandler->openPort()) {
ROS_ERROR("Failed to open the port!");
return -1;
}
if (!portHandler->setBaudRate(BAUDRATE)) {
ROS_ERROR("Failed to set the baudrate!");
return -1;
}
dxl_comm_result = packetHandler->write1ByteTxRx(
portHandler, DXL1_ID, ADDR_TORQUE_ENABLE, 1, &dxl_error);
if (dxl_comm_result != COMM_SUCCESS) {
ROS_ERROR("Failed to enable torque for Dynamixel ID %d", DXL1_ID);
return -1;
}
dxl_comm_result = packetHandler->write1ByteTxRx(
portHandler, DXL2_ID, ADDR_TORQUE_ENABLE, 1, &dxl_error);
if (dxl_comm_result != COMM_SUCCESS) {
ROS_ERROR("Failed to enable torque for Dynamixel ID %d", DXL2_ID);
return -1;
}
ros::init(argc, argv, "read_write_node");
ros::NodeHandle nh;
ros::ServiceServer get_position_srv = nh.advertiseService("/get_position", getPresentPositionCallback);
ros::Subscriber set_position_sub = nh.subscribe("/set_position", 10, setPositionCallback);
ros::spin();
portHandler->closePort();
return 0;
} |
Yes, I changer the protocol to 1.0, right now one motor is connected to the other, and one motor to the U2D2, here is my code, // Copyright 2020 ROBOTIS CO., LTD. /*******************************************************************************
#include <ros/ros.h> #include "std_msgs/String.h" using namespace dynamixel; //For AX-18 // Protocol version // Default setting // //For XL-320 // // Protocol version // // Default setting #define DEVICE_NAME "/dev/ttyUSB0" // [Linux] To find assigned port, use "$ ls /dev/ttyUSB*" command PortHandler * portHandler; bool getPresentPositionCallback( // Position Value of X series is 4 byte data. For AX & MX(1.0) use 2 byte data(int16_t) for the Position Value. // Read Present Position (length : 4 bytes) and Convert uint32 -> int32 void setPositionCallback(const dynamixel_sdk_examples::SetPosition::ConstPtr & msg) // Position Value of X series is 4 byte data. For AX & MX(1.0) use 2 byte data(uint16_t) for the Position Value. // Write Goal Position (length : 4 bytes) int main(int argc, char ** argv) portHandler = PortHandler::getPortHandler(DEVICE_NAME); if (!portHandler->openPort()) { if (!portHandler->setBaudRate(BAUDRATE)) { dxl_comm_result = packetHandler->write1ByteTxRx( dxl_comm_resultt = packetHandler->write1ByteTxRx( ros::init(argc, argv, "read_write_node"); portHandler->closePort(); |
@Alberto-D |
Yes, i get the error [ERROR] [1653382767.128744369]: Failed to enable torque for Dynamixel ID 1 when launching if i just copy your code, i guess it is because the error code for the AX series is not the same as for the dlx. If I comment When i try to use other baud-rates, the effects vary Does the baud-rate affect the number of motor i can use? when i use 500000 or 400000 the motors dont move at all. |
Oh, you should modify the ID and baudrate for your AX settings. Although AX series support various baudrates, I'd recommend to use baudrates that are widely used such as 57600, 115200, 1Mbps. Thanks! |
This is my code rigth now: /*******************************************************************************
#include <ros/ros.h> #include "std_msgs/String.h" using namespace dynamixel; //For AX-18 // Protocol version // Default setting #define DEVICE_NAME "/dev/ttyUSB0" // [Linux] To find assigned port, use "$ ls /dev/ttyUSB*" command PortHandler * portHandler; bool getPresentPositionCallback( // Position Value of X series is 4 byte data. For AX & MX(1.0) use 2 byte data(int16_t) for the Position Value. // Read Present Position (length : 4 bytes) and Convert uint32 -> int32 void setPositionCallback(const dynamixel_sdk_examples::SetPosition::ConstPtr & msg) // Position Value of X series is 4 byte data. For AX & MX(1.0) use 2 byte data(uint16_t) for the Position Value. // Write Goal Position (length : 4 bytes) int main(int argc, char ** argv) portHandler = PortHandler::getPortHandler(DEVICE_NAME); if (!portHandler->openPort()) { if (!portHandler->setBaudRate(BAUDRATE)) { dxl_comm_result = packetHandler->write1ByteTxRx( dxl_comm_resultt = packetHandler->write1ByteTxRx( ros::init(argc, argv, "read_write_node"); portHandler->closePort(); It works with the first motor, if i send rostopic pub -1 /set_position dynamixel_sdk_examples/SetPosition "{id: 1, position: 0}", only the first motor moves, but if i use id:2 i get an error, on the other hand if i use id:254 both motors move at the same time, so i know the motor itself works, but i can control it individually, Any idea of what cloud be wrong? |
@Alberto-D |
Closing this thread as there isn't recent activity. Please feel free to reopen when necessary. |
ISSUE TEMPLATE ver. 1.2.0
Please fill this template for more accurate and prompt support.
Which DYNAMIXEL SDK version do you use?
DynamixelSDK 3.7.40, downloaded from the noetic-devel branch in Github
Which programming language/tool do you use?
ROS Noetic witch c++
Which operating system do you use?
Ubuntu 20.04
Which USB serial converter do you use?
U2D2 from the DYNAMIXEL Starter Set [INT]
Which DYNAMIXEL do you use?
AX-18A
Have you searched the issue from the closed issue threads?
Yes, but i did not found an answer
Please describe the issue in detail
When trying to move two motors using the example code ( https://www.youtube.com/watch?v=SpdxjsCO9sE ) both of them move at the same time, when i connect only one it works fine ( i have to comment the conexion to the second motor to use only one) , but if i connect two (either connecting one motor to the U2D2 and the other motor to the first one, or connecting both motors directly to the U2D2) i get an error: [ERROR] [1652884359.772566946]: Failed to enable torque for Dynamixel ID 1
I guessed this happend because the error codes for the XL430-W250 (motor used in the example) and the AX-18A are different, so i commented:
if (dxl_comm_resultt != COMM_SUCCESS) {
ROS_ERROR("Failed to enable torque for Dynamixel ID %d", DXL2_ID);
return -1;
}
to see if it worked, and i did, but both motors appear to have the same id (1) and so they move at the same time.
I tried to use rosrun dynamixel_workbench_controllers find_dynamixel /dev/ttyUSB0 but it only detects one motor, and only if only one is connected, if i connect both of them, it doesn't detect anything.
Is there a way to control them individually?
The text was updated successfully, but these errors were encountered: