问:
Choosing correct power supply for Stepper Motors
I am building a machine and need 2 Stepper Motor for that.
The motors are driven using by a 3.3v arm device.

I have made the following selections regarding the stepper motor, stepper motor driver and the power supply.

Power Supply 12 Volt Power Supply - 3.5 Amp Single Output

Stepper Motors Stepper Motor: Unipolar/Bipolar, 200 Steps/Rev, 42×48mm, 4V, 1.2 A/Phase

Stepper Motor Driver DRV8825 Stepper Motor Driver Carrier, High Current

I tried my best to research the compatibility and came up with these.

Is this a good selection considering the fact that the Power Supply will be driving 2 of these motors.

I will be running the motors at 1/16 step for high resolution.As far as the speed is concerned,it's going to be pretty slow but they will be running continuously for hours in end.Basically what I am trying to do here is make a V-Plotter.As far I can tell, there will be loads of start stop motion in the motors though.

答:
As long as the steppers are running relatively slowly, let's say a few hundred steps per second, you should be fine.

Your driver uses PWM to control the current through the motor windings.  In microstepping mode the driving waveform at the motor terminals looks like a sine and cosine (sines offset by 90 degrees) and the driver modulates the outputs to maintain the current to the windings.

The 1.2A appears to be peak current.  So at standstill we're talking 1.2A*4V = 4.8W max per phase (though a microstepping driver will never drive those two phases "fully" simultaneously).  At any rate, at very slow speeds/standing we're talking about ~13W for the two motors vs. your 40W power supply.  So no problem.

As you start speeding things up two things happen:

