Skip to content

Commit

Permalink
Merge pull request #376 from tinymovr/develop
Browse files Browse the repository at this point in the history
Studio and Docs fixes
  • Loading branch information
yconst authored Dec 8, 2024
2 parents 32ca0ae + 45b7232 commit 22fb7f7
Show file tree
Hide file tree
Showing 10 changed files with 84 additions and 48 deletions.
2 changes: 2 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -7,3 +7,5 @@ docs/_build/
*.log
*.state.json
Tinymovr.code-workspace
.aider*
.env
20 changes: 10 additions & 10 deletions docs/features/features.rst
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ Before using the planner, the desired acceleration, deceleration and max velocit
tm1.traj_planner.max_decel = {max_deceleration} # ticks/sec^2
tm1.traj_planner.max_vel = {mac_velocity} # ticks/sec
Once you set the desired acceleration and deceleration parameters, they do not need to be re-set. The parameters can be saved in NVRAM using ``tmx.save_config()``.
Once you set the desired acceleration and deceleration parameters, they do not need to be re-set. The parameters can be saved in NVRAM using ``tm1.save_config()``.

Once the parameters are set, you can execute a plan to a target position:

Expand Down Expand Up @@ -95,14 +95,14 @@ Because the homing planner relies on mechanical resistance of the structure, it

There are six parameters in total that control the homing behavior:

* ``tmx.homing.velocity``: The velocity at which the motor performs homing
* ``tmx.homing.max_homing_t``: The maximum time the motor is allowed to travel before aborting homing
* ``tmx.homing.retract_dist``: The retraction distance the motor travels after the endstop has been found
* ``tmx.homing.stall_detect.velocity``: The velocity below which (and together with ``stall_detect.delta_pos``) stall detection mode is triggered
* ``tmx.homing.stall_detect.delta_pos``: The position error above which (and together with ``stall_detect.velocity``) stall detection mode is triggered
* ``tmx.homing.stall_detect.t``: The time to remain in stall detection mode before the motor is considered stalled
* ``tm1.homing.velocity``: The velocity at which the motor performs homing
* ``tm1.homing.max_homing_t``: The maximum time the motor is allowed to travel before aborting homing
* ``tm1.homing.retract_dist``: The retraction distance the motor travels after the endstop has been found
* ``tm1.homing.stall_detect.velocity``: The velocity below which (and together with ``stall_detect.delta_pos``) stall detection mode is triggered
* ``tm1.homing.stall_detect.delta_pos``: The position error above which (and together with ``stall_detect.velocity``) stall detection mode is triggered
* ``tm1.homing.stall_detect.t``: The time to remain in stall detection mode before the motor is considered stalled

In addition to the above, the phase current while the motor is stopped, until ``stall_detect.t`` time passes is the maximum allowed phase current, as defined in ``tmx.controller.current.Iq_limit``. It is advisable to set this value so that mechanical damage or fatigue is avoided.
In addition to the above, the phase current while the motor is stopped, until ``stall_detect.t`` time passes is the maximum allowed phase current, as defined in ``tm1.controller.current.Iq_limit``. It is advisable to set this value so that mechanical damage or fatigue is avoided.

Operation
*********
Expand All @@ -125,7 +125,7 @@ FOC decouples the torque-producing and magnetizing currents by aligning the stat

Two parameters control flux braking:

1. ``tmx.controller.current.max_Ibus_regen``: The maximum current (in amperes) allowed to be fed back to the power source before flux braking activates. By adjusting this value, you can control the regenerative braking threshold and determine when flux braking should take effect.
1. ``tm1.controller.current.max_Ibus_regen``: The maximum current (in amperes) allowed to be fed back to the power source before flux braking activates. By adjusting this value, you can control the regenerative braking threshold and determine when flux braking should take effect.

2. ``tmx.controller.current.max_Ibrake``: The maximum current (in amperes) allowed to be dumped to the motor windings during flux braking. By setting this value to zero, you can deactivate flux braking. Adjusting this parameter allows you to manage the braking torque and the heat generated during the braking process.
2. ``tm1.controller.current.max_Ibrake``: The maximum current (in amperes) allowed to be dumped to the motor windings during flux braking. By setting this value to zero, you can deactivate flux braking. Adjusting this parameter allows you to manage the braking torque and the heat generated during the braking process.

