Skip to content

Latest commit

 

History

History
149 lines (114 loc) · 4.17 KB

SDK.md

File metadata and controls

149 lines (114 loc) · 4.17 KB

Libwing SDK Documentation

Libwing is a C++ library for interfacing with Behringer Wing digital mixing consoles. It provides functionality for discovering Wing consoles on the network, connecting to them, reading/writing console parameters, and receiving any changes made on the mixer itself.

There is a C wrapper for this library. It generally follows the C++ API. You can find it in wing_c_api.h.

Basic Concepts

The Wing console exposes its functionality through a tree of nodes. Each node has:

  • A unique numeric ID
  • A hierarchical path name (like a filesystem path)
  • A type (string, float, integer, enum, etc.)
  • Optional min/max values and units
  • Read/write or read-only access

Getting Started

Discovery

To find Wing consoles on your network:

auto discovered = WingConsole::scan();
if (!discovered.empty()) {
    // Found at least one console
    auto firstConsole = discovered[0];
    std::cout << "Found console: " << firstConsole.name 
              << " at IP: " << firstConsole.ip << std::endl;
}

Connecting

Once you have a console's IP address, you can connect to it:

WingConsole console = WingConsole::connect("192.168.1.100");

Communication Model

The Wing console uses an asynchronous communication model:

  1. You make requests using methods like requestNodeDefinition() and requestNodeData()
  2. Responses come back through callback functions you register
  3. The Wing device also sends unsolicited updates when values change on the mixer
  4. All messages are received through the read() method, which never returns

Callbacks

Register callbacks to handle different types of messages. These callbacks will be called on the thread from which the read() method was called.

// Called when a node definition is received
console.onNodeDefinition = [](NodeDefinition node) {
    std::cout << "Got definition for node: " << node.name << std::endl;
};

// Called when node data/values are received, in response to a request or
// unsolicited due to manipulation of the console
console.onNodeData = [](uint32_t id, NodeData data) {
    std::cout
        << "Node "
        << NodeDefinition::nodeIdToName(id)
        << " ("
        << id
        << ") = "
        << data.getString()
        << std::endl;
};

// Called when a request is complete. You will get one of these for each time
// you call `requestNodeDefinition()` or `requestNodeData()`.
console.onRequestEnd = []() {
    std::cout << "Request completed" << std::endl;
};

IDs and Names

Nodes are identified by numeric IDs. You can convert between IDs and names:

uint32_t id = WingConsole::nodeNameToId(name);  // Returns the ID for this node

and

std::string name = WingConsole::nodeIdToName(id);  // Returns the ID for this node

The mapping of name to ID is generated by the wingschema utility and is pulled into the lirbary at compile time. It is quite large (over 35k entries as of firmware 3.0.5), and adds about 1MB to the library size. If you need this trimmed and can give up this name/id mapping, just delete all (or some) of the rows in wing-schema.cpp.

Reading Data

To start receiving data:

console.read();  // This blocks and processes incoming messages

You can request data from the console:

// Request a node definition -- this is the schema of the node.
// You can pass zero (0) to get the root nodes.
console.requestNodeDefinition(id);
// Request a node's data -- this is the parameter value.
console.requestNodeData(id);

These methods can be called on any thread.

Writing Data

To change values on the console:

// Set values by node ID
console.setString(nodeId, "value");
console.setFloat(nodeId, 0.5f);
console.setInt(nodeId, 42);

These methods can be called on any thread.

Example Programs

wingmon

The wingmon program demonstrates basic connection and monitoring:

  • Discovers consoles on the network
  • Connects to the first one found
  • Monitors and displays value changes

wingschema

The wingschema program shows how to:

  • Traverse the entire node tree
  • Request and process node definitions
  • Generate documentation of the console's parameter space
  • Handle asynchronous responses systematically