diff --git a/Controllers/CorsairHydroController/CorsairHydroController.cpp b/Controllers/CorsairHydroController/CorsairHydroController.cpp index b548a7a6..ee446e0d 100644 --- a/Controllers/CorsairHydroController/CorsairHydroController.cpp +++ b/Controllers/CorsairHydroController/CorsairHydroController.cpp @@ -6,6 +6,8 @@ #include "CorsairHydroController.h" +#include + CorsairHydroController::CorsairHydroController(libusb_device_handle* dev_handle) { dev = dev_handle; @@ -20,58 +22,230 @@ std::string CorsairHydroController::GetFirmwareString() return(firmware_version); } +void CorsairHydroController::SetBlink + ( + std::vector & colors, + unsigned char speed + ) +{ + SendColors(colors); + SendSpeed(speed); + SendApplyBlink(); +} + +void CorsairHydroController::SetFixed + ( + std::vector & colors + ) +{ + SendColors(colors); + + /*-----------------------------------------------------*\ + | Fixed mode seems to just be shift mode with the same | + | value for both colors | + \*-----------------------------------------------------*/ + SendApplyShift(); +} + +void CorsairHydroController::SetPulse + ( + std::vector & colors, + unsigned char speed + ) +{ + SendColors(colors); + SendSpeed(speed); + SendApplyPulse(); +} + +void CorsairHydroController::SetShift + ( + std::vector & colors, + unsigned char speed + ) +{ + SendColors(colors); + SendSpeed(speed); + SendApplyShift(); +} + +/*-------------------------------------------------------------------------------------------------*\ +| Private packet sending functions. | +\*-------------------------------------------------------------------------------------------------*/ + +void CorsairHydroController::SendApplyBlink() +{ + unsigned char usb_buf[3]; + int actual; + + /*-----------------------------------------------------*\ + | Zero out buffer | + \*-----------------------------------------------------*/ + memset(usb_buf, 0, sizeof(usb_buf)); + + /*-----------------------------------------------------*\ + | Set up Apply Blink packet | + \*-----------------------------------------------------*/ + usb_buf[0] = 0x58; + usb_buf[1] = 0x01; + + /*-----------------------------------------------------*\ + | Send packet | + \*-----------------------------------------------------*/ + libusb_bulk_transfer(dev, 0x01, usb_buf, 2, &actual, 1000); + libusb_bulk_transfer(dev, 0x81, usb_buf, 3, &actual, 1000); +} + +void CorsairHydroController::SendApplyPulse() +{ + unsigned char usb_buf[3]; + int actual; + + /*-----------------------------------------------------*\ + | Zero out buffer | + \*-----------------------------------------------------*/ + memset(usb_buf, 0, sizeof(usb_buf)); + + /*-----------------------------------------------------*\ + | Set up Apply Pulse packet | + \*-----------------------------------------------------*/ + usb_buf[0] = 0x52; + usb_buf[1] = 0x01; + + /*-----------------------------------------------------*\ + | Send packet | + \*-----------------------------------------------------*/ + libusb_bulk_transfer(dev, 0x01, usb_buf, 2, &actual, 1000); + libusb_bulk_transfer(dev, 0x81, usb_buf, 3, &actual, 1000); +} + +void CorsairHydroController::SendApplyShift() +{ + unsigned char usb_buf[3]; + int actual; + + /*-----------------------------------------------------*\ + | Zero out buffer | + \*-----------------------------------------------------*/ + memset(usb_buf, 0, sizeof(usb_buf)); + + /*-----------------------------------------------------*\ + | Set up Apply Shift packet | + \*-----------------------------------------------------*/ + usb_buf[0] = 0x55; + usb_buf[1] = 0x01; + + /*-----------------------------------------------------*\ + | Send packet | + \*-----------------------------------------------------*/ + libusb_bulk_transfer(dev, 0x01, usb_buf, 2, &actual, 1000); + libusb_bulk_transfer(dev, 0x81, usb_buf, 3, &actual, 1000); +} + void CorsairHydroController::SendFirmwareRequest() { unsigned char usb_buf[8]; int actual; + /*-----------------------------------------------------*\ + | Zero out buffer | + \*-----------------------------------------------------*/ + memset(usb_buf, 0, sizeof(usb_buf)); + + /*-----------------------------------------------------*\ + | Set up Firmware Request packet | + \*-----------------------------------------------------*/ usb_buf[0] = 0xAA; + /*-----------------------------------------------------*\ + | Send packet | + \*-----------------------------------------------------*/ libusb_bulk_transfer(dev, 0x01, usb_buf, 1, &actual, 1000); libusb_bulk_transfer(dev, 0x81, usb_buf, 7, &actual, 1000); firmware_version = std::to_string(usb_buf[3]) + "." + std::to_string(usb_buf[4]) + "." + std::to_string(usb_buf[5]) + "." + std::to_string(usb_buf[6]); } -void CorsairHydroController::SetFixed +void CorsairHydroController::SendColors ( - unsigned char red, - unsigned char green, - unsigned char blue + std::vector & colors ) { - unsigned char usb_buf[8]; + unsigned char usb_buf[23]; int actual; + /*-----------------------------------------------------*\ + | Zero out buffer | + \*-----------------------------------------------------*/ + memset(usb_buf, 0, sizeof(usb_buf)); + + /*-----------------------------------------------------*\ + | Set up Send Colors packet | + \*-----------------------------------------------------*/ usb_buf[0] = 0x56; - usb_buf[1] = 0x02; - usb_buf[2] = red; - usb_buf[3] = green; - usb_buf[4] = blue; - usb_buf[5] = red; - usb_buf[6] = green; - usb_buf[7] = blue; + usb_buf[1] = colors.size(); - libusb_bulk_transfer(dev, 0x01, usb_buf, 8, &actual, 1000); - libusb_bulk_transfer(dev, 0x81, usb_buf, 3, &actual, 1000); + /*---------------------------------------------------------*\ + | Fill in colors from vector | + \*---------------------------------------------------------*/ + for(std::size_t color_idx = 0; color_idx < colors.size(); color_idx++) + { + usb_buf[(color_idx * 3) + 2] = RGBGetRValue(colors[color_idx]); + usb_buf[(color_idx * 3) + 3] = RGBGetGValue(colors[color_idx]); + usb_buf[(color_idx * 3) + 4] = RGBGetBValue(colors[color_idx]); - SendApply(); -} + /*---------------------------------------------------------*\ + | If the color vector only has one entry, duplicate it, as | + | the controller appears to require two colors in order to | + | update. | + \*---------------------------------------------------------*/ + if((color_idx == 0) && colors.size() == 1) + { + usb_buf[1] = colors.size() + 1; + usb_buf[(color_idx * 3) + 5] = RGBGetRValue(colors[color_idx]); + usb_buf[(color_idx * 3) + 6] = RGBGetGValue(colors[color_idx]); + usb_buf[(color_idx * 3) + 7] = RGBGetBValue(colors[color_idx]); + } + } -void CorsairHydroController::SendApply() -{ - unsigned char usb_buf[3]; - int actual; - - usb_buf[0] = 0x55; - usb_buf[1] = 0x01; - - libusb_bulk_transfer(dev, 0x01, usb_buf, 2, &actual, 1000); + /*-----------------------------------------------------*\ + | Send packet | + \*-----------------------------------------------------*/ + libusb_bulk_transfer(dev, 0x01, usb_buf, 2 + (usb_buf[1] * 3), &actual, 1000); libusb_bulk_transfer(dev, 0x81, usb_buf, 3, &actual, 1000); } void CorsairHydroController::SendInit() { + /*-----------------------------------------------------*\ + | Send packet | + \*-----------------------------------------------------*/ libusb_control_transfer( dev, 0x40, 0x00, 0xffff, 0x0000, NULL, 0, 0 ); libusb_control_transfer( dev, 0x40, 0x02, 0x0002, 0x0000, NULL, 0, 0 ); +} + +void CorsairHydroController::SendSpeed + ( + unsigned char speed + ) +{ + unsigned char usb_buf[3]; + int actual; + + /*-----------------------------------------------------*\ + | Zero out buffer | + \*-----------------------------------------------------*/ + memset(usb_buf, 0, sizeof(usb_buf)); + + /*-----------------------------------------------------*\ + | Set up Send Speed packet | + \*-----------------------------------------------------*/ + usb_buf[0] = 0x53; + usb_buf[1] = speed; + + /*-----------------------------------------------------*\ + | Send packet | + \*-----------------------------------------------------*/ + libusb_bulk_transfer(dev, 0x01, usb_buf, 2, &actual, 1000); + libusb_bulk_transfer(dev, 0x81, usb_buf, 3, &actual, 1000); } \ No newline at end of file diff --git a/Controllers/CorsairHydroController/CorsairHydroController.h b/Controllers/CorsairHydroController/CorsairHydroController.h index e8591c44..5750644e 100644 --- a/Controllers/CorsairHydroController/CorsairHydroController.h +++ b/Controllers/CorsairHydroController/CorsairHydroController.h @@ -39,18 +39,48 @@ public: std::string GetFirmwareString(); + void SetBlink + ( + std::vector & colors, + unsigned char speed + ); + void SetFixed ( - unsigned char red, - unsigned char green, - unsigned char blue + std::vector & colors ); + void SetPulse + ( + std::vector & colors, + unsigned char speed + ); + + void SetShift + ( + std::vector & colors, + unsigned char speed + ); + private: libusb_device_handle* dev; std::string firmware_version; - void SendApply(); + void SendApplyBlink(); + void SendApplyPulse(); + void SendApplyShift(); + + void SendColors + ( + std::vector & colors + ); + void SendFirmwareRequest(); + void SendInit(); + + void SendSpeed + ( + unsigned char speed + ); }; diff --git a/RGBController/RGBController_CorsairHydro.cpp b/RGBController/RGBController_CorsairHydro.cpp index 44742a94..8383ca77 100644 --- a/RGBController/RGBController_CorsairHydro.cpp +++ b/RGBController/RGBController_CorsairHydro.cpp @@ -18,12 +18,51 @@ RGBController_CorsairHydro::RGBController_CorsairHydro(CorsairHydroController* c type = DEVICE_TYPE_COOLER; mode Direct; - Direct.name = "Direct"; - Direct.value = 0; - Direct.flags = MODE_FLAG_HAS_PER_LED_COLOR; + 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); + mode Blinking; + Blinking.name = "Blinking"; + Blinking.value = 1; + Blinking.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR; + Blinking.color_mode = MODE_COLORS_MODE_SPECIFIC; + Blinking.speed_min = 0x0F; + Blinking.speed_max = 0x05; + Blinking.speed = 0x0A; + Blinking.colors_min = 2; + Blinking.colors_max = 2; + Blinking.colors.resize(2); + modes.push_back(Blinking); + + mode ColorShift; + ColorShift.name = "Color Shift"; + ColorShift.value = 2; + ColorShift.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR; + ColorShift.color_mode = MODE_COLORS_MODE_SPECIFIC; + ColorShift.speed_min = 0x46; + ColorShift.speed_max = 0x0F; + ColorShift.speed = 0x28; + ColorShift.colors_min = 2; + ColorShift.colors_max = 2; + ColorShift.colors.resize(2); + modes.push_back(ColorShift); + + mode Pulsing; + Pulsing.name = "Pulsing"; + Pulsing.value = 3; + Pulsing.flags = MODE_FLAG_HAS_SPEED | MODE_FLAG_HAS_MODE_SPECIFIC_COLOR; + Pulsing.color_mode = MODE_COLORS_MODE_SPECIFIC; + Pulsing.speed_min = 0x50; + Pulsing.speed_max = 0x1E; + Pulsing.speed = 0x37; + Pulsing.colors_min = 2; + Pulsing.colors_max = 2; + Pulsing.colors.resize(2); + modes.push_back(Pulsing); + SetupZones(); } @@ -49,12 +88,14 @@ void RGBController_CorsairHydro::SetupZones() void RGBController_CorsairHydro::ResizeZone(int /*zone*/, int /*new_size*/) { - + /*---------------------------------------------------------*\ + | This device does not support resizing zones | + \*---------------------------------------------------------*/ } void RGBController_CorsairHydro::DeviceUpdateLEDs() { - corsair->SetFixed(RGBGetRValue(colors[0]), RGBGetGValue(colors[0]), RGBGetBValue(colors[0])); + DeviceUpdateMode(); } void RGBController_CorsairHydro::UpdateZoneLEDs(int zone) @@ -74,5 +115,22 @@ void RGBController_CorsairHydro::SetCustomMode() void RGBController_CorsairHydro::DeviceUpdateMode() { - DeviceUpdateLEDs(); + switch(modes[active_mode].value) + { + case 0: + corsair->SetFixed(colors); + break; + + case 1: + corsair->SetBlink(modes[active_mode].colors, modes[active_mode].speed); + break; + + case 2: + corsair->SetShift(modes[active_mode].colors, modes[active_mode].speed); + break; + + case 3: + corsair->SetPulse(modes[active_mode].colors, modes[active_mode].speed); + break; + } } \ No newline at end of file