mirror of
https://github.com/wheremyfoodat/Panda3DS.git
synced 2025-04-20 20:49:12 +12:00
Add external libraries
This commit is contained in:
parent
70f443b06e
commit
e8dc11cc31
17 changed files with 2010 additions and 0 deletions
423
third_party/open-bp-cpp/source/buttplugclient.cpp
vendored
Normal file
423
third_party/open-bp-cpp/source/buttplugclient.cpp
vendored
Normal file
|
@ -0,0 +1,423 @@
|
|||
#include "../include/buttplugclient.h"
|
||||
|
||||
/*
|
||||
TODO: Let the user access the devices in more details, that is, how many scalar cmds,
|
||||
how many sensor cmds and their types. Implement some kind of logging to track whether
|
||||
commands are successful. Implement Linear and Rotation cmds. Port to Linux.
|
||||
Investigate whether push back won't ruin sending scalar and sensor cmds, since the
|
||||
device list does not provide scalar or sensor indices (don't think it will).
|
||||
*/
|
||||
|
||||
|
||||
// Connection function with a function parameter which acts as a callback.
|
||||
int Client::connect(void (*callFunc)(const mhl::Messages)) {
|
||||
FullUrl = lUrl + ":" + std::to_string(lPort);
|
||||
|
||||
webSocket.setUrl(FullUrl);
|
||||
|
||||
// Ping interval option.
|
||||
webSocket.setPingInterval(10);
|
||||
|
||||
// Per message deflate connection is enabled by default. You can tweak its parameters or disable it
|
||||
webSocket.disablePerMessageDeflate();
|
||||
|
||||
// Set the callback function of the websocket
|
||||
std::function<void(const ix::WebSocketMessagePtr&)> callback = std::bind(&Client::callbackFunction, this, std::placeholders::_1);
|
||||
messageCallback = callFunc;
|
||||
|
||||
webSocket.setOnMessageCallback(callback);
|
||||
|
||||
// Start websocket and indicate that it is connecting (non blocking function, other functions must wait for it to connect).
|
||||
webSocket.start();
|
||||
isConnecting = 1;
|
||||
|
||||
// Start a message handler thread and detach it.
|
||||
std::thread messageHandler(&Client::messageHandling, this);
|
||||
messageHandler.detach();
|
||||
|
||||
// Connect to server, specifically send a RequestServerInfo
|
||||
connectServer();
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
// Websocket callback function.
|
||||
void Client::callbackFunction(const ix::WebSocketMessagePtr& msg) {
|
||||
// If a message is received to the websocket, pass it to the message handler and notify to stop waiting.
|
||||
if (msg->type == ix::WebSocketMessageType::Message)
|
||||
{
|
||||
// Mutex lock this scope.
|
||||
std::lock_guard<std::mutex> lock{msgMx};
|
||||
// Push message.
|
||||
q.push(msg->str);
|
||||
// Notify conditional variable to stop waiting.
|
||||
cond.notify_one();
|
||||
}
|
||||
|
||||
// Handle websocket errors.
|
||||
if (msg->type == ix::WebSocketMessageType::Error)
|
||||
{
|
||||
std::stringstream ss;
|
||||
ss << "Error: " << msg->errorInfo.reason << std::endl;
|
||||
ss << "#retries: " << msg->errorInfo.retries << std::endl;
|
||||
ss << "Wait time(ms): " << msg->errorInfo.wait_time << std::endl;
|
||||
ss << "HTTP Status: " << msg->errorInfo.http_status << std::endl;
|
||||
std::cout << ss.str() << std::endl;
|
||||
}
|
||||
|
||||
// Set atomic variable that websocket is connected once it is open.
|
||||
if (msg->type == ix::WebSocketMessageType::Open) {
|
||||
wsConnected = 1;
|
||||
condWs.notify_all();
|
||||
}
|
||||
|
||||
// Set atomic variable that websocket is not connected if socket closes.
|
||||
if (msg->type == ix::WebSocketMessageType::Close) {
|
||||
wsConnected = 0;
|
||||
}
|
||||
}
|
||||
|
||||
// Function to start scanning in the server.
|
||||
void Client::startScan() {
|
||||
// Mutex lock scope.
|
||||
std::lock_guard<std::mutex> lock{msgMx};
|
||||
|
||||
// Get a request class from message handling header.
|
||||
mhl::Requests req;
|
||||
// Set the ID of message according to the message enum in message handling header.
|
||||
req.startScanning.Id = static_cast<unsigned int>(mhl::MessageTypes::StartScanning);
|
||||
// Set message type for the handler to recognize what message it is.
|
||||
messageHandler.messageType = mhl::MessageTypes::StartScanning;
|
||||
|
||||
// Convert the returned handled request message class to json.
|
||||
json j = json::array({ messageHandler.handleClientRequest(req) });
|
||||
std::cout << j << std::endl;
|
||||
|
||||
// Start a thread that sends the message.
|
||||
std::thread sendHandler(&Client::sendMessage, this, j, messageHandler.messageType);
|
||||
sendHandler.detach();
|
||||
}
|
||||
|
||||
// Function to stop scanning, same as before but different type.
|
||||
void Client::stopScan() {
|
||||
std::lock_guard<std::mutex> lock{msgMx};
|
||||
|
||||
mhl::Requests req;
|
||||
req.stopScanning.Id = static_cast<unsigned int>(mhl::MessageTypes::StopScanning);
|
||||
messageHandler.messageType = mhl::MessageTypes::StopScanning;
|
||||
|
||||
json j = json::array({ messageHandler.handleClientRequest(req) });
|
||||
std::cout << j << std::endl;
|
||||
|
||||
std::thread sendHandler(&Client::sendMessage, this, j, messageHandler.messageType);
|
||||
sendHandler.detach();
|
||||
}
|
||||
|
||||
// Function to get device list, same as before but different type.
|
||||
void Client::requestDeviceList() {
|
||||
std::lock_guard<std::mutex> lock{msgMx};
|
||||
|
||||
mhl::Requests req;
|
||||
req.stopScanning.Id = static_cast<unsigned int>(mhl::MessageTypes::RequestDeviceList);
|
||||
messageHandler.messageType = mhl::MessageTypes::RequestDeviceList;
|
||||
|
||||
json j = json::array({ messageHandler.handleClientRequest(req) });
|
||||
std::cout << j << std::endl;
|
||||
|
||||
std::thread sendHandler(&Client::sendMessage, this, j, messageHandler.messageType);
|
||||
sendHandler.detach();
|
||||
}
|
||||
|
||||
// Function to send RequestServerInfo, same as before but different type.
|
||||
void Client::connectServer() {
|
||||
std::lock_guard<std::mutex> lock{msgMx};
|
||||
|
||||
mhl::Requests req;
|
||||
req.requestServerInfo.Id = static_cast<unsigned int>(mhl::MessageTypes::RequestServerInfo);
|
||||
req.requestServerInfo.ClientName = "Testing";
|
||||
req.requestServerInfo.MessageVersion = 3;
|
||||
messageHandler.messageType = mhl::MessageTypes::RequestServerInfo;
|
||||
|
||||
json j = json::array({ messageHandler.handleClientRequest(req) });
|
||||
std::cout << j << std::endl;
|
||||
|
||||
std::thread sendHandler(&Client::sendMessage, this, j, messageHandler.messageType);
|
||||
sendHandler.detach();
|
||||
}
|
||||
|
||||
// Function that actually sends the message.
|
||||
void Client::sendMessage(json msg, mhl::MessageTypes mType) {
|
||||
// First check whether a connection process is started.
|
||||
if (!isConnecting && !wsConnected) {
|
||||
std::cout << "Client is not connected and not started, start before sending a message" << std::endl;
|
||||
return;
|
||||
}
|
||||
// If started, wait for the socket to connect first.
|
||||
if (!wsConnected && isConnecting) {
|
||||
std::unique_lock<std::mutex> lock{msgMx};
|
||||
DEBUG_MSG("Waiting for socket to connect");
|
||||
auto wsConnStatus = [this]() {return wsConnected == 1; };
|
||||
condWs.wait(lock, wsConnStatus);
|
||||
std::cout << "Connected to socket" << std::endl;
|
||||
//webSocket.send(msg.dump());
|
||||
}
|
||||
// Once socket is connected, either wait for client to connect, or send a message if the message type
|
||||
// is a request server info, since this is our client connection message.
|
||||
if (!clientConnected && isConnecting) {
|
||||
std::cout << "Waiting for client to connect" << std::endl;
|
||||
if (mType == mhl::MessageTypes::RequestServerInfo) {
|
||||
webSocket.send(msg.dump());
|
||||
if (logging) logInfo.logSentMessage("RequestServerInfo", static_cast<unsigned int>(mType));
|
||||
std::cout << "Started connection to client" << std::endl;
|
||||
return;
|
||||
}
|
||||
std::unique_lock<std::mutex> lock{msgMx};
|
||||
auto clientConnStatus = [this]() {return clientConnected == 1; };
|
||||
condClient.wait(lock, clientConnStatus);
|
||||
std::cout << "Connected to client" << std::endl;
|
||||
webSocket.send(msg.dump());
|
||||
}
|
||||
// If everything is connected, simply send message and log request if enabled.
|
||||
else if (wsConnected && clientConnected) webSocket.send(msg.dump());
|
||||
if (logging) {
|
||||
auto result = std::find_if(
|
||||
messageHandler.messageMap.begin(),
|
||||
messageHandler.messageMap.end(),
|
||||
[mType](std::pair<const mhl::MessageTypes, std::basic_string<char> > mo) {return mo.first == mType; });
|
||||
std::string msgTypeText = result->second;
|
||||
logInfo.logSentMessage(msgTypeText, static_cast<unsigned int>(mType));
|
||||
}
|
||||
}
|
||||
|
||||
// This takes the device data from message handler and puts it in to main device class
|
||||
// for user access.
|
||||
void Client::updateDevices() {
|
||||
std::vector<DeviceClass> tempDeviceVec;
|
||||
// Iterate through available devices.
|
||||
for (auto& el : messageHandler.deviceList.Devices) {
|
||||
DeviceClass tempDevice;
|
||||
// Set the appropriate class variables.
|
||||
tempDevice.deviceID = el.DeviceIndex;
|
||||
tempDevice.deviceName = el.DeviceName;
|
||||
tempDevice.displayName = el.DeviceDisplayName;
|
||||
if (el.DeviceMessages.size() > 0) {
|
||||
for (auto& el2 : el.DeviceMessages) tempDevice.commandTypes.push_back(el2.CmdType);
|
||||
}
|
||||
// Push back the device in vector.
|
||||
tempDeviceVec.push_back(tempDevice);
|
||||
}
|
||||
devices = tempDeviceVec;
|
||||
}
|
||||
|
||||
// Mutex locked function to provide the user with available devices.
|
||||
std::vector<DeviceClass> Client::getDevices() {
|
||||
std::lock_guard<std::mutex> lock{msgMx};
|
||||
return devices;
|
||||
}
|
||||
|
||||
SensorClass Client::getSensors() {
|
||||
std::lock_guard<std::mutex> lock{msgMx};
|
||||
return sensorData;
|
||||
}
|
||||
|
||||
int Client::findDevice(DeviceClass dev) {
|
||||
for (int i = 0; i < messageHandler.deviceList.Devices.size(); i++)
|
||||
if (messageHandler.deviceList.Devices[i].DeviceIndex == dev.deviceID)
|
||||
return i;
|
||||
return -1;
|
||||
}
|
||||
|
||||
void Client::stopDevice(DeviceClass dev) {
|
||||
std::lock_guard<std::mutex> lock{msgMx};
|
||||
|
||||
mhl::Requests req;
|
||||
req.stopDeviceCmd.Id = static_cast<unsigned int>(mhl::MessageTypes::StopDeviceCmd);
|
||||
req.stopDeviceCmd.DeviceIndex = dev.deviceID;
|
||||
|
||||
messageHandler.messageType = mhl::MessageTypes::StopDeviceCmd;
|
||||
|
||||
json j = json::array({ messageHandler.handleClientRequest(req) });
|
||||
std::cout << j << std::endl;
|
||||
|
||||
std::thread sendHandler(&Client::sendMessage, this, j, messageHandler.messageType);
|
||||
sendHandler.detach();
|
||||
}
|
||||
|
||||
void Client::stopAllDevices() {
|
||||
std::lock_guard<std::mutex> lock{msgMx};
|
||||
|
||||
mhl::Requests req;
|
||||
req.stopDeviceCmd.Id = static_cast<unsigned int>(mhl::MessageTypes::StopAllDevices);
|
||||
|
||||
messageHandler.messageType = mhl::MessageTypes::StopAllDevices;
|
||||
|
||||
json j = json::array({ messageHandler.handleClientRequest(req) });
|
||||
std::cout << j << std::endl;
|
||||
|
||||
std::thread sendHandler(&Client::sendMessage, this, j, messageHandler.messageType);
|
||||
sendHandler.detach();
|
||||
}
|
||||
|
||||
void Client::sendScalar(DeviceClass dev, double str) {
|
||||
std::lock_guard<std::mutex> lock{msgMx};
|
||||
int idx = findDevice(dev);
|
||||
if (idx > -1) {
|
||||
mhl::Requests req;
|
||||
|
||||
for (auto& el1 : messageHandler.deviceList.Devices[idx].DeviceMessages) {
|
||||
std::string testScalar = "ScalarCmd";
|
||||
if (!el1.CmdType.compare(testScalar)) {
|
||||
req.scalarCmd.DeviceIndex = messageHandler.deviceList.Devices[idx].DeviceIndex;
|
||||
req.scalarCmd.Id = static_cast<unsigned int>(mhl::MessageTypes::ScalarCmd);
|
||||
int i = 0;
|
||||
for (auto& el2: el1.DeviceCmdAttributes) {
|
||||
Scalar sc;
|
||||
sc.ActuatorType = el2.ActuatorType;
|
||||
sc.ScalarVal = str;
|
||||
sc.Index = i;
|
||||
req.scalarCmd.Scalars.push_back(sc);
|
||||
i++;
|
||||
}
|
||||
messageHandler.messageType = mhl::MessageTypes::ScalarCmd;
|
||||
|
||||
json j = json::array({ messageHandler.handleClientRequest(req) });
|
||||
std::cout << j << std::endl;
|
||||
|
||||
std::thread sendHandler(&Client::sendMessage, this, j, messageHandler.messageType);
|
||||
sendHandler.detach();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void Client::sensorRead(DeviceClass dev, int senIndex) {
|
||||
std::lock_guard<std::mutex> lock{msgMx};
|
||||
int idx = findDevice(dev);
|
||||
if (idx > -1) {
|
||||
mhl::Requests req;
|
||||
|
||||
for (auto& el1 : messageHandler.deviceList.Devices[idx].DeviceMessages) {
|
||||
std::string testSensor = "SensorReadCmd";
|
||||
if (!el1.CmdType.compare(testSensor)) {
|
||||
req.sensorReadCmd.DeviceIndex = messageHandler.deviceList.Devices[idx].DeviceIndex;
|
||||
req.sensorReadCmd.Id = static_cast<unsigned int>(mhl::MessageTypes::SensorReadCmd);
|
||||
req.sensorReadCmd.SensorIndex = senIndex;
|
||||
req.sensorReadCmd.SensorType = el1.DeviceCmdAttributes[senIndex].SensorType;
|
||||
int i = 0;
|
||||
messageHandler.messageType = mhl::MessageTypes::SensorReadCmd;
|
||||
|
||||
json j = json::array({ messageHandler.handleClientRequest(req) });
|
||||
std::cout << j << std::endl;
|
||||
|
||||
std::thread sendHandler(&Client::sendMessage, this, j, messageHandler.messageType);
|
||||
sendHandler.detach();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void Client::sensorSubscribe(DeviceClass dev, int senIndex) {
|
||||
std::lock_guard<std::mutex> lock{msgMx};
|
||||
int idx = findDevice(dev);
|
||||
if (idx > -1) {
|
||||
mhl::Requests req;
|
||||
|
||||
for (auto& el1 : messageHandler.deviceList.Devices[idx].DeviceMessages) {
|
||||
std::string testSensor = "SensorReadCmd";
|
||||
if (!el1.CmdType.compare(testSensor)) {
|
||||
req.sensorSubscribeCmd.DeviceIndex = messageHandler.deviceList.Devices[idx].DeviceIndex;
|
||||
req.sensorSubscribeCmd.Id = static_cast<unsigned int>(mhl::MessageTypes::SensorSubscribeCmd);
|
||||
req.sensorSubscribeCmd.SensorIndex = senIndex;
|
||||
req.sensorSubscribeCmd.SensorType = el1.DeviceCmdAttributes[senIndex].SensorType;
|
||||
int i = 0;
|
||||
messageHandler.messageType = mhl::MessageTypes::SensorSubscribeCmd;
|
||||
|
||||
json j = json::array({ messageHandler.handleClientRequest(req) });
|
||||
std::cout << j << std::endl;
|
||||
|
||||
std::thread sendHandler(&Client::sendMessage, this, j, messageHandler.messageType);
|
||||
sendHandler.detach();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void Client::sensorUnsubscribe(DeviceClass dev, int senIndex) {
|
||||
std::lock_guard<std::mutex> lock{msgMx};
|
||||
int idx = findDevice(dev);
|
||||
if (idx > -1) {
|
||||
mhl::Requests req;
|
||||
|
||||
for (auto& el1 : messageHandler.deviceList.Devices[idx].DeviceMessages) {
|
||||
std::string testSensor = "SensorReadCmd";
|
||||
if (!el1.CmdType.compare(testSensor)) {
|
||||
req.sensorUnsubscribeCmd.DeviceIndex = messageHandler.deviceList.Devices[idx].DeviceIndex;
|
||||
req.sensorUnsubscribeCmd.Id = static_cast<unsigned int>(mhl::MessageTypes::SensorUnsubscribeCmd);
|
||||
req.sensorUnsubscribeCmd.SensorIndex = senIndex;
|
||||
req.sensorUnsubscribeCmd.SensorType = el1.DeviceCmdAttributes[senIndex].SensorType;
|
||||
int i = 0;
|
||||
messageHandler.messageType = mhl::MessageTypes::SensorUnsubscribeCmd;
|
||||
|
||||
json j = json::array({ messageHandler.handleClientRequest(req) });
|
||||
std::cout << j << std::endl;
|
||||
|
||||
std::thread sendHandler(&Client::sendMessage, this, j, messageHandler.messageType);
|
||||
sendHandler.detach();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Message handling function.
|
||||
// TODO: add client disconnect which stops this thread too.
|
||||
void Client::messageHandling() {
|
||||
// Start infinite loop.
|
||||
while (1) {
|
||||
std::unique_lock<std::mutex> lock{msgMx};
|
||||
|
||||
// A lambda that waits to receive messages in the queue.
|
||||
cond.wait(
|
||||
lock,
|
||||
[this] {
|
||||
return !q.empty();
|
||||
}
|
||||
);
|
||||
|
||||
// If received, grab the message and pop it out.
|
||||
std::string value = q.front();
|
||||
q.pop();
|
||||
|
||||
// Handle the message.
|
||||
json j = json::parse(value);
|
||||
// Iterate through messages since server can send array.
|
||||
for (auto& el : j.items()) {
|
||||
// Pass the message to actual handler.
|
||||
messageHandler.handleServerMessage(el.value());
|
||||
|
||||
// If server info received, it means client is connected so set the connection atomic variables
|
||||
// and notify all send threads that they are good to go.
|
||||
if (messageHandler.messageType == mhl::MessageTypes::ServerInfo) {
|
||||
isConnecting = 0;
|
||||
clientConnected = 1;
|
||||
condClient.notify_all();
|
||||
}
|
||||
// If a device updated message, make sure to update the devices for the user.
|
||||
if (messageHandler.messageType == mhl::MessageTypes::DeviceAdded ||
|
||||
messageHandler.messageType == mhl::MessageTypes::DeviceList ||
|
||||
messageHandler.messageType == mhl::MessageTypes::DeviceRemoved) updateDevices();
|
||||
|
||||
if (messageHandler.messageType == mhl::MessageTypes::SensorReading) sensorData = messageHandler.sensorReading;
|
||||
|
||||
// Log if logging is enabled.
|
||||
if (logging)
|
||||
logInfo.logReceivedMessage(el.value().begin().key(), static_cast<unsigned int>(messageHandler.messageType));
|
||||
|
||||
// Callback function for the user.
|
||||
messageCallback(messageHandler);
|
||||
}
|
||||
|
||||
lock.unlock();
|
||||
|
||||
std::cout << "[subscriber] Received " << value << std::endl;
|
||||
}
|
||||
}
|
20
third_party/open-bp-cpp/source/log.cpp
vendored
Normal file
20
third_party/open-bp-cpp/source/log.cpp
vendored
Normal file
|
@ -0,0 +1,20 @@
|
|||
#include "../include/log.h"
|
||||
|
||||
void Logger::init(std::string filename) {
|
||||
logFile.open(filename, std::fstream::out);
|
||||
}
|
||||
|
||||
void Logger::logSentMessage(std::string rqType, unsigned int id) {
|
||||
end = std::chrono::system_clock::now();
|
||||
std::chrono::duration<double> elapsed_seconds = end - start;
|
||||
RequestQueue tempQ;
|
||||
tempQ.id = id;
|
||||
tempQ.requestType = rqType;
|
||||
rQueue.push_back(tempQ);
|
||||
|
||||
logFile << elapsed_seconds.count() << " s, Request type sent: " << rqType << ", ID: " << id << std::endl;
|
||||
}
|
||||
|
||||
void Logger::logReceivedMessage(std::string repType, unsigned int id) {
|
||||
//end = std::chrono::system_clock::now();
|
||||
}
|
100
third_party/open-bp-cpp/source/messageHandler.cpp
vendored
Normal file
100
third_party/open-bp-cpp/source/messageHandler.cpp
vendored
Normal file
|
@ -0,0 +1,100 @@
|
|||
#include "../include/messageHandler.h"
|
||||
|
||||
namespace mhl {
|
||||
// Function that handles messages received from server.
|
||||
void Messages::handleServerMessage(json& msg) {
|
||||
// Grab the string of message type and find it in the map.
|
||||
auto msgType = msg.begin().key();
|
||||
auto result = std::find_if(
|
||||
messageMap.begin(),
|
||||
messageMap.end(),
|
||||
[msgType](std::pair<const mhl::MessageTypes, std::basic_string<char> > mo) {return mo.second == msgType; });
|
||||
auto msgEnumType = result->first;
|
||||
|
||||
int i = 0;
|
||||
// Switch that converts message to class.
|
||||
switch (msgEnumType) {
|
||||
case mhl::MessageTypes::Ok:
|
||||
messageType = mhl::MessageTypes::Ok;
|
||||
ok = msg.get<msg::Ok>();
|
||||
break;
|
||||
case mhl::MessageTypes::Error:
|
||||
messageType = mhl::MessageTypes::Error;
|
||||
error = msg.get<msg::Error>();
|
||||
break;
|
||||
case mhl::MessageTypes::ServerInfo:
|
||||
// Set message type and convert to class from json.
|
||||
std::cout << "Server info!" << std::endl;
|
||||
messageType = mhl::MessageTypes::ServerInfo;
|
||||
serverInfo = msg.get<msg::ServerInfo>();
|
||||
break;
|
||||
case mhl::MessageTypes::ScanningFinished:
|
||||
break;
|
||||
case mhl::MessageTypes::DeviceList:
|
||||
std::cout << "Device list!" << std::endl;
|
||||
messageType = mhl::MessageTypes::DeviceList;
|
||||
deviceList = msg.get<msg::DeviceList>();
|
||||
break;
|
||||
case mhl::MessageTypes::DeviceAdded:
|
||||
deviceAdded = msg.get<msg::DeviceAdded>();
|
||||
messageType = mhl::MessageTypes::DeviceAdded;
|
||||
// Push back to message handler class device list the newly added device.
|
||||
deviceList.Devices.push_back(deviceAdded.device);
|
||||
break;
|
||||
case mhl::MessageTypes::DeviceRemoved:
|
||||
deviceRemoved = msg.get<msg::DeviceRemoved>();
|
||||
messageType = mhl::MessageTypes::DeviceRemoved;
|
||||
// Erase device from message handler class device list.
|
||||
for (auto& el : deviceList.Devices) {
|
||||
if (deviceRemoved.DeviceIndex == el.DeviceIndex) {
|
||||
deviceList.Devices.erase(deviceList.Devices.begin() + i);
|
||||
break;
|
||||
}
|
||||
i++;
|
||||
}
|
||||
break;
|
||||
case mhl::MessageTypes::SensorReading:
|
||||
sensorReading = msg.get<msg::SensorReading>();
|
||||
messageType = mhl::MessageTypes::SensorReading;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// Convert client request classes to json.
|
||||
json Messages::handleClientRequest(Requests req) {
|
||||
json j;
|
||||
switch (messageType) {
|
||||
case mhl::MessageTypes::RequestServerInfo:
|
||||
j = req.requestServerInfo;
|
||||
break;
|
||||
case mhl::MessageTypes::RequestDeviceList:
|
||||
j = req.requestDeviceList;
|
||||
break;
|
||||
case mhl::MessageTypes::StartScanning:
|
||||
j = req.startScanning;
|
||||
break;
|
||||
case mhl::MessageTypes::StopScanning:
|
||||
j = req.stopScanning;
|
||||
break;
|
||||
case mhl::MessageTypes::StopDeviceCmd:
|
||||
j = req.stopDeviceCmd;
|
||||
break;
|
||||
case mhl::MessageTypes::StopAllDevices:
|
||||
j = req.stopAllDevices;
|
||||
break;
|
||||
case mhl::MessageTypes::ScalarCmd:
|
||||
j = req.scalarCmd;
|
||||
break;
|
||||
case mhl::MessageTypes::SensorReadCmd:
|
||||
j = req.sensorReadCmd;
|
||||
break;
|
||||
case mhl::MessageTypes::SensorSubscribeCmd:
|
||||
j = req.sensorSubscribeCmd;
|
||||
break;
|
||||
case mhl::MessageTypes::SensorUnsubscribeCmd:
|
||||
j = req.sensorUnsubscribeCmd;
|
||||
break;
|
||||
}
|
||||
return j;
|
||||
}
|
||||
}
|
218
third_party/open-bp-cpp/source/messages.cpp
vendored
Normal file
218
third_party/open-bp-cpp/source/messages.cpp
vendored
Normal file
|
@ -0,0 +1,218 @@
|
|||
#include "../include/messages.h"
|
||||
|
||||
// Function definitions for json conversions.
|
||||
namespace msg {
|
||||
void to_json(json& j, const RequestServerInfo& k) {
|
||||
j["RequestServerInfo"] = { {"Id", k.Id}, {"ClientName", k.ClientName}, {"MessageVersion", k.MessageVersion} };
|
||||
}
|
||||
|
||||
void to_json(json& j, const StartScanning& k) {
|
||||
j["StartScanning"] = { {"Id", k.Id} };
|
||||
}
|
||||
|
||||
void to_json(json& j, const StopScanning& k) {
|
||||
j["StopScanning"] = { {"Id", k.Id} };
|
||||
}
|
||||
|
||||
void to_json(json& j, const RequestDeviceList& k) {
|
||||
j["RequestDeviceList"] = { {"Id", k.Id} };
|
||||
}
|
||||
|
||||
void to_json(json& j, const StopDeviceCmd& k) {
|
||||
j["StopDeviceCmd"] = { {"Id", k.Id}, {"DeviceIndex", k.DeviceIndex} };
|
||||
}
|
||||
|
||||
void to_json(json& j, const StopAllDevices& k) {
|
||||
j["StopAllDevices"] = { {"Id", k.Id} };
|
||||
}
|
||||
|
||||
void to_json(json& j, const ScalarCmd& k) {
|
||||
j["ScalarCmd"] = { {"Id", k.Id}, {"DeviceIndex", k.DeviceIndex} };
|
||||
j["ScalarCmd"]["Scalars"] = json::array();
|
||||
|
||||
for (auto& vec : k.Scalars) {
|
||||
json jTemp = { { "Index", vec.Index }, { "Scalar", vec.ScalarVal }, { "ActuatorType", vec.ActuatorType } };
|
||||
j["ScalarCmd"]["Scalars"].insert(j["ScalarCmd"]["Scalars"].end(), jTemp);
|
||||
}
|
||||
}
|
||||
|
||||
void to_json(json& j, const SensorReadCmd& k) {
|
||||
j["SensorReadCmd"] = { {"Id", k.Id}, {"DeviceIndex", k.DeviceIndex}, {"SensorIndex", k.SensorIndex}, {"SensorType", k.SensorType}};
|
||||
}
|
||||
|
||||
void to_json(json& j, const SensorSubscribeCmd& k) {
|
||||
j["SensorSubscribeCmd"] = { {"Id", k.Id}, {"DeviceIndex", k.DeviceIndex}, {"SensorIndex", k.SensorIndex}, {"SensorType", k.SensorType} };
|
||||
}
|
||||
|
||||
void to_json(json& j, const SensorUnsubscribeCmd& k) {
|
||||
j["SensorUnsubscribeCmd"] = { {"Id", k.Id}, {"DeviceIndex", k.DeviceIndex}, {"SensorIndex", k.SensorIndex}, {"SensorType", k.SensorType} };
|
||||
}
|
||||
|
||||
void from_json(const json& j, ServerInfo& k) {
|
||||
json jTemp;
|
||||
j.at("ServerInfo").get_to(jTemp);
|
||||
jTemp.at("Id").get_to(k.Id);
|
||||
jTemp.at("ServerName").get_to(k.ServerName);
|
||||
jTemp.at("MessageVersion").get_to(k.MessageVersion);
|
||||
jTemp.at("MaxPingTime").get_to(k.MaxPingTime);
|
||||
}
|
||||
|
||||
void from_json(const json& j, Ok& k) {
|
||||
json jTemp;
|
||||
j.at("Ok").get_to(jTemp);
|
||||
jTemp.at("Id").get_to(k.Id);
|
||||
}
|
||||
|
||||
void from_json(const json& j, Error& k) {
|
||||
json jTemp;
|
||||
j.at("Error").get_to(jTemp);
|
||||
jTemp.at("Id").get_to(k.Id);
|
||||
jTemp.at("ErrorCode").get_to(k.ErrorCode);
|
||||
jTemp.at("ErrorMessage").get_to(k.ErrorMessage);
|
||||
}
|
||||
|
||||
void from_json(const json& j, DeviceRemoved& k) {
|
||||
json jTemp;
|
||||
j.at("DeviceRemoved").get_to(jTemp);
|
||||
jTemp.at("Id").get_to(k.Id);
|
||||
jTemp.at("DeviceIndex").get_to(k.DeviceIndex);
|
||||
}
|
||||
|
||||
// The device conversion functions are slightly more complicated since they have some
|
||||
// nested objects and arrays, but otherwise it is simply parsing, just a lot of it.
|
||||
void from_json(const json& j, DeviceList& k) {
|
||||
json jTemp;
|
||||
j.at("DeviceList").get_to(jTemp);
|
||||
jTemp.at("Id").get_to(k.Id);
|
||||
|
||||
if (jTemp["Devices"].size() > 0) {
|
||||
for (auto& el : jTemp["Devices"].items()) {
|
||||
Device tempD;
|
||||
//std::cout << el.value() << std::endl;
|
||||
auto test = el.value().contains("DeviceMessageTimingGap");
|
||||
if (el.value().contains("DeviceName")) tempD.DeviceName = el.value()["DeviceName"];
|
||||
|
||||
if (el.value().contains("DeviceIndex")) tempD.DeviceIndex = el.value()["DeviceIndex"];
|
||||
|
||||
if (el.value().contains("DeviceMessageTimingGap")) tempD.DeviceMessageTimingGap = el.value()["DeviceMessageTimingGap"];
|
||||
|
||||
if (el.value().contains("DeviceDisplayName")) tempD.DeviceName = el.value()["DeviceDisplayName"];
|
||||
|
||||
if (el.value().contains("DeviceMessages")) {
|
||||
json jTemp2;
|
||||
jTemp2 = el.value()["DeviceMessages"];
|
||||
|
||||
for (auto& el2 : jTemp2.items()) {
|
||||
DeviceCmd tempCmd;
|
||||
tempCmd.CmdType = el2.key();
|
||||
|
||||
if (!el2.key().compare("StopDeviceCmd")) {
|
||||
// Do something, not sure what yet
|
||||
continue;
|
||||
}
|
||||
|
||||
for (auto& el3 : el2.value().items()) {
|
||||
DeviceCmdAttr tempAttr;
|
||||
//std::cout << el3.value() << std::endl;
|
||||
|
||||
if (el3.value().contains("FeatureDescriptor")) tempAttr.FeatureDescriptor = el3.value()["FeatureDescriptor"];
|
||||
|
||||
if (el3.value().contains("StepCount")) tempAttr.StepCount = el3.value()["StepCount"];
|
||||
|
||||
if (el3.value().contains("ActuatorType")) tempAttr.ActuatorType = el3.value()["ActuatorType"];
|
||||
|
||||
if (el3.value().contains("SensorType")) tempAttr.SensorType = el3.value()["SensorType"];
|
||||
|
||||
if (el3.value().contains("SensorRange")) {
|
||||
//std::cout << el3.value()["SensorRange"] << std::endl;
|
||||
for (auto& el4 : el3.value()["SensorRange"].items()) {
|
||||
tempAttr.SensorRange.push_back(el4.value()[0]);
|
||||
tempAttr.SensorRange.push_back(el4.value()[1]);
|
||||
}
|
||||
//tempCmd.SensorRange.push_back(el2.value()["SensorRange"]);
|
||||
}
|
||||
|
||||
//if (el2.value().contains("Endpoints")) tempCmd.Endpoints = el2.value()["Endpoints"];
|
||||
//std::cout << el2.key() << std::endl;
|
||||
//std::cout << el2.value() << std::endl;
|
||||
tempCmd.DeviceCmdAttributes.push_back(tempAttr);
|
||||
}
|
||||
|
||||
tempD.DeviceMessages.push_back(tempCmd);
|
||||
}
|
||||
}
|
||||
k.Devices.push_back(tempD);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void from_json(const json& j, DeviceAdded& k) {
|
||||
json jTemp;
|
||||
j.at("DeviceAdded").get_to(jTemp);
|
||||
jTemp.at("Id").get_to(k.Id);
|
||||
|
||||
Device tempD;
|
||||
|
||||
if (jTemp.contains("DeviceName")) k.device.DeviceName = jTemp["DeviceName"];
|
||||
|
||||
if (jTemp.contains("DeviceIndex")) k.device.DeviceIndex = jTemp["DeviceIndex"];
|
||||
|
||||
if (jTemp.contains("DeviceMessageTimingGap")) k.device.DeviceMessageTimingGap = jTemp["DeviceMessageTimingGap"];
|
||||
|
||||
if (jTemp.contains("DeviceDisplayName")) k.device.DeviceName = jTemp["DeviceDisplayName"];
|
||||
|
||||
if (jTemp.contains("DeviceMessages")) {
|
||||
json jTemp2;
|
||||
jTemp2 = jTemp["DeviceMessages"];
|
||||
|
||||
for (auto& el2 : jTemp2.items()) {
|
||||
DeviceCmd tempCmd;
|
||||
tempCmd.CmdType = el2.key();
|
||||
|
||||
if (!el2.key().compare("StopDeviceCmd")) {
|
||||
// Do something, not sure what yet
|
||||
continue;
|
||||
}
|
||||
|
||||
for (auto& el3 : el2.value().items()) {
|
||||
DeviceCmdAttr tempAttr;
|
||||
//std::cout << el3.value() << std::endl;
|
||||
|
||||
if (el3.value().contains("FeatureDescriptor")) tempAttr.FeatureDescriptor = el3.value()["FeatureDescriptor"];
|
||||
|
||||
if (el3.value().contains("StepCount")) tempAttr.StepCount = el3.value()["StepCount"];
|
||||
|
||||
if (el3.value().contains("ActuatorType")) tempAttr.ActuatorType = el3.value()["ActuatorType"];
|
||||
|
||||
if (el3.value().contains("SensorType")) tempAttr.SensorType = el3.value()["SensorType"];
|
||||
|
||||
if (el3.value().contains("SensorRange")) {
|
||||
//std::cout << el3.value()["SensorRange"] << std::endl;
|
||||
for (auto& el4 : el3.value()["SensorRange"].items()) {
|
||||
tempAttr.SensorRange.push_back(el4.value()[0]);
|
||||
tempAttr.SensorRange.push_back(el4.value()[1]);
|
||||
}
|
||||
}
|
||||
|
||||
//if (el2.value().contains("Endpoints")) tempCmd.Endpoints = el2.value()["Endpoints"];
|
||||
//std::cout << el2.key() << std::endl;
|
||||
//std::cout << el2.value() << std::endl;
|
||||
tempCmd.DeviceCmdAttributes.push_back(tempAttr);
|
||||
}
|
||||
|
||||
k.device.DeviceMessages.push_back(tempCmd);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void from_json(const json& j, SensorReading& k) {
|
||||
json jTemp;
|
||||
j.at("SensorReading").get_to(jTemp);
|
||||
jTemp.at("Id").get_to(k.Id);
|
||||
jTemp.at("DeviceIndex").get_to(k.DeviceIndex);
|
||||
jTemp.at("SensorIndex").get_to(k.SensorIndex);
|
||||
jTemp.at("SensorType").get_to(k.SensorType);
|
||||
for (auto& el : jTemp["Data"].items())
|
||||
k.Data.push_back(el.value());
|
||||
}
|
||||
}
|
Loading…
Add table
Add a link
Reference in a new issue