Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 3 additions & 3 deletions wiki/common-platforms/kinova-setup-and-apis.md
Original file line number Diff line number Diff line change
Expand Up @@ -44,11 +44,11 @@ The arm should be resting as in the position below:
![Kinova starting position](/assets/images/common-platforms/kinova_start.png)


It is essential that the *gripper is not blocked*, as the arm will open and close the gripper upon startup. If the arm is in a position where the gripper is blocked, move the arm gently until it reaches a *stable* position where the gripper is free to open and close.
It is essential that the **gripper is not blocked**, as the arm will open and close the gripper upon startup. If the arm is in a position where the gripper is blocked, move the arm gently until it reaches a **stable** position where the gripper is free to open and close.

Once the arm is in a safe position, check that the power supply is connected and turned on. *Localize the red e-stop button and keep it within reach at all times*. Unlock the robot by twisting the e-stop button in the same sense as the arrow on it. The button should pop out.
Once the arm is in a safe position, check that the power supply is connected and turned on. **Localize the red e-stop button and keep it within reach at all times**. Unlock the robot by twisting the e-stop button in the same sense as the arrow on it. The button should pop out.

Then press the silver button on the back of the arm until a blue LED lights up and release it. *DO NOT* press the button for more than 10 seconds, as that will factory reset the arm. The lights will then show blue and yellow during startup. *Once the gripper closes and opens and the light turns to solid green, the arm will be ready for use.*
Then press the silver button on the back of the arm until a blue LED lights up and release it. **DO NOT** press the button for more than 10 seconds, as that will factory reset the arm. The lights will then show blue and yellow during startup. **Once the gripper closes and opens and the light turns to solid green, the arm will be ready for use.**

#### Using

Expand Down
25 changes: 21 additions & 4 deletions wiki/common-platforms/ros/ros-lifecycle.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ title: ROS 2 Node Lifecycle
# and used in other parts of the site.
---
## Introduction
Many robotics platforms implement state machines as part of their functionality. ROS 2 offers a convenient way of working with state machines in the form of `managed nodes`, also called `lifecycle nodes`. These nodes can be turned on/off, configured/unconfigured, etc. In a nutshell, lifecycle nodes can be activated or deactivated based on the current state of a robot's state machine.
Many robotics platforms implement state machines as part of their functionality. ROS 2 offers a convenient way of working with state machines in the form of `managed nodes`, also called `lifecycle nodes`. These nodes can be turned on/off, configured/unconfigured, etc. In a nutshell, lifecycle nodes can be activated or deactivated based on the current state of a robot's state machine.

Before ROS 2, state machine implementations basically relied on ignoring nodes when they were not useful to the current state. While this is still possible in ROS 2, lifecycle nodes offer significant advantages from an efficiency standpoint:

