Add Pico 2 support
This commit is contained in:
+5
-1
@@ -3,6 +3,9 @@ cmake_minimum_required(VERSION 3.13)
|
|||||||
set(PICO_SDK_PATH /home/kenji/programming/pico/c/pico-sdk)
|
set(PICO_SDK_PATH /home/kenji/programming/pico/c/pico-sdk)
|
||||||
set(PICO_PIO_USB_PATH /home/kenji/programming/pico/c/Pico-PIO-USB)
|
set(PICO_PIO_USB_PATH /home/kenji/programming/pico/c/Pico-PIO-USB)
|
||||||
set(TUSB_NETWORKING_PATH ${PICO_SDK_PATH}/lib/tinyusb/lib/networking)
|
set(TUSB_NETWORKING_PATH ${PICO_SDK_PATH}/lib/tinyusb/lib/networking)
|
||||||
|
if (NOT DEFINED PICO_BOARD)
|
||||||
|
set(PICO_BOARD pico)
|
||||||
|
endif()
|
||||||
include (${PICO_SDK_PATH}/external/pico_sdk_import.cmake)
|
include (${PICO_SDK_PATH}/external/pico_sdk_import.cmake)
|
||||||
project(${PROJECT} C CXX ASM)
|
project(${PROJECT} C CXX ASM)
|
||||||
|
|
||||||
@@ -67,5 +70,6 @@ target_link_libraries(${PROJECT} PRIVATE
|
|||||||
hardware_adc
|
hardware_adc
|
||||||
)
|
)
|
||||||
|
|
||||||
pico_add_extra_outputs(${PROJECT})
|
set_target_properties(${PROJECT} PROPERTIES OUTPUT_NAME "${PROJECT}-${PICO_BOARD}")
|
||||||
|
|
||||||
|
pico_add_extra_outputs(${PROJECT})
|
||||||
|
|||||||
@@ -1,9 +1,9 @@
|
|||||||
# HyperX Alloy Elite 2 RGB Controller
|
# HyperX Alloy Elite 2 RGB Controller
|
||||||
|
|
||||||
This project provides individual controls of the RGB LEDs of a HyperX Alloy
|
This project provides individual controls of the RGB LEDs of a HyperX Alloy
|
||||||
Elite 2 keyboard using a webpage served over a USB connection. ADC readings
|
Elite 2 keyboard using a webpage served over a USB connection from a Raspberry
|
||||||
from an attached light dependent resistor can also be used to make the
|
Pi Pico (2). ADC readings from an attached light dependent resistor can also be
|
||||||
lighting adaptive to the environment.
|
used to make the lighting adaptive to the environment.
|
||||||
|
|
||||||

|

|
||||||
|
|
||||||
@@ -12,23 +12,23 @@ lighting adaptive to the environment.
|
|||||||
### Hardware
|
### Hardware
|
||||||
|
|
||||||
You will need the following hardware to make the device:
|
You will need the following hardware to make the device:
|
||||||
- Raspberry Pi Pico
|
- Raspberry Pi Pico or Raspberry Pi Pico 2
|
||||||
- USB extension cable
|
- USB extension cable
|
||||||
- light dependent resistor such as GL5528 (specific part number may vary)
|
- light dependent resistor such as GL5528 (specific part number may vary)
|
||||||
- 10k ohm resistor (resistance value may vary)
|
- 10k ohm resistor (resistance value may vary)
|
||||||
|
|
||||||
You will need to cut the USB extension in half and connect the wires from the
|
You will need to cut the USB extension in half and connect the wires from the
|
||||||
female end to the Raspberry Pi Pico. The default configuration is to attach the
|
female end to the Raspberry Pi Pico (2). The default configuration is to attach
|
||||||
USB's green wire to pin 1/GP0 and USB's white wire to pin 2/GP1. You will also
|
the USB's green wire to pin 1/GP0 and USB's white wire to pin 2/GP1. You will
|
||||||
need to connect the red to 5V VBUS/VSYS (since you'll be powering from the
|
also need to connect the red to 5V VBUS/VSYS (since you'll be powering from the
|
||||||
USB host device, VBUS should be fine) and the black to any ground pin. Pin 38
|
USB host device, VBUS should be fine) and the black to any ground pin. Pin 38
|
||||||
is the closest and most convenient. While you can connect the Raspberry Pi Pico
|
is the closest and most convenient. While you can connect the Raspberry Pi Pico
|
||||||
to the host device using the micro USB port and a micro USB cable, since
|
(2) to the host device using the micro USB port and a micro USB cable, since
|
||||||
you have already sacrificed half of the USB extension cable, you might as well
|
you have already sacrificed half of the USB extension cable, you might as well
|
||||||
use the male half to create a standard USB-A connection. If you wish to do so,
|
use the male half to create a standard USB-A connection. If you wish to do so,
|
||||||
then simply connect the red and black wires of the male connector end to
|
then simply connect the red and black wires of the male connector end to
|
||||||
VBUS (5V) and GND, respectively. For the data wires, you can solder them to the
|
VBUS (5V) and GND, respectively. For the data wires, you can solder them to the
|
||||||
two test points TP2 and TP3 on the back of the Raspberry Pi Pico. The white
|
two test points TP2 and TP3 on the back of the Raspberry Pi Pico (2). The white
|
||||||
cable goes to TP2 and the green cable to TP3.
|
cable goes to TP2 and the green cable to TP3.
|
||||||
|
|
||||||