The motors starts acting as a generator producing counter-EMF (and we don't know the Ke constant for those motors).  Now to maintain the same current your driver has to overcome this counter-EMF.  This is why you want the highest voltage you can get if you're planning to run your motors at speed.

We are going through the microstepping waveform and really start caring more about the RMS current (So we can effectively divide by ~1.4 since the power supply doesn't care about peak current as much over very short durations).  So about 0.86A RMS per phase.  That adds up to ~3.42A which is still lower (though not by much, than your 3.5A supply).

So as long as you're well below a speed where your back-EMF is ~8V you're fine.  If you plan to go to this point or above it you'll run out of voltage and you're also left with relatively small margins on power.  It also depends on how much power you need for the rest of your system.  Unfortunately I'm not quite sure how to calculate the back-EMF constant (Ke) from your motor parameters.  Looking at the pulling torque curve (given with a 24V supply) I would guess that up to 1000-2000pps you'll still be OK and it looks like the torque is dropping by ~25% over ~1500pps so it's probably in the range of 6V/1500pps (very rough guess).  Since we know the inductance maybe someone can show us how to calculate back-EMF constant (I'd be interested in learning)...


问:
How to formulate the equation and environment equations for motion planning algorithm use?
How to formulate the equation and environment equations for motion planning algorithm use?

And if know the desired state, how to use motion planning to fill the data to reach this desired state?

答:
I will assume that we have a robot arm in a work cell and we want to plan a pick and place motion while avoiding some static obstacles in the work cell.

I understand that having equations is a very essential way of modeling the robot and its environment. However, for such a complex system some higher-level ways of representation are available. For example, the unified robot description format (URDF) that allows us to present the models of the robot and its environment from their CAD models. Those models can be used for the visualization as well as the planning tasks. If you are into modeling robots, you might have already heard of Denavit-Hartenberg (DH) parameters. Consider URDF a new way for the same purpose with more capabilities. This is a very general view of modeling. This is an awesome topic, the following image is an application of what I said. I made it while working on ROS-Industrial developers' training.

Before going to the planning part, let's make sure that we know what are forward and inverse kinematics. Forward kinematics means we give the robot motor joint values and want to know where the last link of the robot is. This is a relatively easy task for robot arms. On the other hand, inverse kinematics is the question about which motor joints will bring the robot to where I want it to be (the desired state in your words). This is not an easy task especially when the arm degrees of freedom (DOF) increase. Usually, industrial arms have 6-DOF (6 motors). It is hard to solve because we need to solve sets of non-linear equations. This is why numerical methods are used to obtain the solution.

Then, the planning part. If we know the start and the end poses of the robot to make a pick and place task, how can we know the path between them (sequence of key robot poses and their corresponding joints)? Here comes the need for motion planning algorithms. We need them because we will search for solutions in a high dimensional space 6D for 6DOF robot.

Let's assume we will use the famous rapidly-exploring random tree (RRT) famous planning algorithm. The algorithm will try to connect the start to the end through random sampling. Every sample, in this case, can be a robot pose. While the samples are generated, we can use them to check for things like if there is a collision with the static obstacles in the environment. If samples are satisfactory, they are connected in a path from the start to the end. If not satisfactory (collision is detected, for example) the current sample is discarded and a new satisfactory one is searched for till we reach the end. The result is a path of feasible robot sequences that can get our task done. To learn how to do this using open source software, I do recommend going through the tutorials of ROS-Industrial. It will teach you how to use ROS and MoveIt to accomplish your goal. MoveIt is a package made for making motion planning accessible to us. The following is an example of motion planning for an arm robot with obstacle avoidance.

I wish you got an idea about some of the concepts needed to answer your questions as well as the tools that help to implement them. Please keep asking.

ContentLicense: CC BY-SA 4.0


问:
How to understand the angular velocity of link i+1?
My question is a basic one about velocity propagation from link to link, that is how to understand the following equation.

$
{^i\omega_{i+1}} = {^i\omega_{i}} + {_{i+1}^{\;\;\;i}{R}} \cdot {\dot{\theta}_{i+1}} \cdot {^{i+1}\hat{Z}_{i+1}}
$

The interpretation of this equation from Introduction to Robotics by John J. Craig is:

The angular velocity of link i+1 is the same as that of link i plus a new component caused by rotational velocity at joint i+1. This can be written in terms of frame {i}

Take the following figure as an example, I assume this equation is trying to compute the angular velocity of Link 2 with respect to the frame {1}. i.e., $^1\omega_2$

What bewilders me most is I don't think every point on Link 2 share the same angular velocity with respect to joint 1, because the axis of rotation is not joint 1. Then how come $^1\omega_2$ be computed?

Can anyone please help me out?

答:
What bewilders me most is I don't think every point on Link 2 share the same angular velocity with respect to joint 1, because the axis of rotation is not joint 1. Then how come $^1\omega_2$ be computed?

Every point (more specifically, every frame) on a rigid body does indeed share the same rotational velocity, and the rigid body can thus be said to have a rotational velocity.

To see this, it is helpful to remember that the rotational velocity of a frame is the rate of change of the angle between a line drawn in that frame and a fixed reference line. For a rigid body, the angle between any two lines drawn on the body is constant, and so all frames must have the same rotational velocity.

More abstractly, when thinking about the rotational velocity, it is the axis vector that matters, not the center of rotation. The center of rotation (and its generalization to three dimensions) matters when calculating the difference in the translational velocities of two frames on a rotating rigid body.


问:
On the covariance matrix of the EKF SLAM
In the covariance matrix of the EKF SLAM, there are components that specifies the correlation between landmarks. Are those values important? Because while we bulding map of landmarks, we only draw the ellipse around each landmark (which correspond to the covariance of that landmark). I'm quite new to SLAM so any correction and help would be great. Thank you.</p>

答:
Drawing the error ellipses is more a tool for you the human to see how the system is working. It is a proportional representation of the error, not an exact value. So it is OK to ignore the cross correlation.

The cross covariances are important for the EKF to work correctly. That is why we still keep them in the Filter and propogate/update them accordingly. But you don't have to care about them when drawing the error ellipse.


问:
Telemetry with Ardupilot 2.6
I'm using the telemetry kit from 3DR robotics (433MHz) to interface with Ardupilot Mega 2.6, controlling a quadcopter. The Mission Planner (v1.2.84) by Michael Oborne works well with the telemetry kit, transmitting flight data (IMU, compass, GPS etc.) from the quadcopter to the GCS and displaying them in their GUI.

However, I would like to see the same data in the hyperterminal (windows system). The radio receiver on the GCS connects to my PC through a USB drive. I have tried calling the remote radio station using all possible Baud rates, starting from 110 to 921600 (including 57600). I've set the data bits to 8 and stop bits to 1. 'None' for parity and flow control.

However, all that I ever get on my terminal is either gibberish or no data at all. I also tried burning this software to the radio receiver and tried using AT commands on the radio.

It connects OK with '+++', but keeps returning error for AT1, ATT etc.

Please give me an idea about how to get flight data at the hyperterminal.

Thanks.

答:
From what I understand, this telemetry kit uses Mavlink as a protocol for data transfer and unless I follow the specific header, footer, data etc format for Mavlink, I will invariably end up with gibberish on my hyperterminal. This means in order to read and modify the telemetry data, I'd have to develop a Mavlink engine from scratch, right?

I would like to know if this problem can be cut short by using XBee radio Tx-Rx pair instead of the one 3DR is providing?

ContentLicense: CC BY-SA 3.0

Title: Telemetry with Ardupilot 2.6


问:
Difference between rosservice and rossrv [the info version at least]
What's the difference? I see my service in rossrv list but not with rosservice list.

From ROS wiki

• rossrv: displays information about .srv data structures.

• rosservice: lists and queries ROS Services

There's an abridged tree structure of the files below this text for clarity.

I have catkin_ws/src/simple_arm/srv/GoToPosition.srv that I see when I run

```<code>$ rossrv list
...
simple_arm/GoToPosition
...
</code>```

However, my request handler is in catkin_ws/src/simple_arm/src/arm_mover.cpp and I only see it in rosservice list as

```<code>$ rosservice list
...
/arm_mover/safe_move
...
</code>```

Why can't I see /arm_mover/safe_move under rossrv list if it is a service? And the inverse with simple_arm/GoToPosition?

```<code>$ tree
.
├── build
│   │   ├── setup.bash
│   ├── catkin_generated
│   ├── first_package
│   ├── simple_arm
│          ├── arm_mover.dir
├── devel
│   ├── include
│   │   └── simple_arm
│   │       ├── GoToPosition.h
│   │       ├── GoToPositionRequest.h
│   │       └── GoToPositionResponse.h
│   ├── lib
│   │   └── simple_arm
│   │       ├── arm_mover
│   │       └── simple_mover
└── src
    ├── CMakeLists.txt -> /opt/ros/melodic/share/catkin/cmake/toplevel.cmake
    ├── first_package
    │   ├── CMakeLists.txt
    │   └── package.xml
    └── simple_arm
        ├── CMakeLists.txt
        ├── config
        │   └── controllers.yaml
        ├── images
        │   └── simulation.png
        ├── launch
        │   ├── robot_control.xml
        │   ├── robot_description.xml
        │   └── robot_spawn.launch
        ├── LICENSE
        ├── meshes
        │   └── camera.dae
        ├── package.xml
        ├── README.md
        ├── src
        │   ├── arm_mover.cpp
        │   └── simple_mover.cpp
        ├── srv
        │   └── GoToPosition.srv
        ├── urdf
        │   ├── simple_arm.gazebo.xacro
        │   └── simple_arm.urdf.xacro
        └── worlds
            └── willow_garage.world
</code>```

答:
The difference is that rossrv is a tool for inspecting service types  (i.e. .srv files), while rosservice provides access to running services. So for example, when you call rossrv list it will show what service types are known in the current workspace, while rosservice list shows the names of the services currently running.

In your case, the service type is simple_arm/GoToPosition and the running service name is /arm_mover/safe_move, so logically the former shows up in rossrv list and the latter in rosservice list.

Another way to explain the difference between both tools is to think of rossrv as the service equivalent of rosmsg, and of rosservice as the service equivalent of rostopic. Just like rosmsg is concerned with message types and rostopic with topics to / from which messages are published / subscribed, so does rossrv is concerned with service types and rosservice with endpoints from which services can be called.


问:
Camera Pose Estimation
What is the minimum number of point correspondences required for camera pose estimation given the perspective projections of points with known world coordinates?</p>

答:
The problem is called perspective-n-point. And has the answer in the Wikipedia article.

6 unknowns. 3 for rotation and 3 for translation.

Each perspective measurement provides 2 points of information. (x,y) in pixels.

$\frac{6}{2}$ is 3.

Title: Camera Pose Estimation


问:
What is a low level controller for a quadrotor?
I am studying control systems, and I was reading a paper about quadrotors. In the paper it is said that in the platform of the robot it has to be present a low level controller.

But what is a low level controller?

I have tried to search online, but i have not really understood, since I think its definition depends also on the context in which it is used, so I posted the question here in Robotics stack exchange.

In the paper it is also said that the low level controller is prefereable to be open source, so to have the possibility to add capabilities.

So, what is the difference between a low level controller and a high level controller for a quadrotor?

答:
Controllers, be it for quadrotors or industrial manipulators or any electromechanical system for that matter, are implemented as hierarchies. Controllers that directly drive the hardware are low-level controllers whereas those that implement logical decision-making are high-level controllers. The terms "high" and "low" are relative. Nested controllers ensure abstraction and code modularity.

In the context of a quadrotor, the controller for the motor driver(s) that actually makes the rotors spin would be a low-level controller, whereas another controller that tells the quadrotor to move forward/backward etc. could be a high-level controller. The low-level controller has abstracted away all the details on how exactly to drive the rotors. All the high-level controller does is instruct the low-level controllers that a particular action is desired. It's now the low-level controllers' job to actually spin the rotors in such a way that the quadrotor executes the desired action.

"in the platform of the robot it has to be present a low level
  controller"

Think of making your quadrotor execute actions like ascend(desired_height) or translate_forward(distance). Great, you've called those functions and have passed the arguments. What then? If the control architecture is implemented as a hierarchy, then these functions would call low-level controllers to actuate the rotors:

```<code># high-level controller
ascend(desired_height)
{
    drive_motors(desired_height, 'up')
}

# another high-level controller
translate_forward(distance)
{
    drive_motors(distance, 'forward')
}

# low-level controller
drive_motors(distanceToTarget, direction_to_move_in)
{
    # code that actually drives the motors
}
</code>```

Note that the low-level controller can again call another lower-level controller which is even closer to the "metal". Likewise, the high level controllers can be called by an even higher level controller, for eg. go_above_obstacles() which utilizes ascend() and translate_forward(). High-level controllers thus are for high-level logic and are generally not concerned with the low-level mechatronic actuation.

Here's another answer that might be useful.

Body:
Controllers, be it for quadrotors or industrial manipulators or any electromechanical system for that matter, are implemented as hierarchies. Controllers that directly drive the hardware are low-level controllers whereas those that implement logical decision-making are high-level controllers. The terms "high" and "low" are relative. Nested controllers ensure abstraction and code modularity.

In the context of a quadrotor, the controller for the motor driver(s) that actually makes the rotors spin would be a low-level controller, whereas another controller that tells the quadrotor to move forward/backward etc. could be a high-level controller. The low-level controller has abstracted away all the details on how exactly to drive the rotors. All the high-level controller does is instruct the low-level controllers that a particular action is desired. It's now the low-level controllers' job to actually spin the rotors in such a way that the quadrotor executes the desired action.

"in the platform of the robot it has to be present a low level
  controller"

Think of making your quadrotor execute actions like ascend(desired_height) or translate_forward(distance). Great, you've called those functions and have passed the arguments. What then? If the control architecture is implemented as a hierarchy, then these functions would call low-level controllers to actuate the rotors:

# high-level controller
ascend(desired_height)
{
    drive_motors(desired_height, 'up')
}

# another high-level controller
translate_forward(distance)
{
    drive_motors(distance, 'forward')
}

# low-level controller
drive_motors(distanceToTarget, direction_to_move_in)
{
    # code that actually drives the motors
}

Note that the low-level controller can again call another lower-level controller which is even closer to the "metal". Likewise, the high level controllers can be called by an even higher level controller, for eg. go_above_obstacles() which utilizes ascend() and translate_forward(). High-level controllers thus are for high-level logic and are generally not concerned with the low-level mechatronic actuation.

Here's another answer that might be useful.


问:
Motion planning with Gaussian Process Regression
I was recently introduced to Gaussian Process Regression (GPR). I read multiple papers regarding use cases of GPR in robotics, however, they were more or less very limited.

Use case from the literature:

There is a robot arm with 5 joints.

The authors demonstrate an action such as avoiding an object. After several demonstrations, they build a GPR model.

Using this trained GPR model, they demonstrate that the robot arm can avoid an object in a similar situation.

Use case that I am wondering:

I would like to model the basic movements such as move your arm forward but in a certain manner. For example, I would like to train my GPR model so that it can learn the timing when and how long each joint has to move so that this arm can be moved forward in a certain manner that I demonstrated.

Challenges, in this case, would be that, for instance, the initial joint configuration changes, my trained GPR model will be useless since it is trained for the one specific set of initial joint configuration to move forward.

What could be the solution for this use case? If GPR is not the right choice, what would be the better method?

In the below case, 2 demonstrations are used to represent the behavior/skill. However, in our case, "moving straight forward" action can start from different start posture whereas in the figure below it is always q=0. Now, if we imagine that we are really trying to model this "moving straight forward" more generally (which means for different start postures) the trajectory distribution will be very giant (will probably cover the whole plot).

My question is whether GPR or any regression approach can be used for modeling this kind of general behavior.

答:
Gaussian process regression is utilized in the domain of Learning from demonstration to generate the trajectories from multiple demonstrations. The idea is, that a human operator creates a database of trajectories. The points are converted into a mathematical model and a solver is generating trajectories for new situations. The first step is to build a database as a Python dictionary:

```<code>skill_avoiding = {
    0: [(250,150),(170,160),(180,270)],
    1: [(100,160),(180,180),(180,270)],
    2: [(140,140),(170,180),(180,250)],
}
print(skill_avoiding)
</code>```

The skill avoiding is demonstrated three times with different trajectories. They are forming a space of possible actions. For generating a new trajectory an interpolation method is needed. Regression means, that the solver takes the three demonstration as input and generates a new trajectory which has a similar pattern. Gaussian process interpolation works with a RBF kernel. A kernel is an advanced sort of function approximation. In contrast to linear interpolation the resulting trajectory looks smooth.

Body:
Gaussian process regression is utilized in the domain of Learning from demonstration to generate the trajectories from multiple demonstrations. The idea is, that a human operator creates a database of trajectories. The points are converted into a mathematical model and a solver is generating trajectories for new situations. The first step is to build a database as a Python dictionary:

skill_avoiding = {
    0: [(250,150),(170,160),(180,270)],
    1: [(100,160),(180,180),(180,270)],
    2: [(140,140),(170,180),(180,250)],
}
print(skill_avoiding)

The skill avoiding is demonstrated three times with different trajectories. They are forming a space of possible actions. For generating a new trajectory an interpolation method is needed. Regression means, that the solver takes the three demonstration as input and generates a new trajectory which has a similar pattern. Gaussian process interpolation works with a RBF kernel. A kernel is an advanced sort of function approximation. In contrast to linear interpolation the resulting trajectory looks smooth.


答:
Thanks @RLH for clarifying about the angular velocity of a rigid body. For the ones who are also confused by the naming convention in the book Introduction to Robotics like I was, here's my thoughts.

the most important result of the chapter Jacobians: velocities and static force in the origin convention is:

$
{^i\omega_{i+1}} = {^i\omega_{i}} + {_{i+1}^{\;\;\;i}{R}} \cdot {\dot{\theta}_{i+1}} \cdot {^{i+1}\hat{Z}_{i+1}}
$

$
{^iv_{i+1}} = {^iv_i} + {^i\omega_i} \times {^iP_{i+1}}
$

where $^bv_a$ means the velocity of point $a$ with respect to the reference frame (no specified) as observed in frame $b$. Now I am going to rewrite these two equations in a more tedious convention, in which $^Iv_{i/o}$ means the velocity of point $i$ (or frame $i$) with respect to point $o$ (or frame $o$) as observed in the reference frame $I$ :

$
{^I\omega_{i+1/o} = {^I\omega_{i/o}}} + {^I\omega_{i+1/i}}
$

$
{^Iv_{i+1/o}} = {^Iv_{i/o}} + {^Iv_{i+1/i}} + {^I\omega_{i/o}} \times {^IP_{i+1/i}}
$

The first equation relates to a wonderful property of angular velocity:

$
{^I\omega_{P/O}} = {^I\omega_{P/Q}} + {^I\omega_{Q/R}} + \dots + {^I\omega_{M/N}} + {^I\omega_{N/O}}
$

In other words, angular velocities add over intermediate frames. I once thought it impossible every frame on a rigid body share the same angular velocity while the rotational axis is not attached to the origin of the reference frame. It is completely not the case. @RLH has provided a good intuition about the angular velocity of a rigid body.

To see this, it is helpful to remember that the rotational velocity of a frame is the rate of change of the angle between a line drawn in that frame and a fixed reference line. For a rigid body, the angle between any two lines drawn on the body is constant, and so all frames must have the same rotational velocity.

The second equation is called transport theorem in kinematics. It uses the concept of angular velocity to avoid taking time derivatives of unit vectors on intermediate frames. This theorem is useful especially when trying to solve the velocity of end effector moving on parts moving on parts ...

Title: How to understand the angular velocity of link i+1?

Body:
My question is a basic one about velocity propagation from link to link, that is how to understand the following equation.

$
{^i\omega_{i+1}} = {^i\omega_{i}} + {_{i+1}^{\;\;\;i}{R}} \cdot {\dot{\theta}_{i+1}} \cdot {^{i+1}\hat{Z}_{i+1}}
$

The interpretation of this equation from Introduction to Robotics by John J. Craig is:

The angular velocity of link i+1 is the same as that of link i plus a new component caused by rotational velocity at joint i+1. This can be written in terms of frame {i}

Take the following figure as an example, I assume this equation is trying to compute the angular velocity of Link 2 with respect to the frame {1}. i.e., $^1\omega_2$

What bewilders me most is I don't think every point on Link 2 share the same angular velocity with respect to joint 1, because the axis of rotation is not joint 1. Then how come $^1\omega_2$ be computed?

Can anyone please help me out?


问:
Why are shapes in ROS and Gazebo called links?
I have been trying to figure out why shapes in ROS are called links, ie <link> tags in urdf and gazebo? Why not objects or shapes as names? Why are these objects linked to?

答:
Shapes are called links because they're not joints. Keep in mind that these are for robotics and robotic simulations, so the primary concern is going to be expressing the robot's physical structure in such a way that it can be readily used/evaluated by conventional kinematic and dynamic techniques.

Notably, Gazebo and the URDF formats are not drafting tools and are not intended for "decorating" robots. There are joints, and then there are the physical structures that connect the joints ("links"). From a simulation perspective, the link needs to define the physical distance between joints and should have a mass, a center of mass, and a moment of inertia tensor.

These tools don't care about a front grille on a car, or body panels/trim on a robotic arm, flags, pennants, attached payloads, etc., beyond their effects on the previously mentioned terms - mass, CoM, and moments of inertia.

The term you're referring to - shape - can be part of a link, but again the shape of the link is irrelevant -  it's the physical parameters that matter. You can refer to elements of links from the URDF format and note that "visual" attributes are entirely optional. However, if you choose to implement a visual attribute for a link, notice that geometry is mandatory.

The geometry sub-attribute is what you're referring to as "shape" in the question. But again, to re-iterate the points above, Gazebo and URDF formats are intended for use with robotic simulations, so they prioritize the information that is most important kinematic and dynamic simulation. Visual appearance is irrelevant.


问:
Turtulebot not showing in custom world
I  made a map.world file and placed it under

```<code>/opt/ros/kinetic/share/turtlebot_gazebo/worlds
</code>```

and ran

```<code>roslaunch turtlebot_gazebo turtlebot_world.launch world_file:=/opt/ros/kinetic/share/turtlebot_gazebo/worlds/map.world
</code>```

as mentioned here

I see the map but I don't see turtlebot. What am I doing wrong?

答:
Welcome to Robotics, sevebebe. Your question doesn't include any supporting information, so it's hard to tell what you have and what you've done. From the bringup guide:

In this tutorial, we will bring up the turtlebot in the Gazebo simulator. This tutorial assumes you have completed TurtleBot Installation.

Did you install the turtlebot? What do you get if you run the following?

```<code>$ roslaunch turtlebot_gazebo turtlebot_world.launch
</code>```

Title: Turtulebot not showing in custom world

Body:
Welcome to Robotics, sevebebe. Your question doesn't include any supporting information, so it's hard to tell what you have and what you've done. From the bringup guide:

In this tutorial, we will bring up the turtlebot in the Gazebo simulator. This tutorial assumes you have completed TurtleBot Installation.

Did you install the turtlebot? What do you get if you run the following?

$ roslaunch turtlebot_gazebo turtlebot_world.launch


问:
How to take prediction step in particle filter?
I am working on particle filter. I have studied it thoroughly, but stucked at one point during implementation. I have to implement it using MatLab. The issue is this that I am unable to implement the prediction step. As far as I know, it is dependent upon the motion model. motion model is generally dependent upon the noise and previous value of its output.

```<code>                      x(t)= P[x(t) | x(t-1)] = f(x(t-1))+noise  //motion model
</code>```

But I am not getting this point that what should be my prediction step depends upon the motion model. As at time t, it is dependent upon the x(t) and X_predict(t-1), but how do I arrange it, so that my actual and estimated output will have small error. I have tried different methods, but still having the same issue that my actual and estimated values are not approximated, and giving large errors.

I know that weights depend upon the X_predict(t), and if it is not correct, so my estimated output will be wrong.

Kindly guide me how do I proceed.

答:
Like edwinem mentioned, the motion model just describes how the object should move. Consider gravity:

$$
\ddot{y} = -g \\
$$

If you wanted a motion model for position, then:

$$
y = y_0 + \dot{y}t + \frac{1}{2}\ddot{y}t^2 \\
y = y_0 + \dot{y}t - \frac{1}{2}gt^2 \\
$$

So if you have a ball at $y_0 = 5$, does the ball go down in the next instant or does it go up? The answer to that depends on the previous state of your system. If it had a vertical velocity such that $\left(\dot{y}t\right)>\left(\frac{1}{2}gt^2\right)$ then the ball goes up.

If you are finding that your predictions are very far from your measured values, then either your estimated states X_predict(t-1) are wrong or your model is wrong. That is, you're either starting in the wrong location or you're moving in the wrong direction.

:EDIT:

If you don't think anything should be moving, then you could do the same, but now instead of:

$$
\ddot{y} = -g\\
$$

You could model acceleration as resulting strictly from some noise:

$$
\ddot{y} = \sigma\\
$$

And then modify the position model to rely on "incremental" updates, such that:

$$
y = y_0 + \dot{y}t + \frac{1}{2}\ddot{y}t^2\\
$$

becomes:

$$
y_k = y_{k-1} + \dot{y}\Delta t + \frac{1}{2}\ddot{y}\Delta t^2 \\
$$

And then, if the noisy acceleration is an input to the system, you wind up with:

$$
\left[\begin{matrix}
\dot{y} \\
\ddot{y} \end{matrix}\right] = \left[\begin{matrix}
0 & 1\\
0 & 0 \end{matrix}\right]\left[\begin{matrix}
y \\
\dot{y}\end{matrix}\right] +
\left[\begin{matrix}
0 \\
1\end{matrix}\right]\sigma
$$

If you depict this as:

$$
\dot{x} = Ax + Bu \\
$$

then you can do a kind of integration, such that:

$$
x_k = I*x_{k-1} + \left(\dot{x}\Delta t\right) \\
$$

and so you get:

$$
\begin{matrix}
x_k \\
\left[\begin{matrix}
y_k \\
\dot{y}_k \end{matrix}\right]\end{matrix} = \begin{matrix}
I \\
\left[\begin{matrix}
1 & 0\\
0 & 1 \end{matrix}\right]\end{matrix} \begin{matrix}
x_{k-1} \\
\left[\begin{matrix}
y_{k-1} \\
\dot{y}_{k-1}\end{matrix}\right]\end{matrix} + \left(\begin{matrix}
A\Delta t \\
\left[\begin{matrix}
0 & \Delta t\\
0 & 0 \end{matrix}\right]\end{matrix}\begin{matrix}
x_{k-1} \\
\left[\begin{matrix}
y_{k-1} \\
\dot{y}_{k-1}\end{matrix}\right]\end{matrix} +
\begin{matrix}
B\Delta t & \sigma\\
\left[\begin{matrix}
0 \\
\Delta t\end{matrix}\right] & \sigma\end{matrix}\right)
$$

which of course reduces to:

$$
\left[\begin{matrix}
y_k \\
\dot{y}_k \end{matrix}\right] = \left[\begin{matrix}
1 & \Delta t\\
0 & 1 \end{matrix}\right]\left[\begin{matrix}
y_{k-1} \\
\dot{y}_{k-1}\end{matrix}\right] +
\left[\begin{matrix}
0 \\
\Delta t\end{matrix}\right]\sigma
$$

The above would be a decent first motion model if you had no prior knowledge of how you expected something to move.


答:
There is a way to derive the joint velocity kinematics from the joint position kinematics.

For me it is easier to express everything on a common coordinate system (the inertial frame) such that vector algebra can be done between terms on different links.

Each link $i$ has a local to world transformation matrix $\mathbf{R}_i$ such that for example the local joint axis ${}^i\boldsymbol{\hat{Z}}_i$ expressed in world coordinates is $$ \boldsymbol{\hat{Z}}_i = \mathbf{R}_i {}^i\boldsymbol{\hat{Z}}_i \tag{1}$$

The rotational kinematics of the next joint is

$$ \mathbf{R}_{i+1} = \mathbf{R}_i \, {\rm rot}({}^i\boldsymbol{\hat{Z}}_i, \theta_{i+1}) \tag{2}
$$

Now take the derivative of the above and note the following sub-expressions, derived from the time derivative of vectors in rotating frames

$$ \begin{aligned}
 \tfrac{\rm d}{{\rm d}t} \mathbf{R}_i & = \boldsymbol{\omega}_i \times \mathbf{R}_i \\
 \tfrac{\rm d}{{\rm d}t} \mathbf{R}_{i+1} & = \boldsymbol{\omega}_{i+1} \times \mathbf{R}_{i+1} \\
 \tfrac{\rm d}{{\rm d}t} {\rm rot}({}^i\boldsymbol{\hat{Z}}_i, \theta_{i+1}) & = \left( {}^i\boldsymbol{\hat{Z}}_i, \dot\theta_{i+1} \right) \times {\rm rot}({}^i\boldsymbol{\hat{Z}}_i, \theta_{i+1})
\end{aligned} \tag{3}$$

Now use (3) into (2) and use the product rule to get

$$\begin{aligned}
\tfrac{\rm d}{{\rm d}t} \mathbf{R}_{i+1} &=\left( \tfrac{\rm d}{{\rm d}t}\mathbf{R}_i \right)\, {\rm rot}({}^i\boldsymbol{\hat{Z}}_i\, \theta_{i+1}) +  \mathbf{R}_i \,\left( \tfrac{\rm d}{{\rm d}t}{\rm rot}({}^i\boldsymbol{\hat{Z}}_i\, \theta_{i+1})\right) \\
\boldsymbol{\omega}_{i+1} \times \mathbf{R}_{i+1} & = \boldsymbol{\omega}_i \times \mathbf{R}_i\, {\rm rot}({}^i\boldsymbol{\hat{Z}}_i\, \theta_{i+1}) +  \mathbf{R}_i \,\left( {}^i\boldsymbol{\hat{Z}}_i\, \dot\theta_{i+1} \right) \times {\rm rot}({}^i\boldsymbol{\hat{Z}}_i, \theta_{i+1}) \\
& =\boldsymbol{\omega}_i \times \mathbf{R}_{i+1} +  \left( \mathbf{R}_i \,{}^i\boldsymbol{\hat{Z}}_i, \dot\theta_{i+1} \right) \times \left( \mathbf{R}_i \,{\rm rot}({}^i\boldsymbol{\hat{Z}}_i, \theta_{i+1}) \right) \\
 & = \boldsymbol{\omega}_i \times \mathbf{R}_{i+1} + \boldsymbol{\hat{Z}}_i\, \dot\theta_{i+1} \times \mathbf{R}_{i+1}
\end{aligned} \tag{4}$$

From which you factor out $\mathbf{R}_{i+1}$ to get

$$ \boxed{ \boldsymbol{\omega}_{i+1} = \boldsymbol{\omega}_{i} + \boldsymbol{\hat{Z}}_i\, \dot\theta_{i+1} } \tag{5}$$

The interpretation is clear now. Add the velocity of link $i$ to the rotation about this axis (in word coordinates) $\boldsymbol{\hat{Z}}_i$ with speed $\dot{\theta}_i$.


问:
Cmake Error While Buliding Pixhawk simulator
I am trying to run "px4 SITL simulation" using gazebo7 on my machine with "UBUNTU-14.04 LTS" using these commands:

```<code>mkdir -p ~/src
cd ~/src
git clone https://github.com/PX4/Firmware.git
cd Firmware
git submodule update --init --recursive
</code>```

But as I enter the next command i.e :

```<code>make posix_sitl_default gazebo
</code>```

It gives an error -->

```<code>CMake Error: The source directory "/home/arpit/src/Firmware/build/posix_sitl_default/-Wno-deprecated" does not exist.
Specify --help for usage, or press the help button on the CMake GUI.
/bin/sh: 1: cd: can't cd to /home/arpit/src/Firmware/build/posix_sitl_default
make: *** [posix_sitl_default] Error 2
</code>```

Any Solutions?

答:
I think there is a missing space in the makefile. the flag should be on a separate line from directories.
That is as far as I can say since I don't have the file.</p>


答:
The prediction step generates a new set of states from the old set of states. The motion model of the system is used to make this best estimate of what we think the new state might be. The motion model basically uses the information about the previous state and the current control input to determine the new state. Some noise is also added for stochasticity. In cases where you do not have a motion model or any information about the control input, just adding noise is an option but most likely gives a less accurate estimate.
In a particle filter, the the accuracy of your best estimate/particle really depends on how well you have propagated your new particles into the next time step using the motion model. As you can imagine, having a higher number of particles to represent the distribution increases the chances that one of them is very close to the actual state. </p>

Title: How to take prediction step in particle filter?

Body:
I am working on particle filter. I have studied it thoroughly, but stucked at one point during implementation. I have to implement it using MatLab. The issue is this that I am unable to implement the prediction step. As far as I know, it is dependent upon the motion model. motion model is generally dependent upon the noise and previous value of its output.

```<code>                      x(t)= P[x(t) | x(t-1)] = f(x(t-1))+noise  //motion model
</code>```

But I am not getting this point that what should be my prediction step depends upon the motion model. As at time t, it is dependent upon the x(t) and X_predict(t-1), but how do I arrange it, so that my actual and estimated output will have small error. I have tried different methods, but still having the same issue that my actual and estimated values are not approximated, and giving large errors.

I know that weights depend upon the X_predict(t), and if it is not correct, so my estimated output will be wrong.

Kindly guide me how do I proceed.


问:
Directional hearing for Linux robot?
I want to give my Linux robot the ability to locate a sound source and drive towards it. I am reading a paper on sound localization that seems to cover the theory well enough, but I'm at a loss as to how do I implement it. Specifically I would like to know:

How do I connect two microphones to a Linux PC?

How do I record from two microphones simultaneously?

Is there any library of sound processing algorithms (similar to how OpenCV is a library of computer vision algorithms) available for Linux?

答:
I strongly suggest using a single sound card instead of multiple USB microphones or sound cards. For an application like sound location, it is essential that the samples from the different microphones are recorded at exactly the same time. When using multiple devices, that's next to impossible; they will be slightly out of sync when the recording starts, and because their sample rates are not exactly the same, after some time the time difference becomes substantial. This can be counteracted using adaptive clock synchronization and adaptive rate resampling (see alsaloop for an example) but you will never obtain the precision a single sound card can get you.

So this means either using the stereo input of a standard sound card and dealing with the ambiguities this introduces or using a (USB) sound card that has 4 (microphone) inputs. Also a tip on the microphones: get omnidirectional ones, it makes the samples much easier to compare.

I'm not aware of the kind of the kind of software you're looking for, but directly working with ALSA is not too difficult; ALSA comes with great examples and audio data is relatively easy to work with compared to image data.

Title: Directional hearing for Linux robot?


问:
Coordinates seem to show overlapping but RViz doesn't
How can you place two objects that seem to overlap with their units but appear stacked on top of each other [original intent] in RViz?

I was watching this video tutorial on ROS and URDF. I have tried to paste screenshots to clarify but feel free to watch the video if you have the time. The presenter is showing how to create a joint between base link and link 01 in the first image below.

Here's the xacro file that I am confused about. If the xyz coordinates of the origin of the box are [0 0 0] and its dimensions are [1 1 1], how can the cylinder have its origin at [0 0 0.2]? Isn't it within the box?

I considered that the xyz coordinates may be relative to the link itself but where does RViz know where to place the object in the world? Moreover, the joint is placed at [0 0 0.5] and this makes sense. Shouldn't the origin of the cylinder have been [0 0 1.2]? This is how it looks like in RViz.

答:
The origin defined inside link_01 is not the position of the cylinder in the global coordinate frame (the "world"), but in its own private frame. By default the object's center lies at the origin of its own coordinate frame, but in this case, the cylinder is shifted $0.2 m$ upwards along the $z$ axis, placing its bottom on the origin.

The effect of this shift is that the reference point for any further manipulations of link_01 now lies on its bottom, instead of its center as would normally be the case.

Likewise, the origin defined in the base_link__link_01 joint is defined relative to the coordinate frame of the parent link, in this case base_link. It also specifies where the origin frame of the child link will be placed, relative to the frame of the parent link.

All this leads to the following configuration:

As you can see in the image above, the base_link__link_01 joint places the origin frame of link_01 $0.5 m$ above the origin frame of base_link. And since link_01 itself is shifted relative to its own frame, the result is that the bottom of link_01 is placed exactly on top of base_link.

The topic of coordinate frames, the transforms between them and their use in robotics is one of the more advanced, and unfortunately I don't know of a comprehensive reference on it, but this tutorial seems a good start point to getting acquainted with it.


问:
What is the difference between the holding torque and stall torque of a motor?
Do the terms holding torque and stall torque imply the same thing? The information on torque for these stepper motors is given as holding torque. While these servo motors have the torque given as stall torque. My hope is to use the maximum torque a motor can handle to compare different motors for a project.</p>

答: Both holding torque for a stepper motor, and stall torque for a servo motor, refer to the maximum amount of torque when the shaft is not spinning and the windings are fully energized.   A stepper motor also has a detent torque because of its magnet arrangement.  Detent torque is the amount of torque it takes to overcome the magnetic attraction and move a shaft one step from being stopped when the windings are not energized.  </p>


问:
How to PID tune a four wheel robot?
Four wheel mecanum rover with a mass of approximately 50 Kg.  Each wheel has a 20:1 gearbox with encoder at the wheel (rather than the motor).

If this was something like a robot arm I would PID tune each DOF starting with the distal joints and work my way back to the base.  This is a case of four motors collaborating to accelerate and control the total mass.  What's the best approach to doing this?

One thought I had was to setup a tuning jig for single motor+gearbox+wheel, load it with 1/4 of the mass and tune them individually in this fashion.  This would likely work just fine.  Perhaps not the most elegant but it might do OK.

The other one is to run the system open loop, issue a step change command, observe and record the response and use this to iterate a solution.  In many ways this is similar to the Twiddle algorithm, which is nothing more than sequential approximation and optimization.

I'll have the hardware built next week so I can't test at the moment.  I am leaning towards tuning each motor+gearbox+wheel using the 1/4 mass jig first.  This could be followed by a fine tuning process using fine-step successive approximation to get it right with all four motors driving the entire mass.

One of the questions I have has to do with what happens to this tuning in the context of a holonomic drive, which can move the mass in multiple directions and rotate about its axis (as well as rotate about any point on the xy plane).

Twiddle algorithm:
https://www.youtube.com/watch?v=2uQ2BSzDvXs

答:
I can think of three ways to control this robot:

Do as you described and have one separate controller for each motor, tuned independently using a test fixture;

Use a MIMO PID controller to simultaneously control the four motors;

Use two PID controllers, one for linear speed, another for angular.

The last option would take advantage of the fact that, according to the kinematic equations for a four-wheeled drive, the front and rear left wheels $W_{LF}$ and $W_{LR}$ can be combined into a single "virtual" wheel $W_L$ such that:

$$
\omega W_L = \frac{\omega W_{LF} + \omega W_{LR}}{2}
$$

Where $\omega W_L$, $\omega W_{LF}$ and $\omega W_{LR}$ are respectively the angular speeds of the virtual left, left front and left rear wheels. A virtual right wheel $W_R$ can be defined analogously. This reduces the system definition to a differential drive, for which linear and angular speeds can be computed as:

$$
v = \frac{r (\omega W_L + \omega W_R)}{2}
$$

$$
\omega = \frac{\omega W_R - \omega W_L}{2l}
$$

Where $r$ is the wheel radius and $l$ the lateral distance between wheels. From the formulas above you get:

$$
\omega W_L = \frac{v}{r} - \omega l
$$

$$
\omega W_R = \frac{v}{r} + \omega l
$$

Allowing you to use linear and angular speeds as references to control the virtual wheels.

Title: How to PID tune a four wheel robot?


问:
What is the purpose of an empty link without any child elements?
I was looking at a model xacro [urdf] file in a ROS tutorial when I saw:

```<code><link name="robot_footprint"></link>
</code>```

right at the top. There were no child tags for:  <collision>, <visual> or <inertial>. There was however a joint right after but no further references to the robot_footprint link.

```<code>  <joint name="robot_footprint_joint" type="fixed">
    <origin xyz="0 0 0" rpy="0 0 0" />
    <parent link="robot_footprint"/>
    <child link="chassis" />
  </joint>
</code>```

What does the empty link serve?

答:
In this particular case, it's probably used as a projection of the robot's root link on the floor. This is often useful for motion planning or SLAM, where the robot's pose is read (or set) as the projection from that frame to the global frame. Going back to that other case involving coordinate frames, robot_footprint would serve the same purpose as shifting link_01 vertically relative to its frame.

Another common use of such links is to define sensor coordinate frames. For example, coordinates in a point cloud are often given relative to frame of the sensor that generated it; by creating a link that matches the sensor's position relative to the robot's root link, transforms can be computed to map those points to the robot's pose in the global coordinate frame.

See the URDF tutorials for more information on how links and joints work and are used in ROS.


问:
Can you refresh gazebo when you load through ROS?
I have a urdf model that I have loaded with:

```<code>roslaunch my_robot world.launch
</code>```

I noticed that I gave the wrong color to a part of the robot. I have made changes. Is there a command to run to refresh gazebo from roslaunch? I have been quitting everything every time I make a change and I feel it is too much of RAM usage and slower.

答: It depends. If you're spawning the robot at runtime, either through the spawn_model service or from the Gazebo model database, then you can just just remove the robot from the simulation (click it and hit the <Delete> key), edit the model file and load it again. If it's directly included in the world file, then as far as I can find, no, you cannot reload it without restarting Gazebo.


问:
Gazebo not reading the material color in URDF
I have a chassis link that has casters. I would like the casters to be grey and the box to be blue. The ROS link doc mentions <material> and <color> tags as being needed for color.

```<code>  <link name='chassis'>
    <pose>0 0 0.1 0 0 0</pose>

    <inertial>
      <mass value="15.0"/>
      <origin xyz="0.0 0 0" rpy=" 0 0 0"/>
      <inertia
          ixx="0.1" ixy="0" ixz="0"
          iyy="0.1" iyz="0"
          izz="0.1"
      />
    </inertial>

    <collision name='chassis_collision'>
      <origin xyz="0 0 0" rpy=" 0 0 0"/>
      <geometry>
        <box size=".4 .2 .1"/>
      </geometry>
    </collision>

    <visual name='chassis_visual'>
      <origin xyz="0 0 0" rpy=" 0 0 0"/>
      <geometry>
        <box size=".4 .2 .1"/>
      </geometry>
      <material name="blue">
        <color rgba= "0 0 1 1"/>
      </material>
    </visual>

    <collision name='back_caster_collision'>
      <origin xyz="-0.15 0 -0.05" rpy=" 0 0 0"/>
      <geometry>
        <sphere radius="0.0499"/>
      </geometry>
    </collision>

    <visual name='back_caster_visual'>
      <origin xyz="-0.15 0 -0.05" rpy=" 0 0 0"/>
      <geometry>
        <sphere radius="0.05"/>
      </geometry>
      <material name="grey">
        <color rgba="0.75 0.75 0.75 1"/>
      </material>
    </visual>

    <collision name='front_caster_collision'>
      <origin xyz="0.15 0 -0.05" rpy=" 0 0 0"/>
      <geometry>
        <sphere radius="0.0499"/>
      </geometry>
    </collision>

    <visual name='front_caster_visual'>
      <origin xyz="0.15 0 -0.05" rpy=" 0 0 0"/>
      <geometry>
        <sphere radius="0.05"/>
      </geometry>
      <material name="grey">
        <color rgba="0.75 0.75 0.75 1"/>
      </material>
    </visual>

  </link>

</code>```

However, when I roslaunch my_robot world.launch the bot is the same color, gray. It is only when I add the following that the color changes to blue. What is the purpose of the <color> tag then?

```<code>  <gazebo reference="chassis">
    <material>Gazebo/Blue</material>
  </gazebo>
</code>```

答:
I've never used ROS or Gazebo before, but it looks like all of your components are defined as being part of the same link, so Gazebo may be applying the last-specified color to all components because, as the documentation is written,

The link element describes a rigid body with an inertia, visual features, and collision properties.

Describes A rigid body. If you wanted to troubleshoot this, I would try changing the last color from grey to something completely different, like magenta, and see if that causes everything in the link to change to that color.

I would also try splitting the individual components out into their own links; if it's only using the last-specified color then it may also only be using the last-specified collider.


答:
It's a limitation in Gazebo's ability to convert URDF to SDF, Gazebo's native object description format. Frustratingly, RViz works the other way around: it correctly parses URDF colors, but not the SDF fragments inserted by the gazebo tag.

One tip though, instead of inlining your material definitions inside links, it's better to define them once at the beginning and just refer to them throughout the rest of the file. It's more concise and if you ever want to change a material's definition, you have just one place to change. For example:

```<code><robot name="robot" xmlns:xacro="http://ros.org/wiki/xacro">
  <material name="blue">
    <color rgba= "0 0 1 1"/>
  </material>
  <material name="grey">
    <color rgba="0.75 0.75 0.75 1"/>
  </material>

  <!-- ... -->

  <link name='chassis'>
    <pose>0 0 0.1 0 0 0</pose>

    <inertial>
      <mass value="15.0"/>
      <origin xyz="0.0 0 0" rpy=" 0 0 0"/>
      <inertia
          ixx="0.1" ixy="0" ixz="0"
          iyy="0.1" iyz="0"
          izz="0.1"
      />
    </inertial>

    <collision name='chassis_collision'>
      <origin xyz="0 0 0" rpy=" 0 0 0"/>
      <geometry>
        <box size=".4 .2 .1"/>
      </geometry>
    </collision>

    <visual name='chassis_visual'>
      <origin xyz="0 0 0" rpy=" 0 0 0"/>
      <geometry>
        <box size=".4 .2 .1"/>
      </geometry>
      <material name="blue"/>
    </visual>

    <collision name='back_caster_collision'>
      <origin xyz="-0.15 0 -0.05" rpy=" 0 0 0"/>
      <geometry>
        <sphere radius="0.0499"/>
      </geometry>
    </collision>

    <visual name='back_caster_visual'>
      <origin xyz="-0.15 0 -0.05" rpy=" 0 0 0"/>
      <geometry>
        <sphere radius="0.05"/>
      </geometry>
      <material name="grey"/>
    </visual>

    <collision name='front_caster_collision'>
      <origin xyz="0.15 0 -0.05" rpy=" 0 0 0"/>
      <geometry>
        <sphere radius="0.0499"/>
      </geometry>
    </collision>

    <visual name='front_caster_visual'>
      <origin xyz="0.15 0 -0.05" rpy=" 0 0 0"/>
      <geometry>
        <sphere radius="0.05"/>
      </geometry>
      <material name="grey"/>
    </visual>
  </link>

  <!-- ... -->

</robot>
</code>```

Title: Gazebo not reading the material color in URDF

Body:
I have a chassis link that has casters. I would like the casters to be grey and the box to be blue. The ROS link doc mentions <material> and <color> tags as being needed for color.

```<code>  <link name='chassis'>
    <pose>0 0 0.1 0 0 0</pose>

    <inertial>
      <mass value="15.0"/>
      <origin xyz="0.0 0 0" rpy=" 0 0 0"/>
      <inertia
          ixx="0.1" ixy="0" ixz="0"
          iyy="0.1" iyz="0"
          izz="0.1"
      />
    </inertial>

    <collision name='chassis_collision'>
      <origin xyz="0 0 0" rpy=" 0 0 0"/>
      <geometry>
        <box size=".4 .2 .1"/>
      </geometry>
    </collision>

    <visual name='chassis_visual'>
      <origin xyz="0 0 0" rpy=" 0 0 0"/>
      <geometry>
        <box size=".4 .2 .1"/>
      </geometry>
      <material name="blue">
        <color rgba= "0 0 1 1"/>
      </material>
    </visual>

    <collision name='back_caster_collision'>
      <origin xyz="-0.15 0 -0.05" rpy=" 0 0 0"/>
      <geometry>
        <sphere radius="0.0499"/>
      </geometry>
    </collision>

    <visual name='back_caster_visual'>
      <origin xyz="-0.15 0 -0.05" rpy=" 0 0 0"/>
      <geometry>
        <sphere radius="0.05"/>
      </geometry>
      <material name="grey">
        <color rgba="0.75 0.75 0.75 1"/>
      </material>
    </visual>

    <collision name='front_caster_collision'>
      <origin xyz="0.15 0 -0.05" rpy=" 0 0 0"/>
      <geometry>
        <sphere radius="0.0499"/>
      </geometry>
    </collision>

    <visual name='front_caster_visual'>
      <origin xyz="0.15 0 -0.05" rpy=" 0 0 0"/>
      <geometry>
        <sphere radius="0.05"/>
      </geometry>
      <material name="grey">
        <color rgba="0.75 0.75 0.75 1"/>
      </material>
    </visual>

  </link>

</code>```

However, when I roslaunch my_robot world.launch the bot is the same color, gray. It is only when I add the following that the color changes to blue. What is the purpose of the <color> tag then?

```<code>  <gazebo reference="chassis">
    <material>Gazebo/Blue</material>
  </gazebo>
</code>```

Body:
It's a limitation in Gazebo's ability to convert URDF to SDF, Gazebo's native object description format. Frustratingly, RViz works the other way around: it correctly parses URDF colors, but not the SDF fragments inserted by the gazebo tag.

One tip though, instead of inlining your material definitions inside links, it's better to define them once at the beginning and just refer to them throughout the rest of the file. It's more concise and if you ever want to change a material's definition, you have just one place to change. For example:

<robot name="robot" xmlns:xacro="http://ros.org/wiki/xacro">
  <material name="blue">
    <color rgba= "0 0 1 1"/>
  </material>
  <material name="grey">
    <color rgba="0.75 0.75 0.75 1"/>
  </material>

  <!-- ... -->

  <link name='chassis'>
    <pose>0 0 0.1 0 0 0</pose>

    <inertial>
      <mass value="15.0"/>
      <origin xyz="0.0 0 0" rpy=" 0 0 0"/>
      <inertia
          ixx="0.1" ixy="0" ixz="0"
          iyy="0.1" iyz="0"
          izz="0.1"
      />
    </inertial>

    <collision name='chassis_collision'>
      <origin xyz="0 0 0" rpy=" 0 0 0"/>
      <geometry>
        <box size=".4 .2 .1"/>
      </geometry>
    </collision>

    <visual name='chassis_visual'>
      <origin xyz="0 0 0" rpy=" 0 0 0"/>
      <geometry>
        <box size=".4 .2 .1"/>
      </geometry>
      <material name="blue"/>
    </visual>

    <collision name='back_caster_collision'>
      <origin xyz="-0.15 0 -0.05" rpy=" 0 0 0"/>
      <geometry>
        <sphere radius="0.0499"/>
      </geometry>
    </collision>

    <visual name='back_caster_visual'>
      <origin xyz="-0.15 0 -0.05" rpy=" 0 0 0"/>
      <geometry>
        <sphere radius="0.05"/>
      </geometry>
      <material name="grey"/>
    </visual>

    <collision name='front_caster_collision'>
      <origin xyz="0.15 0 -0.05" rpy=" 0 0 0"/>
      <geometry>
        <sphere radius="0.0499"/>
      </geometry>
    </collision>

    <visual name='front_caster_visual'>
      <origin xyz="0.15 0 -0.05" rpy=" 0 0 0"/>
      <geometry>
        <sphere radius="0.05"/>
      </geometry>
      <material name="grey"/>
    </visual>
  </link>

  <!-- ... -->

</robot>


答:
MAVLink is an encoded message. In order for you to get specific data out of it you will need to decode it in some way. There are a number of ways of doing this including writing your own code and attaching MAVlink to it. This is described here: http://qgroundcontrol.org/dev/mavlink_onboard_integration_tutorial. In order to use this you will have to have downloaded the mavlink libraries from the repository here: https://github.com/mavlink/mavlink.

If you are wanting a platform independent java based implementation, a friend of mine Owen McAree developed MAVNode a Node.js based decoder for MAVLink which will decode the messages you require. It is a nvm repository https://npmjs.org/package/mavlink.

Title: Telemetry with Ardupilot 2.6

Body:
I'm using the telemetry kit from 3DR robotics (433MHz) to interface with Ardupilot Mega 2.6, controlling a quadcopter. The Mission Planner (v1.2.84) by Michael Oborne works well with the telemetry kit, transmitting flight data (IMU, compass, GPS etc.) from the quadcopter to the GCS and displaying them in their GUI.

However, I would like to see the same data in the hyperterminal (windows system). The radio receiver on the GCS connects to my PC through a USB drive. I have tried calling the remote radio station using all possible Baud rates, starting from 110 to 921600 (including 57600). I've set the data bits to 8 and stop bits to 1. 'None' for parity and flow control.

However, all that I ever get on my terminal is either gibberish or no data at all. I also tried burning this software to the radio receiver and tried using AT commands on the radio.

It connects OK with '+++', but keeps returning error for AT1, ATT etc.

Please give me an idea about how to get flight data at the hyperterminal.

Thanks.


问:
Odometry using wheel encoder with no differential drive
I am currently looking for a way to do odometry using wheel encoders, for a car that has no differential drive. The two rear wheel would rotate at the exact same speed. I have been looking everywhere for an answer, but unable to find any. I am starting to think that this is not a possible thing to do. I would be very grateful if anybody can point me in the correct direction.</p>

答:
So long you have a sensor to read the angle of the steering wheel, you can use the bicycle kinematic model to compute odometry for an Ackermann drive platform, e.g. a car:

$$
\begin{align}
 \\
\dot{x} & = v \; cos(\psi + \beta) \\ \\
\dot{y} & = v \; sin(\psi + \beta) \\ \\
\dot{\psi} & = \frac{v}{l_r} sin(\beta) \\ \\
\beta  & = tan^{-1} \left ( \frac{l_r}{l_f + l_r} tan(\delta_f) \right )
\end{align}
$$

Where $v$ is linear forward velocity, $\dot{x}$ and $\dot{y}$ are the linear velocities alongside the Cartesian axes, $\psi$ and $\dot{\psi}$ are the heading angle and angular velocity, $l_f$ and $l_r$ are the distances from the center of mass to the front an rear axles, and $\delta_f$ is the steering wheel angle.

Assuming $v$ and $\delta_f$ are retrieved using encoders or other sensors, the vehicle pose can be approximated by:

$$
\begin{align}
 \\
x_t & = x_{t - 1} + \dot{x} \; \Delta t \\ \\
y_t & = y_{t - 1} + \dot{y} \; \Delta t \\ \\
\psi_t & = \psi_{t - 1} + \dot{\psi} \; \Delta t \\ \\
\end{align}
$$


问:
Kalman filter with a known motion model
I have a robot whose pose $(x, y)$ is defined relative to the global frame. I have a sensor which estimates the robot's current pose in the global frame, and the sensor is known to have Gaussian error. The robot has a sensor which estimates the robot's local velocity $(u, v)$ relative to the robot's own frame, and the sensor is known to have zero error, so the motion model is known perfectly.

I now want to track the estimated pose of the robot in the global frame, using a Kalman filter. I know that my observation noise is Gaussian, which is one requirement of the Kalman filter. The other requirement is that the dynamics model is linear. Most examples of this type (global position frame, local velocity frame) I have seen say that the Extended Kalman filter is needed. However, I am not sure about whether this is true for my case, because my velocity sensor has zero error.  I have two ideas:

1) The velocity sensor has zero error, and so the motion model is known perfectly. So, at every timestep, the estimated state is simply the previous state, plus the velocity multiplied by the timestep. Since there is no uncertainty in the velocity, there is no uncertainty in the motion. Therefore, I can use a regular Kalman filter.

