Files
OpenRGB/Controllers/SinowealthController/SinowealthController.cpp
2022-02-01 18:10:24 +00:00

215 lines
7.1 KiB
C++

/*-----------------------------------------*\
| SinowealthController.cpp |
| |
| Definitions and types for Sinowealth |
| mice, including Glorious |
| |
| Niels Westphal (crashniels) 20/5/2020 |
\*-----------------------------------------*/
#include "SinowealthController.h"
#include <cstring>
#include <LogManager.h>
SinowealthController::SinowealthController(hid_device* dev_data_handle, hid_device* dev_cmd_handle, char *_path)
{
dev_data = dev_data_handle;
dev_cmd = dev_cmd_handle;
led_count = 1;
current_mode = GLORIOUS_MODE_STATIC;
current_speed = GLORIOUS_SPEED_NORMAL;
current_direction = GLORIOUS_DIRECTION_UP;
location = _path;
}
SinowealthController::~SinowealthController()
{
hid_close(dev_data);
hid_close(dev_cmd);
}
std::string SinowealthController::GetLocation()
{
return("HID: " + location);
}
unsigned int SinowealthController::GetLEDCount()
{
return(led_count);
}
std::string SinowealthController::GetSerialString()
{
wchar_t serial_string[128];
int ret = hid_get_serial_number_string(dev_data, serial_string, 128);
if(ret != 0)
{
return("");
}
std::wstring return_wstring = serial_string;
std::string return_string(return_wstring.begin(), return_wstring.end());
return(return_string);
}
std::string SinowealthController::GetFirmwareVersion()
{
unsigned char usb_buf[SINOWEALTH_COMMAND_REPORT_SIZE + 1]; // Additional byte for null-terminator
memset(usb_buf, 0x00, sizeof(usb_buf));
usb_buf[0] = 5;
usb_buf[1] = 1;
int ret = hid_send_feature_report(dev_cmd, usb_buf, SINOWEALTH_COMMAND_REPORT_SIZE);
if(ret < 0) return("");
usb_buf[1] = 0;
ret = hid_get_feature_report(dev_cmd, usb_buf, SINOWEALTH_COMMAND_REPORT_SIZE);
if(ret < 0) return("");
return std::string(reinterpret_cast<char*>(usb_buf) + 2); // Skip report and command byte
}
void SinowealthController::SetLEDColor
(
RGBColor* color_buf
)
{
if (GetProfile() < SINOWEALTH_CONFIG_SIZE_MIN) return;
unsigned char usb_buf[SINOWEALTH_CONFIG_REPORT_SIZE];
memcpy(usb_buf, device_configuration, SINOWEALTH_CONFIG_SIZE); // Yes, we only copy 167 bytes back, for now - if anything weird starts happening use SINOWEALTH_CONFIG_REPORT_SIZE
usb_buf[0x03] = 0x7B; //write to device
usb_buf[0x06] = 0x00;
usb_buf[0x35] = GLORIOUS_MODE_STATIC;
usb_buf[0x38] = 0x40; //max brightness
usb_buf[0x39] = RGBGetRValue(color_buf[0]);
usb_buf[0x3A] = RGBGetBValue(color_buf[0]);
usb_buf[0x3B] = RGBGetGValue(color_buf[0]);
hid_send_feature_report(dev_data, usb_buf, SINOWEALTH_CONFIG_REPORT_SIZE);
}
void SinowealthController::SetMode
(
unsigned char mode,
unsigned char speed,
unsigned char direction,
RGBColor* color_buf
)
{
if (GetProfile() < SINOWEALTH_CONFIG_SIZE_MIN) return;
unsigned char usb_buf[SINOWEALTH_CONFIG_REPORT_SIZE];
memcpy(usb_buf, device_configuration, SINOWEALTH_CONFIG_SIZE); // Yes, we only copy 167 bytes back, for now - if anything weird starts happening use SINOWEALTH_CONFIG_REPORT_SIZE
usb_buf[0x03] = 0x7B; //write to device
usb_buf[0x06] = 0x00;
usb_buf[0x35] = mode;
switch (mode)
{
case GLORIOUS_MODE_OFF:
usb_buf[0x81] = 0x00; //mode 0 either 0x00 or 0x03
break;
case GLORIOUS_MODE_RAINBOW:
usb_buf[0x36] = speed;
usb_buf[0x37] = direction;
break;
case GLORIOUS_MODE_SPECTRUM_BREATING:
//colours not yet researched
usb_buf[0x3C] = speed; //speed for mode 3
usb_buf[0x3D] = 0x07; //maybe some kind of bank change?+
//usb_buf[0x3D] = 0x06;
usb_buf[0x3E] = RGBGetRValue(color_buf[0]); //mode 3 red 1
usb_buf[0x3F] = RGBGetBValue(color_buf[0]); //mode 3 blue 1
usb_buf[0x40] = RGBGetGValue(color_buf[0]); //mode 3 green 1
usb_buf[0x41] = RGBGetRValue(color_buf[1]); //mode 3 red 2
usb_buf[0x42] = RGBGetBValue(color_buf[1]); //mode 3 blue 2
usb_buf[0x43] = RGBGetGValue(color_buf[1]); //mode 3 green 2
usb_buf[0x44] = RGBGetRValue(color_buf[2]); //mode 3 red 3
usb_buf[0x45] = RGBGetBValue(color_buf[2]); //mode 3 blue 3
usb_buf[0x46] = RGBGetGValue(color_buf[2]); //mode 3 green 3
usb_buf[0x47] = RGBGetRValue(color_buf[3]); //mode 3 red 4
usb_buf[0x48] = RGBGetBValue(color_buf[3]); //mode 3 blue 4
usb_buf[0x49] = RGBGetGValue(color_buf[3]); //mode 3 green 4
usb_buf[0x4A] = RGBGetRValue(color_buf[4]); //mode 3 red 5
usb_buf[0x4B] = RGBGetBValue(color_buf[4]); //mode 3 blue 5
usb_buf[0x4C] = RGBGetGValue(color_buf[4]); //mode 3 green 5
usb_buf[0x4D] = RGBGetRValue(color_buf[5]); //mode 3 red 6
usb_buf[0x4E] = RGBGetBValue(color_buf[5]); //mode 3 blue 6
usb_buf[0x4F] = RGBGetGValue(color_buf[5]); //mode 3 green 6
usb_buf[0x50] = RGBGetRValue(color_buf[6]); //mode 3 red 7
usb_buf[0x51] = RGBGetBValue(color_buf[6]); //mode 3 blue 7
usb_buf[0x52] = RGBGetGValue(color_buf[6]); //mode 3 green 7
break;
case GLORIOUS_MODE_TAIL:
usb_buf[0x53] = speed; //Speed for mode 4
break;
case GLORIOUS_MODE_SPECTRUM_CYCLE:
usb_buf[0x54] = speed; //Speed for mode 1,2,5
break;
case GLORIOUS_MODE_RAVE:
usb_buf[0x74] = speed; //Speed for mode 7
usb_buf[0x75] = RGBGetRValue(color_buf[0]); //mode 7 red 1
usb_buf[0x76] = RGBGetBValue(color_buf[0]); //mode 7 blue 1
usb_buf[0x77] = RGBGetGValue(color_buf[0]); //mode 7 green 1
usb_buf[0x78] = RGBGetRValue(color_buf[1]); //mode 7 red 2
usb_buf[0x79] = RGBGetBValue(color_buf[1]); //mode 7 blue 2
usb_buf[0x7A] = RGBGetGValue(color_buf[1]); //mode 7 green 2
break;
case GLORIOUS_MODE_WAVE:
usb_buf[0x7C] = speed; //Speed for mode 9
break;
case GLORIOUS_MODE_BREATHING:
usb_buf[0x7D] = speed;
usb_buf[0x7E] = RGBGetRValue(color_buf[0]); //mode 0a red
usb_buf[0x7F] = RGBGetBValue(color_buf[0]); //mode 0a blue
usb_buf[0x80] = RGBGetGValue(color_buf[0]); //mode 0a green
default:
break;
}
hid_send_feature_report(dev_data, usb_buf, SINOWEALTH_CONFIG_REPORT_SIZE);
}
int SinowealthController::GetProfile()
{
int actual;
unsigned char usb_buf[SINOWEALTH_COMMAND_REPORT_SIZE];
memset(usb_buf, 0x00, sizeof(usb_buf));
usb_buf[0] = 0x05;
usb_buf[1] = 0x11;
actual = hid_send_feature_report(dev_cmd, usb_buf, sizeof(usb_buf));
if (actual != SINOWEALTH_COMMAND_REPORT_SIZE)
{
LOG_ERROR("[Sinowealth Mouse] Error sending read request!");
return -1;
}
else
{
memset(device_configuration, 0x00, SINOWEALTH_CONFIG_REPORT_SIZE);
device_configuration[0] = 0x04;
actual = hid_get_feature_report(dev_data, device_configuration, SINOWEALTH_CONFIG_REPORT_SIZE);
if (actual < 0)
{
LOG_ERROR("[Sinowealth Mouse] Error reading device configuration!");
}
}
return actual;
}