Expand Down Expand Up @@ -41,14 +41,15 @@ Please note that ROS offers a lot of freedom when implementing these states (eve

Secondary states: also known as "transition states", these states serve as buffers between primary states, where the node will be doing some internal operation relating to a corresponding `transition` function. These states are:


+ `Configuring`
+ `CleaningUp`
+ `ShuttingDown`
+ `Activating`
+ `Deactivating`
+ `ErrorProcessing`

While almost all these states' functionalities and their corresponding transition functions can be easily inferred from the lifecycle diagram, `ErrorProcessing` deserves some extra explanation. As you can see from the diagram, sometimes transition states can fail, returning to the previous primary state. This is *not* the purpose of `ErrorProcessing`. The transition state will return to the original primary state when it's function fails "logically", e.g. the program has to be running for 10 minutes before the node activates, checked for inside an if-loop. The `ErrorProcessing`, on the other hand, is reached when an error is *raised*, e.g. you tried dividing something by zero.
While almost all these states' functionalities and their corresponding transition functions can be easily inferred from the lifecycle diagram, `ErrorProcessing` deserves some extra explanation. As you can see from the diagram, sometimes transition states can fail, returning to the previous primary state. This is **not** the purpose of `ErrorProcessing`. The transition state will return to the original primary state when it's function fails "logically", e.g. the program has to be running for 10 minutes before the node activates, checked for inside an if-loop. The `ErrorProcessing`, on the other hand, is reached when an error is **raised**, e.g. you tried dividing something by zero.

## Triggering Transitions

Expand All @@ -63,33 +64,39 @@ With all this in mind, changing a node state can happen in two ways: either thro
### CLI Lifecycle

For CLI commands, you can run:

```bash
ros2 lifecycle <command>
```

Start the lifecycle talker node provided with ROS:

```bash
ros2 run lifecycle lifecycle_talker
```

To get the state the node is in, run

```bash
ros2 lifecycle get /lc_talker
```

Which should return

```bash
unconfigured [1]
```

As expected. The number in brackets is the id of the node state. This is not super relevant for node states, as these ids are not really used for commands.

Much more interesting are the ids for transitions. If you run:

```bash
ros2 lifecycle list /lc_talker
```

You should get as output:

```bash
- configure [1]
Start: unconfigured
Expand All @@ -102,11 +109,13 @@ You should get as output:
These are the possible transitions from primary state `Unconfigured`, as shown in the lifecycle diagram. Note the ids here, as they will be useful when discussing services.

To change states, you should call the command `set` with the transition function name e.g.:

```bash
ros2 lifecycle set /lc_talker configure
```

Returning to the `lc_talker` terminal should reveal the messages:

```bash
[INFO] [1732664038.655707440] [lc_talker]: on_configure() is called.
[INFO] [1732664039.655992380] [lc_talker]: Lifecycle publisher is currently inactive. Messages are not published.
Expand All @@ -119,6 +128,7 @@ Returning to the `lc_talker` terminal should reveal the messages:
All these lifecycle commands are basically services.

For example, we can make a standard service call to get the current state of the node:

```bash
ros2 service call /lc_talker/get_state lifecycle_msgs/GetState
```
Expand All @@ -129,6 +139,7 @@ lifecycle_msgs.srv.GetState_Response(current_state=lifecycle_msgs.msg.State(id=2
```

See the id field? This is where they become important. For service calls requesting state transitions, you need to know the id of the transition (not to be confused with the id of the state itself). To get those, you could run, for example:

```bash
ros2 service call /lc_talker/get_available_transitions lifecycle_msgs/srv/GetAvailableTransitions
```
Expand All @@ -139,11 +150,13 @@ lifecycle_msgs.srv.GetAvailableTransitions_Response(available_transitions=[lifec
```

The output is a bit confusing (and better seen in RQt), but we can notice that the id for `activate` is 3. If we want to move to that state, a service call is also possible:

```bash
ros2 service call /lc_talker/change_state lifecycle_msgs/ChangeState "{transition: {id: 3}}"
```

This service also has a `label` field, which is not required (but highly recommended). Back in the talker terminal:

```bash
[INFO] [1732664498.641014385] [lc_talker]: Lifecycle publisher is active. Publishing: [Lifecycle HelloWorld #459]
```
Expand All @@ -152,16 +165,18 @@ When inside the code, all lifecycle changes are done through service calls. More

## In Code

You can find the lifecycle examples at the ROS demo [github](https://github.com/ros2/demos/tree/rolling/lifecycle/src). This guide will comment just a few key points on that code.
You can find the lifecycle examples at the ROS demo [github](https://github.com/ros2/demos/tree/rolling/lifecycle/src).This guide will comment just a few key points on that code.

Right at the definition of the talker node, we see:

```cpp
class LifecycleTalker : public rclcpp_lifecycle::LifecycleNode
```

Note that the node doesn't inherit from the typical `rclcpp:Node` class. Not all node capabilities are available for a lifecycle node (and vice-versa, obviously).

As for the callback functions, you can see that they have special signatures and return values:

```cpp
rclcpp_lifecycle::node_interfaces::LifecycleNodeInterface::CallbackReturn
on_configure(const rclcpp_lifecycle::State &)
Expand Down Expand Up @@ -192,7 +207,8 @@ rclcpp_lifecycle::node_interfaces::LifecycleNodeInterface::CallbackReturn

From the code, you can also see that `on_configure()` (and the other callbacks) are never explicitly defined as service callbacks. The lifecycle framework takes care of that.

The last point that should be highlighted is in `main`. Notice the node is note run as a regular node:
The last point that should be highlighted is in `main`. Notice the node is not run as a regular node:

```cpp
rclcpp::init(argc, argv);

Expand All @@ -211,6 +227,7 @@ rclcpp::shutdown();
Executors are beyond the scope of this document, but you can read more about them [here](https://docs.ros.org/en/foxy/Concepts/About-Executors.html).

Finally, as kind of a side note, you can also launch and trigger lifecycle nodes from launch files, as explained in [1]:

```python
from launch import LaunchDescription
from launch_ros.actions import LifecycleNode
Expand Down
10 changes: 5 additions & 5 deletions wiki/computing/quantum.md
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ title: Quantum Computing and the Qiskit Package
# The 'title' is automatically displayed at the top of the page
# and used in other parts of the site.
---
With the undeniable rise of quantum computers, future generations of roboticists must be versed in the functioning and applications of this technology. However, very few concise guides exist that explain quantum computing in introductory terms for a techincal audience. This article shows some basic principles of quantum computing together with the Python package Qiskit, developed by IBM.
With the undeniable rise of quantum computers, future generations of roboticists must be versed in the functioning and applications of this technology. However, very few concise guides exist that explain quantum computing in introductory terms for a technical audience. This article shows some basic principles of quantum computing together with the Python package Qiskit, developed by IBM.

## Fundamentals of Quantum Computing - Single Qubit Systems

Expand All @@ -28,7 +28,7 @@ $$

We can use the electron’s spin (or some other physical entity bound by quantum mechanics) as a means of transmitting information, therefore stepping into the world of quantum computing (QC).

Any quantum signal whose state can be written as a superposition of two binary states is a "quibt". In our example, the spin of a single electron is a qubit. The pair $\{|0\rangle, |1\rangle\}$ represents an orthonormal basis, called the computational basis, which can be used to perform measurements. These measurements allow us to access the information stored in a qubit and transform it into a classical signal, or "cbit" (classical bit). This is generally done by assigning $|0\rangle \rightarrow 0$ and $|1\rangle \rightarrow 1$.
Any quantum signal whose state can be written as a superposition of two binary states is a "qubit". In our example, the spin of a single electron is a qubit. The pair $\{|0\rangle, |1\rangle\}$ represents an orthonormal basis, called the computational basis, which can be used to perform measurements. These measurements allow us to access the information stored in a qubit and transform it into a classical signal, or "cbit" (classical bit). This is generally done by assigning $|0\rangle \rightarrow 0$ and $|1\rangle \rightarrow 1$.

Some differences in relation to classical computing already start to appear. Consider, for example, the qubit whose state is given by $|\psi\rangle = \frac{1}{\sqrt{2}}|0\rangle + \frac{1}{\sqrt{2}}|1\rangle$. If we measure this signal with respect to the computational basis, we get $Pr[|0\rangle] = Pr[|1\rangle] = \frac{1}{2}$, meaning that the same signal, when converted to a classical bit (using the equivalence previously established) will yield bit 0 50% of the time and bit 1 50% of the time. Therefore, the same signal can result in different values when measured. This property is what makes QC different than classical computing. While a classical bit can be either 0 or 1, a quantum bit exists as a whole range of superpositions, and its measured value is probabilistic.

Expand All @@ -54,7 +54,7 @@ Back to the technical bit. We previously mentioned the computational basis $\{|0

There are several ways to represent a single qubit. One of them is the vector representation, which is particularly useful when we wish to represent operators/gates as matrices. In this representation, a state such is written as $|\psi\rangle = \begin{bmatrix} \alpha \\ \beta \end{bmatrix}$. Henceforth, whenever a vector notation is used, we'll assume it is with respect to the computational basis.

Another representation of a single qubit system relates to the concepts of global phase and relative phase. Two qubit states $|\psi\rangle$ and $|\psi'\rangle$ are considered equivalent ($|\psi\rangle \sim |\psi'\rangle$) if there exists a value $\alpha \in [0, 2\pi)$ such that $|\psi\rangle = e^{i \alpha} |\psi'\rangle$. The angle $\alpha$ is called the global phase of the state. By manipulating the global phase of the state, it is possible to see that any qubit state can be written as $|\psi\rangle = \begin{bmatrix} \cos{\frac{\theta}{2}} \\ e^{i\varphi} \sin{\frac{\theta}{2}}\end{bmatrix}$, with $\theta \in [0, \pi]$ and $\varphi \in [0, 2\pi)$. The angle $\varphi$ is called the relative phase. The angle pair $(\theta, \varphi)$ can be used to represent the qubit using the so-called "Bloch sphere", which is shown below. In the Bloch sphere, we represent the state $|\psi\rangle$ as a unit vector from the origin, with $\theta$ being its polar angle and $\varphi$ its azimuth angle. Another feature of the Bloch sphere is that it maps the special states previosuly described to key points on the sphere's surface.
Another representation of a single qubit system relates to the concepts of global phase and relative phase. Two qubit states $|\psi\rangle$ and $|\psi'\rangle$ are considered equivalent ($|\psi\rangle \sim |\psi'\rangle$) if there exists a value $\alpha \in [0, 2\pi)$ such that $|\psi\rangle = e^{i \alpha} |\psi'\rangle$. The angle $\alpha$ is called the global phase of the state. By manipulating the global phase of the state, it is possible to see that any qubit state can be written as $|\psi\rangle = \begin{bmatrix} \cos{\frac{\theta}{2}} \\ e^{i\varphi} \sin{\frac{\theta}{2}}\end{bmatrix}$, with $\theta \in [0, \pi]$ and $\varphi \in [0, 2\pi)$. The angle $\varphi$ is called the relative phase. The angle pair $(\theta, \varphi)$ can be used to represent the qubit using the so-called "Bloch sphere", which is shown below. In the Bloch sphere, we represent the state $|\psi\rangle$ as a unit vector from the origin, with $\theta$ being its polar angle and $\varphi$ its azimuth angle. Another feature of the Bloch sphere is that it maps the special states previously described to key points on the sphere's surface.

![Representing a state on the Bloch sphere](/assets/images/computing/bloch.png)

Expand Down Expand Up @@ -153,7 +153,7 @@ As a general formula for the Bell states, we can write $|\Psi^{ij}\rangle = \fra

## Operators and Quantum Ports

Operators will be defined as transformations from the state space of a quantum system to itself \cite{rieffel2011quantum}. Not all operators imaginable are permissible, for they must satisfy the rules of quantum mechanics. Namely, the operators, once defined in their vector spaces, need to satisfy the requirements of linearity, for the principle of superposition to hold, and the preservation of the inner product, so that no contradictions arise in terms of measurement. In these equations, $U$ is an operator and $U^\dag$ means the complex conjugate transpose of $U$. Operators can be represented as both matrices or bra-ket entities.
Operators will be defined as transformations from the state space of a quantum system to itself [1]. Not all operators imaginable are permissible, for they must satisfy the rules of quantum mechanics. Namely, the operators, once defined in their vector spaces, need to satisfy the requirements of linearity, for the principle of superposition to hold, and the preservation of the inner product, so that no contradictions arise in terms of measurement. In these equations, $U$ is an operator and $U^\dag$ means the complex conjugate transpose of $U$. Operators can be represented as both matrices or bra-ket entities.

Linearity:

Expand Down Expand Up @@ -234,7 +234,7 @@ Gates can be combined into circuits. The circuits shown in this work, such as th
1. Information flows from left to right;
2. Qubit registers, which are represented by single lines, are numbered, and the higher the value, the more signification the qubit;
3. Double lines represent classical bits, It is possible to have either many double lines, each one representing a bit, or a single double line representing a bit string;
4. Measurements, which are always done against the computational basis, take a 1-qubit state to a classical bit in accordance to the encoding in section \ref{sec:single_qubit}. If measuring into a bit string, significance is preserved;
4. Measurements, which are always done against the computational basis, take a 1-qubit state to a classical bit in accordance to the encoding in the section on Single Qubit Systems. If measuring into a bit string, significance is preserved;
5. Gates are represented by squares, with the operator involved represented by letters.


Expand Down
Loading
Loading