|

|
||||||
@@ -49,23 +49,23 @@ hole for the LDR to detect ambient light.
|
|||||||
|
|
||||||
## Software
|
## Software
|
||||||
|
|
||||||
Flash the elite2_rgb.uf2 file from the latest
|
Flash the elite2_rgb-pico.uf2 or elite2_rgb-pico2.uf2 file from the latest
|
||||||
[release](https://git.kkozai.com/kenji/alloy_elite2_rgb/releases) to the
|
[release](https://git.kkozai.com/kenji/alloy_elite2_rgb/releases) to the
|
||||||
Raspberry Pi Pico, and connect the keyboard to the female USB port and insert
|
Raspberry Pi Pico (2), and connect the keyboard to the female USB port and
|
||||||
the male USB connector of the device into your host device such as PC.
|
insert the male USB connector of the device into your host device such as PC.
|
||||||
|
|
||||||
To load the UI for configuring the RGB lighting, open a browser to the page at
|
To load the UI for configuring the RGB lighting, open a browser to the page at
|
||||||
http://alloyelite2.usb, or if that doesn't load, to http://192.168.226.1
|
http://alloyelite2.usb, or if that doesn't load, to http://192.168.226.1
|
||||||
(226 is E2 for "Elite 2" in hexademical). From the webpage, you can click on
|
(226 is E2 for "Elite 2" in hexadecimal). From the webpage, you can click on
|
||||||
any individual key that you want to configure and change the color using the
|
any individual key that you want to configure and change the color using the
|
||||||
color selector or by manually inputting the RGB color value into the text
|
color selector or by manually inputting the RGB color value into the text
|
||||||
boxes. To finalize setting the color for the selected key(s), click on the
|
boxes. To finalize setting the color for the selected key(s), click on the
|
||||||
"Set Color" button.
|
"Set Color" button.
|
||||||
|
|
||||||
To save the lighting configuration to the Pico 2 so that it loads the next time
|
To save the lighting configuration to the Pico (2) so that it loads the next
|
||||||
it is powered on, click on the "Save" button under the "Flash Memory" section.
|
time it is powered on, click on the "Save" button under the "Flash Memory"
|
||||||
If you make unsaved changes and want to reload the configuration from memory,
|
section. If you make unsaved changes and want to reload the configuration from
|
||||||
you can also click the "Load" button to reset to the last saved setting.
|
memory, you can also click the "Load" button to reset to the last saved setting.
|
||||||
|
|
||||||
If the checkbox next to "Adaptive" is selected when setting the color, the key's
|
If the checkbox next to "Adaptive" is selected when setting the color, the key's
|
||||||
brightness will automatically adjust with the ambient lighting, as determined by
|
brightness will automatically adjust with the ambient lighting, as determined by
|
||||||
|
|||||||
+7
-23
@@ -1,4 +1,5 @@
|
|||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
|
#include <math.h>
|
||||||
|
|
||||||
#include "pico/stdlib.h"
|
#include "pico/stdlib.h"
|
||||||
#include "pico/multicore.h"
|
#include "pico/multicore.h"
|
||||||
@@ -13,7 +14,8 @@
|
|||||||
|
|
||||||
static absolute_time_t lastSend;
|
static absolute_time_t lastSend;
|
||||||
static absolute_time_t lastRead;
|
static absolute_time_t lastRead;
|
||||||
static uint16_t adc_value = 0;
|
//static uint16_t adc_value = 0;
|
||||||
|
static uint8_t adc_value = 0;
|
||||||
static bool mute = false;
|
static bool mute = false;
|
||||||
|
|
||||||
static unsigned char buf[BUF_SIZE];
|
static unsigned char buf[BUF_SIZE];
|
||||||
@@ -165,7 +167,7 @@ static struct key key_list[NUM_KEYS] =
|
|||||||
void get_light() {
|
void get_light() {
|
||||||
// get ADC reading from LDR every 500ms
|
// get ADC reading from LDR every 500ms
|
||||||
if ( absolute_time_diff_us(lastRead, get_absolute_time()) >= 500000) {
|
if ( absolute_time_diff_us(lastRead, get_absolute_time()) >= 500000) {
|
||||||
adc_value = adc_read();
|
adc_value = log2(adc_read());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -176,24 +178,6 @@ void rgb_task(uint8_t dev_addr) {
|
|||||||
// updated color info (packets_sent>0) and continue to send the next
|
// updated color info (packets_sent>0) and continue to send the next
|
||||||
// packet if so at a rate of one packet every 20ms
|
// packet if so at a rate of one packet every 20ms
|
||||||
// otherwise, wait 0.5s before sending the next set of color packets
|
// otherwise, wait 0.5s before sending the next set of color packets
|
||||||
|
|
||||||
/*if (packets_sent>0) {
|
|
||||||
if ( absolute_time_diff_us(lastSend, get_absolute_time()) >= 20000) {
|
|
||||||
if (backlight) {
|
|
||||||
send_color(dev_addr, 0x20, 0x20, 0x20);
|
|
||||||
// send a dim white color (#202020) for all keys
|
|
||||||
} else {
|
|
||||||
send_color(dev_addr, 0x00, 0x00, 0x00);
|
|
||||||
// turn off all lighting by sending (#000000) for all keys
|
|
||||||
}
|
|
||||||
lastSend = get_absolute_time();
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
if ( absolute_time_diff_us(lastSend, get_absolute_time()) >= 500000) {
|
|
||||||
send_initial(dev_addr);
|
|
||||||
lastSend = get_absolute_time();
|
|
||||||
}
|
|
||||||
}*/
|
|
||||||
if ( absolute_time_diff_us(lastSend, get_absolute_time()) >= delay) {
|
if ( absolute_time_diff_us(lastSend, get_absolute_time()) >= delay) {
|
||||||
if ( packets_sent == 0) {
|
if ( packets_sent == 0) {
|
||||||
// first packet is initialization packet
|
// first packet is initialization packet
|
||||||
@@ -227,9 +211,9 @@ static void send_color(uint8_t dev_addr) {
|
|||||||
buf[buf_idx] = 0x81;
|
buf[buf_idx] = 0x81;
|
||||||
switch (key_list[key_idx].mode) {
|
switch (key_list[key_idx].mode) {
|
||||||
case RGB_MODE_ADAPTIVE: // adjust brightness based on LDR ADC reading
|
case RGB_MODE_ADAPTIVE: // adjust brightness based on LDR ADC reading
|
||||||
buf[buf_idx+1] = (ADC_MAX-adc_value)*key_list[key_idx].red/ADC_MAX;
|
buf[buf_idx+1] = (ADC_MAX_LOG2-adc_value)*key_list[key_idx].red/ADC_MAX_LOG2;
|
||||||
buf[buf_idx+2] = (ADC_MAX-adc_value)*key_list[key_idx].green/ADC_MAX;
|
buf[buf_idx+2] = (ADC_MAX_LOG2-adc_value)*key_list[key_idx].green/ADC_MAX_LOG2;
|
||||||
buf[buf_idx+3] = (ADC_MAX-adc_value)*key_list[key_idx].blue/ADC_MAX;
|
buf[buf_idx+3] = (ADC_MAX_LOG2-adc_value)*key_list[key_idx].blue/ADC_MAX_LOG2;
|
||||||
break;
|
break;
|
||||||
case RGB_MODE_MUTE:
|
case RGB_MODE_MUTE:
|
||||||
if (mute) {
|
if (mute) {
|
||||||
|
|||||||
@@ -11,6 +11,7 @@
|
|||||||
#define NUM_KEYS 126
|
#define NUM_KEYS 126
|
||||||
#define BUF_SIZE 64
|
#define BUF_SIZE 64
|
||||||
#define ADC_MAX 4096
|
#define ADC_MAX 4096
|
||||||
|
#define ADC_MAX_LOG2 log2(ADC_MAX)
|
||||||
|
|
||||||
enum {
|
enum {
|
||||||
RGG_MODE_INVALID=0,
|
RGG_MODE_INVALID=0,
|
||||||
@@ -187,6 +188,13 @@ bool load_rgb_config(void);
|
|||||||
|
|
||||||
#define CFG_SIGNATURE 0x9e4c
|
#define CFG_SIGNATURE 0x9e4c
|
||||||
|
|
||||||
|
#if PICO_RP2040
|
||||||
#define FLASH_TARGET_OFFSET (PICO_FLASH_SIZE_BYTES - FLASH_SECTOR_SIZE)
|
#define FLASH_TARGET_OFFSET (PICO_FLASH_SIZE_BYTES - FLASH_SECTOR_SIZE)
|
||||||
|
#elif PICO_RP2350
|
||||||
|
#define FLASH_TARGET_OFFSET (PICO_FLASH_SIZE_BYTES - FLASH_BLOCK_SIZE - FLASH_SECTOR_SIZE)
|
||||||
|
#else
|
||||||
|
#error "Unsupported device. Expected RP2040 or RP2350."
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
+25
-1
@@ -1034,7 +1034,31 @@ static const unsigned char data_index_html[] = {
|
|||||||
0x61, 0x6c, 0x75, 0x65, 0x29, 0x20, 0x3c, 0x20, 0x30, 0x29,
|
0x61, 0x6c, 0x75, 0x65, 0x29, 0x20, 0x3c, 0x20, 0x30, 0x29,
|
||||||
0x20, 0x7b, 0xa, 0x9, 0x9, 0x9, 0x63, 0x68, 0x61, 0x6e,
|
0x20, 0x7b, 0xa, 0x9, 0x9, 0x9, 0x63, 0x68, 0x61, 0x6e,
|
||||||
0x6e, 0x65, 0x6c, 0x2e, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x20,
|
0x6e, 0x65, 0x6c, 0x2e, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x20,
|
||||||
0x3d, 0x20, 0x30, 0x3b, 0xa, 0x9, 0x9, 0x7d, 0xa, 0x9,
|
0x3d, 0x20, 0x30, 0x3b, 0xa, 0x9, 0x9, 0x7d, 0x20, 0x65,
|
||||||
|
0x6c, 0x73, 0x65, 0x20, 0x69, 0x66, 0x20, 0x28, 0x20, 0x69,
|
||||||
|
0x73, 0x4e, 0x61, 0x4e, 0x28, 0x70, 0x61, 0x72, 0x73, 0x65,
|
||||||
|
0x49, 0x6e, 0x74, 0x28, 0x63, 0x68, 0x61, 0x6e, 0x6e, 0x65,
|
||||||
|
0x6c, 0x2e, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x29, 0x29, 0x20,
|
||||||
|
0x29, 0x20, 0x7b, 0xa, 0x9, 0x9, 0x9, 0x2f, 0x2f, 0x20,
|
||||||
|
0x6e, 0x6f, 0x6e, 0x2d, 0x6e, 0x75, 0x6d, 0x65, 0x72, 0x69,
|
||||||
|
0x63, 0x61, 0x6c, 0x20, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x20,
|
||||||
|
0x65, 0x6e, 0x74, 0x65, 0x72, 0x65, 0x64, 0x2c, 0x20, 0x73,
|
||||||
|
0x65, 0x74, 0x20, 0x74, 0x6f, 0x20, 0x64, 0x65, 0x66, 0x61,
|
||||||
|
0x75, 0x6c, 0x74, 0xa, 0x9, 0x9, 0x9, 0x63, 0x68, 0x61,
|
||||||
|
0x6e, 0x6e, 0x65, 0x6c, 0x2e, 0x76, 0x61, 0x6c, 0x75, 0x65,
|
||||||
|
0x20, 0x3d, 0x20, 0x31, 0x32, 0x38, 0x3b, 0xa, 0x9, 0x9,
|
||||||
|
0x7d, 0x20, 0x65, 0x6c, 0x73, 0x65, 0x20, 0x7b, 0xa, 0x9,
|
||||||
|
0x9, 0x9, 0x2f, 0x2f, 0x20, 0x6d, 0x61, 0x6b, 0x65, 0x20,
|
||||||
|
0x73, 0x75, 0x72, 0x65, 0x20, 0x74, 0x68, 0x61, 0x74, 0x20,
|
||||||
|
0x76, 0x61, 0x6c, 0x75, 0x65, 0x20, 0x69, 0x6e, 0x20, 0x62,
|
||||||
|
0x6f, 0x78, 0x20, 0x72, 0x65, 0x66, 0x6c, 0x65, 0x63, 0x74,
|
||||||
|
0x73, 0x20, 0x77, 0x68, 0x61, 0x74, 0x20, 0x70, 0x61, 0x72,
|
||||||
|
0x73, 0x65, 0x72, 0x20, 0x74, 0x68, 0x69, 0x6e, 0x6b, 0x73,
|
||||||
|
0xa, 0x9, 0x9, 0x9, 0x63, 0x68, 0x61, 0x6e, 0x6e, 0x65,
|
||||||
|
0x6c, 0x2e, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x20, 0x3d, 0x20,
|
||||||
|
0x70, 0x61, 0x72, 0x73, 0x65, 0x49, 0x6e, 0x74, 0x28, 0x63,
|
||||||
|
0x68, 0x61, 0x6e, 0x6e, 0x65, 0x6c, 0x2e, 0x76, 0x61, 0x6c,
|
||||||
|
0x75, 0x65, 0x29, 0x3b, 0xa, 0x9, 0x9, 0x7d, 0xa, 0x9,
|
||||||
0x7d, 0xa, 0xa, 0x9, 0x64, 0x6f, 0x63, 0x75, 0x6d, 0x65,
|
0x7d, 0xa, 0xa, 0x9, 0x64, 0x6f, 0x63, 0x75, 0x6d, 0x65,
|
||||||
0x6e, 0x74, 0x2e, 0x67, 0x65, 0x74, 0x45, 0x6c, 0x65, 0x6d,
|
0x6e, 0x74, 0x2e, 0x67, 0x65, 0x74, 0x45, 0x6c, 0x65, 0x6d,
|
||||||
0x65, 0x6e, 0x74, 0x42, 0x79, 0x49, 0x64, 0x28, 0x22, 0x72,
|
0x65, 0x6e, 0x74, 0x42, 0x79, 0x49, 0x64, 0x28, 0x22, 0x72,
|
||||||
|
|||||||
+2
-2
@@ -13,9 +13,9 @@
|
|||||||
|
|
||||||
#include "usb_device.h"
|
#include "usb_device.h"
|
||||||
|
|
||||||
char cdc_buf[64];
|
char cdc_buf[128];
|
||||||
uint16_t cdc_len;
|
uint16_t cdc_len;
|
||||||
size_t cdc_count;
|
uint32_t cdc_count;
|
||||||
device_state_t device_state;
|
device_state_t device_state;
|
||||||
|
|
||||||
static uint8_t desc_configuration[DESC_CFG_MAX];
|
static uint8_t desc_configuration[DESC_CFG_MAX];
|
||||||
|
|||||||
+2
-2
@@ -30,9 +30,9 @@ typedef enum {
|
|||||||
DEVICE_RESTART,
|
DEVICE_RESTART,
|
||||||
} device_state_t;
|
} device_state_t;
|
||||||
|
|
||||||
extern char cdc_buf[64];
|
extern char cdc_buf[128];
|
||||||
extern uint16_t cdc_len;
|
extern uint16_t cdc_len;
|
||||||
extern size_t cdc_count;
|
extern uint32_t cdc_count;
|
||||||
extern device_state_t device_state;
|
extern device_state_t device_state;
|
||||||
|
|
||||||
void usb_device_main(void);
|
void usb_device_main(void);
|
||||||
|
|||||||
+4
-3
@@ -354,12 +354,14 @@ static err_t ws_read(struct altcp_pcb *pcb, struct ws_state *wss, struct pbuf *p
|
|||||||
uint8_t masked = data[1] & 0x80;
|
uint8_t masked = data[1] & 0x80;
|
||||||
uint16_t msg_len = data[1] & 0x7F;
|
uint16_t msg_len = data[1] & 0x7F;
|
||||||
uint8_t *msg;
|
uint8_t *msg;
|
||||||
|
uint8_t *mask;
|
||||||
|
|
||||||
switch (msg_len) {
|
switch (msg_len) {
|
||||||
case 126: // next two bytes are length
|
case 126: // next two bytes are length
|
||||||
memcpy(&msg_len, &data[2], 2);
|
msg_len = ( (uint16_t)data[2] << 8) | data[3];
|
||||||
if (len >= 8) {
|
if (len >= 8) {
|
||||||
msg = &data[8];
|
msg = &data[8];
|
||||||
|
mask = &data[4];
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 127: // next four bytes are length
|
case 127: // next four bytes are length
|
||||||
@@ -369,6 +371,7 @@ static err_t ws_read(struct altcp_pcb *pcb, struct ws_state *wss, struct pbuf *p
|
|||||||
default:
|
default:
|
||||||
if (len >= 6) {
|
if (len >= 6) {
|
||||||
msg = &data[6];
|
msg = &data[6];
|
||||||
|
mask = &data[2];
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@@ -382,8 +385,6 @@ static err_t ws_read(struct altcp_pcb *pcb, struct ws_state *wss, struct pbuf *p
|
|||||||
if (msg && ws_receive_cb != NULL) {
|
if (msg && ws_receive_cb != NULL) {
|
||||||
// unmask the data if mask bit is received
|
// unmask the data if mask bit is received
|
||||||
if (masked) {
|
if (masked) {
|
||||||
uint8_t *mask = &data[2];
|
|
||||||
|
|
||||||
for (int i=0; i<msg_len; i++) {
|
for (int i=0; i<msg_len; i++) {
|
||||||
msg[i] ^= mask[i % 4];
|
msg[i] ^= mask[i % 4];
|
||||||
}
|
}
|
||||||
|
|||||||
+1
-1
@@ -7,7 +7,7 @@
|
|||||||
#define WS_MAX_RETRIES 10
|
#define WS_MAX_RETRIES 10
|
||||||
#define WS_POLL_INTERVAL 60 // WS_POLL_INTERVAL/2 seconds
|
#define WS_POLL_INTERVAL 60 // WS_POLL_INTERVAL/2 seconds
|
||||||
#define WS_MAX_CONN 4
|
#define WS_MAX_CONN 4
|
||||||
#define WS_BUFFER_SIZE 512
|
#define WS_BUFFER_SIZE 1024
|
||||||
|
|
||||||
#define OP_CONT 0x00
|
#define OP_CONT 0x00
|
||||||
#define OP_TEXT 0x01
|
#define OP_TEXT 0x01
|
||||||
|
|||||||
Reference in New Issue
Block a user