Initial commit
This commit is contained in:
2
.gitignore
vendored
Normal file
2
.gitignore
vendored
Normal file
@@ -0,0 +1,2 @@
|
|||||||
|
acer-rgb
|
||||||
|
rgb
|
||||||
34
Makefile
Normal file
34
Makefile
Normal file
@@ -0,0 +1,34 @@
|
|||||||
|
|
||||||
|
all:
|
||||||
|
|
||||||
|
rgb:
|
||||||
|
clang++ -std=c++23 ./rgb.cpp -o ./rgb
|
||||||
|
|
||||||
|
acer-rgb:
|
||||||
|
clang++ -std=c++23 ./acer-rgb.cpp -o ./acer-rgb
|
||||||
|
|
||||||
|
|
||||||
|
all-red: acer-rgb
|
||||||
|
sudo ./acer-rgb /dev/hidraw2 keyboard static --brightness 100 --rgb 255 0 0 --zone all
|
||||||
|
sudo ./acer-rgb /dev/hidraw2 lid static --brightness 100 --rgb 255 0 0 --zone all
|
||||||
|
sudo ./acer-rgb /dev/hidraw2 button static --brightness 100 --rgb 255 0 0 --zone all
|
||||||
|
|
||||||
|
all-green: acer-rgb
|
||||||
|
sudo ./acer-rgb /dev/hidraw2 keyboard static --brightness 100 --rgb 0 255 0 --zone all
|
||||||
|
sudo ./acer-rgb /dev/hidraw2 lid static --brightness 100 --rgb 0 255 0 --zone all
|
||||||
|
sudo ./acer-rgb /dev/hidraw2 button static --brightness 100 --rgb 0 255 0 --zone all
|
||||||
|
|
||||||
|
all-blue: acer-rgb
|
||||||
|
sudo ./acer-rgb /dev/hidraw2 keyboard static --brightness 100 --rgb 0 0 255 --zone all
|
||||||
|
sudo ./acer-rgb /dev/hidraw2 lid static --brightness 100 --rgb 0 0 255 --zone all
|
||||||
|
sudo ./acer-rgb /dev/hidraw2 button static --brightness 100 --rgb 0 0 255 --zone all
|
||||||
|
|
||||||
|
all-magenta: acer-rgb
|
||||||
|
sudo ./acer-rgb /dev/hidraw2 keyboard static --brightness 100 --rgb 255 0 255 --zone all
|
||||||
|
sudo ./acer-rgb /dev/hidraw2 lid static --brightness 100 --rgb 255 0 255 --zone all
|
||||||
|
sudo ./acer-rgb /dev/hidraw2 button static --brightness 100 --rgb 255 0 255 --zone all
|
||||||
|
|
||||||
|
all-cyan: acer-rgb
|
||||||
|
sudo ./acer-rgb /dev/hidraw2 keyboard static --brightness 100 --rgb 0 255 255 --zone all
|
||||||
|
sudo ./acer-rgb /dev/hidraw2 lid static --brightness 100 --rgb 0 255 255 --zone all
|
||||||
|
sudo ./acer-rgb /dev/hidraw2 button static --brightness 100 --rgb 0 255 255 --zone all
|
||||||
281
acer-rgb.cpp
Normal file
281
acer-rgb.cpp
Normal file
@@ -0,0 +1,281 @@
|
|||||||
|
#include <print>
|
||||||
|
#include <vector>
|
||||||
|
#include <unistd.h>
|
||||||
|
#include <fcntl.h>
|
||||||
|
#include <sys/ioctl.h>
|
||||||
|
#include <linux/hidraw.h>
|
||||||
|
#include <string>
|
||||||
|
#include <iostream>
|
||||||
|
#include <limits>
|
||||||
|
#include <cstdint>
|
||||||
|
#include <cstdlib>
|
||||||
|
|
||||||
|
#define RGB_FEATURE_ID 0xa4
|
||||||
|
|
||||||
|
#define KEYBOARD_RGB_ID 0x21
|
||||||
|
#define LID_RGB_ID 0x83
|
||||||
|
#define BUTTON_RGB_ID 0x65
|
||||||
|
|
||||||
|
#define RGB_EFFECT_STATIC 0x02
|
||||||
|
#define RGB_EFFECT_BREATHING 0x04
|
||||||
|
#define RGB_EFFECT_NEON 0x05
|
||||||
|
#define RGB_EFFECT_WAVE 0x07
|
||||||
|
#define RGB_EFFECT_RIPPLE 0x08
|
||||||
|
#define RGB_EFFECT_ZOOM 0x09
|
||||||
|
#define RGB_EFFECT_SNAKE 0x0a
|
||||||
|
#define RGB_EFFECT_DISCO 0x0b
|
||||||
|
#define RGB_EFFECT_SHIFTING 0xff
|
||||||
|
|
||||||
|
static int g_fd = -1;
|
||||||
|
|
||||||
|
static void usage(const char* prog) {
|
||||||
|
std::println(
|
||||||
|
"Usage:\n"
|
||||||
|
" sudo {0} <hidraw_path> <device> <effect> [options]\n\n"
|
||||||
|
"Devices:\n"
|
||||||
|
" keyboard | lid | button\n\n"
|
||||||
|
"Effects:\n"
|
||||||
|
" static | breathing | neon | wave | ripple | zoom | snake | disco | shifting\n\n"
|
||||||
|
"Options:\n"
|
||||||
|
" --brightness <0-100> (required)\n"
|
||||||
|
" --speed <0-9> (required for non-static effects)\n"
|
||||||
|
" --direction <none|right|left> (keyboard only; ignored for static/breathing)\n"
|
||||||
|
" --rgb <R> <G> <B> (required for static)\n"
|
||||||
|
" --zone <all|1|2|3|4> (keyboard only; default: all)\n\n"
|
||||||
|
"Examples:\n"
|
||||||
|
" sudo {0} /dev/hidraw2 keyboard static --brightness 80 --rgb 255 0 0 --zone all\n"
|
||||||
|
" sudo {0} /dev/hidraw2 keyboard wave --brightness 70 --speed 6 --direction right\n"
|
||||||
|
" sudo {0} /dev/hidraw2 lid breathing --brightness 60 --speed 5\n",
|
||||||
|
prog
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
static bool hidrawWrite(const std::vector<uint8_t>& bytes) {
|
||||||
|
for (uint8_t byte : bytes) {
|
||||||
|
std::print("0x{:0x} ", static_cast<uint32_t>(byte));
|
||||||
|
}
|
||||||
|
std::println(" <--- hidraw values");
|
||||||
|
|
||||||
|
int retval = ioctl(g_fd, HIDIOCSFEATURE(bytes.size()), bytes.data());
|
||||||
|
if (retval < 0) {
|
||||||
|
std::println("[ERR] FAILED TO WRITE TO HIDRAW DEVICE!");
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::println("Successfully wrote to hidraw file");
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
static bool streq(const std::string& a, const char* b) {
|
||||||
|
return a == b;
|
||||||
|
}
|
||||||
|
|
||||||
|
static bool parse_u8_int(const std::string& s, int minv, int maxv, uint8_t& out) {
|
||||||
|
char* end = nullptr;
|
||||||
|
long v = std::strtol(s.c_str(), &end, 10);
|
||||||
|
if (!end || *end != '\0') return false;
|
||||||
|
if (v < minv || v > maxv) return false;
|
||||||
|
out = static_cast<uint8_t>(v);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
static bool parse_device(const std::string& s, uint8_t& device, uint8_t& zone_default) {
|
||||||
|
if (streq(s, "keyboard")) { device = KEYBOARD_RGB_ID; zone_default = 0x0f; return true; }
|
||||||
|
if (streq(s, "lid")) { device = LID_RGB_ID; zone_default = 0x00; return true; }
|
||||||
|
if (streq(s, "button")) { device = BUTTON_RGB_ID; zone_default = 0x00; return true; }
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
static bool parse_effect(const std::string& s, uint8_t& effect) {
|
||||||
|
if (streq(s, "static")) { effect = RGB_EFFECT_STATIC; return true; }
|
||||||
|
if (streq(s, "breathing")) { effect = RGB_EFFECT_BREATHING; return true; }
|
||||||
|
if (streq(s, "neon")) { effect = RGB_EFFECT_NEON; return true; }
|
||||||
|
if (streq(s, "wave")) { effect = RGB_EFFECT_WAVE; return true; }
|
||||||
|
if (streq(s, "ripple")) { effect = RGB_EFFECT_RIPPLE; return true; }
|
||||||
|
if (streq(s, "zoom")) { effect = RGB_EFFECT_ZOOM; return true; }
|
||||||
|
if (streq(s, "snake")) { effect = RGB_EFFECT_SNAKE; return true; }
|
||||||
|
if (streq(s, "disco")) { effect = RGB_EFFECT_DISCO; return true; }
|
||||||
|
if (streq(s, "shifting")) { effect = RGB_EFFECT_SHIFTING; return true; }
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
static bool parse_direction(const std::string& s, uint8_t& dir) {
|
||||||
|
if (streq(s, "none")) { dir = 0; return true; }
|
||||||
|
if (streq(s, "right")) { dir = 1; return true; }
|
||||||
|
if (streq(s, "left")) { dir = 2; return true; }
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
static bool parse_zone(const std::string& s, uint8_t& zone) {
|
||||||
|
if (streq(s, "all")) { zone = 0x0f; return true; }
|
||||||
|
if (streq(s, "1")) { zone = 0x01; return true; }
|
||||||
|
if (streq(s, "2")) { zone = 0x02; return true; }
|
||||||
|
if (streq(s, "3")) { zone = 0x04; return true; }
|
||||||
|
if (streq(s, "4")) { zone = 0x08; return true; }
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
int main(int argc, char* argv[]) {
|
||||||
|
if (geteuid() != 0) {
|
||||||
|
std::println("[ERR] THIS APPLICATION MUST BE RUN AS ROOT!");
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (argc < 4) {
|
||||||
|
usage(argv[0]);
|
||||||
|
return 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::string hidraw_path = argv[1];
|
||||||
|
std::string device_str = argv[2];
|
||||||
|
std::string effect_str = argv[3];
|
||||||
|
|
||||||
|
uint8_t device = 0x00;
|
||||||
|
uint8_t zone = 0x00;
|
||||||
|
uint8_t effect = 0x00;
|
||||||
|
|
||||||
|
if (!parse_device(device_str, device, zone)) {
|
||||||
|
std::println("[ERR] Invalid device: {}", device_str);
|
||||||
|
usage(argv[0]);
|
||||||
|
return 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!parse_effect(effect_str, effect)) {
|
||||||
|
std::println("[ERR] Invalid effect: {}", effect_str);
|
||||||
|
usage(argv[0]);
|
||||||
|
return 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Defaults
|
||||||
|
uint8_t brightness = 0x00;
|
||||||
|
uint8_t speed = 0x00;
|
||||||
|
uint8_t direction = 0x00;
|
||||||
|
uint8_t r = 0x00, g = 0x00, b = 0x00;
|
||||||
|
|
||||||
|
bool brightness_set = false;
|
||||||
|
bool speed_set = false;
|
||||||
|
bool rgb_set = false;
|
||||||
|
bool zone_set = false;
|
||||||
|
bool direction_set = false;
|
||||||
|
|
||||||
|
// Parse options
|
||||||
|
for (int i = 4; i < argc; i++) {
|
||||||
|
std::string opt = argv[i];
|
||||||
|
|
||||||
|
auto need_arg = [&](int n) -> bool {
|
||||||
|
if (i + n >= argc) {
|
||||||
|
std::println("[ERR] Missing argument(s) for {}", opt);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
};
|
||||||
|
|
||||||
|
if (opt == "--brightness") {
|
||||||
|
if (!need_arg(1)) return 2;
|
||||||
|
if (!parse_u8_int(argv[++i], 0, 100, brightness)) {
|
||||||
|
std::println("[ERR] brightness must be 0-100");
|
||||||
|
return 2;
|
||||||
|
}
|
||||||
|
brightness_set = true;
|
||||||
|
} else if (opt == "--speed") {
|
||||||
|
if (!need_arg(1)) return 2;
|
||||||
|
if (!parse_u8_int(argv[++i], 0, 9, speed)) {
|
||||||
|
std::println("[ERR] speed must be 0-9");
|
||||||
|
return 2;
|
||||||
|
}
|
||||||
|
speed_set = true;
|
||||||
|
} else if (opt == "--direction") {
|
||||||
|
if (!need_arg(1)) return 2;
|
||||||
|
if (!parse_direction(argv[++i], direction)) {
|
||||||
|
std::println("[ERR] direction must be none|right|left");
|
||||||
|
return 2;
|
||||||
|
}
|
||||||
|
direction_set = true;
|
||||||
|
} else if (opt == "--zone") {
|
||||||
|
if (!need_arg(1)) return 2;
|
||||||
|
if (!parse_zone(argv[++i], zone)) {
|
||||||
|
std::println("[ERR] zone must be all|1|2|3|4");
|
||||||
|
return 2;
|
||||||
|
}
|
||||||
|
zone_set = true;
|
||||||
|
} else if (opt == "--rgb") {
|
||||||
|
if (!need_arg(3)) return 2;
|
||||||
|
uint8_t rr, gg, bb;
|
||||||
|
if (!parse_u8_int(argv[++i], 0, 255, rr) ||
|
||||||
|
!parse_u8_int(argv[++i], 0, 255, gg) ||
|
||||||
|
!parse_u8_int(argv[++i], 0, 255, bb)) {
|
||||||
|
std::println("[ERR] rgb values must be 0-255");
|
||||||
|
return 2;
|
||||||
|
}
|
||||||
|
r = rr; g = gg; b = bb;
|
||||||
|
rgb_set = true;
|
||||||
|
} else if (opt == "--help" || opt == "-h") {
|
||||||
|
usage(argv[0]);
|
||||||
|
return 0;
|
||||||
|
} else {
|
||||||
|
std::println("[ERR] Unknown option: {}", opt);
|
||||||
|
usage(argv[0]);
|
||||||
|
return 2;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Validate required combos
|
||||||
|
if (!brightness_set) {
|
||||||
|
std::println("[ERR] --brightness is required");
|
||||||
|
return 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (effect == RGB_EFFECT_STATIC) {
|
||||||
|
if (!rgb_set) {
|
||||||
|
std::println("[ERR] static requires --rgb R G B");
|
||||||
|
return 2;
|
||||||
|
}
|
||||||
|
// speed ignored for static
|
||||||
|
speed = 0;
|
||||||
|
} else {
|
||||||
|
if (!speed_set) {
|
||||||
|
std::println("[ERR] non-static effects require --speed 0-9");
|
||||||
|
return 2;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Only keyboard supports zone; for others force 0x00
|
||||||
|
if (device != KEYBOARD_RGB_ID) {
|
||||||
|
zone = 0x00;
|
||||||
|
} else {
|
||||||
|
if (!zone_set) zone = 0x0f; // default all
|
||||||
|
// direction only used for certain keyboard effects (like original)
|
||||||
|
if (effect == RGB_EFFECT_STATIC || effect == RGB_EFFECT_BREATHING) {
|
||||||
|
direction = 0;
|
||||||
|
} else {
|
||||||
|
// If user didn't set, keep default 0 (none)
|
||||||
|
(void)direction_set;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Open + identify
|
||||||
|
std::println("Using file: {}", hidraw_path);
|
||||||
|
g_fd = open(hidraw_path.c_str(), O_RDWR | O_NONBLOCK);
|
||||||
|
if (g_fd < 0) {
|
||||||
|
std::println("[ERR] FAILED TO OPEN HIDRAW DEVICE!");
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
char name[256];
|
||||||
|
int retval = ioctl(g_fd, HIDIOCGRAWNAME(256), name);
|
||||||
|
if (retval < 0) {
|
||||||
|
std::println("[ERR] FAILED TO GET HIDRAW DEVICE NAME!");
|
||||||
|
close(g_fd);
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
std::println("Device name: {}", name);
|
||||||
|
|
||||||
|
std::vector<uint8_t> hidraw_data = {
|
||||||
|
RGB_FEATURE_ID, device, effect, brightness, speed, direction, r, g, b, zone, 0x00
|
||||||
|
};
|
||||||
|
|
||||||
|
bool ok = hidrawWrite(hidraw_data);
|
||||||
|
close(g_fd);
|
||||||
|
|
||||||
|
return ok ? 0 : 1;
|
||||||
|
}
|
||||||
256
rgb.cpp
Normal file
256
rgb.cpp
Normal file
@@ -0,0 +1,256 @@
|
|||||||
|
#include <print>
|
||||||
|
#include <vector>
|
||||||
|
#include <unistd.h>
|
||||||
|
#include <fcntl.h>
|
||||||
|
#include <sys/ioctl.h>
|
||||||
|
#include <linux/hidraw.h>
|
||||||
|
#include <string>
|
||||||
|
#include <iostream>
|
||||||
|
|
||||||
|
#define RGB_FEATURE_ID 0xa4
|
||||||
|
|
||||||
|
#define KEYBOARD_RGB_ID 0x21
|
||||||
|
#define LID_RGB_ID 0x83
|
||||||
|
#define BUTTON_RGB_ID 0x65
|
||||||
|
|
||||||
|
#define RGB_EFFECT_STATIC 0x02
|
||||||
|
#define RGB_EFFECT_BREATHING 0x04
|
||||||
|
#define RGB_EFFECT_NEON 0x05
|
||||||
|
#define RGB_EFFECT_WAVE 0x07
|
||||||
|
#define RGB_EFFECT_RIPPLE 0x08
|
||||||
|
#define RGB_EFFECT_ZOOM 0x09
|
||||||
|
#define RGB_EFFECT_SNAKE 0x0a
|
||||||
|
#define RGB_EFFECT_DISCO 0x0b
|
||||||
|
#define RGB_EFFECT_SHIFTING 0xff
|
||||||
|
|
||||||
|
std::string hidraw_path = "/dev/hidraw2";
|
||||||
|
int g_fd = -1;
|
||||||
|
|
||||||
|
bool hidrawWrite(const std::vector<uint8_t>&bytes) {
|
||||||
|
for (uint8_t byte : bytes) {
|
||||||
|
std::print("0x{:0x} ", static_cast<uint32_t>(byte));
|
||||||
|
}
|
||||||
|
std::println(" <--- hidraw values");
|
||||||
|
|
||||||
|
int retval = ioctl(g_fd, HIDIOCSFEATURE(bytes.size()), bytes.data());
|
||||||
|
if (retval < 0) {
|
||||||
|
std::println("[ERR] FAILED TO WRITE TO HIDRAW DEVICE!");
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::println("Successfully wrote to hidraw file");
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
int main(int argc, char* argv[]) {
|
||||||
|
if (argc > 1) {
|
||||||
|
hidraw_path = std::string(argv[1]);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (geteuid() != 0) {
|
||||||
|
std::println("[ERR] THIS APPLICATION MUST BE RUN AS ROOT!");
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::println("Acer Predator Helios Neo 16S (PHN16S-71) RGB Control\nWritten by ZoeBattleSand\n");
|
||||||
|
|
||||||
|
std::println("Using file: {}", hidraw_path);
|
||||||
|
g_fd = open(hidraw_path.c_str(), O_RDWR | O_NONBLOCK);
|
||||||
|
if (g_fd < 0) {
|
||||||
|
std::println("[ERR] FAILED TO OPEN HIDRAW DEVICE!");
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
char name[256];
|
||||||
|
int retval = ioctl(g_fd, HIDIOCGRAWNAME(256), name);
|
||||||
|
if (retval < 0) {
|
||||||
|
std::println("[ERR] FAILED TO GET HIDRAW DEVICE NAME!");
|
||||||
|
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
std::println("Device name: {}", name);
|
||||||
|
|
||||||
|
std::string user_input;
|
||||||
|
|
||||||
|
input_dev_start:
|
||||||
|
std::print("Enter device (0 for keyboard, 1 for lid, 2 for mode button): ");
|
||||||
|
std::cin >> user_input;
|
||||||
|
if (user_input != "0" && user_input != "1" && user_input != "2") {
|
||||||
|
std::println("Invalid input! Try again.");
|
||||||
|
goto input_dev_start;
|
||||||
|
}
|
||||||
|
|
||||||
|
uint8_t device = 0x00;
|
||||||
|
uint8_t zone = 0x00;
|
||||||
|
uint8_t effect = 0x00;
|
||||||
|
uint8_t brightness = 0x00;
|
||||||
|
uint8_t speed = 0x00;
|
||||||
|
uint8_t direction = 0x00;
|
||||||
|
uint8_t r = 0x00;
|
||||||
|
uint8_t g = 0x00;
|
||||||
|
uint8_t b = 0x00;
|
||||||
|
|
||||||
|
if (user_input == "0") {
|
||||||
|
device = KEYBOARD_RGB_ID;
|
||||||
|
zone = 0x0f;
|
||||||
|
} else if (user_input == "1") {
|
||||||
|
device = LID_RGB_ID;
|
||||||
|
zone = 0x00;
|
||||||
|
} else if (user_input == "2") {
|
||||||
|
device = BUTTON_RGB_ID;
|
||||||
|
zone = 0x00;
|
||||||
|
}
|
||||||
|
|
||||||
|
int effect_val = 0;
|
||||||
|
input_effect_start:
|
||||||
|
std::print("Enter effect (0 for static, 1 for breathing, 2 for neon, 3 for wave, 4 for ripple, 5 for zoom, 6 for snake, 7 for disco, 8 for shifting): ");
|
||||||
|
std::cin >> user_input;
|
||||||
|
effect_val = std::stoi(user_input);
|
||||||
|
switch(effect_val) {
|
||||||
|
case 0:
|
||||||
|
effect = RGB_EFFECT_STATIC;
|
||||||
|
break;
|
||||||
|
case 1:
|
||||||
|
effect = RGB_EFFECT_BREATHING;
|
||||||
|
break;
|
||||||
|
case 2:
|
||||||
|
effect = RGB_EFFECT_NEON;
|
||||||
|
break;
|
||||||
|
case 3:
|
||||||
|
effect = RGB_EFFECT_WAVE;
|
||||||
|
break;
|
||||||
|
case 4:
|
||||||
|
effect = RGB_EFFECT_RIPPLE;
|
||||||
|
break;
|
||||||
|
case 5:
|
||||||
|
effect = RGB_EFFECT_ZOOM;
|
||||||
|
break;
|
||||||
|
case 6:
|
||||||
|
effect = RGB_EFFECT_SNAKE;
|
||||||
|
break;
|
||||||
|
case 7:
|
||||||
|
effect = RGB_EFFECT_DISCO;
|
||||||
|
break;
|
||||||
|
case 8:
|
||||||
|
effect = RGB_EFFECT_SHIFTING;
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
std::println("Invalid effect! Try again.");
|
||||||
|
goto input_effect_start;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (effect != RGB_EFFECT_STATIC) {
|
||||||
|
int speed_val = 0;
|
||||||
|
input_speed_start:
|
||||||
|
std::print("Enter speed (0-9): ");
|
||||||
|
std::cin >> user_input;
|
||||||
|
speed_val = std::stoi(user_input);
|
||||||
|
if (speed_val > 9) {
|
||||||
|
std::println("Invalid speed! Try again.");
|
||||||
|
goto input_speed_start;
|
||||||
|
}
|
||||||
|
speed = static_cast<uint8_t>(speed_val);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (device == KEYBOARD_RGB_ID) {
|
||||||
|
if (effect != RGB_EFFECT_STATIC && effect != RGB_EFFECT_BREATHING) {
|
||||||
|
int direction_val = 0;
|
||||||
|
input_direction_start:
|
||||||
|
std::print("Enter direction (0 for none, 1 for right, 2 for left): ");
|
||||||
|
std::cin >> user_input;
|
||||||
|
direction_val = std::stoi(user_input);
|
||||||
|
if (direction_val > 2) {
|
||||||
|
std::println("Invalid direction! Try again.");
|
||||||
|
goto input_direction_start;
|
||||||
|
}
|
||||||
|
direction = static_cast<uint8_t>(direction_val);
|
||||||
|
}
|
||||||
|
|
||||||
|
int zone_val = 0;
|
||||||
|
input_zone_start:
|
||||||
|
std::print("Enter zone (0 for all, 1-4 to select a specific zone): ");
|
||||||
|
std::cin >> user_input;
|
||||||
|
zone_val = std::stoi(user_input);
|
||||||
|
if (zone_val > 4) {
|
||||||
|
std::println("Invalid zone! Try again.");
|
||||||
|
goto input_zone_start;
|
||||||
|
}
|
||||||
|
switch (zone_val) {
|
||||||
|
case 0:
|
||||||
|
zone = 0x0f;
|
||||||
|
break;
|
||||||
|
case 1:
|
||||||
|
zone = 0x01;
|
||||||
|
break;
|
||||||
|
case 2:
|
||||||
|
zone = 0x02;
|
||||||
|
break;
|
||||||
|
case 3:
|
||||||
|
zone = 0x04;
|
||||||
|
break;
|
||||||
|
case 4:
|
||||||
|
zone = 0x08;
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
zone = 0x00;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (effect == RGB_EFFECT_STATIC) {
|
||||||
|
int red_val = 0;
|
||||||
|
input_red_start:
|
||||||
|
std::print("Enter red value (0-255): ");
|
||||||
|
std::cin >> user_input;
|
||||||
|
red_val = std::stoi(user_input);
|
||||||
|
if (red_val > std::numeric_limits<uint8_t>::max()) {
|
||||||
|
std::println("Red value {:d} out of range! Try again.", red_val);
|
||||||
|
goto input_red_start;
|
||||||
|
}
|
||||||
|
r = static_cast<uint8_t>(red_val);
|
||||||
|
|
||||||
|
int green_val = 0;
|
||||||
|
input_green_start:
|
||||||
|
std::print("Enter green value (0-255): ");
|
||||||
|
std::cin >> user_input;
|
||||||
|
green_val = std::stoi(user_input);
|
||||||
|
if (green_val > std::numeric_limits<uint8_t>::max()) {
|
||||||
|
std::println("Green value {:d} out of range! Try again.", green_val);
|
||||||
|
goto input_green_start;
|
||||||
|
}
|
||||||
|
g = static_cast<uint8_t>(green_val);
|
||||||
|
|
||||||
|
int blue_val = 0;
|
||||||
|
input_blue_start:
|
||||||
|
std::print("Enter blue value (0-255): ");
|
||||||
|
std::cin >> user_input;
|
||||||
|
blue_val = std::stoi(user_input);
|
||||||
|
if (blue_val > std::numeric_limits<uint8_t>::max()) {
|
||||||
|
std::println("Blue value {:d} out of range! Try again.", blue_val);
|
||||||
|
goto input_blue_start;
|
||||||
|
}
|
||||||
|
b = static_cast<uint8_t>(blue_val);
|
||||||
|
}
|
||||||
|
|
||||||
|
int bright_val = 0;
|
||||||
|
input_bright_start:
|
||||||
|
std::print("Enter brightness value (0-100): ");
|
||||||
|
std::cin >> user_input;
|
||||||
|
bright_val = std::stoi(user_input);
|
||||||
|
if (bright_val > 100) {
|
||||||
|
std::println("Brightness value {:d} out of range! Try again.", bright_val);
|
||||||
|
goto input_bright_start;
|
||||||
|
}
|
||||||
|
brightness = static_cast<uint8_t>(bright_val);
|
||||||
|
|
||||||
|
std::vector<uint8_t> hidraw_data = { RGB_FEATURE_ID, device, effect, brightness, speed, direction, r, g, b, zone, 0x00 };
|
||||||
|
|
||||||
|
if (!hidrawWrite(hidraw_data)) {
|
||||||
|
std::println("[ERR] FAILED TO WRITE HIDRAW DATA!");
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
close(g_fd);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user