X-Git-Url: http://git.euphorik.ch/?a=blobdiff_plain;f=src%2FAsusAuraUSB.rs;fp=src%2FAsusAuraUSB.rs;h=74face19860f660f27a97bf741a072b36353d1a6;hb=d7ff8803c1b3fa3a2ad2d6ed61e3fc232d1258de;hp=0000000000000000000000000000000000000000;hpb=52520a2f096921aa4e26818c669dc5fdf01c0528;p=temp2RGB.git diff --git a/src/AsusAuraUSB.rs b/src/AsusAuraUSB.rs new file mode 100644 index 0000000..74face1 --- /dev/null +++ b/src/AsusAuraUSB.rs @@ -0,0 +1,139 @@ +use std::str; + +use crate::rgb::RGB; + +/* + * Doc: + * - https://blog.inlart.com/post/openrgb-asus-x570/ + * - https://openrgb-wiki.readthedocs.io/en/latest/asus/ASUS-Aura-USB/ + */ + +const AURA_REQUEST_FIRMWARE_VERSION: u8 = 0x82; +const AURA_REQUEST_CONFIG_TABLE: u8 = 0xB0; + +const VID: u16 = 0x0B05; // Vendor ID: ASUS. + +const PID_650_E: u16 = 0x19AF; // Product ID: AURA LED Controller. +const PID_CROSSHAIR: u16 = 0x18F3; // Product ID: AURA LED Controller. + +pub enum Motherboard { + Asus650e, + AsusCrosshairVIIIHero, +} + +pub struct Device { + device: hidapi::HidDevice, + motherboard: Motherboard, +} + +impl Device { + pub fn new(api: &hidapi::HidApi, motherboard: Motherboard) -> Self { + Device { + device: api + .open( + VID, + match motherboard { + Motherboard::Asus650e => PID_650_E, + Motherboard::AsusCrosshairVIIIHero => PID_CROSSHAIR, + }, + ) + .unwrap(), + motherboard, + } + } + + pub fn get_firmware_string(&self) -> String { + let mut buffer = [0u8; 65]; + buffer[0] = 0xEC; + buffer[1] = AURA_REQUEST_FIRMWARE_VERSION; + let n_write = self.device.write(&buffer).unwrap(); + assert_eq!(n_write, 65); + + buffer.fill(0); + let n_read = self.device.read(&mut buffer).unwrap(); + assert_eq!(n_read, 65); + assert_eq!(buffer[0], 0xEC); + assert_eq!(buffer[1], 0x02); + + String::from(str::from_utf8(&buffer[2..17]).unwrap()) + } + + /* + Example of configuration table: + - Positions 0 and 1 always 1E and 9F. + - Value 02 is the number of adressable channels. + 1E 9F 02 01 00 00 + 78 3C 00 01 00 00 + 78 3C 00 00 00 00 + 00 00 00 00 00 00 + 00 00 00 08 0A 02 + 01 F4 00 00 00 00 + 00 00 00 00 00 00 + 00 00 00 00 00 00 + 00 00 00 00 00 00 + 00 00 00 00 00 00 + */ + pub fn get_configuration_table(&self) -> [u8; 60] { + let mut buffer = [0u8; 65]; + buffer[0] = 0xEC; + buffer[1] = AURA_REQUEST_CONFIG_TABLE; + let n_write = self.device.write(&buffer).unwrap(); + assert_eq!(n_write, 65); + + buffer.fill(0); + let n_read = self.device.read(&mut buffer).unwrap(); + assert_eq!(n_read, 65); + assert_eq!(buffer[0], 0xEC); + assert_eq!(buffer[1], 0x30); + + buffer[4..64] + .try_into() + .expect("slice with incorrect length") + } + + pub fn set_fixed_mode(&self) { + let mut buffer = [0u8; 65]; + buffer[0] = 0xEC; + buffer[1] = 0x35; // Control mode. + buffer[4] = 0x00; // Shutdown effect. + buffer[5] = 0x01; // Mode id: static. + + for channel_effect_id in 0..2 { + buffer[2] = channel_effect_id; // Channel effect id: Fixed. + let n_write = self.device.write(&buffer).unwrap(); + assert_eq!(n_write, 65); + } + } + + pub fn set_color(&self, color: &RGB) { + let mut buffer = [0u8; 65]; + buffer[0] = 0xEC; + buffer[1] = 0x36; + + let start_led = 0u32; + let nb_of_leds = 16u32; + let mask = ((1u32 << nb_of_leds) - 1u32) << start_led; + + buffer[2] = (mask >> 8) as u8; // 16 bits LED mask: first part. + buffer[3] = (mask & 0xFF) as u8; // 16 bits LED mask: second part. + + for n in start_led as usize..(start_led + nb_of_leds) as usize { + buffer[5 + 3 * n] = color.red; + buffer[5 + 3 * n + 1] = color.green; + buffer[5 + 3 * n + 2] = color.blue; + } + + let n_write = self.device.write(&buffer).unwrap(); + assert_eq!(n_write, 65); + } + + pub fn save_current_color(&self) { + let mut buffer = [0u8; 65]; + buffer[0] = 0xEC; + buffer[1] = 0x3F; + buffer[2] = 0x55; + + let n_write = self.device.write(&buffer).unwrap(); + assert_eq!(n_write, 65); + } +}