4 changes: 2 additions & 2 deletions docs/hardware/gimbal.rst
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,7 @@ Example
>>>tm1.motor.L = 2e-3
>>>tm1.motor.I_cal = 0.5
>>>tmx.set_motor_RL(5, 0.002)
>>>tm1.set_motor_RL(5, 0.002)
This specifies a motor with 5 Ohms resistance, 2 Millihenries inductance and 0.5Amps calibration current.
Alternatuvely, using the units interface:
Expand Down Expand Up @@ -99,7 +99,7 @@ Ensure the values above are correct. You can now calibrate the motor:
>>>tm1.controller.calibrate()
Because the motor is set as gimbal, calibration will bypass resistance and inductance measurement, and will only calculate pole pairs, offset and direction. After calibration `tmx.motor.calibrated` should have a value of True:
Because the motor is set as gimbal, calibration will bypass resistance and inductance measurement, and will only calculate pole pairs, offset and direction. After calibration `tm1.motor.calibrated` should have a value of True:

|gui| Calibrate Motor

Expand Down
4 changes: 4 additions & 0 deletions docs/index.rst
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,10 @@ Welcome to Tinymovr documentation!
.. note::
This is the documentation for the latest stable version of the Tinymovr Firmware and Studio app. For the legacy 0.x.x documentation, check out the [legacy docs](https://tinymovr.readthedocs.io/en/attic-legacy/).

.. note::
In all examples, the first intance of the found motor controller is used, namely `tm1`. If working with subsequent instances, please replace with the correct index, e.g. instead of `tm1` use `tm2`, `tm3` etc.


.. toctree::
:maxdepth: 2
:caption: Contents:
Expand Down
8 changes: 4 additions & 4 deletions docs/quickstart.rst
Original file line number Diff line number Diff line change
Expand Up @@ -64,14 +64,14 @@ The Tinymovr Studio GUI offers an overview of the device internals as a tree str

The Tinymovr Servo Kit motor and encoder are already calibrated. If you have your own setup, or if you experience problems with prior calibration, you'll need to go through the following brief calibration procedure.

In Tinymovr Studio, navigate to `tmx->controller`. Press the button with the arrow next to the `calibrate` label. Note that after pressing this button, the motor will spin. Ensure the rotor is free of obstructions or loads, and the motor is firmly fixed.
In Tinymovr Studio, navigate to `tm1->controller`. Press the button with the arrow next to the `calibrate` label. Note that after pressing this button, the motor will spin. Ensure the rotor is free of obstructions or loads, and the motor is firmly fixed.

Follow the on-screen prompts. The motor will produce an audible beep and rotate in one direction.
Your Tinymovr is now ready for operation. Navigate to `tmx->motor`. This will reveal identified motor parameters, namely: phase resistance (R), phase inductance (L) and number of pole pairs.
Your Tinymovr is now ready for operation. Navigate to `tm1->motor`. This will reveal identified motor parameters, namely: phase resistance (R), phase inductance (L) and number of pole pairs.

Testing Position Control using the Studio GUI
#############################################

Navigate back to `tmx->controller`. Press the button with the arrow next to the `position_mode` label. Note that after pressing the button, the motor will hold position and may spin. The motor should now be actively holding it's position. Try moving it by hand and you should feel resistance.
Navigate back to `tm1->controller`. Press the button with the arrow next to the `position_mode` label. Note that after pressing the button, the motor will hold position and may spin. The motor should now be actively holding it's position. Try moving it by hand and you should feel resistance.

To command a new position, navigate to `tmx->controller->position`, and double-click on the value next to the `setpoint` label. This value is expressed in ticks, a unit that denotes 1/8192 of the circle. Type in a new position followed by Enter. The motor should jump to the commanded position.
To command a new position, navigate to `tm1->controller->position`, and double-click on the value next to the `setpoint` label. This value is expressed in ticks, a unit that denotes 1/8192 of the circle. Type in a new position followed by Enter. The motor should jump to the commanded position.
60 changes: 30 additions & 30 deletions docs/sensors/sensors.rst
Original file line number Diff line number Diff line change
Expand Up @@ -172,7 +172,7 @@ Tinymovr makes use of the XF1 library, which has been developed for this purpose
Sensor Configuration
********************

The sensor configuration consists of two steps. The first step concerns the setup of the individual sensors being used, and the second step concerns sensor selection. The corresponding sections in the device spec are `tmx.sensors.setup`, and `tmx.sensors.select`.
The sensor configuration consists of two steps. The first step concerns the setup of the individual sensors being used, and the second step concerns sensor selection. The corresponding sections in the device spec are `tm1.sensors.setup`, and `tm1.sensors.select`.

Sensor Setup
============
Expand Down Expand Up @@ -220,36 +220,36 @@ Then, configure the external sensor type as follows:

.. code-block:: python
tmx.sensors.setup.external_spi.type = tmx.sensors.setup.external_spi.type.AS5047
tm1.sensors.setup.external_spi.type = tm1.sensors.setup.external_spi.type.AS5047
Then select the `EXTERNAL_SPI` sensor for each of the position and commutation sensors:

.. code-block:: python
tmx.sensors.select.commutation_sensor.connection = tmx.sensors.select.commutation_sensor.connection.EXTERNAL_SPI
tmx.sensors.select.position_sensor.connection = tmx.sensors.select.position_sensor.connection.EXTERNAL_SPI
tm1.sensors.select.commutation_sensor.connection = tm1.sensors.select.commutation_sensor.connection.EXTERNAL_SPI
tm1.sensors.select.position_sensor.connection = tm1.sensors.select.position_sensor.connection.EXTERNAL_SPI
At this point, you are ready to perform motor/sensor calibration. This will measure the R and L values of the motor, derive frame transforms and eccentricity compensation tables.

.. code-block:: python
tmx.controller.calibrate()
tm1.controller.calibrate()
After calibration finishes, you should be able to control the motor:

.. code-block:: python
tmx.controller.velocity_mode()
tmx.controller.velocity.setpoint = 8192 # 60 rpm
tm1.controller.velocity_mode()
tm1.controller.velocity.setpoint = 8192 # 60 rpm
The motor should now move at a constant velocity.

Once you have determined that the motor behaves as expected, set to idle and perform another config save to persist the configuration:

.. code-block:: python
tmx.controller.idle()
tmx.save_config()
tm1.controller.idle()
tm1.save_config()
External AMT22 Sensor for Positioning and Onboard MA702/704 for Commutation
Expand All @@ -264,36 +264,36 @@ Then, configure the external sensor type as follows:

.. code-block:: python
tmx.sensors.setup.external_spi.type = tmx.sensors.setup.external_spi.type.AMT22
tm1.sensors.setup.external_spi.type = tm1.sensors.setup.external_spi.type.AMT22
Then select the `EXTERNAL_SPI` sensor for each of the position and commutation sensors:

.. code-block:: python
tmx.sensors.select.commutation_sensor.connection = tmx.sensors.select.commutation_sensor.connection.ONBOARD
tmx.sensors.select.position_sensor.connection = tmx.sensors.select.position_sensor.connection.EXTERNAL_SPI
tm1.sensors.select.commutation_sensor.connection = tm1.sensors.select.commutation_sensor.connection.ONBOARD
tm1.sensors.select.position_sensor.connection = tm1.sensors.select.position_sensor.connection.EXTERNAL_SPI
At this point, you are ready to perform motor/sensor calibration. This will measure the R and L values of the motor, derive frame transforms and eccentricity compensation tables.

.. code-block:: python
tmx.controller.calibrate()
tm1.controller.calibrate()
After calibration finishes, you should be able to control the motor:

.. code-block:: python
tmx.controller.velocity_mode()
tmx.controller.velocity.setpoint = 8192 # 60 rpm
tm1.controller.velocity_mode()
tm1.controller.velocity.setpoint = 8192 # 60 rpm
The motor should now move at a constant velocity.

Once you have determined that the motor behaves as expected, set to idle and perform another config save to persist the configuration:

.. code-block:: python
tmx.controller.idle()
tmx.save_config()
tm1.controller.idle()
tm1.save_config()
Hall Effect Sensor
Expand All @@ -308,18 +308,18 @@ Then select the `HALL` sensor for each of the position and commutation sensors,

.. code-block:: python
tmx.sensors.select.commutation_sensor.connection = HALL
tmx.sensors.select.position_sensor.connection = HALL
tmx.sensors.select.commutation_sensor.bandwidth = 200
tmx.sensors.select.position_sensor.bandwidth = 20
tm1.sensors.select.commutation_sensor.connection = HALL
tm1.sensors.select.position_sensor.connection = HALL
tm1.sensors.select.commutation_sensor.bandwidth = 200
tm1.sensors.select.position_sensor.bandwidth = 20
This sets the type to Hall effect sensor, and each of the commutation and position observer bandwidths. The commutation observer is set to a higher bandwidth value, in order to ensure that commutation is accurate and a runoff scenario is avoided.

Next, you need to set the motor pole pairs:

.. code-block:: python
tmx.motor.pole_pairs = 15
tm1.motor.pole_pairs = 15
Next comes tuning of gains. Gains are determined on the tick count of a full mechanical turn of the motor. When using the an absolute sensor, the tick count is fixed to 8192 ticks (the resolution can be higher as the tick count is a floating point value).

Expand All @@ -328,38 +328,38 @@ Because of this it is possible that the gains need to be updated. Below we prese

.. code-block:: python
tmx.controller.position.p_gain = 5
tmx.controller.velocity.p_gain = 0.00001
tm1.controller.position.p_gain = 5
tm1.controller.velocity.p_gain = 0.00001
For your own motor, you need to determine these experimentally. Take a look at :ref:`Tuning` for more information.

At this point, you are ready to perform motor/sensor calibration. This will measure the R and L values of the motor, as well as the hall effect sensor sequence.

.. code-block:: python
tmx.controller.calibrate()
tm1.controller.calibrate()
After calibration finishes, you should be able to control the motor. Note that the default reference frame for the hall sensors maps to 8192 ticks per motor electrical cycle. You can change this by modifying the user frame multiplier:

.. code-block:: python
tmx.sensors.user_frame.multiplier = 1
tm1.sensors.user_frame.multiplier = 1
Go ahead and enter velocity control mode, and set a setpoint:

.. code-block:: python
tmx.controller.velocity_mode()
tmx.controller.velocity.setpoint = 80000 # around 60 rpm for a 15 pp motor
tm1.controller.velocity_mode()
tm1.controller.velocity.setpoint = 80000 # around 60 rpm for a 15 pp motor
The motor should now move at a constant velocity.

Once you have determined that the motor behaves as expected, set to idle and perform another config save to persist the configuration:

.. code-block:: python
tmx.controller.idle()
tmx.save_config()
tm1.controller.idle()
tm1.save_config()
Observer Bandwidth
Expand Down
24 changes: 24 additions & 0 deletions docs/studio/usage.rst
Original file line number Diff line number Diff line change
Expand Up @@ -198,6 +198,30 @@ Example:
By default, Tinymovr Studio will use slcan as the interface, and will search for CANAble/CANtact-type devices with slcan firmware. Such is the CANine adapter supplied with Tinymovr Servo Kits.


``--bitrate=<chan>``
====================

Specifies a bitrate in baud.

Example:

|gui|

.. code-block:: console
tinymovr --bus=socketcan --bitrate=1000000
|cli|

.. code-block:: console
tinymovr_cli --bus=socketcan --bitrate=1000000
By default, Tinymovr Studio will use 1000000 as bitrate.
We tested with 1000000, 500000 and 250000 baud.



Units
#####

Expand Down
2 changes: 1 addition & 1 deletion docs/upgrade/upgrade.rst
Original file line number Diff line number Diff line change
Expand Up @@ -91,7 +91,7 @@ Flashing the Firmware

.. code-block:: python
tmx.enter_dfu()
tm1.enter_dfu()
Then exit the CLI by typing ``exit``.

Expand Down
5 changes: 5 additions & 0 deletions studio/Python/tests/test_board.py
Original file line number Diff line number Diff line change
Expand Up @@ -98,6 +98,11 @@ def test_d_position_control(self):
self.check_state(0)
self.tm.controller.current.Iq_limit = 5
self.try_calibrate()
if hw_rev > 20:
self.tm.controller.position.p_gain = 5
self.tm.controller.velocity.p_gain = 2e-5
self.tm.controller.velocity.i_gain = 0

self.tm.controller.position_mode()
self.check_state(2)

Expand Down
3 changes: 2 additions & 1 deletion studio/Python/tinymovr/bus_router.py
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@
from enum import Enum
from threading import Thread, Lock
from tinymovr.bus_manager import BusManager
from logging import Logger


bus_router = None
Expand Down Expand Up @@ -86,7 +87,7 @@ def send(self, frame):
self.bus_manager.send(frame)


def init_router(bus_class, bus_params, logger, timeout=0.1):
def init_router(bus_class, bus_params, logger=Logger("tinymovr"), timeout=0.1):
"""
Initializes a bus router using a python-can bus instance
"""
Expand Down

0 comments on commit 22fb7f7

Please sign in to comment.