2) Even though the motion model as zero noise, the dynamics itself is still non-linear. This is because to transform from the local frame to the global frame requires a rotation, which is a non-linear function since it involves sin and cosine functions. There may be zero "extra" uncertainty caused by the motion, but the motion model is still non-lienar. Therefore, I must use an extended Kalman filter.

Please could somebody explain which is correct, or if neither, what the correct solution is?

答: The reason that a Kalman filter requires a linear system is that a gaussian distribution loses its properties when transformed with a non-linear function. Although your transformation from local to global frame is a non-linear function, since your velocity measurement has no gaussian noise associated with it, you dont need to worry about the requirement for linearity. That being said, in the case that you perfectly know you initial pose, then you can just transform the perfect velocity measurement from the local frame to the global frame and find the new pose without any uncertainty. So if you have the perfect initial state you would not even require a filter.</p>

Title: Kalman filter with a known motion model


问:
How to create a Complementary Filter for a linearly accelerating body to obtain estimate of orientation in quaternion?
A complementary filter (CF) uses orientation obtained calculated from gyroscope, accelerometer and magnetometer to find a more accurate measurement of orientation.

However, when my sensor is accelerating linearly, the orientation from trigonometric equations using accelerometer readings is not correct. These equations seem to work only when the linear acceleration is 0. It seems that it is useless to apply accelerometer orientation in the Complementary Filter in this case.

