-
Notifications
You must be signed in to change notification settings - Fork 69
SysEx Configuration
This document will explain in depth OpenDeck System Exclusive protocol and how to configure the board using System Exclusive commands.
Note 1: numbers written like this represent hex notation
Note 2: this documentation uses official OpenDeck board for examples of values
Note 3: this documentation assumes the latest available firmware
Note 4: current firmware uses the two-byte protocol variant only.
- Message structure
- Message types
- Configuration examples
System Exclusive (in further text: SysEx) is a special part of MIDI protocol. All MIDI messages except SysEx have defined length and each byte has specific meaning. In SysEx messages, the only defined bytes are START (F0) and END (F7). Any bytes in-between START and END are arbitrary and meaning of message depends purely on implementation. This is the reason most MIDI controllers which implement some kind of user-configuration use custom SysEx messages to configure the device in question. OpenDeck also implements custom protocol based on SysEx messages for its configuration. SysEx messages on OpenDeck differ from type to type, however, they all have several bytes in common. Those bytes are START, M_ID_0, M_ID_1, M_ID_2, MESSAGE_STATUS, MESSAGE_PART and END. This applies to both requests and responses. Below is a list of all possible SysEx bytes used on OpenDeck:
STARTM_ID_0M_ID_1M_ID_2MESSAGE_STATUSMESSAGE_PARTWISHSPECIAL_REQUEST_IDAMOUNTBLOCKSECTIONINDEX*NEW_VALUE*STOP
Note: current firmware uses two bytes for INDEX and NEW_VALUE values.
Each response to a request is a copy of the request with a changed status byte and appended data before the last byte if needed.
START byte always has value F0 and denotes start of SysEx message.
Although not strictly required, most MIDI manufacturers which implement its own SysEx protocol use up to three manufacturer bytes. Manufacturer bytes ensure that SysEx message doesn't end up on wrong MIDI controller. OpenDeck uses three bytes for manufacturer ID:
-
M_ID_0value:00 -
M_ID_1value:53 -
M_ID_2value:43
If manufacturer bytes aren't specified (or they're wrong), OpenDeck won't respond. Each message must contain those bytes after START byte.
When requesting data, MESSAGE_STATUS always needs to be set to 0. When receiving response, that byte will change into 1 if request was valid, or a specific error code if request was invalid. One exception is a successful BACKUP response: in that case the response is intentionally reformatted to look like a SET request, so MESSAGE_STATUS remains 0. See here.
SysEx buffer takes a relatively large amount of space in firmware. In order to reduce buffer size, messages are limited to a fixed size. OpenDeck limits messages to 32 values. START, M_ID_0, M_ID_1, M_ID_2, MESSAGE_STATUS, MESSAGE_PART and END bytes do not count in. For instance, if a section has 64 parameters, and OpenDeck is configured to use 32 parameters per message, to access parameters 32-63 (numbering starts from 0), MESSAGE_PART byte needs to be set to 1 (parts start from 0) but only for following requests:
GET ALLSET ALLBACKUP ALL
If this byte is set to anything other than 0 when AMOUNT byte is SINGLE, even if the section has more parts, part error will be thrown. In single mode any parameter index can be specified.
For example, if user wants to retrieve all values for section which has 64 parameters, GET ALL request will return only values for parameters 0-31 if the message part is set to 0. If the byte is set to 1, it will return values for parameters 32-63. Same logic applies for backup and set requests.
Special MESSAGE_PART value can be set to 7F when WISH byte is GET or BACKUP. In those cases, board will return values for all message parts. If the MESSAGE_PART is set to 7E, board will also return values for all parts, but one additional ACK message will be sent to indicate the end of retrieval. These special MESSAGE_PART values are not valid for SET ALL.
This byte is used only for special messages to perform specific task. Not present in standard requests and responses. See here.
There are three options available:
GETSETBACKUP
WISH value: 0
Used to retrieve one or all parameters from the board.
WISH value: 1
Used to set one or all parameters to new value.
WISH value: 2
This option is used when user wants to backup selected parameters. When this request is sent to board, board doesn't send usual response, but formats it to look like SET command instead. Using backup command it's easy to create a backup script.
After GET or SET command, AMOUNT byte is needed. AMOUNT determines amount of parameters user wants to manipulate. There are two choices for AMOUNT byte:
SINGLEALL
AMOUNT value: 0
Used to get, set or backup single parameter within block section.
AMOUNT value: 1
Used to get, set or backup all parameters within block section.
BLOCK, SECTION, INDEX and NEW_VALUE bytes are used to manipulate specific parameter (or parameters).
End byte denotes end of SysEx message and its value is always F7.
There are four types of SysEx messages on OpenDeck:
- Special requests
- Configuration messages
- Component info messages
- Status messages
Special requests are split into two groups:
- Predefined requests
- Custom requests
Predefined requests are part of the core protocol, while custom requests are user-defined and can differ depending on implementation. Both groups have the same message structure:
STARTM_ID_0M_ID_1M_ID_2MESSAGE_STATUSMESSAGE_PARTSPECIAL_REQUEST_IDEND
Values returned as a result of special requests are hardcoded and cannot be changed during runtime (no SET or BACKUP is available).
There are four predefined requests:
- Handshake request
- Value size request
- Values per message request
- Connection closure request
SPECIAL_REQUEST_ID value : 1
Before attempting to use SysEx messages to configure OpenDeck board, this message must be sent to board. Handshake request enables SysEx configuration.
Current firmware accepts SysEx configuration through enabled configuration interfaces. Depending on the target, this can be USB MIDI, WebSockets, or both.
- Request:
F0 00 53 43 00 00 01 F7 - Response:
F0 00 53 43 01 00 01 F7
The only changed byte in response is status byte, which is set to 1, meaning that the request is valid and response can be sent without errors.
After the board responds to handshake request, user can continue with board configuration. While in SysEx configuration mode, board sends additional component IDs (see here) which aren't necessary during the normal operation, but are needed to identify component sending MIDI input. To reduce amount of data that is being sent, it is recommended to disable SysEx configuration after configuration is finished. To close SysEx connection, following message should be used:
- Request:
F0 00 53 43 00 00 00 F7 - Response:
F0 00 53 43 01 00 00 F7
SPECIAL_REQUEST_ID value : 2
Current firmware always uses two-byte values for INDEX and NEW_VALUE. Maximum value is 16383 (14-bit maximum), and this request currently always returns 2.
- Request:
F0 00 53 43 00 00 02 F7 - Response:
F0 00 53 43 01 00 02 00 02 F7
Returned data for each request starts after last request byte. In this case, there is only one value to be returned: 2, composed of two bytes.
The following decoding technique should be used:
- Wanted value: 10000
- SysEx bytes:
4E 10
4E is higher byte and 10 is lower byte. Below is C++ code example which can be used to split the 14-bit value into two 7-bit ones:
void split14bit(uint16_t value, uint8_t& high, uint8_t& low)
{
uint8_t newHigh = (value >> 8) & 0xFF;
uint8_t newLow = value & 0xFF;
newHigh = (newHigh << 1) & 0x7F;
if ((newLow >> 7) & 0x01)
newHigh |= 0x01;
else
newHigh &= ~0x01;
newLow &= 0x7F;
high = newHigh;
low = newLow;
}
C++ code below can be used to decode two 7-bit values into single 14-bit value:
void mergeTo14bit(uint16_t& value, uint8_t high, uint8_t low)
{
if (high & 0x01)
low |= (1 << 7);
else
low &= ~(1 << 7);
high >>= 1;
uint16_t joined;
joined = high;
joined <<= 8;
joined |= low;
value = joined;
}
SPECIAL_REQUEST_ID value : 3
Used to retrieve maximum number of parameter values per single SysEx message.
- Request:
F0 00 53 43 00 00 03 F7 - Response:
F0 00 53 43 01 00 03 00 20 F7
Response returns 32 (20 in hex notation) in this case.
Custom requests on OpenDeck board are:
- Firmware version
- Hardware UID
- Serial number
- Firmware version and hardware UID
- Number of supported components
- Reboot
- Bootloader mode
- Factory reset
- Number of supported presets
- Bootloader support
- Full backup
- Restore start
- Restore end
SPECIAL_REQUEST_ID value : 56
This request will return firmware version currently running on board using three bytes. First byte is major version, second byte is minor version and third byte is revision.
- Request:
F0 00 53 43 00 00 56 F7 - Response:
F0 00 53 43 01 00 56 00 05 00 00 00 00 F7
When converted to decimal system, firmware version in this example reads as v5.0.0.
SPECIAL_REQUEST_ID value : 42
This request will return UID of OpenDeck board. UID is composed of four bytes and it's used to uniquely identify board variant.
Unlike other custom requests, this one can be used even if SysEx handshake hasn't been performed yet.
- Request:
F0 00 53 43 00 00 42 F7 - Response:
F0 00 53 43 01 00 42 high_byte1 low_byte1 high_byte2 low_byte2 high_byte3 low_byte3 high_byte4 low_byte4 F7
Response indicates that current board variant is STM32F4 Discovery.
SPECIAL_REQUEST_ID value : 53
This request returns the MCU hardware serial number as raw bytes. Each returned byte is encoded as one two-byte SysEx value. The host should decode each value and treat the lower 8 bits as one serial-number byte.
The serial number is used by the official configurator to verify and unlock configuration access on firmware which requires it. Unlike most custom requests, this request can be used even if SysEx handshake hasn't been performed yet.
- Request:
F0 00 53 43 00 00 53 F7 - Response:
F0 00 53 43 01 00 53 byte0_high byte0_low byte1_high byte1_low ... F7
SPECIAL_REQUEST_ID value : 43
This request will return firmware version and hardware UID in one response.
- Request:
F0 00 53 43 00 00 43 F7 - Response:
F0 00 53 43 01 00 43 00 05 00 00 00 00 00 2B 00 13 00 44 00 7A F7
Response indicates firmware version v5.0.0 and STM32F4 Discovery board.
SPECIAL_REQUEST_ID value : 4D
This request is used to find out maximum number of supported components on OpenDeck board.
- Request:
F0 00 53 43 00 00 4D F7 - Response:
F0 00 53 43 01 00 4D 00 19 00 08 00 08 00 10 00 00 F7
Returned values start after 6th byte, in following order:
- Maximum number of switches - This represents the sum of digital inputs, analog inputs that can be used as switches, and touchscreen switches.
- Maximum number of encoders
- Maximum number of analog inputs
- Maximum number of outputs - This is the sum of physical outputs and touchscreen components that can be used as output indicators.
- Maximum number of touchscreen components
SPECIAL_REQUEST_ID value : 7F
This request schedules an application reboot. Current firmware sends the ACK response first, then performs the reboot 1000 ms later.
- Request:
F0 00 53 43 00 00 7F F7 - Response:
F0 00 53 43 01 00 7F F7
SPECIAL_REQUEST_ID value : 55
This request schedules a reboot into bootloader mode. Current firmware sends the ACK response first, then performs the reboot 1000 ms later.
- Request:
F0 00 53 43 00 00 55 F7 - Response:
F0 00 53 43 01 00 55 F7
More info about bootloader mode and updating firmware on board can be found here.
SPECIAL_REQUEST_ID value : 44
When this message is sent to board, the board will restore all configurable parameters back to default values. Once the reset completes, the firmware sends the ACK response and schedules an application reboot 1000 ms later.
- Request:
F0 00 53 43 00 00 44 F7 - Response:
F0 00 53 43 01 00 44 F7
SPECIAL_REQUEST_ID value : 50
This request is used to find out maximum number of supported presets on OpenDeck board.
- Request:
F0 00 53 43 00 00 50 F7 - Response:
F0 00 53 43 01 00 50 00 05 F7
In this example, response is 5, which means maximum number of supported presets is 5. Current firmware hardcodes this limit to reduce database storage requirements and RAM usage.
SPECIAL_REQUEST_ID value : 51
This request is used to find out whether the board supports bootloader.
- Request:
F0 00 53 43 00 00 51 F7 - Response:
F0 00 53 43 01 00 51 00 01 F7
In this example, response is 1, which means the board supports bootloader.
SPECIAL_REQUEST_ID value : 1B
This request is used to perform full backup of all stored parameters on board for all presets.
- Request:
F0 00 53 43 00 00 1B F7
Response consists of the following messages:
F0 00 53 43 00 00 1C F7- Messages formatted like
SETmessages with currently configured values. These messages can be then sent back to the board. F0 00 53 43 00 00 1D F7F0 00 53 43 01 00 1B F7
Current firmware backs up all presets and preserves the currently active preset while backup is running.
Note: Full backup takes a while.
SPECIAL_REQUEST_ID value : 1C
This request starts a restore session. In normal usage this marker is emitted automatically as the first frame of a full-backup stream, and the same frame should be sent back to the device before replaying the backed-up SET messages.
- Request:
F0 00 53 43 00 00 1C F7 - Response:
F0 00 53 43 01 00 1C F7
SPECIAL_REQUEST_ID value : 1D
This request ends an active restore session. In normal usage this marker is emitted automatically near the end of a full-backup stream and should be replayed after all backed-up SET messages have been sent back to the device. Current firmware sends the ACK response and schedules an application reboot 1000 ms later.
- Request:
F0 00 53 43 00 00 1D F7 - Response:
F0 00 53 43 01 00 1D F7
OpenDeck board hosts large amount of configurable persistent parameters. Configuration messages are used to configure those parameters and they have the following structure:
STARTM_ID_0M_ID_1M_ID_2MESSAGE_STATUSMESSAGE_PARTWISHAMOUNTBLOCKSECTIONINDEXNEW_VALUEEND
BLOCK byte determines which part of the board user wants to configure. This byte comes after AMOUNT byte. The following blocks are available:
- Global
- Switches
- Encoders
- Analog
- Outputs
- I2C
- Touchscreen
Each block has its own sections for precise determination of parameter user wants to configure. Section is determined with SECTION byte. Inside section, INDEX byte must be specified to determine parameter user wants to manipulate, unless AMOUNT byte is ALL, in which case this byte needs to be set to 0. If WISH byte is SET, NEW_VALUE must be specified to set new value to selected parameter, otherwise it needs to be set to 0. For more detailed description of specific options, see the Configurable features document.
-
BLOCKvalue:0 -
SECTIONrange:0-5
List of sections (SECTION value):
-
0- MIDI settings -
1- Unused/reserved -
2- System settings -
3- OSC settings -
4- mDNS hostname bytes -
5- Configuration unlock
-
SECTIONvalue:0 -
INDEXrange:0-F -
NEW_VALUErange:0-1with a single exception for parameterE - Default:
0
List of parameters (INDEX value):
-
0- Standard note off -
1- Running status -
2- DIN to USB thru -
3- DIN MIDI state -
4- USB to DIN thru -
5- USB to USB thru -
6- USB to BLE thru -
7- DIN to DIN thru -
8- DIN to BLE thru -
9- BLE MIDI state -
A- BLE to DIN thru -
B- BLE to USB thru -
C- BLE to BLE thru -
D- Use global MIDI channel -
E- Global MIDI channel -
F- Send MIDI clock (DIN only)
For parameter E (Global MIDI channel) NEW_VALUE range is 1 - 11.
-
SECTIONvalue:2 -
INDEXrange:0-3 -
NEW_VALUErange: Custom for each parameter - Default:
0
List of parameters (INDEX value):
-
0- Active preset -
1- Preset preservation state -
2- Disable forced refresh after preset change -
3- Enable preset change with MIDI Program Change in
Allowed values (NEW_VALUE value):
-
0- Active preset:0-n(depends on number of supported presets) -
1- Preset preservation state:0-1 -
2- Disable forced refresh after preset change:0-1 -
3- Enable preset change with MIDI Program Change in:0-1
-
SECTIONvalue:3 -
INDEXrange:0-15 -
NEW_VALUErange: Custom for each parameter - Default: destination ports
9000, listen port9001, other values0
List of parameters (INDEX value):
-
0- Destination 1 IPv4 octet 0 -
1- Destination 1 IPv4 octet 1 -
2- Destination 1 IPv4 octet 2 -
3- Destination 1 IPv4 octet 3 -
4- Destination 1 port -
5- Destination 2 IPv4 octet 0 -
6- Destination 2 IPv4 octet 1 -
7- Destination 2 IPv4 octet 2 -
8- Destination 2 IPv4 octet 3 -
9- Destination 2 port -
A- Destination 3 IPv4 octet 0 -
B- Destination 3 IPv4 octet 1 -
C- Destination 3 IPv4 octet 2 -
D- Destination 3 IPv4 octet 3 -
E- Destination 3 port -
F- Destination 4 IPv4 octet 0 -
10- Destination 4 IPv4 octet 1 -
11- Destination 4 IPv4 octet 2 -
12- Destination 4 IPv4 octet 3 -
13- Destination 4 port -
14- Listen port -
15- Restrict incoming packets to configured destination IPs
Allowed values (NEW_VALUE value):
-
0- Destination 1 IPv4 octet 0:0-FF -
1- Destination 1 IPv4 octet 1:0-FF -
2- Destination 1 IPv4 octet 2:0-FF -
3- Destination 1 IPv4 octet 3:0-FF -
4- Destination 1 port:1-FFFF -
5- Destination 2 IPv4 octet 0:0-FF -
6- Destination 2 IPv4 octet 1:0-FF -
7- Destination 2 IPv4 octet 2:0-FF -
8- Destination 2 IPv4 octet 3:0-FF -
9- Destination 2 port:1-FFFF -
A- Destination 3 IPv4 octet 0:0-FF -
B- Destination 3 IPv4 octet 1:0-FF -
C- Destination 3 IPv4 octet 2:0-FF -
D- Destination 3 IPv4 octet 3:0-FF -
E- Destination 3 port:1-FFFF -
F- Destination 4 IPv4 octet 0:0-FF -
10- Destination 4 IPv4 octet 1:0-FF -
11- Destination 4 IPv4 octet 2:0-FF -
12- Destination 4 IPv4 octet 3:0-FF -
13- Destination 4 port:1-FFFF -
14- Listen port:1-FFFF -
15- Restrict incoming packets to configured destination IPs:0-1
-
SECTIONvalue:4 -
INDEXrange:0-3F -
NEW_VALUErange:0-FF - Default: all bytes
0
This section stores a custom mDNS hostname as bytes, including a terminating 0 byte. If the stored hostname is empty, unterminated, starts or ends with -, or contains characters other than letters, numbers, and -, firmware ignores it and uses the generated default hostname instead.
-
SECTIONvalue:5 -
INDEXrange:0-3 -
NEW_VALUErange:0-3FFF - Default: none
This is a hidden runtime-only section used by firmware that requires configuration verification. It is not stored in the database and is skipped during full backup.
The official configurator performs the following flow:
- Open the SysEx configuration session with the handshake request.
- Read firmware version with custom request
56. - For firmware versions which require verification, read the serial number with custom request
53. - Verify the serial number in the configurator.
- Derive a four-word unlock token from the raw serial-number bytes.
- Send four
SET SINGLEmessages to Global section5, with indexes0,1,2, and3in order.
The unlock token is derived with 32-bit FNV-1a:
- Offset basis:
2166136261 - Prime:
16777619 - Seed A:
opendeck-config-unlock-v1-a - Seed B:
opendeck-config-unlock-v1-b
For each seed, hash the ASCII seed bytes first, then the raw serial-number bytes returned by request 53. Split each 32-bit hash into two 14-bit words:
- word 0:
hash_a & 0x3FFF - word 1:
(hash_a >> 14) & 0x3FFF - word 2:
hash_b & 0x3FFF - word 3:
(hash_b >> 14) & 0x3FFF
Each word is sent as NEW_VALUE for the matching index. If any word is missing, out of order, or does not match the firmware-derived token, firmware keeps configuration locked and returns a SysEx error.
-
BLOCKvalue:1 -
SECTIONrange:0-4
List of sections (SECTION value):
-
0- Type -
1- Message type -
2- MIDI ID -
3- Value -
4- Channel
-
SECTIONvalue:0 -
INDEXrange:0-n(max number of supported switches) -
NEW_VALUErange:0-1 - Default:
0
List of parameters (INDEX value):
- Each parameter represents the index of the switch
Allowed values (NEW_VALUE value):
-
0- Momentary -
1- Latching
-
SECTIONvalue:1 -
INDEXrange:0-n(max number of supported switches) -
NEW_VALUErange:0-1D - Default:
0
List of parameters (INDEX value):
- Each parameter represents the index of the switch
Allowed values (NEW_VALUE value):
-
0- Notes -
1- Program change -
2- Control change -
3- Control change with reset to 0 on switch release -
4- MMC Stop -
5- MMC Play -
6- MMC Record -
7- MMC Pause -
8- Realtime Clock -
9- Realtime Start -
A- Realtime Continue -
B- Realtime Stop -
C- Realtime Active Sensing -
D- Realtime System Reset -
E- Program Change, increment -
F- Program Change, decrement -
10- No message -
11- OpenDeck preset change -
12- Multi Value IncReset Note -
13- Multi Value IncDec Note -
14- Multi Value IncReset CC -
15- Multi Value IncDec CC -
16- Note off only -
17- Control change with value 0 only -
18- Reserved -
19- Program change offset, increment -
1A- Program change offset, decrement -
1B- BPM, increment -
1C- BPM, decrement -
1D- MMC Play/Stop
-
SECTIONvalue:2 -
INDEXrange:0-n(max number of supported switches) -
NEW_VALUErange:0-7F - Default: Incrementing (value matches parameter index)
List of parameters (INDEX value):
- Each parameter represents the index of the switch
Allowed values (NEW_VALUE value):
-
0-7F
-
SECTIONvalue:3 -
INDEXrange:0-n(max number of supported switches) -
NEW_VALUErange:1-7F - Default:
7F
List of parameters (INDEX value):
- Each parameter represents the index of the switch
Allowed values (NEW_VALUE value):
NEW_VALUE value range: 1 - 7F
-
SECTIONvalue:4 -
INDEXrange:0-n(max number of supported switches) -
NEW_VALUErange:1-11 - Default:
1
List of parameters (INDEX value):
- Each parameter represents the index of the switch
Allowed values (NEW_VALUE value):
-
1-11
-
BLOCKvalue:2 -
SECTIONrange:0-C
List of sections (SECTION value):
-
0- Enabled/disabled -
1- Invert state -
2- Message type -
3- MIDI ID 1 -
4- Channel -
5- Unused/reserved -
6- Acceleration -
7- Unused/reserved -
8- Remote sync -
9- Lower value limit -
A- Upper value limit -
B- Repeated value -
C- MIDI ID 2
-
SECTIONvalue:0 -
INDEXrange:0-n(max number of supported encoders) -
NEW_VALUErange:0-1 - Default:
0
List of parameters (INDEX value):
- Each parameter represents the index of the encoder
Allowed values (NEW_VALUE value):
-
0- Disabled -
1- Enabled
-
SECTIONvalue:1 -
INDEXrange:0-n(max number of supported encoders) -
NEW_VALUErange:0-1 - Default:
0
List of parameters (INDEX value):
- Each parameter represents the index of the encoder
Allowed values (NEW_VALUE value):
-
0- Disabled -
1- Enabled
-
SECTIONvalue:2 -
INDEXrange:0-n(max number of supported encoders) -
NEW_VALUErange:0-E - Default:
0
List of parameters (INDEX value):
- Each parameter represents the index of the encoder
Allowed values (NEW_VALUE value):
-
0- Control change / 7Fh01h encoding -
1- Control change / 3Fh41h encoding -
2- Program change -
3- Control change -
4- Preset change -
5- Pitch bend -
6- NRPN 7-bit -
7- NRPN 14-bit -
8- Control change 14-bit -
9- Control change / 41h01h ecoding -
A- BPM -
B- Note -
C- Note with fixed value, both directions -
D- Note with fixed value, one direction sends 0 -
E- Two note mode
-
SECTIONvalue:3 -
INDEXrange:0-n(max number of supported encoders) -
NEW_VALUErange:0-3FFF - Default: Incrementing (value matches parameter index)
List of parameters (INDEX value):
- Each parameter represents the index of the encoder
Allowed values (NEW_VALUE value):
-
0-3FFF
-
SECTIONvalue:4 -
INDEXrange:0-n(max number of supported encoders) -
NEW_VALUErange:1-11 - Default:
1
List of parameters (INDEX value):
- Each parameter represents the index of the encoder
Allowed values (NEW_VALUE value):
-
1-11
-
SECTIONvalue:5
This section is reserved for compatibility and should not be used with current firmware.
-
SECTIONvalue:6 -
INDEXrange:0-n(max number of supported encoders) -
NEW_VALUErange:0-3 - Default:
0
List of parameters (INDEX value):
- Each parameter represents the index of the encoder
Allowed values (NEW_VALUE value):
-
0- Disabled -
1- Slow -
2- Medium -
3- Fast
-
SECTIONvalue:7
This section is reserved for compatibility and should not be used with current firmware.
-
SECTIONvalue:8 -
INDEXrange:0-n(max number of supported encoders) -
NEW_VALUErange:0-1 - Default:
0
List of parameters (INDEX value):
- Each parameter represents the index of the encoder
Allowed values (NEW_VALUE value):
-
0- Disabled -
1- Enabled
Remote sync supports continuous 7-bit CC and Pitch Bend encoder modes. For CC, the incoming controller ID must match the encoder's MIDI ID 1. Pitch Bend has no controller ID and is matched by channel only.
-
SECTIONvalue:9 -
INDEXrange:0-n(max number of supported encoders) -
NEW_VALUErange:0-3FFF - Default:
0
-
SECTIONvalue:A -
INDEXrange:0-n(max number of supported encoders) -
NEW_VALUErange:0-3FFF - Default:
3FFF
-
SECTIONvalue:B -
INDEXrange:0-n(max number of supported encoders) -
NEW_VALUErange:0-3FFF - Default:
0
-
SECTIONvalue:C -
INDEXrange:0-n(max number of supported encoders) -
NEW_VALUErange:0-3FFF - Default:
0
-
BLOCKvalue:3 -
SECTIONrange:0-B
List of sections (SECTION value):
-
0- Enabled/disabled -
1- Invert state -
2- Message type -
3- MIDI ID -
4- Unused/reserved -
5- Lower CC limit -
6- Unused/reserved -
7- Upper CC limit -
8- Unused/reserved -
9- Channel -
A- Lower ADC offset -
B- Upper ADC offset
-
SECTIONvalue:0 -
INDEXrange:0-n(max number of supported analog components) -
NEW_VALUErange:0-1 - Default:
0
List of parameters (INDEX value):
- Each parameter represents the index of the analog component
Allowed values (NEW_VALUE value):
-
0- Disabled -
1- Enabled
-
SECTIONvalue:1 -
INDEXrange:0-n(max number of supported analog components) -
NEW_VALUErange:0-1 - Default:
0
List of parameters (INDEX value):
- Each parameter represents the index of the analog component
Allowed values (NEW_VALUE value):
-
0- Disabled -
1- Enabled
-
SECTIONvalue:2 -
INDEXrange:0-n(max number of supported analog components) -
NEW_VALUErange:0-8 - Default:
0
List of parameters (INDEX value):
- Each parameter represents the index of the analog component
Allowed values (NEW_VALUE value):
-
0- Potentiometer with control change message, 7-bit -
1- Potentiometer with note message -
2- FSR -
3- Switch -
4- NRPN, 7-bit -
5- NRPN, 14-bit -
6- Pitch Bend -
7- Potentiometer with control change message, 14-bit -
8- Reserved
-
SECTIONvalue:3 -
INDEXrange:0-n(max number of supported analog components) -
NEW_VALUErange:0-3FFF - Default: Incrementing (value matches parameter index)
List of parameters (INDEX value):
- Each parameter represents the index of the analog component
Allowed values (NEW_VALUE value):
-
0-3FFF
-
SECTIONvalue:4
This section is reserved for compatibility and should not be used with current firmware.
-
SECTIONvalue:5 -
INDEXrange:0-n(max number of supported analog components) -
NEW_VALUErange:0-3FFF - Default: 0
List of parameters (INDEX value):
- Each parameter represents the index of the analog component
Allowed values (NEW_VALUE value):
-
0-3FFF
-
SECTIONvalue:6
This section is reserved for compatibility and should not be used with current firmware.
-
SECTIONvalue:7 -
INDEXrange:0-n(max number of supported analog components) -
NEW_VALUErange:0-3FFF - Default:
3FFF
List of parameters (INDEX value):
- Each parameter represents the index of the analog component
Allowed values (NEW_VALUE value):
-
0-3FFF
-
SECTIONvalue:8
This section is reserved for compatibility and should not be used with current firmware.
-
SECTIONvalue:9 -
INDEXrange:0-n(max number of supported analog components) -
NEW_VALUErange:1-11 - Default:
1
List of parameters (INDEX value):
- Each parameter represents the index of the analog component
Allowed values (NEW_VALUE value):
-
1-11
-
SECTIONvalue:A -
INDEXrange:0-n(max number of supported analog components) -
NEW_VALUErange:0-64 - Default:
0
List of parameters (INDEX value):
- Each parameter represents the index of the analog component
Allowed values (NEW_VALUE value):
-
0-64
-
SECTIONvalue:B -
INDEXrange:0-n(max number of supported analog components) -
NEW_VALUErange:0-64 - Default:
0
List of parameters (INDEX value):
- Each parameter represents the index of the analog component
Allowed values (NEW_VALUE value):
-
0-64
-
BLOCKvalue:4 -
SECTIONrange:0-7
List of sections (SECTION value):
-
0- Output state -
1- Output pulse testing -
2- Global settings -
3- Activation ID -
4- Reserved output section 2 -
5- Control type -
6- Activation value -
7- Channel
-
SECTIONvalue:0 -
INDEXrange:0-n(max number of supported outputs) -
NEW_VALUErange:0-1
List of parameters (INDEX value):
- Each parameter represents the index of the output
Allowed values (NEW_VALUE value):
-
0- Off -
1- On
Note: this is not persistent setting. Output must be turned on for this setting to take any effect.
-
SECTIONvalue:1 -
INDEXrange:0-n(max number of supported outputs) -
NEW_VALUErange:0-1
List of parameters (INDEX value):
- Each parameter represents the index of the output
Allowed values (NEW_VALUE value):
-
0- Disabled -
1- Enabled
-
SECTIONvalue:2 -
INDEXrange:0-3 -
NEW_VALUErange: Custom for each parameter - Default:
0
List of parameters (INDEX value):
-
0- Pulse with MIDI clock -
1- Unused/reserved -
2- Enable startup animation -
3- Use MIDI program offset
Allowed values (NEW_VALUE value):
-
0- Pulse with MIDI clock:0-1 -
1- Unused/reserved -
2- Enable startup animation:0-1 -
3- Use MIDI program offset:0-1
-
SECTIONvalue:3 -
INDEXrange:0-n(max number of supported outputs) -
NEW_VALUErange:0-7F - Default: Incrementing (value matches parameter index)
List of parameters (INDEX value):
- Each parameter represents the index of the output
Allowed values (NEW_VALUE value):
-
0-7F
This section is reserved for compatibility with older configurators.
-
SECTIONvalue:4 - Reserved/unused
-
SECTIONvalue:5 -
INDEXrange:0-n(max number of supported outputs) -
NEW_VALUErange:0-A - Default:
0
List of parameters (INDEX value):
- Each parameter represents the index of the output
Allowed values (NEW_VALUE value):
-
0- MIDI in / Note for output state, CC for output pulsing -
1- Local / Note for output state, no pulsing -
2- MIDI in / CC for output state, Note for output pulsing -
3- Local / CC for output state, no pulsing -
4- Program change for output state, no pulsing -
5- Preset -
6- MIDI in / Note for output level and output pulsing -
7- Local / Note for output level and output pulsing -
8- MIDI in / CC for output level and output pulsing -
9- Local / CC for output level and output pulsing -
A- Static / constantly on
-
SECTIONvalue:6 -
INDEXrange:0-n(max number of supported outputs) -
NEW_VALUErange:1-7F - Default:
7F
List of parameters (INDEX value):
- Each parameter represents the index of the output
Allowed values (NEW_VALUE value):
-
1-7F
-
SECTIONvalue:7 -
INDEXrange:0-n(max number of supported outputs) -
NEW_VALUErange:1-11 - Default:
1
List of parameters (INDEX value):
- Each parameter represents the index of the output
SECTION value: 7
Allowed values (NEW_VALUE value):
-
1-11
-
BLOCKvalue:5 -
SECTIONrange:0-5
List of sections (SECTION value):
-
0- Display settings -
1- APDS-9960 settings -
2- BNO085 settings -
3- CAP1188 settings -
4- VL53L4CX settings -
5- VL53L5CX settings
-
SECTIONvalue:0 -
INDEXrange:0-6 -
NEW_VALUErange: Custom for each parameter - Default:
0
List of parameters (INDEX value):
-
0- SW/HW version info on startup -
1- Display controller -
2- Display resolution -
3- MIDI event time -
4- Alternate MIDI display -
5- Octave normalization value -
6- Reserved
Allowed values (NEW_VALUE value):
-
0- SW/HW version info on startup:0-1 -
1- Display controller:-
0- Invalid -
1- SSD1306
-
-
2- Display resolution:-
0- Invalid -
1- 128x64 -
2- 128x32
-
-
3- MIDI event time -
4- Alternate MIDI display -
5- Octave normalization value -
6- Reserved:0
-
SECTIONvalue:1 -
INDEXrange:0-8 -
NEW_VALUErange: Custom for each parameter - Default: proximity/gesture mode
0, gesture inversion0, ambient light0, RGB0, proximity gain2, ambient/RGB gain1, lower proximity value0, upper proximity value255
List of parameters (INDEX value):
-
0- Proximity/gesture mode -
1- Invert left/right gestures -
2- Invert up/down gestures -
3- Enable ambient light output -
4- Enable RGB output -
5- Proximity gain -
6- Ambient/RGB gain -
7- Lower proximity value -
8- Upper proximity value
Allowed values (NEW_VALUE value):
-
0- Proximity/gesture mode:-
0- Disabled -
1- Proximity -
2- Gesture
-
-
1- Invert left/right gestures:0-1 -
2- Invert up/down gestures:0-1 -
3- Enable ambient light output:0-1 -
4- Enable RGB output:0-1 -
5- Proximity gain:-
0- 1x -
1- 2x -
2- 4x -
3- 8x
-
-
6- Ambient/RGB gain:-
0- 1x -
1- 4x -
2- 16x -
3- 64x
-
-
7- Lower proximity value:0-255 -
8- Upper proximity value:0-255
-
SECTIONvalue:2 -
INDEXrange:0-5 -
NEW_VALUErange: Custom for each parameter - Default:
0
List of parameters (INDEX value):
-
0- Enable quaternion output -
1- Enable Euler output -
2- Enable gyroscope output -
3- Enable linear acceleration output -
4- Enable gravity output -
5- Smoothing
Allowed values (NEW_VALUE value):
-
0- Enable quaternion output:0-1 -
1- Enable Euler output:0-1 -
2- Enable gyroscope output:0-1 -
3- Enable linear acceleration output:0-1 -
4- Enable gravity output:0-1 -
5- Smoothing:-
0- Off -
1- Light -
2- Medium -
3- Heavy
-
Smoothing applies to gyroscope, linear acceleration, and gravity output. Quaternion and Euler orientation output is sent unsmoothed.
-
SECTIONvalue:3 -
INDEXrange:0-0 -
NEW_VALUErange:0-2 - Default:
1
List of parameters (INDEX value):
-
0- Sensitivity
Allowed values (NEW_VALUE value):
-
0- Sensitivity:-
0- Low -
1- Medium -
2- High
-
-
SECTIONvalue:4 -
INDEXrange:0-6 -
NEW_VALUErange: Custom for each parameter - Default: distance mm
0, distance normalized0, smoothing3, tracking area0, distance mode0, distance normalized input min0, distance normalized input max6000
List of parameters (INDEX value):
-
0- Enable distance mm output -
1- Enable distance normalized output -
2- Smoothing -
3- Tracking area -
4- Distance mode -
5- Distance normalized input min -
6- Distance normalized input max
Allowed values (NEW_VALUE value):
-
0- Enable distance mm output:0-1 -
1- Enable distance normalized output:0-1 -
2- Smoothing:-
0- Off -
1- Light -
2- Medium -
3- Heavy
-
-
3- Tracking area:-
0- Narrow -
1- Medium -
2- Wide -
3- Full
-
-
4- Distance mode:-
0- Medium -
1- Long
-
-
5- Distance normalized input min:0-6000 -
6- Distance normalized input max:0-6000
-
SECTIONvalue:5 -
INDEXrange:0-8 -
NEW_VALUErange: Custom for each parameter - Default: output rate
1, other values0
List of parameters (INDEX value):
-
0- Resolution -
1- Smoothing -
2- Output mode -
3- Distance input min -
4- Distance input max -
5- Invert X -
6- Invert Y -
7- Rotation -
8- Output rate
Allowed values (NEW_VALUE value):
-
0- Resolution:-
0- 8x8 -
1- 4x4
-
-
1- Smoothing:-
0- Off -
1- Light -
2- Medium -
3- Heavy
-
-
2- Output mode:-
0- Disabled -
1- Grid -
2- Nearest -
3- Centroid -
4- Presence
-
-
3- Distance input min:0-4000 -
4- Distance input max:0-4000 -
5- Invert X:0-1 -
6- Invert Y:0-1 -
7- Rotation:-
0- 0 degrees -
1- 90 degrees -
2- 180 degrees -
3- 270 degrees
-
-
8- Output rate:-
0- Low -
1- Normal -
2- High
-
-
BLOCKvalue:6 -
SECTIONrange:0-8
List of sections (SECTION value):
-
0- Settings -
1- X position -
2- Y position -
3- Width -
4- Height -
5- Screen index of touchscreen component/icon in on state -
6- Screen index of touchscreen component/icon in off state -
7- Touchscreen component changes screen -
8- Screen to switch to
-
SECTIONvalue:0 -
INDEXrange:0-4 -
NEW_VALUErange: Custom for each parameter
List of parameters (INDEX value):
-
0- Enable touchscreen -
1- Touchscreen model -
2- Touchscreen brightness -
3- Initial screen -
4- Unused/reserved
Allowed values (NEW_VALUE value):
-
0- Enable touchscreen:-
0- Disabled -
1- Enabled
-
-
1- Touchscreen model:-
0- Nextion
-
-
2- Touchscreen brightness:-
0- 10% -
1- 25% -
2- 50% -
3- 75% -
4- 80% -
5- 90% -
6- 100%
-
-
3- Initial screen:0-F
-
SECTIONvalue:1 -
INDEXrange:0-n(max number of supported touchscreen components) -
NEW_VALUErange: depends on the configured touchscreen model and active display resolution - Default:
0
This value is stored in the touchscreen coordinate space. Current firmware does not apply one universal SysEx range check for X coordinates because valid values depend on the configured touchscreen/display setup.
-
SECTIONvalue:2 -
INDEXrange:0-n(max number of supported touchscreen components) -
NEW_VALUErange: depends on the configured touchscreen model and active display resolution - Default:
0
This value is stored in the touchscreen coordinate space. Current firmware does not apply one universal SysEx range check for Y coordinates because valid values depend on the configured touchscreen/display setup.
-
SECTIONvalue:3 -
INDEXrange:0-n(max number of supported touchscreen components) -
NEW_VALUErange:0-1024 - Default:
0
Width uses the same coordinate space as the touchscreen model. Practical values still depend on the configured display resolution.
-
SECTIONvalue:4 -
INDEXrange:0-n(max number of supported touchscreen components) -
NEW_VALUErange:0-600 - Default:
0
Height uses the same coordinate space as the touchscreen model. Practical values still depend on the configured display resolution.
-
SECTIONvalue:5 -
INDEXrange:0-n(max number of supported touchscreen components) -
NEW_VALUErange:0-15 - Default:
0
-
SECTIONvalue:6 -
INDEXrange:0-n(max number of supported touchscreen components) -
NEW_VALUErange:0-15 - Default:
0
-
SECTIONvalue:7 -
INDEXrange:0-n(max number of supported touchscreen components) -
NEW_VALUErange:0-1 - Default:
0
-
SECTIONvalue:8 -
INDEXrange:0-n(max number of supported touchscreen components) -
NEW_VALUErange:0-15 - Default:
0
Component info messages have similar structure to special requests:
STARTM_ID_0M_ID_1M_ID_2MESSAGE_STATUSMESSAGE_PARTSPECIAL_MESSAGE_IDBLOCKINDEXEND
MESSAGE_STATUS is always 1(ACK).
SPECIAL_MESSAGE_ID value: 49.
BLOCK is the block ID of component that is sending MIDI data - switch (1), encoder (2), analog (3) or touchscreen component (6).
INDEX is the component ID. Current firmware always uses 2 bytes for INDEX.
Unlike all other special messages, this message isn't sent to board - it's received from the board. This message is sent when SysEx configuration is enabled. It's used primarily for identifying component sending MIDI data.
Let's take a look at following scenario:
User has enabled analog input 1 (index 0).
- Request:
F0 00 53 43 00 00 01 00 03 00 00 01 F7
When user moves potentiometer (default option for analog input), BLOCK byte in Component info message will be 3, since that is analog block ID, and INDEX byte will be 0, since user has enabled analog input 1 (index 0).
- Component info message:
F0 00 53 43 01 00 49 03 00 00 F7
This doesn't seem useful at first, but let's take a look at another example:
User wants to set CC number for potentiometer 1 (index 0) to 5.
- Request:
F0 00 53 43 00 00 01 00 03 03 00 05 F7
Now, potentiometer sends CC 5. If the board was already enclosed (easy access isn't possible) and user wants to change CC for that potentiometer again, cable from potentiometer would had to be tracked to board. When SysEx is turned on, component info message sends the component ID.
The process is the same for switches and encoders.
Each request sent to board receives response (except for factory reset and reboot requests). When board sends response, it sets MESSAGE_STATUS byte to value 1 if request was valid (or 0 if WISH byte is BACKUP), or other value if request was invalid. MESSAGE_STATUS has 13 possible states:
-
0- Request -
1- Response/ACK (request is valid) -
2- Status error -
3- Handshake error -
4- Wish error -
5- Amount error -
6- Block error -
7- Section error -
8- Part error -
9- Index error -
A- New value error -
B- Message length error -
C- Write error -
D- Not supported error -
E- Read error -
80- UART allocation error
Code: 00
Each request to the board must contain REQUEST (0) value in MESSAGE_STATUS byte.
Code: 01
Request was valid if response sets MESSAGE_STATUS to ACK (1).
Code: 02
This error happens when MESSAGE_STATUS isn't REQUEST (0) in request.
Code: 03
This error is returned when request is correct, but handshake request hasn't been sent to board (or SysEx connection has been closed).
Code: 04
This error is returned when WISH is anything other than GET, SET or BACKUP.
Error code: 05
This error is returned when AMOUNT is anything other than SINGLE or ALL.
Error code: 06
This error is returned when BLOCK byte is incorrect.
Error code: 07
This error is returned when SECTION byte is incorrect.
Code: 08
This error is returned when message part is incorrect.
Error code: 09
This error is returned when wanted parameter is incorrect.
Error code: 0A
This error is returned when NEW_VALUE is incorrect.
Error code: 0B
This error is returned when request is too short.
- Response:
0C
This error is returned when writing new value to board has failed. This can happen if EEPROM on board is damaged.
- Response:
0D
This error is returned when the requested parameter isn't supported on the board.
- Response:
0E
This error is returned when the reading of requested index fails.
- Response:
80
This error is returned when UART peripheral sharing the channel with other UART peripheral cannot be enabled because the other peripheral is already initialized.
Note: All GET examples assume default board configuration.
-
MESSAGE_STATUS:0(Request) -
MESSAGE_PART:0 -
WISH:GET(0) -
AMOUNT:SINGLE(0) -
BLOCK: Analog (3) -
SECTION: MIDI ID (3) -
INDEX MSB:0 -
INDEX LSB:5 -
NEW_VALUE MSB:0(unused but required) -
NEW_VALUE LSB:0(unused but required) -
Request:
F0 00 53 43 00 00 00 00 03 03 00 05 00 00 F7 -
Response:
F0 00 53 43 01 00 00 00 03 03 00 05 00 00 00 05 F7
-
MESSAGE_STATUS:0(Request) -
MESSAGE_PART: 0 -
WISH:GET(0) -
AMOUNT:ALL(1) -
BLOCK: Encoder (2) -
SECTION: Message type (2) -
INDEX MSB: 0 (unused but required) -
INDEX LSB: 0 (unused but required) -
NEW_VALUE MSB: 0 (unused but required) -
NEW_VALUE LSB: 0 (unused but required) -
Request:
F0 00 53 43 00 00 00 01 02 02 00 00 00 00 F7 -
Response:
F0 00 53 43 01 00 00 01 02 02 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 F7
-
MESSAGE_STATUS:0(Request) -
MESSAGE_PART:7F -
WISH:GET(0) -
AMOUNT:ALL(1) -
BLOCK: Switches (1) -
SECTION: MIDI ID (2) -
INDEX MSB: 0 (unused but required) -
INDEX LSB: 0 (unused but required) -
NEW_VALUE MSB: 0 (unused but required) -
NEW_VALUE LSB: 0 (unused but required) -
Request:
F0 00 53 43 00 7F 00 01 01 02 00 00 00 00 F7 -
Response 1:
F0 00 53 43 01 00 00 01 01 02 00 00 00 00 00 00 00 01 00 02 00 03 00 04 00 05 00 06 00 07 00 08 00 09 00 0A 00 0B 00 0C 00 0D 00 0E 00 0F 00 10 00 11 00 12 00 13 00 14 00 15 00 16 00 17 00 18 00 19 00 1A 00 1B 00 1C 00 1D 00 1E 00 1F F7 -
Response 2:
F0 00 53 43 01 01 00 01 01 02 00 00 00 00 00 20 00 21 00 22 00 23 00 24 00 25 00 26 00 27 00 28 00 29 00 2A 00 2B 00 2C 00 2D 00 2E 00 2F 00 30 00 31 00 32 00 33 00 34 00 35 00 36 00 37 00 38 00 39 00 3A 00 3B 00 3C 00 3D 00 3E 00 3F F7 -
Response 3:
F0 00 53 43 01 02 00 01 01 02 00 00 00 00 00 40 00 41 00 42 00 43 00 44 00 45 00 46 00 47 00 48 00 49 00 4A 00 4B 00 4C 00 4D 00 4E 00 4F 00 50 00 51 00 52 00 53 00 54 00 55 00 56 00 57 00 58 00 59 00 5A 00 5B 00 5C 00 5D 00 5E 00 5F F7
If the MESSAGE_PART is set to value 7E, same three messages will be sent, however, one extra message containing the copy of the original request will be sent with the status byte set to ACK:
- Response 4:
F0 00 53 43 01 7E 00 01 01 02 00 00 00 00 00 00 F7
Once this message has been received, the stream of messages is finished.
-
MESSAGE_STATUS:0(Request) -
MESSAGE_PART:0 -
WISH:SET(1) -
AMOUNT:SINGLE(0) -
BLOCK: Outputs (4) -
SECTION: Control type (5) -
INDEX MSB:0(output 1) -
INDEX LSB:0(output 1) -
NEW_VALUE MSB:0 -
NEW_VALUE LSB:A(Static / constantly on) -
Request:
F0 00 53 43 00 00 01 00 04 05 00 00 00 0A F7 -
Response:
F0 00 53 43 01 00 01 00 04 05 00 00 00 0A F7
User wants to configure switch 4 to send program change event instead of note event.
-
MESSAGE_STATUS:0(Request) -
MESSAGE_PART:0 -
WISH:SET(1) -
AMOUNT:SINGLE(0) -
BLOCK: Switch (1) -
SECTION: Message type (1) -
INDEX MSB:0 -
INDEX LSB:4 -
NEW_VALUE MSB:1 -
NEW_VALUE LSB:1 -
Request:
F0 00 53 43 00 00 01 00 01 01 00 04 00 01 F7 -
Response:
F0 00 53 43 01 00 01 00 01 01 00 04 00 01 F7
-
MESSAGE_STATUS:0(Request) -
MESSAGE_PART:0 -
WISH:SET(1) -
AMOUNT:SINGLE(0) -
BLOCK: Analog (3) -
SECTION: Upper CC limit (7) -
INDEX MSB:0 -
INDEX LSB:5 -
NEW_VALUE MSB:32 -
NEW_VALUE LSB:4 -
Request:
F0 00 53 43 00 00 01 00 03 07 00 05 20 04 F7 -
Response:
F0 00 53 43 01 00 01 00 03 07 00 05 20 04 F7
Hardware
- Supported microcontrollers
- Supported components
-
Supported boards
- Adafruit
- Arduino
- Generic
- LILYGO
- Nordic Semiconductor
- Olimex
- PJRC
- Raspberry Pi
- Shantea Controls
- Silicognition
- STMicroelectronics
- Waveshare
- WIZnet
- Recommended components and where to get them
- LED indicators
Configuration and usage
- Configurable features
- Output control
- OSC
- Presets
- Timing and latency
- Configuring touchscreens
- Firmware update via bootloader
Advanced