Controller API reference
Controller- Base API for all controller types
MotorController- Motor controller API
CounterTimerController- Counter/Timer controller API
ZeroDController- 0D controller API
PseudoMotorController- PseudoMotor controller API
PseudoCounterController- PseudoCounter controller API
TriggerGateController- Trigger/Gate controller API
IORegisterController- IORegister controller API
Data Type definition
When writing a new controller you may need to specify extra attributes (per
controller or/and per axis) as well as extra properties. This chapter describes
how to describe the data type for each of this additional members.
Controller data type definition has the following equivalences. This means you
can use any of the given possibilities to describe a field data type. The
possibilities are ordered by preference (example: usage of int is
preferred to “int” or “PyTango.DevLong”):
- for 0D data types:
integer:
int|DataType.Integer| “int” | “integer” | “long” |long| [ “PyTango.” ] “DevLong”double:
float|DataType.Double| “double” | “float” | [ “PyTango.” ] “DevDouble”string:
str|DataType.String| “str” | “string” | [ “PyTango.” ] “DevString”boolean:
bool|DataType.Boolean| “bool” | “boolean” | [ “PyTango.” ] “DevBoolean”
- for 1D data types:
integer: (
int,) | (DataType.Integer,) | (“int”,) | (“integer”,) | (long,) | (“long”,) | [ “PyTango.” ] “DevVarLongArray” | ([ “PyTango.” ] “DevLong”,)double: (
float,) | (DataType.Double,) | (“double”,) | (“float”,) | [ “PyTango.” ] “DevVarDoubleArray” | ([ “PyTango.” ] “DevDouble”,)string: (
str,) | (DataType.String,) | (“str”,) | (“string”,) | [ “PyTango.” ] “DevVarStringArray” | ([ “PyTango.” ] “DevString”,)boolean: (
bool,) | (DataType.Boolean,) | (“bool”,) | (“boolean”,) | [ “PyTango.” ] “DevVarBooleanArray” | ([ “PyTango.” ] “DevBoolean”,)
Deprecated since version 1.0: [ “PyTango.” ] “Dev”<concrete type string> types are considered deprecated.
Note
when string, types are case insensitive. This means “long” is the same as “LONG”
Here is an example on how to define extra attributes per axis:
EncoderSource: a scalar r/w string
ReflectionMatrix: a 2D readable float with customized getter method
from sardana import State, DataAccess
from sardana.pool.controller import MotorController, \
Type, Description, DefaultValue, Access, FGet, FSet
class MyMotorCtrl(MotorController):
axis_attributes = \
{
'EncoderSource' : { Type : str,
Description : 'motor encoder source', },
'ReflectionMatrix' : { Type : ( (float,), ),
Access : DataAccess.ReadOnly,
FGet : 'getReflectionMatrix', },
}
def getAxisExtraPar(self, axis, name):
name = name.lower()
if name == 'encodersource':
return self._encodersource[axis]
def setAxisPar(self, axis, name, value):
name = name.lower()
if name == 'encodersource':
self._encodersource[axis] = value
def getReflectionMatrix(self, axis):
return ( (1.0, 0.0), (0.0, 1.0) )
Custom command definition
A controller may add Tango commands to its element devices, via
axis_commands, and to the controller device itself, via
ctrl_commands. Both are a list of tuple,
one tuple per command, with the following positional fields:
pos. |
field |
Mandatory |
Meaning |
Default |
|---|---|---|---|---|
1 |
|
Yes |
controller method to call |
— |
2 |
|
No |
Tango input data type |
|
3 |
|
No |
Tango input data format |
|
4 |
|
No |
input documentation |
|
5 |
|
No |
Tango output data type |
|
6 |
|
No |
Tango output data format |
|
7 |
|
No |
output documentation |
|
8 |
|
No |
Tango display level |
|
9 |
|
No |
run in the green mode executor |
|
A tuple may be truncated after any field; omitted fields take their default.
("MyCommand",) is therefore a valid declaration of a command taking and
returning nothing. Passing None for display_level is equivalent to
omitting it.
The method named by fname is looked up on the controller instance. For
axis_commands the axis number is bound as the method’s first
argument, so the signature is (self, axis), or (self, axis, value) when
dtype_in is not DevVoid; the Tango command itself takes only the user
argument. For ctrl_commands no axis is bound, so the
signature is (self) or (self, value).
axis_commands applies to every axis of the controller.
To give different axes different commands, override
GetAxisCommands(): it is called once per axis, with that axis
number, and the list it returns is the one used for that axis. Its default
implementation returns a copy of axis_commands.
The command set of a device is built once, when the dynamic Tango interface of
that device is created. A change in what GetAxisCommands()
returns therefore requires a restart of the Pool server; the Tango Init
command and a controller library reload do not rebuild it.
Note
Custom commands require PyTango >= 10.0; below that version no command
is created. cmd_green_mode requires PyTango >= 10.1; on PyTango 10.0
it is forced to False. In both cases a RuntimeWarning is issued
and the rest of the device is unaffected. Sardana’s own requirement is
PyTango >= 9.2.5, so this is not guaranteed by installing Sardana.
See also
Custom commands for a worked example, and Per-axis custom commands for the per-axis override.