Magnetometer on the other hand gives only the heading angle and the roll angle and not the pitch.

Is there any way of using CF to find orientation for a linearly accelerating vehicle? Or is CF intended only for cases when linear acceleration is 0?

答:
The point of a complementary filter is combine the low-pass parts of some measurements (e.g. accelerometer) with the high-pass parts of other measurements (e.g. gyro). If the accelerometer perfectly reflected the direction of gravity you wouldn't need the gyroscope part.

So practical applications that successfully use complementary filters with an accelerometer have an average acceleration close to zero over the relevant time scale. Cars, quadrotors, etc all meet this requirement. Note that as your gyroscope quality improves, and you adjust the filter accordingly, you can tolerate longer and longer periods of significant acceleration.

Also, accelerometers are not required for complementary filters. Any directional measurement will work. For example, if a plane were to track a known feature on the ground that could work as well.


问:
For pose estimation, what is the typical range of the rotation values that are estimated? Is it from -180 to 180 degrees?
I am currently working with the Rutgers APC 2015 data set for pose estimation, and see that the pose estimates, specifically the rotation estimates, have seemingly been rescaled to range between -1 and 1. Does anyone know if these values were arrived at by dividing by 180? </p>

答: The range between -1 or +1 is a normalized range like you said. The question is the following: Were those values divided by 180 (degrees) or 2*pi (radians)? You should check any existant documentation regarding Rutgers APC 2015. Usually, the convention is to have the angles bounded between -pi/pi or -180/180, because expressions like atan2 or atan2d returns angles in that range. The range 0-360 might lead to tricky bugs to catch and error during the 360,0 crossover. </p>


