Publish LumaOps source
This commit is contained in:
@@ -0,0 +1,61 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| A4TechDetector.cpp |
|
||||
| |
|
||||
| Detector for A4Tech Devices |
|
||||
| |
|
||||
| Chris M (Dr_No) 30 Jun 2022 |
|
||||
| Mohammed Julfikar Ali Mahbub (o-julfikar) 01 Apr 2024 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| OpenRGB includes |
|
||||
\*-----------------------------------------------------*/
|
||||
#include <hidapi.h>
|
||||
#include "Detector.h"
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| A4 Tech specific includes |
|
||||
\*-----------------------------------------------------*/
|
||||
#include "RGBController_BloodyMouse.h"
|
||||
#include "RGBController_BloodyB820R.h"
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| A4 Tech USB vendor ID |
|
||||
\*-----------------------------------------------------*/
|
||||
#define A4_TECH_VID 0x09DA
|
||||
|
||||
void DetectA4TechMouseControllers(hid_device_info* info, const std::string& name)
|
||||
{
|
||||
hid_device* dev = hid_open_path(info->path);
|
||||
|
||||
if(dev)
|
||||
{
|
||||
BloodyMouseController* controller = new BloodyMouseController(dev, info->path, info->product_id, name);
|
||||
RGBController_BloodyMouse* rgb_controller = new RGBController_BloodyMouse(controller);
|
||||
|
||||
ResourceManager::get()->RegisterRGBController(rgb_controller);
|
||||
}
|
||||
}
|
||||
|
||||
void DetectBloodyB820R(hid_device_info* info, const std::string& name)
|
||||
{
|
||||
hid_device* dev = hid_open_path(info->path);
|
||||
|
||||
if(dev)
|
||||
{
|
||||
BloodyB820RController* controller = new BloodyB820RController(dev, info->path, name);
|
||||
RGBController_BloodyB820R* rgb_controller = new RGBController_BloodyB820R(controller);
|
||||
|
||||
ResourceManager::get()->RegisterRGBController(rgb_controller);
|
||||
}
|
||||
}
|
||||
|
||||
REGISTER_HID_DETECTOR_IPU("Bloody W60 Pro", DetectA4TechMouseControllers, A4_TECH_VID, BLOODY_W60_PRO_PID, 2, 0xFF33, 0x0529);
|
||||
REGISTER_HID_DETECTOR_IPU("Bloody W70 Max", DetectA4TechMouseControllers, A4_TECH_VID, BLOODY_W70_MAX_PID, 2, 0xFF33, 0x0518);
|
||||
REGISTER_HID_DETECTOR_IPU("Bloody W90 Max", DetectA4TechMouseControllers, A4_TECH_VID, BLOODY_W90_MAX_PID, 2, 0xFF33, 0x053D);
|
||||
REGISTER_HID_DETECTOR_IPU("Bloody W90 Pro", DetectA4TechMouseControllers, A4_TECH_VID, BLOODY_W90_PRO_PID, 2, 0xFF33, 0x054D);
|
||||
REGISTER_HID_DETECTOR_IPU("Bloody MP 50RS", DetectA4TechMouseControllers, A4_TECH_VID, BLOODY_MP_50RS_PID, 2, 0xFFF2, 0x6009);
|
||||
REGISTER_HID_DETECTOR_IPU("Bloody B820R", DetectBloodyB820R, A4_TECH_VID, BLOODY_B820R_PID, 2, 0xFF52, 0x0210);
|
||||
@@ -0,0 +1,110 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| BloodyB820RController.cpp |
|
||||
| |
|
||||
| Driver for A4Tech Bloody B820R Keyboard |
|
||||
| |
|
||||
| Mohammed Julfikar Ali Mahbub (o-julfikar) 01 Apr 2024 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "BloodyB820RController.h"
|
||||
#include "StringUtils.h"
|
||||
|
||||
/*-------------------------------------------------------------------------------------*\
|
||||
| The controller for this device should pass a packet of 64 bytes where the subsequent |
|
||||
| two packets are for RED, GREEN, and BLUE respectively. The first 6 bytes are control |
|
||||
| or information bytes and colors bytes starts from index 6. Moreover, the first pack- |
|
||||
| et of each RGB contains color for 58 keys and the rest (104 - 58 == 46) are send on |
|
||||
| the second packet. |
|
||||
\*-------------------------------------------------------------------------------------*/
|
||||
|
||||
BloodyB820RController::BloodyB820RController(hid_device* dev_handle, const char* path, std::string dev_name)
|
||||
{
|
||||
dev = dev_handle;
|
||||
location = path;
|
||||
name = dev_name;
|
||||
|
||||
SendControlPacket(BLOODY_B820R_GAIN_CONTROL);
|
||||
}
|
||||
|
||||
BloodyB820RController::~BloodyB820RController()
|
||||
{
|
||||
SendControlPacket(BLOODY_B820R_RELEASE_CONTROL);
|
||||
hid_close(dev);
|
||||
}
|
||||
|
||||
std::string BloodyB820RController::GetSerial()
|
||||
{
|
||||
wchar_t serial_string[HID_MAX_STR];
|
||||
int ret = hid_get_serial_number_string(dev, serial_string, HID_MAX_STR);
|
||||
|
||||
if(ret != 0)
|
||||
{
|
||||
return("");
|
||||
}
|
||||
|
||||
return(StringUtils::wstring_to_string(serial_string));
|
||||
}
|
||||
|
||||
std::string BloodyB820RController::GetLocation()
|
||||
{
|
||||
return("HID: " + location);
|
||||
}
|
||||
|
||||
std::string BloodyB820RController::GetName()
|
||||
{
|
||||
return(name);
|
||||
}
|
||||
|
||||
void BloodyB820RController::SendControlPacket(uint8_t data)
|
||||
{
|
||||
uint8_t buffer[BLOODY_B820R_PACKET_SIZE] = { 0x07, 0x03, 0x06, 0x01, 0x00, 0x00, 0x00, 0x00 };
|
||||
|
||||
hid_send_feature_report(dev, buffer, BLOODY_B820R_PACKET_SIZE);
|
||||
|
||||
buffer[BLOODY_B820R_MODE_BYTE] = 0;
|
||||
buffer[BLOODY_B820R_DATA_BYTE] = data;
|
||||
|
||||
hid_send_feature_report(dev, buffer, BLOODY_B820R_PACKET_SIZE);
|
||||
}
|
||||
|
||||
void BloodyB820RController::SetLEDDirect(std::vector<RGBColor> colors)
|
||||
{
|
||||
|
||||
uint8_t r1_buffer[BLOODY_B820R_PACKET_SIZE] = { 0x07, 0x03, 0x06, 0x07, 0x00, 0x00 };
|
||||
uint8_t r2_buffer[BLOODY_B820R_PACKET_SIZE] = { 0x07, 0x03, 0x06, 0x08, 0x00, 0x00 };
|
||||
uint8_t g1_buffer[BLOODY_B820R_PACKET_SIZE] = { 0x07, 0x03, 0x06, 0x09, 0x00, 0x00 };
|
||||
uint8_t g2_buffer[BLOODY_B820R_PACKET_SIZE] = { 0x07, 0x03, 0x06, 0x0A, 0x00, 0x00 };
|
||||
uint8_t b1_buffer[BLOODY_B820R_PACKET_SIZE] = { 0x07, 0x03, 0x06, 0x0B, 0x00, 0x00 };
|
||||
uint8_t b2_buffer[BLOODY_B820R_PACKET_SIZE] = { 0x07, 0x03, 0x06, 0x0C, 0x00, 0x00 };
|
||||
|
||||
/*-----------------------------------------------------------------*\
|
||||
| Set up Direct packet |
|
||||
| packet_map is the index of the Key from full_matrix_map and |
|
||||
| the value is the position in the direct packet buffer |
|
||||
\*-----------------------------------------------------------------*/
|
||||
for(size_t i = 0; i < colors.size(); i++)
|
||||
{
|
||||
RGBColor color = colors[i];
|
||||
uint8_t offset = BLOODY_B820R_RGB_OFFSET;
|
||||
uint8_t buffer_idx = offset + i % BLOODY_B820R_RGB_BUFFER_SIZE;
|
||||
uint8_t* buffers[2][3] =
|
||||
{
|
||||
{r1_buffer, g1_buffer, b1_buffer},
|
||||
{r2_buffer, g2_buffer, b2_buffer}
|
||||
};
|
||||
|
||||
buffers[i >= BLOODY_B820R_RGB_BUFFER_SIZE][0][buffer_idx] = RGBGetRValue(color);
|
||||
buffers[i >= BLOODY_B820R_RGB_BUFFER_SIZE][1][buffer_idx] = RGBGetGValue(color);
|
||||
buffers[i >= BLOODY_B820R_RGB_BUFFER_SIZE][2][buffer_idx] = RGBGetBValue(color);
|
||||
}
|
||||
|
||||
hid_send_feature_report(dev, r1_buffer, BLOODY_B820R_PACKET_SIZE);
|
||||
hid_send_feature_report(dev, r2_buffer, BLOODY_B820R_PACKET_SIZE);
|
||||
hid_send_feature_report(dev, g1_buffer, BLOODY_B820R_PACKET_SIZE);
|
||||
hid_send_feature_report(dev, g2_buffer, BLOODY_B820R_PACKET_SIZE);
|
||||
hid_send_feature_report(dev, b1_buffer, BLOODY_B820R_PACKET_SIZE);
|
||||
hid_send_feature_report(dev, b2_buffer, BLOODY_B820R_PACKET_SIZE);
|
||||
}
|
||||
@@ -0,0 +1,55 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| BloodyB820RController.h |
|
||||
| |
|
||||
| Driver for A4Tech Bloody B820R Keyboard |
|
||||
| |
|
||||
| Mohammed Julfikar Ali Mahbub (o-julfikar) 01 Apr 2024 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <string>
|
||||
#include <hidapi.h>
|
||||
#include "RGBController.h"
|
||||
|
||||
#define HID_MAX_STR 255
|
||||
|
||||
#define BLOODY_B820R_RGB_BUFFER_SIZE 58
|
||||
#define BLOODY_B820R_RGB_OFFSET 6
|
||||
#define BLOODY_B820R_PACKET_SIZE 64
|
||||
#define BLOODY_B820R_KEYCOUNT 104
|
||||
#define BLOODY_B820R_MODE_BYTE 3
|
||||
#define BLOODY_B820R_DATA_BYTE 8
|
||||
#define BLOODY_B820R_GAIN_CONTROL 0x01
|
||||
#define BLOODY_B820R_RELEASE_CONTROL 0x00
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Bloody B820R product ID |
|
||||
\*---------------------------------------------------------*/
|
||||
#define BLOODY_B820R_PID 0xFA10
|
||||
|
||||
enum
|
||||
{
|
||||
BLOODY_B820R_MODE_DIRECT = 0x01, // Direct LED control - Independently set LEDs in zone
|
||||
};
|
||||
|
||||
class BloodyB820RController
|
||||
{
|
||||
public:
|
||||
BloodyB820RController(hid_device* dev_handle, const char* path, std::string dev_name);
|
||||
~BloodyB820RController();
|
||||
|
||||
std::string GetSerial();
|
||||
std::string GetLocation();
|
||||
std::string GetName();
|
||||
|
||||
void SetLEDDirect(std::vector<RGBColor> colors);
|
||||
void SendControlPacket(uint8_t data);
|
||||
private:
|
||||
std::string location;
|
||||
std::string name;
|
||||
hid_device* dev;
|
||||
};
|
||||
@@ -0,0 +1,253 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_BloodyB820R.cpp |
|
||||
| |
|
||||
| RGBController for A4Tech Bloody B820R Keyboard |
|
||||
| |
|
||||
| Mohammed Julfikar Ali Mahbub (o-julfikar) 01 Apr 2024 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "RGBControllerKeyNames.h"
|
||||
#include "RGBController_BloodyB820R.h"
|
||||
|
||||
//0xFFFFFFFF indicates an unused entry in matrix
|
||||
#define NA 0xFFFFFFFF
|
||||
|
||||
static unsigned int matrix_map[6][21] =
|
||||
{
|
||||
{0, NA, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, NA, NA, NA, NA, 13, 14, 15},
|
||||
{16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36},
|
||||
{37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57},
|
||||
{58, 59, 60, 61, 62, 63, 64, 65, 66, 67, 68, 69, 70, NA, NA, NA, NA, 71, 72, 73, NA},
|
||||
{74, NA, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, NA, NA, 86, NA, 87, 88, 89, 90},
|
||||
{91, 92, 93, 94, NA, NA, NA, NA, NA, NA, 95, 96, 97, 98, 99, 100, 101, 102, NA, 103, NA},
|
||||
};
|
||||
|
||||
static const char *led_names[] =
|
||||
{
|
||||
KEY_EN_ESCAPE, //00
|
||||
KEY_EN_F1,
|
||||
KEY_EN_F2,
|
||||
KEY_EN_F3,
|
||||
KEY_EN_F4,
|
||||
KEY_EN_F5,
|
||||
KEY_EN_F6,
|
||||
KEY_EN_F7,
|
||||
KEY_EN_F8,
|
||||
KEY_EN_F9,
|
||||
KEY_EN_F10,
|
||||
KEY_EN_F11,
|
||||
KEY_EN_F12,
|
||||
KEY_EN_PRINT_SCREEN,
|
||||
KEY_EN_SCROLL_LOCK,
|
||||
KEY_EN_PAUSE_BREAK,
|
||||
|
||||
KEY_EN_BACK_TICK, //10
|
||||
KEY_EN_1,
|
||||
KEY_EN_2,
|
||||
KEY_EN_3,
|
||||
KEY_EN_4,
|
||||
KEY_EN_5,
|
||||
KEY_EN_6,
|
||||
KEY_EN_7,
|
||||
KEY_EN_8,
|
||||
KEY_EN_9,
|
||||
KEY_EN_0,
|
||||
KEY_EN_MINUS,
|
||||
KEY_EN_EQUALS,
|
||||
KEY_EN_BACKSPACE,
|
||||
KEY_EN_INSERT,
|
||||
KEY_EN_HOME,
|
||||
KEY_EN_PAGE_UP,
|
||||
KEY_EN_NUMPAD_LOCK,
|
||||
KEY_EN_NUMPAD_DIVIDE,
|
||||
KEY_EN_NUMPAD_TIMES,
|
||||
KEY_EN_NUMPAD_MINUS,
|
||||
|
||||
KEY_EN_TAB, //20
|
||||
KEY_EN_Q,
|
||||
KEY_EN_W,
|
||||
KEY_EN_E,
|
||||
KEY_EN_R,
|
||||
KEY_EN_T,
|
||||
KEY_EN_Y,
|
||||
KEY_EN_U,
|
||||
KEY_EN_I,
|
||||
KEY_EN_O,
|
||||
KEY_EN_P,
|
||||
KEY_EN_LEFT_BRACKET,
|
||||
KEY_EN_RIGHT_BRACKET,
|
||||
KEY_EN_ANSI_BACK_SLASH,
|
||||
KEY_EN_DELETE,
|
||||
KEY_EN_END,
|
||||
KEY_EN_PAGE_DOWN,
|
||||
KEY_EN_NUMPAD_7,
|
||||
KEY_EN_NUMPAD_8,
|
||||
KEY_EN_NUMPAD_9,
|
||||
KEY_EN_NUMPAD_PLUS,
|
||||
|
||||
KEY_EN_CAPS_LOCK, //30
|
||||
KEY_EN_A,
|
||||
KEY_EN_S,
|
||||
KEY_EN_D,
|
||||
KEY_EN_F,
|
||||
KEY_EN_G,
|
||||
KEY_EN_H,
|
||||
KEY_EN_J,
|
||||
KEY_EN_K,
|
||||
KEY_EN_L,
|
||||
KEY_EN_SEMICOLON,
|
||||
KEY_EN_QUOTE,
|
||||
KEY_EN_ANSI_ENTER,
|
||||
KEY_EN_NUMPAD_4,
|
||||
KEY_EN_NUMPAD_5,
|
||||
KEY_EN_NUMPAD_6,
|
||||
|
||||
KEY_EN_LEFT_SHIFT, //40
|
||||
KEY_EN_Z,
|
||||
KEY_EN_X,
|
||||
KEY_EN_C,
|
||||
KEY_EN_V,
|
||||
KEY_EN_B,
|
||||
KEY_EN_N,
|
||||
KEY_EN_M,
|
||||
KEY_EN_COMMA,
|
||||
KEY_EN_PERIOD,
|
||||
KEY_EN_FORWARD_SLASH,
|
||||
KEY_EN_RIGHT_SHIFT,
|
||||
KEY_EN_UP_ARROW,
|
||||
KEY_EN_NUMPAD_1,
|
||||
KEY_EN_NUMPAD_2,
|
||||
KEY_EN_NUMPAD_3,
|
||||
KEY_EN_NUMPAD_ENTER,
|
||||
|
||||
KEY_EN_LEFT_CONTROL, //50
|
||||
KEY_EN_LEFT_WINDOWS,
|
||||
KEY_EN_LEFT_ALT,
|
||||
KEY_EN_SPACE,
|
||||
KEY_EN_RIGHT_ALT,
|
||||
KEY_EN_RIGHT_FUNCTION,
|
||||
KEY_EN_MENU,
|
||||
KEY_EN_RIGHT_CONTROL,
|
||||
KEY_EN_LEFT_ARROW,
|
||||
KEY_EN_DOWN_ARROW,
|
||||
KEY_EN_RIGHT_ARROW,
|
||||
KEY_EN_NUMPAD_0,
|
||||
KEY_EN_NUMPAD_PERIOD
|
||||
};
|
||||
|
||||
/**------------------------------------------------------------------*\
|
||||
@name A4Tech Bloody B820R
|
||||
@category Keyboard
|
||||
@type USB
|
||||
@save :x:
|
||||
@direct :white_check_mark:
|
||||
@effects :x:
|
||||
@detectors DetectBloodyB820R
|
||||
@comment The A4Tech Bloody B820R keyboard controller currently
|
||||
supports the full size (ANSI layout).
|
||||
\*-------------------------------------------------------------------*/
|
||||
|
||||
RGBController_BloodyB820R::RGBController_BloodyB820R(BloodyB820RController *controller_ptr)
|
||||
{
|
||||
controller = controller_ptr;
|
||||
|
||||
name = controller->GetName();
|
||||
vendor = "A4Tech";
|
||||
type = DEVICE_TYPE_KEYBOARD;
|
||||
description = "A4Tech Bloody Keyboard";
|
||||
serial = controller->GetSerial();
|
||||
location = controller->GetLocation();
|
||||
|
||||
mode Direct;
|
||||
Direct.name = "Direct";
|
||||
Direct.value = BLOODY_B820R_MODE_DIRECT;
|
||||
Direct.flags = MODE_FLAG_HAS_PER_LED_COLOR;
|
||||
Direct.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Direct);
|
||||
|
||||
SetupZones();
|
||||
}
|
||||
|
||||
RGBController_BloodyB820R::~RGBController_BloodyB820R()
|
||||
{
|
||||
delete controller;
|
||||
}
|
||||
|
||||
void RGBController_BloodyB820R::SetupZones()
|
||||
{
|
||||
/*-------------------------------------------------*\
|
||||
| Create the Keyboard zone and add the matrix map |
|
||||
\*-------------------------------------------------*/
|
||||
zone KB_zone;
|
||||
KB_zone.name = ZONE_EN_KEYBOARD;
|
||||
KB_zone.type = ZONE_TYPE_MATRIX;
|
||||
KB_zone.leds_min = BLOODY_B820R_KEYCOUNT;
|
||||
KB_zone.leds_max = BLOODY_B820R_KEYCOUNT;
|
||||
KB_zone.leds_count = BLOODY_B820R_KEYCOUNT;
|
||||
|
||||
KB_zone.matrix_map = new matrix_map_type;
|
||||
KB_zone.matrix_map->height = 6;
|
||||
KB_zone.matrix_map->width = 21;
|
||||
KB_zone.matrix_map->map = (unsigned int *)&matrix_map;
|
||||
zones.push_back(KB_zone);
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| Clear any existing color/LED configuration |
|
||||
\*-------------------------------------------------*/
|
||||
leds.clear();
|
||||
colors.clear();
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Set up zones |
|
||||
\*---------------------------------------------------------*/
|
||||
for(unsigned int led_index = 0; led_index < BLOODY_B820R_KEYCOUNT; led_index++)
|
||||
{
|
||||
led new_led;
|
||||
new_led.name = led_names[led_index];
|
||||
new_led.value = led_index;
|
||||
leds.push_back(new_led);
|
||||
}
|
||||
|
||||
SetupColors();
|
||||
}
|
||||
|
||||
void RGBController_BloodyB820R::ResizeZone(int /*zone*/, int /*new_size*/)
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| This device does not support resizing zones |
|
||||
\*---------------------------------------------------------*/
|
||||
}
|
||||
|
||||
|
||||
void RGBController_BloodyB820R::DeviceUpdateLEDs()
|
||||
{
|
||||
controller->SetLEDDirect(colors);
|
||||
}
|
||||
|
||||
void RGBController_BloodyB820R::UpdateZoneLEDs(int zone)
|
||||
{
|
||||
std::vector<RGBColor> colour;
|
||||
|
||||
for(size_t i = 0; i < zones[zone].leds_count; i++)
|
||||
{
|
||||
colour.push_back(zones[zone].colors[i]);
|
||||
}
|
||||
|
||||
controller->SetLEDDirect(colour);
|
||||
}
|
||||
|
||||
void RGBController_BloodyB820R::UpdateSingleLED(int led)
|
||||
{
|
||||
std::vector<RGBColor> colour;
|
||||
colour.push_back(colors[led]);
|
||||
|
||||
controller->SetLEDDirect(colour);
|
||||
}
|
||||
|
||||
void RGBController_BloodyB820R::DeviceUpdateMode()
|
||||
{
|
||||
/* This device does not support modes yet */
|
||||
}
|
||||
@@ -0,0 +1,35 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_BloodyB820R.h |
|
||||
| |
|
||||
| RGBController for A4Tech Bloody B820R Keyboard |
|
||||
| |
|
||||
| Mohammed Julfikar Ali Mahbub (o-julfikar) 01 Apr 2024 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <vector>
|
||||
#include "RGBController.h"
|
||||
#include "BloodyB820RController.h"
|
||||
|
||||
class RGBController_BloodyB820R : public RGBController
|
||||
{
|
||||
public:
|
||||
RGBController_BloodyB820R(BloodyB820RController* controller_ptr);
|
||||
~RGBController_BloodyB820R();
|
||||
|
||||
void SetupZones();
|
||||
void ResizeZone(int zone, int new_size);
|
||||
|
||||
void DeviceUpdateLEDs();
|
||||
void UpdateZoneLEDs(int zone);
|
||||
void UpdateSingleLED(int led);
|
||||
|
||||
void DeviceUpdateMode();
|
||||
|
||||
private:
|
||||
BloodyB820RController* controller;
|
||||
};
|
||||
@@ -0,0 +1,84 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| BloodyMouseController.cpp |
|
||||
| |
|
||||
| Driver for A4Tech Bloody Mouse |
|
||||
| |
|
||||
| Chris M (Dr_No) 30 Jun 2022 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "BloodyMouseController.h"
|
||||
#include "StringUtils.h"
|
||||
|
||||
BloodyMouseController::BloodyMouseController(hid_device* dev_handle, const char* path, uint16_t product_id, std::string dev_name)
|
||||
{
|
||||
dev = dev_handle;
|
||||
location = path;
|
||||
pid = product_id;
|
||||
name = dev_name;
|
||||
|
||||
InitDevice();
|
||||
}
|
||||
|
||||
BloodyMouseController::~BloodyMouseController()
|
||||
{
|
||||
hid_close(dev);
|
||||
}
|
||||
|
||||
uint16_t BloodyMouseController::GetPid()
|
||||
{
|
||||
return(pid);
|
||||
}
|
||||
|
||||
std::string BloodyMouseController::GetSerial()
|
||||
{
|
||||
wchar_t serial_string[HID_MAX_STR];
|
||||
int ret = hid_get_serial_number_string(dev, serial_string, HID_MAX_STR);
|
||||
|
||||
if(ret != 0)
|
||||
{
|
||||
return("");
|
||||
}
|
||||
|
||||
return(StringUtils::wstring_to_string(serial_string));
|
||||
}
|
||||
|
||||
std::string BloodyMouseController::GetLocation()
|
||||
{
|
||||
return("HID: " + location);
|
||||
}
|
||||
|
||||
std::string BloodyMouseController::GetName()
|
||||
{
|
||||
return(name);
|
||||
}
|
||||
|
||||
void BloodyMouseController::InitDevice()
|
||||
{
|
||||
uint8_t buffer[BLOODYMOUSE_WRITE_PACKET_SIZE] = { 0x07, 0x03, 0x06, 0x01, 0x00, 0x00, 0x00, 0x00 };
|
||||
|
||||
hid_send_feature_report(dev, buffer, BLOODYMOUSE_WRITE_PACKET_SIZE);
|
||||
|
||||
buffer[BLOODYMOUSE_MODE_BYTE] = 0;
|
||||
buffer[BLOODYMOUSE_DATA_BYTE] = 1;
|
||||
|
||||
hid_send_feature_report(dev, buffer, BLOODYMOUSE_WRITE_PACKET_SIZE);
|
||||
}
|
||||
|
||||
void BloodyMouseController::SetLedsDirect(std::vector<RGBColor> colors)
|
||||
{
|
||||
uint8_t buffer[BLOODYMOUSE_WRITE_PACKET_SIZE] = { 0x07, 0x03, 0x06, 0x02, 0x00, 0x00, 0x00, 0x00 };
|
||||
|
||||
for(uint8_t i = 0; i < colors.size(); i++)
|
||||
{
|
||||
uint8_t offset = 3 * (colors[i] >> 24) + BLOODYMOUSE_DATA_BYTE;
|
||||
|
||||
buffer[offset] = RGBGetRValue(colors[i]);
|
||||
buffer[offset + 1] = RGBGetGValue(colors[i]);
|
||||
buffer[offset + 2] = RGBGetBValue(colors[i]);
|
||||
}
|
||||
|
||||
hid_send_feature_report(dev, buffer, BLOODYMOUSE_WRITE_PACKET_SIZE);
|
||||
}
|
||||
@@ -0,0 +1,70 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| BloodyMouseController.h |
|
||||
| |
|
||||
| Driver for A4Tech Bloody Mouse |
|
||||
| |
|
||||
| Chris M (Dr_No) 30 Jun 2022 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <string>
|
||||
#include <hidapi.h>
|
||||
#include "RGBController.h"
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Mouse product IDs |
|
||||
\*-----------------------------------------------------*/
|
||||
#define BLOODY_W60_PRO_PID 0x37EA
|
||||
#define BLOODY_W70_MAX_PID 0x79EF
|
||||
#define BLOODY_W90_MAX_PID 0x3666
|
||||
#define BLOODY_W90_PRO_PID 0x39B6
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Mousemat product IDs |
|
||||
\*-----------------------------------------------------*/
|
||||
#define BLOODY_MP_50RS_PID 0xFA60
|
||||
|
||||
#define HID_MAX_STR 255
|
||||
#define BLOODYMOUSE_WRITE_PACKET_SIZE 64
|
||||
|
||||
#define BLOODYMOUSE_BRIGHTNESS_MIN 0
|
||||
#define BLOODYMOUSE_BRIGHTNESS_MAX 255
|
||||
|
||||
enum
|
||||
{
|
||||
BLOODYMOUSE_MODE_DIRECT = 0x01, //Direct Led Control - Independently set LEDs in zone
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
BLOODYMOUSE_REPORT_BYTE = 1,
|
||||
BLOODYMOUSE_COMMAND_BYTE = 2,
|
||||
BLOODYMOUSE_MODE_BYTE = 3,
|
||||
BLOODYMOUSE_DATA_BYTE = 8,
|
||||
};
|
||||
|
||||
class BloodyMouseController
|
||||
{
|
||||
public:
|
||||
BloodyMouseController(hid_device* dev_handle, const char* path, uint16_t product_id, std::string dev_name);
|
||||
~BloodyMouseController();
|
||||
|
||||
uint16_t GetPid();
|
||||
std::string GetSerial();
|
||||
std::string GetLocation();
|
||||
std::string GetName();
|
||||
|
||||
void SetLedsDirect(std::vector<RGBColor> colors);
|
||||
|
||||
private:
|
||||
uint16_t pid;
|
||||
std::string location;
|
||||
std::string name;
|
||||
hid_device* dev;
|
||||
|
||||
void InitDevice();
|
||||
};
|
||||
@@ -0,0 +1,197 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_BloodyMouse.cpp |
|
||||
| |
|
||||
| RGBController for A4Tech Bloody Mouse |
|
||||
| |
|
||||
| Chris M (Dr_No) 30 Jun 2022 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "RGBController_BloodyMouse.h"
|
||||
|
||||
static const mouse_layout w60_pro
|
||||
{
|
||||
{
|
||||
"Scroll Wheel", { 14 }
|
||||
},
|
||||
{
|
||||
"Mid Line", { 0, 1, 2, 9, 3, 4, 5, 6 }
|
||||
},
|
||||
{
|
||||
"Logo", { 10 }
|
||||
},
|
||||
{
|
||||
"Rear", { 8, 7, 13, 12, 11 }
|
||||
}
|
||||
};
|
||||
|
||||
static const mouse_layout w90_max
|
||||
{
|
||||
{
|
||||
"Scroll Wheel", { 14 }
|
||||
},
|
||||
{
|
||||
"Logo", { 7 }
|
||||
},
|
||||
{
|
||||
"Rear", { 13, 12, 11, 10, 9, 8, 6, 5, 4, 3, 2, 1, 0 }
|
||||
}
|
||||
};
|
||||
|
||||
static const mouse_layout mp_50rs
|
||||
{
|
||||
{
|
||||
"Mouse Pad", { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 }
|
||||
}
|
||||
};
|
||||
|
||||
/**------------------------------------------------------------------*\
|
||||
@name BloodyMouse
|
||||
@category Mouse
|
||||
@type USB
|
||||
@save :x:
|
||||
@direct :white_check_mark:
|
||||
@effects :x:
|
||||
@detectors DetectA4TechMouseControllers
|
||||
@comment
|
||||
\*-------------------------------------------------------------------*/
|
||||
|
||||
RGBController_BloodyMouse::RGBController_BloodyMouse(BloodyMouseController *controller_ptr)
|
||||
{
|
||||
controller = controller_ptr;
|
||||
|
||||
switch(controller->GetPid())
|
||||
{
|
||||
case BLOODY_MP_50RS_PID:
|
||||
type = DEVICE_TYPE_MOUSEMAT;
|
||||
break;
|
||||
default:
|
||||
type = DEVICE_TYPE_MOUSE;
|
||||
}
|
||||
|
||||
name = controller->GetName();
|
||||
vendor = "Bloody";
|
||||
description = "Controller compatible with the Bloody W60 Pro and MP 50RS";
|
||||
serial = controller->GetSerial();
|
||||
location = controller->GetLocation();
|
||||
|
||||
mode Direct;
|
||||
Direct.name = "Direct";
|
||||
Direct.value = BLOODYMOUSE_MODE_DIRECT;
|
||||
Direct.flags = MODE_FLAG_HAS_PER_LED_COLOR;
|
||||
Direct.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Direct);
|
||||
|
||||
SetupZones();
|
||||
}
|
||||
|
||||
RGBController_BloodyMouse::~RGBController_BloodyMouse()
|
||||
{
|
||||
delete controller;
|
||||
}
|
||||
|
||||
void RGBController_BloodyMouse::SetupZones()
|
||||
{
|
||||
/*-------------------------------------------------*\
|
||||
| Clear any existing color/LED configuration |
|
||||
\*-------------------------------------------------*/
|
||||
leds.clear();
|
||||
colors.clear();
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| Select layout from PID |
|
||||
\*-------------------------------------------------*/
|
||||
mouse_layout layout;
|
||||
|
||||
switch(controller->GetPid())
|
||||
{
|
||||
case BLOODY_W60_PRO_PID:
|
||||
layout = w60_pro;
|
||||
break;
|
||||
case BLOODY_W70_MAX_PID:
|
||||
case BLOODY_W90_MAX_PID:
|
||||
case BLOODY_W90_PRO_PID:
|
||||
layout = w90_max;
|
||||
break;
|
||||
case BLOODY_MP_50RS_PID:
|
||||
layout = mp_50rs;
|
||||
break;
|
||||
}
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Set up zones |
|
||||
\*---------------------------------------------------------*/
|
||||
for(uint8_t zone_idx = 0; zone_idx < layout.size(); zone_idx++)
|
||||
{
|
||||
mouse_zone mz = layout[zone_idx];
|
||||
bool bool_single = mz.zone_leds.size() == 1;
|
||||
|
||||
zone new_zone;
|
||||
new_zone.name = mz.name;
|
||||
new_zone.leds_min = (unsigned int)mz.zone_leds.size();
|
||||
new_zone.leds_max = new_zone.leds_min;
|
||||
new_zone.leds_count = new_zone.leds_min;
|
||||
new_zone.type = bool_single ? ZONE_TYPE_SINGLE : ZONE_TYPE_LINEAR;
|
||||
new_zone.matrix_map = NULL;
|
||||
zones.push_back(new_zone);
|
||||
|
||||
for(unsigned int lp_idx = 0; lp_idx < zones[zone_idx].leds_count; lp_idx++)
|
||||
{
|
||||
led new_led;
|
||||
|
||||
new_led.value = mz.zone_leds[lp_idx];
|
||||
|
||||
if(bool_single)
|
||||
{
|
||||
new_led.name = mz.name + " LED";
|
||||
}
|
||||
else
|
||||
{
|
||||
new_led.name = mz.name;
|
||||
new_led.name.append(" LED " + std::to_string(lp_idx));
|
||||
}
|
||||
|
||||
leds.push_back(new_led);
|
||||
}
|
||||
}
|
||||
|
||||
SetupColors();
|
||||
}
|
||||
|
||||
void RGBController_BloodyMouse::ResizeZone(int /*zone*/, int /*new_size*/)
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| This device does not support resizing zones |
|
||||
\*---------------------------------------------------------*/
|
||||
}
|
||||
|
||||
void RGBController_BloodyMouse::DeviceUpdateLEDs()
|
||||
{
|
||||
std::vector<RGBColor> colour;
|
||||
for(size_t i = 0; i < colors.size(); i++)
|
||||
{
|
||||
RGBColor c = colors[i] | (leds[i].value << 24);
|
||||
colour.push_back(c);
|
||||
}
|
||||
|
||||
controller->SetLedsDirect(colour);
|
||||
}
|
||||
|
||||
void RGBController_BloodyMouse::UpdateZoneLEDs(int /*zone*/)
|
||||
{
|
||||
DeviceUpdateLEDs();
|
||||
}
|
||||
|
||||
void RGBController_BloodyMouse::UpdateSingleLED(int /*led*/)
|
||||
{
|
||||
DeviceUpdateLEDs();
|
||||
}
|
||||
|
||||
void RGBController_BloodyMouse::DeviceUpdateMode()
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| This device only supports Direct mode |
|
||||
\*---------------------------------------------------------*/
|
||||
}
|
||||
@@ -0,0 +1,43 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_BloodyMouse.h |
|
||||
| |
|
||||
| RGBController for A4Tech Bloody Mouse |
|
||||
| |
|
||||
| Chris M (Dr_No) 30 Jun 2022 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <vector>
|
||||
#include "RGBController.h"
|
||||
#include "BloodyMouseController.h"
|
||||
|
||||
struct mouse_zone
|
||||
{
|
||||
std::string name;
|
||||
std::vector<uint8_t> zone_leds;
|
||||
};
|
||||
|
||||
typedef std::vector<mouse_zone> mouse_layout;
|
||||
|
||||
class RGBController_BloodyMouse : public RGBController
|
||||
{
|
||||
public:
|
||||
RGBController_BloodyMouse(BloodyMouseController* controller_ptr);
|
||||
~RGBController_BloodyMouse();
|
||||
|
||||
void SetupZones();
|
||||
void ResizeZone(int zone, int new_size);
|
||||
|
||||
void DeviceUpdateLEDs();
|
||||
void UpdateZoneLEDs(int zone);
|
||||
void UpdateSingleLED(int led);
|
||||
|
||||
void DeviceUpdateMode();
|
||||
|
||||
private:
|
||||
BloodyMouseController* controller;
|
||||
};
|
||||
@@ -0,0 +1,195 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AMBXController.cpp |
|
||||
| |
|
||||
| Driver for Philips amBX Gaming lights |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "AMBXController.h"
|
||||
#include "LogManager.h"
|
||||
#include "StringUtils.h"
|
||||
#include <cstring>
|
||||
#include <thread>
|
||||
#include <chrono>
|
||||
|
||||
AMBXController::AMBXController(const char* path)
|
||||
{
|
||||
initialized = false;
|
||||
usb_context = nullptr;
|
||||
dev_handle = nullptr;
|
||||
|
||||
location = "USB: ";
|
||||
location += path;
|
||||
|
||||
// Initialize libusb in this instance
|
||||
if(libusb_init(&usb_context) < 0)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
// Get the device list
|
||||
libusb_device** device_list;
|
||||
ssize_t device_count = libusb_get_device_list(usb_context, &device_list);
|
||||
|
||||
if(device_count < 0)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
for(ssize_t i = 0; i < device_count; i++)
|
||||
{
|
||||
libusb_device* device = device_list[i];
|
||||
struct libusb_device_descriptor desc;
|
||||
|
||||
if(libusb_get_device_descriptor(device, &desc) != LIBUSB_SUCCESS)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
if(desc.idVendor == AMBX_VID && desc.idProduct == AMBX_PID)
|
||||
{
|
||||
uint8_t bus = libusb_get_bus_number(device);
|
||||
uint8_t address = libusb_get_device_address(device);
|
||||
|
||||
char current_path[32];
|
||||
snprintf(current_path, sizeof(current_path), "%d-%d", bus, address);
|
||||
|
||||
if(strcmp(path, current_path) == 0)
|
||||
{
|
||||
// Try to open this device
|
||||
if(libusb_open(device, &dev_handle) != LIBUSB_SUCCESS)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
// Try to detach the kernel driver if attached
|
||||
if(libusb_kernel_driver_active(dev_handle, 0))
|
||||
{
|
||||
libusb_detach_kernel_driver(dev_handle, 0);
|
||||
}
|
||||
|
||||
// Set auto-detach for Windows compatibility
|
||||
libusb_set_auto_detach_kernel_driver(dev_handle, 1);
|
||||
|
||||
// Claim the interface
|
||||
if(libusb_claim_interface(dev_handle, 0) != LIBUSB_SUCCESS)
|
||||
{
|
||||
libusb_close(dev_handle);
|
||||
dev_handle = nullptr;
|
||||
continue;
|
||||
}
|
||||
|
||||
// Get string descriptor for serial number if available
|
||||
if(desc.iSerialNumber != 0)
|
||||
{
|
||||
unsigned char serial_str[256];
|
||||
int serial_result = libusb_get_string_descriptor_ascii(dev_handle, desc.iSerialNumber,
|
||||
serial_str, sizeof(serial_str));
|
||||
if(serial_result > 0)
|
||||
{
|
||||
serial = std::string(reinterpret_cast<char*>(serial_str), serial_result);
|
||||
}
|
||||
}
|
||||
|
||||
// Successfully opened and claimed the device
|
||||
initialized = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
libusb_free_device_list(device_list, 1);
|
||||
}
|
||||
|
||||
AMBXController::~AMBXController()
|
||||
{
|
||||
if(initialized)
|
||||
{
|
||||
// Turn off all lights before closing
|
||||
unsigned int led_ids[5] =
|
||||
{
|
||||
AMBX_LIGHT_LEFT,
|
||||
AMBX_LIGHT_RIGHT,
|
||||
AMBX_LIGHT_WALL_LEFT,
|
||||
AMBX_LIGHT_WALL_CENTER,
|
||||
AMBX_LIGHT_WALL_RIGHT
|
||||
};
|
||||
|
||||
RGBColor colors[5] = { 0, 0, 0, 0, 0 };
|
||||
SetLEDColors(led_ids, colors, 5);
|
||||
}
|
||||
|
||||
if(dev_handle != nullptr)
|
||||
{
|
||||
// Release the interface
|
||||
libusb_release_interface(dev_handle, 0);
|
||||
|
||||
// Close the device
|
||||
libusb_close(dev_handle);
|
||||
dev_handle = nullptr;
|
||||
}
|
||||
|
||||
if(usb_context != nullptr)
|
||||
{
|
||||
libusb_exit(usb_context);
|
||||
usb_context = nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
std::string AMBXController::GetDeviceLocation()
|
||||
{
|
||||
return location;
|
||||
}
|
||||
|
||||
std::string AMBXController::GetSerialString()
|
||||
{
|
||||
return serial;
|
||||
}
|
||||
|
||||
bool AMBXController::IsInitialized()
|
||||
{
|
||||
return initialized;
|
||||
}
|
||||
|
||||
void AMBXController::SendPacket(unsigned char* packet, unsigned int size)
|
||||
{
|
||||
if(!initialized || dev_handle == nullptr)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
int actual_length = 0;
|
||||
libusb_interrupt_transfer(dev_handle, AMBX_ENDPOINT_OUT, packet, size, &actual_length, 100);
|
||||
}
|
||||
|
||||
void AMBXController::SetLEDColor(unsigned int led, RGBColor color)
|
||||
{
|
||||
if(!initialized)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
unsigned char color_buf[6] =
|
||||
{
|
||||
AMBX_PACKET_HEADER,
|
||||
static_cast<unsigned char>(led),
|
||||
AMBX_SET_COLOR,
|
||||
(unsigned char)RGBGetRValue(color),
|
||||
(unsigned char)RGBGetGValue(color),
|
||||
(unsigned char)RGBGetBValue(color)
|
||||
};
|
||||
|
||||
SendPacket(color_buf, 6);
|
||||
|
||||
std::this_thread::sleep_for(std::chrono::milliseconds(2));
|
||||
}
|
||||
|
||||
void AMBXController::SetLEDColors(unsigned int* leds, RGBColor* colors, unsigned int count)
|
||||
{
|
||||
for(unsigned int i = 0; i < count; i++)
|
||||
{
|
||||
SetLEDColor(leds[i], colors[i]);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,57 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AMBXController.h |
|
||||
| |
|
||||
| Driver for Philips amBX Gaming lights |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "RGBController.h"
|
||||
#include <string>
|
||||
|
||||
#ifdef _WIN32
|
||||
#include "dependencies/libusb-1.0.27/include/libusb.h"
|
||||
#else
|
||||
#include <libusb.h>
|
||||
#endif
|
||||
|
||||
#define AMBX_VID 0x0471
|
||||
#define AMBX_PID 0x083F
|
||||
#define AMBX_ENDPOINT_OUT 0x02
|
||||
#define AMBX_PACKET_HEADER 0xA1
|
||||
#define AMBX_SET_COLOR 0x03
|
||||
|
||||
enum
|
||||
{
|
||||
AMBX_LIGHT_LEFT = 0x0B,
|
||||
AMBX_LIGHT_RIGHT = 0x1B,
|
||||
AMBX_LIGHT_WALL_LEFT = 0x2B,
|
||||
AMBX_LIGHT_WALL_CENTER = 0x3B,
|
||||
AMBX_LIGHT_WALL_RIGHT = 0x4B
|
||||
};
|
||||
|
||||
class AMBXController
|
||||
{
|
||||
public:
|
||||
AMBXController(const char* path);
|
||||
~AMBXController();
|
||||
|
||||
std::string GetDeviceLocation();
|
||||
std::string GetSerialString();
|
||||
|
||||
bool IsInitialized();
|
||||
void SetLEDColor(unsigned int led, RGBColor color);
|
||||
void SetLEDColors(unsigned int* leds, RGBColor* colors, unsigned int count);
|
||||
|
||||
private:
|
||||
libusb_context* usb_context;
|
||||
libusb_device_handle* dev_handle;
|
||||
std::string location;
|
||||
std::string serial;
|
||||
bool initialized;
|
||||
|
||||
void SendPacket(unsigned char* packet, unsigned int size);
|
||||
};
|
||||
@@ -0,0 +1,83 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AMBXControllerDetect.cpp |
|
||||
| |
|
||||
| Detector for Philips amBX Gaming lights |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "Detector.h"
|
||||
#include "AMBXController.h"
|
||||
#include "RGBController.h"
|
||||
#include "RGBController_AMBX.h"
|
||||
|
||||
#ifdef _WIN32
|
||||
#include "dependencies/libusb-1.0.27/include/libusb.h"
|
||||
#else
|
||||
#include <libusb.h>
|
||||
#endif
|
||||
|
||||
/******************************************************************************************\
|
||||
* *
|
||||
* DetectAMBXControllers *
|
||||
* *
|
||||
* Detect Philips amBX Gaming devices *
|
||||
* *
|
||||
\******************************************************************************************/
|
||||
|
||||
void DetectAMBXControllers()
|
||||
{
|
||||
libusb_context* ctx = NULL;
|
||||
|
||||
if(libusb_init(&ctx) < 0)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
libusb_device** devs;
|
||||
ssize_t num_devs = libusb_get_device_list(ctx, &devs);
|
||||
|
||||
if(num_devs <= 0)
|
||||
{
|
||||
libusb_exit(ctx);
|
||||
return;
|
||||
}
|
||||
|
||||
for(ssize_t i = 0; i < num_devs; i++)
|
||||
{
|
||||
libusb_device* dev = devs[i];
|
||||
libusb_device_descriptor desc;
|
||||
|
||||
if(libusb_get_device_descriptor(dev, &desc) != 0)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
if(desc.idVendor == AMBX_VID && desc.idProduct == AMBX_PID)
|
||||
{
|
||||
uint8_t bus = libusb_get_bus_number(dev);
|
||||
uint8_t address = libusb_get_device_address(dev);
|
||||
char device_path[32];
|
||||
snprintf(device_path, sizeof(device_path), "%d-%d", bus, address);
|
||||
|
||||
// Use the AMBXController to handle opening and initializing
|
||||
AMBXController* controller = new AMBXController(device_path);
|
||||
|
||||
if(controller->IsInitialized())
|
||||
{
|
||||
RGBController_AMBX* rgb_controller = new RGBController_AMBX(controller);
|
||||
ResourceManager::get()->RegisterRGBController(rgb_controller);
|
||||
}
|
||||
else
|
||||
{
|
||||
delete controller;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
libusb_free_device_list(devs, 1);
|
||||
libusb_exit(ctx);
|
||||
}
|
||||
|
||||
REGISTER_DETECTOR("Philips amBX", DetectAMBXControllers);
|
||||
@@ -0,0 +1,179 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_AMBX.cpp |
|
||||
| |
|
||||
| RGB Controller for Philips amBX Gaming lights |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "RGBController_AMBX.h"
|
||||
|
||||
/**------------------------------------------------------------------*\
|
||||
@name Philips amBX
|
||||
@category Accessory
|
||||
@type USB
|
||||
@save :x:
|
||||
@direct :white_check_mark:
|
||||
@effects :x:
|
||||
@detectors DetectAMBXControllers
|
||||
@comment The Philips amBX Gaming lights system includes left and right
|
||||
lights and a wall-washer bar with three zones.
|
||||
\*-------------------------------------------------------------------*/
|
||||
|
||||
RGBController_AMBX::RGBController_AMBX(AMBXController* controller_ptr)
|
||||
{
|
||||
controller = controller_ptr;
|
||||
|
||||
name = "Philips amBX";
|
||||
vendor = "Philips";
|
||||
type = DEVICE_TYPE_ACCESSORY;
|
||||
description = "Philips amBX Gaming Device";
|
||||
location = controller->GetDeviceLocation();
|
||||
serial = controller->GetSerialString();
|
||||
|
||||
mode Direct;
|
||||
Direct.name = "Direct";
|
||||
Direct.value = 0;
|
||||
Direct.flags = MODE_FLAG_HAS_PER_LED_COLOR;
|
||||
Direct.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Direct);
|
||||
|
||||
SetupZones();
|
||||
}
|
||||
|
||||
RGBController_AMBX::~RGBController_AMBX()
|
||||
{
|
||||
delete controller;
|
||||
}
|
||||
|
||||
void RGBController_AMBX::SetupZones()
|
||||
{
|
||||
// Set up zones
|
||||
zone side_lights_zone;
|
||||
side_lights_zone.name = "Side Lights";
|
||||
side_lights_zone.type = ZONE_TYPE_LINEAR;
|
||||
side_lights_zone.leds_min = 2;
|
||||
side_lights_zone.leds_max = 2;
|
||||
side_lights_zone.leds_count = 2;
|
||||
side_lights_zone.matrix_map = NULL;
|
||||
zones.push_back(side_lights_zone);
|
||||
|
||||
zone wallwasher_zone;
|
||||
wallwasher_zone.name = "Wallwasher";
|
||||
wallwasher_zone.type = ZONE_TYPE_LINEAR;
|
||||
wallwasher_zone.leds_min = 3;
|
||||
wallwasher_zone.leds_max = 3;
|
||||
wallwasher_zone.leds_count = 3;
|
||||
wallwasher_zone.matrix_map = NULL;
|
||||
zones.push_back(wallwasher_zone);
|
||||
|
||||
// Set up LEDs
|
||||
led left_light;
|
||||
left_light.name = "Left";
|
||||
left_light.value = AMBX_LIGHT_LEFT;
|
||||
leds.push_back(left_light);
|
||||
|
||||
led right_light;
|
||||
right_light.name = "Right";
|
||||
right_light.value = AMBX_LIGHT_RIGHT;
|
||||
leds.push_back(right_light);
|
||||
|
||||
led wall_left;
|
||||
wall_left.name = "Wall Left";
|
||||
wall_left.value = AMBX_LIGHT_WALL_LEFT;
|
||||
leds.push_back(wall_left);
|
||||
|
||||
led wall_center;
|
||||
wall_center.name = "Wall Center";
|
||||
wall_center.value = AMBX_LIGHT_WALL_CENTER;
|
||||
leds.push_back(wall_center);
|
||||
|
||||
led wall_right;
|
||||
wall_right.name = "Wall Right";
|
||||
wall_right.value = AMBX_LIGHT_WALL_RIGHT;
|
||||
leds.push_back(wall_right);
|
||||
|
||||
SetupColors();
|
||||
}
|
||||
|
||||
void RGBController_AMBX::ResizeZone(int /*zone*/, int /*new_size*/)
|
||||
{
|
||||
// This device does not support resizing zones
|
||||
}
|
||||
|
||||
void RGBController_AMBX::DeviceUpdateLEDs()
|
||||
{
|
||||
if(!controller->IsInitialized())
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
unsigned int led_values[5];
|
||||
RGBColor led_colors[5];
|
||||
|
||||
for(unsigned int led_idx = 0; led_idx < leds.size(); led_idx++)
|
||||
{
|
||||
led_values[led_idx] = leds[led_idx].value;
|
||||
led_colors[led_idx] = colors[led_idx];
|
||||
}
|
||||
|
||||
controller->SetLEDColors(led_values, led_colors, static_cast<unsigned int>(leds.size()));
|
||||
}
|
||||
|
||||
void RGBController_AMBX::UpdateZoneLEDs(int zone)
|
||||
{
|
||||
if(!controller->IsInitialized())
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
unsigned int start_idx = 0;
|
||||
unsigned int zone_size = 0;
|
||||
|
||||
// Calculate start index and size
|
||||
for(unsigned int z_idx = 0; z_idx < zones.size(); z_idx++)
|
||||
{
|
||||
if(z_idx == (unsigned int)zone)
|
||||
{
|
||||
zone_size = zones[z_idx].leds_count;
|
||||
break;
|
||||
}
|
||||
|
||||
start_idx += zones[z_idx].leds_count;
|
||||
}
|
||||
|
||||
unsigned int led_values[5];
|
||||
RGBColor led_colors[5];
|
||||
|
||||
for(unsigned int led_idx = 0; led_idx < zone_size; led_idx++)
|
||||
{
|
||||
unsigned int current_idx = start_idx + led_idx;
|
||||
led_values[led_idx] = leds[current_idx].value;
|
||||
led_colors[led_idx] = colors[current_idx];
|
||||
}
|
||||
|
||||
controller->SetLEDColors(led_values, led_colors, zone_size);
|
||||
}
|
||||
|
||||
void RGBController_AMBX::UpdateSingleLED(int led)
|
||||
{
|
||||
if(!controller->IsInitialized())
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
unsigned int led_value = leds[led].value;
|
||||
RGBColor color = colors[led];
|
||||
controller->SetLEDColor(led_value, color);
|
||||
}
|
||||
|
||||
void RGBController_AMBX::DeviceUpdateMode()
|
||||
{
|
||||
if(!controller->IsInitialized())
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
DeviceUpdateLEDs();
|
||||
}
|
||||
@@ -0,0 +1,32 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_AMBX.h |
|
||||
| |
|
||||
| RGB Controller for Philips amBX Gaming lights |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "RGBController.h"
|
||||
#include "AMBXController.h"
|
||||
|
||||
class RGBController_AMBX : public RGBController
|
||||
{
|
||||
public:
|
||||
RGBController_AMBX(AMBXController* controller_ptr);
|
||||
~RGBController_AMBX();
|
||||
|
||||
void SetupZones();
|
||||
void ResizeZone(int zone, int new_size);
|
||||
|
||||
void DeviceUpdateLEDs();
|
||||
void UpdateZoneLEDs(int zone);
|
||||
void UpdateSingleLED(int led);
|
||||
|
||||
void DeviceUpdateMode();
|
||||
|
||||
private:
|
||||
AMBXController* controller;
|
||||
};
|
||||
@@ -0,0 +1,374 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AMDWraithPrismController.cpp |
|
||||
| |
|
||||
| Driver for AMD Wraith Prism |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 06 Dec 2019 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include <cstring>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include "AMDWraithPrismController.h"
|
||||
#include "StringUtils.h"
|
||||
|
||||
AMDWraithPrismController::AMDWraithPrismController(hid_device* dev_handle, const char* path)
|
||||
{
|
||||
dev = dev_handle;
|
||||
location = path;
|
||||
|
||||
current_fan_mode = AMD_WRAITH_PRISM_FAN_LOGO_MODE_STATIC;
|
||||
current_fan_speed = 0xFF;
|
||||
current_fan_random_color = false;
|
||||
current_fan_brightness = 0xFF;
|
||||
|
||||
current_logo_mode = AMD_WRAITH_PRISM_FAN_LOGO_MODE_STATIC;
|
||||
current_logo_speed = 0xFF;
|
||||
current_logo_random_color = false;
|
||||
current_logo_brightness = 0xFF;
|
||||
|
||||
current_ring_mode = AMD_WRAITH_PRISM_EFFECT_CHANNEL_STATIC;
|
||||
current_ring_speed = 0xFF;
|
||||
current_ring_direction = false;
|
||||
current_ring_brightness = 0xFF;
|
||||
}
|
||||
|
||||
AMDWraithPrismController::~AMDWraithPrismController()
|
||||
{
|
||||
hid_close(dev);
|
||||
}
|
||||
|
||||
std::string AMDWraithPrismController::GetLocationString()
|
||||
{
|
||||
return("HID: " + location);
|
||||
}
|
||||
|
||||
std::string AMDWraithPrismController::GetSerialString()
|
||||
{
|
||||
wchar_t serial_string[128];
|
||||
int ret = hid_get_serial_number_string(dev, serial_string, 128);
|
||||
|
||||
if(ret != 0)
|
||||
{
|
||||
return("");
|
||||
}
|
||||
|
||||
return(StringUtils::wstring_to_string(serial_string));
|
||||
}
|
||||
|
||||
std::string AMDWraithPrismController::GetFirmwareVersionString()
|
||||
{
|
||||
std::string ret_string = "";
|
||||
|
||||
unsigned char usb_buf[] =
|
||||
{
|
||||
0x00,
|
||||
0x12, 0x20, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
};
|
||||
|
||||
unsigned char fw_buf[16] = {0x00};
|
||||
|
||||
hid_write(dev, usb_buf, 65);
|
||||
hid_read(dev, usb_buf, 64);
|
||||
|
||||
for(int char_idx = 0; char_idx < 16; char_idx+=2)
|
||||
{
|
||||
if(usb_buf[char_idx + 0x08] != 0)
|
||||
{
|
||||
fw_buf[char_idx / 2] = usb_buf[char_idx + 0x08];
|
||||
}
|
||||
else
|
||||
{
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
ret_string.append((char *)fw_buf);
|
||||
|
||||
return(ret_string);
|
||||
}
|
||||
|
||||
void AMDWraithPrismController::SetFanMode(unsigned char mode, unsigned char speed, unsigned char brightness, bool random_color)
|
||||
{
|
||||
current_fan_mode = mode;
|
||||
current_fan_speed = speed_values_fan_logo[mode][speed];
|
||||
current_fan_brightness = brightness;
|
||||
current_fan_random_color = random_color;
|
||||
}
|
||||
|
||||
void AMDWraithPrismController::SetFanColor(unsigned char red, unsigned char green, unsigned char blue)
|
||||
{
|
||||
SendEffectChannelUpdate
|
||||
(
|
||||
AMD_WRAITH_PRISM_EFFECT_CHANNEL_FAN_LED,
|
||||
current_fan_speed,
|
||||
false,
|
||||
current_fan_random_color,
|
||||
current_fan_mode,
|
||||
current_fan_brightness,
|
||||
red,
|
||||
green,
|
||||
blue
|
||||
);
|
||||
}
|
||||
|
||||
void AMDWraithPrismController::SetLogoMode(unsigned char mode, unsigned char speed, unsigned char brightness, bool random_color)
|
||||
{
|
||||
current_logo_mode = mode;
|
||||
current_logo_speed = speed_values_fan_logo[mode][speed];
|
||||
current_logo_brightness = brightness;
|
||||
current_logo_random_color = random_color;
|
||||
}
|
||||
|
||||
void AMDWraithPrismController::SetLogoColor(unsigned char red, unsigned char green, unsigned char blue)
|
||||
{
|
||||
SendEffectChannelUpdate
|
||||
(
|
||||
AMD_WRAITH_PRISM_EFFECT_CHANNEL_LOGO_LED,
|
||||
current_logo_speed,
|
||||
false,
|
||||
current_logo_random_color,
|
||||
current_logo_mode,
|
||||
current_logo_brightness,
|
||||
red,
|
||||
green,
|
||||
blue
|
||||
);
|
||||
}
|
||||
|
||||
void AMDWraithPrismController::SetRingMode(unsigned char mode, unsigned char speed, unsigned char brightness, bool direction, bool random_color)
|
||||
{
|
||||
current_ring_mode = mode;
|
||||
current_ring_speed = speed_values_ring[mode][speed];
|
||||
current_ring_direction = direction;
|
||||
current_ring_brightness = brightness;
|
||||
current_ring_random_color = random_color;
|
||||
}
|
||||
|
||||
void AMDWraithPrismController::SetRingColor(unsigned char red, unsigned char green, unsigned char blue)
|
||||
{
|
||||
SetRingEffectChannel(current_ring_mode);
|
||||
|
||||
SendEffectChannelUpdate
|
||||
(
|
||||
current_ring_mode,
|
||||
current_ring_speed,
|
||||
current_ring_direction,
|
||||
current_ring_random_color,
|
||||
mode_value_ring[current_ring_mode],
|
||||
current_ring_brightness,
|
||||
red,
|
||||
green,
|
||||
blue
|
||||
);
|
||||
|
||||
SendApplyCommand();
|
||||
}
|
||||
|
||||
void AMDWraithPrismController::SetRingEffectChannel(unsigned char channel)
|
||||
{
|
||||
SendChannelRemap(channel, AMD_WRAITH_PRISM_EFFECT_CHANNEL_LOGO_LED, AMD_WRAITH_PRISM_EFFECT_CHANNEL_FAN_LED);
|
||||
}
|
||||
|
||||
void AMDWraithPrismController::SendEnableCommand(bool direct)
|
||||
{
|
||||
unsigned char usb_buf[] =
|
||||
{
|
||||
0x00,
|
||||
0x41, 0x80, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
};
|
||||
|
||||
if(direct)
|
||||
{
|
||||
usb_buf[0x02] = 0x03;
|
||||
}
|
||||
|
||||
hid_write(dev, usb_buf, 65);
|
||||
hid_read(dev, usb_buf, 64);
|
||||
}
|
||||
|
||||
void AMDWraithPrismController::SendApplyCommand()
|
||||
{
|
||||
unsigned char usb_buf[] =
|
||||
{
|
||||
0x00,
|
||||
0x51, 0x28, 0x00, 0x00,
|
||||
0xE0, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
};
|
||||
|
||||
hid_write(dev, usb_buf, 65);
|
||||
hid_read(dev, usb_buf, 64);
|
||||
}
|
||||
|
||||
void AMDWraithPrismController::SendDirectPacket
|
||||
(
|
||||
unsigned char size,
|
||||
unsigned char * led_ids,
|
||||
RGBColor * colors
|
||||
)
|
||||
{
|
||||
unsigned char usb_buf[] =
|
||||
{
|
||||
0x00,
|
||||
0xC0, 0x01, size, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
};
|
||||
|
||||
for(unsigned int led_idx = 0; led_idx < size; led_idx++)
|
||||
{
|
||||
unsigned int index = led_idx * 4;
|
||||
|
||||
usb_buf[index + 5] = led_ids[led_idx];
|
||||
usb_buf[index + 6] = RGBGetRValue(colors[led_idx]);
|
||||
usb_buf[index + 7] = RGBGetGValue(colors[led_idx]);
|
||||
usb_buf[index + 8] = RGBGetBValue(colors[led_idx]);
|
||||
}
|
||||
|
||||
hid_write(dev, usb_buf, 65);
|
||||
hid_read(dev, usb_buf, 64);
|
||||
}
|
||||
|
||||
void AMDWraithPrismController::SendEffectChannelUpdate
|
||||
(
|
||||
unsigned char effect_channel,
|
||||
unsigned char speed,
|
||||
bool direction,
|
||||
bool random_color,
|
||||
unsigned char mode,
|
||||
unsigned char brightness,
|
||||
unsigned char red,
|
||||
unsigned char green,
|
||||
unsigned char blue
|
||||
)
|
||||
{
|
||||
unsigned char usb_buf[] =
|
||||
{
|
||||
0x00,
|
||||
0x51, 0x2C, 0x01, 0x00,
|
||||
0x05, 0xFF, 0x00, 0x01,
|
||||
0xFF, 0xFF, 0x00, 0xFF,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0xFF, 0xFF, 0xFF, 0xFF,
|
||||
0xFF, 0xFF, 0xFF, 0xFF,
|
||||
0xFF, 0xFF, 0xFF, 0xFF,
|
||||
0xFF, 0xFF, 0xFF, 0xFF,
|
||||
0xFF, 0xFF, 0xFF, 0xFF,
|
||||
0xFF, 0xFF, 0xFF, 0xFF,
|
||||
0xFF, 0xFF, 0xFF, 0xFF,
|
||||
0xFF, 0xFF, 0xFF, 0xFF,
|
||||
0xFF, 0xFF, 0xFF, 0xFF,
|
||||
0xFF, 0xFF, 0xFF, 0xFF,
|
||||
0xFF, 0xFF, 0xFF, 0xFF,
|
||||
0xFF, 0xFF, 0xFF, 0xFF
|
||||
};
|
||||
|
||||
usb_buf[0x05] = effect_channel;
|
||||
usb_buf[0x06] = speed;
|
||||
usb_buf[0x07] = (direction ? 0x01 : 0x00) | (random_color ? 0x80 : 0x00);
|
||||
usb_buf[0x08] = mode;
|
||||
|
||||
usb_buf[0x0A] = brightness;
|
||||
|
||||
usb_buf[0x0B] = red;
|
||||
usb_buf[0x0C] = green;
|
||||
usb_buf[0x0D] = blue;
|
||||
|
||||
hid_write(dev, usb_buf, 65);
|
||||
hid_read(dev, usb_buf, 64);
|
||||
}
|
||||
|
||||
void AMDWraithPrismController::SendChannelRemap(unsigned char ring_channel, unsigned char logo_channel, unsigned char fan_channel)
|
||||
{
|
||||
unsigned char usb_buf[] =
|
||||
{
|
||||
0x00,
|
||||
0x51, 0xA0, 0x01, 0x00,
|
||||
0x00, 0x03, 0x00, 0x00,
|
||||
0x05, 0x06, 0x07, 0x07,
|
||||
0x07, 0x07, 0x07, 0x07,
|
||||
0x07, 0x07, 0x07, 0x07,
|
||||
0x07, 0x07, 0x07, 0x07,
|
||||
0x07, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00,
|
||||
};
|
||||
|
||||
usb_buf[0x09] = logo_channel;
|
||||
usb_buf[0x0A] = fan_channel;
|
||||
|
||||
for(int led = 0x0B; led <= 0x19; led++)
|
||||
{
|
||||
usb_buf[led] = ring_channel;
|
||||
}
|
||||
|
||||
hid_write(dev, usb_buf, 65);
|
||||
hid_read(dev, usb_buf, 64);
|
||||
}
|
||||
@@ -0,0 +1,157 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AMDWraithPrismController.h |
|
||||
| |
|
||||
| Driver for AMD Wraith Prism |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 06 Dec 2019 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <string>
|
||||
#include <hidapi.h>
|
||||
#include "RGBController.h"
|
||||
|
||||
#define AMD_WRAITH_PRISM_FAN_BRIGHTNESS_DEFAULT_MAX 0xFF
|
||||
#define AMD_WRAITH_PRISM_FAN_BRIGHTNESS_CYCLE_MAX 0x7F
|
||||
|
||||
static const unsigned char speed_values_fan_logo[][5] =
|
||||
{
|
||||
{ 0x00, 0x00, 0x00, 0x00, 0x00 }, /* */
|
||||
{ 0xFF, 0xFF, 0xFF, 0xFF, 0xFF }, /* Static */
|
||||
{ 0x96, 0x8C, 0x80, 0x6E, 0x68 }, /* Color Cycle */
|
||||
{ 0x3C, 0x37, 0x31, 0x2C, 0x26 }, /* Breathing */
|
||||
};
|
||||
|
||||
static const unsigned char mode_value_ring[] =
|
||||
{
|
||||
0xFF,
|
||||
0x03,
|
||||
0xFF,
|
||||
0x00,
|
||||
0x00,
|
||||
0x00,
|
||||
0x00,
|
||||
0x05,
|
||||
0xFF,
|
||||
0xC3,
|
||||
0x4A,
|
||||
0x05
|
||||
};
|
||||
|
||||
static const unsigned char speed_values_ring[][5] =
|
||||
{
|
||||
{ 0xFF, 0xFF, 0xFF, 0xFF, 0xFF }, /* Static */
|
||||
{ 0x3C, 0x37, 0x31, 0x2C, 0x26 }, /* Breathing */
|
||||
{ 0x96, 0x8C, 0x80, 0x6E, 0x68 }, /* Color Cycle */
|
||||
{ 0x00, 0x00, 0x00, 0x00, 0x00 }, /* */
|
||||
{ 0x00, 0x00, 0x00, 0x00, 0x00 }, /* */
|
||||
{ 0x00, 0x00, 0x00, 0x00, 0x00 }, /* */
|
||||
{ 0x00, 0x00, 0x00, 0x00, 0x00 }, /* */
|
||||
{ 0x72, 0x68, 0x64, 0x62, 0x61 }, /* Rainbow */
|
||||
{ 0x00, 0x00, 0x00, 0x00, 0x00 }, /* Bounce */
|
||||
{ 0x77, 0x74, 0x6E, 0x6B, 0x67 }, /* Chase */
|
||||
{ 0x77, 0x74, 0x6E, 0x6B, 0x67 }, /* Swirl */
|
||||
{ 0x00, 0x00, 0x00, 0x00, 0x00 }, /* Morse Code */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
AMD_WRAITH_PRISM_FAN_LOGO_MODE_STATIC = 0x01, /* Fan/Logo Static Mode */
|
||||
AMD_WRAITH_PRISM_FAN_LOGO_MODE_COLOR_CYCLE = 0x02, /* Fan/Logo Color Cycle Mode */
|
||||
AMD_WRAITH_PRISM_FAN_LOGO_MODE_BREATHING = 0x03, /* Fan/Logo Breathing Mode */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
AMD_WRAITH_PRISM_EFFECT_CHANNEL_STATIC = 0x00, /* Static effect channel */
|
||||
AMD_WRAITH_PRISM_EFFECT_CHANNEL_BREATHING = 0x01, /* Breathing effect channel */
|
||||
AMD_WRAITH_PRISM_EFFECT_CHANNEL_COLOR_CYCLE = 0x02, /* Color cycle effect channel */
|
||||
AMD_WRAITH_PRISM_EFFECT_CHANNEL_LOGO_LED = 0x05, /* Logo LED effect channel */
|
||||
AMD_WRAITH_PRISM_EFFECT_CHANNEL_FAN_LED = 0x06, /* Fan LED effect channel */
|
||||
AMD_WRAITH_PRISM_EFFECT_CHANNEL_RAINBOW = 0x07, /* Rainbow effect channel */
|
||||
AMD_WRAITH_PRISM_EFFECT_CHANNEL_BOUNCE = 0x08, /* Bounce effect channel */
|
||||
AMD_WRAITH_PRISM_EFFECT_CHANNEL_CHASE = 0x09, /* Chase effect channel */
|
||||
AMD_WRAITH_PRISM_EFFECT_CHANNEL_SWIRL = 0x0A, /* Swirl effect channel */
|
||||
AMD_WRAITH_PRISM_EFFECT_CHANNEL_MORSE = 0x0B, /* Morse code effect channel */
|
||||
AMD_WRAITH_PRISM_EFFECT_CHANNEL_DIRECT = 0xFF, /* Value for direct mode */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
AMD_WRAITH_PRISM_SPEED_SLOWEST = 0x00, /* Slowest speed */
|
||||
AMD_WRAITH_PRISM_SPEED_SLOW = 0x01, /* Slow speed */
|
||||
AMD_WRAITH_PRISM_SPEED_NORMAL = 0x02, /* Normal speed */
|
||||
AMD_WRAITH_PRISM_SPEED_FAST = 0x03, /* Fast speed */
|
||||
AMD_WRAITH_PRISM_SPEED_FASTEST = 0x04, /* Fastest speed */
|
||||
};
|
||||
|
||||
class AMDWraithPrismController
|
||||
{
|
||||
public:
|
||||
AMDWraithPrismController(hid_device* dev_handle, const char* path);
|
||||
~AMDWraithPrismController();
|
||||
|
||||
std::string GetEffectChannelString(unsigned char channel);
|
||||
std::string GetFirmwareVersionString();
|
||||
std::string GetLocationString();
|
||||
std::string GetSerialString();
|
||||
|
||||
unsigned char current_fan_mode;
|
||||
unsigned char current_fan_speed;
|
||||
unsigned char current_fan_brightness;
|
||||
bool current_fan_random_color;
|
||||
|
||||
unsigned char current_logo_mode;
|
||||
unsigned char current_logo_speed;
|
||||
unsigned char current_logo_brightness;
|
||||
bool current_logo_random_color;
|
||||
|
||||
unsigned char current_ring_mode;
|
||||
unsigned char current_ring_speed;
|
||||
unsigned char current_ring_brightness;
|
||||
bool current_ring_direction;
|
||||
bool current_ring_random_color;
|
||||
|
||||
void SetFanMode(unsigned char mode, unsigned char speed, unsigned char brightness, bool random_color);
|
||||
void SetFanColor(unsigned char red, unsigned char green, unsigned char blue);
|
||||
void SetLogoMode(unsigned char mode, unsigned char speed, unsigned char brightness, bool random_color);
|
||||
void SetLogoColor(unsigned char red, unsigned char green, unsigned char blue);
|
||||
void SetRingMode(unsigned char mode, unsigned char speed, unsigned char brightness, bool direction, bool random_color);
|
||||
void SetRingColor(unsigned char red, unsigned char green, unsigned char blue);
|
||||
|
||||
void SendDirectPacket
|
||||
(
|
||||
unsigned char size,
|
||||
unsigned char * led_ids,
|
||||
RGBColor * colors
|
||||
);
|
||||
|
||||
void SendEnableCommand(bool direct);
|
||||
|
||||
void SendApplyCommand();
|
||||
|
||||
private:
|
||||
hid_device* dev;
|
||||
std::string location;
|
||||
|
||||
void SetRingEffectChannel(unsigned char channel);
|
||||
|
||||
void SendEffectChannelUpdate
|
||||
(
|
||||
unsigned char effect_channel,
|
||||
unsigned char speed,
|
||||
bool direction,
|
||||
bool random_color,
|
||||
unsigned char mode,
|
||||
unsigned char brightness,
|
||||
unsigned char red,
|
||||
unsigned char green,
|
||||
unsigned char blue
|
||||
);
|
||||
|
||||
void SendChannelRemap(unsigned char ring_channel, unsigned char logo_channel, unsigned char fan_channel);
|
||||
};
|
||||
@@ -0,0 +1,48 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AMDWraithPrismControllerDetect.cpp |
|
||||
| |
|
||||
| Detector for AMD Wraith Prism |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 06 Dec 2019 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include <hidapi.h>
|
||||
#include "Detector.h"
|
||||
#include "AMDWraithPrismController.h"
|
||||
#include "RGBController_AMDWraithPrism.h"
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| AMD Wraith Prism vendor ID |
|
||||
\*---------------------------------------------------------*/
|
||||
#define AMD_WRAITH_PRISM_VID 0x2516
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| AMD Wraith Prism product ID |
|
||||
\*---------------------------------------------------------*/
|
||||
#define AMD_WRAITH_PRISM_PID 0x0051
|
||||
|
||||
/******************************************************************************************\
|
||||
* *
|
||||
* DetectAMDWraithPrismControllers *
|
||||
* *
|
||||
* Tests the USB address to see if an AMD Wraith Prism controller exists there. *
|
||||
* *
|
||||
\******************************************************************************************/
|
||||
|
||||
void DetectAMDWraithPrismControllers(hid_device_info* info, const std::string&)
|
||||
{
|
||||
hid_device* dev = hid_open_path(info->path);
|
||||
|
||||
if(dev)
|
||||
{
|
||||
AMDWraithPrismController* controller = new AMDWraithPrismController(dev, info->path);
|
||||
RGBController_AMDWraithPrism* rgb_controller = new RGBController_AMDWraithPrism(controller);
|
||||
|
||||
ResourceManager::get()->RegisterRGBController(rgb_controller);
|
||||
}
|
||||
}
|
||||
|
||||
REGISTER_HID_DETECTOR_IP("AMD Wraith Prism", DetectAMDWraithPrismControllers, AMD_WRAITH_PRISM_VID, AMD_WRAITH_PRISM_PID, 1, 0xFF00);
|
||||
@@ -0,0 +1,336 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_AMDWraithPrism.cpp |
|
||||
| |
|
||||
| RGBController for AMD Wraith Prism |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 25 Dec 2019 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "RGBController_AMDWraithPrism.h"
|
||||
|
||||
/**------------------------------------------------------------------*\
|
||||
@name AMD Wraith Prism
|
||||
@category Cooler
|
||||
@type USB
|
||||
@save :o:
|
||||
@direct :white_check_mark:
|
||||
@effects :tools:
|
||||
@detectors DetectAMDWraithPrismControllers
|
||||
@comment The Wraith Prism comes with 2 cables but is only detectable
|
||||
and controlable when using the USB cable. `Morse Code` and `Mirage`
|
||||
modes have not been implemented. Saving to flash is supported by
|
||||
the device but not yet implemented.
|
||||
\*-------------------------------------------------------------------*/
|
||||
|
||||
RGBController_AMDWraithPrism::RGBController_AMDWraithPrism(AMDWraithPrismController* controller_ptr)
|
||||
{
|
||||
controller = controller_ptr;
|
||||
|
||||
name = "AMD Wraith Prism";
|
||||
vendor = "Cooler Master";
|
||||
type = DEVICE_TYPE_COOLER;
|
||||
description = "AMD Wraith Prism Device";
|
||||
version = controller->GetFirmwareVersionString();
|
||||
location = controller->GetLocationString();
|
||||
|
||||
mode Direct;
|
||||
Direct.name = "Direct";
|
||||
Direct.value = AMD_WRAITH_PRISM_EFFECT_CHANNEL_DIRECT;
|
||||
Direct.flags = MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
|
||||
Direct.brightness_min = 0;
|
||||
Direct.brightness_max = 0;
|
||||
Direct.brightness = 0;
|
||||
Direct.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Direct);
|
||||
|
||||
mode Breathing;
|
||||
Breathing.name = "Breathing";
|
||||
Breathing.value = AMD_WRAITH_PRISM_EFFECT_CHANNEL_BREATHING;
|
||||
Breathing.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
|
||||
Breathing.speed_min = AMD_WRAITH_PRISM_SPEED_SLOWEST;
|
||||
Breathing.speed_max = AMD_WRAITH_PRISM_SPEED_FASTEST;
|
||||
Breathing.brightness_min = 0;
|
||||
Breathing.brightness_max = AMD_WRAITH_PRISM_FAN_BRIGHTNESS_DEFAULT_MAX;
|
||||
Breathing.brightness = AMD_WRAITH_PRISM_FAN_BRIGHTNESS_DEFAULT_MAX;
|
||||
Breathing.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Breathing.speed = AMD_WRAITH_PRISM_SPEED_NORMAL;
|
||||
Breathing.colors.resize(3);
|
||||
modes.push_back(Breathing);
|
||||
|
||||
mode ColorCycle;
|
||||
ColorCycle.name = "Spectrum Cycle";
|
||||
ColorCycle.value = AMD_WRAITH_PRISM_EFFECT_CHANNEL_COLOR_CYCLE;
|
||||
ColorCycle.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_BRIGHTNESS;
|
||||
ColorCycle.speed_min = AMD_WRAITH_PRISM_SPEED_SLOWEST;
|
||||
ColorCycle.speed_max = AMD_WRAITH_PRISM_SPEED_FASTEST;
|
||||
ColorCycle.brightness_min = 0;
|
||||
ColorCycle.brightness_max = AMD_WRAITH_PRISM_FAN_BRIGHTNESS_CYCLE_MAX;
|
||||
ColorCycle.brightness = AMD_WRAITH_PRISM_FAN_BRIGHTNESS_CYCLE_MAX;
|
||||
ColorCycle.color_mode = MODE_COLORS_NONE;
|
||||
ColorCycle.speed = AMD_WRAITH_PRISM_SPEED_NORMAL;
|
||||
modes.push_back(ColorCycle);
|
||||
|
||||
mode Rainbow;
|
||||
Rainbow.name = "Rainbow Wave";
|
||||
Rainbow.value = AMD_WRAITH_PRISM_EFFECT_CHANNEL_RAINBOW;
|
||||
Rainbow.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_BRIGHTNESS;
|
||||
Rainbow.speed_min = AMD_WRAITH_PRISM_SPEED_SLOWEST;
|
||||
Rainbow.speed_max = AMD_WRAITH_PRISM_SPEED_FASTEST;
|
||||
Rainbow.brightness_min = 0;
|
||||
Rainbow.brightness_max = AMD_WRAITH_PRISM_FAN_BRIGHTNESS_DEFAULT_MAX;
|
||||
Rainbow.brightness = AMD_WRAITH_PRISM_FAN_BRIGHTNESS_DEFAULT_MAX; //The Ring zone can not get brighter but Logo / Fan can
|
||||
Rainbow.color_mode = MODE_COLORS_NONE;
|
||||
Rainbow.speed = AMD_WRAITH_PRISM_SPEED_NORMAL;
|
||||
modes.push_back(Rainbow);
|
||||
|
||||
mode Bounce;
|
||||
Bounce.name = "Bounce";
|
||||
Bounce.value = AMD_WRAITH_PRISM_EFFECT_CHANNEL_BOUNCE;
|
||||
Bounce.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_BRIGHTNESS;
|
||||
Bounce.speed_min = AMD_WRAITH_PRISM_SPEED_SLOWEST;
|
||||
Bounce.speed_max = AMD_WRAITH_PRISM_SPEED_FASTEST;
|
||||
Bounce.brightness_min = 0;
|
||||
Bounce.brightness_max = AMD_WRAITH_PRISM_FAN_BRIGHTNESS_DEFAULT_MAX;
|
||||
Bounce.brightness = AMD_WRAITH_PRISM_FAN_BRIGHTNESS_DEFAULT_MAX; //The Ring zone can not get brighter but Logo / Fan can
|
||||
Bounce.color_mode = MODE_COLORS_NONE;
|
||||
Bounce.speed = AMD_WRAITH_PRISM_SPEED_NORMAL;
|
||||
modes.push_back(Bounce);
|
||||
|
||||
mode Chase;
|
||||
Chase.name = "Chase";
|
||||
Chase.value = AMD_WRAITH_PRISM_EFFECT_CHANNEL_CHASE;
|
||||
Chase.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
|
||||
Chase.speed_min = AMD_WRAITH_PRISM_SPEED_SLOWEST;
|
||||
Chase.speed_max = AMD_WRAITH_PRISM_SPEED_FASTEST;
|
||||
Chase.brightness_min = 0;
|
||||
Chase.brightness_max = AMD_WRAITH_PRISM_FAN_BRIGHTNESS_DEFAULT_MAX;
|
||||
Chase.brightness = AMD_WRAITH_PRISM_FAN_BRIGHTNESS_DEFAULT_MAX;
|
||||
Chase.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Chase.speed = AMD_WRAITH_PRISM_SPEED_NORMAL;
|
||||
Chase.colors.resize(3);
|
||||
modes.push_back(Chase);
|
||||
|
||||
mode Swirl;
|
||||
Swirl.name = "Swirl";
|
||||
Swirl.value = AMD_WRAITH_PRISM_EFFECT_CHANNEL_SWIRL;
|
||||
Swirl.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
|
||||
Swirl.speed_min = AMD_WRAITH_PRISM_SPEED_SLOWEST;
|
||||
Swirl.speed_max = AMD_WRAITH_PRISM_SPEED_FASTEST;
|
||||
Swirl.brightness_min = 0;
|
||||
Swirl.brightness_max = AMD_WRAITH_PRISM_FAN_BRIGHTNESS_DEFAULT_MAX;
|
||||
Swirl.brightness = AMD_WRAITH_PRISM_FAN_BRIGHTNESS_DEFAULT_MAX;
|
||||
Swirl.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Swirl.speed = AMD_WRAITH_PRISM_SPEED_NORMAL;
|
||||
Swirl.colors.resize(3);
|
||||
modes.push_back(Swirl);
|
||||
|
||||
SetupZones();
|
||||
}
|
||||
|
||||
RGBController_AMDWraithPrism::~RGBController_AMDWraithPrism()
|
||||
{
|
||||
delete controller;
|
||||
}
|
||||
|
||||
void RGBController_AMDWraithPrism::SetupZones()
|
||||
{
|
||||
/*-----------------------------------------------------*\
|
||||
| LED maps |
|
||||
\*-----------------------------------------------------*/
|
||||
const unsigned int logo_leds[1] = { 0x00 };
|
||||
const unsigned int fan_leds[1] = { 0x01 };
|
||||
const unsigned int ring_leds[15] = { 0x08, 0x07, 0x06, 0x05, 0x04, 0x03, 0x02, 0x10,
|
||||
0x0F, 0x0E, 0x0D, 0x0C, 0x0B, 0x0A, 0x09 };
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up zones |
|
||||
\*-----------------------------------------------------*/
|
||||
zone logo_zone;
|
||||
logo_zone.name = "Logo";
|
||||
logo_zone.type = ZONE_TYPE_SINGLE;
|
||||
logo_zone.leds_min = 1;
|
||||
logo_zone.leds_max = 1;
|
||||
logo_zone.leds_count = 1;
|
||||
logo_zone.matrix_map = NULL;
|
||||
zones.push_back(logo_zone);
|
||||
|
||||
zone fan_zone;
|
||||
fan_zone.name = "Fan";
|
||||
fan_zone.type = ZONE_TYPE_SINGLE;
|
||||
fan_zone.leds_min = 1;
|
||||
fan_zone.leds_max = 1;
|
||||
fan_zone.leds_count = 1;
|
||||
fan_zone.matrix_map = NULL;
|
||||
zones.push_back(fan_zone);
|
||||
|
||||
zone ring_zone;
|
||||
ring_zone.name = "Ring";
|
||||
ring_zone.type = ZONE_TYPE_LINEAR;
|
||||
ring_zone.leds_min = 15;
|
||||
ring_zone.leds_max = 15;
|
||||
ring_zone.leds_count = 15;
|
||||
ring_zone.matrix_map = NULL;
|
||||
zones.push_back(ring_zone);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up LEDs |
|
||||
\*-----------------------------------------------------*/
|
||||
for(unsigned int led_idx = 0; led_idx < 1; led_idx++)
|
||||
{
|
||||
led logo_led;
|
||||
logo_led.name = "Logo LED";
|
||||
logo_led.value = logo_leds[led_idx];
|
||||
leds.push_back(logo_led);
|
||||
}
|
||||
|
||||
for(unsigned int led_idx = 0; led_idx < 1; led_idx++)
|
||||
{
|
||||
led fan_led;
|
||||
fan_led.name = "Fan LED";
|
||||
fan_led.value = fan_leds[led_idx];
|
||||
leds.push_back(fan_led);
|
||||
}
|
||||
|
||||
for(unsigned int led_idx = 0; led_idx < 15; led_idx++)
|
||||
{
|
||||
led ring_led;
|
||||
ring_led.name = "Ring LED";
|
||||
ring_led.value = ring_leds[led_idx];
|
||||
leds.push_back(ring_led);
|
||||
}
|
||||
|
||||
SetupColors();
|
||||
}
|
||||
|
||||
void RGBController_AMDWraithPrism::ResizeZone(int /*zone*/, int /*new_size*/)
|
||||
{
|
||||
/*-----------------------------------------------------*\
|
||||
| This device does not support resizing zones |
|
||||
\*-----------------------------------------------------*/
|
||||
}
|
||||
|
||||
void RGBController_AMDWraithPrism::DeviceUpdateLEDs()
|
||||
{
|
||||
if(modes[active_mode].color_mode == MODE_COLORS_PER_LED)
|
||||
{
|
||||
unsigned char led_ids[17];
|
||||
RGBColor color_buf[17];
|
||||
unsigned int leds_count;
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| Send logo and fan LEDs in the first packet |
|
||||
\*-------------------------------------------------*/
|
||||
leds_count = 0;
|
||||
for(std::size_t led_idx = 0; led_idx < 2; led_idx++)
|
||||
{
|
||||
led_ids[leds_count] = (unsigned char)leds[led_idx].value;
|
||||
color_buf[leds_count] = colors[led_idx];
|
||||
|
||||
leds_count++;
|
||||
}
|
||||
controller->SendDirectPacket(leds_count, led_ids, color_buf);
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| Send all ring LEDs in the second packet |
|
||||
\*-------------------------------------------------*/
|
||||
leds_count = 0;
|
||||
for(std::size_t led_idx = 0; led_idx < ( colors.size() - 2 ); led_idx++)
|
||||
{
|
||||
led_ids[leds_count] = (unsigned char)leds[led_idx + 2].value;
|
||||
color_buf[leds_count] = colors[led_idx + 2];
|
||||
|
||||
leds_count++;
|
||||
}
|
||||
controller->SendDirectPacket(leds_count, led_ids, color_buf);
|
||||
}
|
||||
else if(modes[active_mode].color_mode == MODE_COLORS_MODE_SPECIFIC)
|
||||
{
|
||||
unsigned char red = RGBGetRValue(modes[active_mode].colors[0]);
|
||||
unsigned char grn = RGBGetGValue(modes[active_mode].colors[0]);
|
||||
unsigned char blu = RGBGetBValue(modes[active_mode].colors[0]);
|
||||
controller->SetLogoColor(red, grn, blu);
|
||||
|
||||
red = RGBGetRValue(modes[active_mode].colors[1]);
|
||||
grn = RGBGetGValue(modes[active_mode].colors[1]);
|
||||
blu = RGBGetBValue(modes[active_mode].colors[1]);
|
||||
controller->SetFanColor(red, grn, blu);
|
||||
|
||||
red = RGBGetRValue(modes[active_mode].colors[2]);
|
||||
grn = RGBGetGValue(modes[active_mode].colors[2]);
|
||||
blu = RGBGetBValue(modes[active_mode].colors[2]);
|
||||
controller->SetRingColor(red, grn, blu);
|
||||
}
|
||||
else
|
||||
{
|
||||
controller->SetLogoColor(0, 0, 0);
|
||||
controller->SetFanColor(0, 0, 0);
|
||||
controller->SetRingColor(0, 0, 0);
|
||||
}
|
||||
}
|
||||
|
||||
void RGBController_AMDWraithPrism::UpdateZoneLEDs(int /*zone*/)
|
||||
{
|
||||
DeviceUpdateLEDs();
|
||||
}
|
||||
|
||||
void RGBController_AMDWraithPrism::UpdateSingleLED(int /*led*/)
|
||||
{
|
||||
DeviceUpdateLEDs();
|
||||
}
|
||||
|
||||
void RGBController_AMDWraithPrism::DeviceUpdateMode()
|
||||
{
|
||||
bool random = (modes[active_mode].color_mode == MODE_COLORS_RANDOM);
|
||||
|
||||
switch(modes[active_mode].value)
|
||||
{
|
||||
case AMD_WRAITH_PRISM_EFFECT_CHANNEL_DIRECT:
|
||||
controller->SendEnableCommand(true);
|
||||
controller->SendApplyCommand();
|
||||
break;
|
||||
|
||||
case AMD_WRAITH_PRISM_EFFECT_CHANNEL_COLOR_CYCLE:
|
||||
controller->SendEnableCommand(false);
|
||||
controller->SetRingMode(modes[active_mode].value, modes[active_mode].speed, modes[active_mode].brightness, modes[active_mode].direction, random);
|
||||
controller->SetFanMode(AMD_WRAITH_PRISM_FAN_LOGO_MODE_COLOR_CYCLE, modes[active_mode].speed, modes[active_mode].brightness, random);
|
||||
controller->SetLogoMode(AMD_WRAITH_PRISM_FAN_LOGO_MODE_COLOR_CYCLE, modes[active_mode].speed, modes[active_mode].brightness, random);
|
||||
break;
|
||||
|
||||
case AMD_WRAITH_PRISM_EFFECT_CHANNEL_RAINBOW:
|
||||
case AMD_WRAITH_PRISM_EFFECT_CHANNEL_BOUNCE:
|
||||
controller->SendEnableCommand(false);
|
||||
controller->SetRingMode(modes[active_mode].value, modes[active_mode].speed, modes[active_mode].brightness, modes[active_mode].direction, random);
|
||||
controller->SetFanMode(AMD_WRAITH_PRISM_FAN_LOGO_MODE_COLOR_CYCLE, modes[active_mode].speed, (modes[active_mode].brightness >> 1), random);
|
||||
controller->SetLogoMode(AMD_WRAITH_PRISM_FAN_LOGO_MODE_COLOR_CYCLE, modes[active_mode].speed, (modes[active_mode].brightness >> 1), random);
|
||||
break;
|
||||
|
||||
case AMD_WRAITH_PRISM_EFFECT_CHANNEL_BREATHING:
|
||||
controller->SendEnableCommand(false);
|
||||
controller->SetRingMode(modes[active_mode].value, modes[active_mode].speed, modes[active_mode].brightness, modes[active_mode].direction, random);
|
||||
controller->SetFanMode(AMD_WRAITH_PRISM_FAN_LOGO_MODE_BREATHING, modes[active_mode].speed, modes[active_mode].brightness, random);
|
||||
controller->SetLogoMode(AMD_WRAITH_PRISM_FAN_LOGO_MODE_BREATHING, modes[active_mode].speed, modes[active_mode].brightness, random);
|
||||
break;
|
||||
|
||||
default:
|
||||
if(random)
|
||||
{
|
||||
controller->SendEnableCommand(false);
|
||||
controller->SetRingMode(modes[active_mode].value, modes[active_mode].speed, modes[active_mode].brightness, modes[active_mode].direction, random);
|
||||
controller->SetFanMode(AMD_WRAITH_PRISM_FAN_LOGO_MODE_COLOR_CYCLE, modes[active_mode].speed, modes[active_mode].brightness, random);
|
||||
controller->SetLogoMode(AMD_WRAITH_PRISM_FAN_LOGO_MODE_COLOR_CYCLE, modes[active_mode].speed, modes[active_mode].brightness, random);
|
||||
}
|
||||
else
|
||||
{
|
||||
controller->SendEnableCommand(false);
|
||||
controller->SetRingMode(modes[active_mode].value, modes[active_mode].speed, modes[active_mode].brightness, modes[active_mode].direction, random);
|
||||
controller->SetFanMode(AMD_WRAITH_PRISM_FAN_LOGO_MODE_STATIC, modes[active_mode].speed, modes[active_mode].brightness, random);
|
||||
controller->SetLogoMode(AMD_WRAITH_PRISM_FAN_LOGO_MODE_STATIC, modes[active_mode].speed, modes[active_mode].brightness, random);
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
DeviceUpdateLEDs();
|
||||
}
|
||||
@@ -0,0 +1,35 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_AMDWraithPrism.h |
|
||||
| |
|
||||
| RGBController for AMD Wraith Prism |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 25 Dec 2019 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "RGBController.h"
|
||||
#include "AMDWraithPrismController.h"
|
||||
|
||||
class RGBController_AMDWraithPrism : public RGBController
|
||||
{
|
||||
public:
|
||||
RGBController_AMDWraithPrism(AMDWraithPrismController* controller_ptr);
|
||||
~RGBController_AMDWraithPrism();
|
||||
|
||||
void SetupZones();
|
||||
|
||||
void ResizeZone(int zone, int new_size);
|
||||
|
||||
void DeviceUpdateLEDs();
|
||||
void UpdateZoneLEDs(int zone);
|
||||
void UpdateSingleLED(int led);
|
||||
|
||||
void DeviceUpdateMode();
|
||||
|
||||
private:
|
||||
AMDWraithPrismController* controller;
|
||||
};
|
||||
@@ -0,0 +1,216 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AOCKeyboardController.cpp |
|
||||
| |
|
||||
| Driver for AOC keyboard |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 10 May 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include <chrono>
|
||||
#include <cstring>
|
||||
#include <thread>
|
||||
#include "AOCKeyboardController.h"
|
||||
#include "StringUtils.h"
|
||||
|
||||
using namespace std::chrono_literals;
|
||||
|
||||
AOCKeyboardController::AOCKeyboardController(hid_device* dev_handle, const char* path, std::string dev_name)
|
||||
{
|
||||
dev = dev_handle;
|
||||
location = path;
|
||||
name = dev_name;
|
||||
}
|
||||
|
||||
AOCKeyboardController::~AOCKeyboardController()
|
||||
{
|
||||
hid_close(dev);
|
||||
}
|
||||
|
||||
std::string AOCKeyboardController::GetDeviceLocation()
|
||||
{
|
||||
return("HID " + location);
|
||||
}
|
||||
|
||||
std::string AOCKeyboardController::GetDeviceName()
|
||||
{
|
||||
return(name);
|
||||
}
|
||||
|
||||
std::string AOCKeyboardController::GetSerialString()
|
||||
{
|
||||
wchar_t serial_string[128];
|
||||
int ret = hid_get_serial_number_string(dev, serial_string, 128);
|
||||
|
||||
if(ret != 0)
|
||||
{
|
||||
return("");
|
||||
}
|
||||
|
||||
return(StringUtils::wstring_to_string(serial_string));
|
||||
}
|
||||
|
||||
void AOCKeyboardController::SetLightingConfig
|
||||
(
|
||||
unsigned char mode,
|
||||
unsigned char random,
|
||||
unsigned char brightness,
|
||||
unsigned char speed,
|
||||
unsigned char direction,
|
||||
RGBColor* color_data
|
||||
)
|
||||
{
|
||||
SendStartPacket();
|
||||
std::this_thread::sleep_for(5ms);
|
||||
|
||||
SendLightingConfigPacket(mode, random, brightness, speed, direction, color_data);
|
||||
std::this_thread::sleep_for(5ms);
|
||||
|
||||
SendEndPacket();
|
||||
std::this_thread::sleep_for(10ms);
|
||||
}
|
||||
|
||||
void AOCKeyboardController::SetCustom
|
||||
(
|
||||
RGBColor* color_data
|
||||
)
|
||||
{
|
||||
SendStartPacket();
|
||||
std::this_thread::sleep_for(5ms);
|
||||
|
||||
SendCustomPacket(color_data);
|
||||
std::this_thread::sleep_for(5ms);
|
||||
|
||||
SendEndPacket();
|
||||
std::this_thread::sleep_for(5ms);
|
||||
}
|
||||
|
||||
/*-------------------------------------------------------------------------------------------------*\
|
||||
| Private packet sending functions. |
|
||||
\*-------------------------------------------------------------------------------------------------*/
|
||||
|
||||
void AOCKeyboardController::SendStartPacket()
|
||||
{
|
||||
unsigned char buf[64];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(buf, 0x00, sizeof(buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up start packet |
|
||||
\*-----------------------------------------------------*/
|
||||
buf[0x00] = 0x09;
|
||||
buf[0x01] = 0x21;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_write(dev, buf, sizeof(buf));
|
||||
}
|
||||
|
||||
void AOCKeyboardController::SendEndPacket()
|
||||
{
|
||||
unsigned char buf[64];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(buf, 0x00, sizeof(buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up end packet |
|
||||
\*-----------------------------------------------------*/
|
||||
buf[0x00] = 0x09;
|
||||
buf[0x01] = 0x22;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_write(dev, buf, sizeof(buf));
|
||||
}
|
||||
|
||||
void AOCKeyboardController::SendCustomPacket
|
||||
(
|
||||
RGBColor* color_data
|
||||
)
|
||||
{
|
||||
unsigned char buf[361];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(buf, 0x00, sizeof(buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up custom lighting packet |
|
||||
\*-----------------------------------------------------*/
|
||||
buf[0x00] = 0x20;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Copy in color data |
|
||||
\*-----------------------------------------------------*/
|
||||
for(unsigned int color_idx = 0; color_idx < 120; color_idx++)
|
||||
{
|
||||
buf[color_idx + 1] = RGBGetRValue(color_data[color_idx]);
|
||||
buf[color_idx + 121] = RGBGetGValue(color_data[color_idx]);
|
||||
buf[color_idx + 241] = RGBGetBValue(color_data[color_idx]);
|
||||
}
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_send_feature_report(dev, buf, sizeof(buf));
|
||||
}
|
||||
|
||||
void AOCKeyboardController::SendLightingConfigPacket
|
||||
(
|
||||
unsigned char mode,
|
||||
unsigned char random,
|
||||
unsigned char brightness,
|
||||
unsigned char speed,
|
||||
unsigned char direction,
|
||||
RGBColor* color_data
|
||||
)
|
||||
{
|
||||
unsigned char buf[117];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(buf, 0x00, sizeof(buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up lighting configuration packet |
|
||||
\*-----------------------------------------------------*/
|
||||
buf[0x00] = 0x14;
|
||||
buf[0x01] = 0x01;
|
||||
|
||||
buf[0x06] = mode;
|
||||
|
||||
buf[0x07 + (9 * mode) + 0] = RGBGetRValue(color_data[0]);
|
||||
buf[0x07 + (9 * mode) + 1] = RGBGetGValue(color_data[0]);
|
||||
buf[0x07 + (9 * mode) + 2] = RGBGetBValue(color_data[0]);
|
||||
buf[0x07 + (9 * mode) + 3] = random;
|
||||
buf[0x07 + (9 * mode) + 4] = direction;
|
||||
buf[0x07 + (9 * mode) + 5] = speed;
|
||||
buf[0x07 + (9 * mode) + 6] = brightness;
|
||||
|
||||
unsigned short checksum = 0x4A9E;
|
||||
|
||||
for(unsigned int buf_idx = 0; buf_idx < 115; buf_idx++)
|
||||
{
|
||||
checksum += buf[buf_idx];
|
||||
}
|
||||
|
||||
buf[115] = checksum & 0xFF;
|
||||
buf[116] = checksum >> 8;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_send_feature_report(dev, buf, 117);
|
||||
}
|
||||
@@ -0,0 +1,111 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AOCKeyboardController.h |
|
||||
| |
|
||||
| Driver for AOC keyboard |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 10 May 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <string>
|
||||
#include <hidapi.h>
|
||||
#include "RGBController.h"
|
||||
|
||||
/*-----------------------------------------*\
|
||||
| AOC Keyboard Modes |
|
||||
\*-----------------------------------------*/
|
||||
enum
|
||||
{
|
||||
AOC_KEYBOARD_MODE_STATIC = 0x00, /* Static mode */
|
||||
AOC_KEYBOARD_MODE_BREATHING = 0x01, /* Breathing mode */
|
||||
AOC_KEYBOARD_MODE_REACT = 0x02, /* React mode */
|
||||
AOC_KEYBOARD_MODE_RIPPLE = 0x04, /* Ripple mode */
|
||||
AOC_KEYBOARD_MODE_RADAR = 0x05, /* Radar mode */
|
||||
AOC_KEYBOARD_MODE_FIREWORKS = 0x06, /* Fireworks mode */
|
||||
AOC_KEYBOARD_MODE_BLINK = 0x07, /* Blink mode */
|
||||
AOC_KEYBOARD_MODE_WAVE = 0x08, /* Wave mode */
|
||||
AOC_KEYBOARD_MODE_CUSTOM = 0x09, /* Custom mode */
|
||||
AOC_KEYBOARD_MODE_CONCENTRIC_CIRCLES = 0x0A, /* Concentric Circles mode */
|
||||
AOC_KEYBOARD_MODE_W_WAVE = 0x0B, /* W Wave mode */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
AOC_KEYBOARD_SPEED_SLOW = 0x03, /* Slowest speed */
|
||||
AOC_KEYBOARD_SPEED_MEDIUM = 0x02, /* Medium speed */
|
||||
AOC_KEYBOARD_SPEED_FAST = 0x01, /* Fastest speed */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
AOC_KEYBOARD_BRIGHTNESS_OFF = 0x00, /* Lowest brightness (off) */
|
||||
AOC_KEYBOARD_BRIGHTNESS_LOW = 0x01, /* Low brightness */
|
||||
AOC_KEYBOARD_BRIGHTNESS_MEDIUM = 0x02, /* Medium brightness */
|
||||
AOC_KEYBOARD_BRIGHTNESS_HIGH = 0x03, /* Highest brightness */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
AOC_KEYBOARD_SINGLE_COLOR = 0x00, /* Single color mode */
|
||||
AOC_KEYBOARD_RANDOM = 0x01, /* Random color mode */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
AOC_KEYBOARD_DIRECTION_CLOCKWISE = 0x00, /* Clockwise direction */
|
||||
AOC_KEYBOARD_DIRECTION_COUNTERCLOCKWISE = 0x01, /* Counter-clockwise direction */
|
||||
};
|
||||
|
||||
|
||||
class AOCKeyboardController
|
||||
{
|
||||
public:
|
||||
AOCKeyboardController(hid_device* dev_handle, const char* path, std::string dev_name);
|
||||
~AOCKeyboardController();
|
||||
|
||||
std::string GetDeviceLocation();
|
||||
std::string GetDeviceName();
|
||||
std::string GetSerialString();
|
||||
|
||||
void SetLightingConfig
|
||||
(
|
||||
unsigned char mode,
|
||||
unsigned char random,
|
||||
unsigned char brightness,
|
||||
unsigned char speed,
|
||||
unsigned char direction,
|
||||
RGBColor* color_data
|
||||
);
|
||||
|
||||
void SetCustom
|
||||
(
|
||||
RGBColor* color_data
|
||||
);
|
||||
|
||||
private:
|
||||
hid_device* dev;
|
||||
std::string location;
|
||||
std::string name;
|
||||
|
||||
void SendStartPacket();
|
||||
void SendEndPacket();
|
||||
|
||||
void SendCustomPacket
|
||||
(
|
||||
RGBColor* color_data
|
||||
);
|
||||
|
||||
void SendLightingConfigPacket
|
||||
(
|
||||
unsigned char mode,
|
||||
unsigned char random,
|
||||
unsigned char brightness,
|
||||
unsigned char speed,
|
||||
unsigned char direction,
|
||||
RGBColor* color_data
|
||||
);
|
||||
};
|
||||
@@ -0,0 +1,45 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AOCKeyboardControllerDetect.cpp |
|
||||
| |
|
||||
| Detector for AOC keyboard |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 10 May 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "Detector.h"
|
||||
#include "AOCKeyboardController.h"
|
||||
#include "RGBController_AOCKeyboard.h"
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| AOC Keyboard IDs |
|
||||
\*-----------------------------------------------------*/
|
||||
#define AOC_VID 0x3938
|
||||
#define AOC_GK500_PID 0x1178
|
||||
#define AOC_GK500_PID_2 0x1229
|
||||
|
||||
/******************************************************************************************\
|
||||
* *
|
||||
* DetectAOCKeyboardControllers *
|
||||
* *
|
||||
* Tests the USB address to see if an AOC Keyboard controller exists there. *
|
||||
* *
|
||||
\******************************************************************************************/
|
||||
|
||||
void DetectAOCKeyboardControllers(hid_device_info* info, const std::string& name)
|
||||
{
|
||||
hid_device* dev = hid_open_path(info->path);
|
||||
|
||||
if(dev)
|
||||
{
|
||||
AOCKeyboardController* controller = new AOCKeyboardController(dev, info->path, name);
|
||||
RGBController_AOCKeyboard* rgb_controller = new RGBController_AOCKeyboard(controller);
|
||||
|
||||
ResourceManager::get()->RegisterRGBController(rgb_controller);
|
||||
}
|
||||
}
|
||||
|
||||
REGISTER_HID_DETECTOR_PU("AOC GK500", DetectAOCKeyboardControllers, AOC_VID, AOC_GK500_PID, 0xFF19, 0xFF19);
|
||||
REGISTER_HID_DETECTOR_PU("AOC GK500", DetectAOCKeyboardControllers, AOC_VID, AOC_GK500_PID_2, 0xFF19, 0xFF19);
|
||||
@@ -0,0 +1,371 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_AOCKeyboard.cpp |
|
||||
| |
|
||||
| RGBController for AOC keyboard |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 10 May 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "RGBController_AOCKeyboard.h"
|
||||
#include "KeyboardLayoutManager.h"
|
||||
|
||||
/**--------------------------------------------------------------------*\
|
||||
@name AOC Keyboard
|
||||
@category Keyboard
|
||||
@type USB
|
||||
@save :x:
|
||||
@direct :white_check_mark:
|
||||
@effects :white_check_mark:
|
||||
@detectors DetectAOCKeyboardControllers
|
||||
@comment
|
||||
\*---------------------------------------------------------------------*/
|
||||
|
||||
/*---------------------------------------------------------------------*\
|
||||
| AOC Keyboard KLM Layout |
|
||||
\*---------------------------------------------------------------------*/
|
||||
layout_values aoc_keyboard_offset_values =
|
||||
{
|
||||
{
|
||||
/* ESC F1 F2 F3 F4 F5 F6 F7 F8 F9 F10 F11 F12 PRSC SCLK PSBK */
|
||||
90, 92, 77, 63, 79, 94, 81, 96, 82, 83, 98, 40, 55, 85, 100, 104,
|
||||
/* BKTK 1 2 3 4 5 6 7 8 9 0 - = BSPC INS HOME PGUP NLCK NP/ NP* NP- */
|
||||
75, 76, 91, 62, 48, 64, 50, 65, 66, 67, 97, 68, 84, 70, 59, 74, 89, 58, 73, 88, 103,
|
||||
/* TAB Q W E R T Y U I O P [ ] \ DEL END PGDN NP7 NP8 NP9 NP+ */
|
||||
60, 61, 47, 78, 33, 49, 35, 80, 51, 52, 53, 69, 99, 25, 44, 29, 14, 43, 28, 13, 102,
|
||||
/* CPLK A S D F G H J K L ; " # ENTR NP4 NP5 NP6 */
|
||||
45, 46, 32, 93, 18, 34, 20, 95, 36, 37, 38, 54, 0, 10, 57, 72, 87,
|
||||
/* LSFT \ Z X C V B N M , . / RSFT ARWU NP1 NP2 NP3 NPEN */
|
||||
30, 0, 31, 17, 2, 3, 19, 5, 6, 21, 22, 23, 39, 11, 42, 27, 12, 101,
|
||||
/* LCTL LWIN LALT SPC RALT RFNC RMNU RCTL ARWL ARWD ARWR NP0 NP. */
|
||||
15, 0, 1, 4, 7, 8, 24, 9, 26, 41, 56, 71, 86
|
||||
},
|
||||
{
|
||||
/* Add more regional layout fixes here */
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
RGBController_AOCKeyboard::RGBController_AOCKeyboard(AOCKeyboardController* controller_ptr)
|
||||
{
|
||||
controller = controller_ptr;
|
||||
|
||||
name = controller->GetDeviceName();
|
||||
vendor = "AOC";
|
||||
type = DEVICE_TYPE_KEYBOARD;
|
||||
description = "AOC Keyboard Device";
|
||||
location = controller->GetDeviceLocation();
|
||||
serial = controller->GetSerialString();
|
||||
|
||||
mode Static;
|
||||
Static.name = "Static";
|
||||
Static.value = AOC_KEYBOARD_MODE_STATIC;
|
||||
Static.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
|
||||
Static.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Static.brightness_min = AOC_KEYBOARD_BRIGHTNESS_OFF;
|
||||
Static.brightness_max = AOC_KEYBOARD_BRIGHTNESS_HIGH;
|
||||
Static.brightness = AOC_KEYBOARD_BRIGHTNESS_HIGH;
|
||||
Static.colors_min = 1;
|
||||
Static.colors_max = 1;
|
||||
Static.colors.resize(1);
|
||||
modes.push_back(Static);
|
||||
|
||||
mode SpectrumCycle;
|
||||
SpectrumCycle.name = "Spectrum Cycle";
|
||||
SpectrumCycle.value = AOC_KEYBOARD_MODE_STATIC;
|
||||
SpectrumCycle.flags = MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_SPEED;
|
||||
SpectrumCycle.color_mode = MODE_COLORS_RANDOM;
|
||||
SpectrumCycle.brightness_min = AOC_KEYBOARD_BRIGHTNESS_OFF;
|
||||
SpectrumCycle.brightness_max = AOC_KEYBOARD_BRIGHTNESS_HIGH;
|
||||
SpectrumCycle.brightness = AOC_KEYBOARD_BRIGHTNESS_HIGH;
|
||||
SpectrumCycle.speed_min = AOC_KEYBOARD_SPEED_SLOW;
|
||||
SpectrumCycle.speed_max = AOC_KEYBOARD_SPEED_FAST;
|
||||
SpectrumCycle.speed = AOC_KEYBOARD_SPEED_MEDIUM;
|
||||
modes.push_back(SpectrumCycle);
|
||||
|
||||
mode Breathing;
|
||||
Breathing.name = "Breathing";
|
||||
Breathing.value = AOC_KEYBOARD_MODE_BREATHING;
|
||||
Breathing.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_SPEED;
|
||||
Breathing.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Breathing.brightness_min = AOC_KEYBOARD_BRIGHTNESS_OFF;
|
||||
Breathing.brightness_max = AOC_KEYBOARD_BRIGHTNESS_HIGH;
|
||||
Breathing.brightness = AOC_KEYBOARD_BRIGHTNESS_HIGH;
|
||||
Breathing.speed_min = AOC_KEYBOARD_SPEED_SLOW;
|
||||
Breathing.speed_max = AOC_KEYBOARD_SPEED_FAST;
|
||||
Breathing.speed = AOC_KEYBOARD_SPEED_MEDIUM;
|
||||
Breathing.colors_min = 1;
|
||||
Breathing.colors_max = 1;
|
||||
Breathing.colors.resize(1);
|
||||
modes.push_back(Breathing);
|
||||
|
||||
mode React;
|
||||
React.name = "React";
|
||||
React.value = AOC_KEYBOARD_MODE_REACT;
|
||||
React.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_SPEED;
|
||||
React.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
React.brightness_min = AOC_KEYBOARD_BRIGHTNESS_OFF;
|
||||
React.brightness_max = AOC_KEYBOARD_BRIGHTNESS_HIGH;
|
||||
React.brightness = AOC_KEYBOARD_BRIGHTNESS_HIGH;
|
||||
React.speed_min = AOC_KEYBOARD_SPEED_SLOW;
|
||||
React.speed_max = AOC_KEYBOARD_SPEED_FAST;
|
||||
React.speed = AOC_KEYBOARD_SPEED_MEDIUM;
|
||||
React.colors_min = 1;
|
||||
React.colors_max = 1;
|
||||
React.colors.resize(1);
|
||||
modes.push_back(React);
|
||||
|
||||
mode Ripple;
|
||||
Ripple.name = "Ripple";
|
||||
Ripple.value = AOC_KEYBOARD_MODE_RIPPLE;
|
||||
Ripple.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_SPEED;
|
||||
Ripple.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Ripple.brightness_min = AOC_KEYBOARD_BRIGHTNESS_OFF;
|
||||
Ripple.brightness_max = AOC_KEYBOARD_BRIGHTNESS_HIGH;
|
||||
Ripple.brightness = AOC_KEYBOARD_BRIGHTNESS_HIGH;
|
||||
Ripple.speed_min = AOC_KEYBOARD_SPEED_SLOW;
|
||||
Ripple.speed_max = AOC_KEYBOARD_SPEED_FAST;
|
||||
Ripple.speed = AOC_KEYBOARD_SPEED_MEDIUM;
|
||||
Ripple.colors_min = 1;
|
||||
Ripple.colors_max = 1;
|
||||
Ripple.colors.resize(1);
|
||||
modes.push_back(Ripple);
|
||||
|
||||
mode Radar;
|
||||
Radar.name = "Radar";
|
||||
Radar.value = AOC_KEYBOARD_MODE_RADAR;
|
||||
Radar.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_DIRECTION_LR;
|
||||
Radar.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Radar.brightness_min = AOC_KEYBOARD_BRIGHTNESS_OFF;
|
||||
Radar.brightness_max = AOC_KEYBOARD_BRIGHTNESS_HIGH;
|
||||
Radar.brightness = AOC_KEYBOARD_BRIGHTNESS_HIGH;
|
||||
Radar.speed_min = AOC_KEYBOARD_SPEED_SLOW;
|
||||
Radar.speed_max = AOC_KEYBOARD_SPEED_FAST;
|
||||
Radar.speed = AOC_KEYBOARD_SPEED_MEDIUM;
|
||||
Radar.colors_min = 1;
|
||||
Radar.colors_max = 1;
|
||||
Radar.colors.resize(1);
|
||||
modes.push_back(Radar);
|
||||
|
||||
mode Fireworks;
|
||||
Fireworks.name = "Fireworks";
|
||||
Fireworks.value = AOC_KEYBOARD_MODE_FIREWORKS;
|
||||
Fireworks.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_SPEED;
|
||||
Fireworks.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Fireworks.brightness_min = AOC_KEYBOARD_BRIGHTNESS_OFF;
|
||||
Fireworks.brightness_max = AOC_KEYBOARD_BRIGHTNESS_HIGH;
|
||||
Fireworks.brightness = AOC_KEYBOARD_BRIGHTNESS_HIGH;
|
||||
Fireworks.speed_min = AOC_KEYBOARD_SPEED_SLOW;
|
||||
Fireworks.speed_max = AOC_KEYBOARD_SPEED_FAST;
|
||||
Fireworks.speed = AOC_KEYBOARD_SPEED_MEDIUM;
|
||||
Fireworks.colors_min = 1;
|
||||
Fireworks.colors_max = 1;
|
||||
Fireworks.colors.resize(1);
|
||||
modes.push_back(Fireworks);
|
||||
|
||||
mode Blink;
|
||||
Blink.name = "Flashing";
|
||||
Blink.value = AOC_KEYBOARD_MODE_BLINK;
|
||||
Blink.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_SPEED;
|
||||
Blink.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Blink.brightness_min = AOC_KEYBOARD_BRIGHTNESS_OFF;
|
||||
Blink.brightness_max = AOC_KEYBOARD_BRIGHTNESS_HIGH;
|
||||
Blink.brightness = AOC_KEYBOARD_BRIGHTNESS_HIGH;
|
||||
Blink.speed_min = AOC_KEYBOARD_SPEED_SLOW;
|
||||
Blink.speed_max = AOC_KEYBOARD_SPEED_FAST;
|
||||
Blink.speed = AOC_KEYBOARD_SPEED_MEDIUM;
|
||||
Blink.colors_min = 1;
|
||||
Blink.colors_max = 1;
|
||||
Blink.colors.resize(1);
|
||||
modes.push_back(Blink);
|
||||
|
||||
mode Wave;
|
||||
Wave.name = "Wave";
|
||||
Wave.value = AOC_KEYBOARD_MODE_WAVE;
|
||||
Wave.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_DIRECTION_LR;
|
||||
Wave.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Wave.brightness_min = AOC_KEYBOARD_BRIGHTNESS_OFF;
|
||||
Wave.brightness_max = AOC_KEYBOARD_BRIGHTNESS_HIGH;
|
||||
Wave.brightness = AOC_KEYBOARD_BRIGHTNESS_HIGH;
|
||||
Wave.speed_min = AOC_KEYBOARD_SPEED_SLOW;
|
||||
Wave.speed_max = AOC_KEYBOARD_SPEED_FAST;
|
||||
Wave.speed = AOC_KEYBOARD_SPEED_MEDIUM;
|
||||
Wave.colors_min = 1;
|
||||
Wave.colors_max = 1;
|
||||
Wave.colors.resize(1);
|
||||
modes.push_back(Wave);
|
||||
|
||||
mode RainbowWave;
|
||||
RainbowWave.name = "Rainbow Wave";
|
||||
RainbowWave.value = AOC_KEYBOARD_MODE_WAVE;
|
||||
RainbowWave.flags = MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_DIRECTION_LR;
|
||||
RainbowWave.color_mode = MODE_COLORS_RANDOM;
|
||||
RainbowWave.brightness_min = AOC_KEYBOARD_BRIGHTNESS_OFF;
|
||||
RainbowWave.brightness_max = AOC_KEYBOARD_BRIGHTNESS_HIGH;
|
||||
RainbowWave.brightness = AOC_KEYBOARD_BRIGHTNESS_HIGH;
|
||||
RainbowWave.speed_min = AOC_KEYBOARD_SPEED_SLOW;
|
||||
RainbowWave.speed_max = AOC_KEYBOARD_SPEED_FAST;
|
||||
RainbowWave.speed = AOC_KEYBOARD_SPEED_MEDIUM;
|
||||
modes.push_back(RainbowWave);
|
||||
|
||||
mode ConcentricCircles;
|
||||
ConcentricCircles.name = "Concentric Circles";
|
||||
ConcentricCircles.value = AOC_KEYBOARD_MODE_CONCENTRIC_CIRCLES;
|
||||
ConcentricCircles.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_DIRECTION_LR;
|
||||
ConcentricCircles.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
ConcentricCircles.brightness_min= AOC_KEYBOARD_BRIGHTNESS_OFF;
|
||||
ConcentricCircles.brightness_max= AOC_KEYBOARD_BRIGHTNESS_HIGH;
|
||||
ConcentricCircles.brightness = AOC_KEYBOARD_BRIGHTNESS_HIGH;
|
||||
ConcentricCircles.speed_min = AOC_KEYBOARD_SPEED_SLOW;
|
||||
ConcentricCircles.speed_max = AOC_KEYBOARD_SPEED_FAST;
|
||||
ConcentricCircles.speed = AOC_KEYBOARD_SPEED_MEDIUM;
|
||||
ConcentricCircles.colors_min = 1;
|
||||
ConcentricCircles.colors_max = 1;
|
||||
ConcentricCircles.colors.resize(1);
|
||||
modes.push_back(ConcentricCircles);
|
||||
|
||||
mode WWave;
|
||||
WWave.name = "W Wave";
|
||||
WWave.value = AOC_KEYBOARD_MODE_W_WAVE;
|
||||
WWave.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_SPEED;
|
||||
WWave.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
WWave.brightness_min = AOC_KEYBOARD_BRIGHTNESS_OFF;
|
||||
WWave.brightness_max = AOC_KEYBOARD_BRIGHTNESS_HIGH;
|
||||
WWave.brightness = AOC_KEYBOARD_BRIGHTNESS_HIGH;
|
||||
WWave.speed_min = AOC_KEYBOARD_SPEED_SLOW;
|
||||
WWave.speed_max = AOC_KEYBOARD_SPEED_FAST;
|
||||
WWave.speed = AOC_KEYBOARD_SPEED_MEDIUM;
|
||||
WWave.colors_min = 1;
|
||||
WWave.colors_max = 1;
|
||||
WWave.colors.resize(1);
|
||||
modes.push_back(WWave);
|
||||
|
||||
mode Direct;
|
||||
Direct.name = "Direct";
|
||||
Direct.value = AOC_KEYBOARD_MODE_CUSTOM;
|
||||
Direct.flags = MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
|
||||
Direct.color_mode = MODE_COLORS_PER_LED;
|
||||
Direct.brightness_min = AOC_KEYBOARD_BRIGHTNESS_OFF;
|
||||
Direct.brightness_max = AOC_KEYBOARD_BRIGHTNESS_HIGH;
|
||||
Direct.brightness = AOC_KEYBOARD_BRIGHTNESS_HIGH;
|
||||
modes.push_back(Direct);
|
||||
|
||||
SetupZones();
|
||||
};
|
||||
|
||||
RGBController_AOCKeyboard::~RGBController_AOCKeyboard()
|
||||
{
|
||||
delete controller;
|
||||
}
|
||||
|
||||
void RGBController_AOCKeyboard::SetupZones()
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| Create the keyboard zone usiung Keyboard Layout Manager |
|
||||
\*---------------------------------------------------------*/
|
||||
zone new_zone;
|
||||
new_zone.name = ZONE_EN_KEYBOARD;
|
||||
new_zone.type = ZONE_TYPE_MATRIX;
|
||||
|
||||
KeyboardLayoutManager new_kb(KEYBOARD_LAYOUT_ANSI_QWERTY, KEYBOARD_SIZE_FULL, aoc_keyboard_offset_values);
|
||||
|
||||
matrix_map_type * new_map = new matrix_map_type;
|
||||
new_zone.matrix_map = new_map;
|
||||
new_zone.matrix_map->height = new_kb.GetRowCount();
|
||||
new_zone.matrix_map->width = new_kb.GetColumnCount();
|
||||
|
||||
new_zone.matrix_map->map = new unsigned int[new_map->height * new_map->width];
|
||||
new_zone.leds_count = new_kb.GetKeyCount();
|
||||
new_zone.leds_min = new_zone.leds_count;
|
||||
new_zone.leds_max = new_zone.leds_count;
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Matrix map still uses declared zone rows and columns |
|
||||
| as the packet structure depends on the matrix map |
|
||||
\*---------------------------------------------------------*/
|
||||
new_kb.GetKeyMap(new_map->map, KEYBOARD_MAP_FILL_TYPE_COUNT, new_map->height, new_map->width);
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Create LEDs for the Matrix zone |
|
||||
| Place keys in the layout to populate the matrix |
|
||||
\*---------------------------------------------------------*/
|
||||
for(unsigned int led_idx = 0; led_idx < new_zone.leds_count; led_idx++)
|
||||
{
|
||||
led new_led;
|
||||
|
||||
new_led.name = new_kb.GetKeyNameAt(led_idx);
|
||||
new_led.value = new_kb.GetKeyValueAt(led_idx);
|
||||
leds.push_back(new_led);
|
||||
}
|
||||
|
||||
zones.push_back(new_zone);
|
||||
|
||||
SetupColors();
|
||||
}
|
||||
|
||||
void RGBController_AOCKeyboard::ResizeZone(int /*zone*/, int /*new_size*/)
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| This device does not support resizing zones |
|
||||
\*---------------------------------------------------------*/
|
||||
}
|
||||
|
||||
void RGBController_AOCKeyboard::DeviceUpdateLEDs()
|
||||
{
|
||||
if(modes[active_mode].value == AOC_KEYBOARD_MODE_CUSTOM)
|
||||
{
|
||||
RGBColor color_buf[120];
|
||||
|
||||
for(unsigned int led_idx = 0; led_idx < leds.size(); led_idx++)
|
||||
{
|
||||
color_buf[leds[led_idx].value] = colors[led_idx];
|
||||
}
|
||||
|
||||
controller->SetCustom(&color_buf[0]);
|
||||
}
|
||||
else
|
||||
{
|
||||
DeviceUpdateMode();
|
||||
}
|
||||
}
|
||||
|
||||
void RGBController_AOCKeyboard::UpdateZoneLEDs(int /*zone*/)
|
||||
{
|
||||
DeviceUpdateLEDs();
|
||||
}
|
||||
|
||||
void RGBController_AOCKeyboard::UpdateSingleLED(int /*led*/)
|
||||
{
|
||||
DeviceUpdateLEDs();
|
||||
}
|
||||
|
||||
void RGBController_AOCKeyboard::DeviceUpdateMode()
|
||||
{
|
||||
unsigned char aoc_direction = AOC_KEYBOARD_DIRECTION_CLOCKWISE;
|
||||
unsigned char aoc_random = AOC_KEYBOARD_SINGLE_COLOR;
|
||||
RGBColor* aoc_colors = &colors[0];
|
||||
|
||||
if(modes[active_mode].direction == MODE_DIRECTION_LEFT)
|
||||
{
|
||||
aoc_direction = AOC_KEYBOARD_DIRECTION_COUNTERCLOCKWISE;
|
||||
}
|
||||
|
||||
if(modes[active_mode].color_mode == MODE_COLORS_RANDOM)
|
||||
{
|
||||
aoc_random = AOC_KEYBOARD_RANDOM;
|
||||
}
|
||||
|
||||
if(modes[active_mode].color_mode == MODE_COLORS_MODE_SPECIFIC)
|
||||
{
|
||||
aoc_colors = &modes[active_mode].colors[0];
|
||||
}
|
||||
|
||||
controller->SetLightingConfig(modes[active_mode].value,
|
||||
aoc_random,
|
||||
modes[active_mode].brightness,
|
||||
modes[active_mode].speed,
|
||||
aoc_direction,
|
||||
aoc_colors);
|
||||
}
|
||||
@@ -0,0 +1,35 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_AOCKeyboard.h |
|
||||
| |
|
||||
| RGBController for AOC keyboard |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 10 May 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "RGBController.h"
|
||||
#include "AOCKeyboardController.h"
|
||||
|
||||
class RGBController_AOCKeyboard : public RGBController
|
||||
{
|
||||
public:
|
||||
RGBController_AOCKeyboard(AOCKeyboardController* controller_ptr);
|
||||
~RGBController_AOCKeyboard();
|
||||
|
||||
void SetupZones();
|
||||
|
||||
void ResizeZone(int zone, int new_size);
|
||||
|
||||
void DeviceUpdateLEDs();
|
||||
void UpdateZoneLEDs(int zone);
|
||||
void UpdateSingleLED(int led);
|
||||
|
||||
void DeviceUpdateMode();
|
||||
|
||||
private:
|
||||
AOCKeyboardController* controller;
|
||||
};
|
||||
@@ -0,0 +1,136 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AOCMouseController.cpp |
|
||||
| |
|
||||
| Driver for AOC mouse |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 20 Apr 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include <cstring>
|
||||
#include "AOCMouseController.h"
|
||||
#include "StringUtils.h"
|
||||
|
||||
AOCMouseController::AOCMouseController(hid_device* dev_handle, const char* path, std::string dev_name)
|
||||
{
|
||||
dev = dev_handle;
|
||||
location = path;
|
||||
name = dev_name;
|
||||
}
|
||||
|
||||
AOCMouseController::~AOCMouseController()
|
||||
{
|
||||
hid_close(dev);
|
||||
}
|
||||
|
||||
std::string AOCMouseController::GetDeviceLocation()
|
||||
{
|
||||
return("HID " + location);
|
||||
}
|
||||
|
||||
std::string AOCMouseController::GetDeviceName()
|
||||
{
|
||||
return(name);
|
||||
}
|
||||
|
||||
std::string AOCMouseController::GetSerialString()
|
||||
{
|
||||
wchar_t serial_string[128];
|
||||
int ret = hid_get_serial_number_string(dev, serial_string, 128);
|
||||
|
||||
if(ret != 0)
|
||||
{
|
||||
return("");
|
||||
}
|
||||
|
||||
return(StringUtils::wstring_to_string(serial_string));
|
||||
}
|
||||
|
||||
/*-------------------------------------------------------------------------------------------------*\
|
||||
| Private packet sending functions. |
|
||||
\*-------------------------------------------------------------------------------------------------*/
|
||||
|
||||
void AOCMouseController::SendDirect
|
||||
(
|
||||
RGBColor* color_data
|
||||
)
|
||||
{
|
||||
SendPacket(AOC_MOUSE_MODE_STATIC_SINGLE_COLOR,
|
||||
AOC_MOUSE_BRIGHTNESS_HIGH,
|
||||
AOC_MOUSE_SPEED_MEDIUM,
|
||||
AOC_MOUSE_DIRECTION_CLOCKWISE,
|
||||
color_data);
|
||||
}
|
||||
|
||||
void AOCMouseController::SendPacket
|
||||
(
|
||||
unsigned char mode,
|
||||
unsigned char brightness,
|
||||
unsigned char speed,
|
||||
unsigned char direction,
|
||||
RGBColor* color_data
|
||||
)
|
||||
{
|
||||
unsigned char buf[60];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(buf, 0x00, sizeof(buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up packet |
|
||||
\*-----------------------------------------------------*/
|
||||
buf[0x00] = 0x20;
|
||||
buf[0x01] = 0x03;
|
||||
buf[0x02] = 0x01;
|
||||
buf[0x03] = mode;
|
||||
buf[0x04] = speed;
|
||||
buf[0x05] = brightness;
|
||||
buf[0x06] = direction;
|
||||
buf[0x07] = 0x01;
|
||||
buf[0x08] = 0x02;
|
||||
buf[0x09] = 0xFF;
|
||||
buf[0x0D] = 0x01;
|
||||
buf[0x0E] = 0x03;
|
||||
buf[0x0F] = 0xFF;
|
||||
buf[0x10] = 0x7F;
|
||||
buf[0x13] = 0x01;
|
||||
buf[0x14] = 0x04;
|
||||
buf[0x17] = 0xFF;
|
||||
buf[0x19] = 0x01;
|
||||
buf[0x1A] = 0x05;
|
||||
buf[0x1C] = 0xFF;
|
||||
buf[0x1F] = 0x01;
|
||||
buf[0x20] = 0x06;
|
||||
buf[0x21] = 0xFF;
|
||||
buf[0x23] = 0xFF;
|
||||
buf[0x25] = 0x01;
|
||||
buf[0x26] = 0x07;
|
||||
buf[0x27] = 0xFF;
|
||||
buf[0x28] = 0xFF;
|
||||
buf[0x2C] = 0x0A;
|
||||
buf[0x2D] = 0x0A;
|
||||
buf[0x30] = 0x14;
|
||||
buf[0x31] = 0x08;
|
||||
buf[0x3A] = 0x32;
|
||||
buf[0x3B] = 0x32;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Copy in color |
|
||||
\*-----------------------------------------------------*/
|
||||
buf[0x33] = RGBGetRValue(color_data[0]);
|
||||
buf[0x34] = RGBGetGValue(color_data[0]);
|
||||
buf[0x35] = RGBGetBValue(color_data[0]);
|
||||
|
||||
buf[0x36] = RGBGetRValue(color_data[1]);
|
||||
buf[0x37] = RGBGetGValue(color_data[1]);
|
||||
buf[0x38] = RGBGetBValue(color_data[1]);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_send_feature_report(dev, buf, 60);
|
||||
}
|
||||
@@ -0,0 +1,84 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AOCMouseController.h |
|
||||
| |
|
||||
| Driver for AOC mouse |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 20 Apr 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <string>
|
||||
#include <hidapi.h>
|
||||
#include "RGBController.h"
|
||||
|
||||
/*-----------------------------------------*\
|
||||
| AOC Mousemat Modes |
|
||||
| Note: The 0x80 bit is the random flag |
|
||||
\*-----------------------------------------*/
|
||||
enum
|
||||
{
|
||||
AOC_MOUSE_MODE_STATIC_SINGLE_COLOR = 0x00, /* Static single color mode */
|
||||
AOC_MOUSE_MODE_STATIC_RANDOM = 0x80, /* Static random color mode */
|
||||
AOC_MOUSE_MODE_BREATHING_SINGLE_COLOR = 0x01, /* Breathing single color mode */
|
||||
AOC_MOUSE_MODE_BREATHING_RANDOM = 0x81, /* Breathing random color mode */
|
||||
AOC_MOUSE_MODE_BLINK_SINGLE_COLOR = 0x02, /* Blink single color mode */
|
||||
AOC_MOUSE_MODE_BLINK_RANDOM = 0x82, /* Blink random color mode */
|
||||
AOC_MOUSE_MODE_WAVE_SINGLE_COLOR = 0x03, /* Wave single color mode */
|
||||
AOC_MOUSE_MODE_WAVE_RANDOM = 0x83, /* Wave random color mode */
|
||||
AOC_MOUSE_MODE_DPI = 0x04, /* DPI mode */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
AOC_MOUSE_SPEED_SLOW = 0x03, /* Slowest speed */
|
||||
AOC_MOUSE_SPEED_MEDIUM = 0x02, /* Medium speed */
|
||||
AOC_MOUSE_SPEED_FAST = 0x01, /* Fastest speed */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
AOC_MOUSE_BRIGHTNESS_OFF = 0x00, /* Lowest brightness (off) */
|
||||
AOC_MOUSE_BRIGHTNESS_LOW = 0x01, /* Low brightness */
|
||||
AOC_MOUSE_BRIGHTNESS_MEDIUM = 0x02, /* Medium brightness */
|
||||
AOC_MOUSE_BRIGHTNESS_HIGH = 0x03, /* Highest brightness */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
AOC_MOUSE_DIRECTION_CLOCKWISE = 0x00, /* Clockwise direction */
|
||||
AOC_MOUSE_DIRECTION_COUNTERCLOCKWISE = 0x01, /* Counter-clockwise direction */
|
||||
};
|
||||
|
||||
class AOCMouseController
|
||||
{
|
||||
public:
|
||||
AOCMouseController(hid_device* dev_handle, const char* path, std::string dev_name);
|
||||
~AOCMouseController();
|
||||
|
||||
std::string GetDeviceLocation();
|
||||
std::string GetDeviceName();
|
||||
std::string GetSerialString();
|
||||
|
||||
void SendDirect
|
||||
(
|
||||
RGBColor* color_data
|
||||
);
|
||||
|
||||
void SendPacket
|
||||
(
|
||||
unsigned char mode,
|
||||
unsigned char brightness,
|
||||
unsigned char speed,
|
||||
unsigned char direction,
|
||||
RGBColor* color_data
|
||||
);
|
||||
|
||||
private:
|
||||
hid_device* dev;
|
||||
std::string location;
|
||||
std::string name;
|
||||
};
|
||||
@@ -0,0 +1,43 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AOCMouseControllerDetect.cpp |
|
||||
| |
|
||||
| Detector for AOC mouse |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 20 Apr 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "Detector.h"
|
||||
#include "AOCMouseController.h"
|
||||
#include "RGBController_AOCMouse.h"
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| AOC Mouse IDs |
|
||||
\*-----------------------------------------------------*/
|
||||
#define AOC_VID 0x3938
|
||||
#define AOC_GM500_PID 0x1179
|
||||
|
||||
/******************************************************************************************\
|
||||
* *
|
||||
* DetectAOCMouseControllers *
|
||||
* *
|
||||
* Tests the USB address to see if an AOC Mouse controller exists there. *
|
||||
* *
|
||||
\******************************************************************************************/
|
||||
|
||||
void DetectAOCMouseControllers(hid_device_info* info, const std::string& name)
|
||||
{
|
||||
hid_device* dev = hid_open_path(info->path);
|
||||
|
||||
if(dev)
|
||||
{
|
||||
AOCMouseController* controller = new AOCMouseController(dev, info->path, name);
|
||||
RGBController_AOCMouse* rgb_controller = new RGBController_AOCMouse(controller);
|
||||
|
||||
ResourceManager::get()->RegisterRGBController(rgb_controller);
|
||||
}
|
||||
}
|
||||
|
||||
REGISTER_HID_DETECTOR_IPU("AOC GM500", DetectAOCMouseControllers, AOC_VID, AOC_GM500_PID, 1, 0xFF19, 0xFF19);
|
||||
@@ -0,0 +1,218 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_AOCMouse.cpp |
|
||||
| |
|
||||
| RGBController for AOC mouse |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 20 Apr 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "RGBController_AOCMouse.h"
|
||||
|
||||
/**------------------------------------------------------------------*\
|
||||
@name AOC Mouse
|
||||
@category Mouse
|
||||
@type USB
|
||||
@save :x:
|
||||
@direct :white_check_mark:
|
||||
@effects :white_check_mark:
|
||||
@detectors DetectAOCMouseControllers
|
||||
@comment
|
||||
\*-------------------------------------------------------------------*/
|
||||
|
||||
RGBController_AOCMouse::RGBController_AOCMouse(AOCMouseController* controller_ptr)
|
||||
{
|
||||
controller = controller_ptr;
|
||||
|
||||
name = controller->GetDeviceName();
|
||||
vendor = "AOC";
|
||||
type = DEVICE_TYPE_MOUSE;
|
||||
description = "AOC Mouse Device";
|
||||
location = controller->GetDeviceLocation();
|
||||
serial = controller->GetSerialString();
|
||||
|
||||
mode Direct;
|
||||
Direct.name = "Direct";
|
||||
Direct.value = AOC_MOUSE_MODE_STATIC_SINGLE_COLOR;
|
||||
Direct.flags = MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
|
||||
Direct.color_mode = MODE_COLORS_PER_LED;
|
||||
Direct.brightness_min = AOC_MOUSE_BRIGHTNESS_OFF;
|
||||
Direct.brightness_max = AOC_MOUSE_BRIGHTNESS_HIGH;
|
||||
Direct.brightness = AOC_MOUSE_BRIGHTNESS_HIGH;
|
||||
modes.push_back(Direct);
|
||||
|
||||
mode SpectrumCycle;
|
||||
SpectrumCycle.name = "Spectrum Cycle";
|
||||
SpectrumCycle.value = AOC_MOUSE_MODE_STATIC_RANDOM;
|
||||
SpectrumCycle.flags = MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_SPEED;
|
||||
SpectrumCycle.color_mode = MODE_COLORS_RANDOM;
|
||||
SpectrumCycle.brightness_min = AOC_MOUSE_BRIGHTNESS_OFF;
|
||||
SpectrumCycle.brightness_max = AOC_MOUSE_BRIGHTNESS_HIGH;
|
||||
SpectrumCycle.brightness = AOC_MOUSE_BRIGHTNESS_HIGH;
|
||||
SpectrumCycle.speed_min = AOC_MOUSE_SPEED_SLOW;
|
||||
SpectrumCycle.speed_max = AOC_MOUSE_SPEED_FAST;
|
||||
SpectrumCycle.speed = AOC_MOUSE_SPEED_MEDIUM;
|
||||
modes.push_back(SpectrumCycle);
|
||||
|
||||
mode Breathing;
|
||||
Breathing.name = "Breathing";
|
||||
Breathing.value = AOC_MOUSE_MODE_BREATHING_SINGLE_COLOR;
|
||||
Breathing.flags = MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_SPEED;
|
||||
Breathing.color_mode = MODE_COLORS_PER_LED;
|
||||
Breathing.brightness_min = AOC_MOUSE_BRIGHTNESS_OFF;
|
||||
Breathing.brightness_max = AOC_MOUSE_BRIGHTNESS_HIGH;
|
||||
Breathing.brightness = AOC_MOUSE_BRIGHTNESS_HIGH;
|
||||
Breathing.speed_min = AOC_MOUSE_SPEED_SLOW;
|
||||
Breathing.speed_max = AOC_MOUSE_SPEED_FAST;
|
||||
Breathing.speed = AOC_MOUSE_SPEED_MEDIUM;
|
||||
modes.push_back(Breathing);
|
||||
|
||||
mode Blink;
|
||||
Blink.name = "Flashing";
|
||||
Blink.value = AOC_MOUSE_MODE_BLINK_SINGLE_COLOR;
|
||||
Blink.flags = MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_SPEED;
|
||||
Blink.color_mode = MODE_COLORS_PER_LED;
|
||||
Blink.brightness_min = AOC_MOUSE_BRIGHTNESS_OFF;
|
||||
Blink.brightness_max = AOC_MOUSE_BRIGHTNESS_HIGH;
|
||||
Blink.brightness = AOC_MOUSE_BRIGHTNESS_HIGH;
|
||||
Blink.speed_min = AOC_MOUSE_SPEED_SLOW;
|
||||
Blink.speed_max = AOC_MOUSE_SPEED_FAST;
|
||||
Blink.speed = AOC_MOUSE_SPEED_MEDIUM;
|
||||
modes.push_back(Blink);
|
||||
|
||||
mode Wave;
|
||||
Wave.name = "Wave";
|
||||
Wave.value = AOC_MOUSE_MODE_WAVE_SINGLE_COLOR;
|
||||
Wave.flags = MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_DIRECTION_LR;
|
||||
Wave.color_mode = MODE_COLORS_PER_LED;
|
||||
Wave.brightness_min = AOC_MOUSE_BRIGHTNESS_OFF;
|
||||
Wave.brightness_max = AOC_MOUSE_BRIGHTNESS_HIGH;
|
||||
Wave.brightness = AOC_MOUSE_BRIGHTNESS_HIGH;
|
||||
Wave.speed_min = AOC_MOUSE_SPEED_SLOW;
|
||||
Wave.speed_max = AOC_MOUSE_SPEED_FAST;
|
||||
Wave.speed = AOC_MOUSE_SPEED_MEDIUM;
|
||||
modes.push_back(Wave);
|
||||
|
||||
mode RainbowWave;
|
||||
RainbowWave.name = "Rainbow Wave";
|
||||
RainbowWave.value = AOC_MOUSE_MODE_WAVE_RANDOM;
|
||||
RainbowWave.flags = MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_DIRECTION_LR;
|
||||
RainbowWave.color_mode = MODE_COLORS_RANDOM;
|
||||
RainbowWave.brightness_min = AOC_MOUSE_BRIGHTNESS_OFF;
|
||||
RainbowWave.brightness_max = AOC_MOUSE_BRIGHTNESS_HIGH;
|
||||
RainbowWave.brightness = AOC_MOUSE_BRIGHTNESS_HIGH;
|
||||
RainbowWave.speed_min = AOC_MOUSE_SPEED_SLOW;
|
||||
RainbowWave.speed_max = AOC_MOUSE_SPEED_FAST;
|
||||
RainbowWave.speed = AOC_MOUSE_SPEED_MEDIUM;
|
||||
modes.push_back(RainbowWave);
|
||||
|
||||
mode DPI;
|
||||
DPI.name = "DPI";
|
||||
DPI.value = AOC_MOUSE_MODE_DPI;
|
||||
DPI.flags = MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
|
||||
DPI.color_mode = MODE_COLORS_RANDOM;
|
||||
DPI.brightness_min = AOC_MOUSE_BRIGHTNESS_OFF;
|
||||
DPI.brightness_max = AOC_MOUSE_BRIGHTNESS_HIGH;
|
||||
DPI.brightness = AOC_MOUSE_BRIGHTNESS_HIGH;
|
||||
modes.push_back(DPI);
|
||||
|
||||
SetupZones();
|
||||
};
|
||||
|
||||
RGBController_AOCMouse::~RGBController_AOCMouse()
|
||||
{
|
||||
delete controller;
|
||||
}
|
||||
|
||||
void RGBController_AOCMouse::SetupZones()
|
||||
{
|
||||
zone logo_zone;
|
||||
logo_zone.name = "Logo";
|
||||
logo_zone.type = ZONE_TYPE_SINGLE;
|
||||
logo_zone.leds_min = 1;
|
||||
logo_zone.leds_max = 1;
|
||||
logo_zone.leds_count = 1;
|
||||
logo_zone.matrix_map = NULL;
|
||||
zones.push_back(logo_zone);
|
||||
|
||||
led logo_led;
|
||||
logo_led.name = "Logo";
|
||||
leds.push_back(logo_led);
|
||||
|
||||
zone scroll_wheel_zone;
|
||||
scroll_wheel_zone.name = "Scroll Wheel";
|
||||
scroll_wheel_zone.type = ZONE_TYPE_SINGLE;
|
||||
scroll_wheel_zone.leds_min = 1;
|
||||
scroll_wheel_zone.leds_max = 1;
|
||||
scroll_wheel_zone.leds_count = 1;
|
||||
scroll_wheel_zone.matrix_map = NULL;
|
||||
zones.push_back(scroll_wheel_zone);
|
||||
|
||||
led scroll_wheel_led;
|
||||
scroll_wheel_led.name = "Scroll Wheel";
|
||||
leds.push_back(scroll_wheel_led);
|
||||
|
||||
SetupColors();
|
||||
}
|
||||
|
||||
void RGBController_AOCMouse::ResizeZone(int /*zone*/, int /*new_size*/)
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| This device does not support resizing zones |
|
||||
\*---------------------------------------------------------*/
|
||||
}
|
||||
|
||||
void RGBController_AOCMouse::DeviceUpdateLEDs()
|
||||
{
|
||||
DeviceUpdateMode();
|
||||
}
|
||||
|
||||
void RGBController_AOCMouse::UpdateZoneLEDs(int /*zone*/)
|
||||
{
|
||||
DeviceUpdateLEDs();
|
||||
}
|
||||
|
||||
void RGBController_AOCMouse::UpdateSingleLED(int /*led*/)
|
||||
{
|
||||
DeviceUpdateLEDs();
|
||||
}
|
||||
|
||||
void RGBController_AOCMouse::DeviceUpdateMode()
|
||||
{
|
||||
if(modes[active_mode].value == AOC_MOUSE_MODE_STATIC_SINGLE_COLOR)
|
||||
{
|
||||
controller->SendDirect(&colors[0]);
|
||||
}
|
||||
else
|
||||
{
|
||||
unsigned char aoc_direction = AOC_MOUSE_DIRECTION_CLOCKWISE;
|
||||
unsigned int aoc_mode = modes[active_mode].value;
|
||||
|
||||
if(modes[active_mode].direction == MODE_DIRECTION_LEFT)
|
||||
{
|
||||
aoc_direction = AOC_MOUSE_DIRECTION_COUNTERCLOCKWISE;
|
||||
}
|
||||
|
||||
if(modes[active_mode].color_mode == MODE_COLORS_RANDOM)
|
||||
{
|
||||
switch(modes[active_mode].value)
|
||||
{
|
||||
case AOC_MOUSE_MODE_BREATHING_SINGLE_COLOR:
|
||||
aoc_mode = AOC_MOUSE_MODE_BREATHING_RANDOM;
|
||||
break;
|
||||
|
||||
case AOC_MOUSE_MODE_BLINK_SINGLE_COLOR:
|
||||
aoc_mode = AOC_MOUSE_MODE_BLINK_RANDOM;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
controller->SendPacket(aoc_mode,
|
||||
modes[active_mode].brightness,
|
||||
modes[active_mode].speed,
|
||||
aoc_direction,
|
||||
&colors[0]);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,35 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_AOCMouse.h |
|
||||
| |
|
||||
| RGBController for AOC mouse |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 20 Apr 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "RGBController.h"
|
||||
#include "AOCMouseController.h"
|
||||
|
||||
class RGBController_AOCMouse : public RGBController
|
||||
{
|
||||
public:
|
||||
RGBController_AOCMouse(AOCMouseController* controller_ptr);
|
||||
~RGBController_AOCMouse();
|
||||
|
||||
void SetupZones();
|
||||
|
||||
void ResizeZone(int zone, int new_size);
|
||||
|
||||
void DeviceUpdateLEDs();
|
||||
void UpdateZoneLEDs(int zone);
|
||||
void UpdateSingleLED(int led);
|
||||
|
||||
void DeviceUpdateMode();
|
||||
|
||||
private:
|
||||
AOCMouseController* controller;
|
||||
};
|
||||
@@ -0,0 +1,117 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AOCMousematController.cpp |
|
||||
| |
|
||||
| Driver for AOC mousemat |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 15 Apr 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include <cstring>
|
||||
#include "AOCMousematController.h"
|
||||
#include "StringUtils.h"
|
||||
|
||||
AOCMousematController::AOCMousematController(hid_device* dev_handle, const char* path, std::string dev_name)
|
||||
{
|
||||
dev = dev_handle;
|
||||
location = path;
|
||||
name = dev_name;
|
||||
}
|
||||
|
||||
AOCMousematController::~AOCMousematController()
|
||||
{
|
||||
hid_close(dev);
|
||||
}
|
||||
|
||||
std::string AOCMousematController::GetDeviceLocation()
|
||||
{
|
||||
return("HID " + location);
|
||||
}
|
||||
|
||||
std::string AOCMousematController::GetDeviceName()
|
||||
{
|
||||
return(name);
|
||||
}
|
||||
|
||||
std::string AOCMousematController::GetSerialString()
|
||||
{
|
||||
wchar_t serial_string[128];
|
||||
int ret = hid_get_serial_number_string(dev, serial_string, 128);
|
||||
|
||||
if(ret != 0)
|
||||
{
|
||||
return("");
|
||||
}
|
||||
|
||||
return(StringUtils::wstring_to_string(serial_string));
|
||||
}
|
||||
|
||||
/*-------------------------------------------------------------------------------------------------*\
|
||||
| Private packet sending functions. |
|
||||
\*-------------------------------------------------------------------------------------------------*/
|
||||
|
||||
void AOCMousematController::SendDirect
|
||||
(
|
||||
RGBColor* color_data
|
||||
)
|
||||
{
|
||||
SendPacket(AOC_MOUSEMAT_MODE_STATIC_SINGLE_COLOR,
|
||||
AOC_MOUSEMAT_BRIGHTNESS_HIGH,
|
||||
AOC_MOUSEMAT_SPEED_MEDIUM,
|
||||
AOC_MOUSEMAT_DIRECTION_CLOCKWISE,
|
||||
color_data);
|
||||
}
|
||||
|
||||
void AOCMousematController::SendPacket
|
||||
(
|
||||
unsigned char mode,
|
||||
unsigned char brightness,
|
||||
unsigned char speed,
|
||||
unsigned char direction,
|
||||
RGBColor* color_data
|
||||
)
|
||||
{
|
||||
unsigned char buf[32];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(buf, 0x00, sizeof(buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up packet |
|
||||
\*-----------------------------------------------------*/
|
||||
buf[0x00] = 0x20;
|
||||
buf[0x01] = brightness;
|
||||
buf[0x02] = speed;
|
||||
buf[0x03] = direction;
|
||||
buf[0x04] = 0x01;
|
||||
buf[0x05] = mode;
|
||||
buf[0x09] = 0xFF;
|
||||
buf[0x0C] = 0xFF;
|
||||
buf[0x0D] = 0x3F;
|
||||
buf[0x0F] = 0xFF;
|
||||
buf[0x10] = 0xFF;
|
||||
buf[0x13] = 0xFF;
|
||||
buf[0x17] = 0xFF;
|
||||
buf[0x19] = 0xFF;
|
||||
buf[0x1A] = 0xFF;
|
||||
buf[0x1B] = 0xFF;
|
||||
buf[0x1D] = 0xFF;
|
||||
buf[0x1E] = 0x32;
|
||||
buf[0x1F] = 0x32;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Copy in color |
|
||||
\*-----------------------------------------------------*/
|
||||
buf[0x06] = RGBGetRValue(color_data[0]);
|
||||
buf[0x07] = RGBGetGValue(color_data[0]);
|
||||
buf[0x08] = RGBGetBValue(color_data[0]);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_send_feature_report(dev, buf, 32);
|
||||
}
|
||||
@@ -0,0 +1,83 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AOCMousematController.h |
|
||||
| |
|
||||
| Driver for AOC mousemat |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 15 Apr 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <string>
|
||||
#include <hidapi.h>
|
||||
#include "RGBController.h"
|
||||
|
||||
/*-----------------------------------------*\
|
||||
| AOC Mousemat Modes |
|
||||
| Note: The 0x80 bit is the random flag |
|
||||
\*-----------------------------------------*/
|
||||
enum
|
||||
{
|
||||
AOC_MOUSEMAT_MODE_STATIC_SINGLE_COLOR = 0x00, /* Static single color mode */
|
||||
AOC_MOUSEMAT_MODE_STATIC_RANDOM = 0x80, /* Static random color mode */
|
||||
AOC_MOUSEMAT_MODE_BREATHING_SINGLE_COLOR = 0x01, /* Breathing single color mode */
|
||||
AOC_MOUSEMAT_MODE_BREATHING_RANDOM = 0x81, /* Breathing random color mode */
|
||||
AOC_MOUSEMAT_MODE_BLINK_SINGLE_COLOR = 0x02, /* Blink single color mode */
|
||||
AOC_MOUSEMAT_MODE_BLINK_RANDOM = 0x82, /* Blink random color mode */
|
||||
AOC_MOUSEMAT_MODE_WAVE_SINGLE_COLOR = 0x03, /* Wave single color mode */
|
||||
AOC_MOUSEMAT_MODE_WAVE_RANDOM = 0x83, /* Wave random color mode */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
AOC_MOUSEMAT_SPEED_SLOW = 0x03, /* Slowest speed */
|
||||
AOC_MOUSEMAT_SPEED_MEDIUM = 0x02, /* Medium speed */
|
||||
AOC_MOUSEMAT_SPEED_FAST = 0x01, /* Fastest speed */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
AOC_MOUSEMAT_BRIGHTNESS_OFF = 0x00, /* Lowest brightness (off) */
|
||||
AOC_MOUSEMAT_BRIGHTNESS_LOW = 0x01, /* Low brightness */
|
||||
AOC_MOUSEMAT_BRIGHTNESS_MEDIUM = 0x02, /* Medium brightness */
|
||||
AOC_MOUSEMAT_BRIGHTNESS_HIGH = 0x03, /* Highest brightness */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
AOC_MOUSEMAT_DIRECTION_CLOCKWISE = 0x00, /* Clockwise direction */
|
||||
AOC_MOUSEMAT_DIRECTION_COUNTERCLOCKWISE = 0x01, /* Counter-clockwise direction */
|
||||
};
|
||||
|
||||
class AOCMousematController
|
||||
{
|
||||
public:
|
||||
AOCMousematController(hid_device* dev_handle, const char* path, std::string dev_name);
|
||||
~AOCMousematController();
|
||||
|
||||
std::string GetDeviceLocation();
|
||||
std::string GetDeviceName();
|
||||
std::string GetSerialString();
|
||||
|
||||
void SendDirect
|
||||
(
|
||||
RGBColor* color_data
|
||||
);
|
||||
|
||||
void SendPacket
|
||||
(
|
||||
unsigned char mode,
|
||||
unsigned char brightness,
|
||||
unsigned char speed,
|
||||
unsigned char direction,
|
||||
RGBColor* color_data
|
||||
);
|
||||
|
||||
private:
|
||||
hid_device* dev;
|
||||
std::string location;
|
||||
std::string name;
|
||||
};
|
||||
@@ -0,0 +1,43 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AOCMousematControllerDetect.cpp |
|
||||
| |
|
||||
| Detector for AOC mousemat |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 15 Apr 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "Detector.h"
|
||||
#include "AOCMousematController.h"
|
||||
#include "RGBController_AOCMousemat.h"
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| AOC Mousemat IDs |
|
||||
\*-----------------------------------------------------*/
|
||||
#define AOC_VID 0x3938
|
||||
#define AOC_AMM700_PID 0x1162
|
||||
|
||||
/******************************************************************************************\
|
||||
* *
|
||||
* DetectAOCMousematControllers *
|
||||
* *
|
||||
* Tests the USB address to see if an AOC Mousemat controller exists there. *
|
||||
* *
|
||||
\******************************************************************************************/
|
||||
|
||||
void DetectAOCMousematControllers(hid_device_info* info, const std::string& name)
|
||||
{
|
||||
hid_device* dev = hid_open_path(info->path);
|
||||
|
||||
if(dev)
|
||||
{
|
||||
AOCMousematController* controller = new AOCMousematController(dev, info->path, name);
|
||||
RGBController_AOCMousemat* rgb_controller = new RGBController_AOCMousemat(controller);
|
||||
|
||||
ResourceManager::get()->RegisterRGBController(rgb_controller);
|
||||
}
|
||||
}
|
||||
|
||||
REGISTER_HID_DETECTOR_IPU("AOC AGON AMM700", DetectAOCMousematControllers, AOC_VID, AOC_AMM700_PID, 1, 0xFF19, 0xFF19);
|
||||
@@ -0,0 +1,195 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_AOCMousemat.cpp |
|
||||
| |
|
||||
| RGBController for AOC mousemat |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 15 Apr 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "RGBController_AOCMousemat.h"
|
||||
|
||||
/**------------------------------------------------------------------*\
|
||||
@name AOC Mousemat
|
||||
@category Mousemat
|
||||
@type USB
|
||||
@save :x:
|
||||
@direct :white_check_mark:
|
||||
@effects :white_check_mark:
|
||||
@detectors DetectAOCMousematControllers
|
||||
@comment
|
||||
\*-------------------------------------------------------------------*/
|
||||
|
||||
RGBController_AOCMousemat::RGBController_AOCMousemat(AOCMousematController* controller_ptr)
|
||||
{
|
||||
controller = controller_ptr;
|
||||
|
||||
name = controller->GetDeviceName();
|
||||
vendor = "AOC";
|
||||
type = DEVICE_TYPE_MOUSEMAT;
|
||||
description = "AOC Mousemat Device";
|
||||
location = controller->GetDeviceLocation();
|
||||
serial = controller->GetSerialString();
|
||||
|
||||
mode Direct;
|
||||
Direct.name = "Direct";
|
||||
Direct.value = AOC_MOUSEMAT_MODE_STATIC_SINGLE_COLOR;
|
||||
Direct.flags = MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
|
||||
Direct.color_mode = MODE_COLORS_PER_LED;
|
||||
Direct.brightness_min = AOC_MOUSEMAT_BRIGHTNESS_OFF;
|
||||
Direct.brightness_max = AOC_MOUSEMAT_BRIGHTNESS_HIGH;
|
||||
Direct.brightness = AOC_MOUSEMAT_BRIGHTNESS_HIGH;
|
||||
modes.push_back(Direct);
|
||||
|
||||
mode SpectrumCycle;
|
||||
SpectrumCycle.name = "Spectrum Cycle";
|
||||
SpectrumCycle.value = AOC_MOUSEMAT_MODE_STATIC_RANDOM;
|
||||
SpectrumCycle.flags = MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_SPEED;
|
||||
SpectrumCycle.color_mode = MODE_COLORS_RANDOM;
|
||||
SpectrumCycle.brightness_min = AOC_MOUSEMAT_BRIGHTNESS_OFF;
|
||||
SpectrumCycle.brightness_max = AOC_MOUSEMAT_BRIGHTNESS_HIGH;
|
||||
SpectrumCycle.brightness = AOC_MOUSEMAT_BRIGHTNESS_HIGH;
|
||||
SpectrumCycle.speed_min = AOC_MOUSEMAT_SPEED_SLOW;
|
||||
SpectrumCycle.speed_max = AOC_MOUSEMAT_SPEED_FAST;
|
||||
SpectrumCycle.speed = AOC_MOUSEMAT_SPEED_MEDIUM;
|
||||
modes.push_back(SpectrumCycle);
|
||||
|
||||
mode Breathing;
|
||||
Breathing.name = "Breathing";
|
||||
Breathing.value = AOC_MOUSEMAT_MODE_BREATHING_SINGLE_COLOR;
|
||||
Breathing.flags = MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_SPEED;
|
||||
Breathing.color_mode = MODE_COLORS_PER_LED;
|
||||
Breathing.brightness_min = AOC_MOUSEMAT_BRIGHTNESS_OFF;
|
||||
Breathing.brightness_max = AOC_MOUSEMAT_BRIGHTNESS_HIGH;
|
||||
Breathing.brightness = AOC_MOUSEMAT_BRIGHTNESS_HIGH;
|
||||
Breathing.speed_min = AOC_MOUSEMAT_SPEED_SLOW;
|
||||
Breathing.speed_max = AOC_MOUSEMAT_SPEED_FAST;
|
||||
Breathing.speed = AOC_MOUSEMAT_SPEED_MEDIUM;
|
||||
modes.push_back(Breathing);
|
||||
|
||||
mode Blink;
|
||||
Blink.name = "Flashing";
|
||||
Blink.value = AOC_MOUSEMAT_MODE_BLINK_SINGLE_COLOR;
|
||||
Blink.flags = MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_SPEED;
|
||||
Blink.color_mode = MODE_COLORS_PER_LED;
|
||||
Blink.brightness_min = AOC_MOUSEMAT_BRIGHTNESS_OFF;
|
||||
Blink.brightness_max = AOC_MOUSEMAT_BRIGHTNESS_HIGH;
|
||||
Blink.brightness = AOC_MOUSEMAT_BRIGHTNESS_HIGH;
|
||||
Blink.speed_min = AOC_MOUSEMAT_SPEED_SLOW;
|
||||
Blink.speed_max = AOC_MOUSEMAT_SPEED_FAST;
|
||||
Blink.speed = AOC_MOUSEMAT_SPEED_MEDIUM;
|
||||
modes.push_back(Blink);
|
||||
|
||||
mode Wave;
|
||||
Wave.name = "Wave";
|
||||
Wave.value = AOC_MOUSEMAT_MODE_WAVE_SINGLE_COLOR;
|
||||
Wave.flags = MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_DIRECTION_LR;
|
||||
Wave.color_mode = MODE_COLORS_PER_LED;
|
||||
Wave.brightness_min = AOC_MOUSEMAT_BRIGHTNESS_OFF;
|
||||
Wave.brightness_max = AOC_MOUSEMAT_BRIGHTNESS_HIGH;
|
||||
Wave.brightness = AOC_MOUSEMAT_BRIGHTNESS_HIGH;
|
||||
Wave.speed_min = AOC_MOUSEMAT_SPEED_SLOW;
|
||||
Wave.speed_max = AOC_MOUSEMAT_SPEED_FAST;
|
||||
Wave.speed = AOC_MOUSEMAT_SPEED_MEDIUM;
|
||||
modes.push_back(Wave);
|
||||
|
||||
mode RainbowWave;
|
||||
RainbowWave.name = "Rainbow Wave";
|
||||
RainbowWave.value = AOC_MOUSEMAT_MODE_WAVE_RANDOM;
|
||||
RainbowWave.flags = MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_DIRECTION_LR;
|
||||
RainbowWave.color_mode = MODE_COLORS_RANDOM;
|
||||
RainbowWave.brightness_min = AOC_MOUSEMAT_BRIGHTNESS_OFF;
|
||||
RainbowWave.brightness_max = AOC_MOUSEMAT_BRIGHTNESS_HIGH;
|
||||
RainbowWave.brightness = AOC_MOUSEMAT_BRIGHTNESS_HIGH;
|
||||
RainbowWave.speed_min = AOC_MOUSEMAT_SPEED_SLOW;
|
||||
RainbowWave.speed_max = AOC_MOUSEMAT_SPEED_FAST;
|
||||
RainbowWave.speed = AOC_MOUSEMAT_SPEED_MEDIUM;
|
||||
modes.push_back(RainbowWave);
|
||||
|
||||
SetupZones();
|
||||
};
|
||||
|
||||
RGBController_AOCMousemat::~RGBController_AOCMousemat()
|
||||
{
|
||||
delete controller;
|
||||
}
|
||||
|
||||
void RGBController_AOCMousemat::SetupZones()
|
||||
{
|
||||
zone mousemat_zone;
|
||||
mousemat_zone.name = "Mousemat";
|
||||
mousemat_zone.type = ZONE_TYPE_SINGLE;
|
||||
mousemat_zone.leds_min = 1;
|
||||
mousemat_zone.leds_max = 1;
|
||||
mousemat_zone.leds_count = 1;
|
||||
mousemat_zone.matrix_map = NULL;
|
||||
zones.push_back(mousemat_zone);
|
||||
|
||||
led mousemat_led;
|
||||
mousemat_led.name = "Mousemat";
|
||||
leds.push_back(mousemat_led);
|
||||
|
||||
SetupColors();
|
||||
}
|
||||
|
||||
void RGBController_AOCMousemat::ResizeZone(int /*zone*/, int /*new_size*/)
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| This device does not support resizing zones |
|
||||
\*---------------------------------------------------------*/
|
||||
}
|
||||
|
||||
void RGBController_AOCMousemat::DeviceUpdateLEDs()
|
||||
{
|
||||
DeviceUpdateMode();
|
||||
}
|
||||
|
||||
void RGBController_AOCMousemat::UpdateZoneLEDs(int /*zone*/)
|
||||
{
|
||||
DeviceUpdateLEDs();
|
||||
}
|
||||
|
||||
void RGBController_AOCMousemat::UpdateSingleLED(int /*led*/)
|
||||
{
|
||||
DeviceUpdateLEDs();
|
||||
}
|
||||
|
||||
void RGBController_AOCMousemat::DeviceUpdateMode()
|
||||
{
|
||||
if(modes[active_mode].value == AOC_MOUSEMAT_MODE_STATIC_SINGLE_COLOR)
|
||||
{
|
||||
controller->SendDirect(&colors[0]);
|
||||
}
|
||||
else
|
||||
{
|
||||
unsigned char aoc_direction = AOC_MOUSEMAT_DIRECTION_CLOCKWISE;
|
||||
unsigned int aoc_mode = modes[active_mode].value;
|
||||
|
||||
if(modes[active_mode].direction == MODE_DIRECTION_LEFT)
|
||||
{
|
||||
aoc_direction = AOC_MOUSEMAT_DIRECTION_COUNTERCLOCKWISE;
|
||||
}
|
||||
|
||||
if(modes[active_mode].color_mode == MODE_COLORS_RANDOM)
|
||||
{
|
||||
switch(modes[active_mode].value)
|
||||
{
|
||||
case AOC_MOUSEMAT_MODE_BREATHING_SINGLE_COLOR:
|
||||
aoc_mode = AOC_MOUSEMAT_MODE_BREATHING_RANDOM;
|
||||
break;
|
||||
|
||||
case AOC_MOUSEMAT_MODE_BLINK_SINGLE_COLOR:
|
||||
aoc_mode = AOC_MOUSEMAT_MODE_BLINK_RANDOM;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
controller->SendPacket(aoc_mode,
|
||||
modes[active_mode].brightness,
|
||||
modes[active_mode].speed,
|
||||
aoc_direction,
|
||||
&colors[0]);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,35 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_AOCMousemat.h |
|
||||
| |
|
||||
| RGBController for AOC mousemat |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 15 Apr 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "RGBController.h"
|
||||
#include "AOCMousematController.h"
|
||||
|
||||
class RGBController_AOCMousemat : public RGBController
|
||||
{
|
||||
public:
|
||||
RGBController_AOCMousemat(AOCMousematController* controller_ptr);
|
||||
~RGBController_AOCMousemat();
|
||||
|
||||
void SetupZones();
|
||||
|
||||
void ResizeZone(int zone, int new_size);
|
||||
|
||||
void DeviceUpdateLEDs();
|
||||
void UpdateZoneLEDs(int zone);
|
||||
void UpdateSingleLED(int led);
|
||||
|
||||
void DeviceUpdateMode();
|
||||
|
||||
private:
|
||||
AOCMousematController* controller;
|
||||
};
|
||||
@@ -0,0 +1,588 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| ASRockPolychromeUSBController.cpp |
|
||||
| |
|
||||
| Driver for ASRock Polychrome USB motherboards |
|
||||
| |
|
||||
| Ed Kambulow (dredvard) 20 Dec 2020 |
|
||||
| Shady Nawara (ShadyNawara) 16 Jan 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include <cstring>
|
||||
#include "RGBController.h"
|
||||
#include "ResourceManager.h"
|
||||
#include "SettingsManager.h"
|
||||
#include "StringUtils.h"
|
||||
#include "ASRockPolychromeUSBController.h"
|
||||
#include "dmiinfo.h"
|
||||
|
||||
#define POLYCHROME_USB_READ_ZONE_CONFIG 0x11
|
||||
#define POLYCHROME_USB_READ_HEADER 0x14
|
||||
#define POLYCHROME_USB_WRITE_HEADER 0x15
|
||||
#define POLYCHROME_USB_SET_ZONE 0x10
|
||||
#define POLYCHROME_USB_INITIAL_CHUNK 0xE3
|
||||
#define POLYCHROME_USB_SEND_CHUNK 0xE4
|
||||
#define POLYCHROME_USB_INIT 0xA4
|
||||
#define POLYCHROME_USB_COMMIT 0x12
|
||||
|
||||
const char* polychrome_USB_zone_names[] =
|
||||
{
|
||||
"RGB LED 1 Header",
|
||||
"RGB LED 2 Header",
|
||||
"Addressable Header 1",
|
||||
"Addressable Header 2",
|
||||
"PCH",
|
||||
"IO Cover",
|
||||
"PCB",
|
||||
"Addressable Header 3/Audio",
|
||||
};
|
||||
|
||||
PolychromeUSBController::PolychromeUSBController(hid_device* dev_handle, const char* path)
|
||||
{
|
||||
DMIInfo dmi;
|
||||
|
||||
dev = dev_handle;
|
||||
device_name = "ASRock " + dmi.getMainboard();
|
||||
location = path;
|
||||
|
||||
SetDeviceInfo();
|
||||
}
|
||||
|
||||
PolychromeUSBController::~PolychromeUSBController()
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
unsigned int PolychromeUSBController::GetChannelCount()
|
||||
{
|
||||
return((unsigned int)device_info.size());
|
||||
}
|
||||
|
||||
std::string PolychromeUSBController::GetDeviceLocation()
|
||||
{
|
||||
return("HID: " + location);
|
||||
}
|
||||
|
||||
std::string PolychromeUSBController::GetDeviceName()
|
||||
{
|
||||
return(device_name);
|
||||
}
|
||||
|
||||
std::string PolychromeUSBController::GetSerialString()
|
||||
{
|
||||
wchar_t serial_string[128];
|
||||
int ret = hid_get_serial_number_string(dev, serial_string, 128);
|
||||
|
||||
if(ret != 0)
|
||||
{
|
||||
return("");
|
||||
}
|
||||
|
||||
return(StringUtils::wstring_to_string(serial_string));
|
||||
}
|
||||
|
||||
void PolychromeUSBController::SetDeviceInfo()
|
||||
{
|
||||
PolychromeDeviceInfo newdev_info;
|
||||
|
||||
ReadConfigTables();
|
||||
|
||||
/*--------------------------------------------------*\
|
||||
| Read settings to check for configured RGSwap |
|
||||
\*--------------------------------------------------*/
|
||||
const std::string detector_name = "ASRock Polychrome USB";
|
||||
const std::string json_rgswap = "RGSwap";
|
||||
SettingsManager* settings_manager = ResourceManager::get()->GetSettingsManager();
|
||||
json device_settings = settings_manager->GetSettings(detector_name);
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Get RGSwap settings from the settings manager |
|
||||
| If RGSwap settings are not found then write them out |
|
||||
| Onboard leds are set to their existing values, |
|
||||
| Addressable RGB and RGB headers are set to false |
|
||||
\*---------------------------------------------------------*/
|
||||
if(!device_settings.contains(json_rgswap))
|
||||
{
|
||||
device_settings[json_rgswap][polychrome_USB_zone_names[0]] = false;
|
||||
device_settings[json_rgswap][polychrome_USB_zone_names[1]] = false;
|
||||
device_settings[json_rgswap][polychrome_USB_zone_names[2]] = false;
|
||||
device_settings[json_rgswap][polychrome_USB_zone_names[3]] = false;
|
||||
device_settings[json_rgswap][polychrome_USB_zone_names[4]] = ((configtable[8] >> 4) & 1) ? true : false;
|
||||
device_settings[json_rgswap][polychrome_USB_zone_names[5]] = ((configtable[8] >> 5) & 1) ? true : false;
|
||||
device_settings[json_rgswap][polychrome_USB_zone_names[6]] = ((configtable[8] >> 6) & 1) ? true : false;
|
||||
device_settings[json_rgswap][polychrome_USB_zone_names[7]] = false;
|
||||
|
||||
settings_manager->SetSettings(detector_name, device_settings);
|
||||
settings_manager->SaveSettings();
|
||||
}
|
||||
else
|
||||
{
|
||||
for(std::size_t idx = 0; idx < 8; idx++)
|
||||
{
|
||||
if(device_settings[json_rgswap].contains(polychrome_USB_zone_names[idx]))
|
||||
{
|
||||
rgswapconfig[idx] = device_settings[json_rgswap][polychrome_USB_zone_names[idx]];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
bool rgswap_final[8] = {0};
|
||||
|
||||
for (unsigned int zonecnt = 0; zonecnt < POLYCHROME_USB_ZONE_MAX_NUM; zonecnt++)
|
||||
{
|
||||
if(configtable[zonecnt] == 0x1E || !((configtable[9] >> zonecnt) & 1))
|
||||
{
|
||||
/*-----------------------------------------------------------------------*\
|
||||
| If we don't have this device type (0x1E) we will skip it and continue. |
|
||||
| Or if the device is not available we skip it and continue |
|
||||
\*-----------------------------------------------------------------------*/
|
||||
continue;
|
||||
}
|
||||
|
||||
newdev_info.num_leds = configtable[zonecnt];
|
||||
newdev_info.rgswap = ((configtable[8] >> zonecnt) & 1) || rgswapconfig[zonecnt];
|
||||
rgswap_final[zonecnt] = newdev_info.rgswap;
|
||||
|
||||
/*--------------------------------------------------------------------------------------------------*\
|
||||
| We will need to know what zone type this is, so that we can look up the name and make calls later. |
|
||||
\*--------------------------------------------------------------------------------------------------*/
|
||||
newdev_info.zone_type = zonecnt;
|
||||
|
||||
switch (zonecnt)
|
||||
{
|
||||
/*-----------------------------------------*\
|
||||
| Type: Addressable, configurable |
|
||||
\*-----------------------------------------*/
|
||||
case POLYCHROME_USB_ZONE_ARGB1:
|
||||
case POLYCHROME_USB_ZONE_ARGB2:
|
||||
/*---------------------------------------------*\
|
||||
| The last led channel is allocated to a |
|
||||
| third ARGB header on some newer motherboards |
|
||||
\*---------------------------------------------*/
|
||||
case POLYCHROME_USB_ZONE_AUDIO:
|
||||
newdev_info.device_type = PolychromeDeviceType::ADDRESSABLE;
|
||||
break;
|
||||
|
||||
/*-----------------------------------------*\
|
||||
| Type: Addressable, not configurable |
|
||||
\*-----------------------------------------*/
|
||||
case POLYCHROME_USB_ZONE_PCH:
|
||||
case POLYCHROME_USB_ZONE_IOCOVER:
|
||||
case POLYCHROME_USB_ZONE_PCB:
|
||||
newdev_info.device_type = PolychromeDeviceType::FIXED;
|
||||
break;
|
||||
|
||||
/*-----------------------------------------*\
|
||||
| Type: Fixed |
|
||||
\*-----------------------------------------*/
|
||||
case POLYCHROME_USB_ZONE_RGB1:
|
||||
case POLYCHROME_USB_ZONE_RGB2:
|
||||
default:
|
||||
newdev_info.device_type = PolychromeDeviceType::FIXED;
|
||||
break;
|
||||
}
|
||||
|
||||
device_info.push_back(newdev_info);
|
||||
}
|
||||
|
||||
// set rgswap to match our settings
|
||||
WriteRGSwap(rgswap_final[0], rgswap_final[1], rgswap_final[2], rgswap_final[3], rgswap_final[4], rgswap_final[5], rgswap_final[6], rgswap_final[7]);
|
||||
}
|
||||
|
||||
void PolychromeUSBController::ResizeZone(int zone, int new_size)
|
||||
{
|
||||
unsigned char zonecfg[POLYCHROME_USB_ZONE_MAX_NUM];
|
||||
|
||||
memset(zonecfg, POLYCHROME_USB_ZONE_UNAVAILABLE, POLYCHROME_USB_ZONE_MAX_NUM);
|
||||
|
||||
configtable[zone] = new_size;
|
||||
|
||||
for(unsigned int i = 0; i < POLYCHROME_USB_ZONE_MAX_NUM; i++)
|
||||
{
|
||||
zonecfg[i] = configtable[i];
|
||||
}
|
||||
|
||||
unsigned char zonecmd = POLYCHROME_USB_LEDCOUNT_CFG;
|
||||
WriteHeader(zonecmd, zonecfg, sizeof(zonecfg));
|
||||
}
|
||||
|
||||
void PolychromeUSBController::WriteZone
|
||||
(
|
||||
unsigned char zone,
|
||||
unsigned char mode,
|
||||
unsigned char speed,
|
||||
RGBColor rgb,
|
||||
bool allzone = false
|
||||
)
|
||||
{
|
||||
|
||||
/*----------------------------------------------------*\
|
||||
| Get the device info so we can look up the zone type. |
|
||||
\*----------------------------------------------------*/
|
||||
PolychromeDeviceInfo device_info = GetPolychromeDevices()[zone];
|
||||
|
||||
unsigned char usb_buf[65];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up message packet with leading 00 |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x01] = POLYCHROME_USB_SET_ZONE;
|
||||
usb_buf[0x03] = device_info.zone_type;
|
||||
usb_buf[0x04] = mode;
|
||||
|
||||
if(device_info.rgswap)
|
||||
{
|
||||
usb_buf[0x05] = RGBGetRValue(rgb);
|
||||
usb_buf[0x06] = RGBGetGValue(rgb);
|
||||
}
|
||||
else
|
||||
{
|
||||
usb_buf[0x05] = RGBGetGValue(rgb);
|
||||
usb_buf[0x06] = RGBGetRValue(rgb);
|
||||
}
|
||||
|
||||
usb_buf[0x07] = RGBGetBValue(rgb);
|
||||
usb_buf[0x08] = speed;
|
||||
usb_buf[0x09] = 0xFF;
|
||||
usb_buf[0x10] = allzone;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_write(dev, usb_buf, 65);
|
||||
hid_read(dev, usb_buf, 64);
|
||||
};
|
||||
|
||||
void PolychromeUSBController::WriteAllZones
|
||||
(
|
||||
const std::vector<PolychromeZoneInfo>& /*zones_info*/,
|
||||
const std::vector<zone>& zones
|
||||
)
|
||||
{
|
||||
std::vector<unsigned char> combined_leds_rgb;
|
||||
std::size_t max_led_count = 0;
|
||||
for(std::size_t zone_idx = 0; zone_idx < zones.size(); zone_idx++){
|
||||
PolychromeDeviceInfo device_info = GetPolychromeDevices()[zone_idx];
|
||||
|
||||
for(std::size_t led_idx = 0; led_idx < zones[zone_idx].leds_count; led_idx++)
|
||||
{
|
||||
if(device_info.rgswap)
|
||||
{
|
||||
combined_leds_rgb.push_back(RGBGetRValue(zones[zone_idx].colors[led_idx]));
|
||||
combined_leds_rgb.push_back(RGBGetGValue(zones[zone_idx].colors[led_idx]));
|
||||
}
|
||||
else
|
||||
{
|
||||
combined_leds_rgb.push_back(RGBGetGValue(zones[zone_idx].colors[led_idx]));
|
||||
combined_leds_rgb.push_back(RGBGetRValue(zones[zone_idx].colors[led_idx]));
|
||||
}
|
||||
combined_leds_rgb.push_back(RGBGetBValue(zones[zone_idx].colors[led_idx]));
|
||||
}
|
||||
max_led_count += zones[zone_idx].leds_max;
|
||||
}
|
||||
combined_leds_rgb.resize((max_led_count + 8) * 3, 0);
|
||||
|
||||
unsigned char usb_buf[65];
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up initial message packet with leading 00 |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x01] = POLYCHROME_USB_SET_ZONE;
|
||||
usb_buf[0x03] = 0xFF;
|
||||
usb_buf[0x04] = POLYCHROME_USB_INITIAL_CHUNK;
|
||||
usb_buf[0x07] = 0xFF;
|
||||
usb_buf[0x40] = 0x65;
|
||||
|
||||
std::size_t initial_led_offset = 9;
|
||||
std::size_t message_byte_capacity = 54; // 18 leds * 3 bytes
|
||||
|
||||
std::size_t led_byte_idx = 0;
|
||||
|
||||
while(led_byte_idx < combined_leds_rgb.size())
|
||||
{
|
||||
for(std::size_t byte_idx = 0; byte_idx < message_byte_capacity; byte_idx++)
|
||||
{
|
||||
usb_buf[initial_led_offset + byte_idx] = combined_leds_rgb[led_byte_idx++];
|
||||
if(led_byte_idx >= combined_leds_rgb.size())
|
||||
{
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_write(dev, usb_buf, 65);
|
||||
hid_read(dev, usb_buf, 64);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up message packet with leading 00 |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x01] = POLYCHROME_USB_SET_ZONE;
|
||||
usb_buf[0x03] = 0xFF;
|
||||
usb_buf[0x04] = POLYCHROME_USB_SEND_CHUNK;
|
||||
usb_buf[0x40] = 0x65;
|
||||
|
||||
initial_led_offset = 5;
|
||||
message_byte_capacity = 57; // 19 leds * 3 bytes
|
||||
}
|
||||
}
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| If reset is true, rgswap is set to the values |
|
||||
| specified in the settings file, otherwise set to off |
|
||||
\*-----------------------------------------------------*/
|
||||
void PolychromeUSBController::SetRGSwap(bool reset)
|
||||
{
|
||||
if(reset)
|
||||
{
|
||||
bool rg[8] = {0};
|
||||
std::vector<PolychromeDeviceInfo> devices_info = GetPolychromeDevices();
|
||||
for (PolychromeDeviceInfo device : devices_info)
|
||||
{
|
||||
rg[device.zone_type] = device.rgswap;
|
||||
}
|
||||
WriteRGSwap(rg[0], rg[1], rg[2], rg[3], rg[4], rg[5], rg[6], rg[7]);
|
||||
}
|
||||
else
|
||||
{
|
||||
/*-----------------------------------------------------------------*\
|
||||
| Disable RGSwap as it causes flashing on each update in direct mode|
|
||||
\*-----------------------------------------------------------------*/
|
||||
WriteRGSwap(0, 0, 0, 0, 0, 0, 0, 0);
|
||||
}
|
||||
}
|
||||
|
||||
void PolychromeUSBController::WriteRGSwap
|
||||
(
|
||||
bool hdr0,
|
||||
bool hdr1,
|
||||
bool ahdr0,
|
||||
bool ahdr1,
|
||||
bool pch,
|
||||
bool io,
|
||||
bool pcb,
|
||||
bool chnl8
|
||||
)
|
||||
{
|
||||
unsigned char rgconfig[1] = {static_cast<unsigned char>((((unsigned char)chnl8 << 7) | ((unsigned char)pcb << 6) | ((unsigned char)io << 5) | ((unsigned char)pch << 4) | ((unsigned char)ahdr1 << 3) | ((unsigned char)ahdr0 << 2) | ((unsigned char)hdr1 << 1) | (unsigned char)hdr0))};
|
||||
WriteHeader(POLYCHROME_USB_RGSWAP_CFG, rgconfig, 1);
|
||||
}
|
||||
|
||||
void PolychromeUSBController::WriteHeader
|
||||
(
|
||||
unsigned char cfg,
|
||||
unsigned char* configstring,
|
||||
unsigned int configsize
|
||||
)
|
||||
{
|
||||
unsigned char usb_buf[65];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up message packet with leading 00 |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x01] = POLYCHROME_USB_WRITE_HEADER;
|
||||
usb_buf[0x03] = cfg;
|
||||
memcpy(&usb_buf[4], configstring, configsize);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_write(dev, usb_buf, 65);
|
||||
hid_read(dev, usb_buf, 64);
|
||||
}
|
||||
|
||||
PolychromeZoneInfo PolychromeUSBController::GetZoneConfig(unsigned char zone)
|
||||
{
|
||||
/*-----------------------------------------------------*\
|
||||
| Get the device info so we can look up the zone type |
|
||||
\*-----------------------------------------------------*/
|
||||
PolychromeDeviceInfo device_info = GetPolychromeDevices()[zone];
|
||||
|
||||
unsigned char usb_buf[65];
|
||||
PolychromeZoneInfo zoneinfo;
|
||||
unsigned char r;
|
||||
unsigned char g;
|
||||
unsigned char b;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up config table request packet |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x01] = POLYCHROME_USB_READ_ZONE_CONFIG;
|
||||
usb_buf[0x03] = device_info.zone_type;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_write(dev, usb_buf, 65);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Read response |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
hid_read(dev, usb_buf, 64);
|
||||
|
||||
r = usb_buf[0x05];
|
||||
g = usb_buf[0x06];
|
||||
b = usb_buf[0x07];
|
||||
|
||||
/*------------------------------------------------------*\
|
||||
| Set Chroma mode (0xE2) & Per-Led mode (0xE3) as Direct |
|
||||
\*------------------------------------------------------*/
|
||||
zoneinfo.mode = usb_buf[0x04] != 0xE2 && usb_buf[0x04] != 0xE3 && usb_buf[0x04] < 0x0F ? usb_buf[0x04] : 0x0F;
|
||||
|
||||
/*------------------------------------------------------*\
|
||||
| G & R are swapped since RGSwap is disabled on init, |
|
||||
| Unless overwritten in settings |
|
||||
\*------------------------------------------------------*/
|
||||
if(device_info.rgswap)
|
||||
{
|
||||
zoneinfo.color = ToRGBColor(r,g,b);
|
||||
}
|
||||
else
|
||||
{
|
||||
zoneinfo.color = ToRGBColor(g,r,b);
|
||||
}
|
||||
zoneinfo.speed = usb_buf[0x08];
|
||||
zoneinfo.zone = usb_buf[0x03];
|
||||
|
||||
return(zoneinfo);
|
||||
}
|
||||
|
||||
void PolychromeUSBController::ReadConfigTables()
|
||||
{
|
||||
unsigned char usb_buf[65];
|
||||
unsigned char maxzoneleds[8];
|
||||
unsigned char rgswap;
|
||||
unsigned char header1;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up max led config table request packet |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x01] = POLYCHROME_USB_READ_HEADER;
|
||||
usb_buf[0x03] = POLYCHROME_USB_LEDCOUNT_CFG;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_write(dev, usb_buf, 65);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Read response |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
hid_read(dev, usb_buf, 64);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Reads in format: RGB1, RGB2, ARGB1, ARGB2, PCH, IO, |
|
||||
| PCB, AUDIO/ARGB3 |
|
||||
\*-----------------------------------------------------*/
|
||||
memcpy(&maxzoneleds,&usb_buf[0x04],8);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up RGB Swap table request packet |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x01] = POLYCHROME_USB_READ_HEADER;
|
||||
usb_buf[0x03] = POLYCHROME_USB_RGSWAP_CFG;
|
||||
|
||||
hid_write(dev, usb_buf, 65);
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
hid_read(dev, usb_buf, 64);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Reads bitwise in format: AUDIO/ARGB3, PCB, IO, PCH, |
|
||||
| ARGB2,ARGB1, RGB2, RGB1 if available |
|
||||
\*-----------------------------------------------------*/
|
||||
rgswap=usb_buf[4];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up Header1 config table request packet |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x01] = POLYCHROME_USB_READ_HEADER;
|
||||
usb_buf[0x03] = 0x01;
|
||||
|
||||
hid_write(dev, usb_buf, 64);
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
hid_read(dev, usb_buf, 64);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Reads bitwise in format: AUDIO/ARGB3, PCB, IO, PCH, |
|
||||
| ARGB2,ARGB1, RGB2, RGB1 if available |
|
||||
\*-----------------------------------------------------*/
|
||||
header1=usb_buf[4];
|
||||
|
||||
memcpy(configtable,&maxzoneleds,8);
|
||||
configtable[8]=rgswap;
|
||||
configtable[9]=header1;
|
||||
return;
|
||||
}
|
||||
|
||||
void PolychromeUSBController::Commit()
|
||||
{
|
||||
/*-----------------------------------------------------*\
|
||||
| Saves all Writes in Device - Will keep after powerup |
|
||||
\*-----------------------------------------------------*/
|
||||
unsigned char usb_buf[65];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up message packet with leading 00 |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x01] = POLYCHROME_USB_COMMIT;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_write(dev, usb_buf, 65);
|
||||
hid_read(dev, usb_buf, 64);
|
||||
};
|
||||
|
||||
const std::vector<PolychromeDeviceInfo>& PolychromeUSBController::GetPolychromeDevices() const
|
||||
{
|
||||
return(device_info);
|
||||
};
|
||||
@@ -0,0 +1,166 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| ASRockPolychromeUSBController.h |
|
||||
| |
|
||||
| Driver for ASRock Polychrome USB motherboards |
|
||||
| |
|
||||
| Ed Kambulow (dredvard) 20 Dec 2020 |
|
||||
| Shady Nawara (ShadyNawara) 16 Jan 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <string>
|
||||
#include <hidapi.h>
|
||||
#include "RGBController.h"
|
||||
|
||||
/*----------------------------------------------------------------------------------------------*\
|
||||
| Definitions for Polychrome USB |
|
||||
\*----------------------------------------------------------------------------------------------*/
|
||||
#define POLYCHROME_USB_NUM_MODES 16 /* Number of Polychrome USB modes */
|
||||
|
||||
enum
|
||||
{
|
||||
POLYCHROME_USB_MODE_OFF = 0x00, /* OFF mode */
|
||||
POLYCHROME_USB_MODE_STATIC = 0x01, /* Static color mode */
|
||||
POLYCHROME_USB_MODE_BREATHING = 0x02, /* Breathing effect mode */
|
||||
POLYCHROME_USB_MODE_STROBE = 0x03, /* Strobe effect mode */
|
||||
POLYCHROME_USB_MODE_SPECTRUM_CYCLE = 0x04, /* Spectrum Cycle effect mode */
|
||||
POLYCHROME_USB_MODE_RANDOM = 0x05, /* Random effect mode */
|
||||
POLYCHROME_USB_MODE_MUSIC = 0x06, /* Random effect mode */
|
||||
POLYCHROME_USB_MODE_WAVE = 0x07, /* Wave effect mode */
|
||||
POLYCHROME_USB_MODE_SPRING = 0x08, /* Spring effect mode */
|
||||
POLYCHROME_USB_MODE_STACK = 0x09, /* Stack effect mode */
|
||||
POLYCHROME_USB_MODE_CRAM = 0x0A, /* Cram effect mode */
|
||||
POLYCHROME_USB_MODE_SCAN = 0x0B, /* Scan effect mode */
|
||||
POLYCHROME_USB_MODE_NEON = 0x0C, /* Neon effect mode */
|
||||
POLYCHROME_USB_MODE_WATER = 0x0D, /* Water effect mode */
|
||||
POLYCHROME_USB_MODE_RAINBOW = 0x0E, /* Rainbow effect mode */
|
||||
POLYCHROME_USB_MODE_DIRECT = 0x0F, /* CHROMA CONNECT effect mode */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
POLYCHROME_USB_SPEED_MIN = 0xFF, /* Slowest speed */
|
||||
POLYCHROME_USB_SPEED_DEFAULT = 0xE0, /* Default speed */
|
||||
POLYCHROME_USB_SPEED_MAX = 0x00, /* Fastest speed */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
POLYCHROME_USB_ZONE_MAX_NUM = 0x08, /* Total Max number of zones */
|
||||
POLYCHROME_USB_ZONE_ADDRESSABLE_MAX = 0x64, /* Maxinum number of ARGB LEDs */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
POLYCHROME_USB_LEDCOUNT_CFG = 0x02, // Config for LED Count
|
||||
POLYCHROME_USB_RGSWAP_CFG = 0x03, // Config for RGSWAP
|
||||
POLYCHROME_USB_ZONE_UNAVAILABLE = 0x1E, // Value from LEDCOUNT CFG if zone not present
|
||||
};
|
||||
|
||||
extern const char* polychrome_USB_zone_names[];
|
||||
|
||||
enum
|
||||
{
|
||||
POLYCHROME_USB_ZONE_RGB1 = 0x00, // RGB Header 1
|
||||
POLYCHROME_USB_ZONE_RGB2 = 0X01, // RGB Header 2
|
||||
POLYCHROME_USB_ZONE_ARGB1 = 0X02, // ARGB Header 1
|
||||
POLYCHROME_USB_ZONE_ARGB2 = 0X03, // ARGB Header 2
|
||||
POLYCHROME_USB_ZONE_PCH = 0X04, // PCH
|
||||
POLYCHROME_USB_ZONE_IOCOVER = 0X05, // IOCOVER
|
||||
POLYCHROME_USB_ZONE_PCB = 0X06, // PCB - Could be mixed swapped with 0x07
|
||||
POLYCHROME_USB_ZONE_AUDIO = 0X07 // AUDIO/ARGB Header 3
|
||||
};
|
||||
|
||||
enum class PolychromeDeviceType
|
||||
{
|
||||
FIXED,
|
||||
ADDRESSABLE,
|
||||
};
|
||||
|
||||
struct PolychromeZoneInfo
|
||||
{
|
||||
unsigned char mode;
|
||||
unsigned char zone;
|
||||
unsigned char speed;
|
||||
RGBColor color;
|
||||
};
|
||||
|
||||
struct PolychromeDeviceInfo
|
||||
{
|
||||
unsigned char effect_channel;
|
||||
unsigned char num_leds;
|
||||
unsigned char zone_type;
|
||||
bool rgswap;
|
||||
PolychromeDeviceType device_type;
|
||||
};
|
||||
|
||||
class PolychromeUSBController
|
||||
{
|
||||
public:
|
||||
unsigned char zone_led_count[8];
|
||||
|
||||
PolychromeUSBController(hid_device* dev_handle, const char* path);
|
||||
~PolychromeUSBController();
|
||||
|
||||
unsigned int GetChannelCount();
|
||||
std::string GetDeviceLocation();
|
||||
std::string GetDeviceName();
|
||||
const std::vector<PolychromeDeviceInfo>& GetPolychromeDevices() const;
|
||||
std::string GetSerialString();
|
||||
PolychromeZoneInfo GetZoneConfig (unsigned char zone);
|
||||
|
||||
void WriteZone
|
||||
(
|
||||
unsigned char zone,
|
||||
unsigned char mode,
|
||||
unsigned char speed,
|
||||
RGBColor rgb,
|
||||
bool allzone
|
||||
);
|
||||
|
||||
void WriteAllZones
|
||||
(
|
||||
const std::vector<PolychromeZoneInfo> &zones_info,
|
||||
const std::vector<zone> &zones
|
||||
);
|
||||
|
||||
void WriteHeader
|
||||
(
|
||||
unsigned char cfg,
|
||||
unsigned char* configstring,
|
||||
unsigned int configsize
|
||||
);
|
||||
|
||||
void ResizeZone(int zone, int new_size);
|
||||
void SetRGSwap(bool reset);
|
||||
|
||||
protected:
|
||||
hid_device* dev;
|
||||
std::vector<PolychromeDeviceInfo> device_info;
|
||||
std::string location;
|
||||
|
||||
void WriteRGSwap
|
||||
(
|
||||
bool hdr0,
|
||||
bool hdr1,
|
||||
bool ahdr0,
|
||||
bool ahdr1,
|
||||
bool pch,
|
||||
bool io,
|
||||
bool pcb,
|
||||
bool chnl8
|
||||
);
|
||||
|
||||
private:
|
||||
std::string device_name;
|
||||
unsigned char configtable[12];
|
||||
bool rgswapconfig[8] = { 0 };
|
||||
|
||||
void SetDeviceInfo();
|
||||
void ReadConfigTables();
|
||||
void Commit();
|
||||
};
|
||||
@@ -0,0 +1,42 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| ASRockPolychromeUSBControllerDetect.cpp |
|
||||
| |
|
||||
| Detector for ASRock Polychrome USB motherboards |
|
||||
| |
|
||||
| Ed Kambulow (dredvard) 20 Dec 2020 |
|
||||
| Shady Nawara (ShadyNawara) 16 Jan 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include <hidapi.h>
|
||||
#include "Detector.h"
|
||||
#include "ASRockPolychromeUSBController.h"
|
||||
#include "RGBController_ASRockPolychromeUSB.h"
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| ASRock vendor ID |
|
||||
\*---------------------------------------------------------*/
|
||||
#define ASROCK_VID 0x26CE
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| ASRock product ID |
|
||||
\*---------------------------------------------------------*/
|
||||
#define ASROCK_MOTHERBOARD_1_PID 0x01A2
|
||||
#define ASROCK_DESKMINI_ADDRESSABLE_LED_STRIP_PID 0x01A6
|
||||
|
||||
void DetectPolychromeUSBControllers(hid_device_info* info, const std::string& /*name*/)
|
||||
{
|
||||
hid_device* dev = hid_open_path(info->path);
|
||||
|
||||
if(dev)
|
||||
{
|
||||
PolychromeUSBController* controller = new PolychromeUSBController(dev, info->path);
|
||||
RGBController_PolychromeUSB* rgb_controller = new RGBController_PolychromeUSB(controller);
|
||||
ResourceManager::get()->RegisterRGBController(rgb_controller);
|
||||
}
|
||||
}
|
||||
|
||||
REGISTER_HID_DETECTOR("ASRock Polychrome USB", DetectPolychromeUSBControllers, ASROCK_VID, ASROCK_MOTHERBOARD_1_PID);
|
||||
REGISTER_HID_DETECTOR("ASRock Deskmini Addressable LED Strip", DetectPolychromeUSBControllers, ASROCK_VID, ASROCK_DESKMINI_ADDRESSABLE_LED_STRIP_PID);
|
||||
@@ -0,0 +1,361 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_ASRockPolychromeUSB.cpp |
|
||||
| |
|
||||
| RGBController for ASRock Polychrome USB motherboards |
|
||||
| |
|
||||
| Ed Kambulow (dredvard) 20 Dec 2020 |
|
||||
| Shady Nawara (ShadyNawara) 16 Jan 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include <string.h>
|
||||
#include "RGBController_ASRockPolychromeUSB.h"
|
||||
|
||||
#define ASROCK_USB_MAX_ZONES 8
|
||||
#define ASROCK_ADDRESSABLE_MAX_LEDS 100
|
||||
|
||||
/**------------------------------------------------------------------*\
|
||||
@name ASrock Polychrome USB
|
||||
@category Motherboard
|
||||
@type USB
|
||||
@save :robot:
|
||||
@direct :x:
|
||||
@effects :white_check_mark:
|
||||
@detectors DetectPolychromeUSBControllers
|
||||
@comment ASRock Polychrome controllers will save with each update.
|
||||
\*-------------------------------------------------------------------*/
|
||||
|
||||
RGBController_PolychromeUSB::RGBController_PolychromeUSB(PolychromeUSBController* controller_ptr)
|
||||
{
|
||||
controller = controller_ptr;
|
||||
|
||||
name = controller->GetDeviceName();
|
||||
description = "ASRock Polychrome USB Device";
|
||||
vendor = "ASRock";
|
||||
type = DEVICE_TYPE_MOTHERBOARD;
|
||||
location = controller->GetDeviceLocation();
|
||||
|
||||
mode Off;
|
||||
Off.name = "Off";
|
||||
Off.value = POLYCHROME_USB_MODE_OFF;
|
||||
Off.flags = 0;
|
||||
Off.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Off);
|
||||
|
||||
mode Static;
|
||||
Static.name = "Static";
|
||||
Static.value = POLYCHROME_USB_MODE_STATIC;
|
||||
Static.flags = MODE_FLAG_HAS_PER_LED_COLOR;
|
||||
Static.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Static);
|
||||
|
||||
mode Breathing;
|
||||
Breathing.name = "Breathing";
|
||||
Breathing.value = POLYCHROME_USB_MODE_BREATHING;
|
||||
Breathing.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_PER_LED_COLOR;
|
||||
Breathing.speed_min = POLYCHROME_USB_SPEED_MIN;
|
||||
Breathing.speed_max = POLYCHROME_USB_SPEED_MAX;
|
||||
Breathing.speed = POLYCHROME_USB_SPEED_DEFAULT;
|
||||
Breathing.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Breathing);
|
||||
|
||||
mode Strobe;
|
||||
Strobe.name = "Strobe";
|
||||
Strobe.value = POLYCHROME_USB_MODE_STROBE;
|
||||
Strobe.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_PER_LED_COLOR;
|
||||
Strobe.speed_min = POLYCHROME_USB_SPEED_MIN;
|
||||
Strobe.speed_max = POLYCHROME_USB_SPEED_MAX;
|
||||
Strobe.speed = POLYCHROME_USB_SPEED_DEFAULT;
|
||||
Strobe.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Strobe);
|
||||
|
||||
mode SpectrumCycle;
|
||||
SpectrumCycle.name = "Spectrum Cycle";
|
||||
SpectrumCycle.value = POLYCHROME_USB_MODE_SPECTRUM_CYCLE;
|
||||
SpectrumCycle.flags = MODE_FLAG_HAS_SPEED;
|
||||
SpectrumCycle.speed_min = POLYCHROME_USB_SPEED_MIN;
|
||||
SpectrumCycle.speed_max = POLYCHROME_USB_SPEED_MAX;
|
||||
SpectrumCycle.speed = POLYCHROME_USB_SPEED_DEFAULT;
|
||||
SpectrumCycle.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(SpectrumCycle);
|
||||
|
||||
mode Random;
|
||||
Random.name = "Random";
|
||||
Random.value = POLYCHROME_USB_MODE_RANDOM;
|
||||
Random.flags = MODE_FLAG_HAS_SPEED;
|
||||
Random.speed_min = POLYCHROME_USB_SPEED_MIN;
|
||||
Random.speed_max = POLYCHROME_USB_SPEED_MAX;
|
||||
Random.speed = POLYCHROME_USB_SPEED_DEFAULT;
|
||||
Random.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Random);
|
||||
|
||||
mode Music;
|
||||
Random.name = "Music";
|
||||
Random.value = POLYCHROME_USB_MODE_RANDOM;
|
||||
Random.flags = MODE_FLAG_HAS_BRIGHTNESS;
|
||||
Random.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Random);
|
||||
|
||||
mode Wave;
|
||||
Wave.name = "Wave";
|
||||
Wave.value = POLYCHROME_USB_MODE_WAVE;
|
||||
Wave.flags = MODE_FLAG_HAS_SPEED;
|
||||
Wave.speed_min = POLYCHROME_USB_SPEED_MIN;
|
||||
Wave.speed_max = POLYCHROME_USB_SPEED_MAX;
|
||||
Wave.speed = POLYCHROME_USB_SPEED_DEFAULT;
|
||||
Wave.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Wave);
|
||||
|
||||
mode Spring;
|
||||
Spring.name = "Spring";
|
||||
Spring.value = POLYCHROME_USB_MODE_SPRING;
|
||||
Spring.flags = MODE_FLAG_HAS_SPEED;
|
||||
Spring.speed_min = POLYCHROME_USB_SPEED_MIN;
|
||||
Spring.speed_max = POLYCHROME_USB_SPEED_MAX;
|
||||
Spring.speed = POLYCHROME_USB_SPEED_DEFAULT;
|
||||
Spring.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Spring);
|
||||
|
||||
mode Stack;
|
||||
Stack.name = "Stack";
|
||||
Stack.value = POLYCHROME_USB_MODE_STACK;
|
||||
Stack.flags = MODE_FLAG_HAS_SPEED;
|
||||
Stack.speed_min = POLYCHROME_USB_SPEED_MIN;
|
||||
Stack.speed_max = POLYCHROME_USB_SPEED_MAX;
|
||||
Stack.speed = POLYCHROME_USB_SPEED_DEFAULT;
|
||||
Stack.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Stack);
|
||||
|
||||
mode Cram;
|
||||
Cram.name = "Cram";
|
||||
Cram.value = POLYCHROME_USB_MODE_CRAM;
|
||||
Cram.flags = MODE_FLAG_HAS_SPEED;
|
||||
Cram.speed_min = POLYCHROME_USB_SPEED_MIN;
|
||||
Cram.speed_max = POLYCHROME_USB_SPEED_MAX;
|
||||
Cram.speed = POLYCHROME_USB_SPEED_DEFAULT;
|
||||
Cram.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Cram);
|
||||
|
||||
mode Scan;
|
||||
Scan.name = "Scan";
|
||||
Scan.value = POLYCHROME_USB_MODE_SCAN;
|
||||
Scan.flags = MODE_FLAG_HAS_SPEED;
|
||||
Scan.speed_min = POLYCHROME_USB_SPEED_MIN;
|
||||
Scan.speed_max = POLYCHROME_USB_SPEED_MAX;
|
||||
Scan.speed = POLYCHROME_USB_SPEED_DEFAULT;
|
||||
Scan.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Scan);
|
||||
|
||||
mode Neon;
|
||||
Neon.name = "Neon";
|
||||
Neon.value = POLYCHROME_USB_MODE_NEON;
|
||||
Neon.flags = 0;
|
||||
Neon.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Neon);
|
||||
|
||||
mode Water;
|
||||
Water.name = "Water";
|
||||
Water.value = POLYCHROME_USB_MODE_WATER;
|
||||
Water.flags = MODE_FLAG_HAS_SPEED;
|
||||
Water.speed_min = POLYCHROME_USB_SPEED_MIN;
|
||||
Water.speed_max = POLYCHROME_USB_SPEED_MAX;
|
||||
Water.speed = POLYCHROME_USB_SPEED_DEFAULT;
|
||||
Water.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Water);
|
||||
|
||||
mode Rainbow;
|
||||
Rainbow.name = "Rainbow";
|
||||
Rainbow.value = POLYCHROME_USB_MODE_RAINBOW;
|
||||
Rainbow.flags = MODE_FLAG_HAS_SPEED;
|
||||
Rainbow.speed_min = POLYCHROME_USB_SPEED_MIN;
|
||||
Rainbow.speed_max = POLYCHROME_USB_SPEED_MAX;
|
||||
Rainbow.speed = POLYCHROME_USB_SPEED_DEFAULT;
|
||||
Rainbow.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Rainbow);
|
||||
|
||||
mode Direct;
|
||||
Direct.name = "Direct";
|
||||
Direct.value = POLYCHROME_USB_MODE_DIRECT;
|
||||
Direct.flags = MODE_FLAG_HAS_PER_LED_COLOR;
|
||||
Direct.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Direct);
|
||||
|
||||
SetupZones();
|
||||
}
|
||||
|
||||
void RGBController_PolychromeUSB::SetupZones()
|
||||
{
|
||||
/*-------------------------------------------------*\
|
||||
| Clear any existing color/LED configuration |
|
||||
\*-------------------------------------------------*/
|
||||
leds.clear();
|
||||
colors.clear();
|
||||
zones.resize(controller->GetChannelCount());
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| Set zones and leds |
|
||||
\*-------------------------------------------------*/
|
||||
for(unsigned int channel_idx = 0; channel_idx < zones.size(); channel_idx++)
|
||||
{
|
||||
PolychromeDeviceInfo device_info = controller->GetPolychromeDevices()[channel_idx];
|
||||
|
||||
zones[channel_idx].type = ZONE_TYPE_LINEAR;
|
||||
|
||||
if(device_info.device_type== PolychromeDeviceType::ADDRESSABLE)
|
||||
{
|
||||
zones[channel_idx].name = polychrome_USB_zone_names[device_info.zone_type];
|
||||
zones[channel_idx].leds_min = 0;
|
||||
zones[channel_idx].leds_max = ASROCK_ADDRESSABLE_MAX_LEDS;
|
||||
zones[channel_idx].leds_count = device_info.num_leds;
|
||||
}
|
||||
else if(device_info.device_type==PolychromeDeviceType::FIXED)
|
||||
{
|
||||
zones[channel_idx].name = polychrome_USB_zone_names[device_info.zone_type];
|
||||
zones[channel_idx].leds_min = device_info.num_leds;
|
||||
zones[channel_idx].leds_max = device_info.num_leds;
|
||||
zones[channel_idx].leds_count = device_info.num_leds;
|
||||
}
|
||||
|
||||
|
||||
for(unsigned int led_ch_idx = 0; led_ch_idx < zones[channel_idx].leds_count; led_ch_idx++)
|
||||
{
|
||||
led new_led;
|
||||
new_led.name = zones[channel_idx].name;
|
||||
new_led.name.append(", LED ");
|
||||
new_led.name.append(std::to_string(led_ch_idx + 1));
|
||||
new_led.value = channel_idx;
|
||||
|
||||
leds.push_back(new_led);
|
||||
}
|
||||
|
||||
zones[channel_idx].matrix_map = NULL;
|
||||
}
|
||||
|
||||
SetupColors();
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Initialize zone info to track zone, speed, mode |
|
||||
| B550 Boards have modes, speed for each zone |
|
||||
\*---------------------------------------------------------*/
|
||||
for (unsigned int channel_idx = 0; channel_idx < zones.size(); channel_idx++)
|
||||
{
|
||||
PolychromeZoneInfo zoneinfo;
|
||||
zoneinfo = controller->GetZoneConfig(channel_idx);
|
||||
zones_info.push_back(zoneinfo);
|
||||
}
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Initialize colors for each LED |
|
||||
| We cannot currently get the individual led color so |
|
||||
| we use the zone color in each zone to set all leds |
|
||||
| !!TODO: in Per-Led mode, zone color is always black |
|
||||
\*---------------------------------------------------------*/
|
||||
for(std::size_t led_idx = 0; led_idx < leds.size(); led_idx++)
|
||||
{
|
||||
unsigned char led = (unsigned char)leds[led_idx].value;
|
||||
|
||||
colors[led_idx] = zones_info[led].color;
|
||||
}
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| Initialize active mode |
|
||||
\*-------------------------------------------------*/
|
||||
active_mode = zones_info.size() > 1 ? zones_info[0].mode : 0x0;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| If in Direct mode, reset all Leds to match interface |
|
||||
\*-----------------------------------------------------*/
|
||||
if(active_mode == 0x0F)
|
||||
{
|
||||
controller->WriteAllZones(zones_info, zones);
|
||||
}
|
||||
}
|
||||
|
||||
void RGBController_PolychromeUSB::ResizeZone(int zone, int new_size)
|
||||
{
|
||||
zones[zone].leds_count = (unsigned char) new_size;
|
||||
controller->ResizeZone(zones_info[zone].zone, new_size);
|
||||
}
|
||||
|
||||
void RGBController_PolychromeUSB::DeviceUpdateLEDs()
|
||||
{
|
||||
if(POLYCHROME_USB_MODE_DIRECT == zones_info[0].mode )
|
||||
{
|
||||
controller->WriteAllZones(zones_info,zones);
|
||||
return;
|
||||
}
|
||||
for(std::size_t zone_idx = 0; zone_idx < zones.size(); zone_idx++)
|
||||
{
|
||||
unsigned char set_mode = zones_info[zone_idx].mode;
|
||||
|
||||
if (set_mode>modes.size())
|
||||
{
|
||||
set_mode = active_mode;
|
||||
}
|
||||
|
||||
controller->WriteZone((unsigned char)zone_idx, set_mode, zones_info[zone_idx].speed, zones[zone_idx].colors[0], false);
|
||||
}
|
||||
}
|
||||
|
||||
void RGBController_PolychromeUSB::UpdateZoneLEDs(int zone)
|
||||
{
|
||||
unsigned char set_mode=zones_info[zone].mode;
|
||||
|
||||
if(set_mode > modes.size())
|
||||
{
|
||||
set_mode = active_mode;
|
||||
}
|
||||
|
||||
controller->WriteZone(zone, set_mode, zones_info[zone].speed, zones[zone].colors[0], false);
|
||||
}
|
||||
|
||||
void RGBController_PolychromeUSB::UpdateSingleLED(int led)
|
||||
{
|
||||
unsigned int channel = leds[led].value;
|
||||
unsigned char set_mode = zones_info[channel].mode;
|
||||
|
||||
if(set_mode > modes.size())
|
||||
{
|
||||
set_mode = active_mode;
|
||||
}
|
||||
|
||||
controller->WriteZone(channel, set_mode, zones_info[channel].speed, zones[channel].colors[0], false);
|
||||
}
|
||||
|
||||
unsigned char RGBController_PolychromeUSB::GetDeviceMode(unsigned char zone)
|
||||
{
|
||||
int dev_mode;
|
||||
|
||||
dev_mode = controller->GetZoneConfig(zone).mode;
|
||||
active_mode = dev_mode;
|
||||
|
||||
return(active_mode);
|
||||
}
|
||||
|
||||
void RGBController_PolychromeUSB::DeviceUpdateMode()
|
||||
{
|
||||
/*-----------------------------------------------------------------*\
|
||||
| Disable RGSwap as it causes flashing on each update in direct mode|
|
||||
| Otherwise, reset to values specified in settings.json |
|
||||
\*-----------------------------------------------------------------*/
|
||||
controller->SetRGSwap(modes[active_mode].name != "Direct");
|
||||
|
||||
for(unsigned int zone_idx = 0; zone_idx < zones.size(); zone_idx++)
|
||||
{
|
||||
if(zones[zone_idx].leds_count > 0)
|
||||
{
|
||||
unsigned char set_mode =(unsigned char) modes[active_mode].value;
|
||||
zones_info[zone_idx].mode =(unsigned char) modes[active_mode].value;
|
||||
zones_info[zone_idx].speed =(unsigned char) modes[active_mode].speed;
|
||||
|
||||
if(set_mode > modes.size())
|
||||
{
|
||||
set_mode = active_mode;
|
||||
}
|
||||
|
||||
controller->WriteZone(zone_idx, set_mode, zones_info[zone_idx].speed, zones[zone_idx].colors[0], false);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,38 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_ASRockPolychromeUSB.h |
|
||||
| |
|
||||
| RGBController for ASRock Polychrome USB motherboards |
|
||||
| |
|
||||
| Ed Kambulow (dredvard) 20 Dec 2020 |
|
||||
| Shady Nawara (ShadyNawara) 16 Jan 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "RGBController.h"
|
||||
#include "ASRockPolychromeUSBController.h"
|
||||
|
||||
class RGBController_PolychromeUSB : public RGBController
|
||||
{
|
||||
public:
|
||||
RGBController_PolychromeUSB(PolychromeUSBController* controller_ptr);
|
||||
|
||||
void SetupZones();
|
||||
|
||||
void ResizeZone(int zone, int new_size);
|
||||
|
||||
void DeviceUpdateLEDs();
|
||||
void UpdateZoneLEDs(int zone);
|
||||
void UpdateSingleLED(int led);
|
||||
|
||||
void DeviceUpdateMode();
|
||||
|
||||
private:
|
||||
PolychromeUSBController* controller;
|
||||
std::vector<PolychromeZoneInfo> zones_info;
|
||||
|
||||
unsigned char GetDeviceMode(unsigned char zone);
|
||||
};
|
||||
+124
@@ -0,0 +1,124 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| ASRockASRRGBSMBusController.cpp |
|
||||
| |
|
||||
| Driver for SMBus ASRock ASR RGB motherboards |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 14 Dec 2019 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "ASRockASRRGBSMBusController.h"
|
||||
#include <cstring>
|
||||
#include "dmiinfo.h"
|
||||
#include "LogManager.h"
|
||||
|
||||
#define ASROCK_ZONE_LED_COUNT_MESSAGE_EN "[%s] Zone %i LED count: %02d"
|
||||
|
||||
using namespace std::chrono_literals;
|
||||
|
||||
ASRockASRRGBSMBusController::ASRockASRRGBSMBusController(i2c_smbus_interface* bus, polychrome_dev_id dev)
|
||||
{
|
||||
this->bus = bus;
|
||||
this->dev = dev;
|
||||
|
||||
DMIInfo dmi;
|
||||
|
||||
device_name = "ASRock " + dmi.getMainboard();
|
||||
|
||||
}
|
||||
|
||||
ASRockASRRGBSMBusController::~ASRockASRRGBSMBusController()
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
std::string ASRockASRRGBSMBusController::GetDeviceLocation()
|
||||
{
|
||||
std::string return_string(bus->device_name);
|
||||
char addr[5];
|
||||
snprintf(addr, 5, "0x%02X", dev);
|
||||
return_string.append(", address ");
|
||||
return_string.append(addr);
|
||||
return("I2C: " + return_string);
|
||||
}
|
||||
|
||||
std::string ASRockASRRGBSMBusController::GetDeviceName()
|
||||
{
|
||||
return(device_name);
|
||||
}
|
||||
|
||||
std::string ASRockASRRGBSMBusController::GetFirmwareVersion()
|
||||
{
|
||||
uint8_t major_version = fw_version >> 8;
|
||||
uint8_t minor_version = fw_version & 0xFF;
|
||||
|
||||
return(std::to_string(major_version) + "." + std::to_string(minor_version));
|
||||
}
|
||||
|
||||
uint8_t ASRockASRRGBSMBusController::GetMode()
|
||||
{
|
||||
return(active_mode);
|
||||
}
|
||||
|
||||
void ASRockASRRGBSMBusController::SetColorsAndSpeed(uint8_t led, uint8_t red, uint8_t green, uint8_t blue)
|
||||
{
|
||||
uint8_t color_speed_pkt[4] = { red, green, blue, active_speed };
|
||||
uint8_t select_led_pkt[1] = { led };
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Select LED |
|
||||
\*-----------------------------------------------------*/
|
||||
if(active_mode != ASRLED_MODE_OFF)
|
||||
{
|
||||
bus->i2c_smbus_write_block_data(dev, ASROCK_ASR_REG_LED_SELECT, 1, select_led_pkt);
|
||||
std::this_thread::sleep_for(1ms);
|
||||
}
|
||||
|
||||
switch(active_mode)
|
||||
{
|
||||
/*-----------------------------------------------------*\
|
||||
| These modes take 4 bytes in R/G/B/S order |
|
||||
\*-----------------------------------------------------*/
|
||||
case ASRLED_MODE_BREATHING:
|
||||
case ASRLED_MODE_STROBE:
|
||||
case ASRLED_MODE_SPECTRUM_CYCLE:
|
||||
bus->i2c_smbus_write_block_data(dev, active_mode, 4, color_speed_pkt);
|
||||
break;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| These modes take 3 bytes in R/G/B order |
|
||||
\*-----------------------------------------------------*/
|
||||
default:
|
||||
case ASRLED_MODE_STATIC:
|
||||
case ASRLED_MODE_MUSIC:
|
||||
bus->i2c_smbus_write_block_data(dev, active_mode, 3, color_speed_pkt);
|
||||
break;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| These modes take 1 byte - speed |
|
||||
\*-----------------------------------------------------*/
|
||||
case ASRLED_MODE_RANDOM:
|
||||
case ASRLED_MODE_WAVE:
|
||||
bus->i2c_smbus_write_block_data(dev, active_mode, 1, &active_speed);
|
||||
break;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| These modes take no bytes |
|
||||
\*-----------------------------------------------------*/
|
||||
case ASRLED_MODE_OFF:
|
||||
break;
|
||||
}
|
||||
std::this_thread::sleep_for(1ms);
|
||||
}
|
||||
|
||||
void ASRockASRRGBSMBusController::SetMode(uint8_t zone,uint8_t mode, uint8_t speed)
|
||||
{
|
||||
active_zone = zone;
|
||||
active_mode = mode;
|
||||
active_speed = speed;
|
||||
|
||||
bus->i2c_smbus_write_block_data(dev, ASROCK_ASR_REG_MODE, 1, &active_mode);
|
||||
std::this_thread::sleep_for(1ms);
|
||||
}
|
||||
+77
@@ -0,0 +1,77 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| ASRockASRRGBSMBusController.h |
|
||||
| |
|
||||
| Driver for SMBus ASRock ASR RGB motherboards |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 13 Dec 2019 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <string>
|
||||
#include "i2c_smbus.h"
|
||||
|
||||
typedef uint8_t polychrome_dev_id;
|
||||
|
||||
#define ASROCK_ASR_CONTROLLER_NAME "ASRock ASR RGB SMBus Controller"
|
||||
|
||||
enum
|
||||
{
|
||||
/*------------------------------------------------------------------------------------------*\
|
||||
| ASRock Common Registers |
|
||||
\*------------------------------------------------------------------------------------------*/
|
||||
ASROCK_ASR_REG_FIRMWARE_VER = 0x00, /* Firmware version Major.Minor */
|
||||
ASROCK_ASR_REG_MODE = 0x30, /* Mode selection register */
|
||||
ASROCK_ASR_REG_LED_SELECT = 0x31, /* LED selection register */
|
||||
};
|
||||
|
||||
/*----------------------------------------------------------------------------------------------*\
|
||||
| Definitions for ASR LED |
|
||||
\*----------------------------------------------------------------------------------------------*/
|
||||
#define ASRLED_NUM_MODES 8 /* Number of ASR LED modes */
|
||||
|
||||
enum
|
||||
{
|
||||
ASRLED_MODE_OFF = 0x10, /* OFF mode */
|
||||
ASRLED_MODE_STATIC = 0x11, /* Static color mode */
|
||||
ASRLED_MODE_BREATHING = 0x12, /* Breathing effect mode */
|
||||
ASRLED_MODE_STROBE = 0x13, /* Strobe effect mode */
|
||||
ASRLED_MODE_SPECTRUM_CYCLE = 0x14, /* Spectrum Cycle effect mode */
|
||||
ASRLED_MODE_RANDOM = 0x15, /* Random effect mode */
|
||||
ASRLED_MODE_MUSIC = 0x17, /* Music effect mode */
|
||||
ASRLED_MODE_WAVE = 0x18, /* Wave effect mode */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
ASRLED_SPEED_MIN = 0x05, /* Slowest speed */
|
||||
ASRLED_SPEED_DEFAULT = 0x03, /* Default speed */
|
||||
ASRLED_SPEED_MAX = 0x00, /* Fastest speed */
|
||||
};
|
||||
|
||||
class ASRockASRRGBSMBusController
|
||||
{
|
||||
public:
|
||||
ASRockASRRGBSMBusController(i2c_smbus_interface* bus, polychrome_dev_id dev);
|
||||
~ASRockASRRGBSMBusController();
|
||||
|
||||
std::string GetDeviceLocation();
|
||||
std::string GetDeviceName();
|
||||
std::string GetFirmwareVersion();
|
||||
uint8_t GetMode();
|
||||
void SetColorsAndSpeed(uint8_t led, uint8_t red, uint8_t green, uint8_t blue);
|
||||
void SetMode(uint8_t zone, uint8_t mode, uint8_t speed);
|
||||
|
||||
uint16_t fw_version;
|
||||
|
||||
private:
|
||||
std::string device_name;
|
||||
uint8_t active_zone;
|
||||
uint8_t active_mode;
|
||||
uint8_t active_speed;
|
||||
i2c_smbus_interface* bus;
|
||||
polychrome_dev_id dev;
|
||||
};
|
||||
+207
@@ -0,0 +1,207 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_ASRRGBSMBus.cpp |
|
||||
| |
|
||||
| RGBController for SMBus ASRock ASR LED motherboards |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 15 Dec 2019 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "RGBController_ASRockASRRGBSMBus.h"
|
||||
|
||||
#define ASROCK_MAX_ZONES 4
|
||||
#define ASROCK_MAX_LEDS 22
|
||||
|
||||
/**------------------------------------------------------------------*\
|
||||
@name ASRock ASR RGB SMBus
|
||||
@category Motherboard
|
||||
@type SMBus
|
||||
@save :robot:
|
||||
@direct :x:
|
||||
@effects :white_check_mark:
|
||||
@detectors DetectASRockSMBusControllers
|
||||
@comment ASRock ASR RGB LED controllers will save with each update.
|
||||
Per ARGB LED support is not possible with these devices.
|
||||
\*-------------------------------------------------------------------*/
|
||||
|
||||
RGBController_ASRockASRRGBSMBus::RGBController_ASRockASRRGBSMBus(ASRockASRRGBSMBusController* controller_ptr)
|
||||
{
|
||||
controller = controller_ptr;
|
||||
|
||||
name = controller->GetDeviceName();
|
||||
vendor = "ASRock";
|
||||
version = controller->GetFirmwareVersion();
|
||||
type = DEVICE_TYPE_MOTHERBOARD;
|
||||
description = "ASRock ASR RGB LED Device";
|
||||
location = controller->GetDeviceLocation();
|
||||
|
||||
mode Off;
|
||||
Off.name = "Off";
|
||||
Off.value = ASRLED_MODE_OFF;
|
||||
Off.flags = MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Off.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Off);
|
||||
|
||||
mode Static;
|
||||
Static.name = "Static";
|
||||
Static.value = ASRLED_MODE_STATIC;
|
||||
Static.flags = MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Static.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Static);
|
||||
|
||||
mode Breathing;
|
||||
Breathing.name = "Breathing";
|
||||
Breathing.value = ASRLED_MODE_BREATHING;
|
||||
Breathing.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Breathing.speed_min = ASRLED_SPEED_MIN;
|
||||
Breathing.speed_max = ASRLED_SPEED_MAX;
|
||||
Breathing.speed = ASRLED_SPEED_DEFAULT;
|
||||
Breathing.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Breathing);
|
||||
|
||||
mode Strobe;
|
||||
Strobe.name = "Strobe";
|
||||
Strobe.value = ASRLED_MODE_STROBE;
|
||||
Strobe.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Strobe.speed_min = ASRLED_SPEED_MIN;
|
||||
Strobe.speed_max = ASRLED_SPEED_MAX;
|
||||
Strobe.speed = ASRLED_SPEED_DEFAULT;
|
||||
Strobe.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Strobe);
|
||||
|
||||
mode SpectrumCycle;
|
||||
SpectrumCycle.name = "Spectrum Cycle";
|
||||
SpectrumCycle.value = ASRLED_MODE_SPECTRUM_CYCLE;
|
||||
SpectrumCycle.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
SpectrumCycle.speed_min = ASRLED_SPEED_MIN;
|
||||
SpectrumCycle.speed_max = ASRLED_SPEED_MAX;
|
||||
SpectrumCycle.speed = ASRLED_SPEED_DEFAULT;
|
||||
SpectrumCycle.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(SpectrumCycle);
|
||||
|
||||
mode Random;
|
||||
Random.name = "Random";
|
||||
Random.value = ASRLED_MODE_RANDOM;
|
||||
Random.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Random.speed_min = ASRLED_SPEED_MIN;
|
||||
Random.speed_max = ASRLED_SPEED_MAX;
|
||||
Random.speed = ASRLED_SPEED_DEFAULT;
|
||||
Random.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Random);
|
||||
|
||||
mode Music;
|
||||
Music.name = "Music";
|
||||
Music.value = ASRLED_MODE_MUSIC;
|
||||
Music.flags = MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Music.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Music);
|
||||
|
||||
mode Wave;
|
||||
Wave.name = "Wave";
|
||||
Wave.value = ASRLED_MODE_WAVE;
|
||||
Wave.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Wave.speed_min = ASRLED_SPEED_MIN;
|
||||
Wave.speed_max = ASRLED_SPEED_MAX;
|
||||
Wave.speed = ASRLED_SPEED_DEFAULT;
|
||||
Wave.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Wave);
|
||||
|
||||
SetupZones();
|
||||
}
|
||||
|
||||
RGBController_ASRockASRRGBSMBus::~RGBController_ASRockASRRGBSMBus()
|
||||
{
|
||||
delete controller;
|
||||
}
|
||||
|
||||
void RGBController_ASRockASRRGBSMBus::SetupZones()
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| ASR LED motherboards only have a single zone/LED |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Set up zones |
|
||||
\*---------------------------------------------------------*/
|
||||
zone* new_zone = new zone();
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Set single zone name to "Motherboard" |
|
||||
\*---------------------------------------------------------*/
|
||||
new_zone->name = "Motherboard";
|
||||
new_zone->type = ZONE_TYPE_SINGLE;
|
||||
new_zone->leds_min = 1;
|
||||
new_zone->leds_max = 1;
|
||||
new_zone->leds_count = 1;
|
||||
new_zone->matrix_map = NULL;
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Push new zone to zones vector |
|
||||
\*---------------------------------------------------------*/
|
||||
zones.push_back(*new_zone);
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Set up LEDs |
|
||||
\*---------------------------------------------------------*/
|
||||
led* new_led = new led();
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Set single LED name to "Motherboard" |
|
||||
\*---------------------------------------------------------*/
|
||||
new_led->name = "Motherboard";
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Push new LED to LEDs vector |
|
||||
\*---------------------------------------------------------*/
|
||||
leds.push_back(*new_led);
|
||||
|
||||
SetupColors();
|
||||
}
|
||||
|
||||
void RGBController_ASRockASRRGBSMBus::ResizeZone(int /*zone*/, int /*new_size*/)
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| This device does not support resizing zones |
|
||||
\*---------------------------------------------------------*/
|
||||
}
|
||||
|
||||
void RGBController_ASRockASRRGBSMBus::DeviceUpdateLEDs()
|
||||
{
|
||||
for(unsigned int led = 0; led < colors.size(); led++)
|
||||
{
|
||||
UpdateSingleLED(led);
|
||||
}
|
||||
}
|
||||
|
||||
void RGBController_ASRockASRRGBSMBus::UpdateZoneLEDs(int /*zone*/)
|
||||
{
|
||||
DeviceUpdateLEDs();
|
||||
}
|
||||
|
||||
void RGBController_ASRockASRRGBSMBus::UpdateSingleLED(int led)
|
||||
{
|
||||
unsigned char red = RGBGetRValue(colors[led]);
|
||||
unsigned char grn = RGBGetGValue(colors[led]);
|
||||
unsigned char blu = RGBGetBValue(colors[led]);
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| If the LED value is non-zero, this LED overrides the LED |
|
||||
| index |
|
||||
\*---------------------------------------------------------*/
|
||||
if(leds[led].value != 0)
|
||||
{
|
||||
led = leds[led].value;
|
||||
}
|
||||
|
||||
controller->SetColorsAndSpeed(led, red, grn, blu);
|
||||
}
|
||||
|
||||
void RGBController_ASRockASRRGBSMBus::DeviceUpdateMode()
|
||||
{
|
||||
|
||||
controller->SetMode(0, modes[active_mode].value, modes[active_mode].speed);
|
||||
|
||||
DeviceUpdateLEDs();
|
||||
}
|
||||
+35
@@ -0,0 +1,35 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_ASRRGBSMBus.h |
|
||||
| |
|
||||
| RGBController for SMBus ASRock ASR RGB motherboards |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 15 Dec 2019 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "RGBController.h"
|
||||
#include "ASRockASRRGBSMBusController.h"
|
||||
|
||||
class RGBController_ASRockASRRGBSMBus : public RGBController
|
||||
{
|
||||
public:
|
||||
RGBController_ASRockASRRGBSMBus(ASRockASRRGBSMBusController* controller_ptr);
|
||||
~RGBController_ASRockASRRGBSMBus();
|
||||
|
||||
void SetupZones();
|
||||
|
||||
void ResizeZone(int zone, int new_size);
|
||||
|
||||
void DeviceUpdateLEDs();
|
||||
void UpdateZoneLEDs(int zone);
|
||||
void UpdateSingleLED(int led);
|
||||
|
||||
void DeviceUpdateMode();
|
||||
|
||||
private:
|
||||
ASRockASRRGBSMBusController* controller;
|
||||
};
|
||||
+310
@@ -0,0 +1,310 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| ASRockPolychromeV1SMBusController.cpp |
|
||||
| |
|
||||
| Driver for SMBus ASRock Polychrome V1 motherboards |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 14 Dec 2019 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include <cstring>
|
||||
#include "ASRockPolychromeV1SMBusController.h"
|
||||
#include "dmiinfo.h"
|
||||
#include "LogManager.h"
|
||||
|
||||
#define ASROCK_ZONE_LED_COUNT_MESSAGE_EN "[%s] Zone %i LED count: %02d"
|
||||
|
||||
using namespace std::chrono_literals;
|
||||
|
||||
ASRockPolychromeV1SMBusController::ASRockPolychromeV1SMBusController(i2c_smbus_interface* bus, polychrome_dev_id dev)
|
||||
{
|
||||
this->bus = bus;
|
||||
this->dev = dev;
|
||||
|
||||
DMIInfo dmi;
|
||||
device_name = "ASRock " + dmi.getMainboard();
|
||||
|
||||
ReadLEDConfiguration();
|
||||
}
|
||||
|
||||
ASRockPolychromeV1SMBusController::~ASRockPolychromeV1SMBusController()
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
std::string ASRockPolychromeV1SMBusController::GetDeviceLocation()
|
||||
{
|
||||
std::string return_string(bus->device_name);
|
||||
char addr[5];
|
||||
snprintf(addr, 5, "0x%02X", dev);
|
||||
return_string.append(", address ");
|
||||
return_string.append(addr);
|
||||
return("I2C: " + return_string);
|
||||
}
|
||||
|
||||
std::string ASRockPolychromeV1SMBusController::GetDeviceName()
|
||||
{
|
||||
return(device_name);
|
||||
}
|
||||
|
||||
std::string ASRockPolychromeV1SMBusController::GetFirmwareVersion()
|
||||
{
|
||||
uint8_t major_version = fw_version >> 8;
|
||||
uint8_t minor_version = fw_version & 0xFF;
|
||||
|
||||
return(std::to_string(major_version) + "." + std::to_string(minor_version));
|
||||
}
|
||||
|
||||
void ASRockPolychromeV1SMBusController::ReadLEDConfiguration()
|
||||
{
|
||||
/*---------------------------------------------------------------------------------*\
|
||||
| The LED configuration register holds 6 bytes, so the first read should return 6 |
|
||||
| If not, set all zone sizes to zero |
|
||||
\*---------------------------------------------------------------------------------*/
|
||||
LOG_DEBUG("[%s] Reading Zone sizes from controller", device_name.c_str());
|
||||
uint8_t asrock_zone_count[I2C_SMBUS_BLOCK_MAX] = { 0x0, 0x0, 0x0, 0x0, 0x0, 0x0 };
|
||||
if (bus->i2c_smbus_read_block_data(dev, POLYCHROME_V1_REG_ZONE_SIZE, asrock_zone_count) == 0x06)
|
||||
{
|
||||
zone_led_count[POLYCHROME_V1_ZONE_1] = asrock_zone_count[0];
|
||||
zone_led_count[POLYCHROME_V1_ZONE_2] = asrock_zone_count[1];
|
||||
zone_led_count[POLYCHROME_V1_ZONE_3] = asrock_zone_count[2];
|
||||
zone_led_count[POLYCHROME_V1_ZONE_4] = asrock_zone_count[3];
|
||||
zone_led_count[POLYCHROME_V1_ZONE_5] = asrock_zone_count[4];
|
||||
zone_led_count[POLYCHROME_V1_ZONE_ADDRESSABLE] = asrock_zone_count[5];
|
||||
LOG_DEBUG(ASROCK_ZONE_LED_COUNT_MESSAGE_EN, device_name.c_str(), POLYCHROME_V1_ZONE_1, zone_led_count[POLYCHROME_V1_ZONE_1]);
|
||||
LOG_DEBUG(ASROCK_ZONE_LED_COUNT_MESSAGE_EN, device_name.c_str(), POLYCHROME_V1_ZONE_2, zone_led_count[POLYCHROME_V1_ZONE_2]);
|
||||
LOG_DEBUG(ASROCK_ZONE_LED_COUNT_MESSAGE_EN, device_name.c_str(), POLYCHROME_V1_ZONE_3, zone_led_count[POLYCHROME_V1_ZONE_3]);
|
||||
LOG_DEBUG(ASROCK_ZONE_LED_COUNT_MESSAGE_EN, device_name.c_str(), POLYCHROME_V1_ZONE_4, zone_led_count[POLYCHROME_V1_ZONE_4]);
|
||||
LOG_DEBUG(ASROCK_ZONE_LED_COUNT_MESSAGE_EN, device_name.c_str(), POLYCHROME_V1_ZONE_5, zone_led_count[POLYCHROME_V1_ZONE_5]);
|
||||
LOG_DEBUG("[%s] Addressable Zone LED count: %02d", device_name.c_str(), zone_led_count[POLYCHROME_V1_ZONE_ADDRESSABLE]);
|
||||
}
|
||||
else
|
||||
{
|
||||
LOG_WARNING("[%s] LED config read failed", device_name.c_str());
|
||||
memset(zone_led_count, 0, sizeof(zone_led_count));
|
||||
}
|
||||
}
|
||||
|
||||
uint8_t ASRockPolychromeV1SMBusController::GetARGBColorOrder()
|
||||
{
|
||||
uint8_t temp[1] = { 0x00 };
|
||||
LOG_TRACE("[%s] Reading ARGB color order config from the controller", device_name.c_str());
|
||||
|
||||
//Read the data
|
||||
if(bus->i2c_smbus_read_block_data(dev, POLYCHROME_V1_REG_ARGB_GRB, temp) == 0x01)
|
||||
{
|
||||
if(temp[0] == 1)
|
||||
{
|
||||
LOG_DEBUG("[%s] Color order is GRB for the ARGB header", device_name.c_str());
|
||||
}
|
||||
else
|
||||
{
|
||||
LOG_DEBUG("[%s] Color order is RGB for the ARGB header", device_name.c_str());
|
||||
}
|
||||
return temp[0];
|
||||
}
|
||||
else
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
RGBColor ASRockPolychromeV1SMBusController::GetZoneColor(uint8_t zone)
|
||||
{
|
||||
LOG_TRACE("[%s] Reading color from zone %02d", device_name.c_str(), zone);
|
||||
return zone_config[zone].color;
|
||||
}
|
||||
|
||||
uint8_t ASRockPolychromeV1SMBusController::GetZoneMode(uint8_t zone)
|
||||
{
|
||||
LOG_TRACE("[%s] Retreving mode %02X from zone_modes for zone %02d", device_name.c_str(), zone_config[zone].mode, zone);
|
||||
return(zone_config[zone].mode);
|
||||
}
|
||||
|
||||
void ASRockPolychromeV1SMBusController::LoadZoneConfig()
|
||||
{
|
||||
uint8_t zone[1] = { 0x00 };
|
||||
uint8_t mode[1] = { 0xFF };
|
||||
uint8_t color_speed_pkt[4] = { 0, 0, 0, 0 };
|
||||
|
||||
LOG_TRACE("[%s] Reading modes from all zones", device_name.c_str());
|
||||
//Polychrome v1 supports per zone modes so we need to set the zone before we can read the mode.
|
||||
//Write the zone index.
|
||||
|
||||
for(uint8_t zone_idx = 0 ; zone_idx < POLYCHROME_V1_ZONE_COUNT; zone_idx ++)
|
||||
{
|
||||
if(zone_led_count[zone_idx] > 0)
|
||||
{
|
||||
zone[0] = zone_idx;
|
||||
bus->i2c_smbus_write_block_data(dev, POLYCHROME_V1_REG_ZONE_SELECT, 1, zone);
|
||||
|
||||
//Read the data back.
|
||||
if(bus->i2c_smbus_read_block_data(dev, POLYCHROME_V1_REG_ZONE_SELECT, zone) == 0x01)
|
||||
{
|
||||
//Validate that we changed correctly.
|
||||
if(zone[0] == zone_idx)
|
||||
{
|
||||
//Read the mode for the zone.
|
||||
if(bus->i2c_smbus_read_block_data(dev, POLYCHROME_V1_REG_MODE, mode) == 0x01)
|
||||
{
|
||||
LOG_DEBUG("[%s] Mode 0x%02x for zone %02d", device_name.c_str(), mode[0], zone_idx);
|
||||
zone_config[zone_idx].mode = mode[0];
|
||||
|
||||
bus->i2c_smbus_read_block_data(dev, zone_config[zone_idx].mode, color_speed_pkt);
|
||||
|
||||
zone_config[zone_idx].color = color_speed_pkt[0] << 16 | color_speed_pkt[1] << 8 | color_speed_pkt[2];
|
||||
zone_config[zone_idx].speed = color_speed_pkt [3];
|
||||
|
||||
LOG_TRACE("[%s] Mode config: %06X, %02X", device_name.c_str(), zone_config[zone_idx].color, zone_config[zone_idx].speed );
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
LOG_WARNING("[%s] Zone mode register failed to change!", device_name.c_str() );
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
zone_config[zone_idx].mode = 0;
|
||||
zone_config[zone_idx].color = 0;
|
||||
zone_config[zone_idx].speed = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void ASRockPolychromeV1SMBusController::SetARGBColorOrder(bool value)
|
||||
{
|
||||
uint8_t temp[1] = { 0x00 };
|
||||
|
||||
LOG_TRACE("[%s] Setting ARGB color order config to the controller", device_name.c_str());
|
||||
|
||||
temp[0] = (value) ? 0x01 : 0x00;
|
||||
bus->i2c_smbus_write_block_data(dev, POLYCHROME_V1_REG_ARGB_GRB, 1, temp);
|
||||
GetARGBColorOrder();
|
||||
}
|
||||
|
||||
bool ASRockPolychromeV1SMBusController::SetARGBSize(uint8_t new_size)
|
||||
{
|
||||
LOG_DEBUG("[%s] Setting ARGB header to %02d.", device_name.c_str(), new_size);
|
||||
|
||||
uint8_t asrock_zone_count[6] = { 0x0 };
|
||||
uint8_t new_asrock_zone_count[6] = { 0x0 };
|
||||
|
||||
//memcpy(new_asrock_zone_count, zone_led_count, sizeof(new_asrock_zone_count - 1));
|
||||
new_asrock_zone_count[POLYCHROME_V1_ZONE_1] = zone_led_count[POLYCHROME_V1_ZONE_1];
|
||||
new_asrock_zone_count[POLYCHROME_V1_ZONE_2] = zone_led_count[POLYCHROME_V1_ZONE_2];
|
||||
new_asrock_zone_count[POLYCHROME_V1_ZONE_3] = zone_led_count[POLYCHROME_V1_ZONE_3];
|
||||
new_asrock_zone_count[POLYCHROME_V1_ZONE_4] = zone_led_count[POLYCHROME_V1_ZONE_4];
|
||||
new_asrock_zone_count[POLYCHROME_V1_ZONE_5] = zone_led_count[POLYCHROME_V1_ZONE_5];
|
||||
new_asrock_zone_count[POLYCHROME_V1_ZONE_ADDRESSABLE] = new_size;
|
||||
|
||||
//Write the new config to the register
|
||||
bus->i2c_smbus_write_block_data(dev, POLYCHROME_V1_REG_ZONE_SIZE, 6, new_asrock_zone_count);
|
||||
|
||||
//Validate the write
|
||||
if (bus->i2c_smbus_read_block_data(dev, POLYCHROME_V1_REG_ZONE_SIZE, asrock_zone_count) == 0x06)
|
||||
{
|
||||
for (uint8_t i = 0; i < 6; i++)
|
||||
{
|
||||
if (new_asrock_zone_count[i] != asrock_zone_count[i])
|
||||
{
|
||||
LOG_WARNING("[%s] Failed to validate zone %02d size!", device_name.c_str(), i);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
LOG_DEBUG("[%s] Zone configuration validation completed.", device_name.c_str());
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
void ASRockPolychromeV1SMBusController::SetColorsAndSpeed(uint8_t zone, uint8_t red, uint8_t green, uint8_t blue)
|
||||
{
|
||||
LOG_TRACE("[%s] Updating color and speed for zone %02d: 0x%06X", device_name.c_str(), zone, (red << 16 | green << 8 | blue));
|
||||
uint8_t color_speed_pkt[4] = { red, green, blue, zone_config[zone].speed };
|
||||
uint8_t select_zone_pkt[1] = { zone };
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Select Zone |
|
||||
\*-----------------------------------------------------*/
|
||||
if(zone_config[zone].mode != POLYCHROME_V1_MODE_OFF)
|
||||
{
|
||||
bus->i2c_smbus_write_block_data(dev, POLYCHROME_V1_REG_ZONE_SELECT, 1, select_zone_pkt);
|
||||
std::this_thread::sleep_for(1ms);
|
||||
}
|
||||
|
||||
switch(zone_config[zone].mode)
|
||||
{
|
||||
/*-----------------------------------------------------*\
|
||||
| These modes take 4 bytes in R/G/B/S order |
|
||||
\*-----------------------------------------------------*/
|
||||
case POLYCHROME_V1_MODE_BREATHING:
|
||||
case POLYCHROME_V1_MODE_STROBE:
|
||||
case POLYCHROME_V1_MODE_SPECTRUM_CYCLE:
|
||||
case POLYCHROME_V1_MODE_SPRING:
|
||||
case POLYCHROME_V1_MODE_METEOR:
|
||||
case POLYCHROME_V1_MODE_STACK:
|
||||
case POLYCHROME_V1_MODE_CRAM:
|
||||
case POLYCHROME_V1_MODE_SCAN:
|
||||
case POLYCHROME_V1_MODE_NEON:
|
||||
case POLYCHROME_V1_MODE_WATER:
|
||||
|
||||
bus->i2c_smbus_write_block_data(dev, zone_config[zone].mode, 4, color_speed_pkt);
|
||||
break;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| These modes take 3 bytes in R/G/B order |
|
||||
\*-----------------------------------------------------*/
|
||||
default:
|
||||
case POLYCHROME_V1_MODE_STATIC:
|
||||
case POLYCHROME_V1_MODE_MUSIC:
|
||||
bus->i2c_smbus_write_block_data(dev, zone_config[zone].mode, 3, color_speed_pkt);
|
||||
break;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| These modes take 1 byte - speed |
|
||||
\*-----------------------------------------------------*/
|
||||
case POLYCHROME_V1_MODE_RANDOM:
|
||||
case POLYCHROME_V1_MODE_WAVE:
|
||||
case POLYCHROME_V1_MODE_RAINBOW:
|
||||
bus->i2c_smbus_write_block_data(dev, zone_config[zone].mode, 1, &zone_config[zone].speed);
|
||||
break;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| These modes take no bytes |
|
||||
\*-----------------------------------------------------*/
|
||||
case POLYCHROME_V1_MODE_OFF:
|
||||
break;
|
||||
}
|
||||
std::this_thread::sleep_for(1ms);
|
||||
|
||||
}
|
||||
|
||||
void ASRockPolychromeV1SMBusController::SetMode(uint8_t zone, uint8_t mode, uint8_t speed)
|
||||
{
|
||||
LOG_TRACE("[%s] Updating mode for zone %02d, Mode 0x%02X, Speed 0x%02X", device_name.c_str(), zone, mode, speed);
|
||||
uint8_t led_count_pkt[1] = { 0x00 };
|
||||
zone_config[zone].mode = mode;
|
||||
zone_config[zone].speed = speed;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Make sure set all register is set to 0 |
|
||||
\*-----------------------------------------------------*/
|
||||
bus->i2c_smbus_write_block_data(dev, POLYCHROME_V1_REG_SET_ALL, 1, led_count_pkt);
|
||||
std::this_thread::sleep_for(1ms);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set the zone we are working on |
|
||||
\*-----------------------------------------------------*/
|
||||
bus->i2c_smbus_write_block_data(dev, POLYCHROME_V1_REG_ZONE_SELECT, 1, &zone);
|
||||
std::this_thread::sleep_for(1ms);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Write the mode |
|
||||
\*-----------------------------------------------------*/
|
||||
bus->i2c_smbus_write_block_data(dev, POLYCHROME_V1_REG_MODE, 1, &zone_config[zone].mode);
|
||||
std::this_thread::sleep_for(1ms);
|
||||
}
|
||||
+160
@@ -0,0 +1,160 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| ASRockPolychromeV1SMBusController.h |
|
||||
| |
|
||||
| Driver for SMBus ASRock Polychrome V1 motherboards |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 13 Dec 2019 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <string>
|
||||
#include "i2c_smbus.h"
|
||||
#include "RGBController.h"
|
||||
|
||||
typedef uint8_t polychrome_dev_id;
|
||||
|
||||
#define ASROCK_V1_CONTROLLER_NAME "ASRock Polychrome v1 SMBus Controller"
|
||||
|
||||
enum
|
||||
{
|
||||
/*------------------------------------------------------------------------------------------*\
|
||||
| ASRock Polychrome v1 Registers |
|
||||
\*------------------------------------------------------------------------------------------*/
|
||||
POLYCHROME_V1_REG_FIRMWARE_VER = 0x00, /* Firmware version Major.Minor */
|
||||
POLYCHROME_V1_REG_MODE = 0x30, /* Mode selection register */
|
||||
POLYCHROME_V1_REG_ZONE_SELECT = 0x31, /* Zone selection register */
|
||||
POLYCHROME_V1_REG_SET_ALL = 0x32, /* Set All register 0x1 = set all */
|
||||
POLYCHROME_V1_REG_ZONE_SIZE = 0x33, /* Zone size configuration register */
|
||||
POLYCHROME_V1_REG_ARGB_GRB = 0x35, /* ARGB bitstream reversing register */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
POLYCHROME_V1_ZONE_1 = 0x00, /* RGB LED 1 Header */
|
||||
POLYCHROME_V1_ZONE_2 = 0x01, /* RGB LED 2 Header */
|
||||
POLYCHROME_V1_ZONE_3 = 0x02, /* PCH Zone */
|
||||
POLYCHROME_V1_ZONE_4 = 0x03, /* IO Cover Zone */
|
||||
POLYCHROME_V1_ZONE_5 = 0x04, /* Audio Zone LEDs */
|
||||
POLYCHROME_V1_ZONE_ADDRESSABLE = 0x05, /* Addressable LED header */
|
||||
POLYCHROME_V1_ZONE_COUNT = 0x06, /* Total number of zones */
|
||||
POLYCHROME_V1_ZONE_ADDRESSABLE_MAX = 0x64, /* Maximum number of ARGB LEDs */
|
||||
};
|
||||
|
||||
/*----------------------------------------------------------------------------------------------*\
|
||||
| Definitions for Polychrome V1 |
|
||||
\*----------------------------------------------------------------------------------------------*/
|
||||
#define POLYCHROME_V1_NUM_MODES 16 /* Number of Polychrome V1 modes */
|
||||
|
||||
enum
|
||||
{
|
||||
POLYCHROME_V1_MODE_OFF = 0x10, /* OFF mode */
|
||||
POLYCHROME_V1_MODE_STATIC = 0x11, /* Static color mode */
|
||||
POLYCHROME_V1_MODE_BREATHING = 0x12, /* Breathing effect mode */
|
||||
POLYCHROME_V1_MODE_STROBE = 0x13, /* Strobe effect mode */
|
||||
POLYCHROME_V1_MODE_SPECTRUM_CYCLE = 0x14, /* Spectrum Cycle effect mode */
|
||||
POLYCHROME_V1_MODE_RANDOM = 0x15, /* Random effect mode */
|
||||
POLYCHROME_V1_MODE_MUSIC = 0x17, /* Music effect mode */
|
||||
POLYCHROME_V1_MODE_WAVE = 0x18, /* Wave effect mode */
|
||||
/*------------------------------------------------------------------------------------------*\
|
||||
| Modes only available on ARGB headers |
|
||||
\*------------------------------------------------------------------------------------------*/
|
||||
POLYCHROME_V1_MODE_SPRING = 0x19, /* Spring effect mode */
|
||||
POLYCHROME_V1_MODE_METEOR = 0x1A, /* Meteor effect mode */
|
||||
POLYCHROME_V1_MODE_STACK = 0x1B, /* Stack effect mode */
|
||||
POLYCHROME_V1_MODE_CRAM = 0x1C, /* Cram effect mode */
|
||||
POLYCHROME_V1_MODE_SCAN = 0x1D, /* Scan effect mode */
|
||||
POLYCHROME_V1_MODE_NEON = 0x1E, /* Neon effect mode */
|
||||
POLYCHROME_V1_MODE_WATER = 0x1F, /* Water effect mode */
|
||||
POLYCHROME_V1_MODE_RAINBOW = 0x20, /* Rainbow chase effect mode */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
/*------------------------------------------------------------------------------------------*\
|
||||
| POLYCHROME_V1_MODE_BREATHING |
|
||||
\*------------------------------------------------------------------------------------------*/
|
||||
POLYCHROME_V1_SPEED_MIN_BREATHING = 0x0A, /* Slowest speed */
|
||||
POLYCHROME_V1_SPEED_DEFAULT_BREATHING = 0x02, /* Default speed */
|
||||
POLYCHROME_V1_SPEED_MAX_BREATHING = 0x02, /* Fastest speed */
|
||||
/*------------------------------------------------------------------------------------------*\
|
||||
| POLYCHROME_V1_MODE_STROBE |
|
||||
\*------------------------------------------------------------------------------------------*/
|
||||
POLYCHROME_V1_SPEED_MIN_STROBE = 0xA0, /* Slowest speed */
|
||||
POLYCHROME_V1_SPEED_DEFAULT_STROBE = 0x14, /* Default speed */
|
||||
POLYCHROME_V1_SPEED_MAX_STROBE = 0x05, /* Fastest speed */
|
||||
/*------------------------------------------------------------------------------------------*\
|
||||
| POLYCHROME_V1_MODE_SPECTRUM_CYCLE |
|
||||
\*------------------------------------------------------------------------------------------*/
|
||||
POLYCHROME_V1_SPEED_MIN_CYCLE = 0xA0, /* Slowest speed */
|
||||
POLYCHROME_V1_SPEED_DEFAULT_CYCLE = 0x14, /* Default speed */
|
||||
POLYCHROME_V1_SPEED_MAX_CYCLE = 0x0A, /* Fastest speed */
|
||||
/*------------------------------------------------------------------------------------------*\
|
||||
| POLYCHROME_V1_MODE_RANDOM |
|
||||
\*------------------------------------------------------------------------------------------*/
|
||||
POLYCHROME_V1_SPEED_MIN_RANDOM = 0xA0, /* Slowest speed */
|
||||
POLYCHROME_V1_SPEED_DEFAULT_RANDOM = 0x28, /* Default speed */
|
||||
POLYCHROME_V1_SPEED_MAX_RANDOM = 0x05, /* Fastest speed */
|
||||
/*------------------------------------------------------------------------------------------*\
|
||||
| POLYCHROME_V1_MODE_WAVE |
|
||||
\*------------------------------------------------------------------------------------------*/
|
||||
POLYCHROME_V1_SPEED_MIN_WAVE = 0x06, /* Slowest speed */
|
||||
POLYCHROME_V1_SPEED_DEFAULT_WAVE = 0x02, /* Default speed */
|
||||
POLYCHROME_V1_SPEED_MAX_WAVE = 0x01, /* Fastest speed */
|
||||
POLYCHROME_V1_SPEED_DEFAULT_SPRING = 0x04, /* Default speed */
|
||||
POLYCHROME_V1_SPEED_DEFAULT_METEOR = 0x0A, /* Default speed */
|
||||
POLYCHROME_V1_SPEED_DEFAULT_STACK = 0x04, /* Default speed */
|
||||
POLYCHROME_V1_SPEED_DEFAULT_CRAM = 0x04, /* Default speed */
|
||||
POLYCHROME_V1_SPEED_DEFAULT_SCAN = 0x0A, /* Default speed */
|
||||
POLYCHROME_V1_SPEED_DEFAULT_NEON = 0x20, /* Default speed */
|
||||
POLYCHROME_V1_SPEED_DEFAULT_WATER = 0x0A, /* Default speed */
|
||||
/*------------------------------------------------------------------------------------------*\
|
||||
| POLYCHROME_V1_MODE_RAINBOW |
|
||||
\*------------------------------------------------------------------------------------------*/
|
||||
POLYCHROME_V1_SPEED_MIN_RAINBOW = 0x12, /* Slowest speed */
|
||||
POLYCHROME_V1_SPEED_DEFAULT_RAINBOW = 0x0A, /* Default speed */
|
||||
POLYCHROME_V1_SPEED_MAX_RAINBOW = 0x01, /* Fastest speed */
|
||||
POLYCHROME_V1_SPEED_MIN_ARGB = 0x20, /* Slowest speed */
|
||||
POLYCHROME_V1_SPEED_MAX_ARGB = 0x02, /* Fastest speed */
|
||||
};
|
||||
|
||||
struct zone_cfg
|
||||
{
|
||||
uint8_t mode;
|
||||
uint8_t speed;
|
||||
RGBColor color;
|
||||
};
|
||||
|
||||
class ASRockPolychromeV1SMBusController
|
||||
{
|
||||
public:
|
||||
ASRockPolychromeV1SMBusController(i2c_smbus_interface* bus, polychrome_dev_id dev);
|
||||
~ASRockPolychromeV1SMBusController();
|
||||
|
||||
std::string GetDeviceLocation();
|
||||
std::string GetDeviceName();
|
||||
std::string GetFirmwareVersion();
|
||||
|
||||
uint8_t GetARGBColorOrder();
|
||||
RGBColor GetZoneColor(uint8_t zone);
|
||||
uint8_t GetZoneMode(uint8_t zone);
|
||||
void LoadZoneConfig();
|
||||
void SetARGBColorOrder(bool value);
|
||||
bool SetARGBSize(uint8_t led_count);
|
||||
void SetColorsAndSpeed(uint8_t led, uint8_t red, uint8_t green, uint8_t blue);
|
||||
void SetMode(uint8_t zone, uint8_t mode, uint8_t speed);
|
||||
|
||||
uint8_t zone_led_count[6];
|
||||
zone_cfg zone_config[6];
|
||||
uint16_t fw_version;
|
||||
|
||||
private:
|
||||
std::string device_name;
|
||||
i2c_smbus_interface* bus;
|
||||
polychrome_dev_id dev;
|
||||
|
||||
void ReadLEDConfiguration();
|
||||
};
|
||||
+349
@@ -0,0 +1,349 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_ASRockPolychromeV1SMBus.cpp |
|
||||
| |
|
||||
| RGBController for SMBus ASRock Polychrome V1 |
|
||||
| motherboards |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 15 Dec 2019 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "LogManager.h"
|
||||
#include "RGBController_ASRockPolychromeV1SMBus.h"
|
||||
|
||||
static const char* polychrome_v1_zone_names[] =
|
||||
{
|
||||
"RGB LED 1 Header",
|
||||
"RGB LED 2 Header",
|
||||
"PCH",
|
||||
"IO Cover",
|
||||
"Audio",
|
||||
"Addressable Header"
|
||||
};
|
||||
|
||||
/**------------------------------------------------------------------*\
|
||||
@name ASRock Polychrome v1 SMBus
|
||||
@category Motherboard
|
||||
@type SMBus
|
||||
@save :robot:
|
||||
@direct :x:
|
||||
@effects :white_check_mark:
|
||||
@detectors DetectASRockSMBusControllers
|
||||
@comment ASRock Polychrome v1 controllers will save with each update.
|
||||
Per ARGB LED support is not possible with these devices.
|
||||
ARGB size and color order is set using the `ARGB Header Config mode`
|
||||
`Right` = GRB mode that is needed for WS2812B ARGB devices and `Left` = RGB used for WS2811 strips
|
||||
The modes speed slider will set the size of the header
|
||||
Spectrum Cycles uses the RGB values to set the individual color brightness.
|
||||
\*-------------------------------------------------------------------*/
|
||||
|
||||
RGBController_ASRockPolychromeV1SMBus::RGBController_ASRockPolychromeV1SMBus(ASRockPolychromeV1SMBusController* controller_ptr)
|
||||
{
|
||||
controller = controller_ptr;
|
||||
|
||||
name = controller->GetDeviceName();
|
||||
vendor = "ASRock";
|
||||
version = controller->GetFirmwareVersion();
|
||||
type = DEVICE_TYPE_MOTHERBOARD;
|
||||
description = "ASRock Polychrome v1 Device";
|
||||
location = controller->GetDeviceLocation();
|
||||
|
||||
|
||||
mode Off;
|
||||
Off.name = "Off";
|
||||
Off.value = POLYCHROME_V1_MODE_OFF;
|
||||
Off.flags = MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Off.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Off);
|
||||
|
||||
mode Static;
|
||||
Static.name = "Static";
|
||||
Static.value = POLYCHROME_V1_MODE_STATIC;
|
||||
Static.flags = MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Static.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Static);
|
||||
|
||||
mode Breathing;
|
||||
Breathing.name = "Breathing";
|
||||
Breathing.value = POLYCHROME_V1_MODE_BREATHING;
|
||||
Breathing.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Breathing.speed_min = POLYCHROME_V1_SPEED_MIN_BREATHING;
|
||||
Breathing.speed_max = POLYCHROME_V1_SPEED_MAX_BREATHING;
|
||||
Breathing.speed = POLYCHROME_V1_SPEED_DEFAULT_BREATHING;
|
||||
Breathing.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Breathing);
|
||||
|
||||
mode Strobe;
|
||||
Strobe.name = "Strobe";
|
||||
Strobe.value = POLYCHROME_V1_MODE_STROBE;
|
||||
Strobe.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Strobe.speed_min = POLYCHROME_V1_SPEED_MIN_STROBE;
|
||||
Strobe.speed_max = POLYCHROME_V1_SPEED_MAX_STROBE;
|
||||
Strobe.speed = POLYCHROME_V1_SPEED_DEFAULT_STROBE;
|
||||
Strobe.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Strobe);
|
||||
|
||||
mode SpectrumCycle;
|
||||
SpectrumCycle.name = "Spectrum Cycle";
|
||||
SpectrumCycle.value = POLYCHROME_V1_MODE_SPECTRUM_CYCLE;
|
||||
SpectrumCycle.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
SpectrumCycle.speed_min = POLYCHROME_V1_SPEED_MIN_CYCLE;
|
||||
SpectrumCycle.speed_max = POLYCHROME_V1_SPEED_MAX_CYCLE;
|
||||
SpectrumCycle.speed = POLYCHROME_V1_SPEED_DEFAULT_CYCLE;
|
||||
SpectrumCycle.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(SpectrumCycle);
|
||||
|
||||
mode Random;
|
||||
Random.name = "Random";
|
||||
Random.value = POLYCHROME_V1_MODE_RANDOM;
|
||||
Random.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Random.speed_min = POLYCHROME_V1_SPEED_MIN_RANDOM;
|
||||
Random.speed_max = POLYCHROME_V1_SPEED_MAX_RANDOM;
|
||||
Random.speed = POLYCHROME_V1_SPEED_DEFAULT_RANDOM;
|
||||
Random.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Random);
|
||||
|
||||
mode Music;
|
||||
Music.name = "Music";
|
||||
Music.value = POLYCHROME_V1_MODE_MUSIC;
|
||||
Music.flags = MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Music.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Music);
|
||||
|
||||
mode Wave;
|
||||
Wave.name = "Wave";
|
||||
Wave.value = POLYCHROME_V1_MODE_WAVE;
|
||||
Wave.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Wave.speed_min = POLYCHROME_V1_SPEED_MIN_WAVE;
|
||||
Wave.speed_max = POLYCHROME_V1_SPEED_MAX_WAVE;
|
||||
Wave.speed = POLYCHROME_V1_SPEED_DEFAULT_WAVE;
|
||||
Wave.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Wave);
|
||||
|
||||
/*---------------------------------------------------------------------*\
|
||||
| Comment out until per zone modes are working. These are only for ARGB |
|
||||
\*---------------------------------------------------------------------*/
|
||||
mode Spring;
|
||||
Spring.name = "Spring";
|
||||
Spring.value = POLYCHROME_V1_MODE_SPRING;
|
||||
Spring.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Spring.speed_min = POLYCHROME_V1_SPEED_MIN_ARGB;
|
||||
Spring.speed_max = POLYCHROME_V1_SPEED_MAX_ARGB;
|
||||
Spring.speed = POLYCHROME_V1_SPEED_DEFAULT_SPRING;
|
||||
Spring.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Spring);
|
||||
|
||||
mode Stack;
|
||||
Stack.name = "Stack";
|
||||
Stack.value = POLYCHROME_V1_MODE_STACK;
|
||||
Stack.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Stack.speed_min = POLYCHROME_V1_SPEED_MIN_ARGB;
|
||||
Stack.speed_max = POLYCHROME_V1_SPEED_MAX_ARGB;
|
||||
Stack.speed = POLYCHROME_V1_SPEED_DEFAULT_STACK;
|
||||
Stack.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Stack);
|
||||
|
||||
mode Cram;
|
||||
Cram.name = "Cram";
|
||||
Cram.value = POLYCHROME_V1_MODE_CRAM;
|
||||
Cram.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Cram.speed_min = POLYCHROME_V1_SPEED_MIN_ARGB;
|
||||
Cram.speed_max = POLYCHROME_V1_SPEED_MAX_ARGB;
|
||||
Cram.speed = POLYCHROME_V1_SPEED_DEFAULT_CRAM;
|
||||
Cram.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Cram);
|
||||
|
||||
mode Scan;
|
||||
Scan.name = "Scan";
|
||||
Scan.value = POLYCHROME_V1_MODE_SCAN;
|
||||
Scan.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Scan.speed_min = POLYCHROME_V1_SPEED_MIN_ARGB;
|
||||
Scan.speed_max = POLYCHROME_V1_SPEED_MAX_ARGB;
|
||||
Scan.speed = POLYCHROME_V1_SPEED_DEFAULT_SCAN;
|
||||
Scan.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Scan);
|
||||
|
||||
mode Neon;
|
||||
Neon.name = "Neon";
|
||||
Neon.value = POLYCHROME_V1_MODE_NEON;
|
||||
Neon.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Neon.speed_min = POLYCHROME_V1_SPEED_MIN_ARGB;
|
||||
Neon.speed_max = POLYCHROME_V1_SPEED_MAX_ARGB;
|
||||
Neon.speed = POLYCHROME_V1_SPEED_DEFAULT_NEON;
|
||||
Neon.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Neon);
|
||||
|
||||
mode Water;
|
||||
Water.name = "Water";
|
||||
Water.value = POLYCHROME_V1_MODE_WATER;
|
||||
Water.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Water.speed_min = POLYCHROME_V1_SPEED_MIN_ARGB;
|
||||
Water.speed_max = POLYCHROME_V1_SPEED_MAX_ARGB;
|
||||
Water.speed = POLYCHROME_V1_SPEED_DEFAULT_WATER;
|
||||
Water.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Water);
|
||||
|
||||
mode Rainbow;
|
||||
Rainbow.name = "Rainbow";
|
||||
Rainbow.value = POLYCHROME_V1_MODE_RAINBOW;
|
||||
Rainbow.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Rainbow.speed_min = POLYCHROME_V1_SPEED_MIN_RAINBOW;
|
||||
Rainbow.speed_max = POLYCHROME_V1_SPEED_MAX_RAINBOW;
|
||||
Rainbow.speed = POLYCHROME_V1_SPEED_DEFAULT_RAINBOW;
|
||||
Rainbow.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Rainbow);
|
||||
|
||||
/*---------------------------------------------------------------------*\
|
||||
| This ARGB_Config section is a hack to allow users to configure the |
|
||||
| RGB vs GRB mode using the direction of the mode as well as set the |
|
||||
| size of the devices connected to the header using the brightness |
|
||||
| value. |
|
||||
| |
|
||||
| The mode should be removed onece the device settings are avaiable. |
|
||||
\*---------------------------------------------------------------------*/
|
||||
mode ARGB_Config;
|
||||
ARGB_Config.name = "ARGB Header Config";
|
||||
ARGB_Config.value = POLYCHROME_V1_REG_ARGB_GRB;
|
||||
ARGB_Config.flags = MODE_FLAG_HAS_DIRECTION_LR | MODE_FLAG_HAS_SPEED | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
ARGB_Config.speed = controller->zone_led_count[POLYCHROME_V1_ZONE_ADDRESSABLE];
|
||||
ARGB_Config.speed_min = 1;
|
||||
ARGB_Config.speed_max = POLYCHROME_V1_ZONE_ADDRESSABLE_MAX;
|
||||
ARGB_Config.direction = controller -> GetARGBColorOrder();
|
||||
ARGB_Config.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(ARGB_Config);
|
||||
|
||||
SetupZones();
|
||||
|
||||
controller->LoadZoneConfig();
|
||||
active_mode = getModeIndex(controller->zone_config[0].mode); // Hard coding zone 0 until per zone modes are available.
|
||||
|
||||
if(active_mode != POLYCHROME_V1_MODE_OFF)
|
||||
{
|
||||
for( uint8_t zone_idx = 0; zone_idx < zoneIndexMap.size(); zone_idx++)
|
||||
{
|
||||
zones[zone_idx].colors[0] = controller->GetZoneColor(zoneIndexMap[zone_idx]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
RGBController_ASRockPolychromeV1SMBus::~RGBController_ASRockPolychromeV1SMBus()
|
||||
{
|
||||
delete controller;
|
||||
}
|
||||
|
||||
uint8_t RGBController_ASRockPolychromeV1SMBus::getModeIndex(uint8_t mode_value)
|
||||
{
|
||||
for(uint8_t mode_index = 0; mode_index < modes.size(); mode_index++)
|
||||
{
|
||||
if (modes[mode_index].value == mode_value)
|
||||
{
|
||||
return mode_index;
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
void RGBController_ASRockPolychromeV1SMBus::SetupZones()
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| Polychrome motherboards should set up zones based on LED |
|
||||
| configuration register read from device |
|
||||
\*---------------------------------------------------------*/
|
||||
/*---------------------------------------------------------*\
|
||||
| Set up zones |
|
||||
\*---------------------------------------------------------*/
|
||||
for(uint8_t zone_idx = 0; zone_idx < POLYCHROME_V1_ZONE_COUNT; zone_idx++)
|
||||
{
|
||||
if(controller->zone_led_count[zone_idx] > 0)
|
||||
{
|
||||
zone* new_zone = new zone();
|
||||
/*---------------------------------------------------------*\
|
||||
| Set zone name to channel name |
|
||||
\*---------------------------------------------------------*/
|
||||
new_zone->name = polychrome_v1_zone_names[zone_idx];
|
||||
new_zone->type = ZONE_TYPE_SINGLE;
|
||||
new_zone->leds_min = 1;
|
||||
new_zone->leds_max = 1;
|
||||
new_zone->leds_count = 1;
|
||||
new_zone->matrix_map = NULL;
|
||||
|
||||
if(zone_idx == POLYCHROME_V1_ZONE_ADDRESSABLE)
|
||||
{
|
||||
new_zone->leds_max = POLYCHROME_V1_ZONE_ADDRESSABLE_MAX;
|
||||
}
|
||||
/*---------------------------------------------------------*\
|
||||
| Push new zone to zones vector |
|
||||
\*---------------------------------------------------------*/
|
||||
zones.push_back(*new_zone);
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Each zone only has one LED |
|
||||
\*---------------------------------------------------------*/
|
||||
led* new_led = new led();
|
||||
|
||||
new_led->name = polychrome_v1_zone_names[zone_idx];
|
||||
new_led->value = zone_idx;
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Push new LED to LEDs vector |
|
||||
\*---------------------------------------------------------*/
|
||||
leds.push_back(*new_led);
|
||||
zoneIndexMap.push_back(zone_idx);
|
||||
}
|
||||
}
|
||||
|
||||
SetupColors();
|
||||
}
|
||||
|
||||
void RGBController_ASRockPolychromeV1SMBus::ResizeZone(int zone, int new_size)
|
||||
{
|
||||
LOG_TRACE("[%s] ResizeZone(%02X, %02X)", name.c_str(), zone, new_size);
|
||||
controller-> SetARGBSize(new_size & 0xFF);
|
||||
zones[POLYCHROME_V1_ZONE_ADDRESSABLE].leds_count = 1;
|
||||
}
|
||||
|
||||
void RGBController_ASRockPolychromeV1SMBus::DeviceUpdateLEDs()
|
||||
{
|
||||
LOG_TRACE("[%s] DeviceUpdateLEDs()", name.c_str());
|
||||
for (uint8_t zone_idx = 0; zone_idx < zoneIndexMap.size(); zone_idx++)
|
||||
{
|
||||
UpdateSingleLED(zone_idx);
|
||||
}
|
||||
}
|
||||
|
||||
void RGBController_ASRockPolychromeV1SMBus::UpdateZoneLEDs(int /*zone*/)
|
||||
{
|
||||
LOG_TRACE("[%s] UpdateZoneLEDs()", name.c_str());
|
||||
DeviceUpdateLEDs();
|
||||
}
|
||||
|
||||
void RGBController_ASRockPolychromeV1SMBus::UpdateSingleLED(int zone)
|
||||
{
|
||||
LOG_TRACE("[%s] UpdateSingleLED(%02X)", name.c_str(), zone);
|
||||
|
||||
uint8_t red = RGBGetRValue(colors[zone]);
|
||||
uint8_t grn = RGBGetGValue(colors[zone]);
|
||||
uint8_t blu = RGBGetBValue(colors[zone]);
|
||||
|
||||
controller->SetColorsAndSpeed(zoneIndexMap[zone], red, grn, blu);
|
||||
}
|
||||
|
||||
void RGBController_ASRockPolychromeV1SMBus::DeviceUpdateMode()
|
||||
{
|
||||
LOG_TRACE("[%s] DeviceUpdateMode()", name.c_str());
|
||||
if(modes[active_mode].value != POLYCHROME_V1_REG_ARGB_GRB)
|
||||
{
|
||||
for(uint8_t zone_idx = 0; zone_idx < zoneIndexMap.size(); zone_idx++)
|
||||
{
|
||||
controller->SetMode(zoneIndexMap[zone_idx], modes[active_mode].value, modes[active_mode].speed);
|
||||
UpdateSingleLED(zone_idx);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
controller-> SetARGBColorOrder(modes[active_mode].direction);
|
||||
controller-> SetARGBSize(modes[active_mode].speed);
|
||||
}
|
||||
}
|
||||
+38
@@ -0,0 +1,38 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_ASRockPolychromeV1SMBus.h |
|
||||
| |
|
||||
| RGBController for SMBus ASRock Polychrome V1 |
|
||||
| motherboards |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 15 Dec 2019 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "RGBController.h"
|
||||
#include "ASRockPolychromeV1SMBusController.h"
|
||||
|
||||
class RGBController_ASRockPolychromeV1SMBus : public RGBController
|
||||
{
|
||||
public:
|
||||
RGBController_ASRockPolychromeV1SMBus(ASRockPolychromeV1SMBusController* controller_ptr);
|
||||
~RGBController_ASRockPolychromeV1SMBus();
|
||||
|
||||
void SetupZones();
|
||||
|
||||
void ResizeZone(int zone, int new_size);
|
||||
|
||||
void DeviceUpdateLEDs();
|
||||
void UpdateZoneLEDs(int zone);
|
||||
void UpdateSingleLED(int led);
|
||||
|
||||
void DeviceUpdateMode();
|
||||
|
||||
private:
|
||||
ASRockPolychromeV1SMBusController* controller;
|
||||
uint8_t getModeIndex(uint8_t mode_value);
|
||||
std::vector<uint8_t> zoneIndexMap;
|
||||
};
|
||||
+158
@@ -0,0 +1,158 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| ASRockPolychromeV2SMBusController.cpp |
|
||||
| |
|
||||
| Driver for SMBus ASRock Polychrome V2 motherboards |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 14 Dec 2019 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include <cstring>
|
||||
#include "ASRockPolychromeV2SMBusController.h"
|
||||
#include "dmiinfo.h"
|
||||
#include "LogManager.h"
|
||||
|
||||
#define ASROCK_ZONE_LED_COUNT_MESSAGE_EN "[%s] Zone %i LED count: %02d"
|
||||
|
||||
using namespace std::chrono_literals;
|
||||
|
||||
ASRockPolychromeV2SMBusController::ASRockPolychromeV2SMBusController(i2c_smbus_interface* bus, polychrome_dev_id dev)
|
||||
{
|
||||
this->bus = bus;
|
||||
this->dev = dev;
|
||||
|
||||
DMIInfo dmi;
|
||||
|
||||
device_name = "ASRock " + dmi.getMainboard();
|
||||
|
||||
ReadLEDConfiguration();
|
||||
}
|
||||
|
||||
ASRockPolychromeV2SMBusController::~ASRockPolychromeV2SMBusController()
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
std::string ASRockPolychromeV2SMBusController::GetDeviceLocation()
|
||||
{
|
||||
std::string return_string(bus->device_name);
|
||||
char addr[5];
|
||||
snprintf(addr, 5, "0x%02X", dev);
|
||||
return_string.append(", address ");
|
||||
return_string.append(addr);
|
||||
return("I2C: " + return_string);
|
||||
}
|
||||
|
||||
std::string ASRockPolychromeV2SMBusController::GetDeviceName()
|
||||
{
|
||||
return(device_name);
|
||||
}
|
||||
|
||||
std::string ASRockPolychromeV2SMBusController::GetFirmwareVersion()
|
||||
{
|
||||
uint8_t major_version = fw_version >> 8;
|
||||
uint8_t minor_version = fw_version & 0xFF;
|
||||
|
||||
return(std::to_string(major_version) + "." + std::to_string(minor_version));
|
||||
}
|
||||
|
||||
|
||||
void ASRockPolychromeV2SMBusController::ReadLEDConfiguration()
|
||||
{
|
||||
/*---------------------------------------------------------------------------------*\
|
||||
| The LED configuration register holds 6 bytes, so the first read should return 6 |
|
||||
| If not, set all zone sizes to zero |
|
||||
\*---------------------------------------------------------------------------------*/
|
||||
LOG_DEBUG("[%s] Reading LED config from controller", device_name.c_str());
|
||||
uint8_t asrock_zone_count[I2C_SMBUS_BLOCK_MAX] = { 0x0, 0x0, 0x0, 0x0, 0x0, 0x0 };
|
||||
if (bus->i2c_smbus_read_block_data(dev, POLYCHROME_V2_REG_LED_CONFIG, asrock_zone_count) == 0x06)
|
||||
{
|
||||
zone_led_count[POLYCHROME_V2_ZONE_1] = asrock_zone_count[0];
|
||||
zone_led_count[POLYCHROME_V2_ZONE_2] = asrock_zone_count[1];
|
||||
zone_led_count[POLYCHROME_V2_ZONE_3] = asrock_zone_count[2];
|
||||
zone_led_count[POLYCHROME_V2_ZONE_4] = asrock_zone_count[3];
|
||||
zone_led_count[POLYCHROME_V2_ZONE_5] = asrock_zone_count[4];
|
||||
zone_led_count[POLYCHROME_V2_ZONE_ADDRESSABLE] = asrock_zone_count[5];
|
||||
LOG_DEBUG(ASROCK_ZONE_LED_COUNT_MESSAGE_EN, device_name.c_str(), POLYCHROME_V2_ZONE_1, zone_led_count[POLYCHROME_V2_ZONE_1]);
|
||||
LOG_DEBUG(ASROCK_ZONE_LED_COUNT_MESSAGE_EN, device_name.c_str(), POLYCHROME_V2_ZONE_2, zone_led_count[POLYCHROME_V2_ZONE_2]);
|
||||
LOG_DEBUG(ASROCK_ZONE_LED_COUNT_MESSAGE_EN, device_name.c_str(), POLYCHROME_V2_ZONE_3, zone_led_count[POLYCHROME_V2_ZONE_3]);
|
||||
LOG_DEBUG(ASROCK_ZONE_LED_COUNT_MESSAGE_EN, device_name.c_str(), POLYCHROME_V2_ZONE_4, zone_led_count[POLYCHROME_V2_ZONE_4]);
|
||||
LOG_DEBUG(ASROCK_ZONE_LED_COUNT_MESSAGE_EN, device_name.c_str(), POLYCHROME_V2_ZONE_5, zone_led_count[POLYCHROME_V2_ZONE_5]);
|
||||
LOG_DEBUG("[%s] Addressable Zone LED count: %02d", device_name.c_str(), zone_led_count[POLYCHROME_V2_ZONE_ADDRESSABLE]);
|
||||
}
|
||||
else
|
||||
{
|
||||
LOG_WARNING("[%s] LED config read failed", device_name.c_str());
|
||||
memset(zone_led_count, 0, sizeof(zone_led_count));
|
||||
}
|
||||
}
|
||||
|
||||
uint8_t ASRockPolychromeV2SMBusController::GetMode()
|
||||
{
|
||||
return(active_mode);
|
||||
}
|
||||
|
||||
void ASRockPolychromeV2SMBusController::SetColorsAndSpeed(uint8_t led, uint8_t red, uint8_t green, uint8_t blue)
|
||||
{
|
||||
uint8_t color_speed_pkt[4] = { red, green, blue, active_speed };
|
||||
uint8_t select_led_pkt[1] = { led };
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Select LED |
|
||||
\*-----------------------------------------------------*/
|
||||
switch(active_mode)
|
||||
{
|
||||
case POLYCHROME_V2_MODE_OFF:
|
||||
case POLYCHROME_V2_MODE_RAINBOW:
|
||||
case POLYCHROME_V2_MODE_SPECTRUM_CYCLE:
|
||||
break;
|
||||
|
||||
default:
|
||||
bus->i2c_smbus_write_block_data(dev, POLYCHROME_V2_REG_LED_SELECT, 1, select_led_pkt);
|
||||
std::this_thread::sleep_for(1ms);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Polychrome firmware always writes color to fixed reg |
|
||||
\*-----------------------------------------------------*/
|
||||
bus->i2c_smbus_write_block_data(dev, POLYCHROME_V2_REG_COLOR, 3, color_speed_pkt);
|
||||
std::this_thread::sleep_for(1ms);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void ASRockPolychromeV2SMBusController::SetMode(uint8_t zone,uint8_t mode, uint8_t speed)
|
||||
{
|
||||
uint8_t led_count_pkt[1] = { 0x00 };
|
||||
active_zone = zone;
|
||||
active_mode = mode;
|
||||
active_speed = speed;
|
||||
|
||||
bus->i2c_smbus_write_block_data(dev, POLYCHROME_V2_REG_MODE, 1, &active_mode);
|
||||
std::this_thread::sleep_for(1ms);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Select a single LED |
|
||||
\*-----------------------------------------------------*/
|
||||
bus->i2c_smbus_write_block_data(dev, POLYCHROME_V2_REG_LED_COUNT, 0, led_count_pkt);
|
||||
std::this_thread::sleep_for(1ms);
|
||||
|
||||
switch(active_mode)
|
||||
{
|
||||
/*-----------------------------------------------------*\
|
||||
| These modes don't take a speed |
|
||||
\*-----------------------------------------------------*/
|
||||
case POLYCHROME_V2_MODE_OFF:
|
||||
case POLYCHROME_V2_MODE_STATIC:
|
||||
break;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| All other modes, write speed to active mode register |
|
||||
\*-----------------------------------------------------*/
|
||||
default:
|
||||
bus->i2c_smbus_write_block_data(dev, active_mode, 1, &speed);
|
||||
std::this_thread::sleep_for(1ms);
|
||||
break;
|
||||
}
|
||||
}
|
||||
+146
@@ -0,0 +1,146 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| ASRockPolychromeV2SMBusController.h |
|
||||
| |
|
||||
| Driver for SMBus ASRock Polychrome V2 motherboards |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 13 Dec 2019 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <string>
|
||||
#include "i2c_smbus.h"
|
||||
|
||||
typedef uint8_t polychrome_dev_id;
|
||||
|
||||
#define ASROCK_V2_CONTROLLER_NAME "ASRock Polychrome v2 SMBus Controller"
|
||||
|
||||
enum
|
||||
{
|
||||
/*------------------------------------------------------------------------------------------*\
|
||||
| ASRock Polychrome v2 Registers |
|
||||
\*------------------------------------------------------------------------------------------*/
|
||||
POLYCHROME_V2_REG_FIRMWARE_VER = 0x00, /* Firmware version Major.Minor */
|
||||
POLYCHROME_V2_REG_MODE = 0x30, /* Mode selection register */
|
||||
POLYCHROME_V2_REG_LED_SELECT = 0x31, /* LED selection register */
|
||||
POLYCHROME_V2_REG_LED_COUNT = 0x32, /* Additional LED count register */
|
||||
POLYCHROME_V2_REG_LED_CONFIG = 0x33, /* LED configuration register */
|
||||
POLYCHROME_V2_REG_COLOR = 0x34, /* Color register: Red, Green, Blue */
|
||||
POLYCHROME_V2_REG_ARGB_GRB = 0x35, /* ARGB bistream reversing register */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
POLYCHROME_V2_ZONE_1 = 0x00, /* RGB LED 1 Header */
|
||||
POLYCHROME_V2_ZONE_2 = 0x01, /* RGB LED 2 Header */
|
||||
POLYCHROME_V2_ZONE_3 = 0x02, /* Audio/PCH Zone LEDs */
|
||||
POLYCHROME_V2_ZONE_4 = 0x03, /* Audio/PCH Zone LEDs */
|
||||
POLYCHROME_V2_ZONE_5 = 0x04, /* IO Cover Zone LEDs */
|
||||
POLYCHROME_V2_ZONE_ADDRESSABLE = 0x05, /* Addressable LED header */
|
||||
POLYCHROME_V2_ZONE_COUNT = 0x06, /* Total number of zones */
|
||||
POLYCHROME_V2_ZONE_ADDRESSABLE_MAX = 0x64, /* Maxinum number of ARGB LEDs */
|
||||
};
|
||||
|
||||
/*----------------------------------------------------------------------------------------------*\
|
||||
| Definitions for Polychrome V2 |
|
||||
\*----------------------------------------------------------------------------------------------*/
|
||||
#define POLYCHROME_V2_NUM_MODES 14 /* Number of Polychrome V2 modes */
|
||||
|
||||
enum
|
||||
{
|
||||
POLYCHROME_V2_MODE_OFF = 0x10, /* OFF mode */
|
||||
POLYCHROME_V2_MODE_STATIC = 0x11, /* Static color mode */
|
||||
POLYCHROME_V2_MODE_BREATHING = 0x12, /* Breating effect mode */
|
||||
POLYCHROME_V2_MODE_STROBE = 0x13, /* Strobe effect mode */
|
||||
POLYCHROME_V2_MODE_SPECTRUM_CYCLE = 0x14, /* Spectrum Cycle effect mode */
|
||||
POLYCHROME_V2_MODE_RANDOM = 0x15, /* Random effect mode */
|
||||
POLYCHROME_V2_MODE_WAVE = 0x17, /* Wave effect mode */
|
||||
POLYCHROME_V2_MODE_SPRING = 0x18, /* Spring effect mode */
|
||||
POLYCHROME_V2_MODE_STACK = 0x19, /* Stack effect mode */
|
||||
POLYCHROME_V2_MODE_CRAM = 0x1A, /* Cram effect mode */
|
||||
POLYCHROME_V2_MODE_SCAN = 0x1B, /* Scan effect mode */
|
||||
POLYCHROME_V2_MODE_NEON = 0x1C, /* Neon effect mode */
|
||||
POLYCHROME_V2_MODE_WATER = 0x1D, /* Water effect mode */
|
||||
POLYCHROME_V2_MODE_RAINBOW = 0x1E, /* Rainbow effect mode */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
POLYCHROME_V2_BREATHING_SPEED_MIN = 0x0A, /* Slowest speed */
|
||||
POLYCHROME_V2_BREATHING_SPEED_DEFAULT = 0x06, /* Default speed */
|
||||
POLYCHROME_V2_BREATHING_SPEED_MAX = 0x02, /* Fastest speed */
|
||||
|
||||
POLYCHROME_V2_STROBE_SPEED_MIN = 0xA0, /* Slowest speed */
|
||||
POLYCHROME_V2_STROBE_SPEED_DEFAULT = 0x4D, /* Default speed */
|
||||
POLYCHROME_V2_STROBE_SPEED_MAX = 0x05, /* Fastest speed */
|
||||
|
||||
POLYCHROME_V2_SPECTRUM_CYCLE_SPEED_MIN = 0xA0, /* Slowest speed */
|
||||
POLYCHROME_V2_SPECTRUM_CYCLE_SPEED_DEFAULT = 0x50, /* Default speed */
|
||||
POLYCHROME_V2_SPECTRUM_CYCLE_SPEED_MAX = 0x0A, /* Fastest speed */
|
||||
|
||||
POLYCHROME_V2_RANDOM_SPEED_MIN = 0xA0, /* Slowest speed */
|
||||
POLYCHROME_V2_RANDOM_SPEED_DEFAULT = 0x4D, /* Default speed */
|
||||
POLYCHROME_V2_RANDOM_SPEED_MAX = 0x05, /* Fastest speed */
|
||||
|
||||
POLYCHROME_V2_WAVE_SPEED_MIN = 0x06, /* Slowest speed */
|
||||
POLYCHROME_V2_WAVE_SPEED_DEFAULT = 0x03, /* Default speed */
|
||||
POLYCHROME_V2_WAVE_SPEED_MAX = 0x01, /* Fastest speed */
|
||||
|
||||
POLYCHROME_V2_SPRING_SPEED_MIN = 0x20, /* Slowest speed */
|
||||
POLYCHROME_V2_SPRING_SPEED_DEFAULT = 0x11, /* Default speed */
|
||||
POLYCHROME_V2_SPRING_SPEED_MAX = 0x02, /* Fastest speed */
|
||||
|
||||
POLYCHROME_V2_STACK_SPEED_MIN = 0x20, /* Slowest speed */
|
||||
POLYCHROME_V2_STACK_SPEED_DEFAULT = 0x11, /* Default speed */
|
||||
POLYCHROME_V2_STACK_SPEED_MAX = 0x02, /* Fastest speed */
|
||||
|
||||
POLYCHROME_V2_CRAM_SPEED_MIN = 0x20, /* Slowest speed */
|
||||
POLYCHROME_V2_CRAM_SPEED_DEFAULT = 0x11, /* Default speed */
|
||||
POLYCHROME_V2_CRAM_SPEED_MAX = 0x02, /* Fastest speed */
|
||||
|
||||
POLYCHROME_V2_SCAN_SPEED_MIN = 0x20, /* Slowest speed */
|
||||
POLYCHROME_V2_SCAN_SPEED_DEFAULT = 0x11, /* Default speed */
|
||||
POLYCHROME_V2_SCAN_SPEED_MAX = 0x02, /* Fastest speed */
|
||||
|
||||
POLYCHROME_V2_NEON_SPEED_MIN = 0x20, /* Slowest speed */
|
||||
POLYCHROME_V2_NEON_SPEED_DEFAULT = 0x11, /* Default speed */
|
||||
POLYCHROME_V2_NEON_SPEED_MAX = 0x02, /* Fastest speed */
|
||||
|
||||
POLYCHROME_V2_WATER_SPEED_MIN = 0x20, /* Slowest speed */
|
||||
POLYCHROME_V2_WATER_SPEED_DEFAULT = 0x11, /* Default speed */
|
||||
POLYCHROME_V2_WATER_SPEED_MAX = 0x02, /* Fastest speed */
|
||||
|
||||
POLYCHROME_V2_RAINBOW_SPEED_MIN = 0x12, /* Slowest speed */
|
||||
POLYCHROME_V2_RAINBOW_SPEED_DEFAULT = 0x08, /* Default speed */
|
||||
POLYCHROME_V2_RAINBOW_SPEED_MAX = 0x02, /* Fastest speed */
|
||||
};
|
||||
|
||||
class ASRockPolychromeV2SMBusController
|
||||
{
|
||||
public:
|
||||
ASRockPolychromeV2SMBusController(i2c_smbus_interface* bus, polychrome_dev_id dev);
|
||||
~ASRockPolychromeV2SMBusController();
|
||||
|
||||
std::string GetDeviceLocation();
|
||||
std::string GetDeviceName();
|
||||
std::string GetFirmwareVersion();
|
||||
uint8_t GetMode();
|
||||
void SetColorsAndSpeed(uint8_t led, uint8_t red, uint8_t green, uint8_t blue);
|
||||
void SetMode(uint8_t zone, uint8_t mode, uint8_t speed);
|
||||
|
||||
uint8_t zone_led_count[6];
|
||||
uint16_t fw_version;
|
||||
|
||||
private:
|
||||
std::string device_name;
|
||||
uint8_t active_zone;
|
||||
uint8_t active_mode;
|
||||
uint8_t active_speed;
|
||||
i2c_smbus_interface* bus;
|
||||
polychrome_dev_id dev;
|
||||
|
||||
void ReadLEDConfiguration();
|
||||
};
|
||||
+328
@@ -0,0 +1,328 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_ASRockPolychromeV2SMBus.cpp |
|
||||
| |
|
||||
| RGBController for SMBus ASRock Polychrome V2 |
|
||||
| motherboards |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 15 Dec 2019 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "RGBController_ASRockPolychromeV2SMBus.h"
|
||||
|
||||
static const char* polychrome_v2_zone_names[] =
|
||||
{
|
||||
"RGB LED 1 Header",
|
||||
"RGB LED 2 Header",
|
||||
"Audio",
|
||||
"PCH",
|
||||
"IO Cover",
|
||||
"Addressable Header"
|
||||
};
|
||||
|
||||
/**------------------------------------------------------------------*\
|
||||
@name ASRock Polychrome v2 SMBus
|
||||
@category Motherboard
|
||||
@type SMBus
|
||||
@save :robot:
|
||||
@direct :x:
|
||||
@effects :white_check_mark:
|
||||
@detectors DetectASRockSMBusControllers
|
||||
@comment ASRock Polychrome v2 controllers will save with each update.
|
||||
Per ARGB LED support is not possible with these devices.
|
||||
\*-------------------------------------------------------------------*/
|
||||
|
||||
RGBController_ASRockPolychromeV2SMBus::RGBController_ASRockPolychromeV2SMBus(ASRockPolychromeV2SMBusController* controller_ptr)
|
||||
{
|
||||
controller = controller_ptr;
|
||||
|
||||
name = controller->GetDeviceName();
|
||||
vendor = "ASRock";
|
||||
version = controller->GetFirmwareVersion();
|
||||
type = DEVICE_TYPE_MOTHERBOARD;
|
||||
description = "ASRock Polychrome v2 Device";
|
||||
location = controller->GetDeviceLocation();
|
||||
|
||||
|
||||
mode Off;
|
||||
Off.name = "Off";
|
||||
Off.value = POLYCHROME_V2_MODE_OFF;
|
||||
Off.flags = MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Off.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Off);
|
||||
|
||||
mode Static;
|
||||
Static.name = "Static";
|
||||
Static.value = POLYCHROME_V2_MODE_STATIC;
|
||||
Static.flags = MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Static.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Static);
|
||||
|
||||
mode Breathing;
|
||||
Breathing.name = "Breathing";
|
||||
Breathing.value = POLYCHROME_V2_MODE_BREATHING;
|
||||
Breathing.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Breathing.speed_min = POLYCHROME_V2_BREATHING_SPEED_MIN;
|
||||
Breathing.speed_max = POLYCHROME_V2_BREATHING_SPEED_MAX;
|
||||
Breathing.speed = POLYCHROME_V2_BREATHING_SPEED_DEFAULT;
|
||||
Breathing.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Breathing);
|
||||
|
||||
mode Strobe;
|
||||
Strobe.name = "Strobe";
|
||||
Strobe.value = POLYCHROME_V2_MODE_STROBE;
|
||||
Strobe.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Strobe.speed_min = POLYCHROME_V2_STROBE_SPEED_MIN;
|
||||
Strobe.speed_max = POLYCHROME_V2_STROBE_SPEED_MAX;
|
||||
Strobe.speed = POLYCHROME_V2_STROBE_SPEED_DEFAULT;
|
||||
Strobe.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Strobe);
|
||||
|
||||
mode SpectrumCycle;
|
||||
SpectrumCycle.name = "Spectrum Cycle";
|
||||
SpectrumCycle.value = POLYCHROME_V2_MODE_SPECTRUM_CYCLE;
|
||||
SpectrumCycle.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
SpectrumCycle.speed_min = POLYCHROME_V2_SPECTRUM_CYCLE_SPEED_MIN;
|
||||
SpectrumCycle.speed_max = POLYCHROME_V2_SPECTRUM_CYCLE_SPEED_MAX;
|
||||
SpectrumCycle.speed = POLYCHROME_V2_SPECTRUM_CYCLE_SPEED_DEFAULT;
|
||||
SpectrumCycle.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(SpectrumCycle);
|
||||
|
||||
mode Random;
|
||||
Random.name = "Random";
|
||||
Random.value = POLYCHROME_V2_MODE_RANDOM;
|
||||
Random.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Random.speed_min = POLYCHROME_V2_RANDOM_SPEED_MIN;
|
||||
Random.speed_max = POLYCHROME_V2_RANDOM_SPEED_MAX;
|
||||
Random.speed = POLYCHROME_V2_RANDOM_SPEED_DEFAULT;
|
||||
Random.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Random);
|
||||
|
||||
mode Wave;
|
||||
Wave.name = "Wave";
|
||||
Wave.value = POLYCHROME_V2_MODE_WAVE;
|
||||
Wave.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Wave.speed_min = POLYCHROME_V2_WAVE_SPEED_MIN;
|
||||
Wave.speed_max = POLYCHROME_V2_WAVE_SPEED_MAX;
|
||||
Wave.speed = POLYCHROME_V2_WAVE_SPEED_DEFAULT;
|
||||
Wave.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Wave);
|
||||
|
||||
mode Spring;
|
||||
Spring.name = "Spring";
|
||||
Spring.value = POLYCHROME_V2_MODE_SPRING;
|
||||
Spring.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Spring.speed_min = POLYCHROME_V2_SPRING_SPEED_MIN;
|
||||
Spring.speed_max = POLYCHROME_V2_SPRING_SPEED_MAX;
|
||||
Spring.speed = POLYCHROME_V2_SPRING_SPEED_DEFAULT;
|
||||
Spring.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Spring);
|
||||
|
||||
mode Stack;
|
||||
Stack.name = "Stack";
|
||||
Stack.value = POLYCHROME_V2_MODE_STACK;
|
||||
Stack.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Stack.speed_min = POLYCHROME_V2_STACK_SPEED_MIN;
|
||||
Stack.speed_max = POLYCHROME_V2_STACK_SPEED_MAX;
|
||||
Stack.speed = POLYCHROME_V2_STACK_SPEED_DEFAULT;
|
||||
Stack.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Stack);
|
||||
|
||||
mode Cram;
|
||||
Cram.name = "Cram";
|
||||
Cram.value = POLYCHROME_V2_MODE_CRAM;
|
||||
Cram.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Cram.speed_min = POLYCHROME_V2_CRAM_SPEED_MIN;
|
||||
Cram.speed_max = POLYCHROME_V2_CRAM_SPEED_MAX;
|
||||
Cram.speed = POLYCHROME_V2_CRAM_SPEED_DEFAULT;
|
||||
Cram.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Cram);
|
||||
|
||||
mode Scan;
|
||||
Scan.name = "Scan";
|
||||
Scan.value = POLYCHROME_V2_MODE_SCAN;
|
||||
Scan.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Scan.speed_min = POLYCHROME_V2_SCAN_SPEED_MIN;
|
||||
Scan.speed_max = POLYCHROME_V2_SCAN_SPEED_MAX;
|
||||
Scan.speed = POLYCHROME_V2_SCAN_SPEED_DEFAULT;
|
||||
Scan.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Scan);
|
||||
|
||||
mode Neon;
|
||||
Neon.name = "Neon";
|
||||
Neon.value = POLYCHROME_V2_MODE_NEON;
|
||||
Neon.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Neon.speed_min = POLYCHROME_V2_NEON_SPEED_MIN;
|
||||
Neon.speed_max = POLYCHROME_V2_NEON_SPEED_MAX;
|
||||
Neon.speed = POLYCHROME_V2_NEON_SPEED_DEFAULT;
|
||||
Neon.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Neon);
|
||||
|
||||
mode Water;
|
||||
Water.name = "Water";
|
||||
Water.value = POLYCHROME_V2_MODE_WATER;
|
||||
Water.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Water.speed_min = POLYCHROME_V2_WATER_SPEED_MIN;
|
||||
Water.speed_max = POLYCHROME_V2_WATER_SPEED_MAX;
|
||||
Water.speed = POLYCHROME_V2_WATER_SPEED_DEFAULT;
|
||||
Water.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Water);
|
||||
|
||||
mode Rainbow;
|
||||
Rainbow.name = "Rainbow";
|
||||
Rainbow.value = POLYCHROME_V2_MODE_RAINBOW;
|
||||
Rainbow.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Rainbow.speed_min = POLYCHROME_V2_RAINBOW_SPEED_MIN;
|
||||
Rainbow.speed_max = POLYCHROME_V2_RAINBOW_SPEED_MAX;
|
||||
Rainbow.speed = POLYCHROME_V2_RAINBOW_SPEED_DEFAULT;
|
||||
Rainbow.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Rainbow);
|
||||
|
||||
SetupZones();
|
||||
}
|
||||
|
||||
RGBController_ASRockPolychromeV2SMBus::~RGBController_ASRockPolychromeV2SMBus()
|
||||
{
|
||||
delete controller;
|
||||
}
|
||||
|
||||
void RGBController_ASRockPolychromeV2SMBus::SetupZones()
|
||||
{
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Set up zones |
|
||||
\*---------------------------------------------------------*/
|
||||
for(unsigned int zone_idx = 0; zone_idx < POLYCHROME_V2_ZONE_COUNT; zone_idx++)
|
||||
{
|
||||
if(controller->zone_led_count[zone_idx] > 0)
|
||||
{
|
||||
zone* new_zone = new zone();
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Set zone name to channel name |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
new_zone->name = polychrome_v2_zone_names[zone_idx];
|
||||
|
||||
|
||||
if(zone_idx == POLYCHROME_V2_ZONE_ADDRESSABLE)
|
||||
{
|
||||
new_zone->leds_min = 1;
|
||||
new_zone->leds_max = 1;
|
||||
new_zone->leds_count = 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
new_zone->leds_min = controller->zone_led_count[zone_idx];
|
||||
new_zone->leds_max = controller->zone_led_count[zone_idx];
|
||||
new_zone->leds_count = controller->zone_led_count[zone_idx];
|
||||
}
|
||||
|
||||
if(new_zone->leds_count > 1)
|
||||
{
|
||||
new_zone->type = ZONE_TYPE_LINEAR;
|
||||
}
|
||||
else
|
||||
{
|
||||
new_zone->type = ZONE_TYPE_SINGLE;
|
||||
}
|
||||
|
||||
new_zone->matrix_map = NULL;
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Push new zone to zones vector |
|
||||
\*---------------------------------------------------------*/
|
||||
zones.push_back(*new_zone);
|
||||
}
|
||||
}
|
||||
|
||||
unsigned int led_count = 0;
|
||||
/*---------------------------------------------------------*\
|
||||
| Set up LEDs |
|
||||
\*---------------------------------------------------------*/
|
||||
for(unsigned int zone_idx = 0; zone_idx < POLYCHROME_V2_ZONE_COUNT; zone_idx++)
|
||||
{
|
||||
if(controller->zone_led_count[zone_idx] > 0)
|
||||
{
|
||||
for(unsigned int led_idx = 0; led_idx < controller->zone_led_count[zone_idx]; led_idx++)
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| Each zone only has one LED |
|
||||
\*---------------------------------------------------------*/
|
||||
led* new_led = new led();
|
||||
|
||||
new_led->name = polychrome_v2_zone_names[zone_idx];
|
||||
|
||||
new_led->name.append(" " + std::to_string(led_idx + 1));
|
||||
new_led->value = 0;
|
||||
|
||||
if(zone_idx == POLYCHROME_V2_ZONE_ADDRESSABLE)
|
||||
{
|
||||
new_led->value = 0x19;
|
||||
}
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Push new LED to LEDs vector |
|
||||
\*---------------------------------------------------------*/
|
||||
leds.push_back(*new_led);
|
||||
|
||||
led_count++;
|
||||
|
||||
if(zone_idx == POLYCHROME_V2_ZONE_ADDRESSABLE)
|
||||
{
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
SetupColors();
|
||||
}
|
||||
|
||||
void RGBController_ASRockPolychromeV2SMBus::ResizeZone(int /*zone*/, int /*new_size*/)
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| This device does not support resizing zones |
|
||||
\*---------------------------------------------------------*/
|
||||
}
|
||||
|
||||
void RGBController_ASRockPolychromeV2SMBus::DeviceUpdateLEDs()
|
||||
{
|
||||
for(unsigned int led = 0; led < colors.size(); led++)
|
||||
{
|
||||
UpdateSingleLED(led);
|
||||
}
|
||||
}
|
||||
|
||||
void RGBController_ASRockPolychromeV2SMBus::UpdateZoneLEDs(int /*zone*/)
|
||||
{
|
||||
DeviceUpdateLEDs();
|
||||
}
|
||||
|
||||
void RGBController_ASRockPolychromeV2SMBus::UpdateSingleLED(int led)
|
||||
{
|
||||
unsigned char red = RGBGetRValue(colors[led]);
|
||||
unsigned char grn = RGBGetGValue(colors[led]);
|
||||
unsigned char blu = RGBGetBValue(colors[led]);
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| If the LED value is non-zero, this LED overrides the LED |
|
||||
| index |
|
||||
\*---------------------------------------------------------*/
|
||||
if(leds[led].value != 0)
|
||||
{
|
||||
led = leds[led].value;
|
||||
}
|
||||
|
||||
controller->SetColorsAndSpeed(led, red, grn, blu);
|
||||
}
|
||||
|
||||
void RGBController_ASRockPolychromeV2SMBus::DeviceUpdateMode()
|
||||
{
|
||||
|
||||
controller->SetMode(0, modes[active_mode].value, modes[active_mode].speed);
|
||||
|
||||
DeviceUpdateLEDs();
|
||||
}
|
||||
+36
@@ -0,0 +1,36 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_ASRockPolychromeV2SMBus.h |
|
||||
| |
|
||||
| RGBController for SMBus ASRock Polychrome V2 |
|
||||
| motherboards |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 15 Dec 2019 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "RGBController.h"
|
||||
#include "ASRockPolychromeV2SMBusController.h"
|
||||
|
||||
class RGBController_ASRockPolychromeV2SMBus : public RGBController
|
||||
{
|
||||
public:
|
||||
RGBController_ASRockPolychromeV2SMBus(ASRockPolychromeV2SMBusController* controller_ptr);
|
||||
~RGBController_ASRockPolychromeV2SMBus();
|
||||
|
||||
void SetupZones();
|
||||
|
||||
void ResizeZone(int zone, int new_size);
|
||||
|
||||
void DeviceUpdateLEDs();
|
||||
void UpdateZoneLEDs(int zone);
|
||||
void UpdateSingleLED(int led);
|
||||
|
||||
void DeviceUpdateMode();
|
||||
|
||||
private:
|
||||
ASRockPolychromeV2SMBusController* controller;
|
||||
};
|
||||
@@ -0,0 +1,177 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| ASRockSMBusControllerDetect.cpp |
|
||||
| |
|
||||
| Detector for SMBus ASRock ASR RGB and Polychrome |
|
||||
| motherboards |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 14 Dec 2019 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include <vector>
|
||||
#include "Detector.h"
|
||||
#include "ASRockASRRGBSMBusController.h"
|
||||
#include "ASRockPolychromeV1SMBusController.h"
|
||||
#include "ASRockPolychromeV2SMBusController.h"
|
||||
#include "LogManager.h"
|
||||
#include "RGBController_ASRockASRRGBSMBus.h"
|
||||
#include "RGBController_ASRockPolychromeV1SMBus.h"
|
||||
#include "RGBController_ASRockPolychromeV2SMBus.h"
|
||||
#include "i2c_smbus.h"
|
||||
#include "pci_ids.h"
|
||||
|
||||
/*******************************************************************************************\
|
||||
* *
|
||||
* TestForPolychromeSMBusController *
|
||||
* *
|
||||
* Tests the given address to see if an ASRock RGB controller exists there. *
|
||||
* First does a quick write to test for a response *
|
||||
* *
|
||||
\*******************************************************************************************/
|
||||
|
||||
#define ASROCK_DETECTOR_NAME "ASRock SMBus Detectector"
|
||||
#define VENDOR_NAME "ASRock"
|
||||
#define SMBUS_ADDRESS 0x6A
|
||||
|
||||
enum
|
||||
{
|
||||
ASROCK_TYPE_UNKNOWN = 0x00, /* Unknown Type or Not ASRock Device */
|
||||
ASROCK_TYPE_ASRLED = 0x01, /* ASRock Firmware 1.x - ASR LED */
|
||||
ASROCK_TYPE_POLYCHROME_V1 = 0x02, /* ASRock Firmware 2.x - Polychrome V1 */
|
||||
ASROCK_TYPE_POLYCHROME_V2 = 0x03, /* ASRock Firmware 3.x - Polychrome V2 */
|
||||
ASROCK_REG_FIRMWARE_VER = 0x00, /* Firmware version Major.Minor */
|
||||
};
|
||||
|
||||
union u16_to_u8
|
||||
{
|
||||
uint16_t u16;
|
||||
struct
|
||||
{
|
||||
uint8_t lsb;
|
||||
uint8_t msb;
|
||||
};
|
||||
};
|
||||
|
||||
bool TestForPolychromeSMBusController(i2c_smbus_interface* bus, uint8_t address)
|
||||
{
|
||||
bool pass = false;
|
||||
|
||||
int res = bus->i2c_smbus_write_quick(address, I2C_SMBUS_WRITE);
|
||||
|
||||
if (res >= 0)
|
||||
{
|
||||
pass = true;
|
||||
}
|
||||
|
||||
return(pass);
|
||||
|
||||
} /* TestForPolychromeController() */
|
||||
|
||||
uint16_t GetFirmwareVersion(i2c_smbus_interface* bus, uint8_t address)
|
||||
{
|
||||
// The firmware register holds two bytes, so the first read should return 2
|
||||
// If not, report invalid firmware revision
|
||||
LOG_DEBUG("[%s] Reading back device firmware version", ASROCK_DETECTOR_NAME);
|
||||
u16_to_u8 asrock_version_u16;
|
||||
|
||||
// Version response array needs to be 32 bytes to prevent non ASRock board from stack smashing
|
||||
uint8_t asrock_version[I2C_SMBUS_BLOCK_MAX] = { 0x00, 0x00 };
|
||||
|
||||
if (bus->i2c_smbus_read_block_data(address, ASROCK_REG_FIRMWARE_VER, asrock_version) == 0x02)
|
||||
{
|
||||
asrock_version_u16.msb = asrock_version[0];
|
||||
asrock_version_u16.lsb = asrock_version[1];
|
||||
|
||||
LOG_DEBUG("[%s] Device firmware version: v%02d.%02d", ASROCK_DETECTOR_NAME, asrock_version_u16.msb, asrock_version_u16.lsb);
|
||||
return(asrock_version_u16.u16);
|
||||
}
|
||||
else
|
||||
{
|
||||
LOG_WARNING("[%s] Firmware readback failed; Returning Unknown Version", ASROCK_DETECTOR_NAME);
|
||||
return(ASROCK_TYPE_UNKNOWN);
|
||||
}
|
||||
}
|
||||
|
||||
/******************************************************************************************\
|
||||
* *
|
||||
* DetectPolychromeControllers *
|
||||
* *
|
||||
* Detect ASRock Polychrome RGB SMBus controllers on the enumerated I2C busses at *
|
||||
* address 0x6A. *
|
||||
* *
|
||||
* bus - pointer to i2c_smbus_interface where Polychrome device is connected *
|
||||
* dev - I2C address of Polychrome device *
|
||||
* *
|
||||
\******************************************************************************************/
|
||||
|
||||
void DetectASRockSMBusControllers(std::vector<i2c_smbus_interface*>& busses)
|
||||
{
|
||||
for(unsigned int bus = 0; bus < busses.size(); bus++)
|
||||
{
|
||||
IF_MOBO_SMBUS(busses[bus]->pci_vendor, busses[bus]->pci_device)
|
||||
{
|
||||
if(busses[bus]->pci_subsystem_vendor == ASROCK_SUB_VEN)
|
||||
{
|
||||
LOG_DEBUG(SMBUS_CHECK_DEVICE_MESSAGE_EN, ASROCK_DETECTOR_NAME, bus, VENDOR_NAME, SMBUS_ADDRESS);
|
||||
// Check for Polychrome controller at 0x6A
|
||||
if(TestForPolychromeSMBusController(busses[bus], SMBUS_ADDRESS))
|
||||
{
|
||||
LOG_DEBUG("[%s] Detected a device at address 0x%02X, testing for a known controller", ASROCK_DETECTOR_NAME, SMBUS_ADDRESS);
|
||||
|
||||
u16_to_u8 version;
|
||||
version.u16 = GetFirmwareVersion(busses[bus], SMBUS_ADDRESS);
|
||||
|
||||
switch (version.msb)
|
||||
{
|
||||
case ASROCK_TYPE_ASRLED:
|
||||
{
|
||||
LOG_DEBUG("[%s] Found a ASR RGB LED Controller", ASROCK_DETECTOR_NAME);
|
||||
ASRockASRRGBSMBusController* controller = new ASRockASRRGBSMBusController(busses[bus], SMBUS_ADDRESS);
|
||||
controller-> fw_version = version.u16;
|
||||
RGBController_ASRockASRRGBSMBus* rgb_controller = new RGBController_ASRockASRRGBSMBus(controller);
|
||||
ResourceManager::get()->RegisterRGBController(rgb_controller);
|
||||
}
|
||||
break;
|
||||
|
||||
case ASROCK_TYPE_POLYCHROME_V1:
|
||||
{
|
||||
LOG_DEBUG("[%s] Found a Polychrome v1 Controller", ASROCK_DETECTOR_NAME);
|
||||
ASRockPolychromeV1SMBusController* controller = new ASRockPolychromeV1SMBusController(busses[bus], SMBUS_ADDRESS);
|
||||
controller-> fw_version = version.u16;
|
||||
RGBController_ASRockPolychromeV1SMBus* rgb_controller = new RGBController_ASRockPolychromeV1SMBus(controller);
|
||||
ResourceManager::get()->RegisterRGBController(rgb_controller);
|
||||
}
|
||||
break;
|
||||
|
||||
case ASROCK_TYPE_POLYCHROME_V2:
|
||||
{
|
||||
LOG_DEBUG("[%s] Found a Polychrome v2 Controller", ASROCK_DETECTOR_NAME);
|
||||
ASRockPolychromeV2SMBusController* controller = new ASRockPolychromeV2SMBusController(busses[bus], SMBUS_ADDRESS);
|
||||
controller-> fw_version = version.u16;
|
||||
RGBController_ASRockPolychromeV2SMBus* rgb_controller = new RGBController_ASRockPolychromeV2SMBus(controller);
|
||||
ResourceManager::get()->RegisterRGBController(rgb_controller);
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
LOG_DEBUG("[%s] Not a Polychrome device or unknown type", ASROCK_DETECTOR_NAME);
|
||||
break;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
LOG_DEBUG("[%s] Bus %02d has no response at 0x%02X", ASROCK_DETECTOR_NAME, bus, SMBUS_ADDRESS);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
LOG_DEBUG(SMBUS_CHECK_DEVICE_FAILURE_EN, ASROCK_DETECTOR_NAME, bus, VENDOR_NAME);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
} /* DetectSMBusPolychromeControllers() */
|
||||
|
||||
REGISTER_I2C_DETECTOR("ASRock Motherboard SMBus Controllers", DetectASRockSMBusControllers);
|
||||
@@ -0,0 +1,838 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AlienwareController.cpp |
|
||||
| |
|
||||
| Driver for Dell Alienware RGB USB controller |
|
||||
| |
|
||||
| Gabriel Marcano (gemarcano) 21 Apr 2021 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include <cstring>
|
||||
#include <cstdint>
|
||||
#include <map>
|
||||
#include <thread>
|
||||
#include <chrono>
|
||||
#include <algorithm>
|
||||
#include <sstream>
|
||||
#include "RGBController.h"
|
||||
#include "AlienwareController.h"
|
||||
#include "LogManager.h"
|
||||
#include "StringUtils.h"
|
||||
|
||||
typedef uint32_t alienware_platform_id;
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Some devices appear to report the wrong number of zones. |
|
||||
| Record that here. |
|
||||
\*---------------------------------------------------------*/
|
||||
static const std::map<alienware_platform_id, uint8_t> zone_quirks_table =
|
||||
{
|
||||
{ 0x0C01, 4 }, // Dell G5 SE 5505
|
||||
{ 0x0A01, 16 }, // Dell G7 15 7500
|
||||
{ 0x0E03, 4 }, // Dell G15 5511
|
||||
{ 0x0E0A, 4 } // Dell G15 5530
|
||||
|
||||
};
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Add zones for devices here, mapping the platform ID to |
|
||||
| the zone names |
|
||||
\*---------------------------------------------------------*/
|
||||
static const std::map<alienware_platform_id, std::vector<const char*>> zone_names_table =
|
||||
{
|
||||
{ 0x0C01, { "Left", "Middle", "Right", "Numpad" } },
|
||||
{ 0x0A01, { "Left", "Center Left", "Center Right", "Right",
|
||||
"Light Bar 1", "Light Bar 2", "Light Bar 3",
|
||||
"Light Bar 4", "Light Bar 5", "Light Bar 6",
|
||||
"Light Bar 7", "Light Bar 8", "Light Bar 9",
|
||||
"Light Bar 10", "Light Bar 11", "Light Bar 12" } },
|
||||
{ 0x0E03, { "Left", "Middle", "Right", "Numpad" } },
|
||||
{ 0x0E0A, { "Left", "Middle", "Right", "Numpad" } }
|
||||
};
|
||||
|
||||
static void SendHIDReport(hid_device *dev, const unsigned char* usb_buf, size_t usb_buf_size)
|
||||
{
|
||||
using namespace std::chrono_literals;
|
||||
|
||||
hid_send_feature_report(dev, usb_buf, usb_buf_size);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| The controller really doesn't like really spammed by |
|
||||
| too many commands at once... the delay may be command |
|
||||
| dependent also. Delay for longer if the command is |
|
||||
| changing animation state |
|
||||
\*-----------------------------------------------------*/
|
||||
unsigned char command = usb_buf[2];
|
||||
unsigned char subcommand = usb_buf[3];
|
||||
|
||||
if( ( command == ALIENWARE_COMMAND_USER_ANIM )
|
||||
&& ( ( subcommand == ALIENWARE_COMMAND_USER_ANIM_FINISH_PLAY )
|
||||
|| ( subcommand == ALIENWARE_COMMAND_USER_ANIM_FINISH_SAVE ) ) )
|
||||
{
|
||||
std::this_thread::sleep_for(1s);
|
||||
}
|
||||
else
|
||||
{
|
||||
std::this_thread::sleep_for(60ms);
|
||||
}
|
||||
}
|
||||
|
||||
AlienwareController::AlienwareController(hid_device* dev_handle, const hid_device_info& info, std::string name)
|
||||
{
|
||||
HidapiAlienwareReport report;
|
||||
|
||||
dev = dev_handle;
|
||||
device_name = name;
|
||||
location = info.path;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Get serial number |
|
||||
\*-----------------------------------------------------*/
|
||||
serial_number = StringUtils::wstring_to_string(info.serial_number);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Get zone information by checking firmware |
|
||||
| configuration |
|
||||
\*-----------------------------------------------------*/
|
||||
report = Report(ALIENWARE_COMMAND_REPORT_CONFIG);
|
||||
alienware_platform_id platform_id = report.data[4] << 8 | report.data[5];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Check if the device reports the wrong number of zones |
|
||||
\*-----------------------------------------------------*/
|
||||
unsigned number_of_zones = zone_quirks_table.count(platform_id) ? zone_quirks_table.at(platform_id) : report.data[6];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Get firmware version |
|
||||
\*-----------------------------------------------------*/
|
||||
report = Report(ALIENWARE_COMMAND_REPORT_FIRMWARE);
|
||||
|
||||
std::stringstream fw_string;
|
||||
|
||||
fw_string << static_cast<unsigned>(report.data[4]) << '.' << static_cast<unsigned>(report.data[5]) << '.' << static_cast<unsigned>(report.data[6]);
|
||||
version = fw_string.str();
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Initialize Alienware zones |
|
||||
\*-----------------------------------------------------*/
|
||||
zones.resize(number_of_zones);
|
||||
|
||||
if(zone_names_table.count(platform_id))
|
||||
{
|
||||
LOG_INFO("[%s] Known platform: %8X, Number of zones: %d", ALIENWARE_CONTROLLER_NAME, platform_id, number_of_zones);
|
||||
zone_names = zone_names_table.at(platform_id);
|
||||
}
|
||||
else
|
||||
{
|
||||
LOG_WARNING("[%s] Unknown platform: %8X, Number of zones: %d", ALIENWARE_CONTROLLER_NAME, platform_id, number_of_zones);
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| If this is an unknown controller, set the name of |
|
||||
| all regions to "Unknown" |
|
||||
\*-------------------------------------------------*/
|
||||
for(size_t i = 0; i < number_of_zones; i++)
|
||||
{
|
||||
zone_names.emplace_back("Unknown");
|
||||
}
|
||||
}
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set defaults for all zones |
|
||||
| It doesn't seem possible to read the controller's |
|
||||
| current state, hence the default value being set here.|
|
||||
\*-----------------------------------------------------*/
|
||||
for(unsigned int zone_idx = 0; zone_idx < zones.size(); zone_idx++)
|
||||
{
|
||||
zones[zone_idx].color[0] = 0x000000;
|
||||
zones[zone_idx].color[1] = 0x000000;
|
||||
zones[zone_idx].mode = ALIENWARE_MODE_COLOR;
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| Default period value from ACC |
|
||||
\*-------------------------------------------------*/
|
||||
zones[zone_idx].period = 2000;
|
||||
zones[zone_idx].tempo = ALIENWARE_TEMPO_MAX;
|
||||
zones[zone_idx].dim = 0;
|
||||
}
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Initialize dirty flags |
|
||||
\*-----------------------------------------------------*/
|
||||
dirty = true;
|
||||
dirty_dim = true;
|
||||
}
|
||||
|
||||
AlienwareController::~AlienwareController()
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
unsigned int AlienwareController::GetZoneCount()
|
||||
{
|
||||
return((unsigned int)zones.size());
|
||||
}
|
||||
|
||||
std::vector<const char*> AlienwareController::GetZoneNames()
|
||||
{
|
||||
return(zone_names);
|
||||
}
|
||||
|
||||
std::string AlienwareController::GetDeviceLocation()
|
||||
{
|
||||
return("HID: " + location);
|
||||
}
|
||||
|
||||
std::string AlienwareController::GetDeviceName()
|
||||
{
|
||||
return(device_name);
|
||||
}
|
||||
|
||||
std::string AlienwareController::GetSerialString()
|
||||
{
|
||||
return(serial_number);
|
||||
}
|
||||
|
||||
std::string AlienwareController::GetFirmwareVersion()
|
||||
{
|
||||
return(version);
|
||||
}
|
||||
|
||||
AlienwareController::HidapiAlienwareReport AlienwareController::GetResponse()
|
||||
{
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero init. This is not updated if there's a problem. |
|
||||
\*-----------------------------------------------------*/
|
||||
HidapiAlienwareReport result;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(result.data, 0x00, sizeof(result.data));
|
||||
|
||||
|
||||
hid_get_feature_report(dev, result.data, HIDAPI_ALIENWARE_REPORT_SIZE);
|
||||
|
||||
return(result);
|
||||
}
|
||||
|
||||
AlienwareController::HidapiAlienwareReport AlienwareController::Report(uint8_t subcommand)
|
||||
{
|
||||
unsigned char usb_buf[HIDAPI_ALIENWARE_REPORT_SIZE];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up message packet with leading 00, per hidapi |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x00] = 0x00;
|
||||
usb_buf[0x01] = 0x03;
|
||||
usb_buf[0x02] = ALIENWARE_COMMAND_REPORT;
|
||||
usb_buf[0x03] = subcommand;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
SendHIDReport(dev, usb_buf, sizeof(usb_buf));
|
||||
|
||||
return(GetResponse());
|
||||
}
|
||||
|
||||
AlienwareReport AlienwareController::GetStatus(uint8_t subcommand)
|
||||
{
|
||||
HidapiAlienwareReport data = Report(subcommand);
|
||||
AlienwareReport result = AlienwareReport{};
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Skip first byte, as that's the report number, which |
|
||||
| should be 0 |
|
||||
\*-----------------------------------------------------*/
|
||||
memcpy(result.data, &data.data[1], sizeof(result.data));
|
||||
|
||||
return(result);
|
||||
}
|
||||
|
||||
bool AlienwareController::Dim(std::vector<uint8_t> zones, double percent)
|
||||
{
|
||||
/*-----------------------------------------------------*\
|
||||
| Bail out if there are no zones to update |
|
||||
\*-----------------------------------------------------*/
|
||||
if(!zones.size())
|
||||
{
|
||||
return(true);
|
||||
}
|
||||
|
||||
unsigned char usb_buf[HIDAPI_ALIENWARE_REPORT_SIZE];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up message packet with leading 00, per hidapi |
|
||||
\*-----------------------------------------------------*/
|
||||
uint16_t num_zones = (uint16_t)zones.size();
|
||||
|
||||
usb_buf[0x00] = 0x00;
|
||||
usb_buf[0x01] = 0x03;
|
||||
usb_buf[0x02] = ALIENWARE_COMMAND_DIM;
|
||||
usb_buf[0x03] = static_cast<uint8_t>(percent);
|
||||
usb_buf[0x04] = num_zones >> 8;
|
||||
usb_buf[0x05] = num_zones & 0xFF;
|
||||
|
||||
for(size_t i = 0; i < num_zones; i++)
|
||||
{
|
||||
usb_buf[0x06+i] = zones[i];
|
||||
}
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
SendHIDReport(dev, usb_buf, sizeof(usb_buf));
|
||||
|
||||
HidapiAlienwareReport response = GetResponse();
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| For this command, error is if the output equals the |
|
||||
| input |
|
||||
\*-----------------------------------------------------*/
|
||||
return((response.data[1] == 0x03) && memcmp(usb_buf, response.data, HIDAPI_ALIENWARE_REPORT_SIZE));
|
||||
}
|
||||
|
||||
bool AlienwareController::UserAnimation(uint16_t subcommand, uint16_t animation, uint16_t duration)
|
||||
{
|
||||
unsigned char usb_buf[HIDAPI_ALIENWARE_REPORT_SIZE];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up message packet with leading 00 per hidapi |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x00] = 0x00;
|
||||
usb_buf[0x01] = 0x03;
|
||||
usb_buf[0x02] = ALIENWARE_COMMAND_USER_ANIM;
|
||||
usb_buf[0x03] = subcommand >> 8;
|
||||
usb_buf[0x04] = subcommand & 0xFF;
|
||||
usb_buf[0x05] = animation >> 8;
|
||||
usb_buf[0x06] = animation & 0xFF;
|
||||
usb_buf[0x07] = duration >> 8;
|
||||
usb_buf[0x08] = duration & 0xFF;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
SendHIDReport(dev, usb_buf, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Every subcommand appears to report its result on a |
|
||||
| different byte |
|
||||
\*-----------------------------------------------------*/
|
||||
HidapiAlienwareReport response = GetResponse();
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| The only time the 0x03 byte is zero is if the |
|
||||
| controller has crashed |
|
||||
\*-----------------------------------------------------*/
|
||||
if(response.data[1] == 0)
|
||||
{
|
||||
return(false);
|
||||
}
|
||||
|
||||
switch(subcommand)
|
||||
{
|
||||
case ALIENWARE_COMMAND_USER_ANIM_FINISH_SAVE:
|
||||
return(!response.data[7]);
|
||||
case ALIENWARE_COMMAND_USER_ANIM_FINISH_PLAY:
|
||||
return(!response.data[5]);
|
||||
case ALIENWARE_COMMAND_USER_ANIM_PLAY:
|
||||
return(!response.data[7]);
|
||||
default:
|
||||
return(true);
|
||||
}
|
||||
}
|
||||
|
||||
bool AlienwareController::SelectZones(const std::vector<uint8_t>& zones)
|
||||
{
|
||||
/*-----------------------------------------------------*\
|
||||
| Bail if zones is empty, and return false to indicate |
|
||||
| nothing has changed |
|
||||
\*-----------------------------------------------------*/
|
||||
if(!zones.size())
|
||||
{
|
||||
return(false);
|
||||
}
|
||||
|
||||
unsigned char usb_buf[HIDAPI_ALIENWARE_REPORT_SIZE];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up message packet with leading 00, per hidapi |
|
||||
\*-----------------------------------------------------*/
|
||||
uint16_t num_zones = (uint16_t)zones.size();
|
||||
|
||||
usb_buf[0x00] = 0x00;
|
||||
usb_buf[0x01] = 0x03;
|
||||
usb_buf[0x02] = ALIENWARE_COMMAND_SELECT_ZONES;
|
||||
usb_buf[0x03] = 1; // loop?
|
||||
usb_buf[0x04] = num_zones >> 8;
|
||||
usb_buf[0x05] = num_zones & 0xFF;
|
||||
|
||||
for(size_t i = 0; i < num_zones; i++)
|
||||
{
|
||||
usb_buf[0x06+i] = zones[i];
|
||||
}
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
SendHIDReport(dev, usb_buf, sizeof(usb_buf));
|
||||
|
||||
HidapiAlienwareReport response = GetResponse();
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| For this command, error is if the output equals the |
|
||||
| input |
|
||||
\*-----------------------------------------------------*/
|
||||
return((response.data[1] == 0x03) && memcmp(usb_buf, response.data, HIDAPI_ALIENWARE_REPORT_SIZE));
|
||||
}
|
||||
|
||||
bool AlienwareController::ModeAction(uint8_t mode, uint16_t duration, uint16_t tempo, RGBColor color)
|
||||
{
|
||||
return(ModeAction(&mode, &duration, &tempo, &color, 1));
|
||||
}
|
||||
|
||||
bool AlienwareController::ModeAction
|
||||
(
|
||||
const uint8_t* mode,
|
||||
const uint16_t* duration,
|
||||
const uint16_t* tempo,
|
||||
const RGBColor* color,
|
||||
unsigned amount
|
||||
)
|
||||
{
|
||||
unsigned char usb_buf[HIDAPI_ALIENWARE_REPORT_SIZE];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Amount must be 3 or less, as that's how many |
|
||||
| subcommands can fit into one report |
|
||||
\*-----------------------------------------------------*/
|
||||
if(amount > 3)
|
||||
{
|
||||
return(false);
|
||||
}
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up message packet with leading 00, per hidapi |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x00] = 0x00;
|
||||
usb_buf[0x01] = 0x03;
|
||||
usb_buf[0x02] = ALIENWARE_COMMAND_ADD_ACTION;
|
||||
|
||||
for(unsigned int i = 0; i < amount; i++)
|
||||
{
|
||||
usb_buf[0x03 + (8 * i)] = mode[i];
|
||||
usb_buf[0x04 + (8 * i)] = duration[i] >> 8;
|
||||
usb_buf[0x05 + (8 * i)] = duration[i] & 0xFF;
|
||||
usb_buf[0x06 + (8 * i)] = tempo[i] >> 8;
|
||||
usb_buf[0x07 + (8 * i)] = tempo[i] & 0xFF;
|
||||
usb_buf[0x08 + (8 * i)] = RGBGetRValue(color[i]);
|
||||
usb_buf[0x09 + (8 * i)] = RGBGetGValue(color[i]);
|
||||
usb_buf[0x0A + (8 * i)] = RGBGetBValue(color[i]);
|
||||
}
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
SendHIDReport(dev, usb_buf, sizeof(usb_buf));
|
||||
|
||||
HidapiAlienwareReport response = GetResponse();
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| For this command, error is if the output equals the |
|
||||
| input |
|
||||
\*-----------------------------------------------------*/
|
||||
return((response.data[1] == 0x03) && memcmp(usb_buf, response.data, HIDAPI_ALIENWARE_REPORT_SIZE));
|
||||
}
|
||||
|
||||
bool AlienwareController::MultiModeAction
|
||||
(
|
||||
const uint8_t* mode,
|
||||
const uint16_t* duration,
|
||||
const uint16_t* tempo,
|
||||
const RGBColor* color,
|
||||
unsigned amount
|
||||
)
|
||||
{
|
||||
bool result = true;
|
||||
unsigned int left = amount;
|
||||
|
||||
while(left && result)
|
||||
{
|
||||
unsigned int tmp_amount;
|
||||
|
||||
tmp_amount = std::min(left, 3u);
|
||||
result &= ModeAction(mode, duration, tempo, color, tmp_amount);
|
||||
mode += tmp_amount;
|
||||
duration += tmp_amount;
|
||||
tempo += tmp_amount;
|
||||
color += tmp_amount;
|
||||
left -= tmp_amount;
|
||||
}
|
||||
|
||||
return(result);
|
||||
}
|
||||
|
||||
bool AlienwareController::SetColorDirect(RGBColor color, std::vector<uint8_t> zones)
|
||||
{
|
||||
/*-----------------------------------------------------*\
|
||||
| Bail if zones is empty |
|
||||
\*-----------------------------------------------------*/
|
||||
if(zones.empty())
|
||||
{
|
||||
return(true);
|
||||
}
|
||||
|
||||
unsigned char usb_buf[HIDAPI_ALIENWARE_REPORT_SIZE];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up message packet with leading 00, per hidapi |
|
||||
\*-----------------------------------------------------*/
|
||||
uint16_t num_zones = (uint16_t)zones.size();
|
||||
|
||||
usb_buf[0x00] = 0x00;
|
||||
usb_buf[0x01] = 0x03;
|
||||
usb_buf[0x02] = ALIENWARE_COMMAND_SET_COLOR;
|
||||
usb_buf[0x03] = RGBGetRValue(color);
|
||||
usb_buf[0x04] = RGBGetGValue(color);
|
||||
usb_buf[0x05] = RGBGetBValue(color);
|
||||
usb_buf[0x06] = num_zones >> 8;
|
||||
usb_buf[0x07] = num_zones & 0xFF;
|
||||
|
||||
for(size_t i = 0; i < num_zones; i++)
|
||||
{
|
||||
usb_buf[0x08 + i] = zones[i];
|
||||
}
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
SendHIDReport(dev, usb_buf, sizeof(usb_buf));
|
||||
|
||||
HidapiAlienwareReport response = GetResponse();
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| For this command, error is if the output equals the |
|
||||
| input |
|
||||
\*-----------------------------------------------------*/
|
||||
return((response.data[1] == 0x03) && memcmp(usb_buf, response.data, HIDAPI_ALIENWARE_REPORT_SIZE));
|
||||
}
|
||||
|
||||
bool AlienwareController::Reset()
|
||||
{
|
||||
/*-----------------------------------------------------*\
|
||||
| Bail if zones is empty |
|
||||
\*-----------------------------------------------------*/
|
||||
if(zones.empty())
|
||||
{
|
||||
return(true);
|
||||
}
|
||||
|
||||
unsigned char usb_buf[HIDAPI_ALIENWARE_REPORT_SIZE];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up message packet with leading 00, per hidapi |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x00] = 0x00;
|
||||
usb_buf[0x01] = 0x03;
|
||||
usb_buf[0x02] = ALIENWARE_COMMAND_RESET;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
SendHIDReport(dev, usb_buf, sizeof(usb_buf));
|
||||
|
||||
HidapiAlienwareReport response = GetResponse();
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| For this command, error is if the output equals the |
|
||||
| input |
|
||||
\*-----------------------------------------------------*/
|
||||
return(response.data[1] == 0x03);
|
||||
}
|
||||
|
||||
void AlienwareController::SetMode(uint8_t zone, uint8_t mode)
|
||||
{
|
||||
if(mode != zones[zone].mode)
|
||||
{
|
||||
zones[zone].mode = mode;
|
||||
dirty = true;
|
||||
}
|
||||
}
|
||||
|
||||
void AlienwareController::SetColor(uint8_t zone, RGBColor color)
|
||||
{
|
||||
SetColor(zone, color, zones[zone].color[1]);
|
||||
}
|
||||
|
||||
void AlienwareController::SetColor(uint8_t zone, RGBColor color1, RGBColor color2)
|
||||
{
|
||||
if ((color1 == zones[zone].color[0]) && (color2 == zones[zone].color[1]))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
zones[zone].color[0] = color1;
|
||||
zones[zone].color[1] = color2;
|
||||
dirty = true;
|
||||
}
|
||||
|
||||
void AlienwareController::SetPeriod(uint8_t zone, uint16_t period)
|
||||
{
|
||||
if(period != zones[zone].period)
|
||||
{
|
||||
zones[zone].period = period;
|
||||
dirty = true;
|
||||
}
|
||||
}
|
||||
|
||||
void AlienwareController::SetTempo(uint8_t zone, uint16_t tempo)
|
||||
{
|
||||
if(tempo != zones[zone].tempo)
|
||||
{
|
||||
zones[zone].tempo = tempo;
|
||||
dirty = true;
|
||||
}
|
||||
}
|
||||
|
||||
void AlienwareController::SetDim(uint8_t zone, uint8_t dim)
|
||||
{
|
||||
if(dim != zones[zone].dim)
|
||||
{
|
||||
zones[zone].dim = dim;
|
||||
dirty_dim = true;
|
||||
}
|
||||
}
|
||||
|
||||
void AlienwareController::UpdateDim()
|
||||
{
|
||||
if(!dirty_dim)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Collect all zones that share dim settings, and update |
|
||||
| them together |
|
||||
\*-----------------------------------------------------*/
|
||||
std::map<uint8_t, std::vector<uint8_t>> dim_zone_map;
|
||||
|
||||
for(size_t i = 0; i < zones.size(); i++)
|
||||
{
|
||||
dim_zone_map[zones[i].dim].emplace_back((uint8_t)i);
|
||||
}
|
||||
|
||||
for(std::pair<const uint8_t, std::vector<uint8_t>> &pair : dim_zone_map)
|
||||
{
|
||||
/*-------------------------------------------------*\
|
||||
| Bail on an error... |
|
||||
\*-------------------------------------------------*/
|
||||
if(!Dim(pair.second, pair.first))
|
||||
{
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
dirty_dim = false;
|
||||
}
|
||||
|
||||
bool AlienwareController::UpdateDirect()
|
||||
{
|
||||
/*-----------------------------------------------------*\
|
||||
| Collect all zones that share dim settings, and update |
|
||||
| them together |
|
||||
\*-----------------------------------------------------*/
|
||||
std::map<RGBColor, std::vector<uint8_t>> color_zone_map;
|
||||
|
||||
for(size_t i = 0; i < zones.size(); i++)
|
||||
{
|
||||
color_zone_map[zones[i].color[0]].emplace_back((uint8_t)i);
|
||||
}
|
||||
|
||||
for(std::pair<const RGBColor, std::vector<uint8_t>> &pair : color_zone_map)
|
||||
{
|
||||
/*-------------------------------------------------*\
|
||||
| Bail on an error... |
|
||||
\*-------------------------------------------------*/
|
||||
if(!SetColorDirect(pair.first, pair.second))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
static const RGBColor rainbow_colors[4][7] =
|
||||
{
|
||||
{ 0xFF0000, 0xFFA500, 0xFFFF00, 0x008000, 0x00BFFF, 0x0000FF, 0x800080 },
|
||||
{ 0x800080, 0xFF0000, 0xFFA500, 0xFFFF00, 0x008000, 0x00BFFF, 0x0000FF },
|
||||
{ 0x0000FF, 0x800080, 0xFF0000, 0xFFA500, 0xFFFF00, 0x008000, 0x00BFFF },
|
||||
{ 0x00BFFF, 0x0000FF, 0x800080, 0xFF0000, 0xFFA500, 0xFFFF00, 0x008000 }
|
||||
};
|
||||
|
||||
void AlienwareController::UpdateMode()
|
||||
{
|
||||
/*-----------------------------------------------------*\
|
||||
| If there are no updates, don't bother running this |
|
||||
\*-----------------------------------------------------*/
|
||||
if(!dirty)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
bool result = UserAnimation(ALIENWARE_COMMAND_USER_ANIM_NEW, ALIENWARE_COMMAND_USER_ANIM_KEYBOARD, 0);
|
||||
|
||||
if(!result)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
for(std::size_t zone_idx = 0; zone_idx < zones.size(); zone_idx++)
|
||||
{
|
||||
alienware_zone zone = zones[zone_idx];
|
||||
|
||||
result = SelectZones({static_cast<uint8_t>(zone_idx)});
|
||||
|
||||
if(!result)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| Some modes use 0x07D0 for their duration as sent |
|
||||
| by AWCC traces, maybe 2000ms? |
|
||||
\*-------------------------------------------------*/
|
||||
switch (zone.mode)
|
||||
{
|
||||
case ALIENWARE_MODE_COLOR:
|
||||
result = ModeAction(zone.mode, 2000, ALIENWARE_TEMPO_MAX, zone.color[0]);
|
||||
break;
|
||||
|
||||
case ALIENWARE_MODE_PULSE:
|
||||
result = ModeAction(zone.mode, zone.period, zone.tempo, zone.color[0]);
|
||||
break;
|
||||
|
||||
case ALIENWARE_MODE_MORPH:
|
||||
{
|
||||
uint8_t zones[2] = { zone.mode, zone.mode };
|
||||
uint16_t periods[2] = { zone.period, zone.period };
|
||||
uint16_t tempos[2] = { zone.tempo, zone.tempo };
|
||||
RGBColor colors[2] = { zone.color[0], zone.color[1] };
|
||||
|
||||
result = MultiModeAction(zones, periods, tempos, colors, 2);
|
||||
}
|
||||
break;
|
||||
|
||||
case ALIENWARE_MODE_SPECTRUM:
|
||||
{
|
||||
uint8_t zones[7] = { ALIENWARE_MODE_MORPH, ALIENWARE_MODE_MORPH,
|
||||
ALIENWARE_MODE_MORPH, ALIENWARE_MODE_MORPH,
|
||||
ALIENWARE_MODE_MORPH, ALIENWARE_MODE_MORPH,
|
||||
ALIENWARE_MODE_MORPH };
|
||||
uint16_t periods[7] = { zone.period, zone.period,
|
||||
zone.period, zone.period,
|
||||
zone.period, zone.period,
|
||||
zone.period };
|
||||
uint16_t tempos[7] = { zone.tempo, zone.tempo,
|
||||
zone.tempo, zone.tempo,
|
||||
zone.tempo, zone.tempo,
|
||||
zone.tempo };
|
||||
|
||||
result = MultiModeAction(zones, periods, tempos, rainbow_colors[0], 7);
|
||||
}
|
||||
break;
|
||||
|
||||
case ALIENWARE_MODE_RAINBOW:
|
||||
{
|
||||
uint8_t zones[7] = { ALIENWARE_MODE_MORPH, ALIENWARE_MODE_MORPH,
|
||||
ALIENWARE_MODE_MORPH, ALIENWARE_MODE_MORPH,
|
||||
ALIENWARE_MODE_MORPH, ALIENWARE_MODE_MORPH,
|
||||
ALIENWARE_MODE_MORPH };
|
||||
uint16_t periods[7] = { zone.period, zone.period,
|
||||
zone.period, zone.period,
|
||||
zone.period, zone.period,
|
||||
zone.period };
|
||||
uint16_t tempos[7] = { zone.tempo, zone.tempo,
|
||||
zone.tempo, zone.tempo,
|
||||
zone.tempo, zone.tempo,
|
||||
zone.tempo };
|
||||
|
||||
result = MultiModeAction(zones, periods, tempos, rainbow_colors[zone_idx], 7);
|
||||
}
|
||||
break;
|
||||
|
||||
case ALIENWARE_MODE_BREATHING:
|
||||
{
|
||||
uint8_t zones[2] = { ALIENWARE_MODE_MORPH, ALIENWARE_MODE_MORPH };
|
||||
uint16_t periods[2] = { zone.period, zone.period };
|
||||
uint16_t tempos[2] = { zone.tempo, zone.tempo };
|
||||
RGBColor colors[2] = { zone.color[0], 0x0 };
|
||||
|
||||
result = MultiModeAction(zones, periods, tempos, colors, 2);
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
result = false;
|
||||
}
|
||||
|
||||
if(!result)
|
||||
{
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
result = UserAnimation(ALIENWARE_COMMAND_USER_ANIM_FINISH_PLAY, ALIENWARE_COMMAND_USER_ANIM_KEYBOARD, 0);
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| Don't update dirty flag if there's an error |
|
||||
\*-------------------------------------------------*/
|
||||
if(!result)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
dirty = false;
|
||||
}
|
||||
|
||||
void AlienwareController::UpdateController()
|
||||
{
|
||||
UpdateMode();
|
||||
UpdateDim();
|
||||
}
|
||||
@@ -0,0 +1,163 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AlienwareController.h |
|
||||
| |
|
||||
| Driver for Dell Alienware RGB USB controller |
|
||||
| |
|
||||
| Gabriel Marcano (gemarcano) 19 Apr 2021 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <string>
|
||||
#include <hidapi.h>
|
||||
#include "RGBController.h"
|
||||
|
||||
/*----------------------------------------------------------------------------------------------*\
|
||||
| Definitions for Alienware Controller |
|
||||
\*----------------------------------------------------------------------------------------------*/
|
||||
|
||||
#define ALIENWARE_REPORT_SIZE 33
|
||||
#define HIDAPI_ALIENWARE_REPORT_SIZE (ALIENWARE_REPORT_SIZE + 1)
|
||||
#define ALIENWARE_CONTROLLER_NAME "AlienWare Controller"
|
||||
enum
|
||||
{
|
||||
ALIENWARE_COMMAND_REPORT = 0x20, /* Set report type to get */
|
||||
ALIENWARE_COMMAND_USER_ANIM = 0x21, /* Set user animation settings */
|
||||
ALIENWARE_COMMAND_POWER_ANIM = 0x22, /* Set power animation settings */
|
||||
ALIENWARE_COMMAND_SELECT_ZONES = 0x23, /* Select zones to apply actions to */
|
||||
ALIENWARE_COMMAND_ADD_ACTION = 0x24, /* Set actions to apply */
|
||||
ALIENWARE_COMMAND_UNKNOWN1 = 0x25, /* Supposedly set event? */
|
||||
ALIENWARE_COMMAND_DIM = 0x26, /* Set dim percentage */
|
||||
ALIENWARE_COMMAND_SET_COLOR = 0x27, /* Unclear (causes color flash) */
|
||||
ALIENWARE_COMMAND_RESET = 0x28, /* Reset */
|
||||
ALIENWARE_COMMAND_ERASE_FLASH = 0xFF, /* Erases flash memory on controller */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
ALIENWARE_COMMAND_REPORT_FIRMWARE = 0x00, /* Get firmware verion */
|
||||
ALIENWARE_COMMAND_REPORT_STATUS = 0x01, /* Get status */
|
||||
ALIENWARE_COMMAND_REPORT_CONFIG = 0x02, /* Get firmware config */
|
||||
ALIENWARE_COMMAND_REPORT_ANIMATION = 0x03, /* Get animation count and last id */
|
||||
ALIENWARE_COMMAND_REPORT_UNKNOWN1 = 0x04, /* Get ELC animation by ID */
|
||||
ALIENWARE_COMMAND_REPORT_UNKNOWN2 = 0x05, /* Read series??? */
|
||||
ALIENWARE_COMMAND_REPORT_UNKNOWN3 = 0x06, /* Get action??? */
|
||||
ALIENWARE_COMMAND_REPORT_UNKNOWN4 = 0x07, /* Get Caldera status??? */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
ALIENWARE_COMMAND_USER_ANIM_NEW = 0x0001, /* Start new animation */
|
||||
ALIENWARE_COMMAND_USER_ANIM_FINISH_SAVE = 0x0002, /* Finish and save animation */
|
||||
ALIENWARE_COMMAND_USER_ANIM_FINISH_PLAY = 0x0003, /* Finish and play animation */
|
||||
ALIENWARE_COMMAND_USER_ANIM_REMOVE = 0x0004, /* Remove/erase animation */
|
||||
ALIENWARE_COMMAND_USER_ANIM_PLAY = 0x0005, /* Play animation */
|
||||
ALIENWARE_COMMAND_USER_ANIM_DEFAULT = 0x0006, /* Set default animation */
|
||||
ALIENWARE_COMMAND_USER_ANIM_STARTUP = 0x0007, /* Set startup animation */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
ALIENWARE_ANIM_DEFAULT_STARTUP = 0x0008, /* Default slot for startup */
|
||||
ALIENWARE_ANIM_DEFAULT = 0x0061, /* Default slot */
|
||||
ALIENWARE_COMMAND_USER_ANIM_KEYBOARD = 0xFFFF, /* Non-saved animation slot */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
ALIENWARE_MODE_COLOR = 0x00, /* Action to set color mode */
|
||||
ALIENWARE_MODE_PULSE = 0x01, /* Action to set pulse mode */
|
||||
ALIENWARE_MODE_MORPH = 0x02, /* Action to set morph mode */
|
||||
ALIENWARE_MODE_SPECTRUM, /* Abitrary code for spectrum mode */
|
||||
ALIENWARE_MODE_RAINBOW, /* Arbitrary code for rainbow wave mode */
|
||||
ALIENWARE_MODE_BREATHING, /* Arbitrary code for rainbow wave mode */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
ALIENWARE_TEMPO_MIN = 0x0064, /* Min tempo (as used by AWCC) */
|
||||
ALIENWARE_TEMPO_MAX = 0x00FA, /* Max tempo (as used by AWCC) */
|
||||
ALIENWARE_TEMPO_SPECTRUM = 0x000F, /* Used by Spectrum mode */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
ALIENWARE_DURATION_LONG = 0x09C4, /* Min tempo (as used by AWCC) */
|
||||
ALIENWARE_DURATION_MED = 0x05DC, /* Max tempo (as used by AWCC) */
|
||||
ALIENWARE_DURATION_SHORT = 0x01F3, /* Max tempo (as used by AWCC) */
|
||||
ALIENWARE_DURATION_SPECTRUM = 0x01AC, /* Used by Spectrum mode */
|
||||
};
|
||||
|
||||
typedef struct
|
||||
{
|
||||
unsigned char data[ALIENWARE_REPORT_SIZE];
|
||||
} AlienwareReport;
|
||||
|
||||
class AlienwareController
|
||||
{
|
||||
public:
|
||||
AlienwareController(hid_device* dev_handle, const hid_device_info& info, std::string name);
|
||||
~AlienwareController();
|
||||
|
||||
std::string GetSerialString();
|
||||
std::string GetDeviceLocation();
|
||||
std::string GetDeviceName();
|
||||
std::string GetFirmwareVersion();
|
||||
unsigned GetZoneCount();
|
||||
std::vector<const char*> GetZoneNames();
|
||||
|
||||
void SetColor(uint8_t zone, RGBColor color);
|
||||
void SetColor(uint8_t zone, RGBColor color1, RGBColor color2);
|
||||
void SetMode(uint8_t zone, uint8_t mode);
|
||||
void SetPeriod(uint8_t zone, uint16_t period);
|
||||
void SetTempo(uint8_t zone, uint16_t tempo);
|
||||
void SetDim(uint8_t zone, uint8_t dim);
|
||||
AlienwareReport GetStatus(uint8_t subcommand);
|
||||
|
||||
void UpdateDim();
|
||||
void UpdateMode();
|
||||
void UpdateController();
|
||||
|
||||
protected:
|
||||
hid_device* dev;
|
||||
|
||||
private:
|
||||
typedef struct
|
||||
{
|
||||
RGBColor color[2];
|
||||
uint8_t mode;
|
||||
uint16_t period;
|
||||
uint16_t tempo;
|
||||
uint8_t dim;
|
||||
} alienware_zone;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
unsigned char data[HIDAPI_ALIENWARE_REPORT_SIZE];
|
||||
} HidapiAlienwareReport;
|
||||
|
||||
std::string device_name;
|
||||
std::string location;
|
||||
std::vector<alienware_zone> zones;
|
||||
std::string serial_number;
|
||||
std::string version;
|
||||
std::vector<const char*> zone_names;
|
||||
bool dirty;
|
||||
bool dirty_dim;
|
||||
|
||||
HidapiAlienwareReport GetResponse();
|
||||
HidapiAlienwareReport Report(uint8_t subcommand);
|
||||
|
||||
bool Dim(std::vector<uint8_t> zones, double percent);
|
||||
bool UserAnimation(uint16_t subcommand, uint16_t animation, uint16_t duration);
|
||||
bool SelectZones(const std::vector<uint8_t>& zones);
|
||||
bool ModeAction(uint8_t mode, uint16_t duration, uint16_t tempo, RGBColor color);
|
||||
bool ModeAction(const uint8_t *mode, const uint16_t *duration, const uint16_t *tempo, const RGBColor *color, unsigned amount);
|
||||
bool MultiModeAction(const uint8_t *mode, const uint16_t *duration, const uint16_t *tempo, const RGBColor *color, unsigned amount);
|
||||
bool SetColorDirect(RGBColor color, std::vector<uint8_t> zones);
|
||||
bool UpdateDirect();
|
||||
bool Reset();
|
||||
};
|
||||
@@ -0,0 +1,39 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AlienwareControllerDetect.cpp |
|
||||
| |
|
||||
| Detector for Dell Alienware RGB USB controller |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "Detector.h"
|
||||
#include "AlienwareController.h"
|
||||
#include "RGBController_Alienware.h"
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Alienware vendor ID |
|
||||
\*---------------------------------------------------------*/
|
||||
#define ALIENWARE_VID 0x187C
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Alienware product ID |
|
||||
\*---------------------------------------------------------*/
|
||||
#define ALIENWARE_G_SERIES_PID1 0x0550
|
||||
#define ALIENWARE_G_SERIES_PID2 0x0551
|
||||
|
||||
void DetectAlienwareControllers(hid_device_info* info, const std::string& name)
|
||||
{
|
||||
hid_device* dev = hid_open_path(info->path);
|
||||
|
||||
if(dev)
|
||||
{
|
||||
AlienwareController* controller = new AlienwareController(dev, *info, name);
|
||||
RGBController_Alienware* rgb_controller = new RGBController_Alienware(controller);
|
||||
|
||||
ResourceManager::get()->RegisterRGBController(rgb_controller);
|
||||
}
|
||||
}
|
||||
|
||||
REGISTER_HID_DETECTOR("Dell G Series LED Controller", DetectAlienwareControllers, ALIENWARE_VID, ALIENWARE_G_SERIES_PID1);
|
||||
REGISTER_HID_DETECTOR("Dell G Series LED Controller", DetectAlienwareControllers, ALIENWARE_VID, ALIENWARE_G_SERIES_PID2);
|
||||
@@ -0,0 +1,285 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_Alienware.cpp |
|
||||
| |
|
||||
| RGBController for Dell Alienware RGB USB controller |
|
||||
| |
|
||||
| Gabriel Marcano (gemarcano) 19 Apr 2021 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include <thread>
|
||||
#include <chrono>
|
||||
#include "RGBController_Alienware.h"
|
||||
|
||||
/**------------------------------------------------------------------*\
|
||||
@name Alienware
|
||||
@category Keyboard
|
||||
@type USB
|
||||
@save :x:
|
||||
@direct :x:
|
||||
@effects :white_check_mark:
|
||||
@detectors DetectAlienwareControllers
|
||||
@comment
|
||||
\*-------------------------------------------------------------------*/
|
||||
|
||||
RGBController_Alienware::RGBController_Alienware(AlienwareController* controller_ptr)
|
||||
{
|
||||
controller = controller_ptr;
|
||||
|
||||
name = controller->GetDeviceName();
|
||||
vendor = "Alienware";
|
||||
type = DEVICE_TYPE_KEYBOARD;
|
||||
description = "Alienware USB Device";
|
||||
location = controller->GetDeviceLocation();
|
||||
serial = controller->GetSerialString();
|
||||
version = controller->GetFirmwareVersion();
|
||||
|
||||
mode Color;
|
||||
Color.name = "Static";
|
||||
Color.value = ALIENWARE_MODE_COLOR;
|
||||
Color.flags = MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
|
||||
Color.color_mode = MODE_COLORS_PER_LED;
|
||||
Color.colors_min = 1;
|
||||
Color.colors_max = 1;
|
||||
Color.brightness_min = 100;
|
||||
Color.brightness_max = 0;
|
||||
Color.brightness = 0;
|
||||
modes.push_back(Color);
|
||||
|
||||
mode Pulse;
|
||||
Pulse.name = "Flashing";
|
||||
Pulse.value = ALIENWARE_MODE_PULSE;
|
||||
Pulse.flags = MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_SPEED;
|
||||
Pulse.color_mode = MODE_COLORS_PER_LED;
|
||||
Pulse.colors_min = 1;
|
||||
Pulse.colors_max = 1;
|
||||
Pulse.speed_min = ALIENWARE_TEMPO_MIN;
|
||||
Pulse.speed_max = ALIENWARE_TEMPO_MAX;
|
||||
Pulse.speed = ALIENWARE_TEMPO_MIN;
|
||||
Pulse.brightness_min = 100;
|
||||
Pulse.brightness_max = 0;
|
||||
Pulse.brightness = 0;
|
||||
modes.push_back(Pulse);
|
||||
|
||||
mode Morph;
|
||||
Morph.name = "Morph";
|
||||
Morph.value = ALIENWARE_MODE_MORPH;
|
||||
Morph.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_SPEED;
|
||||
Morph.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Morph.colors_min = 2 * controller->GetZoneCount();
|
||||
Morph.colors_max = Morph.colors_min;
|
||||
Morph.colors.resize(Morph.colors_max);
|
||||
Morph.speed_min = ALIENWARE_TEMPO_MIN;
|
||||
Morph.speed_max = ALIENWARE_TEMPO_MAX;
|
||||
Morph.speed = ALIENWARE_TEMPO_MIN;
|
||||
Morph.brightness_min = 100;
|
||||
Morph.brightness_max = 0;
|
||||
Morph.brightness = 0;
|
||||
modes.push_back(Morph);
|
||||
|
||||
mode Spectrum;
|
||||
Spectrum.name = "Spectrum Cycle";
|
||||
Spectrum.value = ALIENWARE_MODE_SPECTRUM;
|
||||
Spectrum.flags = MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_SPEED;
|
||||
Spectrum.color_mode = MODE_COLORS_NONE;
|
||||
Spectrum.speed_min = ALIENWARE_TEMPO_SPECTRUM;
|
||||
Spectrum.speed_max = ALIENWARE_TEMPO_MAX;
|
||||
Spectrum.speed = ALIENWARE_TEMPO_SPECTRUM;
|
||||
Spectrum.brightness_min = 100;
|
||||
Spectrum.brightness_max = 0;
|
||||
Spectrum.brightness = 0;
|
||||
modes.push_back(Spectrum);
|
||||
|
||||
mode Rainbow;
|
||||
Rainbow.name = "Rainbow Wave";
|
||||
Rainbow.value = ALIENWARE_MODE_RAINBOW;
|
||||
Rainbow.flags = MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_SPEED;
|
||||
Rainbow.color_mode = MODE_COLORS_NONE;
|
||||
Rainbow.speed_min = ALIENWARE_TEMPO_SPECTRUM;
|
||||
Rainbow.speed_max = ALIENWARE_TEMPO_MAX;
|
||||
Rainbow.speed = ALIENWARE_TEMPO_SPECTRUM;
|
||||
Rainbow.brightness_min = 100;
|
||||
Rainbow.brightness_max = 0;
|
||||
Rainbow.brightness = 0;
|
||||
modes.push_back(Rainbow);
|
||||
|
||||
mode Breathing;
|
||||
Breathing.name = "Breathing";
|
||||
Breathing.value = ALIENWARE_MODE_BREATHING;
|
||||
Breathing.flags = MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_SPEED;
|
||||
Breathing.color_mode = MODE_COLORS_PER_LED;
|
||||
Breathing.colors_min = 1;
|
||||
Breathing.colors_max = 1;
|
||||
Breathing.speed_min = ALIENWARE_TEMPO_MIN;
|
||||
Breathing.speed_max = ALIENWARE_TEMPO_MAX;
|
||||
Breathing.speed = ALIENWARE_TEMPO_MIN;
|
||||
Breathing.brightness_min = 100;
|
||||
Breathing.brightness_max = 0;
|
||||
Breathing.brightness = 0;
|
||||
modes.push_back(Breathing);
|
||||
|
||||
SetupZones();
|
||||
|
||||
controller->UpdateDim();
|
||||
}
|
||||
|
||||
void RGBController_Alienware::SetupZones()
|
||||
{
|
||||
/*-------------------------------------------------*\
|
||||
| Set zones and leds |
|
||||
\*-------------------------------------------------*/
|
||||
std::vector<const char*> zone_names = controller->GetZoneNames();
|
||||
|
||||
for(unsigned int zone_idx = 0; zone_idx < controller->GetZoneCount(); zone_idx++)
|
||||
{
|
||||
zone new_zone;
|
||||
|
||||
new_zone.name = zone_names[zone_idx];
|
||||
new_zone.type = ZONE_TYPE_SINGLE;
|
||||
new_zone.leds_min = 1;
|
||||
new_zone.leds_max = 1;
|
||||
new_zone.leds_count = 1;
|
||||
new_zone.matrix_map = nullptr;
|
||||
|
||||
zones.emplace_back(new_zone);
|
||||
}
|
||||
|
||||
for(unsigned int led_idx = 0; led_idx < zones.size(); led_idx++)
|
||||
{
|
||||
led new_led;
|
||||
|
||||
new_led.name = zones[led_idx].name + std::string(" LED");
|
||||
|
||||
leds.emplace_back(new_led);
|
||||
}
|
||||
|
||||
SetupColors();
|
||||
}
|
||||
|
||||
void RGBController_Alienware::ResizeZone(int /*zone*/, int /*new_size*/)
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| This device does not support resizing zones |
|
||||
\*---------------------------------------------------------*/
|
||||
}
|
||||
|
||||
void RGBController_Alienware::DeviceUpdateLEDs()
|
||||
{
|
||||
DeviceUpdateMode();
|
||||
}
|
||||
|
||||
void RGBController_Alienware::UpdateZoneLEDs(int /*zone*/)
|
||||
{
|
||||
DeviceUpdateLEDs();
|
||||
}
|
||||
|
||||
void RGBController_Alienware::UpdateSingleLED(int led)
|
||||
{
|
||||
UpdateZoneLEDs(led);
|
||||
}
|
||||
|
||||
static bool modes_eq(const mode& mode1, const mode& mode2)
|
||||
{
|
||||
return( ( mode1.name == mode2.name )
|
||||
&& ( mode1.value == mode2.value )
|
||||
&& ( mode1.flags == mode2.flags )
|
||||
&& ( mode1.speed_min == mode2.speed_min )
|
||||
&& ( mode1.speed_max == mode2.speed_max )
|
||||
&& ( mode1.colors_min == mode2.colors_min )
|
||||
&& ( mode1.colors_max == mode2.colors_max )
|
||||
&& ( mode1.speed == mode2.speed )
|
||||
&& ( mode1.direction == mode2.direction )
|
||||
&& ( mode1.color_mode == mode2.color_mode )
|
||||
&& ( mode1.colors == mode2.colors )
|
||||
&& ( mode1.brightness == mode2.brightness )
|
||||
&& ( mode1.brightness_min == mode2.brightness_min )
|
||||
&& ( mode1.brightness_max == mode2.brightness_max ) );
|
||||
}
|
||||
|
||||
void RGBController_Alienware::DeviceUpdateMode()
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| Copy mode to get the current state-- this is racy, as the |
|
||||
| UI thread can be actively modifying this variable |
|
||||
\*---------------------------------------------------------*/
|
||||
int current_mode_idx = active_mode;
|
||||
mode current_mode = modes[current_mode_idx];
|
||||
|
||||
bool done = false;
|
||||
|
||||
while(!done)
|
||||
{
|
||||
/*-----------------------------------------------------*\
|
||||
| Setup state per zone |
|
||||
\*-----------------------------------------------------*/
|
||||
for(uint8_t zone_idx = 0; zone_idx < zones.size(); zone_idx++)
|
||||
{
|
||||
zone current_zone = zones[zone_idx];
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| Some modes use 2000ms (0x07D0) for their duration,|
|
||||
| per traces |
|
||||
\*-------------------------------------------------*/
|
||||
uint16_t period = 0x07d0;
|
||||
|
||||
controller->SetMode(zone_idx, current_mode.value);
|
||||
|
||||
switch(current_mode_idx)
|
||||
{
|
||||
case ALIENWARE_MODE_COLOR:
|
||||
controller->SetPeriod(zone_idx, period);
|
||||
controller->SetColor( zone_idx, colors[current_zone.start_idx]);
|
||||
controller->SetTempo( zone_idx, ALIENWARE_TEMPO_MAX);
|
||||
controller->SetDim( zone_idx, modes[current_mode_idx].brightness);
|
||||
break;
|
||||
|
||||
case ALIENWARE_MODE_PULSE:
|
||||
controller->SetPeriod(zone_idx, period);
|
||||
controller->SetColor( zone_idx, colors[current_zone.start_idx]);
|
||||
controller->SetTempo( zone_idx, current_mode.speed);
|
||||
controller->SetDim( zone_idx, modes[current_mode_idx].brightness);
|
||||
break;
|
||||
|
||||
case ALIENWARE_MODE_MORPH:
|
||||
controller->SetPeriod(zone_idx, period);
|
||||
controller->SetColor( zone_idx, current_mode.colors[zone_idx * 2], current_mode.colors[(zone_idx * 2) + 1]);
|
||||
controller->SetTempo( zone_idx, current_mode.speed);
|
||||
controller->SetDim( zone_idx, modes[current_mode_idx].brightness);
|
||||
break;
|
||||
|
||||
case ALIENWARE_MODE_SPECTRUM:
|
||||
case ALIENWARE_MODE_RAINBOW:
|
||||
controller->SetPeriod(zone_idx, ALIENWARE_DURATION_SPECTRUM);
|
||||
controller->SetTempo( zone_idx, current_mode.speed);
|
||||
controller->SetDim( zone_idx, modes[current_mode_idx].brightness);
|
||||
break;
|
||||
|
||||
case ALIENWARE_MODE_BREATHING:
|
||||
controller->SetPeriod(zone_idx, period);
|
||||
controller->SetColor( zone_idx, colors[current_zone.start_idx], 0x0);
|
||||
controller->SetTempo( zone_idx, current_mode.speed);
|
||||
controller->SetDim( zone_idx, modes[current_mode_idx].brightness);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Due to rate-limiting, this can take more than one |
|
||||
| second to execute |
|
||||
\*-----------------------------------------------------*/
|
||||
controller->UpdateController();
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Re-run update if there's anything that's changed from |
|
||||
| under us... |
|
||||
\*-----------------------------------------------------*/
|
||||
int new_current_mode_idx = active_mode;
|
||||
mode new_current_mode = modes[current_mode_idx];
|
||||
|
||||
done = (current_mode_idx == new_current_mode_idx && modes_eq(new_current_mode, current_mode));
|
||||
current_mode_idx = new_current_mode_idx;
|
||||
current_mode = new_current_mode;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,36 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_Alienware.h |
|
||||
| |
|
||||
| RGBController for Dell Alienware RGB USB controller |
|
||||
| |
|
||||
| Gabriel Marcano (gemarcano) 19 Apr 2021 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <chrono>
|
||||
#include "RGBController.h"
|
||||
#include "AlienwareController.h"
|
||||
|
||||
class RGBController_Alienware : public RGBController
|
||||
{
|
||||
public:
|
||||
RGBController_Alienware(AlienwareController* controller_ptr);
|
||||
|
||||
void SetupZones();
|
||||
|
||||
void ResizeZone(int zone, int new_size);
|
||||
|
||||
void DeviceUpdateLEDs();
|
||||
void UpdateZoneLEDs(int zone);
|
||||
void UpdateSingleLED(int led);
|
||||
|
||||
void DeviceUpdateMode();
|
||||
|
||||
private:
|
||||
AlienwareController* controller;
|
||||
std::chrono::steady_clock::time_point last_packet_ts;
|
||||
};
|
||||
+453
@@ -0,0 +1,453 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AlienwareAW410KController.cpp |
|
||||
| |
|
||||
| Driver for Alienware AW410K keyboard |
|
||||
| |
|
||||
| based on AW510K controller by Mohamad Sallal (msallal) |
|
||||
| Dominik Mikolajczyk (dmiko) 23 Oct 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include <cstring>
|
||||
#include "AlienwareAW410KController.h"
|
||||
#include "StringUtils.h"
|
||||
|
||||
AlienwareAW410KController::AlienwareAW410KController(hid_device* dev_handle, const char* path, std::string dev_name)
|
||||
{
|
||||
dev = dev_handle;
|
||||
location = path;
|
||||
name = dev_name;
|
||||
|
||||
SendCommit();
|
||||
}
|
||||
|
||||
AlienwareAW410KController::~AlienwareAW410KController()
|
||||
{
|
||||
hid_close(dev);
|
||||
}
|
||||
|
||||
std::string AlienwareAW410KController::GetDeviceLocation()
|
||||
{
|
||||
return("HID: " + location);
|
||||
}
|
||||
|
||||
std::string AlienwareAW410KController::GetDeviceName()
|
||||
{
|
||||
return(name);
|
||||
}
|
||||
|
||||
std::string AlienwareAW410KController::GetSerialString()
|
||||
{
|
||||
wchar_t serial_string[128];
|
||||
int ret = hid_get_serial_number_string(dev, serial_string, 128);
|
||||
|
||||
if(ret != 0)
|
||||
{
|
||||
return("");
|
||||
}
|
||||
|
||||
return(StringUtils::wstring_to_string(serial_string));
|
||||
}
|
||||
|
||||
void AlienwareAW410KController::SendCommit()
|
||||
{
|
||||
unsigned char usb_buf[65];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up Commit packet |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x00] = 0x00;
|
||||
usb_buf[0x01] = 0x05;
|
||||
usb_buf[0x02] = 0x01;
|
||||
usb_buf[0x0A] = 0x10;
|
||||
usb_buf[0x0B] = 0x0A;
|
||||
usb_buf[0x0C] = 0x01;
|
||||
usb_buf[0x0D] = 0x02;
|
||||
usb_buf[0x0E] = 0x01;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_write(dev, usb_buf, 65);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Delay 20 milliseconds |
|
||||
\*-----------------------------------------------------*/
|
||||
std::this_thread::sleep_for(std::chrono::milliseconds(20));
|
||||
}
|
||||
|
||||
void AlienwareAW410KController::SendfeatureReport
|
||||
(
|
||||
unsigned char first_byte,
|
||||
unsigned char second_byte,
|
||||
unsigned char third_byte,
|
||||
unsigned char forth_byte
|
||||
)
|
||||
{
|
||||
unsigned char usb_buf[65];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up Feature report packet |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x00] = 0x00;
|
||||
usb_buf[0x01] = first_byte;
|
||||
usb_buf[0x02] = second_byte;
|
||||
usb_buf[0x03] = third_byte;
|
||||
usb_buf[0x04] = forth_byte;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send Feature report packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_send_feature_report(dev, usb_buf, 65);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Delay 10 milliseconds |
|
||||
\*-----------------------------------------------------*/
|
||||
std::this_thread::sleep_for(std::chrono::milliseconds(10));
|
||||
}
|
||||
|
||||
void AlienwareAW410KController::SendEdit()
|
||||
{
|
||||
unsigned char usb_buf[65];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up Edit packet |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x00] = 0x00;
|
||||
usb_buf[0x01] = 0x01;
|
||||
usb_buf[0x02] = 0x00;
|
||||
usb_buf[0x03] = 0x01;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_write(dev, usb_buf, 65);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Delay 2 milliseconds |
|
||||
\*-----------------------------------------------------*/
|
||||
std::this_thread::sleep_for(std::chrono::milliseconds(2));
|
||||
}
|
||||
|
||||
void AlienwareAW410KController::SendInitialize()
|
||||
{
|
||||
unsigned char usb_buf[65];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up Commit packet |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x00] = 0x00;
|
||||
usb_buf[0x01] = 0x0E;
|
||||
usb_buf[0x02] = 0x01;
|
||||
usb_buf[0x03] = 0x00;
|
||||
usb_buf[0x04] = 0x01;
|
||||
usb_buf[0x05] = 0xAD;
|
||||
usb_buf[0x06] = 0x80;
|
||||
usb_buf[0x07] = 0x10;
|
||||
usb_buf[0x08] = 0xA5;
|
||||
usb_buf[0x0A] = 0x0A;
|
||||
usb_buf[0x12] = 0x01;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_write(dev, usb_buf, 65);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Delay 2 milliseconds |
|
||||
\*-----------------------------------------------------*/
|
||||
std::this_thread::sleep_for(std::chrono::milliseconds(2));
|
||||
}
|
||||
|
||||
void AlienwareAW410KController::SetDirect
|
||||
(
|
||||
unsigned char /*zone*/,
|
||||
unsigned char r,
|
||||
unsigned char g,
|
||||
unsigned char b
|
||||
)
|
||||
{
|
||||
unsigned char usb_buf[65];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up Lighting Control packet |
|
||||
\*-----------------------------------------------------*/
|
||||
|
||||
usb_buf[0x00] = 0x00;
|
||||
usb_buf[0x01] = 0x05;
|
||||
usb_buf[0x02] = 0x01;
|
||||
usb_buf[0x03] = 0x01;
|
||||
usb_buf[0x04] = r;
|
||||
usb_buf[0x05] = g;
|
||||
usb_buf[0x06] = b;
|
||||
usb_buf[0x0B] = 0x0A;
|
||||
usb_buf[0x0D] = 0x01;
|
||||
usb_buf[0x0E] = 0x01;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_write(dev, (unsigned char *)usb_buf, 65);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Delay 2 milliseconds |
|
||||
\*-----------------------------------------------------*/
|
||||
std::this_thread::sleep_for(std::chrono::milliseconds(2));
|
||||
}
|
||||
|
||||
void AlienwareAW410KController::SendDirectOn
|
||||
(
|
||||
std::vector<SelectedButtons> &frame_data
|
||||
)
|
||||
{
|
||||
SendfeatureReport(0x0E, (unsigned char)frame_data.size(), 0x00, 0x01);
|
||||
|
||||
/*-----------------------------------------------*\
|
||||
| To Guarantee the data are always %4 =0 append |
|
||||
| zeros at end of last packet |
|
||||
\*-----------------------------------------------*/
|
||||
for(unsigned int i = 0; i < (frame_data.size() % 4); i++)
|
||||
{
|
||||
SelectedButtons key;
|
||||
key.idx = 0x00;
|
||||
key.red = 0x00;
|
||||
key.green = 0x00;
|
||||
key.blue = 0x00;
|
||||
|
||||
frame_data.push_back(key);
|
||||
}
|
||||
|
||||
unsigned char usb_buf[65];
|
||||
unsigned int frame_idx = 0;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, 65);
|
||||
|
||||
for(unsigned int packet_idx = 0; packet_idx < frame_data.size(); packet_idx++)
|
||||
{
|
||||
usb_buf[0x00] = 0x00;
|
||||
usb_buf[0x01] = 0x0E;
|
||||
usb_buf[0x02] = 0x01;
|
||||
usb_buf[0x03] = 0x00;
|
||||
usb_buf[0x04] = ++frame_idx;
|
||||
usb_buf[0x05] = frame_data[packet_idx].idx;
|
||||
usb_buf[0x06] = 0x81;
|
||||
usb_buf[0x07] = 0x00;
|
||||
usb_buf[0x08] = 0xA5;
|
||||
usb_buf[0x0A] = 0x0A;
|
||||
usb_buf[0x0B] = frame_data[packet_idx].red;
|
||||
usb_buf[0x0C] = frame_data[packet_idx].green;
|
||||
usb_buf[0x0D] = frame_data[packet_idx].blue;
|
||||
usb_buf[0x12] = 0x01;
|
||||
|
||||
usb_buf[0x14] = frame_data[++packet_idx].idx;
|
||||
usb_buf[0x15] = 0x81;
|
||||
usb_buf[0x16] = 0x00;
|
||||
usb_buf[0x17] = 0xA5;
|
||||
usb_buf[0x19] = 0x0A;
|
||||
usb_buf[0x1A] = frame_data[packet_idx].red;
|
||||
usb_buf[0x1B] = frame_data[packet_idx].green;
|
||||
usb_buf[0x1C] = frame_data[packet_idx].blue;
|
||||
usb_buf[0x21] = 0x01;
|
||||
|
||||
usb_buf[0x23] = frame_data[++packet_idx].idx;
|
||||
usb_buf[0x24] = 0x81;
|
||||
usb_buf[0x25] = 0x00;
|
||||
usb_buf[0x26] = 0xA5;
|
||||
usb_buf[0x28] = 0x0A;
|
||||
usb_buf[0x29] = frame_data[packet_idx].red;
|
||||
usb_buf[0x2A] = frame_data[packet_idx].green;
|
||||
usb_buf[0x2B] = frame_data[packet_idx].blue;
|
||||
usb_buf[0x30] = 0x01;
|
||||
|
||||
usb_buf[0x32] = frame_data[++packet_idx].idx;
|
||||
usb_buf[0x33] = 0x81;
|
||||
usb_buf[0x34] = 0x00;
|
||||
usb_buf[0x35] = 0xA5;
|
||||
usb_buf[0x37] = 0x0A;
|
||||
usb_buf[0x38] = frame_data[packet_idx].red;
|
||||
usb_buf[0x39] = frame_data[packet_idx].green;
|
||||
usb_buf[0x3A] = frame_data[packet_idx].blue;
|
||||
usb_buf[0x3F] = 0x01;
|
||||
|
||||
hid_write(dev, (unsigned char *)usb_buf, 65);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void AlienwareAW410KController::SetMode
|
||||
(
|
||||
unsigned char mode,
|
||||
unsigned char speed,
|
||||
unsigned char direction,
|
||||
unsigned char colorMode,
|
||||
unsigned char red,
|
||||
unsigned char green,
|
||||
unsigned char blue
|
||||
)
|
||||
{
|
||||
SendMode(ALIENWARE_AW410K_ZONE_MODE_KEYBOARD, mode, speed, direction, colorMode, red, green, blue);
|
||||
SendCommit();
|
||||
}
|
||||
|
||||
void AlienwareAW410KController::UpdateSingleLED
|
||||
(
|
||||
unsigned char led,
|
||||
unsigned char red,
|
||||
unsigned char green,
|
||||
unsigned char blue
|
||||
)
|
||||
{
|
||||
SendfeatureReport(0x0E, 0x01, 0x00, 0x01);
|
||||
|
||||
unsigned char usb_buf[65];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up Single LED packet |
|
||||
\*-----------------------------------------------------*/
|
||||
|
||||
usb_buf[0x00] = 0x00;
|
||||
usb_buf[0x01] = 0x0E;
|
||||
usb_buf[0x02] = 0x01;
|
||||
usb_buf[0x03] = 0x00;
|
||||
usb_buf[0x04] = 0x01;
|
||||
usb_buf[0x05] = led;
|
||||
usb_buf[0x06] = 0x81;
|
||||
usb_buf[0x07] = 0x00;
|
||||
usb_buf[0x08] = 0xA5;
|
||||
usb_buf[0x09] = 0x00;
|
||||
usb_buf[0x0A] = 0x0A;
|
||||
usb_buf[0x0B] = red;
|
||||
usb_buf[0x0C] = green;
|
||||
usb_buf[0x0D] = blue;
|
||||
usb_buf[0x12] = 0x01;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_write(dev, usb_buf, 65);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Delay 20 milliseconds |
|
||||
\*-----------------------------------------------------*/
|
||||
std::this_thread::sleep_for(std::chrono::milliseconds(20));
|
||||
|
||||
}
|
||||
void AlienwareAW410KController::SendMode
|
||||
(
|
||||
unsigned char /*zone*/,
|
||||
unsigned char mode,
|
||||
unsigned char speed,
|
||||
unsigned char direction,
|
||||
unsigned char colorMode,
|
||||
unsigned char red,
|
||||
unsigned char green,
|
||||
unsigned char blue
|
||||
)
|
||||
{
|
||||
unsigned char usb_buf[65];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up Mode Control packet |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x00] = 0x00;
|
||||
usb_buf[0x01] = 0x05;
|
||||
usb_buf[0x02] = 0x01;
|
||||
usb_buf[0x03] = mode;
|
||||
usb_buf[0x04] = red;
|
||||
usb_buf[0x05] = green;
|
||||
usb_buf[0x06] = blue;
|
||||
usb_buf[0x0A] = speed;
|
||||
usb_buf[0x0B] = 0x0A;
|
||||
usb_buf[0x0D] = 0x01;
|
||||
usb_buf[0x0E] = colorMode;
|
||||
usb_buf[0x0F] = direction;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_write(dev, usb_buf, 65);
|
||||
}
|
||||
|
||||
void AlienwareAW410KController::SetMorphMode
|
||||
(
|
||||
unsigned char mode,
|
||||
unsigned char speed,
|
||||
unsigned char red1,
|
||||
unsigned char green1,
|
||||
unsigned char blue1,
|
||||
unsigned char red2,
|
||||
unsigned char green2,
|
||||
unsigned char blue2
|
||||
)
|
||||
{
|
||||
unsigned char usb_buf[65];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up Morph Mode packet |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x00] = 0x00;
|
||||
usb_buf[0x01] = 0x05;
|
||||
usb_buf[0x02] = 0x01;
|
||||
usb_buf[0x03] = mode;
|
||||
usb_buf[0x04] = red1;
|
||||
usb_buf[0x05] = green1;
|
||||
usb_buf[0x06] = blue1;
|
||||
usb_buf[0x07] = red2;
|
||||
usb_buf[0x08] = green2;
|
||||
usb_buf[0x09] = blue2;
|
||||
usb_buf[0x0E] = 0x02;
|
||||
usb_buf[0x0A] = speed;
|
||||
usb_buf[0x0B] = 0x0A;
|
||||
usb_buf[0x0D] = 0x01;
|
||||
usb_buf[0x0E] = ALIENWARE_AW410K_TWO_USER_DEFINED_COLOR_MODE;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_write(dev, usb_buf, 65);
|
||||
}
|
||||
+157
@@ -0,0 +1,157 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AlienwareAW410KController.h |
|
||||
| |
|
||||
| Driver for Alienware AW410K keyboard |
|
||||
| |
|
||||
| based on AW510K controller by Mohamad Sallal (msallal) |
|
||||
| Dominik Mikolajczyk (dmiko) 23 Oct 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <string>
|
||||
#include <hidapi.h>
|
||||
#include "RGBController.h"
|
||||
|
||||
enum
|
||||
{
|
||||
ALIENWARE_AW410K_ZONE_MODE_KEYBOARD = 0x01,
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD = 0x01,
|
||||
ALIENWARE_AW410K_ZONE_DIRECT_MEDIA = 0x02,
|
||||
ALIENWARE_AW410K_ZONE_DIRECT_INDICATORS = 0x40,
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
ALIENWARE_AW410K_MODE_OFF = 0x00,
|
||||
ALIENWARE_AW410K_MODE_DIRECT = 0x01,
|
||||
ALIENWARE_AW410K_MODE_PULSE = 0x02,
|
||||
ALIENWARE_AW410K_MODE_MORPH = 0x03,
|
||||
ALIENWARE_AW410K_MODE_BREATHING = 0x07,
|
||||
ALIENWARE_AW410K_MODE_SPECTRUM = 0x08,
|
||||
ALIENWARE_AW410K_MODE_SINGLE_WAVE = 0x0F,
|
||||
ALIENWARE_AW410K_MODE_RAINBOW_WAVE = 0x10,
|
||||
ALIENWARE_AW410K_MODE_SCANNER = 0x11,
|
||||
ALIENWARE_AW410K_MODE_STATIC = 0x13,
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
ALIENWARE_AW410K_SPEED_SLOWEST = 0x2D, /* Slowest speed */
|
||||
ALIENWARE_AW410K_SPEED_NORMAL = 0x19, /* Normal speed */
|
||||
ALIENWARE_AW410K_SPEED_FASTEST = 0x0A, /* Fastest speed */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
ALIENWARE_AW410K_DIRECTION_LEFT_TO_RIGHT = 0x01,
|
||||
ALIENWARE_AW410K_DIRECTION_RIGHT_TO_LEFT = 0x02,
|
||||
ALIENWARE_AW410K_DIRECTION_TOP_TO_BOTTOM = 0x03,
|
||||
ALIENWARE_AW410K_DIRECTION_BOTTOM_TO_TOP = 0x04,
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
ALIENWARE_AW410K_SINGLE_COLOR_MODE = 0x01,
|
||||
ALIENWARE_AW410K_TWO_USER_DEFINED_COLOR_MODE= 0x02,
|
||||
ALIENWARE_AW410K_RANBOW_COLOR_MODE = 0x03,
|
||||
};
|
||||
|
||||
struct SelectedButtons
|
||||
{
|
||||
unsigned char idx;
|
||||
unsigned char red;
|
||||
unsigned char green;
|
||||
unsigned char blue;
|
||||
};
|
||||
|
||||
class AlienwareAW410KController
|
||||
{
|
||||
public:
|
||||
AlienwareAW410KController(hid_device* dev_handle, const char* path, std::string dev_name);
|
||||
~AlienwareAW410KController();
|
||||
|
||||
std::string GetDeviceLocation();
|
||||
std::string GetDeviceName();
|
||||
std::string GetSerialString();
|
||||
|
||||
void SendInitialize();
|
||||
void SendCommit();
|
||||
void SendfeatureReport
|
||||
(
|
||||
unsigned char first_byte,
|
||||
unsigned char second_byte,
|
||||
unsigned char third_byte,
|
||||
unsigned char forth_byte
|
||||
);
|
||||
|
||||
void SendEdit();
|
||||
|
||||
void SetDirect
|
||||
(
|
||||
unsigned char zone,
|
||||
unsigned char r,
|
||||
unsigned char g,
|
||||
unsigned char b
|
||||
);
|
||||
|
||||
void SendDirectOn
|
||||
(
|
||||
std::vector<SelectedButtons> &frame_data
|
||||
);
|
||||
|
||||
void SetMode
|
||||
(
|
||||
unsigned char mode,
|
||||
unsigned char speed,
|
||||
unsigned char direction,
|
||||
unsigned char colorMode,
|
||||
unsigned char red,
|
||||
unsigned char green,
|
||||
unsigned char blue
|
||||
);
|
||||
|
||||
void SetMorphMode
|
||||
(
|
||||
unsigned char mode,
|
||||
unsigned char speed,
|
||||
unsigned char red1,
|
||||
unsigned char green1,
|
||||
unsigned char blue1,
|
||||
unsigned char red2,
|
||||
unsigned char green2,
|
||||
unsigned char blue2
|
||||
);
|
||||
|
||||
void UpdateSingleLED
|
||||
(
|
||||
unsigned char led,
|
||||
unsigned char red,
|
||||
unsigned char green,
|
||||
unsigned char blue
|
||||
);
|
||||
|
||||
private:
|
||||
hid_device* dev;
|
||||
std::string location;
|
||||
std::string name;
|
||||
|
||||
void SendMode
|
||||
(
|
||||
unsigned char zone,
|
||||
unsigned char mode,
|
||||
unsigned char speed,
|
||||
unsigned char direction,
|
||||
unsigned char colorMode,
|
||||
unsigned char red,
|
||||
unsigned char green,
|
||||
unsigned char blue
|
||||
);
|
||||
};
|
||||
+482
@@ -0,0 +1,482 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_AlienwareAW410K.cpp |
|
||||
| |
|
||||
| RGBController for Alienware AW410K keyboard |
|
||||
| |
|
||||
| based on AW510K controller by Mohamad Sallal (msallal) |
|
||||
| Dominik Mikolajczyk (dmiko) 23 Oct 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include <iterator>
|
||||
#include "RGBControllerKeyNames.h"
|
||||
#include "RGBController_AlienwareAW410K.h"
|
||||
|
||||
//0xFFFFFFFF indicates an unused entry in matrix
|
||||
#define NA 0xFFFFFFFF
|
||||
|
||||
int GetAW410K_WaveDirection(int input);
|
||||
|
||||
static unsigned int matrix_map[6][24] =
|
||||
{ { 0, NA, 1, 2, 3, 4, NA, 5, 6, 7, 8, 9, 10, 11, 12, NA, 13, 14, 15, NA, NA, 16, 17, 18 },
|
||||
{ 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, NA, NA, 33, 34, 35, NA, 36, 37, 38, 39 },
|
||||
{ 40, NA, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, NA, 54, 55, 56, NA, 57, 58, 59, 60 },
|
||||
{ 61, NA, 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, NA, 73, NA, NA, NA, NA, NA, 74, 75, 76, NA },
|
||||
{ 77, NA, NA, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, NA, NA, NA, 89, NA, NA, 90, 91, 92, 93 },
|
||||
{ 94, NA, 95, 96, NA, NA, NA, 97, NA, NA, NA, 98, 99, 100, 101, NA, 102, 103, 104, NA, 105, NA, 106, NA }};
|
||||
|
||||
static const char* zone_names[] =
|
||||
{
|
||||
"AW410K",
|
||||
};
|
||||
|
||||
static zone_type zone_types[] =
|
||||
{
|
||||
ZONE_TYPE_MATRIX,
|
||||
};
|
||||
|
||||
static const unsigned int zone_sizes[] =
|
||||
{
|
||||
107,
|
||||
};
|
||||
|
||||
typedef struct
|
||||
{
|
||||
const char * name;
|
||||
const unsigned char zone;
|
||||
const unsigned char idx;
|
||||
} aw410k_led_type;
|
||||
|
||||
static const aw410k_led_type led_names[] =
|
||||
{
|
||||
/* Key Label Zone, Index */
|
||||
{ KEY_EN_ESCAPE, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0xB0 },
|
||||
{ KEY_EN_F1, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x98 },
|
||||
{ KEY_EN_F2, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x90 },
|
||||
{ KEY_EN_F3, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x88 },
|
||||
{ KEY_EN_F4, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x80 },
|
||||
{ KEY_EN_F5, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x70 },
|
||||
{ KEY_EN_F6, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x68 },
|
||||
{ KEY_EN_F7, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x60 },
|
||||
{ KEY_EN_F8, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x58 },
|
||||
{ KEY_EN_F9, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x50 },
|
||||
{ KEY_EN_F10, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x48 },
|
||||
{ KEY_EN_F11, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x40 },
|
||||
{ KEY_EN_F12, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x38 },
|
||||
{ KEY_EN_PRINT_SCREEN, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x30 },
|
||||
{ KEY_EN_SCROLL_LOCK, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x28 },
|
||||
{ KEY_EN_PAUSE_BREAK, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x20 },
|
||||
{ KEY_EN_MEDIA_MUTE, ALIENWARE_AW410K_ZONE_DIRECT_MEDIA, 0x18 },
|
||||
{ KEY_EN_MEDIA_VOLUME_DOWN, ALIENWARE_AW410K_ZONE_DIRECT_MEDIA, 0x10 },
|
||||
{ KEY_EN_MEDIA_VOLUME_UP, ALIENWARE_AW410K_ZONE_DIRECT_MEDIA, 0x08 },
|
||||
{ KEY_EN_BACK_TICK, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0xB1 },
|
||||
{ KEY_EN_1, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0xA1 },
|
||||
{ KEY_EN_2, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x99 },
|
||||
{ KEY_EN_3, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x91 },
|
||||
{ KEY_EN_4, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x89 },
|
||||
{ KEY_EN_5, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x81 },
|
||||
{ KEY_EN_6, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x79 },
|
||||
{ KEY_EN_7, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x71 },
|
||||
{ KEY_EN_8, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x69 },
|
||||
{ KEY_EN_9, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x61 },
|
||||
{ KEY_EN_0, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x59 },
|
||||
{ KEY_EN_MINUS, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x51 },
|
||||
{ KEY_EN_EQUALS, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x49 },
|
||||
{ KEY_EN_BACKSPACE, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x39 },
|
||||
{ KEY_EN_INSERT, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x31 },
|
||||
{ KEY_EN_HOME, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x29 },
|
||||
{ KEY_EN_PAGE_UP, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x21 },
|
||||
{ KEY_EN_NUMPAD_LOCK, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x19 },
|
||||
{ KEY_EN_NUMPAD_DIVIDE, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x11 },
|
||||
{ KEY_EN_NUMPAD_TIMES, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x09 },
|
||||
{ KEY_EN_NUMPAD_MINUS, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x01 },
|
||||
{ KEY_EN_TAB, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0xB2 },
|
||||
{ KEY_EN_Q, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0xA2 },
|
||||
{ KEY_EN_W, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x9A },
|
||||
{ KEY_EN_E, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x92 },
|
||||
{ KEY_EN_R, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x8A },
|
||||
{ KEY_EN_T, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x82 },
|
||||
{ KEY_EN_Y, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x7A },
|
||||
{ KEY_EN_U, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x72 },
|
||||
{ KEY_EN_I, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x6A },
|
||||
{ KEY_EN_O, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x62 },
|
||||
{ KEY_EN_P, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x5A },
|
||||
{ KEY_EN_LEFT_BRACKET, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x52 },
|
||||
{ KEY_EN_RIGHT_BRACKET, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x4A },
|
||||
{ KEY_EN_ANSI_BACK_SLASH, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x42 },
|
||||
{ KEY_EN_DELETE, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x32 },
|
||||
{ KEY_EN_END, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x2A },
|
||||
{ KEY_EN_PAGE_DOWN, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x22 },
|
||||
{ KEY_EN_NUMPAD_7, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x1A },
|
||||
{ KEY_EN_NUMPAD_8, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x12 },
|
||||
{ KEY_EN_NUMPAD_9, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x0A },
|
||||
{ KEY_EN_NUMPAD_PLUS, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x03 },
|
||||
{ KEY_EN_CAPS_LOCK, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0xB3 },
|
||||
{ KEY_EN_A, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0xA3 },
|
||||
{ KEY_EN_S, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x9B },
|
||||
{ KEY_EN_D, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x93 },
|
||||
{ KEY_EN_F, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x8B },
|
||||
{ KEY_EN_G, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x83 },
|
||||
{ KEY_EN_H, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x7B },
|
||||
{ KEY_EN_J, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x73 },
|
||||
{ KEY_EN_K, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x6B },
|
||||
{ KEY_EN_L, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x63 },
|
||||
{ KEY_EN_SEMICOLON, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x5B },
|
||||
{ KEY_EN_QUOTE, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x53 },
|
||||
{ KEY_EN_ANSI_ENTER, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x43 },
|
||||
{ KEY_EN_NUMPAD_4, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x1B },
|
||||
{ KEY_EN_NUMPAD_5, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x13 },
|
||||
{ KEY_EN_NUMPAD_6, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x0B },
|
||||
{ KEY_EN_LEFT_SHIFT, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0xB4 },
|
||||
{ KEY_EN_Z, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0xA4 },
|
||||
{ KEY_EN_X, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x9C },
|
||||
{ KEY_EN_C, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x94 },
|
||||
{ KEY_EN_V, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x8C },
|
||||
{ KEY_EN_B, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x84 },
|
||||
{ KEY_EN_N, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x7C },
|
||||
{ KEY_EN_M, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x74 },
|
||||
{ KEY_EN_COMMA, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x6C },
|
||||
{ KEY_EN_PERIOD, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x64 },
|
||||
{ KEY_EN_FORWARD_SLASH, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x5C },
|
||||
{ KEY_EN_RIGHT_SHIFT, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x4C },
|
||||
{ KEY_EN_UP_ARROW, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x2C },
|
||||
{ KEY_EN_NUMPAD_1, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x1C },
|
||||
{ KEY_EN_NUMPAD_2, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x14 },
|
||||
{ KEY_EN_NUMPAD_3, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x0C },
|
||||
{ KEY_EN_NUMPAD_ENTER, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x05 },
|
||||
{ KEY_EN_LEFT_CONTROL, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0xB5 },
|
||||
{ KEY_EN_LEFT_WINDOWS, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0xAD },
|
||||
{ KEY_EN_LEFT_ALT, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0xA5 },
|
||||
{ KEY_EN_SPACE, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x85 },
|
||||
{ KEY_EN_RIGHT_ALT, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x65 },
|
||||
{ KEY_EN_RIGHT_FUNCTION, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x5D },
|
||||
{ KEY_EN_MENU, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x55 },
|
||||
{ KEY_EN_RIGHT_CONTROL, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x4D },
|
||||
{ KEY_EN_LEFT_ARROW, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x35 },
|
||||
{ KEY_EN_DOWN_ARROW, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x2D },
|
||||
{ KEY_EN_RIGHT_ARROW, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x25 },
|
||||
{ KEY_EN_NUMPAD_0, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x1D },
|
||||
{ KEY_EN_NUMPAD_PERIOD, ALIENWARE_AW410K_ZONE_DIRECT_KEYBOARD, 0x0D }
|
||||
};
|
||||
|
||||
/**------------------------------------------------------------------*\
|
||||
@name Alienware AW410 Keyboard
|
||||
@category Keyboard
|
||||
@type USB
|
||||
@save :x:
|
||||
@direct :white_check_mark:
|
||||
@effects :white_check_mark:
|
||||
@detectors DetectAlienwareAW410KControllers
|
||||
@comment
|
||||
\*-------------------------------------------------------------------*/
|
||||
|
||||
RGBController_AlienwareAW410K::RGBController_AlienwareAW410K(AlienwareAW410KController* controller_ptr)
|
||||
{
|
||||
controller = controller_ptr;
|
||||
|
||||
name = controller->GetDeviceName();
|
||||
vendor = "Alienware";
|
||||
type = DEVICE_TYPE_KEYBOARD;
|
||||
description = "Alienware AW410K Keyboard Device";
|
||||
location = controller->GetDeviceLocation();
|
||||
serial = controller->GetSerialString();
|
||||
|
||||
mode Direct;
|
||||
Direct.name = "Direct";
|
||||
Direct.value = ALIENWARE_AW410K_MODE_DIRECT;
|
||||
Direct.flags = MODE_FLAG_HAS_PER_LED_COLOR;
|
||||
Direct.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Direct);
|
||||
|
||||
mode Static;
|
||||
Static.name = "Static";
|
||||
Static.value = ALIENWARE_AW410K_MODE_STATIC;
|
||||
Static.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR;
|
||||
Static.colors_min = 1;
|
||||
Static.colors_max = 1;
|
||||
Static.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Static.colors.resize(1);
|
||||
modes.push_back(Static);
|
||||
|
||||
mode Pulse;
|
||||
Pulse.name = "Pulse";
|
||||
Pulse.value = ALIENWARE_AW410K_MODE_PULSE;
|
||||
Pulse.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR;
|
||||
Pulse.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Pulse.speed_min = ALIENWARE_AW410K_SPEED_SLOWEST;
|
||||
Pulse.speed_max = ALIENWARE_AW410K_SPEED_NORMAL;
|
||||
Pulse.speed = ALIENWARE_AW410K_SPEED_NORMAL;
|
||||
Pulse.colors_min = 1;
|
||||
Pulse.colors_max = 1;
|
||||
Pulse.colors.resize(1);
|
||||
modes.push_back(Pulse);
|
||||
|
||||
mode Morph;
|
||||
Morph.name = "Morph";
|
||||
Morph.value = ALIENWARE_AW410K_MODE_MORPH;
|
||||
Morph.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR;
|
||||
Morph.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Morph.speed_min = ALIENWARE_AW410K_SPEED_SLOWEST;
|
||||
Morph.speed_max = ALIENWARE_AW410K_SPEED_NORMAL;
|
||||
Morph.speed = ALIENWARE_AW410K_SPEED_NORMAL;
|
||||
Morph.colors_min = 2;
|
||||
Morph.colors_max = 2;
|
||||
Morph.colors.resize(2);
|
||||
modes.push_back(Morph);
|
||||
|
||||
mode Breathing;
|
||||
Breathing.name = "Breathing";
|
||||
Breathing.value = ALIENWARE_AW410K_MODE_BREATHING;
|
||||
Breathing.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_SPEED;
|
||||
Breathing.colors_min = 1;
|
||||
Breathing.colors_max = 1;
|
||||
Breathing.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Breathing.colors.resize(1);
|
||||
Breathing.speed_min = ALIENWARE_AW410K_SPEED_SLOWEST;
|
||||
Breathing.speed_max = ALIENWARE_AW410K_SPEED_FASTEST;
|
||||
Breathing.speed = ALIENWARE_AW410K_SPEED_NORMAL;
|
||||
modes.push_back(Breathing);
|
||||
|
||||
mode SingleWave;
|
||||
SingleWave.name = "Single Wave";
|
||||
SingleWave.value = ALIENWARE_AW410K_MODE_SINGLE_WAVE;
|
||||
SingleWave.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_DIRECTION_LR | MODE_FLAG_HAS_DIRECTION_UD;
|
||||
SingleWave.speed_min = ALIENWARE_AW410K_SPEED_SLOWEST;
|
||||
SingleWave.speed_max = ALIENWARE_AW410K_SPEED_FASTEST;
|
||||
SingleWave.speed = ALIENWARE_AW410K_SPEED_NORMAL;
|
||||
SingleWave.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
SingleWave.colors_min = 1;
|
||||
SingleWave.colors_max = 1;
|
||||
SingleWave.colors.resize(1);
|
||||
modes.push_back(SingleWave);
|
||||
|
||||
mode RainbowWave;
|
||||
RainbowWave.name = "Rainbow Wave";
|
||||
RainbowWave.value = ALIENWARE_AW410K_MODE_RAINBOW_WAVE;
|
||||
RainbowWave.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_DIRECTION_LR | MODE_FLAG_HAS_DIRECTION_UD;
|
||||
RainbowWave.speed_min = ALIENWARE_AW410K_SPEED_SLOWEST;
|
||||
RainbowWave.speed_max = ALIENWARE_AW410K_SPEED_FASTEST;
|
||||
RainbowWave.speed = ALIENWARE_AW410K_SPEED_NORMAL;
|
||||
RainbowWave.colors_min = 1;
|
||||
RainbowWave.colors_max = 1;
|
||||
RainbowWave.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
RainbowWave.colors.resize(1);
|
||||
modes.push_back(RainbowWave);
|
||||
|
||||
mode Off;
|
||||
Off.name = "Off";
|
||||
Off.value = ALIENWARE_AW410K_MODE_OFF;
|
||||
Off.flags = 0;
|
||||
Off.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Off);
|
||||
|
||||
SetupZones();
|
||||
std::copy(colors.begin(), colors.end(),std::back_inserter(current_colors));
|
||||
}
|
||||
|
||||
RGBController_AlienwareAW410K::~RGBController_AlienwareAW410K()
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| Delete the matrix map |
|
||||
\*---------------------------------------------------------*/
|
||||
for(unsigned int zone_index = 0; zone_index < zones.size(); zone_index++)
|
||||
{
|
||||
if(zones[zone_index].matrix_map != NULL)
|
||||
{
|
||||
delete zones[zone_index].matrix_map;
|
||||
}
|
||||
}
|
||||
|
||||
delete controller;
|
||||
}
|
||||
|
||||
void RGBController_AlienwareAW410K::SetupZones()
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| Set up zones |
|
||||
\*---------------------------------------------------------*/
|
||||
unsigned int total_led_count = 0;
|
||||
|
||||
for(unsigned int zone_idx = 0; zone_idx < 1; zone_idx++)
|
||||
{
|
||||
zone new_zone;
|
||||
new_zone.name = zone_names[zone_idx];
|
||||
new_zone.type = zone_types[zone_idx];
|
||||
new_zone.leds_min = zone_sizes[zone_idx];
|
||||
new_zone.leds_max = zone_sizes[zone_idx];
|
||||
new_zone.leds_count = zone_sizes[zone_idx];
|
||||
|
||||
if(zone_types[zone_idx] == ZONE_TYPE_MATRIX)
|
||||
{
|
||||
new_zone.matrix_map = new matrix_map_type;
|
||||
new_zone.matrix_map->height = 6;
|
||||
new_zone.matrix_map->width = 24;
|
||||
new_zone.matrix_map->map = (unsigned int *)&matrix_map;
|
||||
}
|
||||
else
|
||||
{
|
||||
new_zone.matrix_map = NULL;
|
||||
}
|
||||
|
||||
zones.push_back(new_zone);
|
||||
|
||||
total_led_count += zone_sizes[zone_idx];
|
||||
}
|
||||
|
||||
for(unsigned int led_idx = 0; led_idx < total_led_count; led_idx++)
|
||||
{
|
||||
led new_led;
|
||||
new_led.name = led_names[led_idx].name;
|
||||
new_led.value = led_names[led_idx].idx;
|
||||
leds.push_back(new_led);
|
||||
}
|
||||
|
||||
SetupColors();
|
||||
}
|
||||
|
||||
void RGBController_AlienwareAW410K::ResizeZone(int /*zone*/, int /*new_size*/)
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| This device does not support resizing zones |
|
||||
\*---------------------------------------------------------*/
|
||||
}
|
||||
|
||||
void RGBController_AlienwareAW410K::DeviceUpdateLEDs()
|
||||
{
|
||||
std::vector<SelectedButtons> frame_buf_keys;
|
||||
std::vector<RGBColor> new_colors;
|
||||
|
||||
std::copy(colors.begin(), colors.end(),std::back_inserter(new_colors));
|
||||
|
||||
for(std::size_t led_idx = 0; led_idx < leds.size(); led_idx++)
|
||||
{
|
||||
SelectedButtons key;
|
||||
|
||||
key.idx = (unsigned char)leds[led_idx].value;
|
||||
key.red = RGBGetRValue(colors[led_idx]);
|
||||
key.green = RGBGetGValue(colors[led_idx]);
|
||||
key.blue = RGBGetBValue(colors[led_idx]);
|
||||
|
||||
frame_buf_keys.push_back(key);
|
||||
}
|
||||
|
||||
controller->SendInitialize();
|
||||
controller->SendfeatureReport(0x05, 0x01, 0x51, 0x00);
|
||||
controller->SendCommit();
|
||||
|
||||
if(frame_buf_keys.size() > 0)
|
||||
{
|
||||
controller->SendDirectOn(frame_buf_keys);
|
||||
}
|
||||
|
||||
std::copy(new_colors.begin(), new_colors.end(),current_colors.begin());
|
||||
}
|
||||
|
||||
void RGBController_AlienwareAW410K::UpdateZoneLEDs(int zone)
|
||||
{
|
||||
controller->SetDirect((unsigned char) zone, RGBGetRValue(zones[zone].colors[0]), RGBGetGValue(zones[zone].colors[0]), RGBGetBValue(zones[zone].colors[0]));
|
||||
}
|
||||
|
||||
void RGBController_AlienwareAW410K::UpdateSingleLED(int led)
|
||||
{
|
||||
controller->UpdateSingleLED(leds[led].value, RGBGetRValue(colors[led]), RGBGetGValue(colors[led]), RGBGetBValue(colors[led]));
|
||||
}
|
||||
|
||||
void RGBController_AlienwareAW410K::DeviceUpdateMode()
|
||||
{
|
||||
if(active_mode == 0xFFFF)
|
||||
{
|
||||
UpdateLEDs();
|
||||
return;
|
||||
}
|
||||
|
||||
controller->SendfeatureReport(0x05, 0x01, 0x51, 0x00);
|
||||
unsigned char red = 0;
|
||||
unsigned char grn = 0;
|
||||
unsigned char blu = 0;
|
||||
|
||||
if(modes[active_mode].color_mode == MODE_COLORS_MODE_SPECIFIC)
|
||||
{
|
||||
red = RGBGetRValue(modes[active_mode].colors[0]);
|
||||
grn = RGBGetGValue(modes[active_mode].colors[0]);
|
||||
blu = RGBGetBValue(modes[active_mode].colors[0]);
|
||||
}
|
||||
|
||||
switch(modes[active_mode].value)
|
||||
{
|
||||
case ALIENWARE_AW410K_MODE_DIRECT:
|
||||
/*-------------------------------------------------------------*\
|
||||
| Load LEDs again in case of profile load etc. |
|
||||
\*-------------------------------------------------------------*/
|
||||
DeviceUpdateLEDs();
|
||||
break;
|
||||
case ALIENWARE_AW410K_MODE_MORPH:
|
||||
/*-------------------------------------------------------------*\
|
||||
| In case of morph it requires two colors (color1 and color2) |
|
||||
\*-------------------------------------------------------------*/
|
||||
{
|
||||
unsigned char red2 = RGBGetRValue(modes[active_mode].colors[1]);
|
||||
unsigned char grn2 = RGBGetGValue(modes[active_mode].colors[1]);
|
||||
unsigned char blu2 = RGBGetBValue(modes[active_mode].colors[1]);
|
||||
|
||||
controller->SetMorphMode(modes[active_mode].value, modes[active_mode].speed, red, grn, blu, red2, grn2, blu2);
|
||||
}
|
||||
break;
|
||||
|
||||
case ALIENWARE_AW410K_MODE_SPECTRUM:
|
||||
/*-------------------------------------------------------------*\
|
||||
| Spectrum only set mode, speed and colorMode |
|
||||
\*-------------------------------------------------------------*/
|
||||
controller->SetMode(modes[active_mode].value, modes[active_mode].speed, 0x00, ALIENWARE_AW410K_RANBOW_COLOR_MODE, 0x00, 0x00, 0x00);
|
||||
break;
|
||||
|
||||
case ALIENWARE_AW410K_MODE_SINGLE_WAVE:
|
||||
/*-------------------------------------------------------------*\
|
||||
| Wave only set mode, speed, direction and colorMode |
|
||||
\*-------------------------------------------------------------*/
|
||||
{
|
||||
int waveDirection = GetAW410K_WaveDirection(modes[active_mode].direction);
|
||||
controller->SetMode(modes[active_mode].value, modes[active_mode].speed, waveDirection, ALIENWARE_AW410K_SINGLE_COLOR_MODE, red, grn, blu);
|
||||
}
|
||||
break;
|
||||
|
||||
case ALIENWARE_AW410K_MODE_RAINBOW_WAVE:
|
||||
/*-------------------------------------------------------------*\
|
||||
| Wave only set mode, speed, direction and colorMode |
|
||||
\*-------------------------------------------------------------*/
|
||||
{
|
||||
int waveDirection = GetAW410K_WaveDirection(modes[active_mode].direction);
|
||||
controller->SetMode(modes[active_mode].value, modes[active_mode].speed, waveDirection, ALIENWARE_AW410K_RANBOW_COLOR_MODE, 0x00, 0x00, 0x00);
|
||||
}
|
||||
break;
|
||||
|
||||
|
||||
default:
|
||||
controller->SetMode(modes[active_mode].value, modes[active_mode].speed, 0x00, ALIENWARE_AW410K_SINGLE_COLOR_MODE, red, grn, blu);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
int GetAW410K_WaveDirection(int input)
|
||||
{
|
||||
switch(input)
|
||||
{
|
||||
case MODE_DIRECTION_LEFT:
|
||||
return(ALIENWARE_AW410K_DIRECTION_RIGHT_TO_LEFT);
|
||||
|
||||
case MODE_DIRECTION_RIGHT:
|
||||
return(ALIENWARE_AW410K_DIRECTION_LEFT_TO_RIGHT);
|
||||
|
||||
case MODE_DIRECTION_UP:
|
||||
return(ALIENWARE_AW410K_DIRECTION_BOTTOM_TO_TOP);
|
||||
|
||||
case MODE_DIRECTION_DOWN:
|
||||
return(ALIENWARE_AW410K_DIRECTION_TOP_TO_BOTTOM);
|
||||
|
||||
default:
|
||||
return(ALIENWARE_AW410K_DIRECTION_RIGHT_TO_LEFT);
|
||||
}
|
||||
}
|
||||
|
||||
+37
@@ -0,0 +1,37 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_AlienwareAW410K.h |
|
||||
| |
|
||||
| RGBController for Alienware AW410K keyboard |
|
||||
| |
|
||||
| based on AW510K controller by Mohamad Sallal (msallal) |
|
||||
| Dominik Mikolajczyk (dmiko) 23 Oct 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "RGBController.h"
|
||||
#include "AlienwareAW410KController.h"
|
||||
|
||||
class RGBController_AlienwareAW410K : public RGBController
|
||||
{
|
||||
public:
|
||||
RGBController_AlienwareAW410K(AlienwareAW410KController* controller_ptr);
|
||||
~RGBController_AlienwareAW410K();
|
||||
|
||||
void SetupZones();
|
||||
|
||||
void ResizeZone(int zone, int new_size);
|
||||
|
||||
void DeviceUpdateLEDs();
|
||||
void UpdateZoneLEDs(int zone);
|
||||
void UpdateSingleLED(int led);
|
||||
|
||||
void DeviceUpdateMode();
|
||||
|
||||
private:
|
||||
AlienwareAW410KController* controller;
|
||||
std::vector<RGBColor> current_colors;
|
||||
};
|
||||
+452
@@ -0,0 +1,452 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AlienwareAW510KController.cpp |
|
||||
| |
|
||||
| Driver for Alienware AW510K keyboard |
|
||||
| |
|
||||
| Mohamad Sallal (msallal) 22 May 2021 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include <cstring>
|
||||
#include "AlienwareAW510KController.h"
|
||||
#include "StringUtils.h"
|
||||
|
||||
AlienwareAW510KController::AlienwareAW510KController(hid_device* dev_handle, const char* path, std::string dev_name)
|
||||
{
|
||||
dev = dev_handle;
|
||||
location = path;
|
||||
name = dev_name;
|
||||
|
||||
SendCommit();
|
||||
}
|
||||
|
||||
AlienwareAW510KController::~AlienwareAW510KController()
|
||||
{
|
||||
hid_close(dev);
|
||||
}
|
||||
|
||||
std::string AlienwareAW510KController::GetDeviceLocation()
|
||||
{
|
||||
return("HID: " + location);
|
||||
}
|
||||
|
||||
std::string AlienwareAW510KController::GetDeviceName()
|
||||
{
|
||||
return(name);
|
||||
}
|
||||
|
||||
std::string AlienwareAW510KController::GetSerialString()
|
||||
{
|
||||
wchar_t serial_string[128];
|
||||
int ret = hid_get_serial_number_string(dev, serial_string, 128);
|
||||
|
||||
if(ret != 0)
|
||||
{
|
||||
return("");
|
||||
}
|
||||
|
||||
return(StringUtils::wstring_to_string(serial_string));
|
||||
}
|
||||
|
||||
void AlienwareAW510KController::SendCommit()
|
||||
{
|
||||
unsigned char usb_buf[65];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up Commit packet |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x00] = 0x00;
|
||||
usb_buf[0x01] = 0x05;
|
||||
usb_buf[0x02] = 0x01;
|
||||
usb_buf[0x0A] = 0x10;
|
||||
usb_buf[0x0B] = 0x0A;
|
||||
usb_buf[0x0C] = 0x01;
|
||||
usb_buf[0x0D] = 0x02;
|
||||
usb_buf[0x0E] = 0x01;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_write(dev, usb_buf, 65);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Delay 20 milliseconds |
|
||||
\*-----------------------------------------------------*/
|
||||
std::this_thread::sleep_for(std::chrono::milliseconds(20));
|
||||
}
|
||||
|
||||
void AlienwareAW510KController::SendfeatureReport
|
||||
(
|
||||
unsigned char first_byte,
|
||||
unsigned char second_byte,
|
||||
unsigned char third_byte,
|
||||
unsigned char forth_byte
|
||||
)
|
||||
{
|
||||
unsigned char usb_buf[65];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up Feature report packet |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x00] = 0x00;
|
||||
usb_buf[0x01] = first_byte;
|
||||
usb_buf[0x02] = second_byte;
|
||||
usb_buf[0x03] = third_byte;
|
||||
usb_buf[0x04] = forth_byte;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send Feature report packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_send_feature_report(dev, usb_buf, 65);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Delay 10 milliseconds |
|
||||
\*-----------------------------------------------------*/
|
||||
std::this_thread::sleep_for(std::chrono::milliseconds(10));
|
||||
}
|
||||
|
||||
void AlienwareAW510KController::SendEdit()
|
||||
{
|
||||
unsigned char usb_buf[65];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up Edit packet |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x00] = 0x00;
|
||||
usb_buf[0x01] = 0x01;
|
||||
usb_buf[0x02] = 0x00;
|
||||
usb_buf[0x03] = 0x01;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_write(dev, usb_buf, 65);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Delay 2 milliseconds |
|
||||
\*-----------------------------------------------------*/
|
||||
std::this_thread::sleep_for(std::chrono::milliseconds(2));
|
||||
}
|
||||
|
||||
void AlienwareAW510KController::SendInitialize()
|
||||
{
|
||||
unsigned char usb_buf[65];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up Commit packet |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x00] = 0x00;
|
||||
usb_buf[0x01] = 0x0E;
|
||||
usb_buf[0x02] = 0x01;
|
||||
usb_buf[0x03] = 0x00;
|
||||
usb_buf[0x04] = 0x01;
|
||||
usb_buf[0x05] = 0xAD;
|
||||
usb_buf[0x06] = 0x80;
|
||||
usb_buf[0x07] = 0x10;
|
||||
usb_buf[0x08] = 0xA5;
|
||||
usb_buf[0x0A] = 0x0A;
|
||||
usb_buf[0x12] = 0x01;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_write(dev, usb_buf, 65);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Delay 2 milliseconds |
|
||||
\*-----------------------------------------------------*/
|
||||
std::this_thread::sleep_for(std::chrono::milliseconds(2));
|
||||
}
|
||||
|
||||
void AlienwareAW510KController::SetDirect
|
||||
(
|
||||
unsigned char /*zone*/,
|
||||
unsigned char r,
|
||||
unsigned char g,
|
||||
unsigned char b
|
||||
)
|
||||
{
|
||||
unsigned char usb_buf[65];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up Lighting Control packet |
|
||||
\*-----------------------------------------------------*/
|
||||
|
||||
usb_buf[0x00] = 0x00;
|
||||
usb_buf[0x01] = 0x05;
|
||||
usb_buf[0x02] = 0x01;
|
||||
usb_buf[0x03] = 0x01;
|
||||
usb_buf[0x04] = r;
|
||||
usb_buf[0x05] = g;
|
||||
usb_buf[0x06] = b;
|
||||
usb_buf[0x0B] = 0x0A;
|
||||
usb_buf[0x0D] = 0x01;
|
||||
usb_buf[0x0E] = 0x01;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_write(dev, (unsigned char *)usb_buf, 65);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Delay 2 milliseconds |
|
||||
\*-----------------------------------------------------*/
|
||||
std::this_thread::sleep_for(std::chrono::milliseconds(2));
|
||||
}
|
||||
|
||||
void AlienwareAW510KController::SendDirectOn
|
||||
(
|
||||
std::vector<SelectedKeys> &frame_data
|
||||
)
|
||||
{
|
||||
SendfeatureReport(0x0E, (unsigned char)frame_data.size(), 0x00, 0x01);
|
||||
|
||||
/*-----------------------------------------------*\
|
||||
| To Guarantee the data are always %4 =0 append |
|
||||
| zeros at end of last packet |
|
||||
\*-----------------------------------------------*/
|
||||
for(unsigned int i = 0; i < (frame_data.size() % 4); i++)
|
||||
{
|
||||
SelectedKeys key;
|
||||
key.idx = 0x00;
|
||||
key.red = 0x00;
|
||||
key.green = 0x00;
|
||||
key.blue = 0x00;
|
||||
|
||||
frame_data.push_back(key);
|
||||
}
|
||||
|
||||
unsigned char usb_buf[65];
|
||||
unsigned int frame_idx = 0;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, 65);
|
||||
|
||||
for(unsigned int packet_idx = 0; packet_idx < frame_data.size(); packet_idx++)
|
||||
{
|
||||
usb_buf[0x00] = 0x00;
|
||||
usb_buf[0x01] = 0x0E;
|
||||
usb_buf[0x02] = 0x01;
|
||||
usb_buf[0x03] = 0x00;
|
||||
usb_buf[0x04] = ++frame_idx;
|
||||
usb_buf[0x05] = frame_data[packet_idx].idx;
|
||||
usb_buf[0x06] = 0x81;
|
||||
usb_buf[0x07] = 0x00;
|
||||
usb_buf[0x08] = 0xA5;
|
||||
usb_buf[0x0A] = 0x0A;
|
||||
usb_buf[0x0B] = frame_data[packet_idx].red;
|
||||
usb_buf[0x0C] = frame_data[packet_idx].green;
|
||||
usb_buf[0x0D] = frame_data[packet_idx].blue;
|
||||
usb_buf[0x12] = 0x01;
|
||||
|
||||
usb_buf[0x14] = frame_data[++packet_idx].idx;
|
||||
usb_buf[0x15] = 0x81;
|
||||
usb_buf[0x16] = 0x00;
|
||||
usb_buf[0x17] = 0xA5;
|
||||
usb_buf[0x19] = 0x0A;
|
||||
usb_buf[0x1A] = frame_data[packet_idx].red;
|
||||
usb_buf[0x1B] = frame_data[packet_idx].green;
|
||||
usb_buf[0x1C] = frame_data[packet_idx].blue;
|
||||
usb_buf[0x21] = 0x01;
|
||||
|
||||
usb_buf[0x23] = frame_data[++packet_idx].idx;
|
||||
usb_buf[0x24] = 0x81;
|
||||
usb_buf[0x25] = 0x00;
|
||||
usb_buf[0x26] = 0xA5;
|
||||
usb_buf[0x28] = 0x0A;
|
||||
usb_buf[0x29] = frame_data[packet_idx].red;
|
||||
usb_buf[0x2A] = frame_data[packet_idx].green;
|
||||
usb_buf[0x2B] = frame_data[packet_idx].blue;
|
||||
usb_buf[0x30] = 0x01;
|
||||
|
||||
usb_buf[0x32] = frame_data[++packet_idx].idx;
|
||||
usb_buf[0x33] = 0x81;
|
||||
usb_buf[0x34] = 0x00;
|
||||
usb_buf[0x35] = 0xA5;
|
||||
usb_buf[0x37] = 0x0A;
|
||||
usb_buf[0x38] = frame_data[packet_idx].red;
|
||||
usb_buf[0x39] = frame_data[packet_idx].green;
|
||||
usb_buf[0x3A] = frame_data[packet_idx].blue;
|
||||
usb_buf[0x3F] = 0x01;
|
||||
|
||||
hid_write(dev, (unsigned char *)usb_buf, 65);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void AlienwareAW510KController::SetMode
|
||||
(
|
||||
unsigned char mode,
|
||||
unsigned char speed,
|
||||
unsigned char direction,
|
||||
unsigned char colorMode,
|
||||
unsigned char red,
|
||||
unsigned char green,
|
||||
unsigned char blue
|
||||
)
|
||||
{
|
||||
SendMode(ALIENWARE_AW510K_ZONE_MODE_KEYBOARD, mode, speed, direction, colorMode, red, green, blue);
|
||||
SendCommit();
|
||||
}
|
||||
|
||||
void AlienwareAW510KController::UpdateSingleLED
|
||||
(
|
||||
unsigned char led,
|
||||
unsigned char red,
|
||||
unsigned char green,
|
||||
unsigned char blue
|
||||
)
|
||||
{
|
||||
SendfeatureReport(0x0E, 0x01, 0x00, 0x01);
|
||||
|
||||
unsigned char usb_buf[65];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up Single LED packet |
|
||||
\*-----------------------------------------------------*/
|
||||
|
||||
usb_buf[0x00] = 0x00;
|
||||
usb_buf[0x01] = 0x0E;
|
||||
usb_buf[0x02] = 0x01;
|
||||
usb_buf[0x03] = 0x00;
|
||||
usb_buf[0x04] = 0x01;
|
||||
usb_buf[0x05] = led;
|
||||
usb_buf[0x06] = 0x81;
|
||||
usb_buf[0x07] = 0x00;
|
||||
usb_buf[0x08] = 0xA5;
|
||||
usb_buf[0x09] = 0x00;
|
||||
usb_buf[0x0A] = 0x0A;
|
||||
usb_buf[0x0B] = red;
|
||||
usb_buf[0x0C] = green;
|
||||
usb_buf[0x0D] = blue;
|
||||
usb_buf[0x12] = 0x01;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_write(dev, usb_buf, 65);
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Delay 20 milliseconds |
|
||||
\*-----------------------------------------------------*/
|
||||
std::this_thread::sleep_for(std::chrono::milliseconds(20));
|
||||
|
||||
}
|
||||
void AlienwareAW510KController::SendMode
|
||||
(
|
||||
unsigned char /*zone*/,
|
||||
unsigned char mode,
|
||||
unsigned char speed,
|
||||
unsigned char direction,
|
||||
unsigned char colorMode,
|
||||
unsigned char red,
|
||||
unsigned char green,
|
||||
unsigned char blue
|
||||
)
|
||||
{
|
||||
unsigned char usb_buf[65];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up Mode Control packet |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x00] = 0x00;
|
||||
usb_buf[0x01] = 0x05;
|
||||
usb_buf[0x02] = 0x01;
|
||||
usb_buf[0x03] = mode;
|
||||
usb_buf[0x04] = red;
|
||||
usb_buf[0x05] = green;
|
||||
usb_buf[0x06] = blue;
|
||||
usb_buf[0x0A] = speed;
|
||||
usb_buf[0x0B] = 0x0A;
|
||||
usb_buf[0x0D] = 0x01;
|
||||
usb_buf[0x0E] = colorMode;
|
||||
usb_buf[0x0F] = direction;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_write(dev, usb_buf, 65);
|
||||
}
|
||||
|
||||
void AlienwareAW510KController::SetMorphMode
|
||||
(
|
||||
unsigned char mode,
|
||||
unsigned char speed,
|
||||
unsigned char red1,
|
||||
unsigned char green1,
|
||||
unsigned char blue1,
|
||||
unsigned char red2,
|
||||
unsigned char green2,
|
||||
unsigned char blue2
|
||||
)
|
||||
{
|
||||
unsigned char usb_buf[65];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up Morph Mode packet |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x00] = 0x00;
|
||||
usb_buf[0x01] = 0x05;
|
||||
usb_buf[0x02] = 0x01;
|
||||
usb_buf[0x03] = mode;
|
||||
usb_buf[0x04] = red1;
|
||||
usb_buf[0x05] = green1;
|
||||
usb_buf[0x06] = blue1;
|
||||
usb_buf[0x07] = red2;
|
||||
usb_buf[0x08] = green2;
|
||||
usb_buf[0x09] = blue2;
|
||||
usb_buf[0x0E] = 0x02;
|
||||
usb_buf[0x0A] = speed;
|
||||
usb_buf[0x0B] = 0x0A;
|
||||
usb_buf[0x0D] = 0x01;
|
||||
usb_buf[0x0E] = ALIENWARE_AW510K_TWO_USER_DEFINED_COLOR_MODE;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_write(dev, usb_buf, 65);
|
||||
}
|
||||
+159
@@ -0,0 +1,159 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AlienwareAW510KController.h |
|
||||
| |
|
||||
| Driver for Alienware AW510K keyboard |
|
||||
| |
|
||||
| Mohamad Sallal (msallal) 22 May 2021 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <string>
|
||||
#include <hidapi.h>
|
||||
#include "RGBController.h"
|
||||
|
||||
enum
|
||||
{
|
||||
ALIENWARE_AW510K_ZONE_MODE_KEYBOARD = 0x01,
|
||||
ALIENWARE_AW510K_ZONE_MODE_LOGO = 0x07, /* logo is only need key value, which equal 07 */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD = 0x01,
|
||||
ALIENWARE_AW510K_ZONE_DIRECT_MEDIA = 0x02,
|
||||
ALIENWARE_AW510K_ZONE_DIRECT_LOGO = 0x07,
|
||||
ALIENWARE_AW510K_ZONE_DIRECT_INDICATORS = 0x40,
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
ALIENWARE_AW510K_MODE_OFF = 0x00,
|
||||
ALIENWARE_AW510K_MODE_DIRECT_PER_LED = 0x01,
|
||||
ALIENWARE_AW510K_MODE_DIRECT = 0x01,
|
||||
ALIENWARE_AW510K_MODE_PULSE = 0x02,
|
||||
ALIENWARE_AW510K_MODE_MORPH = 0x03,
|
||||
ALIENWARE_AW510K_MODE_BREATHING = 0x07,
|
||||
ALIENWARE_AW510K_MODE_SPECTRUM = 0x08,
|
||||
ALIENWARE_AW510K_MODE_SINGLE_WAVE = 0x0F,
|
||||
ALIENWARE_AW510K_MODE_RAINBOW_WAVE = 0x10,
|
||||
ALIENWARE_AW510K_MODE_SCANNER = 0x11,
|
||||
ALIENWARE_AW510K_MODE_STATIC = 0x13,
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
ALIENWARE_AW510K_SPEED_SLOWEST = 0x2D, /* Slowest speed */
|
||||
ALIENWARE_AW510K_SPEED_NORMAL = 0x19, /* Normal speed */
|
||||
ALIENWARE_AW510K_SPEED_FASTEST = 0x0A, /* Fastest speed */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
ALIENWARE_AW510K_DIRECTION_LEFT_TO_RIGHT = 0x01,
|
||||
ALIENWARE_AW510K_DIRECTION_RIGHT_TO_LEFT = 0x02,
|
||||
ALIENWARE_AW510K_DIRECTION_TOP_TO_BOTTOM = 0x03,
|
||||
ALIENWARE_AW510K_DIRECTION_BOTTOM_TO_TOP = 0x04,
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
ALIENWARE_AW510K_SINGLE_COLOR_MODE = 0x01,
|
||||
ALIENWARE_AW510K_TWO_USER_DEFINED_COLOR_MODE= 0x02,
|
||||
ALIENWARE_AW510K_RANBOW_COLOR_MODE = 0x03,
|
||||
};
|
||||
|
||||
struct SelectedKeys
|
||||
{
|
||||
unsigned char idx;
|
||||
unsigned char red;
|
||||
unsigned char green;
|
||||
unsigned char blue;
|
||||
};
|
||||
|
||||
class AlienwareAW510KController
|
||||
{
|
||||
public:
|
||||
AlienwareAW510KController(hid_device* dev_handle, const char* path, std::string dev_name);
|
||||
~AlienwareAW510KController();
|
||||
|
||||
std::string GetDeviceLocation();
|
||||
std::string GetDeviceName();
|
||||
std::string GetSerialString();
|
||||
|
||||
void SendInitialize();
|
||||
void SendCommit();
|
||||
void SendfeatureReport
|
||||
(
|
||||
unsigned char first_byte,
|
||||
unsigned char second_byte,
|
||||
unsigned char third_byte,
|
||||
unsigned char forth_byte
|
||||
);
|
||||
|
||||
void SendEdit();
|
||||
|
||||
void SetDirect
|
||||
(
|
||||
unsigned char zone,
|
||||
unsigned char r,
|
||||
unsigned char g,
|
||||
unsigned char b
|
||||
);
|
||||
|
||||
void SendDirectOn
|
||||
(
|
||||
std::vector<SelectedKeys> &frame_data
|
||||
);
|
||||
|
||||
void SetMode
|
||||
(
|
||||
unsigned char mode,
|
||||
unsigned char speed,
|
||||
unsigned char direction,
|
||||
unsigned char colorMode,
|
||||
unsigned char red,
|
||||
unsigned char green,
|
||||
unsigned char blue
|
||||
);
|
||||
|
||||
void SetMorphMode
|
||||
(
|
||||
unsigned char mode,
|
||||
unsigned char speed,
|
||||
unsigned char red1,
|
||||
unsigned char green1,
|
||||
unsigned char blue1,
|
||||
unsigned char red2,
|
||||
unsigned char green2,
|
||||
unsigned char blue2
|
||||
);
|
||||
|
||||
void UpdateSingleLED
|
||||
(
|
||||
unsigned char led,
|
||||
unsigned char red,
|
||||
unsigned char green,
|
||||
unsigned char blue
|
||||
);
|
||||
|
||||
private:
|
||||
hid_device* dev;
|
||||
std::string location;
|
||||
std::string name;
|
||||
|
||||
void SendMode
|
||||
(
|
||||
unsigned char zone,
|
||||
unsigned char mode,
|
||||
unsigned char speed,
|
||||
unsigned char direction,
|
||||
unsigned char colorMode,
|
||||
unsigned char red,
|
||||
unsigned char green,
|
||||
unsigned char blue
|
||||
);
|
||||
};
|
||||
+497
@@ -0,0 +1,497 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_AlienwareAW510K.cpp |
|
||||
| |
|
||||
| RGBController for Alienware AW510K keyboard |
|
||||
| |
|
||||
| Mohamad Sallal (msallal) 22 May 2021 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include <iterator>
|
||||
#include "RGBControllerKeyNames.h"
|
||||
#include "RGBController_AlienwareAW510K.h"
|
||||
|
||||
//0xFFFFFFFF indicates an unused entry in matrix
|
||||
#define NA 0xFFFFFFFF
|
||||
|
||||
int GetAW520K_WaveDirection(int input);
|
||||
|
||||
static unsigned int matrix_map[7][24] =
|
||||
{ { 0, NA, 1, 2, 3, 4, NA, 5, 6, 7, 8, 9, 10, 11, 12, NA, 13, 14, 15, NA, 16, NA, NA, NA },
|
||||
{ 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, NA, NA, 31, 32, 33, NA, 34, 35, 36, 37 },
|
||||
{ 38, NA, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, NA, 52, 53, 54, NA, 55, 56, 57, 74 },
|
||||
{ 58, NA, 59, 60, 61, 62, 63, 64, 65, 66, 67, 68, 69, NA, 70, NA, NA, NA, NA, NA, 71, 72, 73, NA },
|
||||
{ 75, NA, NA, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, NA, NA, NA, 87, NA, NA, 88, 89, 90, 104 },
|
||||
{ 91, NA, 92, 93, NA, 94, NA, NA, NA, NA, NA, 95, 96, 97, 98, NA, 99, 100, 101, NA, 102, NA, 103, NA },
|
||||
{ NA, NA, NA, NA, NA, NA, NA, NA, NA, NA, 105, NA, NA, NA, NA, NA, NA, NA, NA, NA, NA, NA, NA, NA }};
|
||||
|
||||
static const char* zone_names[] =
|
||||
{
|
||||
"AW510K",
|
||||
};
|
||||
|
||||
static zone_type zone_types[] =
|
||||
{
|
||||
ZONE_TYPE_MATRIX,
|
||||
};
|
||||
|
||||
static const unsigned int zone_sizes[] =
|
||||
{
|
||||
106,
|
||||
};
|
||||
|
||||
typedef struct
|
||||
{
|
||||
const char * name;
|
||||
const unsigned char zone;
|
||||
const unsigned char idx;
|
||||
} aw510k_led_type;
|
||||
|
||||
static const aw510k_led_type led_names[] =
|
||||
{
|
||||
/* Key Label Zone, Index */
|
||||
{ KEY_EN_ESCAPE, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0xB0 },
|
||||
{ KEY_EN_F1, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x98 },
|
||||
{ KEY_EN_F2, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x90 },
|
||||
{ KEY_EN_F3, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x88 },
|
||||
{ KEY_EN_F4, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x80 },
|
||||
{ KEY_EN_F5, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x70 },
|
||||
{ KEY_EN_F6, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x68 },
|
||||
{ KEY_EN_F7, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x60 },
|
||||
{ KEY_EN_F8, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x58 },
|
||||
{ KEY_EN_F9, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x50 },
|
||||
{ KEY_EN_F10, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x48 },
|
||||
{ KEY_EN_F11, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x40 },
|
||||
{ KEY_EN_F12, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x38 },
|
||||
{ KEY_EN_PRINT_SCREEN, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x30 },
|
||||
{ KEY_EN_SCROLL_LOCK, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x28 },
|
||||
{ KEY_EN_PAUSE_BREAK, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x20 },
|
||||
{ KEY_EN_MEDIA_MUTE, ALIENWARE_AW510K_ZONE_DIRECT_MEDIA, 0x18 },
|
||||
{ KEY_EN_BACK_TICK, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0xB1 },
|
||||
{ KEY_EN_1, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0xA1 },
|
||||
{ KEY_EN_2, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x99 },
|
||||
{ KEY_EN_3, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x91 },
|
||||
{ KEY_EN_4, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x89 },
|
||||
{ KEY_EN_5, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x81 },
|
||||
{ KEY_EN_6, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x79 },
|
||||
{ KEY_EN_7, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x71 },
|
||||
{ KEY_EN_8, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x69 },
|
||||
{ KEY_EN_9, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x61 },
|
||||
{ KEY_EN_0, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x59 },
|
||||
{ KEY_EN_MINUS, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x51 },
|
||||
{ KEY_EN_EQUALS, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x49 },
|
||||
{ KEY_EN_BACKSPACE, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x39 },
|
||||
{ KEY_EN_INSERT, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x31 },
|
||||
{ KEY_EN_HOME, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x29 },
|
||||
{ KEY_EN_PAGE_UP, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x21 },
|
||||
{ KEY_EN_NUMPAD_LOCK, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x19 },
|
||||
{ KEY_EN_NUMPAD_DIVIDE, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x11 },
|
||||
{ KEY_EN_NUMPAD_TIMES, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x09 },
|
||||
{ KEY_EN_NUMPAD_MINUS, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x01 },
|
||||
{ KEY_EN_TAB, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0xB2 },
|
||||
{ KEY_EN_Q, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0xA2 },
|
||||
{ KEY_EN_W, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x9A },
|
||||
{ KEY_EN_E, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x92 },
|
||||
{ KEY_EN_R, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x8A },
|
||||
{ KEY_EN_T, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x82 },
|
||||
{ KEY_EN_Y, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x7A },
|
||||
{ KEY_EN_U, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x72 },
|
||||
{ KEY_EN_I, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x6A },
|
||||
{ KEY_EN_O, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x62 },
|
||||
{ KEY_EN_P, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x5A },
|
||||
{ KEY_EN_LEFT_BRACKET, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x52 },
|
||||
{ KEY_EN_RIGHT_BRACKET, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x4A },
|
||||
{ KEY_EN_ANSI_BACK_SLASH, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x42 },//ANSI only
|
||||
{ KEY_EN_DELETE, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x32 },
|
||||
{ KEY_EN_END, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x2A },
|
||||
{ KEY_EN_PAGE_DOWN, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x22 },
|
||||
{ KEY_EN_NUMPAD_7, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x1A },
|
||||
{ KEY_EN_NUMPAD_8, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x12 },
|
||||
{ KEY_EN_NUMPAD_9, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x0A },
|
||||
{ KEY_EN_CAPS_LOCK, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0xB3 },
|
||||
{ KEY_EN_A, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0xA3 },
|
||||
{ KEY_EN_S, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x9B },
|
||||
{ KEY_EN_D, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x93 },
|
||||
{ KEY_EN_F, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x8B },
|
||||
{ KEY_EN_G, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x83 },
|
||||
{ KEY_EN_H, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x7B },
|
||||
{ KEY_EN_J, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x73 },
|
||||
{ KEY_EN_K, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x6B },
|
||||
{ KEY_EN_L, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x63 },
|
||||
{ KEY_EN_SEMICOLON, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x5B },
|
||||
{ KEY_EN_QUOTE, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x53 },
|
||||
{ KEY_EN_ANSI_ENTER, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x43 },
|
||||
{ KEY_EN_NUMPAD_4, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x1B },
|
||||
{ KEY_EN_NUMPAD_5, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x13 },
|
||||
{ KEY_EN_NUMPAD_6, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x0B },
|
||||
{ KEY_EN_NUMPAD_PLUS, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x03 },
|
||||
{ KEY_EN_LEFT_SHIFT, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0xB4 },
|
||||
{ KEY_EN_Z, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0xA4 },
|
||||
{ KEY_EN_X, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x9C },
|
||||
{ KEY_EN_C, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x94 },
|
||||
{ KEY_EN_V, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x8C },
|
||||
{ KEY_EN_B, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x84 },
|
||||
{ KEY_EN_N, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x7C },
|
||||
{ KEY_EN_M, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x74 },
|
||||
{ KEY_EN_COMMA, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x6C },
|
||||
{ KEY_EN_PERIOD, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x64 },
|
||||
{ KEY_EN_FORWARD_SLASH, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x5C },
|
||||
{ KEY_EN_RIGHT_SHIFT, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x4C },
|
||||
{ KEY_EN_UP_ARROW, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x2C },
|
||||
{ KEY_EN_NUMPAD_1, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x1C },
|
||||
{ KEY_EN_NUMPAD_2, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x14 },
|
||||
{ KEY_EN_NUMPAD_3, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x0C },
|
||||
{ KEY_EN_LEFT_CONTROL, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0xB5 },
|
||||
{ KEY_EN_LEFT_WINDOWS, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0xAD },
|
||||
{ KEY_EN_LEFT_ALT, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0xA5 },
|
||||
{ KEY_EN_SPACE, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x85 },
|
||||
{ KEY_EN_RIGHT_ALT, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x65 },
|
||||
{ KEY_EN_RIGHT_FUNCTION, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x5D },
|
||||
{ KEY_EN_MENU, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x55 },
|
||||
{ KEY_EN_RIGHT_CONTROL, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x4D },
|
||||
{ KEY_EN_LEFT_ARROW, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x35 },
|
||||
{ KEY_EN_DOWN_ARROW, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x2D },
|
||||
{ KEY_EN_RIGHT_ARROW, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x25 },
|
||||
{ KEY_EN_NUMPAD_0, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x1D },
|
||||
{ KEY_EN_NUMPAD_PERIOD, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x0D },
|
||||
{ KEY_EN_NUMPAD_ENTER, ALIENWARE_AW510K_ZONE_DIRECT_KEYBOARD, 0x05 },
|
||||
{ "Logo", ALIENWARE_AW510K_ZONE_DIRECT_LOGO, 0x07 }
|
||||
};
|
||||
|
||||
/**------------------------------------------------------------------*\
|
||||
@name Alienware AW510 Keyboard
|
||||
@category Keyboard
|
||||
@type USB
|
||||
@save :x:
|
||||
@direct :white_check_mark:
|
||||
@effects :white_check_mark:
|
||||
@detectors DetectAlienwareAW510KControllers
|
||||
@comment
|
||||
\*-------------------------------------------------------------------*/
|
||||
|
||||
RGBController_AlienwareAW510K::RGBController_AlienwareAW510K(AlienwareAW510KController* controller_ptr)
|
||||
{
|
||||
controller = controller_ptr;
|
||||
|
||||
name = controller->GetDeviceName();
|
||||
vendor = "Alienware";
|
||||
type = DEVICE_TYPE_KEYBOARD;
|
||||
description = "Alienware AW510K Keyboard Device";
|
||||
location = controller->GetDeviceLocation();
|
||||
serial = controller->GetSerialString();
|
||||
|
||||
mode Direct;
|
||||
Direct.name = "Direct";
|
||||
Direct.value = ALIENWARE_AW510K_MODE_DIRECT_PER_LED;
|
||||
Direct.flags = MODE_FLAG_HAS_PER_LED_COLOR;
|
||||
Direct.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Direct);
|
||||
|
||||
mode Static;
|
||||
Static.name = "Static";
|
||||
Static.value = ALIENWARE_AW510K_MODE_STATIC;
|
||||
Static.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR;
|
||||
Static.colors_min = 1;
|
||||
Static.colors_max = 1;
|
||||
Static.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Static.colors.resize(1);
|
||||
modes.push_back(Static);
|
||||
|
||||
mode Pulse;
|
||||
Pulse.name = "Pulse";
|
||||
Pulse.value = ALIENWARE_AW510K_MODE_PULSE;
|
||||
Pulse.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR;
|
||||
Pulse.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Pulse.speed_min = ALIENWARE_AW510K_SPEED_SLOWEST;
|
||||
Pulse.speed_max = ALIENWARE_AW510K_SPEED_NORMAL;
|
||||
Pulse.speed = ALIENWARE_AW510K_SPEED_NORMAL;
|
||||
Pulse.colors_min = 1;
|
||||
Pulse.colors_max = 1;
|
||||
Pulse.colors.resize(1);
|
||||
modes.push_back(Pulse);
|
||||
|
||||
mode Morph;
|
||||
Morph.name = "Morph";
|
||||
Morph.value = ALIENWARE_AW510K_MODE_MORPH;
|
||||
Morph.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR;
|
||||
Morph.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Morph.speed_min = ALIENWARE_AW510K_SPEED_SLOWEST;
|
||||
Morph.speed_max = ALIENWARE_AW510K_SPEED_NORMAL;
|
||||
Morph.speed = ALIENWARE_AW510K_SPEED_NORMAL;
|
||||
Morph.colors_min = 2;
|
||||
Morph.colors_max = 2;
|
||||
Morph.colors.resize(2);
|
||||
modes.push_back(Morph);
|
||||
|
||||
mode Breathing;
|
||||
Breathing.name = "Breathing";
|
||||
Breathing.value = ALIENWARE_AW510K_MODE_BREATHING;
|
||||
Breathing.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_SPEED;
|
||||
Breathing.colors_min = 1;
|
||||
Breathing.colors_max = 1;
|
||||
Breathing.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Breathing.colors.resize(1);
|
||||
Breathing.speed_min = ALIENWARE_AW510K_SPEED_SLOWEST;
|
||||
Breathing.speed_max = ALIENWARE_AW510K_SPEED_FASTEST;
|
||||
Breathing.speed = ALIENWARE_AW510K_SPEED_NORMAL;
|
||||
modes.push_back(Breathing);
|
||||
|
||||
mode SingleWave;
|
||||
SingleWave.name = "Single Wave";
|
||||
SingleWave.value = ALIENWARE_AW510K_MODE_SINGLE_WAVE;
|
||||
SingleWave.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_DIRECTION_LR | MODE_FLAG_HAS_DIRECTION_UD;
|
||||
SingleWave.speed_min = ALIENWARE_AW510K_SPEED_SLOWEST;
|
||||
SingleWave.speed_max = ALIENWARE_AW510K_SPEED_FASTEST;
|
||||
SingleWave.speed = ALIENWARE_AW510K_SPEED_NORMAL;
|
||||
SingleWave.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
SingleWave.colors_min = 1;
|
||||
SingleWave.colors_max = 1;
|
||||
SingleWave.colors.resize(1);
|
||||
modes.push_back(SingleWave);
|
||||
|
||||
mode RainbowWave;
|
||||
RainbowWave.name = "Rainbow Wave";
|
||||
RainbowWave.value = ALIENWARE_AW510K_MODE_RAINBOW_WAVE;
|
||||
RainbowWave.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_DIRECTION_LR | MODE_FLAG_HAS_DIRECTION_UD;
|
||||
RainbowWave.speed_min = ALIENWARE_AW510K_SPEED_SLOWEST;
|
||||
RainbowWave.speed_max = ALIENWARE_AW510K_SPEED_FASTEST;
|
||||
RainbowWave.speed = ALIENWARE_AW510K_SPEED_NORMAL;
|
||||
RainbowWave.colors_min = 1;
|
||||
RainbowWave.colors_max = 1;
|
||||
RainbowWave.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
RainbowWave.colors.resize(1);
|
||||
modes.push_back(RainbowWave);
|
||||
|
||||
mode Off;
|
||||
Off.name = "Off";
|
||||
Off.value = ALIENWARE_AW510K_MODE_OFF;
|
||||
Off.flags = 0;
|
||||
Off.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Off);
|
||||
|
||||
SetupZones();
|
||||
std::copy(colors.begin(), colors.end(),std::back_inserter(current_colors));
|
||||
}
|
||||
|
||||
RGBController_AlienwareAW510K::~RGBController_AlienwareAW510K()
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| Delete the matrix map |
|
||||
\*---------------------------------------------------------*/
|
||||
for(unsigned int zone_index = 0; zone_index < zones.size(); zone_index++)
|
||||
{
|
||||
if(zones[zone_index].matrix_map != NULL)
|
||||
{
|
||||
delete zones[zone_index].matrix_map;
|
||||
}
|
||||
}
|
||||
|
||||
delete controller;
|
||||
}
|
||||
|
||||
void RGBController_AlienwareAW510K::SetupZones()
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| Set up zones |
|
||||
\*---------------------------------------------------------*/
|
||||
unsigned int total_led_count = 0;
|
||||
|
||||
for(unsigned int zone_idx = 0; zone_idx < 1; zone_idx++)
|
||||
{
|
||||
zone new_zone;
|
||||
new_zone.name = zone_names[zone_idx];
|
||||
new_zone.type = zone_types[zone_idx];
|
||||
new_zone.leds_min = zone_sizes[zone_idx];
|
||||
new_zone.leds_max = zone_sizes[zone_idx];
|
||||
new_zone.leds_count = zone_sizes[zone_idx];
|
||||
|
||||
if(zone_types[zone_idx] == ZONE_TYPE_MATRIX)
|
||||
{
|
||||
new_zone.matrix_map = new matrix_map_type;
|
||||
new_zone.matrix_map->height = 7;
|
||||
new_zone.matrix_map->width = 24;
|
||||
new_zone.matrix_map->map = (unsigned int *)&matrix_map;
|
||||
}
|
||||
else
|
||||
{
|
||||
new_zone.matrix_map = NULL;
|
||||
}
|
||||
|
||||
zones.push_back(new_zone);
|
||||
|
||||
total_led_count += zone_sizes[zone_idx];
|
||||
}
|
||||
|
||||
for(unsigned int led_idx = 0; led_idx < total_led_count; led_idx++)
|
||||
{
|
||||
led new_led;
|
||||
new_led.name = led_names[led_idx].name;
|
||||
new_led.value = led_names[led_idx].idx;
|
||||
leds.push_back(new_led);
|
||||
}
|
||||
|
||||
SetupColors();
|
||||
}
|
||||
|
||||
void RGBController_AlienwareAW510K::ResizeZone(int /*zone*/, int /*new_size*/)
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| This device does not support resizing zones |
|
||||
\*---------------------------------------------------------*/
|
||||
}
|
||||
|
||||
void RGBController_AlienwareAW510K::DeviceUpdateLEDs()
|
||||
{
|
||||
std::vector<SelectedKeys> frame_buf_keys;
|
||||
std::vector<RGBColor> new_colors;
|
||||
|
||||
std::copy(colors.begin(), colors.end(),std::back_inserter(new_colors));
|
||||
|
||||
for(std::size_t led_idx = 0; led_idx < leds.size(); led_idx++)
|
||||
{
|
||||
if (current_colors[led_idx]==new_colors[led_idx])
|
||||
{
|
||||
/*-------------------------------------------------*\
|
||||
| Don't send if key color is not changed |
|
||||
\*-------------------------------------------------*/
|
||||
continue;
|
||||
}
|
||||
|
||||
if(RGBGetRValue(colors[led_idx]) != 0x00 || RGBGetBValue(colors[led_idx]) != 0x00 || RGBGetBValue(colors[led_idx]) != 0x00)
|
||||
{
|
||||
SelectedKeys key;
|
||||
|
||||
key.idx = (unsigned char)leds[led_idx].value;
|
||||
key.red = RGBGetRValue(colors[led_idx]);
|
||||
key.green = RGBGetGValue(colors[led_idx]);
|
||||
key.blue = RGBGetBValue(colors[led_idx]);
|
||||
|
||||
frame_buf_keys.push_back(key);
|
||||
}
|
||||
else
|
||||
{
|
||||
SelectedKeys key;
|
||||
|
||||
key.idx = (unsigned char)leds[led_idx].value;
|
||||
key.red = RGBGetRValue(colors[led_idx]);
|
||||
key.green = RGBGetGValue(colors[led_idx]);
|
||||
key.blue = RGBGetBValue(colors[led_idx]);
|
||||
|
||||
frame_buf_keys.push_back(key);
|
||||
}
|
||||
}
|
||||
|
||||
controller->SendInitialize();
|
||||
controller->SendfeatureReport(0x05, 0x01, 0x51, 0x00);
|
||||
controller->SendCommit();
|
||||
|
||||
if(frame_buf_keys.size() > 0)
|
||||
{
|
||||
controller->SendDirectOn(frame_buf_keys);
|
||||
}
|
||||
|
||||
std::copy(new_colors.begin(), new_colors.end(),current_colors.begin());
|
||||
}
|
||||
|
||||
void RGBController_AlienwareAW510K::UpdateZoneLEDs(int zone)
|
||||
{
|
||||
controller->SetDirect((unsigned char) zone, RGBGetRValue(zones[zone].colors[0]), RGBGetGValue(zones[zone].colors[0]), RGBGetBValue(zones[zone].colors[0]));
|
||||
}
|
||||
|
||||
void RGBController_AlienwareAW510K::UpdateSingleLED(int led)
|
||||
{
|
||||
controller->UpdateSingleLED(leds[led].value, RGBGetRValue(colors[led]), RGBGetGValue(colors[led]), RGBGetBValue(colors[led]));
|
||||
}
|
||||
|
||||
void RGBController_AlienwareAW510K::DeviceUpdateMode()
|
||||
{
|
||||
if(active_mode == 0xFFFF)
|
||||
{
|
||||
UpdateLEDs();
|
||||
return;
|
||||
}
|
||||
|
||||
controller->SendfeatureReport(0x05, 0x01, 0x51, 0x00);
|
||||
unsigned char red = 0;
|
||||
unsigned char grn = 0;
|
||||
unsigned char blu = 0;
|
||||
|
||||
if(modes[active_mode].color_mode == MODE_COLORS_MODE_SPECIFIC)
|
||||
{
|
||||
red = RGBGetRValue(modes[active_mode].colors[0]);
|
||||
grn = RGBGetGValue(modes[active_mode].colors[0]);
|
||||
blu = RGBGetBValue(modes[active_mode].colors[0]);
|
||||
}
|
||||
|
||||
switch(modes[active_mode].value)
|
||||
{
|
||||
case ALIENWARE_AW510K_MODE_MORPH:
|
||||
/*-------------------------------------------------------------*\
|
||||
| In case of morph it requires two colors (color1 and color2) |
|
||||
\*-------------------------------------------------------------*/
|
||||
{
|
||||
unsigned char red2 = RGBGetRValue(modes[active_mode].colors[1]);
|
||||
unsigned char grn2 = RGBGetGValue(modes[active_mode].colors[1]);
|
||||
unsigned char blu2 = RGBGetBValue(modes[active_mode].colors[1]);
|
||||
|
||||
controller->SetMorphMode(modes[active_mode].value, modes[active_mode].speed, red, grn, blu, red2, grn2, blu2);
|
||||
}
|
||||
break;
|
||||
|
||||
case ALIENWARE_AW510K_MODE_SPECTRUM:
|
||||
/*-------------------------------------------------------------*\
|
||||
| Spectrum only set mode, speed and colorMode |
|
||||
\*-------------------------------------------------------------*/
|
||||
controller->SetMode(modes[active_mode].value, modes[active_mode].speed, 0x00, ALIENWARE_AW510K_RANBOW_COLOR_MODE, 0x00, 0x00, 0x00);
|
||||
break;
|
||||
|
||||
case ALIENWARE_AW510K_MODE_SINGLE_WAVE:
|
||||
/*-------------------------------------------------------------*\
|
||||
| Wave only set mode, speed, direction and colorMode |
|
||||
\*-------------------------------------------------------------*/
|
||||
{
|
||||
int waveDirection = GetAW520K_WaveDirection(modes[active_mode].direction);
|
||||
controller->SetMode(modes[active_mode].value, modes[active_mode].speed, waveDirection, ALIENWARE_AW510K_SINGLE_COLOR_MODE, red, grn, blu);
|
||||
}
|
||||
break;
|
||||
|
||||
case ALIENWARE_AW510K_MODE_RAINBOW_WAVE:
|
||||
/*-------------------------------------------------------------*\
|
||||
| Wave only set mode, speed, direction and colorMode |
|
||||
\*-------------------------------------------------------------*/
|
||||
{
|
||||
int waveDirection = GetAW520K_WaveDirection(modes[active_mode].direction);
|
||||
controller->SetMode(modes[active_mode].value, modes[active_mode].speed, waveDirection, ALIENWARE_AW510K_RANBOW_COLOR_MODE, 0x00, 0x00, 0x00);
|
||||
}
|
||||
break;
|
||||
|
||||
|
||||
default:
|
||||
controller->SetMode(modes[active_mode].value, modes[active_mode].speed, 0x00, ALIENWARE_AW510K_SINGLE_COLOR_MODE, red, grn, blu);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
int GetAW520K_WaveDirection(int input)
|
||||
{
|
||||
switch(input)
|
||||
{
|
||||
case MODE_DIRECTION_LEFT:
|
||||
return(ALIENWARE_AW510K_DIRECTION_RIGHT_TO_LEFT);
|
||||
|
||||
case MODE_DIRECTION_RIGHT:
|
||||
return(ALIENWARE_AW510K_DIRECTION_LEFT_TO_RIGHT);
|
||||
|
||||
case MODE_DIRECTION_UP:
|
||||
return(ALIENWARE_AW510K_DIRECTION_BOTTOM_TO_TOP);
|
||||
|
||||
case MODE_DIRECTION_DOWN:
|
||||
return(ALIENWARE_AW510K_DIRECTION_TOP_TO_BOTTOM);
|
||||
|
||||
default:
|
||||
return(ALIENWARE_AW510K_DIRECTION_RIGHT_TO_LEFT);
|
||||
}
|
||||
}
|
||||
|
||||
+36
@@ -0,0 +1,36 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_AlienwareAW510K.h |
|
||||
| |
|
||||
| RGBController for Alienware AW510K keyboard |
|
||||
| |
|
||||
| Mohamad Sallal (msallal) 22 May 2021 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "RGBController.h"
|
||||
#include "AlienwareAW510KController.h"
|
||||
|
||||
class RGBController_AlienwareAW510K : public RGBController
|
||||
{
|
||||
public:
|
||||
RGBController_AlienwareAW510K(AlienwareAW510KController* controller_ptr);
|
||||
~RGBController_AlienwareAW510K();
|
||||
|
||||
void SetupZones();
|
||||
|
||||
void ResizeZone(int zone, int new_size);
|
||||
|
||||
void DeviceUpdateLEDs();
|
||||
void UpdateZoneLEDs(int zone);
|
||||
void UpdateSingleLED(int led);
|
||||
|
||||
void DeviceUpdateMode();
|
||||
|
||||
private:
|
||||
AlienwareAW510KController* controller;
|
||||
std::vector<RGBColor> current_colors;
|
||||
};
|
||||
@@ -0,0 +1,62 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AlienwareKeyboardControllerDetect.cpp |
|
||||
| |
|
||||
| Detector for Alienware Keyboard |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include <hidapi.h>
|
||||
#include "Detector.h"
|
||||
#include "AlienwareAW510KController.h"
|
||||
#include "AlienwareAW410KController.h"
|
||||
#include "RGBController_AlienwareAW510K.h"
|
||||
#include "RGBController_AlienwareAW410K.h"
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Alienware vendor ID |
|
||||
\*-----------------------------------------------------*/
|
||||
#define ALIENWARE_VID 0x04F2
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Keyboard product IDs |
|
||||
\*-----------------------------------------------------*/
|
||||
#define ALIENWARE_AW510K_PID 0x1830
|
||||
#define ALIENWARE_AW410K_PID 0x1968
|
||||
|
||||
/******************************************************************************************\
|
||||
* *
|
||||
* DetectAlienwareKeyboardControllers *
|
||||
* *
|
||||
* Tests the USB address to see if a Alienware RGB Keyboard controller exists there. *
|
||||
* *
|
||||
\******************************************************************************************/
|
||||
|
||||
void DetectAlienwareAW510KControllers(hid_device_info* info, const std::string& name)
|
||||
{
|
||||
hid_device* dev = hid_open_path(info->path);
|
||||
if( dev )
|
||||
{
|
||||
AlienwareAW510KController* controller = new AlienwareAW510KController(dev, info->path, name);
|
||||
RGBController_AlienwareAW510K* rgb_controller = new RGBController_AlienwareAW510K(controller);
|
||||
|
||||
ResourceManager::get()->RegisterRGBController(rgb_controller);
|
||||
}
|
||||
}
|
||||
|
||||
void DetectAlienwareAW410KControllers(hid_device_info* info, const std::string& name)
|
||||
{
|
||||
hid_device* dev = hid_open_path(info->path);
|
||||
if( dev )
|
||||
{
|
||||
AlienwareAW410KController* controller = new AlienwareAW410KController(dev, info->path, name);
|
||||
RGBController_AlienwareAW410K* rgb_controller = new RGBController_AlienwareAW410K(controller);
|
||||
|
||||
ResourceManager::get()->RegisterRGBController(rgb_controller);
|
||||
}
|
||||
}/* DetectAlienwareKeyboardControllers() */
|
||||
|
||||
|
||||
REGISTER_HID_DETECTOR_IPU("Alienware AW510K", DetectAlienwareAW510KControllers, ALIENWARE_VID, ALIENWARE_AW510K_PID, 0x02, 0xFF00, 0x01);
|
||||
REGISTER_HID_DETECTOR_IPU("Alienware AW410K", DetectAlienwareAW410KControllers, ALIENWARE_VID, ALIENWARE_AW410K_PID, 0x02, 0xFF00, 0x01);
|
||||
@@ -0,0 +1,183 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AlienwareAW3423DWFController.cpp |
|
||||
| |
|
||||
| Driver for the Alienware AW3423DWF monitor |
|
||||
| |
|
||||
| Ferréol DUBOIS COLI (Fefe_du_973) 23 Jan 2025 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include <bitset>
|
||||
#include <chrono>
|
||||
#include <cstring>
|
||||
#include <thread>
|
||||
|
||||
#include "AlienwareAW3423DWFController.h"
|
||||
#include "StringUtils.h"
|
||||
|
||||
AlienwareAW3423DWFController::AlienwareAW3423DWFController(hid_device *dev_handle, const char *path) : dev(dev_handle), location(path){}
|
||||
|
||||
void AlienwareAW3423DWFController::SendControlPacket(const unsigned char *data, size_t length)
|
||||
{
|
||||
unsigned char buffer[256] = {0x00};
|
||||
memcpy(buffer + 1, data, length);
|
||||
|
||||
hid_write(dev, buffer, length + 1);
|
||||
}
|
||||
|
||||
std::vector<unsigned char> AlienwareAW3423DWFController::GetReportResponse()
|
||||
{
|
||||
uint8_t buffer[193];
|
||||
|
||||
memset(buffer, 0, 193);
|
||||
|
||||
hid_get_input_report(dev, buffer, 193);
|
||||
|
||||
return std::vector<unsigned char>(buffer + 1, buffer + 18);
|
||||
}
|
||||
|
||||
void AlienwareAW3423DWFController::PerformLogin()
|
||||
{
|
||||
unsigned char init_packet[64] =
|
||||
{
|
||||
0x40, 0xE1, 0x01
|
||||
};
|
||||
SendControlPacket(init_packet, 4);
|
||||
|
||||
std::vector<unsigned char> response = GetReportResponse();
|
||||
|
||||
std::vector<unsigned char> key = GenerateKey(response);
|
||||
|
||||
unsigned char login_packet[192] = {0x00};
|
||||
login_packet[0] = 0x40;
|
||||
login_packet[1] = 0xE1;
|
||||
login_packet[2] = 0x02;
|
||||
memcpy(login_packet + 64, key.data(), key.size());
|
||||
|
||||
SendControlPacket(login_packet, 192);
|
||||
}
|
||||
|
||||
void AlienwareAW3423DWFController::SendColor(unsigned char led_id, unsigned char r, unsigned char g, unsigned char b)
|
||||
{
|
||||
unsigned char led_id_2 = (led_id == 0x01) ? 0xf6 : (led_id == 0x02) ? 0xf5
|
||||
: (led_id == 0x08) ? 0xff
|
||||
: 0xfc;
|
||||
PerformLogin();
|
||||
|
||||
unsigned char color_packet[192] = {0x00};
|
||||
|
||||
color_packet[0] = 0x40;
|
||||
color_packet[1] = 0xC6;
|
||||
color_packet[6] = 0x0A;
|
||||
color_packet[8] = 0x6E;
|
||||
color_packet[10] = 0x82;
|
||||
color_packet[64] = 0x51;
|
||||
color_packet[65] = 0x87;
|
||||
color_packet[66] = 0xD0;
|
||||
color_packet[67] = 0x04;
|
||||
|
||||
color_packet[68] = led_id;
|
||||
color_packet[69] = r;
|
||||
color_packet[70] = g;
|
||||
color_packet[71] = b;
|
||||
color_packet[72] = 0x64;
|
||||
color_packet[73] = led_id_2;
|
||||
|
||||
SendControlPacket(color_packet, 192);
|
||||
|
||||
std::this_thread::sleep_for(std::chrono::milliseconds(200));
|
||||
}
|
||||
|
||||
std::vector<unsigned char> AlienwareAW3423DWFController::GenerateKey(
|
||||
const std::vector<unsigned char> &response)
|
||||
{
|
||||
std::vector<unsigned char> syn_key(8, 0);
|
||||
|
||||
const std::vector<unsigned char> oem_key = {
|
||||
0xf5, 0x3f, 0xc1, 0x39, 0x44, 0x3a, 0x31, 0x79, 0x0d, 0xb1, 0x82, 0x76
|
||||
};
|
||||
|
||||
size_t sk_idx = 0, ok_idx = 0;
|
||||
while(ok_idx < oem_key.size() && sk_idx < 8)
|
||||
{
|
||||
unsigned char ok_sub_len = (oem_key[ok_idx] & 1) + ((oem_key[ok_idx] & 0x10) >> 4);
|
||||
|
||||
for(unsigned int i = 0; i < ok_sub_len && sk_idx < 8; i++)
|
||||
{
|
||||
syn_key[sk_idx] = oem_key[ok_idx + 1] ^ oem_key[ok_idx];
|
||||
ok_idx++;
|
||||
sk_idx++;
|
||||
}
|
||||
ok_idx++;
|
||||
}
|
||||
|
||||
std::vector<unsigned char> out_buffer;
|
||||
|
||||
uint16_t v15 = static_cast<uint16_t>(response[15]) |
|
||||
(static_cast<uint16_t>(response[0]) << 8);
|
||||
bool parity_odd = (std::bitset<16>(v15).count() % 2 != 0);
|
||||
|
||||
if(parity_odd)
|
||||
{
|
||||
size_t end = std::min<size_t>(8, response.size());
|
||||
out_buffer = std::vector<unsigned char>(response.begin(), response.begin() + end);
|
||||
|
||||
if(response.size() > 14)
|
||||
{
|
||||
unsigned char idx = response[14] & 0x07;
|
||||
if((idx + 8) < (unsigned char)response.size())
|
||||
{
|
||||
out_buffer[idx] ^= response[idx + 8];
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
size_t start = std::min<size_t>(8, response.size());
|
||||
size_t end = std::min<size_t>(start + 8, response.size());
|
||||
out_buffer = std::vector<unsigned char>(response.begin() + start, response.begin() + end);
|
||||
|
||||
if(response.size() > 6)
|
||||
{
|
||||
unsigned char idx = response[6] & 0x07;
|
||||
if(idx < response.size())
|
||||
{
|
||||
out_buffer[idx] ^= response[idx];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for(size_t i = 0; i < 8 && i < out_buffer.size(); i++)
|
||||
{
|
||||
syn_key[i] ^= out_buffer[i];
|
||||
}
|
||||
|
||||
return syn_key;
|
||||
}
|
||||
|
||||
AlienwareAW3423DWFController::~AlienwareAW3423DWFController()
|
||||
{
|
||||
if(dev)
|
||||
{
|
||||
hid_close(dev);
|
||||
dev = nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
std::string AlienwareAW3423DWFController::GetLocation()
|
||||
{
|
||||
return "HID: " + location;
|
||||
}
|
||||
|
||||
std::string AlienwareAW3423DWFController::GetSerialString()
|
||||
{
|
||||
wchar_t serial[256];
|
||||
if(hid_get_serial_number_string(dev, serial, 256) >= 0)
|
||||
{
|
||||
std::wstring ws(serial);
|
||||
return StringUtils::wstring_to_string(ws);
|
||||
}
|
||||
return "";
|
||||
}
|
||||
@@ -0,0 +1,38 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AlienwareAW3423DWFController.h |
|
||||
| |
|
||||
| Driver for the Alienware AW3423DWF monitor |
|
||||
| |
|
||||
| Ferréol DUBOIS COLI (Fefe_du_973) 23 Jan 2025 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <hidapi.h>
|
||||
#include <vector>
|
||||
#include <string>
|
||||
|
||||
class AlienwareAW3423DWFController
|
||||
{
|
||||
public:
|
||||
AlienwareAW3423DWFController(hid_device* dev_handle, const char* path);
|
||||
~AlienwareAW3423DWFController();
|
||||
|
||||
std::string GetLocation();
|
||||
std::string GetSerialString();
|
||||
void SendColor(unsigned char led_id, unsigned char r, unsigned char g, unsigned char b);
|
||||
|
||||
private:
|
||||
hid_device* dev;
|
||||
std::string location;
|
||||
|
||||
static const std::vector<std::vector<unsigned char>> OEM_KEYS;
|
||||
|
||||
void PerformLogin();
|
||||
std::vector<unsigned char> GenerateKey(const std::vector<unsigned char>& response);
|
||||
void SendControlPacket(const unsigned char* data, size_t length);
|
||||
std::vector<unsigned char> GetReportResponse();
|
||||
};
|
||||
@@ -0,0 +1,146 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AlienwareMonitorController.cpp |
|
||||
| |
|
||||
| Detector for Alienware monitors |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 08 May 2025 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include <chrono>
|
||||
#include <cstring>
|
||||
#include <thread>
|
||||
|
||||
#include "AlienwareMonitorController.h"
|
||||
|
||||
AlienwareMonitorController::AlienwareMonitorController(hid_device *dev_handle, const char *path, std::string dev_name)
|
||||
{
|
||||
dev = dev_handle;
|
||||
location = path;
|
||||
name = dev_name;
|
||||
|
||||
Initialize();
|
||||
}
|
||||
|
||||
AlienwareMonitorController::~AlienwareMonitorController()
|
||||
{
|
||||
hid_close(dev);
|
||||
}
|
||||
|
||||
std::string AlienwareMonitorController::GetLocation()
|
||||
{
|
||||
return("HID: " + location);
|
||||
}
|
||||
|
||||
std::string AlienwareMonitorController::GetName()
|
||||
{
|
||||
return(name);
|
||||
}
|
||||
|
||||
std::string AlienwareMonitorController::GetSerialString()
|
||||
{
|
||||
return("");
|
||||
}
|
||||
|
||||
void fillInChecksum(unsigned char *packet)
|
||||
{
|
||||
unsigned char checksum = 110;
|
||||
|
||||
for(unsigned int index = 5; index <= 13; index++)
|
||||
{
|
||||
checksum ^= packet[index];
|
||||
}
|
||||
|
||||
packet[14] = checksum;
|
||||
}
|
||||
|
||||
void AlienwareMonitorController::SendColor(unsigned char led_id, unsigned char r, unsigned char g, unsigned char b)
|
||||
{
|
||||
unsigned char packet[65];
|
||||
|
||||
memset(packet, 0xFF, sizeof(packet));
|
||||
|
||||
packet[0] = 0x00;
|
||||
packet[1] = 0x92;
|
||||
packet[2] = 0x37;
|
||||
packet[3] = 0x0a;
|
||||
packet[4] = 0x00;
|
||||
packet[5] = 0x51;
|
||||
packet[6] = 0x87;
|
||||
packet[7] = 0xd0;
|
||||
packet[8] = 0x04;
|
||||
|
||||
packet[9] = led_id;
|
||||
packet[10] = r;
|
||||
packet[11] = g;
|
||||
packet[12] = b;
|
||||
packet[13] = 0x64;
|
||||
|
||||
fillInChecksum(packet);
|
||||
|
||||
hid_write(dev, packet, sizeof(packet));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Delay 50 milliseconds |
|
||||
\*-----------------------------------------------------*/
|
||||
std::this_thread::sleep_for(std::chrono::milliseconds(50));
|
||||
}
|
||||
|
||||
void AlienwareMonitorController::Initialize()
|
||||
{
|
||||
unsigned char packet[65];
|
||||
|
||||
memset(packet, 0xFF, sizeof(packet));
|
||||
|
||||
packet[0] = 0x00;
|
||||
packet[1] = 0x95;
|
||||
packet[2] = 0x00;
|
||||
packet[3] = 0x00;
|
||||
packet[4] = 0x00;
|
||||
|
||||
hid_write(dev, packet, sizeof(packet));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Delay 50 milliseconds |
|
||||
\*-----------------------------------------------------*/
|
||||
std::this_thread::sleep_for(std::chrono::milliseconds(50));
|
||||
|
||||
memset(packet, 0xFF, sizeof(packet));
|
||||
|
||||
packet[0] = 0x00;
|
||||
packet[1] = 0x92;
|
||||
packet[2] = 0x37;
|
||||
packet[3] = 0x08;
|
||||
packet[4] = 0x00;
|
||||
packet[5] = 0x51;
|
||||
packet[6] = 0x85;
|
||||
packet[7] = 0x01;
|
||||
packet[8] = 0xFE;
|
||||
packet[9] = 0x03;
|
||||
packet[10] = 0x00;
|
||||
packet[11] = 0x06;
|
||||
packet[12] = 0x40;
|
||||
|
||||
hid_write(dev, packet, sizeof(packet));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Delay 50 milliseconds |
|
||||
\*-----------------------------------------------------*/
|
||||
std::this_thread::sleep_for(std::chrono::milliseconds(50));
|
||||
|
||||
memset(packet, 0x00, sizeof(packet));
|
||||
|
||||
packet[0] = 0x00;
|
||||
packet[1] = 0x93;
|
||||
packet[2] = 0x37;
|
||||
packet[3] = 0x12;
|
||||
|
||||
hid_write(dev, packet, sizeof(packet));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Delay 50 milliseconds |
|
||||
\*-----------------------------------------------------*/
|
||||
std::this_thread::sleep_for(std::chrono::milliseconds(50));
|
||||
}
|
||||
@@ -0,0 +1,35 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AlienwareMonitorController.h |
|
||||
| |
|
||||
| Detector for Alienware monitors |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 08 May 2025 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <hidapi.h>
|
||||
#include <vector>
|
||||
#include <string>
|
||||
|
||||
class AlienwareMonitorController
|
||||
{
|
||||
public:
|
||||
AlienwareMonitorController(hid_device* dev_handle, const char* path, std::string dev_name);
|
||||
~AlienwareMonitorController();
|
||||
|
||||
std::string GetLocation();
|
||||
std::string GetName();
|
||||
std::string GetSerialString();
|
||||
void SendColor(unsigned char led_id, unsigned char r, unsigned char g, unsigned char b);
|
||||
|
||||
private:
|
||||
hid_device* dev;
|
||||
std::string location;
|
||||
std::string name;
|
||||
|
||||
void Initialize();
|
||||
};
|
||||
@@ -0,0 +1,66 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AlienwareMonitorControllerDetect.cpp |
|
||||
| |
|
||||
| Detector for Alienware monitors |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 08 May 2025 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "Detector.h"
|
||||
#include "AlienwareAW3423DWFController.h"
|
||||
#include "AlienwareMonitorController.h"
|
||||
#include "RGBController_AlienwareAW3423DWF.h"
|
||||
#include "RGBController_AlienwareMonitor.h"
|
||||
#include <hidapi.h>
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Alienware Vendor ID |
|
||||
\*---------------------------------------------------------*/
|
||||
#define ALIENWARE_VID 0x187C
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Alienware Vendor ID |
|
||||
\*---------------------------------------------------------*/
|
||||
#define ALIENWARE_AW3423DWF_PID 0x100E
|
||||
#define ALIENWARE_AW3225QF_PID 0x1013
|
||||
#define ALIENWARE_USAGE_PAGE 0xFFDA
|
||||
#define ALIENWARE_USAGE 0x00DA
|
||||
|
||||
/******************************************************************************************\
|
||||
* *
|
||||
* AlienwareAW3423DWFControllerDetect *
|
||||
* *
|
||||
* Tests the USB address to see if an Alienware AW3423DWF exists there. *
|
||||
* *
|
||||
\******************************************************************************************/
|
||||
|
||||
void DetectAlienwareAW3423DWFControllers(hid_device_info* info, const std::string&)
|
||||
{
|
||||
hid_device* dev = hid_open_path(info->path);
|
||||
if(dev)
|
||||
{
|
||||
AlienwareAW3423DWFController* controller = new AlienwareAW3423DWFController(dev, info->path);
|
||||
RGBController_AlienwareAW3423DWF* rgb_controller = new RGBController_AlienwareAW3423DWF(controller);
|
||||
|
||||
ResourceManager::get()->RegisterRGBController(rgb_controller);
|
||||
}
|
||||
}
|
||||
|
||||
void DetectAlienwareMonitorControllers(hid_device_info* info, const std::string& name)
|
||||
{
|
||||
hid_device* dev = hid_open_path(info->path);
|
||||
|
||||
if(dev)
|
||||
{
|
||||
AlienwareMonitorController* controller = new AlienwareMonitorController(dev, info->path, name);
|
||||
RGBController_AlienwareMonitor* rgb_controller = new RGBController_AlienwareMonitor(controller);
|
||||
|
||||
ResourceManager::get()->RegisterRGBController(rgb_controller);
|
||||
}
|
||||
}
|
||||
|
||||
REGISTER_HID_DETECTOR("Alienware AW3423DWF", DetectAlienwareAW3423DWFControllers, ALIENWARE_VID, ALIENWARE_AW3423DWF_PID);
|
||||
REGISTER_HID_DETECTOR("Alienware AW3225QF", DetectAlienwareMonitorControllers, ALIENWARE_VID, ALIENWARE_AW3225QF_PID);
|
||||
@@ -0,0 +1,141 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_AlienwareAW3423DWF.cpp |
|
||||
| |
|
||||
| RGBController for the Alienware AW3423DWF monitor |
|
||||
| |
|
||||
| Ferréol DUBOIS COLI (Fefe_du_973) 23 Jan 2025 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "RGBController_AlienwareAW3423DWF.h"
|
||||
|
||||
/**------------------------------------------------------------------*\
|
||||
@name AW3423DWF
|
||||
@category Accessory
|
||||
@type USB
|
||||
@save :x:
|
||||
@direct :white_check_mark:
|
||||
@effects :x:
|
||||
@detectors DetectAlienwareAW3423DWFControllers
|
||||
@comment
|
||||
\*-------------------------------------------------------------------*/
|
||||
|
||||
RGBController_AlienwareAW3423DWF::RGBController_AlienwareAW3423DWF(AlienwareAW3423DWFController* controller_ptr)
|
||||
{
|
||||
controller = controller_ptr;
|
||||
|
||||
name = "Alienware AW3423DWF";
|
||||
vendor = "Alienware";
|
||||
type = DEVICE_TYPE_MONITOR;
|
||||
description = "Alienware AW3423DWF Monitor Device";
|
||||
location = controller->GetLocation();
|
||||
serial = controller->GetSerialString();
|
||||
|
||||
mode Direct;
|
||||
Direct.name = "Direct";
|
||||
Direct.flags = MODE_FLAG_HAS_PER_LED_COLOR;
|
||||
Direct.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Direct);
|
||||
|
||||
active_mode = 0;
|
||||
|
||||
SetupZones();
|
||||
}
|
||||
|
||||
RGBController_AlienwareAW3423DWF::~RGBController_AlienwareAW3423DWF()
|
||||
{
|
||||
delete controller;
|
||||
}
|
||||
|
||||
void RGBController_AlienwareAW3423DWF::SetupZones()
|
||||
{
|
||||
zone Logo;
|
||||
Logo.name = "Logo";
|
||||
Logo.type = ZONE_TYPE_SINGLE;
|
||||
Logo.leds_min = 1;
|
||||
Logo.leds_max = 1;
|
||||
Logo.leds_count = 1;
|
||||
Logo.matrix_map = NULL;
|
||||
zones.push_back(Logo);
|
||||
|
||||
led Logo_LED;
|
||||
Logo_LED.name = "Logo";
|
||||
Logo_LED.value = 0x01;
|
||||
leds.push_back(Logo_LED);
|
||||
|
||||
zone Number;
|
||||
Number.name = "Number";
|
||||
Number.type = ZONE_TYPE_SINGLE;
|
||||
Number.leds_min = 1;
|
||||
Number.leds_max = 1;
|
||||
Number.leds_count = 1;
|
||||
Number.matrix_map = NULL;
|
||||
zones.push_back(Number);
|
||||
|
||||
led Number_LED;
|
||||
Number_LED.name = "Number";
|
||||
Number_LED.value = 0x02;
|
||||
leds.push_back(Number_LED);
|
||||
|
||||
zone PowerButton;
|
||||
PowerButton.name = "Power Button";
|
||||
PowerButton.type = ZONE_TYPE_SINGLE;
|
||||
PowerButton.leds_min = 1;
|
||||
PowerButton.leds_max = 1;
|
||||
PowerButton.leds_count = 1;
|
||||
PowerButton.matrix_map = NULL;
|
||||
zones.push_back(PowerButton);
|
||||
|
||||
led PowerButton_LED;
|
||||
PowerButton_LED.name = "Power Button";
|
||||
PowerButton_LED.value = 0x08;
|
||||
leds.push_back(PowerButton_LED);
|
||||
|
||||
SetupColors();
|
||||
}
|
||||
|
||||
void RGBController_AlienwareAW3423DWF::ResizeZone(int /*zone*/, int /*new_size*/)
|
||||
{
|
||||
}
|
||||
|
||||
void RGBController_AlienwareAW3423DWF::DeviceUpdateLEDs()
|
||||
{
|
||||
/*-----------------------------------------------------*\
|
||||
| If all three colors are the same value, speed up the |
|
||||
| direct mode by using the ALL target (0x0B) instead of |
|
||||
| setting each LED individually. |
|
||||
\*-----------------------------------------------------*/
|
||||
if((colors[0] == colors[1]) && (colors[1] == colors[2]))
|
||||
{
|
||||
unsigned char red = RGBGetRValue(colors[0]);
|
||||
unsigned char grn = RGBGetGValue(colors[0]);
|
||||
unsigned char blu = RGBGetBValue(colors[0]);
|
||||
controller->SendColor(0x0B, red, grn, blu);
|
||||
}
|
||||
else
|
||||
{
|
||||
for(unsigned int led_idx = 0; led_idx < leds.size(); led_idx++)
|
||||
{
|
||||
UpdateSingleLED(led_idx);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void RGBController_AlienwareAW3423DWF::UpdateZoneLEDs(int /*zone*/)
|
||||
{
|
||||
DeviceUpdateLEDs();
|
||||
}
|
||||
|
||||
void RGBController_AlienwareAW3423DWF::UpdateSingleLED(int led)
|
||||
{
|
||||
unsigned char red = RGBGetRValue(colors[led]);
|
||||
unsigned char grn = RGBGetGValue(colors[led]);
|
||||
unsigned char blu = RGBGetBValue(colors[led]);
|
||||
controller->SendColor(leds[led].value, red, grn, blu);
|
||||
}
|
||||
|
||||
void RGBController_AlienwareAW3423DWF::DeviceUpdateMode()
|
||||
{
|
||||
}
|
||||
@@ -0,0 +1,34 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_AlienwareAW3423DWF.h |
|
||||
| |
|
||||
| RGBController for the Alienware AW3423DWF monitor |
|
||||
| |
|
||||
| Ferréol DUBOIS COLI (Fefe_du_973) 23 Jan 2025 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "AlienwareAW3423DWFController.h"
|
||||
#include "RGBController.h"
|
||||
|
||||
class RGBController_AlienwareAW3423DWF : public RGBController
|
||||
{
|
||||
public:
|
||||
explicit RGBController_AlienwareAW3423DWF(AlienwareAW3423DWFController* controller_ptr);
|
||||
~RGBController_AlienwareAW3423DWF();
|
||||
|
||||
void SetupZones();
|
||||
void ResizeZone(int zone, int new_size);
|
||||
|
||||
void DeviceUpdateLEDs();
|
||||
void UpdateZoneLEDs(int zone);
|
||||
void UpdateSingleLED(int led);
|
||||
|
||||
void DeviceUpdateMode();
|
||||
|
||||
private:
|
||||
AlienwareAW3423DWFController* controller;
|
||||
};
|
||||
@@ -0,0 +1,143 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_AlienwareMonitor.cpp |
|
||||
| |
|
||||
| RGBController for Alienware monitors |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 08 May 2025 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "RGBController_AlienwareMonitor.h"
|
||||
|
||||
/**------------------------------------------------------------------*\
|
||||
@name Alienware Monitor
|
||||
@category Accessory
|
||||
@type USB
|
||||
@save :x:
|
||||
@direct :white_check_mark:
|
||||
@effects :x:
|
||||
@detectors DetectAlienwareMonitorControllers
|
||||
@comment
|
||||
\*-------------------------------------------------------------------*/
|
||||
|
||||
RGBController_AlienwareMonitor::RGBController_AlienwareMonitor(AlienwareMonitorController* controller_ptr)
|
||||
{
|
||||
controller = controller_ptr;
|
||||
|
||||
name = controller->GetName();
|
||||
description = "Alienware Monitor";
|
||||
vendor = "Alienware";
|
||||
type = DEVICE_TYPE_MONITOR;
|
||||
location = controller->GetLocation();
|
||||
serial = controller->GetSerialString();
|
||||
|
||||
mode Direct;
|
||||
Direct.name = "Direct";
|
||||
Direct.flags = MODE_FLAG_HAS_PER_LED_COLOR;
|
||||
Direct.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Direct);
|
||||
|
||||
active_mode = 0;
|
||||
|
||||
SetupZones();
|
||||
}
|
||||
|
||||
RGBController_AlienwareMonitor::~RGBController_AlienwareMonitor()
|
||||
{
|
||||
delete controller;
|
||||
}
|
||||
|
||||
void RGBController_AlienwareMonitor::SetupZones()
|
||||
{
|
||||
zone Logo;
|
||||
Logo.name = "Logo";
|
||||
Logo.type = ZONE_TYPE_SINGLE;
|
||||
Logo.leds_min = 1;
|
||||
Logo.leds_max = 1;
|
||||
Logo.leds_count = 1;
|
||||
Logo.matrix_map = NULL;
|
||||
zones.push_back(Logo);
|
||||
|
||||
led Logo_LED;
|
||||
Logo_LED.name = "Logo";
|
||||
Logo_LED.value = 0x01;
|
||||
leds.push_back(Logo_LED);
|
||||
|
||||
zone Number;
|
||||
Number.name = "Number";
|
||||
Number.type = ZONE_TYPE_SINGLE;
|
||||
Number.leds_min = 1;
|
||||
Number.leds_max = 1;
|
||||
Number.leds_count = 1;
|
||||
Number.matrix_map = NULL;
|
||||
zones.push_back(Number);
|
||||
|
||||
led Number_LED;
|
||||
Number_LED.name = "Number";
|
||||
Number_LED.value = 0x02;
|
||||
leds.push_back(Number_LED);
|
||||
|
||||
zone PowerButton;
|
||||
PowerButton.name = "Power Button";
|
||||
PowerButton.type = ZONE_TYPE_SINGLE;
|
||||
PowerButton.leds_min = 1;
|
||||
PowerButton.leds_max = 1;
|
||||
PowerButton.leds_count = 1;
|
||||
PowerButton.matrix_map = NULL;
|
||||
zones.push_back(PowerButton);
|
||||
|
||||
led PowerButton_LED;
|
||||
PowerButton_LED.name = "Power Button";
|
||||
PowerButton_LED.value = 0x08;
|
||||
leds.push_back(PowerButton_LED);
|
||||
|
||||
SetupColors();
|
||||
}
|
||||
|
||||
void RGBController_AlienwareMonitor::ResizeZone(int /*zone*/, int /*new_size*/)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
void RGBController_AlienwareMonitor::DeviceUpdateLEDs()
|
||||
{
|
||||
/*-----------------------------------------------------*\
|
||||
| If all three colors are the same value, speed up the |
|
||||
| direct mode by using the ALL target (0x0B) instead of |
|
||||
| setting each LED individually. |
|
||||
\*-----------------------------------------------------*/
|
||||
if((colors[0] == colors[1]) && (colors[1] == colors[2]))
|
||||
{
|
||||
unsigned char red = RGBGetRValue(colors[0]);
|
||||
unsigned char grn = RGBGetGValue(colors[0]);
|
||||
unsigned char blu = RGBGetBValue(colors[0]);
|
||||
controller->SendColor(0x0B, red, grn, blu);
|
||||
}
|
||||
else
|
||||
{
|
||||
for(unsigned int led_idx = 0; led_idx < leds.size(); led_idx++)
|
||||
{
|
||||
UpdateSingleLED(led_idx);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void RGBController_AlienwareMonitor::UpdateZoneLEDs(int /*zone*/)
|
||||
{
|
||||
DeviceUpdateLEDs();
|
||||
}
|
||||
|
||||
void RGBController_AlienwareMonitor::UpdateSingleLED(int led)
|
||||
{
|
||||
unsigned char red = RGBGetRValue(colors[led]);
|
||||
unsigned char grn = RGBGetGValue(colors[led]);
|
||||
unsigned char blu = RGBGetBValue(colors[led]);
|
||||
controller->SendColor(leds[led].value, red, grn, blu);
|
||||
}
|
||||
|
||||
void RGBController_AlienwareMonitor::DeviceUpdateMode()
|
||||
{
|
||||
|
||||
}
|
||||
@@ -0,0 +1,34 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_AlienwareMonitor.h |
|
||||
| |
|
||||
| RGBController for Alienware monitors |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 08 May 2025 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "RGBController.h"
|
||||
#include "AlienwareMonitorController.h"
|
||||
|
||||
class RGBController_AlienwareMonitor : public RGBController
|
||||
{
|
||||
public:
|
||||
RGBController_AlienwareMonitor(AlienwareMonitorController* controller_ptr);
|
||||
~RGBController_AlienwareMonitor();
|
||||
|
||||
void SetupZones();
|
||||
void ResizeZone(int zone, int new_size);
|
||||
|
||||
void DeviceUpdateLEDs();
|
||||
void UpdateZoneLEDs(int zone);
|
||||
void UpdateSingleLED(int led);
|
||||
|
||||
void DeviceUpdateMode();
|
||||
|
||||
private:
|
||||
AlienwareMonitorController* controller;
|
||||
};
|
||||
@@ -0,0 +1,123 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AnnePro2Controller.cpp |
|
||||
| |
|
||||
| Driver for Obins Lab AnnePro2 keyboard |
|
||||
| |
|
||||
| Sergey Gavrilov (DrZlo13) 06 Jun 2021 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "AnnePro2Controller.h"
|
||||
#include "StringUtils.h"
|
||||
|
||||
using namespace std::chrono_literals;
|
||||
|
||||
AnnePro2Controller::AnnePro2Controller(hid_device* dev_handle, const char* path)
|
||||
{
|
||||
dev = dev_handle;
|
||||
location = path;
|
||||
}
|
||||
|
||||
AnnePro2Controller::~AnnePro2Controller()
|
||||
{
|
||||
hid_close(dev);
|
||||
}
|
||||
|
||||
std::string AnnePro2Controller::GetDeviceLocation()
|
||||
{
|
||||
return("HID: " + location);
|
||||
}
|
||||
|
||||
std::string AnnePro2Controller::GetSerialString()
|
||||
{
|
||||
wchar_t serial_string[128];
|
||||
int ret = hid_get_serial_number_string(dev, serial_string, 128);
|
||||
|
||||
if(ret != 0)
|
||||
{
|
||||
return("");
|
||||
}
|
||||
|
||||
return(StringUtils::wstring_to_string(serial_string));
|
||||
}
|
||||
|
||||
void AnnePro2Controller::SendDirect(unsigned char frame_count, unsigned char * frame_data)
|
||||
{
|
||||
/*-------------------------------------------------------------*\
|
||||
| Reverse engineered by https://github.com/manualmanul/Annemone |
|
||||
\*-------------------------------------------------------------*/
|
||||
|
||||
const unsigned char hid_cmd_service_data_length = 4;
|
||||
const unsigned char hid_cmd_service_data[hid_cmd_service_data_length] = {0, 123, 16, 65};
|
||||
|
||||
const unsigned char hid_cmd_static_message_length = 3;
|
||||
const unsigned char hid_cmd_static_message[hid_cmd_static_message_length] = {0, 0, 125};
|
||||
|
||||
const unsigned char hid_cmd_command_info_length = 3;
|
||||
const unsigned char hid_cmd_command_info[hid_cmd_command_info_length] = {32, 3, 255};
|
||||
|
||||
const unsigned char real_command_info_length = hid_cmd_command_info_length + 1;
|
||||
const unsigned char max_hid_length = 64;
|
||||
|
||||
const unsigned char max_command_length = max_hid_length - hid_cmd_service_data_length - 2 - hid_cmd_static_message_length;
|
||||
const unsigned char max_message_length = max_command_length - real_command_info_length;
|
||||
const unsigned char messages_to_send_amount = frame_count / max_message_length + 1;
|
||||
const unsigned char val_1 = frame_count % max_message_length;
|
||||
const unsigned char val_2 = (0 == val_1) ? max_message_length : val_1;
|
||||
|
||||
unsigned char hid_command[max_hid_length];
|
||||
|
||||
unsigned char led_data = 0;
|
||||
|
||||
for(unsigned char p = 0; p < messages_to_send_amount; p++)
|
||||
{
|
||||
const unsigned char e = (messages_to_send_amount << 4) + p;
|
||||
const unsigned char a = ((messages_to_send_amount - 1) == p) ? val_2 + real_command_info_length : max_message_length + real_command_info_length;
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Service data |
|
||||
\*---------------------------------------------------------*/
|
||||
hid_command[0] = hid_cmd_service_data[0];
|
||||
hid_command[1] = hid_cmd_service_data[1];
|
||||
hid_command[2] = hid_cmd_service_data[2];
|
||||
hid_command[3] = hid_cmd_service_data[3];
|
||||
|
||||
hid_command[4] = e;
|
||||
hid_command[5] = a;
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Static message |
|
||||
\*---------------------------------------------------------*/
|
||||
hid_command[6] = hid_cmd_static_message[0];
|
||||
hid_command[7] = hid_cmd_static_message[1];
|
||||
hid_command[8] = hid_cmd_static_message[2];
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Command info |
|
||||
\*---------------------------------------------------------*/
|
||||
hid_command[9] = hid_cmd_command_info[0];
|
||||
hid_command[10] = hid_cmd_command_info[1];
|
||||
hid_command[11] = hid_cmd_command_info[2];
|
||||
|
||||
hid_command[12] = 2;
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| LED data |
|
||||
\*---------------------------------------------------------*/
|
||||
for(uint8_t i = 0; i < max_message_length; i++)
|
||||
{
|
||||
hid_command[13 + i] = frame_data[led_data];
|
||||
led_data++;
|
||||
}
|
||||
|
||||
hid_write(dev, hid_command, max_hid_length);
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Needed due to Anne Pro 2 ignoring commands when they're |
|
||||
| sent faster than 50ms apart from each other. |
|
||||
\*---------------------------------------------------------*/
|
||||
std::this_thread::sleep_for(50ms);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,37 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AnnePro2Controller.h |
|
||||
| |
|
||||
| Driver for Obins Lab AnnePro2 keyboard |
|
||||
| |
|
||||
| Sergey Gavrilov (DrZlo13) 06 Jun 2021 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <string>
|
||||
#include <vector>
|
||||
#include <hidapi.h>
|
||||
#include "RGBController.h"
|
||||
|
||||
class AnnePro2Controller
|
||||
{
|
||||
public:
|
||||
AnnePro2Controller(hid_device* dev_handle, const char* path);
|
||||
~AnnePro2Controller();
|
||||
|
||||
std::string GetDeviceLocation();
|
||||
std::string GetSerialString();
|
||||
|
||||
void SendDirect
|
||||
(
|
||||
unsigned char frame_count,
|
||||
unsigned char * frame_data
|
||||
);
|
||||
|
||||
private:
|
||||
hid_device* dev;
|
||||
std::string location;
|
||||
};
|
||||
@@ -0,0 +1,57 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AnnePro2ControllerDetect.cpp |
|
||||
| |
|
||||
| Detector for Obins Lab AnnePro2 keyboard |
|
||||
| |
|
||||
| Sergey Gavrilov (DrZlo13) 06 Jun 2021 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "Detector.h"
|
||||
#include "AnnePro2Controller.h"
|
||||
#include "RGBController_AnnePro2.h"
|
||||
#include <hidapi.h>
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Anne Pro 2 vendor IDs |
|
||||
\*---------------------------------------------------------*/
|
||||
#define ANNE_PRO_2_VID_1 0x04D9
|
||||
#define ANNE_PRO_2_VID_2 0x3311
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Anne Pro 2 product IDs |
|
||||
\*---------------------------------------------------------*/
|
||||
#define ANNE_PRO_2_PID_1 0x8008
|
||||
#define ANNE_PRO_2_PID_2 0x8009
|
||||
#define ANNE_PRO_2_PID_3 0xA292
|
||||
#define ANNE_PRO_2_PID_4 0xA293
|
||||
#define ANNE_PRO_2_PID_5 0xA297
|
||||
|
||||
/******************************************************************************************\
|
||||
* *
|
||||
* DetectAnnePro2Controllers *
|
||||
* *
|
||||
* Tests the USB address to see if an Obins Lab AnnePro2 keyboard exists there. *
|
||||
* *
|
||||
\******************************************************************************************/
|
||||
|
||||
void DetectAnnePro2Controllers(hid_device_info* info, const std::string&)
|
||||
{
|
||||
hid_device* dev = hid_open_path(info->path);
|
||||
|
||||
if(dev)
|
||||
{
|
||||
AnnePro2Controller* controller = new AnnePro2Controller(dev, info->path);
|
||||
RGBController_AnnePro2* rgb_controller = new RGBController_AnnePro2(controller);
|
||||
|
||||
ResourceManager::get()->RegisterRGBController(rgb_controller);
|
||||
}
|
||||
}
|
||||
|
||||
REGISTER_HID_DETECTOR_I("Anne Pro 2", DetectAnnePro2Controllers, ANNE_PRO_2_VID_1, ANNE_PRO_2_PID_1, 1);
|
||||
REGISTER_HID_DETECTOR_I("Anne Pro 2", DetectAnnePro2Controllers, ANNE_PRO_2_VID_1, ANNE_PRO_2_PID_2, 1);
|
||||
REGISTER_HID_DETECTOR_I("Anne Pro 2", DetectAnnePro2Controllers, ANNE_PRO_2_VID_1, ANNE_PRO_2_PID_3, 1);
|
||||
REGISTER_HID_DETECTOR_I("Anne Pro 2", DetectAnnePro2Controllers, ANNE_PRO_2_VID_1, ANNE_PRO_2_PID_4, 1);
|
||||
REGISTER_HID_DETECTOR_I("Anne Pro 2", DetectAnnePro2Controllers, ANNE_PRO_2_VID_2, ANNE_PRO_2_PID_5, 1);
|
||||
@@ -0,0 +1,244 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_AnnePro2.cpp |
|
||||
| |
|
||||
| RGBController for Obins Lab AnnePro2 keyboard |
|
||||
| |
|
||||
| Sergey Gavrilov (DrZlo13) 06 Jun 2021 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "RGBControllerKeyNames.h"
|
||||
#include "RGBController_AnnePro2.h"
|
||||
|
||||
#define NA 0xFFFFFFFF
|
||||
#define LED_REAL_COUNT (5*14)
|
||||
#define LED_COUNT (LED_REAL_COUNT - 9)
|
||||
|
||||
static unsigned int matrix_map[5][14] =
|
||||
{ { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13 },
|
||||
{ 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27 },
|
||||
{ 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, NA },
|
||||
{ 41, NA, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, NA },
|
||||
{ 53, NA, 54, 55, NA, NA, 56, NA, NA, 57, 58, 59, 60, NA } };
|
||||
|
||||
static const char* zone_names[] =
|
||||
{
|
||||
ZONE_EN_KEYBOARD,
|
||||
};
|
||||
|
||||
static zone_type zone_types[] =
|
||||
{
|
||||
ZONE_TYPE_MATRIX
|
||||
};
|
||||
|
||||
static const unsigned int zone_sizes[] =
|
||||
{
|
||||
LED_COUNT,
|
||||
};
|
||||
|
||||
typedef struct
|
||||
{
|
||||
const char * name;
|
||||
const unsigned char idx;
|
||||
} annepro2_led_type;
|
||||
|
||||
static const annepro2_led_type led_names[] =
|
||||
{
|
||||
/* Key Label Index */
|
||||
{ KEY_EN_ESCAPE, 0 },
|
||||
{ KEY_EN_1, 1 },
|
||||
{ KEY_EN_2, 2 },
|
||||
{ KEY_EN_3, 3 },
|
||||
{ KEY_EN_4, 4 },
|
||||
{ KEY_EN_5, 5 },
|
||||
{ KEY_EN_6, 6 },
|
||||
{ KEY_EN_7, 7 },
|
||||
{ KEY_EN_8, 8 },
|
||||
{ KEY_EN_9, 9 },
|
||||
{ KEY_EN_0, 10 },
|
||||
{ KEY_EN_MINUS, 11 },
|
||||
{ KEY_EN_EQUALS, 12 },
|
||||
{ KEY_EN_BACKSPACE, 13 },
|
||||
{ KEY_EN_TAB, 14 },
|
||||
{ KEY_EN_Q, 15 },
|
||||
{ KEY_EN_W, 16 },
|
||||
{ KEY_EN_E, 17 },
|
||||
{ KEY_EN_R, 18 },
|
||||
{ KEY_EN_T, 19 },
|
||||
{ KEY_EN_Y, 20 },
|
||||
{ KEY_EN_U, 21 },
|
||||
{ KEY_EN_I, 22 },
|
||||
{ KEY_EN_O, 23 },
|
||||
{ KEY_EN_P, 24 },
|
||||
{ KEY_EN_LEFT_BRACKET, 25 },
|
||||
{ KEY_EN_RIGHT_BRACKET, 26 },
|
||||
{ KEY_EN_ANSI_BACK_SLASH, 27 },
|
||||
{ KEY_EN_CAPS_LOCK, 28 },
|
||||
{ KEY_EN_A, 29 },
|
||||
{ KEY_EN_S, 30 },
|
||||
{ KEY_EN_D, 31 },
|
||||
{ KEY_EN_F, 32 },
|
||||
{ KEY_EN_G, 33 },
|
||||
{ KEY_EN_H, 34 },
|
||||
{ KEY_EN_J, 35 },
|
||||
{ KEY_EN_K, 36 },
|
||||
{ KEY_EN_L, 37 },
|
||||
{ KEY_EN_SEMICOLON, 38 },
|
||||
{ KEY_EN_QUOTE, 39 },
|
||||
{ KEY_EN_ANSI_ENTER, 40 },
|
||||
{ KEY_EN_LEFT_SHIFT, 41 },
|
||||
{ KEY_EN_Z, 42 },
|
||||
{ KEY_EN_X, 43 },
|
||||
{ KEY_EN_C, 44 },
|
||||
{ KEY_EN_V, 45 },
|
||||
{ KEY_EN_B, 46 },
|
||||
{ KEY_EN_N, 47 },
|
||||
{ KEY_EN_M, 48 },
|
||||
{ KEY_EN_COMMA, 49 },
|
||||
{ KEY_EN_PERIOD, 50 },
|
||||
{ KEY_EN_FORWARD_SLASH, 51 },
|
||||
{ KEY_EN_RIGHT_SHIFT, 52 },
|
||||
{ KEY_EN_LEFT_CONTROL, 53 },
|
||||
{ KEY_EN_LEFT_WINDOWS, 54 },
|
||||
{ KEY_EN_LEFT_ALT, 55 },
|
||||
{ KEY_EN_SPACE, 56 },
|
||||
{ KEY_EN_RIGHT_ALT, 57 },
|
||||
{ KEY_EN_RIGHT_FUNCTION, 58 },
|
||||
{ KEY_EN_MENU, 59 },
|
||||
{ KEY_EN_RIGHT_CONTROL, 60 },
|
||||
};
|
||||
|
||||
/**------------------------------------------------------------------*\
|
||||
@name Anne Pro 2
|
||||
@category Keyboard
|
||||
@type USB
|
||||
@save :x:
|
||||
@direct :white_check_mark:
|
||||
@effects :x:
|
||||
@detectors DetectAnnePro2Controllers
|
||||
@comment
|
||||
\*-------------------------------------------------------------------*/
|
||||
|
||||
RGBController_AnnePro2::RGBController_AnnePro2(AnnePro2Controller* controller_ptr)
|
||||
{
|
||||
controller = controller_ptr;
|
||||
|
||||
name = "Anne Pro 2";
|
||||
vendor = "Obinslab";
|
||||
type = DEVICE_TYPE_KEYBOARD;
|
||||
description = "Obinslab Anne Pro 2 Device";
|
||||
location = controller->GetDeviceLocation();
|
||||
serial = controller->GetSerialString();
|
||||
|
||||
mode Direct;
|
||||
Direct.name = "Direct";
|
||||
Direct.value = 0;
|
||||
Direct.flags = MODE_FLAG_HAS_PER_LED_COLOR;
|
||||
Direct.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Direct);
|
||||
|
||||
SetupZones();
|
||||
}
|
||||
|
||||
RGBController_AnnePro2::~RGBController_AnnePro2()
|
||||
{
|
||||
delete controller;
|
||||
}
|
||||
|
||||
void RGBController_AnnePro2::SetupZones()
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| Set up zones |
|
||||
\*---------------------------------------------------------*/
|
||||
unsigned int total_led_count = 0;
|
||||
for(unsigned int zone_idx = 0; zone_idx < 1; zone_idx++)
|
||||
{
|
||||
zone new_zone;
|
||||
new_zone.name = zone_names[zone_idx];
|
||||
new_zone.type = zone_types[zone_idx];
|
||||
new_zone.leds_min = zone_sizes[zone_idx];
|
||||
new_zone.leds_max = zone_sizes[zone_idx];
|
||||
new_zone.leds_count = zone_sizes[zone_idx];
|
||||
|
||||
if(zone_types[zone_idx] == ZONE_TYPE_MATRIX)
|
||||
{
|
||||
new_zone.matrix_map = new matrix_map_type;
|
||||
new_zone.matrix_map->height = 5;
|
||||
new_zone.matrix_map->width = 14;
|
||||
new_zone.matrix_map->map = (unsigned int *)&matrix_map;
|
||||
}
|
||||
else
|
||||
{
|
||||
new_zone.matrix_map = NULL;
|
||||
}
|
||||
|
||||
zones.push_back(new_zone);
|
||||
|
||||
total_led_count += zone_sizes[zone_idx];
|
||||
}
|
||||
|
||||
for(unsigned int led_idx = 0; led_idx < total_led_count; led_idx++)
|
||||
{
|
||||
led new_led;
|
||||
new_led.name = led_names[led_idx].name;
|
||||
new_led.value = led_names[led_idx].idx;
|
||||
leds.push_back(new_led);
|
||||
}
|
||||
|
||||
SetupColors();
|
||||
}
|
||||
|
||||
void RGBController_AnnePro2::ResizeZone(int /*zone*/, int /*new_size*/)
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| This device does not support resizing zones |
|
||||
\*---------------------------------------------------------*/
|
||||
}
|
||||
|
||||
void RGBController_AnnePro2::DeviceUpdateLEDs()
|
||||
{
|
||||
const unsigned char frame_buf_length = LED_REAL_COUNT * 3;
|
||||
unsigned char frame_buf[frame_buf_length];
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| TODO: Send packets with multiple LED frames |
|
||||
\*---------------------------------------------------------*/
|
||||
std::size_t led_real_idx = 0;
|
||||
for(std::size_t led_idx = 0; led_idx < leds.size(); led_idx++)
|
||||
{
|
||||
frame_buf[(led_real_idx * 3) + 0] = RGBGetRValue(colors[led_idx]);
|
||||
frame_buf[(led_real_idx * 3) + 1] = RGBGetGValue(colors[led_idx]);
|
||||
frame_buf[(led_real_idx * 3) + 2] = RGBGetBValue(colors[led_idx]);
|
||||
|
||||
if(led_idx == 40 || led_idx == 41 || led_idx == 52 || led_idx == 53 || led_idx == 60)
|
||||
{
|
||||
led_real_idx++;
|
||||
}
|
||||
else if(led_idx == 55 || led_idx == 56)
|
||||
{
|
||||
led_real_idx++;
|
||||
led_real_idx++;
|
||||
}
|
||||
|
||||
led_real_idx++;
|
||||
}
|
||||
|
||||
controller->SendDirect(frame_buf_length, frame_buf);
|
||||
}
|
||||
|
||||
void RGBController_AnnePro2::UpdateZoneLEDs(int /*zone*/)
|
||||
{
|
||||
DeviceUpdateLEDs();
|
||||
}
|
||||
|
||||
void RGBController_AnnePro2::UpdateSingleLED(int /*led*/)
|
||||
{
|
||||
DeviceUpdateLEDs();
|
||||
}
|
||||
|
||||
void RGBController_AnnePro2::DeviceUpdateMode()
|
||||
{
|
||||
|
||||
}
|
||||
@@ -0,0 +1,34 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_AnnePro2.h |
|
||||
| |
|
||||
| RGBController for Obins Lab AnnePro2 keyboard |
|
||||
| |
|
||||
| Sergey Gavrilov (DrZlo13) 06 Jun 2021 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "RGBController.h"
|
||||
#include "AnnePro2Controller.h"
|
||||
|
||||
class RGBController_AnnePro2 : public RGBController
|
||||
{
|
||||
public:
|
||||
RGBController_AnnePro2(AnnePro2Controller* controller_ptr);
|
||||
~RGBController_AnnePro2();
|
||||
|
||||
void SetupZones();
|
||||
void ResizeZone(int zone, int new_size);
|
||||
|
||||
void DeviceUpdateLEDs();
|
||||
void UpdateZoneLEDs(int zone);
|
||||
void UpdateSingleLED(int led);
|
||||
|
||||
void DeviceUpdateMode();
|
||||
|
||||
private:
|
||||
AnnePro2Controller* controller;
|
||||
};
|
||||
@@ -0,0 +1,158 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| ArcticController.cpp |
|
||||
| |
|
||||
| Driver for Arctic devices |
|
||||
| |
|
||||
| Armin Wolf (Wer-Wolf) 09 Jan 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include <cstring>
|
||||
#include "ArcticController.h"
|
||||
|
||||
using namespace std::chrono_literals;
|
||||
|
||||
#define ARCTIC_COMMAND_SET_RGB 0x00
|
||||
#define ARCTIC_COMMAND_IDENTIFY 0x5C
|
||||
|
||||
#define ARCTIC_RESPONSE_BUFFER_LENGTH 15
|
||||
#define ARCTIC_RESPONSE_COMMAND_OFFSET 0
|
||||
#define ARCTIC_RESPONSE_DATA_OFFSET 1
|
||||
#define ARCTIC_RESPONSE_DATA_LENGTH 12
|
||||
#define ARCTIC_RESPONSE_XOR_CSUM_OFFSET 13
|
||||
#define ARCTIC_RESPONSE_ADD_CSUM_OFFSET 14
|
||||
|
||||
#define ARCTIC_COMMAND_BUFFER_LENGTH(payload_size) (sizeof(header) + 1 + payload_size)
|
||||
#define ARCTIC_COMMAND_COMMAND_OFFSET (sizeof(header))
|
||||
#define ARCTIC_COMMAND_PAYLOAD_OFFSET (sizeof(header) + 1)
|
||||
|
||||
const unsigned char header[] =
|
||||
{
|
||||
0x01,
|
||||
0x02,
|
||||
0x03,
|
||||
0xFF,
|
||||
0x05,
|
||||
0xFF,
|
||||
0x02,
|
||||
0x03
|
||||
};
|
||||
|
||||
const unsigned char identify_payload[] =
|
||||
{
|
||||
0x01,
|
||||
0xFE,
|
||||
0x01,
|
||||
0xFE
|
||||
};
|
||||
|
||||
ArcticController::ArcticController(const std::string &portname)
|
||||
: serialport(portname.c_str(), 250000, SERIAL_PORT_PARITY_NONE, SERIAL_PORT_SIZE_8, SERIAL_PORT_STOP_BITS_2, false)
|
||||
{
|
||||
port_name = portname;
|
||||
serialport.serial_set_dtr(true);
|
||||
}
|
||||
|
||||
ArcticController::~ArcticController()
|
||||
{
|
||||
serialport.serial_set_dtr(false);
|
||||
}
|
||||
|
||||
static void FormatCommandBuffer(char *buffer, char command)
|
||||
{
|
||||
std::memcpy(buffer, header, sizeof(header));
|
||||
buffer[ARCTIC_COMMAND_COMMAND_OFFSET] = command;
|
||||
}
|
||||
|
||||
void ArcticController::SetChannels(std::vector<RGBColor> colors)
|
||||
{
|
||||
char* buffer = new char[ARCTIC_COMMAND_BUFFER_LENGTH(colors.size() * 3)];
|
||||
|
||||
FormatCommandBuffer(buffer, ARCTIC_COMMAND_SET_RGB);
|
||||
|
||||
for(unsigned int channel = 0; channel < colors.size(); channel++)
|
||||
{
|
||||
const unsigned int offset = ARCTIC_COMMAND_PAYLOAD_OFFSET + channel * 3;
|
||||
|
||||
buffer[offset + 0x00] = (char)std::min<unsigned int>(254, RGBGetRValue(colors[channel]));
|
||||
buffer[offset + 0x01] = (char)std::min<unsigned int>(254, RGBGetGValue(colors[channel]));
|
||||
buffer[offset + 0x02] = (char)std::min<unsigned int>(254, RGBGetBValue(colors[channel]));
|
||||
}
|
||||
|
||||
serialport.serial_write(buffer, sizeof(buffer));
|
||||
|
||||
delete[] buffer;
|
||||
}
|
||||
|
||||
static char XORChecksum(char *data, int length)
|
||||
{
|
||||
char sum = 0;
|
||||
|
||||
for(int i = 0; i < length; i++)
|
||||
{
|
||||
sum ^= data[i];
|
||||
}
|
||||
|
||||
return sum;
|
||||
}
|
||||
|
||||
static char AddChecksum(char *data, int length)
|
||||
{
|
||||
char sum = 0;
|
||||
|
||||
for(int i = 0; i < length; i++)
|
||||
{
|
||||
sum = (char)(sum + data[i]);
|
||||
}
|
||||
|
||||
return sum;
|
||||
}
|
||||
|
||||
bool ArcticController::IsPresent()
|
||||
{
|
||||
char buffer[ARCTIC_COMMAND_BUFFER_LENGTH(sizeof(identify_payload))];
|
||||
char response[ARCTIC_RESPONSE_BUFFER_LENGTH];
|
||||
int ret;
|
||||
|
||||
FormatCommandBuffer(buffer, ARCTIC_COMMAND_IDENTIFY);
|
||||
std::memcpy(buffer + ARCTIC_COMMAND_PAYLOAD_OFFSET, identify_payload, sizeof(identify_payload));
|
||||
|
||||
serialport.serial_flush_rx();
|
||||
ret = serialport.serial_write(buffer, sizeof(buffer));
|
||||
if(ret != sizeof(buffer))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
std::this_thread::sleep_for(100ms);
|
||||
|
||||
ret = serialport.serial_read(response, sizeof(response));
|
||||
if(ret != sizeof(response))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
if(response[ARCTIC_RESPONSE_COMMAND_OFFSET] != ARCTIC_COMMAND_IDENTIFY)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
if(response[ARCTIC_RESPONSE_XOR_CSUM_OFFSET] != XORChecksum(&response[ARCTIC_RESPONSE_DATA_OFFSET], ARCTIC_RESPONSE_DATA_LENGTH))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
if(response[ARCTIC_RESPONSE_ADD_CSUM_OFFSET] != AddChecksum(&response[ARCTIC_RESPONSE_DATA_OFFSET], ARCTIC_RESPONSE_DATA_LENGTH))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
std::string ArcticController::GetLocation()
|
||||
{
|
||||
return port_name;
|
||||
}
|
||||
@@ -0,0 +1,32 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| ArcticController.h |
|
||||
| |
|
||||
| Driver for Arctic devices |
|
||||
| |
|
||||
| Armin Wolf (Wer-Wolf) 09 Jan 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <algorithm>
|
||||
#include "RGBController.h"
|
||||
#include "serial_port.h"
|
||||
|
||||
class ArcticController
|
||||
{
|
||||
public:
|
||||
ArcticController(const std::string &portname);
|
||||
~ArcticController();
|
||||
|
||||
void SetChannels(std::vector<RGBColor> colors);
|
||||
bool IsPresent();
|
||||
|
||||
std::string GetLocation();
|
||||
|
||||
private:
|
||||
std::string port_name;
|
||||
serial_port serialport;
|
||||
};
|
||||
@@ -0,0 +1,48 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| ArcticControllerDetect.cpp |
|
||||
| |
|
||||
| Detector for Arctic devices |
|
||||
| |
|
||||
| Armin Wolf (Wer-Wolf) 09 Jan 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include <vector>
|
||||
#include "Detector.h"
|
||||
#include "ArcticController.h"
|
||||
#include "RGBController_Arctic.h"
|
||||
#include "find_usb_serial_port.h"
|
||||
|
||||
#define CH341_VID 0x1A86
|
||||
#define CH341_PID 0x7523
|
||||
|
||||
void DetectArcticControllers()
|
||||
{
|
||||
std::vector<std::string *> ports = find_usb_serial_port(CH341_VID, CH341_PID);
|
||||
|
||||
for(unsigned int device = 0; device < ports.size(); device++)
|
||||
{
|
||||
ArcticController *controller = new ArcticController(*ports[device]);
|
||||
|
||||
if(controller->IsPresent())
|
||||
{
|
||||
RGBController_Arctic *rgb_controller = new RGBController_Arctic(controller);
|
||||
ResourceManager::get()->RegisterRGBController(rgb_controller);
|
||||
}
|
||||
else
|
||||
{
|
||||
delete controller;
|
||||
}
|
||||
|
||||
delete ports[device];
|
||||
}
|
||||
}
|
||||
|
||||
REGISTER_DETECTOR("Arctic RGB controller", DetectArcticControllers);
|
||||
/*---------------------------------------------------------------------------------------------------------*\
|
||||
| Entries for dynamic UDEV rules |
|
||||
| |
|
||||
| DUMMY_DEVICE_DETECTOR("Arctic RGB controller", DetectArcticControllers, 0x1A86, 0x7523 ) |
|
||||
\*---------------------------------------------------------------------------------------------------------*/
|
||||
@@ -0,0 +1,134 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_Arctic.cpp |
|
||||
| |
|
||||
| RGBController for Arctic devices |
|
||||
| |
|
||||
| Armin Wolf (Wer-Wolf) 09 Jan 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include <math.h>
|
||||
#include "RGBController_Arctic.h"
|
||||
|
||||
using namespace std::chrono_literals;
|
||||
|
||||
#define ARCTIC_NUM_CHANNELS 4
|
||||
#define ARCTIC_SLEEP_THRESHOLD 100ms
|
||||
#define ARCTIC_KEEPALIVE_PERIOD 500ms /* Device requires at least 1s */
|
||||
|
||||
/**------------------------------------------------------------------*\
|
||||
@name Arctic RGB Controller Devices
|
||||
@category LEDStrip
|
||||
@type Serial
|
||||
@save :x:
|
||||
@direct :white_check_mark:
|
||||
@effects :x:
|
||||
@detectors DetectArcticControllers
|
||||
@comment
|
||||
\*-------------------------------------------------------------------*/
|
||||
|
||||
RGBController_Arctic::RGBController_Arctic(ArcticController* controller_ptr)
|
||||
{
|
||||
controller = controller_ptr;
|
||||
|
||||
name = "Arctic RGB Controller";
|
||||
vendor = "Arctic";
|
||||
description = "Arctic 4-Channel RGB Controller";
|
||||
location = controller->GetLocation();
|
||||
type = DEVICE_TYPE_LEDSTRIP;
|
||||
|
||||
mode DirectMode;
|
||||
DirectMode.name = "Direct";
|
||||
DirectMode.value = 0;
|
||||
DirectMode.flags = MODE_FLAG_HAS_PER_LED_COLOR;
|
||||
DirectMode.color_mode = MODE_COLORS_PER_LED;
|
||||
|
||||
modes.push_back(DirectMode);
|
||||
|
||||
SetupZones();
|
||||
|
||||
keepalive_thread_run = true;
|
||||
keepalive_thread = std::thread(&RGBController_Arctic::KeepaliveThreadFunction, this);
|
||||
}
|
||||
|
||||
RGBController_Arctic::~RGBController_Arctic()
|
||||
{
|
||||
keepalive_thread_run = false;
|
||||
keepalive_thread.join();
|
||||
delete controller;
|
||||
}
|
||||
|
||||
void RGBController_Arctic::SetupZones()
|
||||
{
|
||||
for(int channel = 0; channel < ARCTIC_NUM_CHANNELS; channel++)
|
||||
{
|
||||
zone LedZone;
|
||||
LedZone.name = "LED Strip " + std::to_string(channel);
|
||||
LedZone.type = ZONE_TYPE_SINGLE;
|
||||
LedZone.leds_count = 1;
|
||||
LedZone.leds_min = 1;
|
||||
LedZone.leds_max = 1;
|
||||
LedZone.matrix_map = nullptr;
|
||||
|
||||
led Led;
|
||||
Led.name = LedZone.name + " LED";
|
||||
Led.value = channel;
|
||||
|
||||
zones.push_back(LedZone);
|
||||
leds.push_back(Led);
|
||||
}
|
||||
|
||||
SetupColors();
|
||||
}
|
||||
|
||||
void RGBController_Arctic::ResizeZone(int /* zone */, int /* new_size */)
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| This device does not support resizing zones |
|
||||
\*---------------------------------------------------------*/
|
||||
}
|
||||
|
||||
void RGBController_Arctic::DeviceUpdateLEDs()
|
||||
{
|
||||
last_update_time = std::chrono::steady_clock::now();
|
||||
|
||||
controller->SetChannels(colors);
|
||||
}
|
||||
|
||||
void RGBController_Arctic::UpdateZoneLEDs(int /* zone */)
|
||||
{
|
||||
DeviceUpdateLEDs();
|
||||
}
|
||||
|
||||
void RGBController_Arctic::UpdateSingleLED(int /* led */)
|
||||
{
|
||||
DeviceUpdateLEDs();
|
||||
}
|
||||
|
||||
void RGBController_Arctic::DeviceUpdateMode()
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| This device does not support mode updates |
|
||||
\*---------------------------------------------------------*/
|
||||
}
|
||||
|
||||
void RGBController_Arctic::KeepaliveThreadFunction()
|
||||
{
|
||||
std::chrono::nanoseconds sleep_time;
|
||||
|
||||
while(keepalive_thread_run.load())
|
||||
{
|
||||
sleep_time = ARCTIC_KEEPALIVE_PERIOD - (std::chrono::steady_clock::now() - last_update_time);
|
||||
if(sleep_time <= ARCTIC_SLEEP_THRESHOLD)
|
||||
{
|
||||
UpdateLEDs(); // Already protected thru a device update thread
|
||||
std::this_thread::sleep_for(ARCTIC_KEEPALIVE_PERIOD);
|
||||
}
|
||||
else
|
||||
{
|
||||
std::this_thread::sleep_for(sleep_time);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,44 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_Arctic.h |
|
||||
| |
|
||||
| RGBController for Arctic devices |
|
||||
| |
|
||||
| Armin Wolf (Wer-Wolf) 09 Jan 2023 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <chrono>
|
||||
#include <thread>
|
||||
#include "ArcticController.h"
|
||||
#include "RGBController.h"
|
||||
#include "serial_port.h"
|
||||
|
||||
class RGBController_Arctic : public RGBController
|
||||
{
|
||||
public:
|
||||
RGBController_Arctic(ArcticController* controller_ptr);
|
||||
~RGBController_Arctic();
|
||||
|
||||
void SetupZones();
|
||||
|
||||
void ResizeZone(int zone, int new_size);
|
||||
|
||||
void DeviceUpdateLEDs();
|
||||
void UpdateZoneLEDs(int zone);
|
||||
void UpdateSingleLED(int led);
|
||||
|
||||
void DeviceUpdateMode();
|
||||
|
||||
void KeepaliveThreadFunction();
|
||||
|
||||
private:
|
||||
ArcticController* controller;
|
||||
std::chrono::time_point<std::chrono::steady_clock> last_update_time;
|
||||
std::atomic<bool> keepalive_thread_run;
|
||||
std::thread keepalive_thread;
|
||||
};
|
||||
|
||||
@@ -0,0 +1,140 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AresonController.cpp |
|
||||
| |
|
||||
| Driver for Areson mice |
|
||||
| |
|
||||
| Morgan Guimard (morg) 29 Jan 2022 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include <string.h>
|
||||
#include "StringUtils.h"
|
||||
#include "AresonController.h"
|
||||
|
||||
AresonController::AresonController(hid_device* dev_handle, const hid_device_info& info, std::string dev_name)
|
||||
{
|
||||
dev = dev_handle;
|
||||
location = info.path;
|
||||
name = dev_name;
|
||||
}
|
||||
|
||||
AresonController::~AresonController()
|
||||
{
|
||||
hid_close(dev);
|
||||
}
|
||||
|
||||
std::string AresonController::GetDeviceLocation()
|
||||
{
|
||||
return("HID: " + location);
|
||||
}
|
||||
|
||||
std::string AresonController::GetNameString()
|
||||
{
|
||||
return(name);
|
||||
}
|
||||
|
||||
std::string AresonController::GetSerialString()
|
||||
{
|
||||
wchar_t serial_string[128];
|
||||
int ret = hid_get_serial_number_string(dev, serial_string, 128);
|
||||
|
||||
if(ret != 0)
|
||||
{
|
||||
return("");
|
||||
}
|
||||
|
||||
return(StringUtils::wstring_to_string(serial_string));
|
||||
}
|
||||
|
||||
unsigned char AresonController::GetSpeedValue(unsigned char speed, unsigned char mode_value)
|
||||
{
|
||||
unsigned char speed_values_lookup_high[ARESON_SPEED_MAX] =
|
||||
{
|
||||
0xFF, 0xE6, 0xD2, 0xBe, 0xAA, 0x96, 0x82, 0x6E, 0x46, 0x28
|
||||
};
|
||||
|
||||
unsigned char speed_values_lookup_low[ARESON_SPEED_MAX] =
|
||||
{
|
||||
0x2D, 0x28, 0x23, 0x1E, 0x19, 0x13, 0x0F, 0x0A, 0x05, 0x03
|
||||
};
|
||||
|
||||
switch (mode_value)
|
||||
{
|
||||
case BREATHING_MODE_VALUE:
|
||||
case SPECRTUM_CYCLE_MODE_VALUE:
|
||||
case SINGLE_COLOR_WAVE_MODE_VALUE:
|
||||
case BREATHING_COLORFUL_MODE_VALUE:
|
||||
return speed_values_lookup_high[speed -1];
|
||||
|
||||
case RAINBOW_WAVE_MODE_VALUE:
|
||||
return speed_values_lookup_low[speed -1];
|
||||
|
||||
default:
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
void AresonController::SetMode(RGBColor color, unsigned char brightness, unsigned char speed, unsigned char mode_value)
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| Init the packet buffer |
|
||||
\*---------------------------------------------------------*/
|
||||
unsigned char usb_buf[ARESON_PACKET_SIZE];
|
||||
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*---------------------------------------------------------*\œ
|
||||
| Constant data |
|
||||
\*---------------------------------------------------------*/
|
||||
usb_buf[0x00] = ARESON_REPORT_ID;
|
||||
usb_buf[0x01] = 0x07;
|
||||
usb_buf[0x04] = 0xA0;
|
||||
usb_buf[0x05] = 0x07;
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Set the mode |
|
||||
\*---------------------------------------------------------*/
|
||||
usb_buf[0x06] = mode_value;
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Set the color |
|
||||
\*---------------------------------------------------------*/
|
||||
usb_buf[0x07] = RGBGetRValue(color);
|
||||
usb_buf[0x08] = RGBGetGValue(color);
|
||||
usb_buf[0x09] = RGBGetBValue(color);
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Set speed if needed |
|
||||
\*---------------------------------------------------------*/
|
||||
usb_buf[0x0A] = GetSpeedValue(speed, mode_value);
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Set brightness if needed |
|
||||
\*---------------------------------------------------------*/
|
||||
if(mode_value != OFF_MODE_VALUE)
|
||||
{
|
||||
unsigned char brightness_values[ARESON_BRIGHTNESS_MAX] =
|
||||
{
|
||||
0x19, 0x32, 0x4B, 0x64, 0x7D, 0x96, 0xAF, 0xC8, 0xE1, 0xFF
|
||||
};
|
||||
|
||||
usb_buf[0x0B] = brightness_values[brightness - 1];
|
||||
}
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Custom CRC - thanks to Vaker for this <3 |
|
||||
\*---------------------------------------------------------*/
|
||||
usb_buf[0x0C] = 0x55 - usb_buf[0x06] - usb_buf[0x07] - usb_buf[0x08] - usb_buf[0x09] - usb_buf[0x0A] - usb_buf[0x0B];
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Constant data |
|
||||
\*---------------------------------------------------------*/
|
||||
usb_buf[0x10] = ARESON_PACKET_END;
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Send the report |
|
||||
\*---------------------------------------------------------*/
|
||||
hid_send_feature_report(dev, usb_buf, ARESON_PACKET_SIZE);
|
||||
}
|
||||
@@ -0,0 +1,61 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AresonController.h |
|
||||
| |
|
||||
| Driver for Areson mice |
|
||||
| |
|
||||
| Morgan Guimard (morg) 29 Jan 2022 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <string>
|
||||
#include <hidapi.h>
|
||||
#include "RGBController.h"
|
||||
|
||||
#define ARESON_PACKET_SIZE 17
|
||||
#define ARESON_REPORT_ID 0x08
|
||||
#define ARESON_PACKET_END 0x4A
|
||||
|
||||
enum
|
||||
{
|
||||
RAINBOW_WAVE_MODE_VALUE = 0x00,
|
||||
BREATHING_MODE_VALUE = 0x01,
|
||||
STATIC_MODE_VALUE = 0x02,
|
||||
SPECRTUM_CYCLE_MODE_VALUE = 0x03,
|
||||
OFF_MODE_VALUE = 0x04,
|
||||
SINGLE_COLOR_WAVE_MODE_VALUE = 0x05,
|
||||
BREATHING_COLORFUL_MODE_VALUE = 0x07,
|
||||
};
|
||||
|
||||
|
||||
enum
|
||||
{
|
||||
ARESON_BRIGHTNESS_MIN = 1,
|
||||
ARESON_BRIGHTNESS_MAX = 10,
|
||||
ARESON_SPEED_MIN = 1,
|
||||
ARESON_SPEED_MAX = 10
|
||||
};
|
||||
|
||||
class AresonController
|
||||
{
|
||||
public:
|
||||
AresonController(hid_device* dev_handle, const hid_device_info& info, std::string dev_name);
|
||||
~AresonController();
|
||||
|
||||
std::string GetDeviceLocation();
|
||||
std::string GetNameString();
|
||||
std::string GetSerialString();
|
||||
|
||||
void SetMode(RGBColor color, unsigned char brightness, unsigned char speed, unsigned char mode_value);
|
||||
|
||||
protected:
|
||||
hid_device* dev;
|
||||
|
||||
private:
|
||||
std::string location;
|
||||
std::string name;
|
||||
unsigned char GetSpeedValue(unsigned char speed, unsigned char mode_value);
|
||||
};
|
||||
@@ -0,0 +1,49 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AresonControllerDetect.cpp |
|
||||
| |
|
||||
| Detector for Areson mice |
|
||||
| |
|
||||
| Morgan Guimard (morg) 29 Jan 2022 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "Detector.h"
|
||||
#include "AresonController.h"
|
||||
#include "RGBController_Areson.h"
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Areson vendor ID |
|
||||
\*---------------------------------------------------------*/
|
||||
#define ARESON_VID 0x25A7
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Product ID |
|
||||
\*---------------------------------------------------------*/
|
||||
#define ZET_GAMING_EDGE_AIR_PRO_WIRELESS_PID 0xFA3F
|
||||
#define ZET_GAMING_EDGE_AIR_PRO_PID 0xFA40
|
||||
#define ZET_GAMING_EDGE_AIR_ELIT_WIRELESS_PID 0xFA48
|
||||
#define ZET_GAMING_EDGE_AIR_ELIT_PID 0xFA49
|
||||
#define REDRAGON_M914_PID 0xFA7B
|
||||
#define REDRAGON_M914_WIRELESS_PID 0xFA7C
|
||||
|
||||
void DetectAresonControllers(hid_device_info* info, const std::string& name)
|
||||
{
|
||||
hid_device* dev = hid_open_path(info->path);
|
||||
|
||||
if(dev)
|
||||
{
|
||||
AresonController* controller = new AresonController(dev, *info, name);
|
||||
RGBController_Areson* rgb_controller = new RGBController_Areson(controller);
|
||||
|
||||
ResourceManager::get()->RegisterRGBController(rgb_controller);
|
||||
}
|
||||
}
|
||||
|
||||
REGISTER_HID_DETECTOR_IPU("ZET GAMING Edge Air Pro (Wireless)", DetectAresonControllers, ARESON_VID, ZET_GAMING_EDGE_AIR_PRO_WIRELESS_PID, 1, 0xFF02, 2);
|
||||
REGISTER_HID_DETECTOR_IPU("ZET GAMING Edge Air Pro", DetectAresonControllers, ARESON_VID, ZET_GAMING_EDGE_AIR_PRO_PID, 1, 0xFF02, 2);
|
||||
REGISTER_HID_DETECTOR_IPU("ZET GAMING Edge Air Elit (Wireless)", DetectAresonControllers, ARESON_VID, ZET_GAMING_EDGE_AIR_ELIT_WIRELESS_PID, 1, 0xFF02, 2);
|
||||
REGISTER_HID_DETECTOR_IPU("ZET GAMING Edge Air Elit", DetectAresonControllers, ARESON_VID, ZET_GAMING_EDGE_AIR_ELIT_PID, 1, 0xFF02, 2);
|
||||
REGISTER_HID_DETECTOR_IPU("Redragon M914 NIX (Wireless)", DetectAresonControllers, ARESON_VID, REDRAGON_M914_WIRELESS_PID, 1, 0xFF02, 2);
|
||||
REGISTER_HID_DETECTOR_IPU("Redragon M914 NIX", DetectAresonControllers, ARESON_VID, REDRAGON_M914_PID, 1, 0xFF02, 2);
|
||||
@@ -0,0 +1,189 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_Areson.cpp |
|
||||
| |
|
||||
| RGBController for Areson mice |
|
||||
| |
|
||||
| Morgan Guimard (morg) 29 Jan 2022 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include <chrono>
|
||||
#include <thread>
|
||||
#include "RGBController_Areson.h"
|
||||
|
||||
/**------------------------------------------------------------------*\
|
||||
@name Areson
|
||||
@category Mouse
|
||||
@type USB
|
||||
@save :x:
|
||||
@direct :x:
|
||||
@effects :white_check_mark:
|
||||
@detectors DetectAresonControllers
|
||||
@comment
|
||||
\*-------------------------------------------------------------------*/
|
||||
|
||||
RGBController_Areson::RGBController_Areson(AresonController* controller_ptr)
|
||||
{
|
||||
controller = controller_ptr;
|
||||
|
||||
name = controller->GetNameString();
|
||||
vendor = "Areson";
|
||||
type = DEVICE_TYPE_MOUSE;
|
||||
description = "Areson mouse";
|
||||
location = controller->GetDeviceLocation();
|
||||
serial = controller->GetSerialString();
|
||||
|
||||
mode Static;
|
||||
Static.name = "Static";
|
||||
Static.value = STATIC_MODE_VALUE;
|
||||
Static.flags = MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Static.color_mode = MODE_COLORS_PER_LED;
|
||||
Static.brightness_min = ARESON_BRIGHTNESS_MIN;
|
||||
Static.brightness_max = ARESON_BRIGHTNESS_MAX;
|
||||
Static.brightness = ARESON_BRIGHTNESS_MAX;
|
||||
modes.push_back(Static);
|
||||
|
||||
mode RainbowWave;
|
||||
RainbowWave.name = "Rainbow Wave";
|
||||
RainbowWave.value = RAINBOW_WAVE_MODE_VALUE;
|
||||
RainbowWave.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
RainbowWave.color_mode = MODE_COLORS_NONE;
|
||||
RainbowWave.brightness_min = ARESON_BRIGHTNESS_MIN;
|
||||
RainbowWave.brightness_max = ARESON_BRIGHTNESS_MAX;
|
||||
RainbowWave.brightness = ARESON_BRIGHTNESS_MAX;
|
||||
RainbowWave.speed_min = ARESON_SPEED_MIN;
|
||||
RainbowWave.speed_max = ARESON_SPEED_MAX;
|
||||
RainbowWave.speed = ARESON_SPEED_MAX;
|
||||
modes.push_back(RainbowWave);
|
||||
|
||||
mode Breathing;
|
||||
Breathing.name = "Breathing";
|
||||
Breathing.value = BREATHING_MODE_VALUE;
|
||||
Breathing.flags = MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
Breathing.color_mode = MODE_COLORS_PER_LED;
|
||||
Breathing.brightness_min = ARESON_BRIGHTNESS_MIN;
|
||||
Breathing.brightness_max = ARESON_BRIGHTNESS_MAX;
|
||||
Breathing.brightness = ARESON_BRIGHTNESS_MAX;
|
||||
Breathing.speed_min = ARESON_SPEED_MIN;
|
||||
Breathing.speed_max = ARESON_SPEED_MAX;
|
||||
Breathing.speed = ARESON_SPEED_MIN;
|
||||
Breathing.colors.resize(1);
|
||||
modes.push_back(Breathing);
|
||||
|
||||
mode SpectrumCycle;
|
||||
SpectrumCycle.name = "Spectrum Cycle";
|
||||
SpectrumCycle.value = SPECRTUM_CYCLE_MODE_VALUE;
|
||||
SpectrumCycle.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
SpectrumCycle.color_mode = MODE_COLORS_NONE;
|
||||
SpectrumCycle.brightness_min = ARESON_BRIGHTNESS_MIN;
|
||||
SpectrumCycle.brightness_max = ARESON_BRIGHTNESS_MAX;
|
||||
SpectrumCycle.brightness = ARESON_BRIGHTNESS_MAX;
|
||||
SpectrumCycle.speed_min = ARESON_SPEED_MIN;
|
||||
SpectrumCycle.speed_max = ARESON_SPEED_MAX;
|
||||
SpectrumCycle.speed = ARESON_SPEED_MAX;
|
||||
modes.push_back(SpectrumCycle);
|
||||
|
||||
mode SingleColorWave;
|
||||
SingleColorWave.name = "Single Color Wave";
|
||||
SingleColorWave.value = SINGLE_COLOR_WAVE_MODE_VALUE;
|
||||
SingleColorWave.flags = MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
SingleColorWave.color_mode = MODE_COLORS_PER_LED;
|
||||
SingleColorWave.brightness_min = ARESON_BRIGHTNESS_MIN;
|
||||
SingleColorWave.brightness_max = ARESON_BRIGHTNESS_MAX;
|
||||
SingleColorWave.brightness = ARESON_BRIGHTNESS_MAX;
|
||||
SingleColorWave.speed_min = ARESON_SPEED_MIN;
|
||||
SingleColorWave.speed_max = ARESON_SPEED_MAX;
|
||||
SingleColorWave.speed = ARESON_SPEED_MAX;
|
||||
SingleColorWave.colors.resize(1);
|
||||
modes.push_back(SingleColorWave);
|
||||
|
||||
mode ColorfulBreathing;
|
||||
ColorfulBreathing.name = "Colorful Breathing";
|
||||
ColorfulBreathing.value = BREATHING_COLORFUL_MODE_VALUE;
|
||||
ColorfulBreathing.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_AUTOMATIC_SAVE;
|
||||
ColorfulBreathing.color_mode = MODE_COLORS_NONE;
|
||||
ColorfulBreathing.brightness_min = ARESON_BRIGHTNESS_MIN;
|
||||
ColorfulBreathing.brightness_max = ARESON_BRIGHTNESS_MAX;
|
||||
ColorfulBreathing.brightness = ARESON_BRIGHTNESS_MAX;
|
||||
ColorfulBreathing.speed_min = ARESON_SPEED_MIN;
|
||||
ColorfulBreathing.speed_max = ARESON_SPEED_MAX;
|
||||
ColorfulBreathing.speed = ARESON_SPEED_MAX;
|
||||
ColorfulBreathing.colors.resize(1);
|
||||
modes.push_back(ColorfulBreathing);
|
||||
|
||||
mode OFF;
|
||||
OFF.name = "Off";
|
||||
OFF.value = OFF_MODE_VALUE;
|
||||
OFF.flags = MODE_FLAG_AUTOMATIC_SAVE;
|
||||
OFF.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(OFF);
|
||||
|
||||
SetupZones();
|
||||
}
|
||||
|
||||
RGBController_Areson::~RGBController_Areson()
|
||||
{
|
||||
delete controller;
|
||||
}
|
||||
|
||||
void RGBController_Areson::SetupZones()
|
||||
{
|
||||
zone new_zone;
|
||||
|
||||
new_zone.name = "Mouse";
|
||||
new_zone.type = ZONE_TYPE_LINEAR;
|
||||
new_zone.leds_min = 1;
|
||||
new_zone.leds_max = 1;
|
||||
new_zone.leds_count = 1;
|
||||
new_zone.matrix_map = nullptr;
|
||||
|
||||
zones.emplace_back(new_zone);
|
||||
|
||||
leds.resize(1);
|
||||
|
||||
led new_led;
|
||||
new_led.name = "LED 1";
|
||||
leds[0] = new_led;
|
||||
|
||||
SetupColors();
|
||||
}
|
||||
|
||||
void RGBController_Areson::ResizeZone(int /*zone*/, int /*new_size*/)
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| This device does not support resizing zones |
|
||||
\*---------------------------------------------------------*/
|
||||
}
|
||||
|
||||
void RGBController_Areson::DeviceUpdateLEDs()
|
||||
{
|
||||
DeviceUpdateMode();
|
||||
}
|
||||
|
||||
void RGBController_Areson::UpdateZoneLEDs(int /*zone*/)
|
||||
{
|
||||
DeviceUpdateMode();
|
||||
}
|
||||
|
||||
void RGBController_Areson::UpdateSingleLED(int /*led*/)
|
||||
{
|
||||
DeviceUpdateMode();
|
||||
}
|
||||
|
||||
void RGBController_Areson::DeviceUpdateMode()
|
||||
{
|
||||
RGBColor color;
|
||||
|
||||
if(modes[active_mode].flags & MODE_FLAG_HAS_PER_LED_COLOR)
|
||||
{
|
||||
color = colors[0];
|
||||
}
|
||||
else
|
||||
{
|
||||
color = ToRGBColor(0,0,0);
|
||||
}
|
||||
|
||||
controller->SetMode(color, modes[active_mode].brightness, modes[active_mode].speed, modes[active_mode].value);
|
||||
}
|
||||
@@ -0,0 +1,34 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_Areson.h |
|
||||
| |
|
||||
| RGBController for Areson mice |
|
||||
| |
|
||||
| Morgan Guimard (morg) 29 Jan 2022 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "RGBController.h"
|
||||
#include "AresonController.h"
|
||||
|
||||
class RGBController_Areson : public RGBController
|
||||
{
|
||||
public:
|
||||
RGBController_Areson(AresonController* controller_ptr);
|
||||
~RGBController_Areson();
|
||||
|
||||
void SetupZones();
|
||||
void ResizeZone(int zone, int new_size);
|
||||
|
||||
void DeviceUpdateLEDs();
|
||||
void UpdateZoneLEDs(int zone);
|
||||
void UpdateSingleLED(int led);
|
||||
|
||||
void DeviceUpdateMode();
|
||||
|
||||
private:
|
||||
AresonController* controller;
|
||||
};
|
||||
@@ -0,0 +1,410 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AsusAuraCoreController.cpp |
|
||||
| |
|
||||
| Driver for ASUS ROG Aura Core |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 13 Apr 2020 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include <cstring>
|
||||
#include "AsusAuraCoreController.h"
|
||||
#include "StringUtils.h"
|
||||
|
||||
#define AURA_CORE_MAX_MESSAGE_SIZE 64
|
||||
|
||||
AuraCoreController::AuraCoreController(hid_device* dev_handle, const char* path)
|
||||
{
|
||||
dev = dev_handle;
|
||||
location = path;
|
||||
|
||||
aura_device.aura_type = AURA_CORE_DEVICE_UNKNOWN;
|
||||
aura_device.buff_size = 0;
|
||||
aura_device.report_id = 0x5D;
|
||||
aura_device.num_leds = 4;
|
||||
aura_device.supports_direct = false;
|
||||
|
||||
IdentifyDevice();
|
||||
Handshake();
|
||||
}
|
||||
|
||||
AuraCoreController::~AuraCoreController()
|
||||
{
|
||||
hid_close(dev);
|
||||
}
|
||||
|
||||
std::string AuraCoreController::GetDeviceLocation()
|
||||
{
|
||||
return("HID: " + location);
|
||||
}
|
||||
|
||||
std::string AuraCoreController::GetSerialString()
|
||||
{
|
||||
wchar_t serial_string[128];
|
||||
int ret = hid_get_serial_number_string(dev, serial_string, 128);
|
||||
|
||||
if(ret != 0)
|
||||
{
|
||||
return("");
|
||||
}
|
||||
|
||||
return(StringUtils::wstring_to_string(serial_string));
|
||||
}
|
||||
|
||||
void AuraCoreController::SendBrightness
|
||||
(
|
||||
unsigned char brightness
|
||||
)
|
||||
{
|
||||
unsigned char usb_buf[AURA_CORE_MAX_MESSAGE_SIZE];
|
||||
|
||||
if(aura_device.aura_type != AURA_CORE_DEVICE_UNKNOWN)
|
||||
{
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up message packet |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x00] = 0x5A;
|
||||
usb_buf[0x01] = AURA_CORE_COMMAND_BRIGHTNESS;
|
||||
usb_buf[0x02] = 0xC5;
|
||||
usb_buf[0x03] = 0xC4;
|
||||
usb_buf[0x04] = brightness;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_send_feature_report(dev, usb_buf, aura_device.buff_size);
|
||||
}
|
||||
}
|
||||
|
||||
void AuraCoreController::SendUpdate
|
||||
(
|
||||
unsigned char zone,
|
||||
unsigned char mode,
|
||||
unsigned char speed,
|
||||
unsigned char dir,
|
||||
unsigned char red,
|
||||
unsigned char green,
|
||||
unsigned char blue
|
||||
)
|
||||
{
|
||||
unsigned char usb_buf[AURA_CORE_MAX_MESSAGE_SIZE];
|
||||
|
||||
if(aura_device.aura_type != AURA_CORE_DEVICE_UNKNOWN)
|
||||
{
|
||||
if(aura_device.aura_type == AURA_CORE_DEVICE_KEYBOARD)
|
||||
{
|
||||
zone += 1;
|
||||
}
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up message packet |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x00] = aura_device.report_id;
|
||||
usb_buf[0x01] = AURA_CORE_COMMAND_UPDATE;
|
||||
usb_buf[0x02] = zone;
|
||||
usb_buf[0x03] = mode;
|
||||
usb_buf[0x04] = red;
|
||||
usb_buf[0x05] = green;
|
||||
usb_buf[0x06] = blue;
|
||||
usb_buf[0x07] = speed;
|
||||
usb_buf[0x08] = dir;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_send_feature_report(dev, usb_buf, aura_device.buff_size);
|
||||
}
|
||||
}
|
||||
|
||||
void AuraCoreController::SendSet()
|
||||
{
|
||||
unsigned char usb_buf[AURA_CORE_MAX_MESSAGE_SIZE];
|
||||
|
||||
if(aura_device.aura_type != AURA_CORE_DEVICE_UNKNOWN)
|
||||
{
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up message packet |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x00] = aura_device.report_id;
|
||||
usb_buf[0x01] = AURA_CORE_COMMAND_SET;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_send_feature_report(dev, usb_buf, aura_device.buff_size);
|
||||
}
|
||||
}
|
||||
|
||||
void AuraCoreController::SendApply()
|
||||
{
|
||||
unsigned char usb_buf[AURA_CORE_MAX_MESSAGE_SIZE];
|
||||
|
||||
if(aura_device.aura_type != AURA_CORE_DEVICE_UNKNOWN)
|
||||
{
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up message packet |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x00] = aura_device.report_id;
|
||||
usb_buf[0x01] = AURA_CORE_COMMAND_APPLY;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_send_feature_report(dev, usb_buf, aura_device.buff_size);
|
||||
}
|
||||
}
|
||||
|
||||
void AuraCoreController::InitDirectMode()
|
||||
{
|
||||
unsigned char usb_buf[AURA_CORE_MAX_MESSAGE_SIZE];
|
||||
unsigned char msg_num = 0;
|
||||
int led_count = aura_device.num_leds;
|
||||
|
||||
if(aura_device.supports_direct)
|
||||
{
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up message packet |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x00] = aura_device.report_id;
|
||||
usb_buf[0x01] = AURA_CORE_COMMAND_DIRECT;
|
||||
usb_buf[0x02] = 0xD0;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_send_feature_report(dev, usb_buf, aura_device.buff_size);
|
||||
|
||||
while(led_count > 0)
|
||||
{
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up second message packet |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x03] = 0x01;
|
||||
usb_buf[0x04] = 0x02;
|
||||
usb_buf[0x05] = 0x00;
|
||||
usb_buf[0x06] = msg_num++;
|
||||
usb_buf[0x07] = (led_count > aura_device.max_leds_per_message) ? aura_device.max_leds_per_message : led_count;
|
||||
usb_buf[0x08] = 0x00;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet 2 |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_send_feature_report(dev, usb_buf, aura_device.buff_size);
|
||||
|
||||
led_count -= aura_device.max_leds_per_message;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void AuraCoreController::UpdateDirect(std::vector<AuraColor>& color_set)
|
||||
{
|
||||
unsigned char usb_buf[AURA_CORE_MAX_MESSAGE_SIZE];
|
||||
unsigned char msg_num = 0;
|
||||
unsigned char color_index = 0;
|
||||
unsigned char set_count = 0;
|
||||
int led_count = aura_device.num_leds;
|
||||
|
||||
if(aura_device.supports_direct)
|
||||
{
|
||||
while(led_count > 0)
|
||||
{
|
||||
unsigned char msg_index = 0x09;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up message packet |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x00] = aura_device.report_id;
|
||||
usb_buf[0x01] = AURA_CORE_COMMAND_DIRECT;
|
||||
usb_buf[0x02] = 0xD0;
|
||||
usb_buf[0x03] = 0x01;
|
||||
usb_buf[0x04] = 0x02;
|
||||
usb_buf[0x05] = 0x00;
|
||||
usb_buf[0x06] = msg_num++;
|
||||
usb_buf[0x07] = (led_count > aura_device.max_leds_per_message) ? aura_device.max_leds_per_message : led_count;
|
||||
usb_buf[0x08] = 0x00;
|
||||
|
||||
set_count = 0;
|
||||
|
||||
while( (msg_index < sizeof(usb_buf) ) &&
|
||||
(led_count > 0 ) &&
|
||||
(set_count < aura_device.max_leds_per_message) )
|
||||
{
|
||||
if(color_index < color_set.size())
|
||||
{
|
||||
usb_buf[msg_index++] = color_set[color_index].red;
|
||||
usb_buf[msg_index++] = color_set[color_index].green;
|
||||
usb_buf[msg_index++] = color_set[color_index].blue;
|
||||
}
|
||||
else
|
||||
{
|
||||
usb_buf[msg_index++] = 0;
|
||||
usb_buf[msg_index++] = 0;
|
||||
usb_buf[msg_index++] = 0;
|
||||
}
|
||||
|
||||
led_count--;
|
||||
color_index++;
|
||||
set_count++;
|
||||
}
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_send_feature_report(dev, usb_buf, aura_device.buff_size);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void AuraCoreController::IdentifyDevice()
|
||||
{
|
||||
unsigned char usb_buf[AURA_CORE_MAX_MESSAGE_SIZE];
|
||||
int num_bytes = 0;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| First, attempt to read the report from the Keyboard |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x00] = aura_device.report_id;
|
||||
|
||||
num_bytes = hid_get_feature_report(dev, usb_buf, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Currently, there is no need to attempt to read the |
|
||||
| returned data. If the device responded,to the report,|
|
||||
| we're good. |
|
||||
\*-----------------------------------------------------*/
|
||||
if(num_bytes > 0)
|
||||
{
|
||||
aura_device.aura_type = AURA_CORE_DEVICE_KEYBOARD;
|
||||
aura_device.buff_size = 17;
|
||||
aura_device.report_id = 0x5D;
|
||||
aura_device.num_leds = 4;
|
||||
aura_device.supports_direct = false;
|
||||
}
|
||||
else if(num_bytes == -1)
|
||||
{
|
||||
/*-------------------------------------------------*\
|
||||
| First, attempt to read the report from the |
|
||||
| Keyboard |
|
||||
\*-------------------------------------------------*/
|
||||
usb_buf[0] = 0x5E;
|
||||
num_bytes = hid_get_feature_report(dev, usb_buf, sizeof(usb_buf));
|
||||
|
||||
if(num_bytes > 0)
|
||||
{
|
||||
/*---------------------------------------------*\
|
||||
| Currently, there is no need to attempt to |
|
||||
| read the returned data. If the device |
|
||||
| responded,to the report, we're good. |
|
||||
\*---------------------------------------------*/
|
||||
aura_device.aura_type = AURA_CORE_DEVICE_GA15DH;
|
||||
aura_device.buff_size = 64;
|
||||
aura_device.report_id = 0x5E;
|
||||
aura_device.num_leds = 20;
|
||||
aura_device.max_leds_per_message = 16;
|
||||
aura_device.supports_direct = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void AuraCoreController::Handshake()
|
||||
{
|
||||
unsigned char usb_buf[AURA_CORE_MAX_MESSAGE_SIZE];
|
||||
|
||||
|
||||
if(aura_device.aura_type == AURA_CORE_DEVICE_GA15DH)
|
||||
{
|
||||
usb_buf[0] = 0x5E;
|
||||
SendIdString();
|
||||
hid_get_feature_report(dev, usb_buf, sizeof(usb_buf));
|
||||
SendQuery();
|
||||
hid_get_feature_report(dev, usb_buf, sizeof(usb_buf));
|
||||
}
|
||||
}
|
||||
|
||||
void AuraCoreController::SendIdString()
|
||||
{
|
||||
unsigned char usb_buf[AURA_CORE_MAX_MESSAGE_SIZE];
|
||||
const char id[] = "ASUS Tech.Inc.";
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up message packet |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x00] = aura_device.report_id;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Copy in string data |
|
||||
\*-----------------------------------------------------*/
|
||||
memcpy(&usb_buf[0x01], id, sizeof(id));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_send_feature_report(dev, usb_buf, aura_device.buff_size);
|
||||
}
|
||||
|
||||
void AuraCoreController::SendQuery()
|
||||
{
|
||||
unsigned char usb_buf[AURA_CORE_MAX_MESSAGE_SIZE];
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Zero out buffer |
|
||||
\*-----------------------------------------------------*/
|
||||
memset(usb_buf, 0x00, sizeof(usb_buf));
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Set up message packet |
|
||||
\*-----------------------------------------------------*/
|
||||
usb_buf[0x00] = aura_device.report_id;
|
||||
usb_buf[0x01] = 0x05;
|
||||
usb_buf[0x02] = 0x20;
|
||||
usb_buf[0x03] = 0x31;
|
||||
usb_buf[0x04] = 0x00;
|
||||
usb_buf[0x05] = 0x10;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Send packet |
|
||||
\*-----------------------------------------------------*/
|
||||
hid_send_feature_report(dev, usb_buf, aura_device.buff_size);
|
||||
}
|
||||
@@ -0,0 +1,123 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AsusAuraCoreController.h |
|
||||
| |
|
||||
| Driver for ASUS ROG Aura Core |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 13 Apr 2020 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <string>
|
||||
#include <hidapi.h>
|
||||
#include "RGBController.h"
|
||||
|
||||
enum AuraCoreDeviceType
|
||||
{
|
||||
AURA_CORE_DEVICE_UNKNOWN = 0,
|
||||
AURA_CORE_DEVICE_KEYBOARD = 1,
|
||||
AURA_CORE_DEVICE_GA15DH = 2
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
AURA_CORE_MODE_STATIC = 0, /* Static color mode */
|
||||
AURA_CORE_MODE_BREATHING = 1, /* Breathing effect mode */
|
||||
AURA_CORE_MODE_SPECTRUM_CYCLE = 2, /* Spectrum Cycle mode */
|
||||
AURA_CORE_MODE_RAINBOW = 3, /* Rainbow mode */
|
||||
AURA_CORE_MODE_STROBE = 10, /* Strobe mode */
|
||||
AURA_CORE_MODE_COMET = 11, /* Comet mode */
|
||||
AURA_CORE_MODE_FLASHNDASH = 12, /* Flash & Dash mode */
|
||||
AURA_CORE_MODE_IRRADIATION = 17, /* Irradiation mode */
|
||||
AURA_CORE_MODE_DIRECT = 255 /* Not a real mode - but need a way to differentiate */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
AURA_CORE_COMMAND_UPDATE = 0xB3, /* Update mode and color */
|
||||
AURA_CORE_COMMAND_SET = 0xB5, /* Set command */
|
||||
AURA_CORE_COMMAND_APPLY = 0xB4, /* Apply command */
|
||||
AURA_CORE_COMMAND_BRIGHTNESS = 0xBA, /* Brightness command */
|
||||
AURA_CORE_COMMAND_DIRECT = 0xBC /* Set LEDs directly */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
AURA_CORE_ZONE_IDX_ALL = 0x00, /* Update all zones */
|
||||
AURA_CORE_ZONE_IDX_1 = 0x01, /* Update zone 1 */
|
||||
AURA_CORE_ZONE_IDX_2 = 0x02, /* Update zone 2 */
|
||||
AURA_CORE_ZONE_IDX_3 = 0x03, /* Update zone 3 */
|
||||
AURA_CORE_ZONE_IDX_4 = 0x04, /* Update zone 4 */
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
AURA_CORE_SPEED_SLOW = 0xE1, /* Slowest speed */
|
||||
AURA_CORE_SPEED_NORMAL = 0xEB, /* Normal speed */
|
||||
AURA_CORE_SPEED_FAST = 0xF5, /* Fastest speed */
|
||||
};
|
||||
|
||||
struct AuraDeviceDescriptor
|
||||
{
|
||||
AuraCoreDeviceType aura_type;
|
||||
unsigned char buff_size;
|
||||
unsigned char report_id;
|
||||
unsigned char num_leds;
|
||||
unsigned char max_leds_per_message;
|
||||
bool supports_direct;
|
||||
};
|
||||
|
||||
struct AuraColor
|
||||
{
|
||||
unsigned char red;
|
||||
unsigned char green;
|
||||
unsigned char blue;
|
||||
};
|
||||
|
||||
class AuraCoreController
|
||||
{
|
||||
public:
|
||||
AuraDeviceDescriptor aura_device;
|
||||
|
||||
AuraCoreController(hid_device* dev_handle, const char* path);
|
||||
~AuraCoreController();
|
||||
|
||||
std::string GetDeviceLocation();
|
||||
std::string GetSerialString();
|
||||
|
||||
void SendBrightness
|
||||
(
|
||||
unsigned char brightness
|
||||
);
|
||||
|
||||
void SendUpdate
|
||||
(
|
||||
unsigned char zone,
|
||||
unsigned char mode,
|
||||
unsigned char speed,
|
||||
unsigned char dir,
|
||||
unsigned char red,
|
||||
unsigned char green,
|
||||
unsigned char blue
|
||||
);
|
||||
|
||||
void SendSet();
|
||||
|
||||
void SendApply();
|
||||
|
||||
void InitDirectMode();
|
||||
|
||||
void UpdateDirect(std::vector<AuraColor>& color_set);
|
||||
|
||||
private:
|
||||
hid_device* dev;
|
||||
std::string location;
|
||||
|
||||
void IdentifyDevice();
|
||||
void Handshake();
|
||||
void SendIdString();
|
||||
void SendQuery();
|
||||
};
|
||||
+328
@@ -0,0 +1,328 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_AsusAuraCore.cpp |
|
||||
| |
|
||||
| RGBController for ASUS ROG Aura Core |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 13 Apr 2020 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "RGBController_AsusAuraCore.h"
|
||||
|
||||
/**------------------------------------------------------------------*\
|
||||
@name Asus AURA Core
|
||||
@category Keyboard,LEDStrip
|
||||
@type USB
|
||||
@save :x:
|
||||
@direct :rotating_light:
|
||||
@effects :white_check_mark:
|
||||
@detectors DetectAsusAuraCoreControllers
|
||||
@comment
|
||||
\*-------------------------------------------------------------------*/
|
||||
|
||||
RGBController_AuraCore::RGBController_AuraCore(AuraCoreController* controller_ptr)
|
||||
{
|
||||
controller = controller_ptr;
|
||||
|
||||
name = "ASUS Aura Core Device";
|
||||
vendor = "ASUS";
|
||||
location = controller->GetDeviceLocation();
|
||||
serial = controller->GetSerialString();
|
||||
description = "ASUS Aura Core Device";
|
||||
type = DEVICE_TYPE_UNKNOWN;
|
||||
|
||||
if(controller->aura_device.aura_type == AURA_CORE_DEVICE_KEYBOARD)
|
||||
{
|
||||
SetupKeyboard();
|
||||
}
|
||||
else if(controller->aura_device.aura_type == AURA_CORE_DEVICE_GA15DH)
|
||||
{
|
||||
SetupGA15DH();
|
||||
}
|
||||
|
||||
SetupZones();
|
||||
}
|
||||
|
||||
void RGBController_AuraCore::SetupKeyboard()
|
||||
{
|
||||
name = "ASUS Aura Keyboard";
|
||||
vendor = "ASUS";
|
||||
type = DEVICE_TYPE_KEYBOARD;
|
||||
description = "ASUS Aura Core Device";
|
||||
|
||||
mode Static;
|
||||
Static.name = "Static";
|
||||
Static.value = AURA_CORE_MODE_STATIC;
|
||||
Static.flags = MODE_FLAG_HAS_PER_LED_COLOR;
|
||||
Static.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Static);
|
||||
|
||||
mode Breathing;
|
||||
Breathing.name = "Breathing";
|
||||
Breathing.value = AURA_CORE_MODE_BREATHING;
|
||||
Breathing.flags = MODE_FLAG_HAS_PER_LED_COLOR;
|
||||
Breathing.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Breathing);
|
||||
|
||||
mode ColorCycle;
|
||||
ColorCycle.name = "Color Cycle";
|
||||
ColorCycle.value = AURA_CORE_MODE_SPECTRUM_CYCLE;
|
||||
ColorCycle.flags = 0;
|
||||
ColorCycle.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(ColorCycle);
|
||||
}
|
||||
|
||||
void RGBController_AuraCore::SetupGA15DH()
|
||||
{
|
||||
name = "ASUS Aura GA15DH";
|
||||
vendor = "ASUS";
|
||||
type = DEVICE_TYPE_LEDSTRIP;
|
||||
description = "ASUS Aura Core Device";
|
||||
|
||||
mode Static;
|
||||
Static.name = "Static";
|
||||
Static.value = AURA_CORE_MODE_STATIC;
|
||||
Static.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR;
|
||||
Static.colors_min = 1;
|
||||
Static.colors_max = 1;
|
||||
Static.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Static.colors.resize(1);
|
||||
modes.push_back(Static);
|
||||
|
||||
mode Breathing;
|
||||
Breathing.name = "Breathing";
|
||||
Breathing.value = AURA_CORE_MODE_BREATHING;
|
||||
Breathing.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_SPEED;
|
||||
Breathing.speed_min = AURA_CORE_SPEED_SLOW;
|
||||
Breathing.speed_max = AURA_CORE_SPEED_FAST;
|
||||
Breathing.speed = AURA_CORE_SPEED_NORMAL;
|
||||
Breathing.colors_min = 1;
|
||||
Breathing.colors_max = 2;
|
||||
Breathing.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Breathing.colors.resize(2);
|
||||
modes.push_back(Breathing);
|
||||
|
||||
mode ColorCycle;
|
||||
ColorCycle.name = "Color Cycle";
|
||||
ColorCycle.value = AURA_CORE_MODE_SPECTRUM_CYCLE;
|
||||
ColorCycle.flags = MODE_FLAG_HAS_SPEED;
|
||||
ColorCycle.speed_min = AURA_CORE_SPEED_SLOW;
|
||||
ColorCycle.speed_max = AURA_CORE_SPEED_FAST;
|
||||
ColorCycle.speed = AURA_CORE_SPEED_NORMAL;
|
||||
ColorCycle.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(ColorCycle);
|
||||
|
||||
mode Rainbow;
|
||||
Rainbow.name = "Rainbow";
|
||||
Rainbow.value = AURA_CORE_MODE_RAINBOW;
|
||||
Rainbow.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_DIRECTION_LR;
|
||||
Rainbow.speed_min = AURA_CORE_SPEED_SLOW;
|
||||
Rainbow.speed_max = AURA_CORE_SPEED_FAST;
|
||||
Rainbow.speed = AURA_CORE_SPEED_NORMAL;
|
||||
Rainbow.direction = MODE_DIRECTION_RIGHT;
|
||||
Rainbow.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Rainbow);
|
||||
|
||||
mode Strobe;
|
||||
Strobe.name = "Strobe";
|
||||
Strobe.value = AURA_CORE_MODE_STROBE;
|
||||
Strobe.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR;
|
||||
Strobe.colors_min = 1;
|
||||
Strobe.colors_max = 1;
|
||||
Strobe.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Strobe.colors.resize(1);
|
||||
modes.push_back(Strobe);
|
||||
|
||||
mode Comet;
|
||||
Comet.name = "Comet";
|
||||
Comet.value = AURA_CORE_MODE_COMET;
|
||||
Comet.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR;
|
||||
Comet.colors_min = 1;
|
||||
Comet.colors_max = 1;
|
||||
Comet.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Comet.colors.resize(1);
|
||||
modes.push_back(Comet);
|
||||
|
||||
mode Flash;
|
||||
Flash.name = "Flash & Dash";
|
||||
Flash.value = AURA_CORE_MODE_FLASHNDASH;
|
||||
Flash.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR;
|
||||
Flash.colors_min = 1;
|
||||
Flash.colors_max = 1;
|
||||
Flash.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Flash.colors.resize(1);
|
||||
modes.push_back(Flash);
|
||||
|
||||
mode Irradiation;
|
||||
Irradiation.name = "Irradiation";
|
||||
Irradiation.value = AURA_CORE_MODE_IRRADIATION;
|
||||
Irradiation.flags = 0;
|
||||
Irradiation.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Irradiation);
|
||||
|
||||
mode Direct;
|
||||
Static.name = "Direct";
|
||||
Static.value = AURA_CORE_MODE_DIRECT;
|
||||
Static.flags = MODE_FLAG_HAS_PER_LED_COLOR;
|
||||
Static.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Static);
|
||||
}
|
||||
|
||||
RGBController_AuraCore::~RGBController_AuraCore()
|
||||
{
|
||||
delete controller;
|
||||
}
|
||||
|
||||
void RGBController_AuraCore::SetupZones()
|
||||
{
|
||||
zone auraZone;
|
||||
|
||||
if(controller->aura_device.aura_type == AURA_CORE_DEVICE_KEYBOARD)
|
||||
{
|
||||
auraZone.name = "Keyboard";
|
||||
auraZone.type = ZONE_TYPE_SINGLE;
|
||||
auraZone.leds_min = 4;
|
||||
auraZone.leds_max = 4;
|
||||
auraZone.leds_count = 4;
|
||||
auraZone.matrix_map = NULL;
|
||||
}
|
||||
else if(controller->aura_device.aura_type == AURA_CORE_DEVICE_GA15DH)
|
||||
{
|
||||
auraZone.name = "GA15DH";
|
||||
auraZone.type = ZONE_TYPE_LINEAR;
|
||||
auraZone.leds_min = 20;
|
||||
auraZone.leds_max = 20;
|
||||
auraZone.leds_count = 20;
|
||||
auraZone.matrix_map = NULL;
|
||||
}
|
||||
else
|
||||
{
|
||||
auraZone.leds_count = 0;
|
||||
}
|
||||
|
||||
zones.push_back(auraZone);
|
||||
|
||||
for(unsigned int led_idx = 0; led_idx < auraZone.leds_count; led_idx++)
|
||||
{
|
||||
led KeyLED;
|
||||
KeyLED.name = auraZone.name + " ";
|
||||
KeyLED.name.append(std::to_string(led_idx + 1));
|
||||
leds.push_back(KeyLED);
|
||||
}
|
||||
|
||||
SetupColors();
|
||||
}
|
||||
|
||||
void RGBController_AuraCore::ResizeZone(int /*zone*/, int /*new_size*/)
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| This device does not support resizing zones |
|
||||
\*---------------------------------------------------------*/
|
||||
}
|
||||
|
||||
void RGBController_AuraCore::DeviceUpdateLEDs()
|
||||
{
|
||||
UpdateZoneLEDs(0);
|
||||
}
|
||||
|
||||
void RGBController_AuraCore::UpdateZoneLEDs(int /*zone*/)
|
||||
{
|
||||
if(modes[active_mode].value == AURA_CORE_MODE_DIRECT)
|
||||
{
|
||||
std::vector<AuraColor> aura_colors;
|
||||
std::vector<RGBColor>& color_set = colors;
|
||||
|
||||
if(modes[active_mode].color_mode == MODE_COLORS_MODE_SPECIFIC)
|
||||
{
|
||||
color_set = modes[active_mode].colors;
|
||||
}
|
||||
|
||||
for(unsigned int led_idx = 0; led_idx < leds.size(); led_idx++)
|
||||
{
|
||||
AuraColor new_color;
|
||||
|
||||
new_color.red = RGBGetRValue(color_set[led_idx]);
|
||||
new_color.green = RGBGetGValue(color_set[led_idx]);
|
||||
new_color.blue = RGBGetBValue(color_set[led_idx]);
|
||||
|
||||
aura_colors.push_back(new_color);
|
||||
}
|
||||
|
||||
controller->UpdateDirect(aura_colors);
|
||||
}
|
||||
else if(modes[active_mode].color_mode == MODE_COLORS_PER_LED)
|
||||
{
|
||||
for(unsigned int led_idx = 0; led_idx < leds.size(); led_idx++)
|
||||
{
|
||||
UpdateSingleLED(led_idx);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
UpdateSingleLED(0);
|
||||
}
|
||||
}
|
||||
|
||||
void RGBController_AuraCore::UpdateSingleLED(int led)
|
||||
{
|
||||
unsigned char speed = 0xFF;
|
||||
unsigned char red = 0;
|
||||
unsigned char green = 0;
|
||||
unsigned char blue = 0;
|
||||
unsigned char dir = 0;
|
||||
mode& curr_mode = modes[active_mode];
|
||||
|
||||
if(curr_mode.color_mode == MODE_COLORS_PER_LED)
|
||||
{
|
||||
red = RGBGetRValue(colors[led]);
|
||||
green = RGBGetGValue(colors[led]);
|
||||
blue = RGBGetBValue(colors[led]);
|
||||
}
|
||||
else if(curr_mode.color_mode == MODE_COLORS_MODE_SPECIFIC)
|
||||
{
|
||||
red = RGBGetRValue(curr_mode.colors[led]);
|
||||
green = RGBGetGValue(curr_mode.colors[led]);
|
||||
blue = RGBGetBValue(curr_mode.colors[led]);
|
||||
}
|
||||
|
||||
if(curr_mode.flags & MODE_FLAG_HAS_SPEED)
|
||||
{
|
||||
speed = curr_mode.speed;
|
||||
}
|
||||
|
||||
if(curr_mode.flags & MODE_FLAG_HAS_DIRECTION_LR)
|
||||
{
|
||||
if(curr_mode.direction == MODE_DIRECTION_RIGHT)
|
||||
{
|
||||
dir = 1;
|
||||
}
|
||||
}
|
||||
|
||||
controller->SendUpdate
|
||||
(
|
||||
led,
|
||||
curr_mode.value,
|
||||
speed,
|
||||
dir,
|
||||
red,
|
||||
green,
|
||||
blue
|
||||
);
|
||||
|
||||
controller->SendSet();
|
||||
controller->SendApply();
|
||||
}
|
||||
|
||||
void RGBController_AuraCore::DeviceUpdateMode()
|
||||
{
|
||||
if(modes[active_mode].value == AURA_CORE_MODE_DIRECT)
|
||||
{
|
||||
controller->InitDirectMode();
|
||||
}
|
||||
else
|
||||
{
|
||||
DeviceUpdateLEDs();
|
||||
}
|
||||
}
|
||||
+37
@@ -0,0 +1,37 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_AsusAuraCore.h |
|
||||
| |
|
||||
| RGBController for ASUS ROG Aura Core |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 13 Apr 2020 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "RGBController.h"
|
||||
#include "AsusAuraCoreController.h"
|
||||
|
||||
class RGBController_AuraCore : public RGBController
|
||||
{
|
||||
public:
|
||||
RGBController_AuraCore(AuraCoreController* controller_ptr);
|
||||
~RGBController_AuraCore();
|
||||
|
||||
void SetupKeyboard();
|
||||
void SetupGA15DH();
|
||||
void SetupZones();
|
||||
|
||||
void ResizeZone(int zone, int new_size);
|
||||
|
||||
void DeviceUpdateLEDs();
|
||||
void UpdateZoneLEDs(int zone);
|
||||
void UpdateSingleLED(int led);
|
||||
|
||||
void DeviceUpdateMode();
|
||||
|
||||
private:
|
||||
AuraCoreController* controller;
|
||||
};
|
||||
@@ -0,0 +1,68 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AsusAuraCoreControllerDetect.cpp |
|
||||
| |
|
||||
| Detector for ASUS ROG Aura Core |
|
||||
| |
|
||||
| Adam Honse (CalcProgrammer1) 13 Apr 2020 |
|
||||
| Chris M (Dr_No) 28 Jul 2022 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "Detector.h"
|
||||
#include "AsusAuraCoreController.h"
|
||||
#include "RGBController.h"
|
||||
#include "RGBController_AsusAuraCore.h"
|
||||
#include "RGBController_AsusAuraCoreLaptop.h"
|
||||
#include <hidapi.h>
|
||||
|
||||
#define AURA_CORE_VID 0x0B05
|
||||
|
||||
/******************************************************************************************\
|
||||
* *
|
||||
* DetectAuraCoreControllers *
|
||||
* *
|
||||
* Tests the USB address to see if an Asus ROG Aura Core controller exists there *
|
||||
* *
|
||||
\******************************************************************************************/
|
||||
|
||||
void DetectAsusAuraCoreControllers(hid_device_info* info, const std::string& /*name*/)
|
||||
{
|
||||
hid_device* dev = hid_open_path(info->path);
|
||||
|
||||
if(dev)
|
||||
{
|
||||
AuraCoreController* controller = new AuraCoreController(dev, info->path);
|
||||
RGBController_AuraCore* rgb_controller = new RGBController_AuraCore(controller);
|
||||
|
||||
if(rgb_controller->type != DEVICE_TYPE_UNKNOWN)
|
||||
{
|
||||
ResourceManager::get()->RegisterRGBController(rgb_controller);
|
||||
}
|
||||
else
|
||||
{
|
||||
delete rgb_controller;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void DetectAsusAuraCoreLaptopControllers(hid_device_info* info, const std::string& /*name*/)
|
||||
{
|
||||
hid_device* dev = hid_open_path(info->path);
|
||||
|
||||
if(dev)
|
||||
{
|
||||
AsusAuraCoreLaptopController* controller = new AsusAuraCoreLaptopController(dev, info->path);
|
||||
RGBController_AsusAuraCoreLaptop* rgb_controller = new RGBController_AsusAuraCoreLaptop(controller);
|
||||
|
||||
ResourceManager::get()->RegisterRGBController(rgb_controller);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
REGISTER_HID_DETECTOR ("ASUS Aura Core", DetectAsusAuraCoreControllers, AURA_CORE_VID, 0x1854);
|
||||
REGISTER_HID_DETECTOR ("ASUS Aura Core", DetectAsusAuraCoreControllers, AURA_CORE_VID, 0x1866);
|
||||
REGISTER_HID_DETECTOR ("ASUS Aura Core", DetectAsusAuraCoreControllers, AURA_CORE_VID, 0x1869);
|
||||
REGISTER_HID_DETECTOR_PU("ASUS ROG Strix SCAR 15", DetectAsusAuraCoreLaptopControllers, AURA_CORE_VID, AURA_STRIX_SCAR_15_PID, 0xFF31, 0x79);
|
||||
REGISTER_HID_DETECTOR_PU("ASUS ROG Strix SCAR 17", DetectAsusAuraCoreLaptopControllers, AURA_CORE_VID, 0x1866, 0xFF31, 0x79);
|
||||
+446
@@ -0,0 +1,446 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AsusAuraCoreLaptopController.cpp |
|
||||
| |
|
||||
| Driver for ASUS ROG Aura Core Laptop |
|
||||
| |
|
||||
| Chris M (Dr_No) 28 Jul 2022 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "AsusAuraCoreLaptopController.h"
|
||||
#include "dmiinfo.h"
|
||||
#include "SettingsManager.h"
|
||||
#include "StringUtils.h"
|
||||
|
||||
static std::string power_zones[ASUSAURACORELAPTOP_POWER_ZONES] =
|
||||
{
|
||||
"Logo",
|
||||
ZONE_EN_KEYBOARD,
|
||||
"Lightbar",
|
||||
"Lid Edges"
|
||||
};
|
||||
|
||||
static std::string power_states[ASUSAURACORELAPTOP_POWER_STATES] =
|
||||
{
|
||||
" when booting",
|
||||
" when awake",
|
||||
" when sleeping",
|
||||
" when off",
|
||||
};
|
||||
|
||||
AsusAuraCoreLaptopController::AsusAuraCoreLaptopController(hid_device* dev_handle, const char* path)
|
||||
{
|
||||
dev = dev_handle;
|
||||
location = path;
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| The motherboard name will uniquely ID the laptop to |
|
||||
| determine the metadata of the device. |
|
||||
\*---------------------------------------------------------*/
|
||||
DMIInfo dmi_info;
|
||||
std::string dmi_name = dmi_info.getMainboard();
|
||||
bool not_found = true;
|
||||
|
||||
for(uint16_t i = 0; i < AURA_CORE_LAPTOP_DEVICE_COUNT; i++)
|
||||
{
|
||||
if(aura_core_laptop_device_list[i]->dmi_name == dmi_name)
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| Set device ID |
|
||||
\*---------------------------------------------------------*/
|
||||
not_found = false;
|
||||
device_index = i;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if(not_found)
|
||||
{
|
||||
LOG_ERROR("[%s] device capabilities not found. Please creata a new device request.",
|
||||
dmi_name.c_str());
|
||||
return;
|
||||
}
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Only set power config for known devices |
|
||||
\*---------------------------------------------------------*/
|
||||
SetPowerConfigFromJSON();
|
||||
SendInitDirectMode();
|
||||
}
|
||||
|
||||
AsusAuraCoreLaptopController::~AsusAuraCoreLaptopController()
|
||||
{
|
||||
hid_close(dev);
|
||||
}
|
||||
|
||||
const aura_core_laptop_device* AsusAuraCoreLaptopController::GetDeviceData()
|
||||
{
|
||||
return aura_core_laptop_device_list[device_index];
|
||||
}
|
||||
|
||||
std::string AsusAuraCoreLaptopController::GetDeviceDescription()
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| Get device name from HID manufacturer and product strings |
|
||||
\*---------------------------------------------------------*/
|
||||
wchar_t name_string[HID_MAX_STR];
|
||||
|
||||
hid_get_manufacturer_string(dev, name_string, HID_MAX_STR);
|
||||
std::string name = StringUtils::wstring_to_string(name_string);
|
||||
|
||||
hid_get_product_string(dev, name_string, HID_MAX_STR);
|
||||
name.append(" ").append(StringUtils::wstring_to_string(name_string));
|
||||
return name;
|
||||
}
|
||||
|
||||
unsigned int AsusAuraCoreLaptopController::GetKeyboardLayout()
|
||||
{
|
||||
const uint8_t index = 6;
|
||||
uint8_t result = 0;
|
||||
uint8_t rd_buf[ASUSAURACORELAPTOP_WRITE_PACKET_SIZE] = { ASUSAURACORELAPTOP_REPORT_ID };
|
||||
uint8_t buffer[ASUSAURACORELAPTOP_WRITE_PACKET_SIZE] = { ASUSAURACORELAPTOP_REPORT_ID,
|
||||
ASUSAURACORELAPTOP_CMD_LAYOUT,
|
||||
0x20,
|
||||
0x31,
|
||||
0x00,
|
||||
0x10 };
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Clear the read buffer to ensure we read the right packet |
|
||||
\*---------------------------------------------------------*/
|
||||
do
|
||||
{
|
||||
result = hid_read_timeout(dev, rd_buf, ASUSAURACORELAPTOP_WRITE_PACKET_SIZE, 10);
|
||||
}
|
||||
while(result > 0);
|
||||
|
||||
memset(&rd_buf[1], 0, ASUSAURACORELAPTOP_WRITE_PACKET_SIZE - 1);
|
||||
memset(&buffer[index], 0, ASUSAURACORELAPTOP_WRITE_PACKET_SIZE - index);
|
||||
|
||||
hid_send_feature_report(dev, buffer, ASUSAURACORELAPTOP_WRITE_PACKET_SIZE);
|
||||
result = hid_get_feature_report(dev, rd_buf, ASUSAURACORELAPTOP_WRITE_PACKET_SIZE);
|
||||
|
||||
LOG_DEBUG("[%s] GetKeyboardLayout %02X %02X %02X %02X %02X %02X %02X {%02X} %02X %02X %02X %02X",
|
||||
aura_core_laptop_device_list[device_index]->dmi_name.c_str(),
|
||||
rd_buf[5], rd_buf[6], rd_buf[7], rd_buf[8], rd_buf[9], rd_buf[10],
|
||||
rd_buf[11], rd_buf[12], rd_buf[13], rd_buf[14], rd_buf[15], rd_buf[16]);
|
||||
|
||||
if(result > 0)
|
||||
{
|
||||
return rd_buf[12];
|
||||
}
|
||||
|
||||
LOG_DEBUG("[%s] GetKeyboardLayout: An error occurred! Setting layout to ANSI",
|
||||
aura_core_laptop_device_list[device_index]->dmi_name.c_str());
|
||||
return ASUSAURACORELAPTOP_LAYOUT_ANSI;
|
||||
}
|
||||
|
||||
std::string AsusAuraCoreLaptopController::GetSerial()
|
||||
{
|
||||
wchar_t serial_string[128];
|
||||
int ret = hid_get_serial_number_string(dev, serial_string, 128);
|
||||
|
||||
if(ret != 0)
|
||||
{
|
||||
LOG_DEBUG("[%s] Get HID Serial string failed",
|
||||
aura_core_laptop_device_list[device_index]->dmi_name.c_str());
|
||||
return("");
|
||||
}
|
||||
|
||||
return(StringUtils::wstring_to_string(serial_string));
|
||||
}
|
||||
|
||||
std::string AsusAuraCoreLaptopController::GetLocation()
|
||||
{
|
||||
return("HID: " + location);
|
||||
}
|
||||
|
||||
void AsusAuraCoreLaptopController::SetMode(uint8_t mode, uint8_t speed, uint8_t brightness, RGBColor color1, RGBColor color2, uint8_t random, uint8_t direction)
|
||||
{
|
||||
bool needs_update = !( (current_mode == mode ) &&
|
||||
(current_speed == speed ) &&
|
||||
(current_brightness == brightness ) &&
|
||||
(current_c1 == color1 ) &&
|
||||
(current_c2 == color2 ) &&
|
||||
(current_random == random ) &&
|
||||
(current_direction == direction ) );
|
||||
|
||||
if(needs_update)
|
||||
{
|
||||
current_mode = mode;
|
||||
current_speed = speed;
|
||||
current_brightness = brightness;
|
||||
current_c1 = color1;
|
||||
current_c2 = color2;
|
||||
current_random = random;
|
||||
current_direction = direction;
|
||||
|
||||
if(current_mode == ASUSAURACORELAPTOP_MODE_DIRECT)
|
||||
{
|
||||
SendBrightness();
|
||||
SendInitDirectMode();
|
||||
return;
|
||||
}
|
||||
|
||||
SendUpdate();
|
||||
SendBrightness();
|
||||
}
|
||||
}
|
||||
|
||||
void AsusAuraCoreLaptopController::SendInitDirectMode()
|
||||
{
|
||||
uint8_t buffer[ASUSAURACORELAPTOP_WRITE_PACKET_SIZE] = { ASUSAURACORELAPTOP_REPORT_ID, ASUSAURACORELAPTOP_CMD_DIRECT };
|
||||
memset(&buffer[2], 0, ASUSAURACORELAPTOP_WRITE_PACKET_SIZE - 2);
|
||||
|
||||
LOG_DEBUG("[%s] Resetting device for direct control", aura_core_laptop_device_list[device_index]->dmi_name.c_str());
|
||||
hid_send_feature_report(dev, buffer, ASUSAURACORELAPTOP_WRITE_PACKET_SIZE);
|
||||
}
|
||||
|
||||
void AsusAuraCoreLaptopController::SetLedsDirect(std::vector<RGBColor *> colors)
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| The keyboard zone is a set of 168 keys (indexed from 0) |
|
||||
| sent in 11 packets of 16 triplets. The Lid and Lightbar |
|
||||
| zones are sent in one final packet afterwards. |
|
||||
\*---------------------------------------------------------*/
|
||||
const uint8_t key_set = 167;
|
||||
const uint8_t led_count = (uint8_t)colors.size();
|
||||
const uint16_t map_size = 3 * led_count;
|
||||
const uint8_t leds_per_packet = 16;
|
||||
uint8_t buffer[ASUSAURACORELAPTOP_WRITE_PACKET_SIZE] = { ASUSAURACORELAPTOP_REPORT_ID, ASUSAURACORELAPTOP_CMD_DIRECT,
|
||||
0x00, 0x01, 0x01, 0x01, 0x00, leds_per_packet, 0x00 };
|
||||
uint8_t* key_buf = new uint8_t[map_size];
|
||||
|
||||
memset(key_buf, 0, map_size);
|
||||
|
||||
for(uint8_t led_index = 0; led_index < led_count; led_index++)
|
||||
{
|
||||
std::size_t buf_idx = (led_index * 3);
|
||||
|
||||
key_buf[buf_idx] = RGBGetRValue(*colors[led_index]);
|
||||
key_buf[buf_idx + 1] = RGBGetGValue(*colors[led_index]);
|
||||
key_buf[buf_idx + 2] = RGBGetBValue(*colors[led_index]);
|
||||
}
|
||||
|
||||
for(uint8_t i = 0; i < key_set; i += leds_per_packet)
|
||||
{
|
||||
uint8_t leds_remaining = key_set - i;
|
||||
|
||||
if(leds_remaining < leds_per_packet)
|
||||
{
|
||||
buffer[07] = leds_remaining;
|
||||
|
||||
memset(&buffer[ASUSAURACORELAPTOP_DATA_BYTE],
|
||||
0,
|
||||
ASUSAURACORELAPTOP_WRITE_PACKET_SIZE - ASUSAURACORELAPTOP_DATA_BYTE);
|
||||
}
|
||||
|
||||
buffer[06] = i;
|
||||
memcpy(&buffer[ASUSAURACORELAPTOP_DATA_BYTE], &key_buf[3 * i], (3 * buffer[07]));
|
||||
|
||||
LOG_DEBUG("[%s] Sending buffer @ index %d thru index %d",
|
||||
aura_core_laptop_device_list[device_index]->dmi_name.c_str(),
|
||||
i,
|
||||
i + buffer[07]);
|
||||
|
||||
hid_send_feature_report(dev, buffer, ASUSAURACORELAPTOP_WRITE_PACKET_SIZE);
|
||||
}
|
||||
|
||||
buffer[4] = 0x04;
|
||||
buffer[5] = 0x00;
|
||||
buffer[6] = 0x00;
|
||||
buffer[7] = 0x00;
|
||||
|
||||
memset(&buffer[ASUSAURACORELAPTOP_DATA_BYTE],
|
||||
0,
|
||||
ASUSAURACORELAPTOP_WRITE_PACKET_SIZE - ASUSAURACORELAPTOP_DATA_BYTE);
|
||||
|
||||
if(led_count > key_set)
|
||||
{
|
||||
memcpy(&buffer[ASUSAURACORELAPTOP_DATA_BYTE],
|
||||
&key_buf[3 * key_set],
|
||||
(3 * (led_count - key_set)));
|
||||
}
|
||||
|
||||
LOG_DEBUG("[%s] Sending buffer @ index %d thru index %d",
|
||||
aura_core_laptop_device_list[device_index]->dmi_name.c_str(),
|
||||
key_set,
|
||||
led_count);
|
||||
|
||||
hid_send_feature_report(dev, buffer, ASUSAURACORELAPTOP_WRITE_PACKET_SIZE);
|
||||
delete[] key_buf;
|
||||
}
|
||||
|
||||
void AsusAuraCoreLaptopController::SendBrightness()
|
||||
{
|
||||
const uint8_t index = 5;
|
||||
uint8_t buffer[ASUSAURACORELAPTOP_WRITE_PACKET_SIZE] = { ASUSAURACORELAPTOP_REPORT_ID, ASUSAURACORELAPTOP_CMD_BRIGHTNESS, 0xC5, 0xC4};
|
||||
|
||||
memset(&buffer[index], 0, ASUSAURACORELAPTOP_WRITE_PACKET_SIZE - index);
|
||||
buffer[4] = current_brightness;
|
||||
|
||||
hid_send_feature_report(dev, buffer, ASUSAURACORELAPTOP_WRITE_PACKET_SIZE);
|
||||
}
|
||||
|
||||
void AsusAuraCoreLaptopController::SendUpdate()
|
||||
{
|
||||
uint8_t buffer[ASUSAURACORELAPTOP_WRITE_PACKET_SIZE] = { ASUSAURACORELAPTOP_REPORT_ID, ASUSAURACORELAPTOP_CMD_UPDATE };
|
||||
|
||||
buffer[ASUSAURACORELAPTOP_ZONE_BYTE] = 0;
|
||||
buffer[ASUSAURACORELAPTOP_MODE_BYTE] = current_mode;
|
||||
buffer[ASUSAURACORELAPTOP_R1_BYTE] = RGBGetRValue(current_c1);
|
||||
buffer[ASUSAURACORELAPTOP_G1_BYTE] = RGBGetGValue(current_c1);
|
||||
buffer[ASUSAURACORELAPTOP_B1_BYTE] = RGBGetBValue(current_c1);
|
||||
buffer[ASUSAURACORELAPTOP_SPEED_BYTE] = current_speed;
|
||||
buffer[ASUSAURACORELAPTOP_DIRECTION_BYTE] = current_direction;
|
||||
buffer[ASUSAURACORELAPTOP_DATA_BYTE] = current_random;
|
||||
buffer[ASUSAURACORELAPTOP_R2_BYTE] = RGBGetRValue(current_c2);
|
||||
buffer[ASUSAURACORELAPTOP_G2_BYTE] = RGBGetGValue(current_c2);
|
||||
buffer[ASUSAURACORELAPTOP_B2_BYTE] = RGBGetBValue(current_c2);
|
||||
|
||||
hid_send_feature_report(dev, buffer, ASUSAURACORELAPTOP_WRITE_PACKET_SIZE);
|
||||
|
||||
SendApply();
|
||||
}
|
||||
|
||||
void AsusAuraCoreLaptopController::SendApply()
|
||||
{
|
||||
const uint8_t index = 2;
|
||||
uint8_t buffer[ASUSAURACORELAPTOP_WRITE_PACKET_SIZE] = { ASUSAURACORELAPTOP_REPORT_ID, ASUSAURACORELAPTOP_CMD_APPLY };
|
||||
|
||||
memset(&buffer[index], 0, ASUSAURACORELAPTOP_WRITE_PACKET_SIZE - index);
|
||||
|
||||
hid_send_feature_report(dev, buffer, ASUSAURACORELAPTOP_WRITE_PACKET_SIZE);
|
||||
}
|
||||
|
||||
void AsusAuraCoreLaptopController::SendSet()
|
||||
{
|
||||
const uint8_t index = 2;
|
||||
uint8_t buffer[ASUSAURACORELAPTOP_WRITE_PACKET_SIZE] = { ASUSAURACORELAPTOP_REPORT_ID, ASUSAURACORELAPTOP_CMD_SET };
|
||||
|
||||
memset(&buffer[index], 0, ASUSAURACORELAPTOP_WRITE_PACKET_SIZE - index);
|
||||
|
||||
hid_send_feature_report(dev, buffer, ASUSAURACORELAPTOP_WRITE_PACKET_SIZE);
|
||||
}
|
||||
|
||||
std::vector<p_state> AsusAuraCoreLaptopController::PowerConfigArray()
|
||||
{
|
||||
std::vector<p_state> temp;
|
||||
|
||||
for(uint8_t zone_index = 0; zone_index < ASUSAURACORELAPTOP_POWER_ZONES; zone_index++)
|
||||
{
|
||||
for(uint8_t state_index = 0; state_index < ASUSAURACORELAPTOP_POWER_STATES; state_index++)
|
||||
{
|
||||
p_state new_state;
|
||||
|
||||
new_state.zone = power_zones[zone_index] + power_states[state_index];
|
||||
new_state.state = true;
|
||||
|
||||
temp.push_back(new_state);
|
||||
}
|
||||
}
|
||||
|
||||
return temp;
|
||||
}
|
||||
|
||||
void AsusAuraCoreLaptopController::SetPowerConfigFromJSON()
|
||||
{
|
||||
std::vector<p_state> power_config = PowerConfigArray();
|
||||
const std::string section_power = "PowerConfig";
|
||||
const std::string detector_name = "Asus Aura Core Laptop";
|
||||
SettingsManager* settings_manager = ResourceManager::get()->GetSettingsManager();
|
||||
json device_settings = settings_manager->GetSettings(detector_name);
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Get Power state config from the settings manager |
|
||||
| If PowerConfig is not found then write it to settings |
|
||||
\*---------------------------------------------------------*/
|
||||
if(!device_settings.contains(section_power))
|
||||
{
|
||||
json pcfg;
|
||||
|
||||
for(size_t i = 0; i < power_config.size(); i++)
|
||||
{
|
||||
pcfg[power_config[i].zone] = power_config[i].state;
|
||||
}
|
||||
|
||||
device_settings[section_power] = pcfg;
|
||||
settings_manager->SetSettings(detector_name, device_settings);
|
||||
settings_manager->SaveSettings();
|
||||
LOG_DEBUG("[%s] default power config saved to openrgb.json",
|
||||
aura_core_laptop_device_list[device_index]->dmi_name.c_str());
|
||||
}
|
||||
else
|
||||
{
|
||||
for(size_t i = 0; i < power_config.size(); i++)
|
||||
{
|
||||
std::string key_name = power_config[i].zone;
|
||||
|
||||
if(device_settings[section_power].contains(key_name))
|
||||
{
|
||||
power_config[i].state = device_settings[section_power][key_name];
|
||||
LOG_DEBUG("[%s] Reading power config for %s: %s",
|
||||
aura_core_laptop_device_list[device_index]->dmi_name.c_str(),
|
||||
key_name.c_str(), ((power_config[i].state) ? "On" : "Off"));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/*-----------------------------------------------------------------------------*\
|
||||
| Power state flags are packed in zones but the order is inconsistent. |
|
||||
| With thanks to AsusCtl for helping to decipher the packet captures |
|
||||
| https://gitlab.com/asus-linux/asusctl/-/blob/main/rog-aura/src/usb.rs#L150 |
|
||||
\*-----------------------------------------------------------------------------*/
|
||||
bool flag_array[32] =
|
||||
{
|
||||
power_config[0].state, power_config[4].state,
|
||||
power_config[1].state, power_config[5].state,
|
||||
!power_config[2].state, !power_config[6].state,
|
||||
!power_config[3].state, !power_config[7].state,
|
||||
|
||||
false, power_config[8].state,
|
||||
power_config[9].state, !power_config[10].state,
|
||||
!power_config[11].state, false,
|
||||
false, false,
|
||||
|
||||
power_config[12].state, power_config[13].state,
|
||||
!power_config[14].state, !power_config[15].state
|
||||
};
|
||||
|
||||
uint32_t flags = PackPowerFlags(flag_array);
|
||||
LOG_DEBUG("[%s] Sending power config Logo+KB: %02X Lightbar: %02X Lid Edges: %02X Raw: %08X",
|
||||
aura_core_laptop_device_list[device_index]->dmi_name.c_str(),
|
||||
(flags & 0xFF), ((flags >> 8) & 0xFF), ((flags >> 16) & 0xFF), flags);
|
||||
SendPowerConfig(flags);
|
||||
}
|
||||
|
||||
void AsusAuraCoreLaptopController::SendPowerConfig(uint32_t flags)
|
||||
{
|
||||
const uint8_t index = 6;
|
||||
uint8_t buffer[ASUSAURACORELAPTOP_WRITE_PACKET_SIZE] = { ASUSAURACORELAPTOP_REPORT_ID, ASUSAURACORELAPTOP_CMD_POWER, 0x01, 0x00, 0x00, 0x0F };
|
||||
|
||||
memset(&buffer[index], 0, ASUSAURACORELAPTOP_WRITE_PACKET_SIZE - index);
|
||||
|
||||
buffer[3] = flags & 0xFF;
|
||||
buffer[4] = (flags >> 8) & 0xFF;
|
||||
buffer[5] = (flags >> 16) & 0xFF;
|
||||
|
||||
hid_send_feature_report(dev, buffer, ASUSAURACORELAPTOP_WRITE_PACKET_SIZE);
|
||||
}
|
||||
|
||||
uint32_t AsusAuraCoreLaptopController::PackPowerFlags(bool flags[])
|
||||
{
|
||||
uint32_t temp = {};
|
||||
const uint8_t length = 32;
|
||||
|
||||
for (size_t i = 0; i < length; ++i)
|
||||
{
|
||||
uint32_t flag = {flags[i]};
|
||||
flag <<= i;
|
||||
temp |= flag;
|
||||
}
|
||||
|
||||
return temp;
|
||||
}
|
||||
+147
@@ -0,0 +1,147 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| AsusAuraCoreLaptopController.h |
|
||||
| |
|
||||
| Driver for ASUS ROG Aura Core Laptop |
|
||||
| |
|
||||
| Chris M (Dr_No) 28 Jul 2022 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <string>
|
||||
#include <vector>
|
||||
#include <hidapi.h>
|
||||
#include "LogManager.h"
|
||||
#include "RGBController.h"
|
||||
#include "ResourceManager.h"
|
||||
#include "RGBControllerKeyNames.h"
|
||||
#include "AsusAuraCoreLaptopDevices.h"
|
||||
|
||||
#define NA 0xFFFFFFFF
|
||||
#define HID_MAX_STR 255
|
||||
#define ASUSAURACORELAPTOP_TIMEOUT 250
|
||||
#define ASUSAURACORELAPTOP_READ_PACKET_SIZE 64
|
||||
#define ASUSAURACORELAPTOP_WRITE_PACKET_SIZE 64 //Buffer requires a prepended ReportID hence + 1
|
||||
|
||||
#define ASUSAURACORELAPTOP_KEYCOUNT 91
|
||||
#define ASUSAURACORELAPTOP_KEY_WIDTH 18
|
||||
#define ASUSAURACORELAPTOP_KEY_HEIGHT 7
|
||||
#define ASUSAURACORELAPTOP_LIGHTBARCOUNT 6
|
||||
#define ASUSAURACORELAPTOP_LIDCOUNT 3
|
||||
#define ASUSAURACORELAPTOP_POWER_ZONES 4
|
||||
#define ASUSAURACORELAPTOP_POWER_STATES 4
|
||||
#define ASUSAURACORELAPTOP_BRIGHTNESS_MIN 0
|
||||
#define ASUSAURACORELAPTOP_BRIGHTNESS_MAX 3 // No device has proven to have 256 keyboard brightness levels, only 0..3
|
||||
|
||||
enum
|
||||
{
|
||||
ASUSAURACORELAPTOP_MODE_OFF = 0x00, //Turn off - All leds off
|
||||
ASUSAURACORELAPTOP_MODE_DIRECT = 0xFF, //Direct Led Control - Independently set LEDs in zone
|
||||
ASUSAURACORELAPTOP_MODE_STATIC = 0x00, //Static Mode - Set entire zone to a single color.
|
||||
ASUSAURACORELAPTOP_MODE_BREATHING = 0x01, //Breathing Mode - Fades between fully off and fully on.
|
||||
ASUSAURACORELAPTOP_MODE_SPECTRUM = 0x02, //Spectrum Cycle Mode - Cycles through the color spectrum on all lights on the device
|
||||
ASUSAURACORELAPTOP_MODE_RAINBOW = 0x03, //Rainbow Wave Mode - Cycle thru the color spectrum as a wave across all LEDs
|
||||
ASUSAURACORELAPTOP_MODE_FLASHING = 0x0A, //Flashing Mode - Abruptly changing between fully off and fully on.
|
||||
|
||||
/*-------------------------------------------------*\
|
||||
| Modes not implemented in the Armoury Crate |
|
||||
| OEM software that were discovered. |
|
||||
\*-------------------------------------------------*/
|
||||
ASUSAURACORELAPTOP_MODE_STARRY_NIGHT = 0x04, //Starry Night Mode
|
||||
ASUSAURACORELAPTOP_MODE_RAIN = 0x05, //Rain Mode
|
||||
ASUSAURACORELAPTOP_MODE_REACT_FADE = 0x06, //Reactive Fade Mode
|
||||
ASUSAURACORELAPTOP_MODE_REACT_LASER = 0x07, //Reactive Laser Mode
|
||||
ASUSAURACORELAPTOP_MODE_REACT_RIPPLE = 0x08, //Reactive Ripple Mode
|
||||
ASUSAURACORELAPTOP_MODE_COMET = 0x0B, //Comet Mode
|
||||
ASUSAURACORELAPTOP_MODE_FLASHNDASH = 0x0C, //Flash n Dash Mode
|
||||
ASUSAURACORELAPTOP_MODE_KEYSTONE = 0x0D, //Keystone Mode
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
ASUSAURACORELAPTOP_ZONE_BYTE = 2,
|
||||
ASUSAURACORELAPTOP_MODE_BYTE = 3,
|
||||
ASUSAURACORELAPTOP_R1_BYTE = 4,
|
||||
ASUSAURACORELAPTOP_G1_BYTE = 5,
|
||||
ASUSAURACORELAPTOP_B1_BYTE = 6,
|
||||
ASUSAURACORELAPTOP_SPEED_BYTE = 7,
|
||||
ASUSAURACORELAPTOP_DIRECTION_BYTE = 8,
|
||||
ASUSAURACORELAPTOP_DATA_BYTE = 9,
|
||||
ASUSAURACORELAPTOP_R2_BYTE = 10,
|
||||
ASUSAURACORELAPTOP_G2_BYTE = 11,
|
||||
ASUSAURACORELAPTOP_B2_BYTE = 12,
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
ASUSAURACORELAPTOP_REPORT_ID = 0x5D,
|
||||
ASUSAURACORELAPTOP_CMD_BRIGHTNESS = 0xBA,
|
||||
ASUSAURACORELAPTOP_CMD_DIRECT = 0xBC,
|
||||
ASUSAURACORELAPTOP_CMD_POWER = 0xBD,
|
||||
ASUSAURACORELAPTOP_CMD_UPDATE = 0xB3,
|
||||
ASUSAURACORELAPTOP_CMD_APPLY = 0xB4,
|
||||
ASUSAURACORELAPTOP_CMD_SET = 0xB5,
|
||||
ASUSAURACORELAPTOP_CMD_LAYOUT = 0x05,
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
ASUSAURACORELAPTOP_SPEED_SLOWEST = 0xE1, // Slowest speed
|
||||
ASUSAURACORELAPTOP_SPEED_NORMAL = 0xEB, // Normal speed
|
||||
ASUSAURACORELAPTOP_SPEED_FASTEST = 0xF5, // Fastest speed
|
||||
};
|
||||
|
||||
enum aura_core_laptop_layout
|
||||
{
|
||||
ASUSAURACORELAPTOP_LAYOUT_ANSI = 0x01, /* US ANSI Layout */
|
||||
ASUSAURACORELAPTOP_LAYOUT_ISO = 0x02, /* EURO ISO Layout */
|
||||
};
|
||||
|
||||
struct p_state
|
||||
{
|
||||
std::string zone;
|
||||
bool state;
|
||||
};
|
||||
|
||||
class AsusAuraCoreLaptopController
|
||||
{
|
||||
public:
|
||||
AsusAuraCoreLaptopController(hid_device* dev_handle, const char* path);
|
||||
~AsusAuraCoreLaptopController();
|
||||
|
||||
const aura_core_laptop_device* GetDeviceData();
|
||||
std::string GetDeviceDescription();
|
||||
std::string GetSerial();
|
||||
unsigned int GetKeyboardLayout();
|
||||
std::string GetLocation();
|
||||
|
||||
void SetMode(uint8_t mode, uint8_t speed, uint8_t brightness, RGBColor color1, RGBColor color2, uint8_t random, uint8_t direction);
|
||||
void SetLedsDirect(std::vector<RGBColor *>colors);
|
||||
void SendInitDirectMode();
|
||||
private:
|
||||
hid_device* dev;
|
||||
uint16_t device_index;
|
||||
std::string location;
|
||||
|
||||
uint8_t current_mode;
|
||||
uint8_t current_speed;
|
||||
uint8_t current_direction;
|
||||
|
||||
RGBColor current_c1;
|
||||
RGBColor current_c2;
|
||||
uint8_t current_brightness;
|
||||
uint8_t current_random;
|
||||
|
||||
void SendApply();
|
||||
void SendBrightness();
|
||||
void SendSet();
|
||||
void SendUpdate();
|
||||
|
||||
void SetPowerConfigFromJSON();
|
||||
void SendPowerConfig(uint32_t flags);
|
||||
uint32_t PackPowerFlags(bool flags[]);
|
||||
std::vector<p_state> PowerConfigArray();
|
||||
};
|
||||
+960
@@ -0,0 +1,960 @@
|
||||
#include "AsusAuraCoreLaptopDevices.h"
|
||||
|
||||
/*-------------------------------------------------------------------------*\
|
||||
| Aura Core Key Values |
|
||||
| NULL values are keys that are handed to the KLM but are removed as |
|
||||
| a part of customisation. They are included to maintain expected key |
|
||||
| count is aligned to the value count. |
|
||||
\*-------------------------------------------------------------------------*/
|
||||
|
||||
std::vector<unsigned int> aura_core_laptop_15_16_values =
|
||||
{
|
||||
/* ESC F1 F2 F3 F4 F5 F6 F7 F8 F9 F10 F11 F12 DEL */
|
||||
21, 23, 24, 25, 26, 28, 29, 30, 31, 33, 34, 35, 36,
|
||||
/* BKTK 1 2 3 4 5 6 7 8 9 0 - = BSPC PLAY */
|
||||
42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55,
|
||||
/* TAB Q W E R T Y U I O P [ ] \ STOP */
|
||||
63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76,
|
||||
/* CPLK A S D F G H J K L ; " # ENTR PREV */
|
||||
84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 98,
|
||||
/* LSFT ISO\ Z X C V B N M , . / RSFT ARWU NEXT */
|
||||
105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116, 119,
|
||||
/* LCTL LWIN LALT SPC RALT RFNC RMNU RCTL ARWL ARWD ARWR */
|
||||
126, 128, 129, 131, 135, 136, 136, 137,
|
||||
};
|
||||
|
||||
std::vector<unsigned int> aura_core_laptop_17_values =
|
||||
{
|
||||
/* ESC F1 F2 F3 F4 F5 F6 F7 F8 F9 F10 F11 F12 NULL NULL PAUS */
|
||||
21, 23, 24, 25, 26, 28, 29, 30, 31, 33, 34, 35, 36, 0, 0, 39,
|
||||
/* BKTK 1 2 3 4 5 6 7 8 9 0 - = BSPC NULL NULL NULL NMLK NMDV NMTM NMMI */
|
||||
42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 56, 0, 0, 0, 59, 60, 61, 62,
|
||||
/* TAB Q W E R T Y U I O P [ ] \ NULL NULL NULL NM7 NM8 NM9 NMPL */
|
||||
63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 0, 0, 0, 80, 81, 82, 83,
|
||||
/* CPLK A S D F G H J K L ; " # ENTR NM4 NM5 NM6 */
|
||||
84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 98, 101, 102, 103,
|
||||
/* LSFT ISO\ Z X C V B N M , . / RSFT ARWU NM1 NM2 NM3 NMER */
|
||||
105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116, 119, 139, 122, 123, 124, 125,
|
||||
/* LCTL LWIN LALT SPC RALT RFNC RMNU RCTL ARWL ARWD ARWR NM0 NMPD */
|
||||
126, 128, 129, 131, 135, 136, 136, 137, 159, 160, 161, 144, 145,
|
||||
};
|
||||
|
||||
std::vector<unsigned int> aura_core_laptop_18_values =
|
||||
{
|
||||
/* ESC F1 F2 F3 F4 F5 F6 F7 F8 F9 F10 F11 F12 NULL NULL PAUS */
|
||||
21, 23, 24, 25, 26, 28, 29, 30, 31, 33, 34, 35, 36, 0, 0, 39,
|
||||
/* BKTK 1 2 3 4 5 6 7 8 9 0 - = BSPC NULL NULL NULL NMLK NMDV NMTM NMMI */
|
||||
42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 56, 0, 0, 0, 59, 60, 61, 62,
|
||||
/* TAB Q W E R T Y U I O P [ ] \ NULL NULL NULL NM7 NM8 NM9 NMPL */
|
||||
63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 0, 0, 0, 80, 81, 82, 83,
|
||||
/* CPLK A S D F G H J K L ; " # ENTR NM4 NM5 NM6 */
|
||||
84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 98, 101, 102, 103,
|
||||
/* LSFT ISO\ Z X C V B N M , . / RSFT ARWU NM1 NM2 NM3 NMER */
|
||||
105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116, 119, 121, 122, 123, 124, 125,
|
||||
/* LCTL LWIN LALT SPC RALT RFNC RMNU RCTL ARWL ARWD ARWR NM0 NMPD */
|
||||
126, 128, 129, 131, 135, 136, 136, 137, 141, 142, 143, 144, 145,
|
||||
};
|
||||
|
||||
std::vector<unsigned int> aura_core_laptop_17_g733qr_values =
|
||||
{
|
||||
/* volD volU Mute Fan ROG */
|
||||
2, 3, 4, 5, 6,
|
||||
/* ESC F1 F2 F3 F4 F5 F6 F7 F8 F9 F10 F11 F12 DEL NUM7 NUM8 NUM9 */
|
||||
21, 23, 24, 25, 26, 28, 29, 30, 31, 33, 34, 35, 36, 38, 39, 40, 41,
|
||||
/* BKTK 1 2 3 4 5 6 7 8 9 0 - = BSPC /NUM NUM4 NUM5 NUM6 */
|
||||
42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 56, 59, 60, 61, 62,
|
||||
/* TAB Q W E R T Y U I O P [ ] # *NUM NUM1 NUM2 NUM3 */
|
||||
63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 78, 80, 81, 82, 83,
|
||||
/* CPLK A S D F G H J K L ; ' ENTR -NUM +NUM NUM0 DOT */
|
||||
84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 98, 101, 102, 103, 104,
|
||||
/* LSFT ISO\ Z X C V B N M , . / RSFT ARWU */
|
||||
105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116, 118, 123,
|
||||
/* LCTL LFNC LWIN LALT SPC RALT PRSC RFNC RCTL ARWL ARWD ARWR KeyStone(only Red) */
|
||||
126, 127, 128, 129, 132, 135, 137, 139, 141, 143, 144, 145, 175,
|
||||
};
|
||||
/*-------------------------------------------------------------------------*\
|
||||
| KEYMAPS |
|
||||
\*-------------------------------------------------------------------------*/
|
||||
keyboard_keymap_overlay_values g533zm_layout
|
||||
{
|
||||
KEYBOARD_SIZE_SEVENTY_FIVE,
|
||||
{
|
||||
aura_core_laptop_15_16_values,
|
||||
{
|
||||
/* Add more regional layout fixes here */
|
||||
}
|
||||
},
|
||||
{
|
||||
/*-------------------------------------------------------------------------------------------------------------------------------------*\
|
||||
| Edit Keys |
|
||||
| Zone, Row, Column, Value, Key, Alternate Name, OpCode, |
|
||||
\*-------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
{ 0, 0, 15, 37, KEY_EN_DELETE, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Delete
|
||||
{ 0, 1, 15, 58, KEY_EN_MEDIA_PLAY_PAUSE, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Play / Pause
|
||||
{ 0, 2, 15, 79, KEY_EN_MEDIA_STOP, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Stop
|
||||
{ 0, 3, 15, 100, KEY_EN_MEDIA_PREVIOUS, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Previous
|
||||
{ 0, 4, 13, 139, KEY_EN_UP_ARROW, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Up Arrow
|
||||
{ 0, 4, 15, 121, KEY_EN_MEDIA_NEXT, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Next
|
||||
{ 0, 5, 12, 159, KEY_EN_LEFT_ARROW, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Left Arrow
|
||||
{ 0, 5, 13, 160, KEY_EN_DOWN_ARROW, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Down Arrow
|
||||
{ 0, 5, 14, 161, KEY_EN_RIGHT_ARROW, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Right Arrow
|
||||
}
|
||||
};
|
||||
|
||||
keyboard_keymap_overlay_values g533zw_layout
|
||||
{
|
||||
KEYBOARD_SIZE_SEVENTY_FIVE,
|
||||
{
|
||||
aura_core_laptop_15_16_values,
|
||||
{
|
||||
/* Add more regional layout fixes here */
|
||||
}
|
||||
},
|
||||
{
|
||||
/*-------------------------------------------------------------------------------------------------------------------------------------*\
|
||||
| Edit Keys |
|
||||
| Zone, Row, Column, Value, Key, Alternate Name, OpCode, |
|
||||
\*-------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
{ 0, 0, 15, 37, KEY_EN_DELETE, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Delete
|
||||
{ 0, 1, 15, 58, KEY_EN_MEDIA_PLAY_PAUSE, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Play / Pause
|
||||
{ 0, 2, 15, 79, KEY_EN_MEDIA_STOP, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Stop
|
||||
{ 0, 3, 15, 100, KEY_EN_MEDIA_PREVIOUS, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Previous
|
||||
{ 0, 4, 15, 121, KEY_EN_MEDIA_NEXT, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Media Next
|
||||
{ 0, 5, 1, 127, KEY_EN_LEFT_FUNCTION, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Left Function key
|
||||
{ 0, 5, 4, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove Unused key
|
||||
{ 0, 5, 11, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove Right Func key
|
||||
{ 0, 5, 11, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove Right Context key
|
||||
{ 0, 5, 13, 139, KEY_EN_UP_ARROW, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Up Arrow
|
||||
{ 0, 5, 15, 142, KEY_EN_PRINT_SCREEN, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Print Screen
|
||||
{ 0, 5, 16, 175, "Keystone", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Keystone (Red only)
|
||||
{ 0, 6, 12, 159, KEY_EN_LEFT_ARROW, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Left Arrow on new row
|
||||
{ 0, 6, 13, 160, KEY_EN_DOWN_ARROW, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Down Arrow
|
||||
{ 0, 6, 14, 161, KEY_EN_RIGHT_ARROW, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Right Arrow
|
||||
{ 0, 0, 2, 2, KEY_EN_MEDIA_VOLUME_DOWN, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_ROW, }, // Insert Row before function keys
|
||||
{ 0, 0, 3, 3, KEY_EN_MEDIA_VOLUME_UP, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Vol Up
|
||||
{ 0, 0, 4, 4, "Mic On / Off", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Mic On / Off
|
||||
{ 0, 0, 5, 5, "Hyperfan", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Hyperfan
|
||||
{ 0, 0, 6, 6, "Armoury Crate", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Armoury Crate
|
||||
}
|
||||
};
|
||||
|
||||
keyboard_keymap_overlay_values g533zw_lid_layout
|
||||
{
|
||||
KEYBOARD_SIZE_EMPTY,
|
||||
{
|
||||
{ /* Values not set in empty keyboard */ },
|
||||
{
|
||||
/* Add more regional layout fixes here */
|
||||
}
|
||||
},
|
||||
{
|
||||
/*-------------------------------------------------------------------------------------------------------------------------------------*\
|
||||
| Edit Keys |
|
||||
| Zone, Row, Column, Value, Key, Alternate Name, OpCode, |
|
||||
\*-------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
{ 0, 0, 0, 167, "Logo", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Lightbar L1
|
||||
{ 0, 0, 1, 176, "Vertical Cut Left", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Lightbar L2
|
||||
{ 0, 0, 2, 177, "Vertical Cut Right", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Lightbar L3
|
||||
}
|
||||
};
|
||||
|
||||
keyboard_keymap_overlay_values g533zw_lightbar_layout
|
||||
{
|
||||
KEYBOARD_SIZE_EMPTY,
|
||||
{
|
||||
{ /* Values not set in empty keyboard */ },
|
||||
{
|
||||
/* Add more regional layout fixes here */
|
||||
}
|
||||
},
|
||||
{
|
||||
/*-------------------------------------------------------------------------------------------------------------------------------------*\
|
||||
| Edit Keys |
|
||||
| Zone, Row, Column, Value, Key, Alternate Name, OpCode, |
|
||||
\*-------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
{ 0, 0, 0, 174, "Lightbar L1", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Lightbar L1
|
||||
{ 0, 0, 1, 173, "Lightbar L2", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Lightbar L2
|
||||
{ 0, 0, 2, 172, "Lightbar L3", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Lightbar L3
|
||||
{ 0, 0, 3, 171, "Lightbar R3", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Lightbar R3
|
||||
{ 0, 0, 4, 170, "Lightbar R2", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Lightbar R2
|
||||
{ 0, 0, 5, 169, "Lightbar R1", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Lightbar R1
|
||||
}
|
||||
};
|
||||
|
||||
keyboard_keymap_overlay_values g614jz_keyboard_layout
|
||||
{
|
||||
KEYBOARD_SIZE_SEVENTY_FIVE,
|
||||
{
|
||||
aura_core_laptop_15_16_values,
|
||||
{
|
||||
/* Add more regional layout fixes here */
|
||||
}
|
||||
},
|
||||
{
|
||||
/*-------------------------------------------------------------------------------------------------------------------------------------*\
|
||||
| Edit Keys |
|
||||
| Zone, Row, Column, Value, Key, Alternate Name, OpCode, |
|
||||
\*-------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
{ 0, 0, 2, 2, KEY_EN_MEDIA_VOLUME_DOWN, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_ROW, }, // Insert Row and add Volume Down
|
||||
{ 0, 0, 3, 3, KEY_EN_MEDIA_VOLUME_UP, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Volume Up
|
||||
{ 0, 0, 4, 4, KEY_EN_MEDIA_MUTE, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Mute
|
||||
{ 0, 0, 5, 5, "Key: Fan", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert "Fan" key
|
||||
{ 0, 0, 6, 6, "Key: ROG", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert "ROG" key
|
||||
{ 0, 6, 1, 127, KEY_EN_LEFT_FUNCTION, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Left Fuction
|
||||
{ 0, 6, 8, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove part of Spacebar
|
||||
{ 0, 6, 8, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove part of Spacebar
|
||||
{ 0, 6, 10, 136, KEY_EN_RIGHT_FUNCTION, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove Right Fuction
|
||||
{ 0, 6, 10, 136, KEY_EN_RIGHT_WINDOWS, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove Right Win Key
|
||||
|
||||
{ 0, 1, 15, 37, KEY_EN_DELETE, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Delete
|
||||
{ 0, 2, 15, 58, KEY_EN_MEDIA_PLAY_PAUSE, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Play / Pause
|
||||
{ 0, 3, 15, 79, KEY_EN_MEDIA_STOP, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Stop
|
||||
{ 0, 3, 13, 76, KEY_EN_ANSI_BACK_SLASH, KEY_EN_UNUSED, KEYBOARD_OPCODE_SWAP_ONLY, }, // Force ANSI | even on ISO layouts
|
||||
{ 0, 4, 15, 100, KEY_EN_MEDIA_PREVIOUS, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Previous
|
||||
{ 0, 5, 15, 121, KEY_EN_MEDIA_NEXT, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Next
|
||||
{ 0, 5, 12, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // gap before arrow up key
|
||||
|
||||
{ 0, 6, 10, 136, KEY_EN_PRINT_SCREEN, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert a Print Screen key
|
||||
{ 0, 6, 15, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // trim extra column before numpad
|
||||
|
||||
// Close numpad gap completely
|
||||
{ 0, 1, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
{ 0, 2, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
{ 0, 3, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
{ 0, 4, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
|
||||
// Move Arrow keys
|
||||
{ 0, 6, 13, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_SWAP_ONLY, }, // Remove Arrow Down
|
||||
{ 0, 5, 13, 120, KEY_EN_UP_ARROW, KEY_EN_UNUSED, KEYBOARD_OPCODE_SWAP_ONLY, }, // Shift Arrow Ups4
|
||||
{ 0, 6, 12, 140, KEY_EN_LEFT_ARROW, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 6, 13, 141, KEY_EN_DOWN_ARROW, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 6, 14, 142, KEY_EN_RIGHT_ARROW, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
}
|
||||
};
|
||||
|
||||
keyboard_keymap_overlay_values g614jz_lightbar_layout
|
||||
{
|
||||
KEYBOARD_SIZE_EMPTY,
|
||||
{
|
||||
{ /* Values not set in empty keyboard */ },
|
||||
{
|
||||
/* Add more regional layout fixes here */
|
||||
}
|
||||
},
|
||||
{
|
||||
/*-------------------------------------------------------------------------------------------------------------------------------------*\
|
||||
| Edit Keys |
|
||||
| Zone, Row, Column, Value, Key, Alternate Name, OpCode, |
|
||||
\*-------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
{ 0, 0, 0, 173, "Lightbar L1", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Lightbar L2
|
||||
{ 0, 1, 0, 172, "Lightbar L2", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Lightbar L3
|
||||
{ 0, 0, 14, 169, "Lightbar R1", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Lightbar R1
|
||||
{ 0, 1, 14, 170, "Lightbar R2", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Lightbar R2
|
||||
}
|
||||
};
|
||||
|
||||
keyboard_keymap_overlay_values g713rw_keyboard_layout
|
||||
{
|
||||
KEYBOARD_SIZE_FULL,
|
||||
{
|
||||
aura_core_laptop_17_values,
|
||||
{
|
||||
/* Add more regional layout fixes here */
|
||||
}
|
||||
},
|
||||
{
|
||||
/*-------------------------------------------------------------------------------------------------------------------------------------*\
|
||||
| Edit Keys |
|
||||
| Zone, Row, Column, Value, Key, Alternate Name, OpCode, |
|
||||
\*-------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
{ 0, 0, 2, 2, KEY_EN_MEDIA_VOLUME_DOWN, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_ROW, }, // Insert Row and add Volume Down
|
||||
{ 0, 0, 3, 3, KEY_EN_MEDIA_VOLUME_UP, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Volume Up
|
||||
{ 0, 0, 4, 4, KEY_EN_MEDIA_MUTE, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Mute
|
||||
{ 0, 0, 5, 5, "Key: Fan", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert "Fan" key
|
||||
{ 0, 0, 6, 6, "Key: ROG", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert "ROG" key
|
||||
{ 0, 6, 1, 127, KEY_EN_LEFT_FUNCTION, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Left Fuction
|
||||
{ 0, 6, 8, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove part of Spacebar
|
||||
{ 0, 6, 8, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove part of Spacebar
|
||||
{ 0, 6, 10, 136, KEY_EN_RIGHT_FUNCTION, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove Right Fuction
|
||||
{ 0, 6, 10, 136, KEY_EN_RIGHT_WINDOWS, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove Right Win Key
|
||||
|
||||
{ 0, 1, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_SWAP_ONLY, },
|
||||
{ 0, 1, 15, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // trim extra column before numpad
|
||||
{ 0, 1, 15, 38, KEY_EN_DELETE, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert a Delete key
|
||||
{ 0, 1, 17, 40, KEY_EN_PRINT_SCREEN, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert a Print Screen key
|
||||
{ 0, 1, 18, 41, KEY_EN_HOME, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert a Home key
|
||||
{ 0, 2, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
{ 0, 2, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
{ 0, 3, 13, 76, KEY_EN_ANSI_BACK_SLASH, KEY_EN_UNUSED, KEYBOARD_OPCODE_SWAP_ONLY, }, // Force ANSI | even on ISO layouts
|
||||
{ 0, 3, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
{ 0, 3, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
{ 0, 4, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
{ 0, 4, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
{ 0, 5, 12, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // gap before arrow up key
|
||||
{ 0, 5, 13, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // trim extra column before numpad
|
||||
|
||||
{ 0, 6, 11, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // 1 empty key before arrow keys
|
||||
{ 0, 6, 15, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // trim extra column before numpad
|
||||
{ 0, 6, 16, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // 1 empty key between numpad 0 and .
|
||||
|
||||
// Close numpad gap completely
|
||||
{ 0, 1, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
{ 0, 2, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
{ 0, 3, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
{ 0, 4, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
{ 0, 5, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
{ 0, 6, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
|
||||
// Move Arrow keys
|
||||
{ 0, 5, 13, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_SWAP_ONLY, }, // Remove Arrow Up
|
||||
{ 0, 6, 13, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_SWAP_ONLY, }, // Remove Arrow Down
|
||||
{ 0, 6, 12, 139, KEY_EN_UP_ARROW, KEY_EN_UNUSED, KEYBOARD_OPCODE_SWAP_ONLY, }, // Shift Arrow Up
|
||||
{ 0, 7, 11, 159, KEY_EN_LEFT_ARROW, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 7, 12, 160, KEY_EN_DOWN_ARROW, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 7, 13, 161, KEY_EN_RIGHT_ARROW, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
}
|
||||
};
|
||||
|
||||
keyboard_keymap_overlay_values g713rw_lightbar_layout
|
||||
{
|
||||
KEYBOARD_SIZE_EMPTY,
|
||||
{
|
||||
{ /* Values not set in empty keyboard */ },
|
||||
{
|
||||
/* Add more regional layout fixes here */
|
||||
}
|
||||
},
|
||||
{
|
||||
/*-------------------------------------------------------------------------------------------------------------------------------------*\
|
||||
| Edit Keys |
|
||||
| Zone, Row, Column, Value, Key, Alternate Name, OpCode, |
|
||||
\*-------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
{ 0, 0, 0, 174, "Lightbar L1", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Lightbar L1
|
||||
{ 0, 0, 1, 173, "Lightbar L2", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Lightbar L2
|
||||
{ 0, 0, 2, 172, "Lightbar L3", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Lightbar L3
|
||||
{ 0, 0, 3, 171, "Lightbar R3", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Lightbar R3
|
||||
{ 0, 0, 4, 170, "Lightbar R2", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Lightbar R2
|
||||
{ 0, 0, 5, 169, "Lightbar R1", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Lightbar R1
|
||||
}
|
||||
};
|
||||
|
||||
keyboard_keymap_overlay_values g713rw_test_layout
|
||||
{
|
||||
KEYBOARD_SIZE_EMPTY,
|
||||
{
|
||||
{ /* Values not set in empty keyboard */ },
|
||||
{
|
||||
/* Add more regional layout fixes here */
|
||||
}
|
||||
},
|
||||
{
|
||||
/*-------------------------------------------------------------------------------------------------------------------------------------*\
|
||||
| Edit Keys |
|
||||
| Zone, Row, Column, Value, Key, Alternate Name, OpCode, |
|
||||
\*-------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
{ 0, 0, 0, 7, "Test01", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 1, 8, "Test02", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 2, 9, "Test03", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 3, 10, "Test04", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 4, 11, "Test05", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 5, 12, "Test06", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 6, 13, "Test07", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 7, 14, "Test08", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 8, 15, "Test09", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 9, 16, "Test10", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 10, 17, "Test11", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 11, 18, "Test12", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 12, 19, "Test13", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 13, 20, "Test14", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 14, 22, "Test15", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 15, 27, "Test16", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 16, 55, "Test17", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 17, 57, "Test18", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 18, 58, "Test19", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 19, 77, "Test20", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 20, 78, "Test21", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 21, 79, "Test22", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 22, 96, "Test23", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 23, 97, "Test24", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 24, 99, "Test25", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 25, 100, "Test26", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 26, 104, "Test27", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 27, 117, "Test28", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 28, 118, "Test29", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 29, 120, "Test30", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 30, 121, "Test31", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 31, 130, "Test32", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 32, 132, "Test33", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 33, 133, "Test34", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 34, 134, "Test35", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 35, 138, "Test36", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 36, 140, "Test37", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 37, 141, "Test38", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 38, 142, "Test39", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 39, 143, "Test40", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 40, 146, "Test41", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 41, 147, "Test42", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 42, 148, "Test43", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 43, 149, "Test44", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 44, 150, "Test45", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 45, 151, "Test46", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 46, 152, "Test47", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 47, 153, "Test48", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 48, 154, "Test49", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 49, 155, "Test50", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 50, 156, "Test51", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 51, 157, "Test52", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 52, 158, "Test53", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 53, 162, "Test54", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 54, 163, "Test55", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 55, 164, "Test56", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 56, 165, "Test57", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 57, 166, "Test58", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
{ 0, 0, 58, 167, "Test59", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, },
|
||||
}
|
||||
};
|
||||
|
||||
keyboard_keymap_overlay_values g733zm_layout
|
||||
{
|
||||
KEYBOARD_SIZE_FULL,
|
||||
{
|
||||
aura_core_laptop_17_values,
|
||||
{
|
||||
/* Add more regional layout fixes here */
|
||||
}
|
||||
},
|
||||
{
|
||||
/*-------------------------------------------------------------------------------------------------------------------------------------*\
|
||||
| Edit Keys |
|
||||
| Zone, Row, Column, Value, Key, Alternate Name, OpCode, |
|
||||
\*-------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
}
|
||||
};
|
||||
|
||||
keyboard_keymap_overlay_values g733qr_keyboard_layout
|
||||
{
|
||||
KEYBOARD_SIZE_EMPTY,
|
||||
{
|
||||
{ /* No base values, we build everything via edit keys */ },
|
||||
{
|
||||
/* Regional layout fixes (none yet) */
|
||||
}
|
||||
},
|
||||
{
|
||||
/*---------------------------------------------------------------------*\
|
||||
| Row 0 - Top macro row (left to right) |
|
||||
\*---------------------------------------------------------------------*/
|
||||
//{ 0, 0, 0, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT }, // GAP
|
||||
//{ 0, 0, 1, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT }, // GAP
|
||||
{ 0, 0, 2, 2, KEY_EN_MEDIA_VOLUME_DOWN, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 0, 3, 3, KEY_EN_MEDIA_VOLUME_UP, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 0, 4, 4, KEY_EN_MEDIA_MUTE, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 0, 5, 5, "Key: Fan", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 0, 6, 6, "Key: ROG", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
|
||||
/*---------------------------------------------------------------------*\
|
||||
| Row 1 - Esc, F-row, Delete, Num 7-9 |
|
||||
\*---------------------------------------------------------------------*/
|
||||
{ 0, 1, 0, 21, KEY_EN_ESCAPE, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
|
||||
//{ 0, 1, 1, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT }, // GAP
|
||||
|
||||
{ 0, 1, 2, 23, KEY_EN_F1, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 1, 3, 24, KEY_EN_F2, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 1, 4, 25, KEY_EN_F3, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 1, 5, 26, KEY_EN_F4, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
|
||||
//{ 0, 1, 6, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT }, // GAP
|
||||
|
||||
{ 0, 1, 7, 28, KEY_EN_F5, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 1, 8, 29, KEY_EN_F6, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 1, 9, 30, KEY_EN_F7, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 1,10, 31, KEY_EN_F8, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
|
||||
//{ 0, 1,11, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT }, // GAP
|
||||
|
||||
{ 0, 1,11, 33, KEY_EN_F9, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 1,12, 34, KEY_EN_F10, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 1,13, 35, KEY_EN_F11, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 1,14, 36, KEY_EN_F12, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
|
||||
//{ 0, 1,16, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT }, // GAP
|
||||
|
||||
{ 0, 1,15, 38, KEY_EN_DELETE, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 1,16, 39, KEY_EN_NUMPAD_7, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 1,17, 40, KEY_EN_NUMPAD_8, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 1,18, 41, KEY_EN_NUMPAD_9, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
|
||||
/*---------------------------------------------------------------------*\
|
||||
| Row 2 - `123...BSPC, Num / 4 5 6 |
|
||||
\*---------------------------------------------------------------------*/
|
||||
{ 0, 2, 0, 42, KEY_EN_BACK_TICK, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 2, 1, 43, KEY_EN_1, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 2, 2, 44, KEY_EN_2, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 2, 3, 45, KEY_EN_3, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 2, 4, 46, KEY_EN_4, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 2, 5, 47, KEY_EN_5, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 2, 6, 48, KEY_EN_6, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 2, 7, 49, KEY_EN_7, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 2, 8, 50, KEY_EN_8, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 2, 9, 51, KEY_EN_9, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 2,10, 52, KEY_EN_0, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 2,11, 53, KEY_EN_MINUS, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 2,12, 54, KEY_EN_EQUALS, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 2,13, 56, KEY_EN_BACKSPACE, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
|
||||
//{ 0, 2,15, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT }, // GAP
|
||||
|
||||
{ 0, 2,15, 59, KEY_EN_NUMPAD_DIVIDE, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 2,16, 60, KEY_EN_NUMPAD_4, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 2,17, 61, KEY_EN_NUMPAD_5, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 2,18, 62, KEY_EN_NUMPAD_6, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
|
||||
/*---------------------------------------------------------------------*\
|
||||
| Row 3 - Tab row + Num * 1 2 3 |
|
||||
\*---------------------------------------------------------------------*/
|
||||
{ 0, 3, 0, 63, KEY_EN_TAB, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 3, 1, 64, KEY_EN_Q, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 3, 2, 65, KEY_EN_W, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 3, 3, 66, KEY_EN_E, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 3, 4, 67, KEY_EN_R, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 3, 5, 68, KEY_EN_T, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 3, 6, 69, KEY_EN_Y, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 3, 7, 70, KEY_EN_U, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 3, 8, 71, KEY_EN_I, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 3, 9, 72, KEY_EN_O, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 3,10, 73, KEY_EN_P, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 3,11, 74, KEY_EN_LEFT_BRACKET, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 3,12, 75, KEY_EN_RIGHT_BRACKET, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 3,13, 78, KEY_EN_POUND, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
|
||||
//{ 0, 3,14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT }, // GAP
|
||||
|
||||
{ 0, 3,15, 80, KEY_EN_NUMPAD_TIMES, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 3,16, 81, KEY_EN_NUMPAD_1, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 3,17, 82, KEY_EN_NUMPAD_2, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 3,18, 83, KEY_EN_NUMPAD_3, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
|
||||
/*---------------------------------------------------------------------*\
|
||||
| Row 4 - Caps row + Num - + 0 . |
|
||||
\*---------------------------------------------------------------------*/
|
||||
{ 0, 4, 0, 84, KEY_EN_CAPS_LOCK, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 4, 1, 85, KEY_EN_A, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 4, 2, 86, KEY_EN_S, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 4, 3, 87, KEY_EN_D, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 4, 4, 88, KEY_EN_F, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 4, 5, 89, KEY_EN_G, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 4, 6, 90, KEY_EN_H, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 4, 7, 91, KEY_EN_J, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 4, 8, 92, KEY_EN_K, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 4, 9, 93, KEY_EN_L, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 4,10, 94, KEY_EN_SEMICOLON, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 4,11, 95, KEY_EN_QUOTE, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 4,12, 98, KEY_EN_ANSI_ENTER, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT},
|
||||
|
||||
//{ 0, 4,14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT }, // GAP
|
||||
|
||||
{ 0, 4,15, 101, KEY_EN_NUMPAD_MINUS, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 4,16, 102, KEY_EN_NUMPAD_PLUS, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 4,17, 103, KEY_EN_NUMPAD_0, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 4,18, 104, KEY_EN_NUMPAD_PERIOD, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
|
||||
/*---------------------------------------------------------------------*\
|
||||
| Row 5 - Shift row + Up Arrow |
|
||||
\*---------------------------------------------------------------------*/
|
||||
{ 0, 5, 0, 105, KEY_EN_LEFT_SHIFT, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 5, 1, 106, KEY_EN_ANSI_BACK_SLASH, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 5, 2, 107, KEY_EN_Z, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 5, 3, 108, KEY_EN_X, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 5, 4, 109, KEY_EN_C, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 5, 5, 110, KEY_EN_V, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 5, 6, 111, KEY_EN_B, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 5, 7, 112, KEY_EN_N, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 5, 8, 113, KEY_EN_M, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 5, 9, 114, KEY_EN_COMMA, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 5,10, 115, KEY_EN_PERIOD, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 5,11, 116, KEY_EN_FORWARD_SLASH, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 5,12, 118, KEY_EN_RIGHT_SHIFT, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
|
||||
//{ 0, 5,14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT }, // GAP
|
||||
//{ 0, 5,15, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT }, // GAP
|
||||
//{ 0, 5,16, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT }, // GAP
|
||||
|
||||
{ 0, 5,16, 123, KEY_EN_UP_ARROW, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
|
||||
/*---------------------------------------------------------------------*\
|
||||
| Row 6 - Ctrl/Win/Alt/Space/Fn/Arrows/Keystone |
|
||||
\*---------------------------------------------------------------------*/
|
||||
{ 0, 6, 0, 126, KEY_EN_LEFT_CONTROL, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 6, 1, 127, KEY_EN_LEFT_FUNCTION, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 6, 2, 128, KEY_EN_LEFT_WINDOWS, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 6, 3, 129, KEY_EN_LEFT_ALT, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 6, 4, 132, KEY_EN_SPACE, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
|
||||
{ 0, 6, 9, 135, KEY_EN_RIGHT_ALT, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 6,10, 137, KEY_EN_PRINT_SCREEN, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 6,11, 139, KEY_EN_RIGHT_FUNCTION, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 6,12, 141, KEY_EN_RIGHT_CONTROL, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
|
||||
//{ 0, 6,13, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT }, // GAP
|
||||
//{ 0, 6,14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT }, // GAP
|
||||
|
||||
{ 0, 6,15, 143, KEY_EN_LEFT_ARROW, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 6,16, 144, KEY_EN_DOWN_ARROW, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 6,17, 145, KEY_EN_RIGHT_ARROW, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
}
|
||||
};
|
||||
|
||||
keyboard_keymap_overlay_values g733qr_lid_layout
|
||||
{
|
||||
KEYBOARD_SIZE_EMPTY,
|
||||
{
|
||||
{ /* Values not set in empty keyboard */ },
|
||||
{
|
||||
/* Regional layout fixes (none) */
|
||||
}
|
||||
},
|
||||
{
|
||||
/*-------------------------------------------------------------------------------------------------------------------------------------*\
|
||||
| Edit Keys |
|
||||
| Zone, Row, Column, Value, Key, Alternate Name, OpCode |
|
||||
\*-------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
{ 0, 0, 0, 167, "ROG Logo", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT }, // Single lid/logo zone
|
||||
{ 0, 0, 1, 176, "Vertical Cut Left", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Lightbar L2
|
||||
{ 0, 0, 2, 177, "Vertical Cut Right", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Lightbar L3
|
||||
}
|
||||
};
|
||||
|
||||
keyboard_keymap_overlay_values g733qr_lightbar_layout
|
||||
{
|
||||
KEYBOARD_SIZE_EMPTY,
|
||||
{
|
||||
{ /* Values not set in empty keyboard */ },
|
||||
{
|
||||
/* Regional layout fixes (none) */
|
||||
}
|
||||
},
|
||||
{
|
||||
/*-------------------------------------------------------------------------------------------------------------------------------------*\
|
||||
| Edit Keys |
|
||||
| Zone, Row, Column, Value, Key, Alternate Name, OpCode |
|
||||
\*-------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
{ 0, 0, 0, 174, "Lightbar L1", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 0, 1, 173, "Lightbar L2", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 0, 2, 172, "Lightbar L3", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 0, 3, 171, "Lightbar R3", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 0, 4, 170, "Lightbar R2", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
{ 0, 0, 5, 169, "Lightbar R1", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
keyboard_keymap_overlay_values g733qr_keystone_layout
|
||||
{
|
||||
KEYBOARD_SIZE_EMPTY,
|
||||
{
|
||||
{ /* Values not set in empty keyboard */ },
|
||||
{
|
||||
/* Regional layout fixes (none) */
|
||||
}
|
||||
},
|
||||
{
|
||||
{ 0, 0, 0, 175, "Keystone", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT },
|
||||
}
|
||||
};
|
||||
|
||||
keyboard_keymap_overlay_values g814jv_keyboard_layout
|
||||
{
|
||||
KEYBOARD_SIZE_FULL,
|
||||
{
|
||||
aura_core_laptop_18_values,
|
||||
{
|
||||
/* Add more regional layout fixes here */
|
||||
}
|
||||
},
|
||||
{
|
||||
/*------------------------------------------------------------------------------------------------------------------------------------*\
|
||||
| Edit Keys |
|
||||
| Zone, Row, Column, Value, Key, Alternate Name, OpCode, |
|
||||
\*-------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
{ 0, 0, 2, 2, KEY_EN_MEDIA_VOLUME_DOWN, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_ROW, }, // Insert Row and add Volume Down
|
||||
{ 0, 0, 3, 3, KEY_EN_MEDIA_VOLUME_UP, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Volume Up
|
||||
{ 0, 0, 4, 4, KEY_EN_MEDIA_MUTE, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Mute
|
||||
{ 0, 0, 5, 5, "Key: Fan", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert "Fan" key
|
||||
{ 0, 0, 6, 6, "Key: ROG", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert "ROG" key
|
||||
{ 0, 6, 8, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove part of Spacebar
|
||||
{ 0, 6, 8, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove part of Spacebar
|
||||
{ 0, 6, 1, 127, KEY_EN_LEFT_FUNCTION, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Left Fuction
|
||||
{ 0, 6, 10, 136, KEY_EN_PRINT_SCREEN, KEY_EN_UNUSED, KEYBOARD_OPCODE_SWAP_ONLY, }, // Replace Right Fuction with PrtSc
|
||||
{ 0, 6, 11, 0, KEY_EN_RIGHT_WINDOWS, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Remove Right Win Key
|
||||
{ 0, 1, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
{ 0, 1, 14, 38, KEY_EN_DELETE, KEY_EN_UNUSED, KEYBOARD_OPCODE_SWAP_ONLY, }, // Insert a Delete key
|
||||
{ 0, 1, 16, 40, KEY_EN_PRINT_SCREEN, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert a Print Screen key
|
||||
{ 0, 1, 17, 41, KEY_EN_HOME, KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert a Home key
|
||||
{ 0, 2, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
{ 0, 2, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
{ 0, 2, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
{ 0, 3, 13, 76, KEY_EN_ANSI_BACK_SLASH, KEY_EN_UNUSED, KEYBOARD_OPCODE_SWAP_ONLY, }, // Force ANSI | even on ISO layouts
|
||||
{ 0, 3, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
{ 0, 3, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, }, // Numpad gap
|
||||
{ 0, 3, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
{ 0, 4, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
{ 0, 4, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
{ 0, 4, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
{ 0, 5, 12, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
{ 0, 5, 13, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
{ 0, 5, 14, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
{ 0, 6, 15, 0, KEY_EN_UNUSED, KEY_EN_UNUSED, KEYBOARD_OPCODE_REMOVE_SHIFT_LEFT, },
|
||||
}
|
||||
};
|
||||
|
||||
keyboard_keymap_overlay_values g814jv_lightbar_layout
|
||||
{
|
||||
KEYBOARD_SIZE_EMPTY,
|
||||
{
|
||||
{ /* Values not set in empty keyboard */ },
|
||||
{
|
||||
/* Add more regional layout fixes here */
|
||||
}
|
||||
},
|
||||
{
|
||||
/*-------------------------------------------------------------------------------------------------------------------------------------*\
|
||||
| Edit Keys |
|
||||
| Zone, Row, Column, Value, Key, Alternate Name, OpCode, |
|
||||
\*-------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
{ 0, 0, 0, 173, "Lightbar L1", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Lightbar L1
|
||||
{ 0, 0, 1, 172, "Lightbar L2", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Lightbar L2
|
||||
{ 0, 0, 2, 170, "Lightbar R2", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Lightbar R2
|
||||
{ 0, 0, 3, 169, "Lightbar R1", KEY_EN_UNUSED, KEYBOARD_OPCODE_INSERT_SHIFT_RIGHT, }, // Insert Lightbar R2
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/*-------------------------------------------------------------------------*\
|
||||
| AURA CORE LAPTOP DEVICES |
|
||||
\*-------------------------------------------------------------------------*/
|
||||
|
||||
/*-------------------------------------------------------------*\
|
||||
| ASUS ROG Strix SCAR 15 G533ZM |
|
||||
| |
|
||||
| Zone "Keyboard" |
|
||||
| Matrix |
|
||||
| 7 Rows, 16 Columns |
|
||||
\*-------------------------------------------------------------*/
|
||||
static const aura_core_laptop_zone g533zm_zone =
|
||||
{
|
||||
ZONE_EN_KEYBOARD,
|
||||
&g533zm_layout
|
||||
};
|
||||
|
||||
static const aura_core_laptop_device g533zm_device =
|
||||
{
|
||||
"G533ZM",
|
||||
{
|
||||
&g533zm_zone,
|
||||
nullptr,
|
||||
nullptr,
|
||||
nullptr,
|
||||
nullptr,
|
||||
nullptr
|
||||
}
|
||||
};
|
||||
|
||||
/*-------------------------------------------------------------*\
|
||||
| ASUS ROG Strix SCAR 15 G533ZW |
|
||||
| |
|
||||
| Zone "Keyboard" |
|
||||
| Matrix |
|
||||
| 7 Rows, 16 Columns |
|
||||
\*-------------------------------------------------------------*/
|
||||
static const aura_core_laptop_zone g533zw_lid_zone =
|
||||
{
|
||||
"Lid",
|
||||
&g533zw_lid_layout
|
||||
};
|
||||
|
||||
static const aura_core_laptop_zone g533zw_kb_zone =
|
||||
{
|
||||
ZONE_EN_KEYBOARD,
|
||||
&g533zw_layout
|
||||
};
|
||||
|
||||
static const aura_core_laptop_zone g533zw_lightbar_zone =
|
||||
{
|
||||
"Lightbar",
|
||||
&g533zw_lightbar_layout
|
||||
};
|
||||
|
||||
static const aura_core_laptop_device g533zw_device =
|
||||
{
|
||||
"G533ZW",
|
||||
{
|
||||
&g533zw_kb_zone,
|
||||
&g533zw_lid_zone,
|
||||
&g533zw_lightbar_zone,
|
||||
nullptr,
|
||||
nullptr,
|
||||
nullptr
|
||||
}
|
||||
};
|
||||
|
||||
/*-------------------------------------------------------------*\
|
||||
| ASUS ROG Strix SCAR 16 G614JZ |
|
||||
| |
|
||||
| Zone "Keyboard" |
|
||||
| Matrix |
|
||||
| 6 Rows, 19 Columns |
|
||||
\*-------------------------------------------------------------*/
|
||||
static const aura_core_laptop_zone g614jz_keyboard_zone =
|
||||
{
|
||||
ZONE_EN_KEYBOARD,
|
||||
&g614jz_keyboard_layout
|
||||
};
|
||||
static const aura_core_laptop_zone g614jz_lightbar_zone =
|
||||
{
|
||||
"Lightbar",
|
||||
&g614jz_lightbar_layout
|
||||
};
|
||||
|
||||
|
||||
static const aura_core_laptop_device g614jz_device =
|
||||
{
|
||||
"G614JZ",
|
||||
{
|
||||
&g614jz_keyboard_zone,
|
||||
&g614jz_lightbar_zone,
|
||||
nullptr,
|
||||
nullptr,
|
||||
nullptr,
|
||||
nullptr
|
||||
}
|
||||
};
|
||||
|
||||
/*-------------------------------------------------------------*\
|
||||
| ASUS ROG Strix SCAR G713RW |
|
||||
| |
|
||||
| Zone "Keyboard" |
|
||||
| Matrix |
|
||||
| 7 Rows, 20 Columns |
|
||||
\*-------------------------------------------------------------*/
|
||||
static const aura_core_laptop_zone g713rw_keyboard_zone =
|
||||
{
|
||||
ZONE_EN_KEYBOARD,
|
||||
&g713rw_keyboard_layout
|
||||
};
|
||||
|
||||
static const aura_core_laptop_zone g713rw_lightbar_zone =
|
||||
{
|
||||
"Lightbar",
|
||||
&g713rw_lightbar_layout
|
||||
};
|
||||
|
||||
static const aura_core_laptop_device g713rw_device =
|
||||
{
|
||||
"G713RW",
|
||||
{
|
||||
&g713rw_keyboard_zone,
|
||||
&g713rw_lightbar_zone,
|
||||
nullptr,
|
||||
nullptr,
|
||||
nullptr,
|
||||
nullptr
|
||||
}
|
||||
};
|
||||
|
||||
/*-------------------------------------------------------------*\
|
||||
| ASUS ROG Strix G17 G733QR |
|
||||
| |
|
||||
| Zones: |
|
||||
| Zone "Keyboard" |
|
||||
| Matrix |
|
||||
| 7 Rows, 19 Columns |
|
||||
\*-------------------------------------------------------------*/
|
||||
static const aura_core_laptop_zone g733qr_keyboard_zone =
|
||||
{
|
||||
ZONE_EN_KEYBOARD,
|
||||
&g733qr_keyboard_layout
|
||||
};
|
||||
|
||||
static const aura_core_laptop_zone g733qr_lid_zone =
|
||||
{
|
||||
"Lid",
|
||||
&g733qr_lid_layout
|
||||
};
|
||||
|
||||
static const aura_core_laptop_zone g733qr_lightbar_zone =
|
||||
{
|
||||
"Lightbar",
|
||||
&g733qr_lightbar_layout
|
||||
};
|
||||
|
||||
static const aura_core_laptop_zone g733qr_keystone_zone =
|
||||
{
|
||||
"Keystone",
|
||||
&g733qr_keystone_layout
|
||||
};
|
||||
|
||||
static const aura_core_laptop_device g733qr_device =
|
||||
{
|
||||
"G733QR",
|
||||
{
|
||||
&g733qr_keyboard_zone,
|
||||
&g733qr_lid_zone,
|
||||
&g733qr_lightbar_zone,
|
||||
&g733qr_keystone_zone,
|
||||
nullptr,
|
||||
nullptr
|
||||
}
|
||||
};
|
||||
|
||||
/*-------------------------------------------------------------*\
|
||||
| ASUS ROG Strix G18 (G814JV) |
|
||||
| |
|
||||
| Zone "Keyboard" |
|
||||
| Matrix |
|
||||
| 7 Rows, 16 Columns |
|
||||
\*-------------------------------------------------------------*/
|
||||
|
||||
static const aura_core_laptop_zone g814rw_keyboard_zone =
|
||||
{
|
||||
ZONE_EN_KEYBOARD,
|
||||
&g814jv_keyboard_layout
|
||||
};
|
||||
|
||||
static const aura_core_laptop_zone g814jv_lightbar_zone =
|
||||
{
|
||||
"Lightbar",
|
||||
&g814jv_lightbar_layout
|
||||
};
|
||||
|
||||
static const aura_core_laptop_device g814jv_device =
|
||||
{
|
||||
"G814JV",
|
||||
{
|
||||
&g814rw_keyboard_zone,
|
||||
&g814jv_lightbar_zone,
|
||||
nullptr,
|
||||
nullptr,
|
||||
nullptr,
|
||||
nullptr
|
||||
}
|
||||
};
|
||||
|
||||
/*-------------------------------------------------------------------------*\
|
||||
| DEVICE MASTER LIST |
|
||||
\*-------------------------------------------------------------------------*/
|
||||
const aura_core_laptop_device* aura_core_laptop_device_list_data[] =
|
||||
{
|
||||
/*-----------------------------------------------------------------*\
|
||||
| KEYBOARDS |
|
||||
\*-----------------------------------------------------------------*/
|
||||
&g533zm_device,
|
||||
&g533zw_device,
|
||||
&g614jz_device,
|
||||
&g713rw_device,
|
||||
&g733qr_device,
|
||||
&g814jv_device,
|
||||
};
|
||||
|
||||
const unsigned int AURA_CORE_LAPTOP_DEVICE_COUNT = (sizeof(aura_core_laptop_device_list_data) / sizeof(aura_core_laptop_device_list_data[ 0 ]));
|
||||
const aura_core_laptop_device** aura_core_laptop_device_list = aura_core_laptop_device_list_data;
|
||||
+50
@@ -0,0 +1,50 @@
|
||||
#pragma once
|
||||
|
||||
#include <string>
|
||||
#include <vector>
|
||||
#include "RGBController.h"
|
||||
#include "RGBControllerKeyNames.h"
|
||||
#include "KeyboardLayoutManager.h"
|
||||
|
||||
#define AURA_CORE_LAPTOP_ZONES_MAX 6
|
||||
|
||||
enum aura_core_kb_layout
|
||||
{
|
||||
AURA_CORE_LAPTOP_KB_LAYOUT_ANSI = 0x01, /* US ANSI Layout */
|
||||
AURA_CORE_LAPTOP_KB_LAYOUT_ISO = 0x02, /* EURO ISO Layout */
|
||||
AURA_CORE_LAPTOP_KB_LAYOUT_ABNT = 0x03, /* Brazilian Layout */
|
||||
AURA_CORE_LAPTOP_KB_LAYOUT_JIS = 0x04, /* Japanese Layout */
|
||||
};
|
||||
|
||||
typedef struct
|
||||
{
|
||||
std::string name;
|
||||
keyboard_keymap_overlay_values* layout_new;
|
||||
} aura_core_laptop_zone;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
uint8_t zone;
|
||||
uint8_t row;
|
||||
uint8_t col;
|
||||
uint8_t index;
|
||||
const char* name;
|
||||
} aura_core_laptop_led;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
std::string dmi_name;
|
||||
const aura_core_laptop_zone* zones[AURA_CORE_LAPTOP_ZONES_MAX];
|
||||
} aura_core_laptop_device;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Aura Core Laptop Protocol Keyboards |
|
||||
\*-----------------------------------------------------*/
|
||||
#define AURA_STRIX_SCAR_15_PID 0x19B6
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| These constant values are defined in |
|
||||
| AsusAuraCoreLaptopDevices.cpp |
|
||||
\*-----------------------------------------------------*/
|
||||
extern const unsigned int AURA_CORE_LAPTOP_DEVICE_COUNT;
|
||||
extern const aura_core_laptop_device** aura_core_laptop_device_list;
|
||||
+444
@@ -0,0 +1,444 @@
|
||||
/*---------------------------------------------------------*\
|
||||
| RGBController_AsusAuraCoreLaptop.cpp |
|
||||
| |
|
||||
| RGBController for ASUS ROG Aura Core Laptop |
|
||||
| |
|
||||
| Chris M (Dr_No) 28 Jul 2022 |
|
||||
| |
|
||||
| This file is part of the OpenRGB project |
|
||||
| SPDX-License-Identifier: GPL-2.0-or-later |
|
||||
\*---------------------------------------------------------*/
|
||||
|
||||
#include "RGBController_AsusAuraCoreLaptop.h"
|
||||
|
||||
/**------------------------------------------------------------------*\
|
||||
@name AsusAuraCoreLaptop
|
||||
@category DEVICE_TYPE_KEYBOARD
|
||||
@type USB
|
||||
@save :x:
|
||||
@direct :white_check_mark:
|
||||
@effects :white_check_mark:
|
||||
@detectors DetectAsusAuraCoreLaptopControllers
|
||||
@comment Power profiles for this controller are set to `On` for all power
|
||||
state and scan be adjusted in the JSON config file.
|
||||
|
||||
For each zone available LEDs can be set as `On = true` or `Off = false` when
|
||||
* Booting
|
||||
* Awake (Normal Usage)
|
||||
* Sleeping
|
||||
* Shutdown / Power Off
|
||||
|
||||
MatrixMaps can be found in ArmouryCrate (it needs a chance to download device data)
|
||||
Default path is:
|
||||
C:\ProgramData\ASUS\ROG Live Service\DeviceContent\<Model name>\<Model name>.csv
|
||||
(Model name is the code like G814JV - can be found in the error in logs)
|
||||
\*-------------------------------------------------------------------*/
|
||||
|
||||
RGBController_AsusAuraCoreLaptop::RGBController_AsusAuraCoreLaptop(AsusAuraCoreLaptopController *controller_ptr)
|
||||
{
|
||||
controller = controller_ptr;
|
||||
const aura_core_laptop_device* aura_dev = controller->GetDeviceData();
|
||||
|
||||
name = aura_dev->dmi_name;
|
||||
vendor = "Asus";
|
||||
type = DEVICE_TYPE_LAPTOP;
|
||||
description = controller->GetDeviceDescription();
|
||||
serial = controller->GetSerial();
|
||||
location = controller->GetLocation();
|
||||
|
||||
mode Direct;
|
||||
Direct.name = "Direct";
|
||||
Direct.value = ASUSAURACORELAPTOP_MODE_DIRECT;
|
||||
Direct.flags = MODE_FLAG_HAS_PER_LED_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
|
||||
Direct.brightness_min = ASUSAURACORELAPTOP_BRIGHTNESS_MIN;
|
||||
Direct.brightness_max = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
Direct.brightness = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
Direct.color_mode = MODE_COLORS_PER_LED;
|
||||
modes.push_back(Direct);
|
||||
|
||||
mode Static;
|
||||
Static.name = "Static";
|
||||
Static.value = ASUSAURACORELAPTOP_MODE_STATIC;
|
||||
Static.flags = MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
|
||||
Static.colors_min = 1;
|
||||
Static.colors_max = 1;
|
||||
Static.colors.resize(Static.colors_max);
|
||||
Static.brightness_min = ASUSAURACORELAPTOP_BRIGHTNESS_MIN;
|
||||
Static.brightness_max = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
Static.brightness = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
Static.speed_min = ASUSAURACORELAPTOP_SPEED_SLOWEST;
|
||||
Static.speed_max = ASUSAURACORELAPTOP_SPEED_FASTEST;
|
||||
Static.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Static.speed = ASUSAURACORELAPTOP_SPEED_NORMAL;
|
||||
modes.push_back(Static);
|
||||
|
||||
mode Breathing;
|
||||
Breathing.name = "Breathing";
|
||||
Breathing.value = ASUSAURACORELAPTOP_MODE_BREATHING;
|
||||
Breathing.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
|
||||
Breathing.colors_min = 1;
|
||||
Breathing.colors_max = 2;
|
||||
Breathing.colors.resize(Breathing.colors_min);
|
||||
Breathing.brightness_min = ASUSAURACORELAPTOP_BRIGHTNESS_MIN;
|
||||
Breathing.brightness_max = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
Breathing.brightness = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
Breathing.speed_min = ASUSAURACORELAPTOP_SPEED_SLOWEST;
|
||||
Breathing.speed_max = ASUSAURACORELAPTOP_SPEED_FASTEST;
|
||||
Breathing.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Breathing.speed = ASUSAURACORELAPTOP_SPEED_NORMAL;
|
||||
modes.push_back(Breathing);
|
||||
|
||||
mode Flashing;
|
||||
Flashing.name = "Flashing";
|
||||
Flashing.value = ASUSAURACORELAPTOP_MODE_FLASHING;
|
||||
Flashing.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
|
||||
Flashing.colors_min = 1;
|
||||
Flashing.colors_max = 1;
|
||||
Flashing.colors.resize(Flashing.colors_max);
|
||||
Flashing.brightness_min = ASUSAURACORELAPTOP_BRIGHTNESS_MIN;
|
||||
Flashing.brightness_max = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
Flashing.brightness = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
Flashing.speed_min = ASUSAURACORELAPTOP_SPEED_SLOWEST;
|
||||
Flashing.speed_max = ASUSAURACORELAPTOP_SPEED_FASTEST;
|
||||
Flashing.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Flashing.speed = ASUSAURACORELAPTOP_SPEED_NORMAL;
|
||||
modes.push_back(Flashing);
|
||||
|
||||
mode Spectrum;
|
||||
Spectrum.name = "Spectrum Cycle";
|
||||
Spectrum.value = ASUSAURACORELAPTOP_MODE_SPECTRUM;
|
||||
Spectrum.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_BRIGHTNESS;
|
||||
Spectrum.brightness_min = ASUSAURACORELAPTOP_BRIGHTNESS_MIN;
|
||||
Spectrum.brightness_max = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
Spectrum.brightness = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
Spectrum.speed_min = ASUSAURACORELAPTOP_SPEED_SLOWEST;
|
||||
Spectrum.speed_max = ASUSAURACORELAPTOP_SPEED_FASTEST;
|
||||
Spectrum.color_mode = MODE_COLORS_NONE;
|
||||
Spectrum.speed = ASUSAURACORELAPTOP_SPEED_NORMAL;
|
||||
modes.push_back(Spectrum);
|
||||
|
||||
mode Rainbow;
|
||||
Rainbow.name = "Rainbow Wave";
|
||||
Rainbow.value = ASUSAURACORELAPTOP_MODE_RAINBOW;
|
||||
Rainbow.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_DIRECTION_LR | MODE_FLAG_HAS_DIRECTION_UD;
|
||||
Rainbow.brightness_min = ASUSAURACORELAPTOP_BRIGHTNESS_MIN;
|
||||
Rainbow.brightness_max = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
Rainbow.brightness = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
Rainbow.speed_min = ASUSAURACORELAPTOP_SPEED_SLOWEST;
|
||||
Rainbow.speed_max = ASUSAURACORELAPTOP_SPEED_FASTEST;
|
||||
Rainbow.color_mode = MODE_COLORS_NONE;
|
||||
Rainbow.speed = ASUSAURACORELAPTOP_SPEED_NORMAL;
|
||||
modes.push_back(Rainbow);
|
||||
|
||||
mode Starry;
|
||||
Starry.name = "Starry Night";
|
||||
Starry.value = ASUSAURACORELAPTOP_MODE_STARRY_NIGHT;
|
||||
Starry.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
|
||||
Starry.colors_min = 1;
|
||||
Starry.colors_max = 2;
|
||||
Starry.colors.resize(Starry.colors_min);
|
||||
Starry.brightness_min = ASUSAURACORELAPTOP_BRIGHTNESS_MIN;
|
||||
Starry.brightness_max = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
Starry.brightness = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
Starry.speed_min = ASUSAURACORELAPTOP_SPEED_SLOWEST;
|
||||
Starry.speed_max = ASUSAURACORELAPTOP_SPEED_FASTEST;
|
||||
Starry.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Starry.speed = ASUSAURACORELAPTOP_SPEED_NORMAL;
|
||||
modes.push_back(Starry);
|
||||
|
||||
mode Rain;
|
||||
Rain.name = "Rain";
|
||||
Rain.value = ASUSAURACORELAPTOP_MODE_RAIN;
|
||||
Rain.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_BRIGHTNESS;
|
||||
Rain.brightness_min = ASUSAURACORELAPTOP_BRIGHTNESS_MIN;
|
||||
Rain.brightness_max = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
Rain.brightness = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
Rain.speed_min = ASUSAURACORELAPTOP_SPEED_SLOWEST;
|
||||
Rain.speed_max = ASUSAURACORELAPTOP_SPEED_FASTEST;
|
||||
Rain.color_mode = MODE_COLORS_NONE;
|
||||
Rain.speed = ASUSAURACORELAPTOP_SPEED_NORMAL;
|
||||
modes.push_back(Rain);
|
||||
|
||||
mode ReactFade;
|
||||
ReactFade.name = "Reactive - Fade";
|
||||
ReactFade.value = ASUSAURACORELAPTOP_MODE_REACT_FADE;
|
||||
ReactFade.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
|
||||
ReactFade.colors_min = 1;
|
||||
ReactFade.colors_max = 1;
|
||||
ReactFade.colors.resize(ReactFade.colors_max);
|
||||
ReactFade.brightness_min = ASUSAURACORELAPTOP_BRIGHTNESS_MIN;
|
||||
ReactFade.brightness_max = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
ReactFade.brightness = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
ReactFade.speed_min = ASUSAURACORELAPTOP_SPEED_SLOWEST;
|
||||
ReactFade.speed_max = ASUSAURACORELAPTOP_SPEED_FASTEST;
|
||||
ReactFade.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
ReactFade.speed = ASUSAURACORELAPTOP_SPEED_NORMAL;
|
||||
modes.push_back(ReactFade);
|
||||
|
||||
mode ReactLaser;
|
||||
ReactLaser.name = "Reactive - Laser";
|
||||
ReactLaser.value = ASUSAURACORELAPTOP_MODE_REACT_LASER;
|
||||
ReactLaser.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
|
||||
ReactLaser.colors_min = 1;
|
||||
ReactLaser.colors_max = 1;
|
||||
ReactLaser.colors.resize(ReactLaser.colors_max);
|
||||
ReactLaser.brightness_min = ASUSAURACORELAPTOP_BRIGHTNESS_MIN;
|
||||
ReactLaser.brightness_max = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
ReactLaser.brightness = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
ReactLaser.speed_min = ASUSAURACORELAPTOP_SPEED_SLOWEST;
|
||||
ReactLaser.speed_max = ASUSAURACORELAPTOP_SPEED_FASTEST;
|
||||
ReactLaser.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
ReactLaser.speed = ASUSAURACORELAPTOP_SPEED_NORMAL;
|
||||
modes.push_back(ReactLaser);
|
||||
|
||||
mode ReactRipple;
|
||||
ReactRipple.name = "Reactive - Ripple";
|
||||
ReactRipple.value = ASUSAURACORELAPTOP_MODE_REACT_RIPPLE;
|
||||
ReactRipple.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_RANDOM_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
|
||||
ReactRipple.colors_min = 1;
|
||||
ReactRipple.colors_max = 1;
|
||||
ReactRipple.colors.resize(ReactRipple.colors_max);
|
||||
ReactRipple.brightness_min = ASUSAURACORELAPTOP_BRIGHTNESS_MIN;
|
||||
ReactRipple.brightness_max = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
ReactRipple.brightness = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
ReactRipple.speed_min = ASUSAURACORELAPTOP_SPEED_SLOWEST;
|
||||
ReactRipple.speed_max = ASUSAURACORELAPTOP_SPEED_FASTEST;
|
||||
ReactRipple.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
ReactRipple.speed = ASUSAURACORELAPTOP_SPEED_NORMAL;
|
||||
modes.push_back(ReactRipple);
|
||||
|
||||
mode Comet;
|
||||
Comet.name = "Comet";
|
||||
Comet.value = ASUSAURACORELAPTOP_MODE_COMET;
|
||||
Comet.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_DIRECTION_LR;
|
||||
Comet.colors_min = 1;
|
||||
Comet.colors_max = 1;
|
||||
Comet.colors.resize(Comet.colors_max);
|
||||
Comet.brightness_min = ASUSAURACORELAPTOP_BRIGHTNESS_MIN;
|
||||
Comet.brightness_max = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
Comet.brightness = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
Comet.speed_min = ASUSAURACORELAPTOP_SPEED_SLOWEST;
|
||||
Comet.speed_max = ASUSAURACORELAPTOP_SPEED_FASTEST;
|
||||
Comet.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Comet.speed = ASUSAURACORELAPTOP_SPEED_NORMAL;
|
||||
modes.push_back(Comet);
|
||||
|
||||
mode FlashNDash;
|
||||
FlashNDash.name = "Flash N Dash";
|
||||
FlashNDash.value = ASUSAURACORELAPTOP_MODE_FLASHNDASH;
|
||||
FlashNDash.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_BRIGHTNESS | MODE_FLAG_HAS_DIRECTION_LR;
|
||||
FlashNDash.colors_min = 1;
|
||||
FlashNDash.colors_max = 1;
|
||||
FlashNDash.colors.resize(FlashNDash.colors_max);
|
||||
FlashNDash.brightness_min = ASUSAURACORELAPTOP_BRIGHTNESS_MIN;
|
||||
FlashNDash.brightness_max = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
FlashNDash.brightness = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
FlashNDash.speed_min = ASUSAURACORELAPTOP_SPEED_SLOWEST;
|
||||
FlashNDash.speed_max = ASUSAURACORELAPTOP_SPEED_FASTEST;
|
||||
FlashNDash.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
FlashNDash.speed = ASUSAURACORELAPTOP_SPEED_NORMAL;
|
||||
modes.push_back(FlashNDash);
|
||||
|
||||
mode Keystone;
|
||||
Keystone.name = "Keystone";
|
||||
Keystone.value = ASUSAURACORELAPTOP_MODE_KEYSTONE;
|
||||
Keystone.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR | MODE_FLAG_HAS_BRIGHTNESS;
|
||||
Keystone.colors_min = 1;
|
||||
Keystone.colors_max = 1;
|
||||
Keystone.colors.resize(Keystone.colors_max);
|
||||
Keystone.brightness_min = ASUSAURACORELAPTOP_BRIGHTNESS_MIN;
|
||||
Keystone.brightness_max = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
Keystone.brightness = ASUSAURACORELAPTOP_BRIGHTNESS_MAX;
|
||||
Keystone.speed_min = ASUSAURACORELAPTOP_SPEED_SLOWEST;
|
||||
Keystone.speed_max = ASUSAURACORELAPTOP_SPEED_FASTEST;
|
||||
Keystone.color_mode = MODE_COLORS_MODE_SPECIFIC;
|
||||
Keystone.speed = ASUSAURACORELAPTOP_SPEED_NORMAL;
|
||||
modes.push_back(Keystone);
|
||||
|
||||
mode Off;
|
||||
Off.name = "Off";
|
||||
Off.value = ASUSAURACORELAPTOP_MODE_OFF;
|
||||
Off.color_mode = MODE_COLORS_NONE;
|
||||
modes.push_back(Off);
|
||||
|
||||
SetupZones();
|
||||
|
||||
SetMode(active_mode);
|
||||
}
|
||||
|
||||
RGBController_AsusAuraCoreLaptop::~RGBController_AsusAuraCoreLaptop()
|
||||
{
|
||||
delete controller;
|
||||
}
|
||||
|
||||
void RGBController_AsusAuraCoreLaptop::SetupZones()
|
||||
{
|
||||
std::string physical_size;
|
||||
KEYBOARD_LAYOUT new_layout;
|
||||
unsigned int max_led_value = 0;
|
||||
|
||||
const aura_core_laptop_device* aura_dev = controller->GetDeviceData();
|
||||
unsigned int layout = controller->GetKeyboardLayout();
|
||||
|
||||
switch(layout)
|
||||
{
|
||||
case ASUSAURACORELAPTOP_LAYOUT_ISO:
|
||||
new_layout = KEYBOARD_LAYOUT_ISO_QWERTY;
|
||||
break;
|
||||
|
||||
case ASUSAURACORELAPTOP_LAYOUT_ANSI:
|
||||
default:
|
||||
new_layout = KEYBOARD_LAYOUT_ANSI_QWERTY;
|
||||
break;
|
||||
}
|
||||
LOG_DEBUG("[%s] layout set as %d", description.c_str(), new_layout);
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Fill in zones from the device data |
|
||||
\*---------------------------------------------------------*/
|
||||
for(size_t i = 0; i < AURA_CORE_LAPTOP_ZONES_MAX; i++)
|
||||
{
|
||||
LOG_DEBUG("[%s] setting up zone %d", description.c_str(), i);
|
||||
|
||||
if(aura_dev->zones[i] == NULL)
|
||||
{
|
||||
break;
|
||||
}
|
||||
else
|
||||
{
|
||||
zone new_zone;
|
||||
|
||||
new_zone.name = aura_dev->zones[i]->name;
|
||||
|
||||
if(aura_dev->zones[i]->layout_new != NULL)
|
||||
{
|
||||
KeyboardLayoutManager new_kb(new_layout,
|
||||
aura_dev->zones[i]->layout_new->base_size,
|
||||
aura_dev->zones[i]->layout_new->key_values);
|
||||
|
||||
if(aura_dev->zones[i]->layout_new->base_size != KEYBOARD_SIZE_EMPTY ||
|
||||
aura_dev->zones[i]->layout_new->edit_keys.size() > 0)
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| Minor adjustments to keyboard layout |
|
||||
\*---------------------------------------------------------*/
|
||||
keyboard_keymap_overlay_values* temp = aura_dev->zones[i]->layout_new;
|
||||
new_kb.ChangeKeys(*temp);
|
||||
|
||||
if(new_kb.GetRowCount() == 1 || new_kb.GetColumnCount() == 1)
|
||||
{
|
||||
if(new_kb.GetKeyCount() == 1)
|
||||
{
|
||||
new_zone.type = ZONE_TYPE_SINGLE;
|
||||
}
|
||||
else
|
||||
{
|
||||
new_zone.type = ZONE_TYPE_LINEAR;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
new_zone.type = ZONE_TYPE_MATRIX;
|
||||
matrix_map_type * new_map = new matrix_map_type;
|
||||
new_zone.matrix_map = new_map;
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Trusting the layout handed to the KLM is correct use the |
|
||||
| row & column counts to set the matrix height & width |
|
||||
\*---------------------------------------------------------*/
|
||||
new_map->height = new_kb.GetRowCount();
|
||||
new_map->width = new_kb.GetColumnCount();
|
||||
new_map->map = new unsigned int[new_map->height * new_map->width];
|
||||
|
||||
new_kb.GetKeyMap(new_map->map, KEYBOARD_MAP_FILL_TYPE_COUNT);
|
||||
}
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Create LEDs for the Matrix zone |
|
||||
| Place keys in the layout to populate the matrix |
|
||||
\*---------------------------------------------------------*/
|
||||
new_zone.leds_count = new_kb.GetKeyCount();
|
||||
for(unsigned int led_idx = 0; led_idx < new_zone.leds_count; led_idx++)
|
||||
{
|
||||
led new_led;
|
||||
|
||||
new_led.name = new_kb.GetKeyNameAt(led_idx);
|
||||
new_led.value = new_kb.GetKeyValueAt(led_idx);
|
||||
max_led_value = std::max(max_led_value, new_led.value);
|
||||
leds.push_back(new_led);
|
||||
}
|
||||
}
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Add 1 the max_led_value to account for the 0th index |
|
||||
\*---------------------------------------------------------*/
|
||||
max_led_value++;
|
||||
}
|
||||
|
||||
LOG_DEBUG("[%s] Creating a %s zone: %s with %d LEDs", name.c_str(),
|
||||
((new_zone.type == ZONE_TYPE_MATRIX) ? "matrix": "linear"),
|
||||
new_zone.name.c_str(), new_zone.leds_count);
|
||||
new_zone.leds_min = new_zone.leds_count;
|
||||
new_zone.leds_max = new_zone.leds_count;
|
||||
zones.push_back(new_zone);
|
||||
}
|
||||
}
|
||||
|
||||
SetupColors();
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Create a buffer map of pointers which contains the |
|
||||
| layout order of colors the device expects. |
|
||||
\*---------------------------------------------------------*/
|
||||
buffer_map.resize(max_led_value, &null_color);
|
||||
|
||||
for(size_t led_idx = 0; led_idx < leds.size(); led_idx++)
|
||||
{
|
||||
buffer_map[leds[led_idx].value] = &colors[led_idx];
|
||||
}
|
||||
}
|
||||
|
||||
void RGBController_AsusAuraCoreLaptop::ResizeZone(int /*zone*/, int /*new_size*/)
|
||||
{
|
||||
/*---------------------------------------------------------*\
|
||||
| This device does not support resizing zones |
|
||||
\*---------------------------------------------------------*/
|
||||
}
|
||||
|
||||
void RGBController_AsusAuraCoreLaptop::DeviceUpdateLEDs()
|
||||
{
|
||||
for(size_t i = 85; i < leds.size(); i++)
|
||||
{
|
||||
LOG_DEBUG("[%s] Setting %s @ LED index %d and buffer index %d to R: %02X G: %02X B: %02X",
|
||||
name.c_str(),
|
||||
leds[i].name.c_str(),
|
||||
i,
|
||||
leds[i].value,
|
||||
RGBGetRValue(colors[i]),
|
||||
RGBGetGValue(colors[i]),
|
||||
RGBGetBValue(colors[i]));
|
||||
}
|
||||
|
||||
controller->SetLedsDirect(buffer_map);
|
||||
}
|
||||
|
||||
void RGBController_AsusAuraCoreLaptop::UpdateZoneLEDs(int /*zone*/)
|
||||
{
|
||||
controller->SetLedsDirect(buffer_map);
|
||||
}
|
||||
|
||||
void RGBController_AsusAuraCoreLaptop::UpdateSingleLED(int /*led*/)
|
||||
{
|
||||
controller->SetLedsDirect(buffer_map);
|
||||
}
|
||||
|
||||
void RGBController_AsusAuraCoreLaptop::DeviceUpdateMode()
|
||||
{
|
||||
mode set_mode = modes[active_mode];
|
||||
|
||||
uint8_t random = (set_mode.color_mode == MODE_COLORS_RANDOM) ? 0xFF : 0;
|
||||
RGBColor color1 = (set_mode.colors.size() > 0) ? set_mode.colors[0] : 0;
|
||||
RGBColor color2 = (set_mode.colors.size() > 1) ? set_mode.colors[1] : 0;
|
||||
|
||||
controller->SetMode(set_mode.value, set_mode.speed, set_mode.brightness, color1, color2, random, set_mode.direction );
|
||||
}
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user