-
Notifications
You must be signed in to change notification settings - Fork 56
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
- 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_1
, M_ID_2
, M_ID_3
, MESSAGE_STATUS
, MESSAGE_PART
and END
. This applies to both requests and response (except for few messages which don't return anything). Below is a list of all possible SysEx bytes used on OpenDeck:
START
M_ID_0
M_ID_1
M_ID_2
MESSAGE_STATUS
MESSAGE_PART
WISH
SPECIAL_REQUEST_ID
AMOUNT
BLOCK
SECTION
INDEX*
NEW_VALUE*
STOP
Note: depending on protocol configuration INDEX
and NEW_VALUE
values can be represented either by single or two bytes.
Each response to a request is a copy of request with changed status byte and appended data before last byte if needed (depending on request).
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_0
value:00
-
M_ID_1
value:53
-
M_ID_2
value: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 specific error code if request was invalid. Exception is scenario when WISH
byte is BACKUP
. In that case, MESSAGE_STATUS
byte is 0
in response if request was valid. See here.
SysEx buffer takes relatively large amount of space in firmware. In order to reduce buffer size, messages are limited to specified size. OpenDeck limits messages to 32 values. START
, M_ID_1
, M_ID_2
, M_ID_3
, 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 ALL
SET ALL
BACKUP 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.
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:
GET
SET
BACKUP
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:
SINGLE
ALL
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 used-defined and can differ depending on implementation. Both groups have the same message structure:
START
M_ID_1
M_ID_2
M_ID_3
MESSAGE_STATUS
MESSAGE_PART
SPECIAL_REQUEST_ID
END
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.
- 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
Depending on how the protocol is configured, returned values and INDEX
and NEW_VALUE
values in requests can be composed of one or two bytes. In one-byte configuration, maximum value can be 127 due to limitations of SysEx. In two-byte configuration, maximum value is 16383 (14-bit maximum). Two-byte values are necessary when there are parameters with index larger than 127, or when certain value can be larger than 127. 2
is returned if board is configured to use two-byte protocol, otherwise, 1
is returned.
- Request:
F0 00 53 43 00 00 02 F7
- Response / single byte protocol:
F0 00 53 43 01 00 02 01 F7
- Response / two byte protocol:
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 (1
in single byte protocol and 2
in two byte protocol, composed of two bytes).
In case 2-byte protocol variant is used, 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 / single byte protocol:
F0 00 53 43 01 00 03 20 F7
- Response / two byte protocol:
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
- Firmware version and hardware UID
- Number of supported components
- Reboot
- Bootloader mode
- Factory reset
- Number of supported presets
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 / single byte protocol:
F0 00 53 43 01 00 56 05 00 00 F7
- Response / two byte protocol:
F0 00 53 43 01 00 56 00 05 00 00 00 00 F7
When converted to decimal system, firmware version (as of date of this writing) 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.
- Request:
F0 00 53 43 00 00 42 F7
- Response / single byte protocol:
F0 00 53 43 01 00 42 byte1 byte2 byte3 byte4 F7
- Response / two byte protocol:
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 : 43
This request will return firmware version and hardware UID in one response.
- Request:
F0 00 53 43 00 00 43 F7
- Response / single byte protocol:
F0 00 53 43 01 00 43 05 00 00 2B 13 44 7A F7
- Response / two byte protocol:
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 / single byte protocol:
F0 00 53 43 01 00 4D 19 08 08 10 00 F7
- Response / two byte protocol:
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 (values for STM32F4 Discovery board):
- Maximum number of buttons (25) - This represents sum of maximum number of digital inputs, analog inputs and touchscreen buttons.
- Maximum number of encoders (8)
- Maximum number of analog inputs (8)
- Maximum number of LEDs (16) - This is sum of maximum number of physical LEDs and touchscreen buttons since they can be also used as indicators (in this case max number of touchscreen buttons is 0)
- Maximum number of touchscreen buttons (0)
SPECIAL_REQUEST_ID
value : 7F
This request will simply reboot the board.
- Request:
F0 00 53 43 00 00 7F F7
- Response: No response
SPECIAL_REQUEST_ID
value : 55
This request will reboot the board into bootloader mode.
- Request:
F0 00 53 43 00 00 55 F7
- Response: No response
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 value and reboot cycle will be performed.
- Request:
F0 00 53 43 00 00 44 F7
- Response: No response
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 / single byte protocol:
F0 00 53 43 01 00 50 0A F7
- Response / two byte protocol:
F0 00 53 43 01 00 50 00 0A F7
In this example, response is 10, which means maximum number of supported presets is 10.
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 / single byte protocol:
F0 00 53 43 01 00 51 01 F7
- Response / two byte protocol:
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 01 00 1B F7
- Messages formatted like
SET
messages with currently configured values. These messages can be then sent back to the board. F0 00 53 43 01 00 1B F7
Note: Full backup takes a while.
OpenDeck board hosts large amount of configurable persistent parameters. Configuration messages are used to configure those parameters and they have the following structure:
START
M_ID_0
M_ID_1
M_ID_1
MESSAGE_STATUS
MESSAGE_PART
WISH
AMOUNT
BLOCK
SECTION
INDEX
NEW_VALUE
STOP
BLOCK
byte determines which part of the board user wants to configure. This byte comes after AMOUNT
byte. The following blocks are available:
- Global
- Buttons
- Encoders
- Analog
- LEDs
- Display
- 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.
-
BLOCK
value:0
-
SECTION
range:0
-3
List of sections (SECTION
value):
-
0
- MIDI settings -
1
- Unused/reserved -
2
- Presets
-
SECTION
value:0
-
INDEX
range:0
-F
-
NEW_VALUE
range:0
-1
with 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
.
-
SECTION
value:2
-
INDEX
range:0
-3
-
NEW_VALUE
range: Custom for each parameter - Default:
0
List of parameters (INDEX
value):
-
0
- Active preset -
1
- Preset preservation state -
2
- Force value 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
- Force value refresh after preset change:0
-1
-
3
- Enable preset change with MIDI Program Change in:0
-1
-
BLOCK
value:1
-
SECTION
range:0
-4
List of sections (SECTION
value):
-
0
- Type -
1
- Message type -
2
- MIDI ID -
3
- Value -
4
- Channel
-
SECTION
value:0
-
INDEX
range:0
-n
(max number of supported buttons) -
NEW_VALUE
range:0
-1
- Default:
0
List of parameters (INDEX
value):
- Each parameter represents the index of the button
Allowed values (NEW_VALUE
value):
-
0
- Momentary -
1
- Latching
-
SECTION
value:1
-
INDEX
range:0
-n
(max number of supported buttons) -
NEW_VALUE
range:0
-1C
- Default:
0
List of parameters (INDEX
value):
- Each parameter represents the index of the button
Allowed values (NEW_VALUE
value):
-
0
- Notes -
1
- Program change -
2
- Control change -
3
- Control change with reset to 0 on button 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
-
SECTION
value:2
-
INDEX
range:0
-n
(max number of supported buttons) -
NEW_VALUE
range:0
-7F
- Default: Incrementing (value matches parameter index)
List of parameters (INDEX
value):
- Each parameter represents the index of the button
Allowed values (NEW_VALUE
value):
-
0
-7F
-
SECTION
value:3
-
INDEX
range:0
-n
(max number of supported buttons) -
NEW_VALUE
range:1
-FF
- Default:
7F
List of parameters (INDEX
value):
- Each parameter represents the index of the button
Allowed values (NEW_VALUE
value):
NEW_VALUE
value range: 1
- 7F
-
SECTION
value:4
-
INDEX
range:0
-n
(max number of supported buttons) -
NEW_VALUE
range:1
-200
- Default:
1
List of parameters (INDEX
value):
- Each parameter represents the index of the button
Allowed values (NEW_VALUE
value):
-
1
-10
-
BLOCK
value:2
-
SECTION
range:0
-8
List of sections (SECTION
value):
-
0
- Enabled/disabled -
1
- Invert state -
2
- Message type -
3
- MIDI ID / LSB -
4
- Channel -
5
- Pulses per step -
6
- Acceleration -
7
- MIDI ID / MSB -
8
- Remote sync
-
SECTION
value:0
-
INDEX
range:0
-n
(max number of supported encoders) -
NEW_VALUE
range: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
-
SECTION
value:1
-
INDEX
range:0
-n
(max number of supported encoders) -
NEW_VALUE
range: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
-
SECTION
value:2
-
INDEX
range:0
-n
(max number of supported encoders) -
NEW_VALUE
range:0
-B
- 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
- NPRN 8-bit -
8
- Control change 14-bit -
9
- Control change / 41h01h ecoding -
A
- BPM -
B
- Note
-
SECTION
value:3
-
INDEX
range:0
-n
(max number of supported encoders) -
NEW_VALUE
range:0
-7F
in single byte protocol variant or0
-3FFF
in two byte variant - 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
-7F
-
SECTION
value:4
-
INDEX
range:0
-n
(max number of supported encoders) -
NEW_VALUE
range:1
-200
- Default:
1
List of parameters (INDEX
value):
- Each parameter represents the index of the encoder
Allowed values (NEW_VALUE
value):
-
0
-10
-
SECTION
value:5
-
INDEX
range:0
-n
(max number of supported encoders) -
NEW_VALUE
range:2
-4
- Default:
4
List of parameters (INDEX
value):
- Each parameter represents the index of the encoder
Allowed values (NEW_VALUE
value):
-
2
-4
-
SECTION
value:6
-
INDEX
range:0
-n
(max number of supported encoders) -
NEW_VALUE
range: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
Note: this section is unavailable in two-byte protocol variant.
-
SECTION
value:7
-
INDEX
range:0
-n
(max number of supported encoders) -
NEW_VALUE
range:0
-7F
- Default:
0
List of parameters (INDEX
value):
- Each parameter represents the index of the encoder
Allowed values (NEW_VALUE
value):
-
0
-7F
-
SECTION
value:8
-
INDEX
range:0
-n
(max number of supported encoders) -
NEW_VALUE
range: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
-
BLOCK
value:3
-
SECTION
range:0
-8
List of sections (SECTION
value):
-
0
- Enabled/disabled -
1
- Invert state -
2
- Message type -
3
- MIDI ID / LSB -
4
- MIDI ID / MSB -
5
- Lower CC limit / LSB -
6
- Lower CC limit / MSB -
7
- Upper CC limit / LSB -
8
- Upper CC limit / MSB -
9
- Channel -
A
- Lower ADC offset -
B
- Upper ADC offset
-
SECTION
value:0
-
INDEX
range:0
-n
(max number of supported analog components) -
NEW_VALUE
range: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
-
SECTION
value:1
-
INDEX
range:0
-n
(max number of supported analog components) -
NEW_VALUE
range: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
-
SECTION
value:2
-
INDEX
range:0
-n
(max number of supported analog components) -
NEW_VALUE
range: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 CC message, 7-bit -
1
- Potentiometer with note message -
2
- FSR -
3
- Button -
4
- NRPN, 7-bit -
5
- NRPN, 14-bit -
6
- Pitch Bend -
7
- Potentiometer with CC message, 14-bit
-
SECTION
value:3
-
INDEX
range:0
-n
(max number of supported analog components) -
NEW_VALUE
range:0
-7F
in single byte protocol variant or0
-3FFF
in two byte variant - 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
-7F
Note: this section is unavailable in two-byte protocol variant.
-
SECTION
value:4
-
INDEX
range:0
-n
(max number of supported analog components) -
NEW_VALUE
range:0
-7F
- Default: 0
List of parameters (INDEX
value):
- Each parameter represents the index of the analog component
Allowed values (NEW_VALUE
value):
-
0
-7F
-
SECTION
value:5
-
INDEX
range:0
-n
(max number of supported analog components) -
NEW_VALUE
range:0
-7F
in single byte protocol variant or0
-3FFF
in two byte variant - Default: 0
List of parameters (INDEX
value):
- Each parameter represents the index of the analog component
Allowed values (NEW_VALUE
value):
-
0
-7F
Note: this section is unavailable in two-byte protocol variant.
-
SECTION
value:6
-
INDEX
range:0
-n
(max number of supported analog components) -
NEW_VALUE
range:0
-7F
- Default: 0
List of parameters (INDEX
value):
- Each parameter represents the index of the analog component
Allowed values (NEW_VALUE
value):
-
0
-7F
-
SECTION
value:7
-
INDEX
range:0
-n
(max number of supported analog components) -
NEW_VALUE
range:0
-7F
in single byte protocol variant or0
-3FFF
in two byte variant - Default:
7F
in single byte protocol variant or0
-3FFF
in two byte variant
List of parameters (INDEX
value):
- Each parameter represents the index of the analog component
Allowed values (NEW_VALUE
value):
-
0
-7F
Note: this section is unavailable in two-byte protocol variant.
-
SECTION
value:8
-
INDEX
range:0
-n
(max number of supported analog components) -
NEW_VALUE
range:0
-7F
- Default:
0
List of parameters (INDEX
value):
- Each parameter represents the index of the analog component
Allowed values (NEW_VALUE
value):
-
0
-7F
-
SECTION
value:9
-
INDEX
range:0
-n
(max number of supported analog components) -
NEW_VALUE
range:1
-200
- Default:
1
List of parameters (INDEX
value):
- Each parameter represents the index of the analog component
Allowed values (NEW_VALUE
value):
-
1
-10
-
SECTION
value:A
-
INDEX
range:0
-n
(max number of supported analog components) -
NEW_VALUE
range: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
-
SECTION
value:B
-
INDEX
range:0
-n
(max number of supported analog components) -
NEW_VALUE
range: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
-
BLOCK
value:4
-
SECTION
range:0
-6
List of sections (SECTION
value):
-
0
- LED color testing -
1
- LED blink testing -
2
- Global settings -
3
- Activation note -
4
- RGB enabled/disabled -
5
- Control type -
6
- Channel
Note: this is not persistent setting
-
SECTION
value:0
-
INDEX
range:0
-n
(max number of supported LEDs) -
NEW_VALUE
range:0
-7
List of parameters (INDEX
value):
- Each parameter represents the index of the LED
Allowed values (NEW_VALUE
value):
-
0
- Off (no color) -
1
- Red -
2
- Green -
3
- Yellow -
4
- Blue -
5
- Magenta -
6
- Cyan -
7
- White
When testing single color LED, color setting is ignored. When using GET
message in this section for single color LED, Red color is returned (value 1
).
Note: this is not persistent setting. LED must be turned on for this setting to take any effect.
-
SECTION
value:1
-
INDEX
range:0
-n
(max number of supported LEDs) -
NEW_VALUE
range:0
-1
List of parameters (INDEX
value):
- Each parameter represents the index of the LED
Allowed values (NEW_VALUE
value):
-
0
- Disabled -
1
- Enabled
-
SECTION
value:2
-
INDEX
range:0
-2
-
NEW_VALUE
range: Custom for each parameter - Default:
0
List of parameters (INDEX
value):
-
0
- Blink with MIDI clock -
1
- Fade speed -
2
- Enable startup animation
Allowed values (NEW_VALUE
value):
-
0
- Blink with MIDI clock:0
-1
-
1
- Fade speed:0
-A
-
2
- Enable startup animation:0
-1
-
SECTION
value:3
-
INDEX
range:0
-n
(max number of supported LEDs) -
NEW_VALUE
range:0
-7F
- Default: Incrementing (value matches parameter index)
List of parameters (INDEX
value):
- Each parameter represents the index of the LED
Allowed values (NEW_VALUE
value):
-
0
-7F
Note: Even though number of supported RGB LEDs is total number of LEDs divided by 3, this command takes as an argument single-color LED index.
-
SECTION
value:4
-
INDEX
range:0
-n
(max number of supported LEDs) -
NEW_VALUE
range:0
-1
- Default:
0
List of parameters (INDEX
value):
- Each parameter represents the index of the LED
Allowed values (NEW_VALUE
value):
-
0
-1
-
SECTION
value:5
-
INDEX
range:0
-n
(max number of supported LEDs) -
NEW_VALUE
range:0
-9
- Default:
0
List of parameters (INDEX
value):
- Each parameter represents the index of the LED
Allowed values (NEW_VALUE
value):
-
0
- MIDI in / Note for LED state, CC for LED blinking -
1
- Local / Note for LED state, no blinking -
2
- MIDI in / CC for LED state, Note for LED blinking -
3
- Local / CC for LED state, no blinking -
4
- MIDI in / Program change for LED state, no blinking -
5
- Local / Program change for LED state, no blinking -
6
- MIDI in / Note for LED state and LED blinking -
7
- Local / Note for LED state and LED blinking -
8
- MIDI in / CC for LED state and LED blinking -
9
- Local / CC for LED state and LED blinking -
10
- Static / constantly on
-
SECTION
value:6
-
INDEX
range:0
-n
(max number of supported LEDs) -
NEW_VALUE
range:1
-7F
- Default:
7F
List of parameters (INDEX
value):
- Each parameter represents the index of the LED
Allowed values (NEW_VALUE
value):
-
1
-7F
-
SECTION
value:7
-
INDEX
range:0
-n
(max number of supported LEDs) -
NEW_VALUE
range:1
-200
- Default:
1
List of parameters (INDEX
value):
- Each parameter represents the index of the LED
SECTION
value: 7
Allowed values (NEW_VALUE
value):
-
1
-10
-
BLOCK
value:5
-
SECTION
range:0
-1
List of sections (SECTION
value):
-
0
- Features -
1
- Settings
-
SECTION
value:0
-
INDEX
range:0
-4
-
NEW_VALUE
range:0
-1
- Default:
0
List of parameters (INDEX
value):
-
0
- Enable display -
1
- Welcome message on startup -
2
- SW/HW version info on startup -
3
- Alternate MIDI display
Allowed values (NEW_VALUE
value):
-
0
-1
-
SECTION
value:1
-
INDEX
range:0
-3
-
NEW_VALUE
range: Custom for each parameter - Default:
0
List of parameters (INDEX
value):
-
0
- Display controller -
1
- Display resolution -
2
- MIDI event time -
3
- Octave normalization value -
4
- I2C address
Allowed values (NEW_VALUE
value):
-
0
- Display controller:-
0
- Invalid -
1
- SSD1306
-
-
1
- Display resolution:-
0
- Invalid -
1
- 128x64 -
2
- 128x32
-
-
2
- MIDI event time:1
-5
-
3
- Octave normalization value:0
-7F
-
4
- I2C address. Valid addresses are:0x78
0x7A
-
BLOCK
value:6
-
SECTION
range:0
-8
List of sections (SECTION
value):
-
0
- Settings -
1
- X position -
2
- Y position -
3
- Width -
4
- Height -
5
- Screen index of button/icon in on state -
6
- Screen index of button/icon in off state -
7
- Button changes screen -
8
- Screen to switch to
-
SECTION
value:0
-
INDEX
range:0
-4
-
NEW_VALUE
range: Custom for each parameter
List of parameters (INDEX
value):
-
0
- Enable touchscreen -
1
- Touchscreen model -
2
- Touchscreen brightness -
3
- Initial screen
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
-
SECTION
value:1
-
INDEX
range:0
-n
(max number of supported buttons on touchscreen) -
NEW_VALUE
range:0
-400
(set depending on screen resolution) - Default:
0
-
SECTION
value:2
-
INDEX
range:0
-n
(max number of supported buttons on touchscreen) -
NEW_VALUE
range:0
-258
(set depending on screen resolution) - Default:
0
-
SECTION
value:3
-
INDEX
range:0
-n
(max number of supported buttons on touchscreen) -
NEW_VALUE
range:0
-400
(set depending on screen resolution) - Default:
0
-
SECTION
value:4
-
INDEX
range:0
-n
(max number of supported buttons on touchscreen) -
NEW_VALUE
range:0
-258
(set depending on screen resolution) - Default:
0
-
SECTION
value:5
-
INDEX
range:0
-n
(max number of supported buttons on touchscreen) -
NEW_VALUE
range:0
-15
- Default:
0
-
SECTION
value:6
-
INDEX
range:0
-n
(max number of supported buttons on touchscreen) -
NEW_VALUE
range:0
-15
- Default:
0
-
SECTION
value:7
-
INDEX
range:0
-n
(max number of supported buttons on touchscreen) -
NEW_VALUE
range:0
-1
- Default:
0
-
SECTION
value:8
-
INDEX
range:0
-n
(max number of supported buttons on touchscreen) -
NEW_VALUE
range:0
-15
- Default:
0
Component info messages have similar structure to special requests:
START
M_ID_0
M_ID_1
M_ID_2
MESSAGE_STATUS
MESSAGE_PART
SPECIAL_MESSAGE_ID
BLOCK
INDEX
END
MESSAGE_STATUS
is always 1
(ACK
).
SPECIAL_MESSAGE_ID
value: 49
.
BLOCK
is the block ID of component that is sending MIDI data - button (1
), encoder (2
), analog (3
) or touchscreen component (6
).
INDEX
is the component ID. Depending on protocol variant, INDEX
is either 1 or 2 bytes long.
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 / single byte protocol:
F0 00 53 43 01 00 49 03 00 F7
- Component info message / two byte protocol:
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 buttons 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.
User wants to find out MIDI ID for analog component 5.
-
MESSAGE_STATUS
:0
(Request) -
MESSAGE_PART
:0
-
WISH
:GET
(0
) -
AMOUNT
:SINGLE
(0
) -
BLOCK
: Analog (3
) -
SECTION
: MIDI ID (3
) -
INDEX
:5
-
NEW_VALUE
:0
(unused but required) -
Request:
F0 00 53 43 00 00 00 00 03 03 05 00 F7
-
Response:
F0 00 53 43 01 00 00 00 03 03 05 00 05 F7
Like each response, this one is also a copy of the request. If data is requested from the board, the data starts after the copy of the request. In this case MIDI ID for analog component 5 is 5, therefore, last byte (before end byte) is 5.
User wants to find out message type for all encoders.
-
MESSAGE_STATUS
:0
(Request) -
MESSAGE_PART
: 0 -
WISH
:GET
(0
) -
AMOUNT
:ALL
(1
) -
BLOCK
: Encoder (2
) -
SECTION
: Message type (2
) -
INDEX
: 0 (unused but required) -
NEW_VALUE
: 0 (unused but required) -
Request:
F0 00 53 43 00 00 00 01 02 02 00 00 F7
-
Response:
F0 00 53 43 01 00 00 01 02 02 00 00 00 00 00 00 00 00 00 00 F7
Response returned 8 values for 8 encoders. Since all encoders have default message type set to 7Fh01h (0
), all 8 values are 0
.
User wants to get notes for all buttons. Official OpenDeck board supports 96 buttons (64 on digital inputs and 32 on analog). Since there can only be 32 parameters per message, user has two options. First one is to simply send two GET ALL requests, one with MESSAGE_PART
set to 0
, second with same byte set to 1
and third with MESSAGE_PART
being 2
. Second option is to set MESSAGE_PART
byte to special value, 7F
. In that case, board will keep returning messages for selected section until all parameters are sent.
-
MESSAGE_STATUS
:0
(Request) -
MESSAGE_PART
:7F
-
WISH
:GET
(0
) -
AMOUNT
:ALL
(1
) -
BLOCK
: Buttons (1
) -
SECTION
: MIDI ID (2
) -
INDEX
: 0 (unused but required) -
NEW_VALUE
: 0 (unused but required) -
Request:
F0 00 53 43 00 7F 00 01 01 02 00 00 F7
-
Response 1:
F0 00 53 43 00 7F 00 01 01 02 00 00 00 01 02 03 04 05 06 07 08 09 0A 0B 0C 0D 0E 0F 10 11 12 13 14 15 16 17 18 19 1A 1B 1C 1D 1E 1F F7
-
Response 2:
F0 00 53 43 00 7F 00 01 01 02 00 00 20 21 22 23 24 25 26 27 28 29 2A 2B 2C 2D 2E 2F 30 31 32 33 34 35 36 37 38 39 3A 3B 3C 3D 3E 3F F7
-
Response 3:
F0 00 53 43 00 7F 00 01 01 02 00 00 40 41 42 43 44 45 46 47 48 49 4A 4B 4C 4D 4E 4F 50 51 52 53 54 55 56 57 58 59 5A 5B 5C 5D 5E 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 7F 00 01 01 02 00 00 F7
Once this message has been received, the stream of messages is finished.
User wants to turn LED 1 (index 0) on.
-
MESSAGE_STATUS
:0
(Request) -
MESSAGE_PART
:1
-
WISH
:SET
(1
) -
AMOUNT
:SINGLE
(0
) -
BLOCK
: LEDs (4
) -
SECTION
: LED color testing (5
) -
INDEX
:0
(LED 1) -
NEW_VALUE
:1
NEW_VALUE
represents LED color. This example assumes that we're trying to turn single-color LED on so any value between 1 and 7 will turn the LED on (see LED color testing). To turn LED off, value 0
needs to be specified.
- Request:
F0 00 53 43 00 00 01 00 04 05 00 01 F7
- Response:
F0 00 53 43 01 00 01 00 04 05 00 01 F7
User wants to configure button 36 to send program change event instead of note event.
-
MESSAGE_STATUS
:0
(Request) -
MESSAGE_PART
:1
-
WISH
:SET
(1
) -
AMOUNT
:SINGLE
(0
) -
BLOCK
: Button (1
) -
SECTION
: Message type (1
) -
INDEX
:4
(index 0 in second message part is button index 32, 4 is 36) -
NEW_VALUE
: Program change (1
) -
Request:
F0 00 53 43 00 01 01 00 01 01 04 01 F7
-
Response:
F0 00 53 43 01 01 01 00 01 01 04 01 F7
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 MSB
: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
: Buttons (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 2:
F0 00 53 43 00 7F 00 01 01 02 00 00 20 21 22 23 24 25 26 27 28 29 2A 2B 2C 2D 2E 2F 30 31 32 33 34 35 36 37 38 39 3A 3B 3C 3D 3E 3F F7
-
Response 3:
F0 00 53 43 00 7F 00 01 01 02 00 00 40 41 42 43 44 45 46 47 48 49 4A 4B 4C 4D 4E 4F 50 51 52 53 54 55 56 57 58 59 5A 5B 5C 5D 5E 5F 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 7F 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
:1
-
WISH
:SET
(1
) -
AMOUNT
:SINGLE
(0
) -
BLOCK
: LEDs (4
) -
SECTION
: LED color testing (0
) -
INDEX MSB
:0
(LED 1) -
INDEX LSB
:0
(LED 1) -
NEW_VALUE MSB
:0
-
NEW_VALUE LSB
:1
-
Request:
F0 00 53 43 00 00 01 00 04 00 00 00 00 01 F7
-
Response:
F0 00 53 43 01 00 01 00 04 00 00 00 00 01 F7
User wants to configure button 36 to send program change event instead of note event.
-
MESSAGE_STATUS
:0
(Request) -
MESSAGE_PART
:1
-
WISH
:SET
(1
) -
AMOUNT
:SINGLE
(0
) -
BLOCK
: Button (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 01 01 00 01 01 00 04 00 01 F7
-
Response:
F0 00 53 43 01 01 01 00 01 01 00 04 00 01 F7
-
MESSAGE_STATUS
:0
(Request) -
MESSAGE_PART
:1
-
WISH
:SET
(1
) -
AMOUNT
:SINGLE
(0
) -
BLOCK
: Analog (3
) -
SECTION
: Lower CC limit / LSB (3
) -
INDEX MSB
:0
-
INDEX LSB
:5
-
NEW_VALUE MSB
:32
-
NEW_VALUE LSB
:4
-
Request:
F0 00 53 43 00 00 01 00 03 03 00 05 32 04 F7
-
Response:
F0 00 53 43 01 00 01 00 03 03 00 05 32 04 F7
Hardware
- Supported microcontrollers
- Supported components
- Pinouts for supported boards
- Recommended components and where to get them
- LED indicators
Configuration and usage
Advanced