问:
Questions about Irobot Create
I'm interested in getting a Create for a project I'll be working on, and wanted some information about it from somebody that already has one:

How much weight can it safely carry? I talked with Irobot's tech support and they told me the maximum is 5lb, but searching on the internet it seems like this limit is actually not as strict as it appears to be. I'm asking because I'd need to put a 3kg laptop on top of it, which would mean ~3.5-4kg if you also consider the kinect and eventual supports for both. I guess I could use a netbook and send the data I need to another computer, but I wanted to avoid the additional overhead of the wireless link.

For how long does it run using AA batteries? I'm inclined on not getting the battery pack, since I'd be using the robot in europe, so I'd also need a transformer if I went with the battery pack option.

Thanks!

答:
The weight of just the 6.6 pound laptop is already 32% over capacity, so you may need to consider lightening the load. If not then you risk lower performance, higher stresses on the robot and possibly even burning out one or more motors under stress testing.

On the matter of battery life, according to the iRobot Create Manual:

Alkaline batteries will power the robot (on a hard floor with no payloads or
  attachments) for up to 1.5 hours if the robot is constantly moving.

So this is less than half the run time of the APS battery:

The iRobot Create robot (without a payload or other attachments) will run for
  up to 3.5 hours with a fully charged APS battery.

Title: Questions about Irobot Create


问:
Gazebo throwing error in opening model created in it
I created my world with gazebo9 and saved it.

```<code>world$ tree
.
└── myworld
    ├── model.config
    └── model.sd
</code>```

Now when I start it with

```<code>$ gazebo myworld
</code>```

I get

```<code>terminate called after throwing an instance of 'std::bad_alloc'
  what():  std::bad_alloc
</code>```

Why am I getting a memory error when all this ran fine. Starting Gazebo on its own works.

I am using:
Ubuntu 18.04
gazebo9

Question 1 and Question 2 don't have solutions.

I have restarted my virtual machine and still get the same error. In some cases, nothing happens.

答:
You might be confusing Gazebo worlds and models. A world is a single SDF file structured as below:

```<code><sdf version="VERSION">
  <world name="NAME">
    <!-- Included models, links etc. -->
  </world>
</sdf>
</code>```

For example, these are the contents of the sample /usr/share/gazebo-9/worlds/willowgarage.world world file:

```<code><?xml version="1.0" ?>
<sdf version="1.5">
  <world name="default">
    <include>
      <uri>model://ground_plane</uri>
    </include>
    <include>
      <uri>model://sun</uri>
    </include>
    <include>
      <uri>model://willowgarage</uri>
    </include>
  </world>
</sdf>
</code>```

In order to pre-load a world at startup time, you pass the path to the file as argument to Gazebo:

```<code>$ gazebo /usr/share/gazebo-9/worlds/willowgarage.world
</code>```

The directory structure you described looks more like that of a model, which in addition to a SDF file also includes a configuration and (optionally) other resources such as meshes, materials etc. As far as I know there's no way to directly load a model at startup time, other than as an element included in a world file.

So to answer your question, the problem is probably that Gazebo is expecting its argument to point to an SDF file, but finds it to be a directory instead, and crashes as a result.

Body:
You might be confusing Gazebo worlds and models. A world is a single SDF file structured as below:

<sdf version="VERSION">
  <world name="NAME">
    <!-- Included models, links etc. -->
  </world>
</sdf>

For example, these are the contents of the sample /usr/share/gazebo-9/worlds/willowgarage.world world file:

<?xml version="1.0" ?>
<sdf version="1.5">
  <world name="default">
    <include>
      <uri>model://ground_plane</uri>
    </include>
    <include>
      <uri>model://sun</uri>
    </include>
    <include>
      <uri>model://willowgarage</uri>
    </include>
  </world>
</sdf>

In order to pre-load a world at startup time, you pass the path to the file as argument to Gazebo:

$ gazebo /usr/share/gazebo-9/worlds/willowgarage.world

The directory structure you described looks more like that of a model, which in addition to a SDF file also includes a configuration and (optionally) other resources such as meshes, materials etc. As far as I know there's no way to directly load a model at startup time, other than as an element included in a world file.

So to answer your question, the problem is probably that Gazebo is expecting its argument to point to an SDF file, but finds it to be a directory instead, and crashes as a result.


问:
Importing a world into another world in gazebo
Is it possible to start with a with an empty world, empty.world and then import walls (other worlds into it)? I can't seem to find an import option in the gazebo menu.

答:
If you mean merging other world's contents into an open world file in the Gazebo GUI, no, there is no way to do that.

You can however open the world files in a text editor and just copy contents over. Most worlds are structured as a sequence of <include> tags pointing to external models, so this would be quite easy to do. Notice you can add a <pose> tag inside <include> to shift models around if you need.


问:
Is it possible to track position using gyroscope and accelerometer without a magnetometer?
I'm looking for help on a project where I will be placing sensor data in 3D space using augmented reality. Most solutions I have found for finding position with an IMU involve the magnetometer, but for my implementation that will not work because I am measuring magnetic fields so the magnetometer value will definitely not be pointing towards any poles. How would I be able to calculate position?

Relevant info:

I am using four IMUs, so I could possibly filter noise by averaging their values.

I will only be measuring for a short time (15-20seconds).

The magnet being measured will be stationary, so it could possibly be used as some sort of reference point?

Any help is appreciated!
Thanks in advance!

答:
The short answer is that it's possible, but tricky.

To estimate position you integrate accelerometer readings over time to get linear velocity estimates, and then integrate the velocities to get position estimates.

The downside of this double integration is that either initial readings must be very accurate, or sophisticated smoothing / filtering algorithms must be used to compensate for errors.

Moreover, since IMU measurements are not relative to a global reference point but only to the previous system state, there is no way to avoid the unbounded (however slowly) accumulation of estimate errors over time, except by resorting to different sensors.

I recommend you refer to this article for a more complete treatment:

Kok, Manon, Jeroen D. Hol, and Thomas B. Schön. "Using inertial sensors for position and orientation estimation." arXiv preprint arXiv:1704.06053 (2017).


问:
Guidance on SBC for Visual-Based SLAM
Intro: I am a student that just started a project regarding prototyping a mobile robot that involve Indoor SLAM implementation. I am very new to the field of computer vision, SLAM and SBC (single board computer).

I am searching for advice on choices of SBC for visual ORB-SLAM implementation.

Below are the few options I came across, welcome to provide new suggestion:

Raspberry Pi : Is the computational power of Raspberry Pi able to support ORB-SLAM? If so, which model would be my best choice?

BeagleBone Black : Any comments on this SBC for ORB-SLAM implementation?

My budget for SBC is around $150

I would also like to know a rough estimate of the minimum requirement for SBC to implement ORB-SLAM.

I really appreciate any advice, resource or help I could get.

Thanks in advance.

答: Tbh ur going to need a Jetson nano at least, maybe a tx.</p>

Title: Guidance on SBC for Visual-Based SLAM


答:
As FourierFlux mentioned, the Jetson Nano is perhaps the most processing power you're going to get for $150 and under. However getting ORB-SLAM to run in it might be a challenge — there is a port but it doesn't seem to be very actively maintained.

If splurging a little more on the SBC is an option, you could get a UDOO Bolt, which is a full x86-64 SBC built around the AMD Ryzen Embedded chipset. That would enable running the stock ORB-SLAM system. It sells online for \$332.00 (Vega 3 graphics) or \$418.00 (Vega 8).

Alternatively, if you don't require running all software on the robot itself, you could get a Raspberry Pi, set it up to stream visual data to a more powerful remote machine (e.g. a desktop PC), and run ORB-SLAM there instead. This could be easily accomplished in ROS by running hardware driver nodes on the Raspberry Pi, more demanding SLAM and navigation nodes on the remote machine, and have the two sides communicate over wi-fi:

See this report for details on how this could be done.

Finally, you could try a more economical SLAM approach: a successful implementation of FastSLAM2.0 for Raspberry Pi has been reported, you could contact the authors and ask for the code, or re-implement it yourself.

Title: Guidance on SBC for Visual-Based SLAM

Body:
Intro: I am a student that just started a project regarding prototyping a mobile robot that involve Indoor SLAM implementation. I am very new to the field of computer vision, SLAM and SBC (single board computer).

I am searching for advice on choices of SBC for visual ORB-SLAM implementation.

Below are the few options I came across, welcome to provide new suggestion:

Raspberry Pi : Is the computational power of Raspberry Pi able to support ORB-SLAM? If so, which model would be my best choice?

BeagleBone Black : Any comments on this SBC for ORB-SLAM implementation?

My budget for SBC is around $150

I would also like to know a rough estimate of the minimum requirement for SBC to implement ORB-SLAM.

I really appreciate any advice, resource or help I could get.

Thanks in advance.


问:
Denavit-Hartenberg parameters for SCARA manipulator
I'm going through the textbook Robot Modeling and Control, learning about the DH convention and working through some examples.

I have an issue with the following example. Given below is an image of the problem, and the link parameter table which I tried filling out myself. I got the same answers, except I believe there should be a parameter d1 representing the link offset between frames 1 and 2. This would be analogous to the d4 parameter.

If anyone could explain why I might be wrong, or confirm that I have it right, that would be great. I hate it when it's me against the textbook lol.

Cheers.

答: You can either have $d_1 \neq 0$ or set $d_1=0$ and embed the vertical displacement in $d_3^*$.


问:
Screw Axes in the Base Frame
I'm trying to find screw axes for joint (on pic) with angle θ. It's on zero position. As I understood:

joint has an angular velocity on the Z axis, clockwise, so the sign is positive and ω=(0,0,1);

joint is located at height L along the X axis, so v=(L,0,0).

But right answer is [0,0,1,0,-L,0]. Why?

答:
If I'm understanding you correctly, you're attempting to put the position of the joint in for the translational velocity component of the screw axis. What you actually want to put in there is the velocity of a point rigidly attached to the rotating part of the joint, but currently located at the origin of the base frame,
$$
v = \begin{bmatrix} \omega_{x} \\ \omega_{y} \\ \omega_{z} \end{bmatrix} \times \begin{bmatrix} -x \\ -y \\ -z \end{bmatrix} = \begin{bmatrix} 0 \\ 0 \\ 1 \end{bmatrix} \times \begin{bmatrix} -L \\ \phantom{-}0 \\ \phantom{-}0 \end{bmatrix} = \begin{bmatrix} \phantom{-}0 \\ -L \\ \phantom{-}0 \end{bmatrix}.
$$
You can interpret
$$
\begin{bmatrix} \omega \\ v \end{bmatrix} = \begin{bmatrix} \phantom{-}0 \\ \phantom{-}0 \\ \phantom{-}1 \\ \phantom{-}0 \\ -L \\ \phantom{-}0 \end{bmatrix}
$$
as the translational velocity you would have to give an object at the origin to have it act as if it were rotating about the $z$ axis passing through $x=L, y=0$. This way of treating velocities is called the "spatial" approach, and I discuss it further in my answer here: Robotic manipulator Jacobian by product of exponentials.

Title: Screw Axes in the Base Frame