Modify UDP protocol to be WLED-compatible.
This commit is contained in:
parent
6dbfcf9e9d
commit
641eba5faa
|
@ -6,16 +6,16 @@ pub const SAMP_RATE: f32 = 48000.0;
|
||||||
pub const SAMPLES_PER_UPDATE: usize = BLOCK_LEN/2;
|
pub const SAMPLES_PER_UPDATE: usize = BLOCK_LEN/2;
|
||||||
|
|
||||||
// LED configuration
|
// LED configuration
|
||||||
pub const NUM_STRIPS: usize = 8;
|
pub const NUM_STRIPS: usize = 1;
|
||||||
pub const NUM_LEDS_PER_STRIP: usize = 16;
|
pub const NUM_LEDS_PER_STRIP: usize = 322;
|
||||||
|
|
||||||
pub const NUM_LEDS_TOTAL: usize = NUM_STRIPS * NUM_LEDS_PER_STRIP;
|
pub const NUM_LEDS_TOTAL: usize = NUM_STRIPS * NUM_LEDS_PER_STRIP;
|
||||||
|
|
||||||
// network configuration
|
// network configuration
|
||||||
pub const UDP_SERVER_ADDR: &str = "192.168.23.118:2703";
|
pub const UDP_SERVER_ADDR: &str = "wled1:21324";
|
||||||
|
|
||||||
pub const FPS_ANIMATION: f32 = SAMP_RATE / SAMPLES_PER_UPDATE as f32;
|
pub const FPS_ANIMATION: f32 = SAMP_RATE / SAMPLES_PER_UPDATE as f32;
|
||||||
pub const FPS_LEDS: f32 = 60.0;
|
pub const FPS_LEDS: f32 = 30.0;
|
||||||
|
|
||||||
// “standby mode” configuration
|
// “standby mode” configuration
|
||||||
pub const STANDBY_MAX_SILENT_SAMPLES: usize = SAMP_RATE as usize;
|
pub const STANDBY_MAX_SILENT_SAMPLES: usize = SAMP_RATE as usize;
|
||||||
|
|
|
@ -25,7 +25,7 @@ fn main()
|
||||||
let mut stdin = std::io::stdin();
|
let mut stdin = std::io::stdin();
|
||||||
|
|
||||||
// set up the UDP protocol
|
// set up the UDP protocol
|
||||||
let mut udpproto = match UdpProto::new(config::UDP_SERVER_ADDR) {
|
let mut udpproto = match UdpProto::new(config::UDP_SERVER_ADDR, config::NUM_LEDS_TOTAL) {
|
||||||
Ok(u) => u,
|
Ok(u) => u,
|
||||||
Err(e) => {
|
Err(e) => {
|
||||||
println!("Error during UDP client setup:\n{}", e);
|
println!("Error during UDP client setup:\n{}", e);
|
||||||
|
@ -135,7 +135,7 @@ fn main()
|
||||||
let led = i % config::NUM_LEDS_PER_STRIP;
|
let led = i % config::NUM_LEDS_PER_STRIP;
|
||||||
|
|
||||||
let r = udpproto.set_color(strip as u8,
|
let r = udpproto.set_color(strip as u8,
|
||||||
led as u8,
|
led,
|
||||||
(colorlists[strip][led].r * 255.0) as u8,
|
(colorlists[strip][led].r * 255.0) as u8,
|
||||||
(colorlists[strip][led].g * 255.0) as u8,
|
(colorlists[strip][led].g * 255.0) as u8,
|
||||||
(colorlists[strip][led].b * 255.0) as u8,
|
(colorlists[strip][led].b * 255.0) as u8,
|
||||||
|
|
102
src/udpproto.rs
102
src/udpproto.rs
|
@ -5,6 +5,8 @@ use std::net::SocketAddrV4;
|
||||||
use std::net::Ipv4Addr;
|
use std::net::Ipv4Addr;
|
||||||
|
|
||||||
const MAX_PACKET_LEN: usize = 1470;
|
const MAX_PACKET_LEN: usize = 1470;
|
||||||
|
const TIMEOUT_SEC: u8 = 3;
|
||||||
|
const WLED_MODE_DRGBW: u8 = 3;
|
||||||
|
|
||||||
struct Command
|
struct Command
|
||||||
{
|
{
|
||||||
|
@ -17,103 +19,45 @@ struct Command
|
||||||
pub struct UdpProto
|
pub struct UdpProto
|
||||||
{
|
{
|
||||||
socket: UdpSocket,
|
socket: UdpSocket,
|
||||||
packet: [u8; MAX_PACKET_LEN],
|
packet: Vec<u8>,
|
||||||
packet_offset: usize,
|
|
||||||
}
|
}
|
||||||
|
|
||||||
impl UdpProto
|
impl UdpProto
|
||||||
{
|
{
|
||||||
pub fn new(target_address: &str) -> std::io::Result<UdpProto>
|
pub fn new(target_address: &str, num_leds_total: usize) -> std::io::Result<UdpProto>
|
||||||
{
|
{
|
||||||
let u = UdpProto {
|
let mut u = UdpProto {
|
||||||
socket: UdpSocket::bind(SocketAddrV4::new(Ipv4Addr::UNSPECIFIED, 0))?,
|
socket: UdpSocket::bind(SocketAddrV4::new(Ipv4Addr::UNSPECIFIED, 0))?,
|
||||||
packet: [0u8; MAX_PACKET_LEN],
|
packet: vec![0; 2 + 4*num_leds_total],
|
||||||
packet_offset: 0,
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
u.packet[0] = WLED_MODE_DRGBW;
|
||||||
|
u.packet[1] = TIMEOUT_SEC;
|
||||||
|
|
||||||
u.socket.connect(target_address)?;
|
u.socket.connect(target_address)?;
|
||||||
|
|
||||||
Ok(u)
|
Ok(u)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn send_packet(&mut self) -> std::io::Result<()>
|
pub fn set_color(&mut self, _strip: u8, led: usize,
|
||||||
{
|
|
||||||
if self.packet_offset == 0 {
|
|
||||||
// nothing to do
|
|
||||||
return Ok( () );
|
|
||||||
}
|
|
||||||
|
|
||||||
self.socket.send(&self.packet[0..self.packet_offset])?;
|
|
||||||
|
|
||||||
self.packet_offset = 0;
|
|
||||||
|
|
||||||
Ok( () )
|
|
||||||
}
|
|
||||||
|
|
||||||
fn add_command(&mut self, cmd: u8, strip: u8, led: u8, data: &[u8; 4]) -> std::io::Result<()>
|
|
||||||
{
|
|
||||||
// put the command into the packet buffer
|
|
||||||
self.packet[self.packet_offset + 0] = cmd;
|
|
||||||
self.packet[self.packet_offset + 1] = strip;
|
|
||||||
self.packet[self.packet_offset + 2] = led;
|
|
||||||
|
|
||||||
for i in 0 .. data.len() {
|
|
||||||
self.packet[self.packet_offset + i + 3] = data[i];
|
|
||||||
}
|
|
||||||
|
|
||||||
self.packet_offset += 7;
|
|
||||||
|
|
||||||
if self.packet_offset >= MAX_PACKET_LEN-7 {
|
|
||||||
self.send_packet()?;
|
|
||||||
}
|
|
||||||
|
|
||||||
Ok( () )
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn set_color(&mut self, strip: u8, led: u8,
|
|
||||||
r: u8, g: u8, b: u8, w: u8) -> std::io::Result<()>
|
r: u8, g: u8, b: u8, w: u8) -> std::io::Result<()>
|
||||||
{
|
{
|
||||||
let data = [r,g,b,w];
|
let offset = 2 + 4*led;
|
||||||
|
if offset > self.packet.len() {
|
||||||
self.add_command(0x00, strip, led, &data)?;
|
Err(std::io::Error::new(std::io::ErrorKind::InvalidInput, "LED index out of range"))
|
||||||
|
}
|
||||||
Ok( () )
|
else {
|
||||||
}
|
self.packet[offset + 0] = r;
|
||||||
|
self.packet[offset + 1] = g;
|
||||||
pub fn fade_color(&mut self, strip: u8, led: u8,
|
self.packet[offset + 2] = b;
|
||||||
r: u8, g: u8, b: u8, w: u8) -> std::io::Result<()>
|
self.packet[offset + 3] = w;
|
||||||
{
|
Ok( () )
|
||||||
let data = [r,g,b,w];
|
}
|
||||||
|
|
||||||
self.add_command(0x01, strip, led, &data)?;
|
|
||||||
|
|
||||||
Ok( () )
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn add_color(&mut self, strip: u8, led: u8,
|
|
||||||
r: u8, g: u8, b: u8, w: u8) -> std::io::Result<()>
|
|
||||||
{
|
|
||||||
let data = [r,g,b,w];
|
|
||||||
|
|
||||||
self.add_command(0x02, strip, led, &data)?;
|
|
||||||
|
|
||||||
Ok( () )
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn set_fadestep(&mut self, fadestep: u8) -> std::io::Result<()>
|
|
||||||
{
|
|
||||||
let data = [fadestep, 0, 0, 0];
|
|
||||||
|
|
||||||
self.add_command(0x03, 0, 0, &data)?;
|
|
||||||
|
|
||||||
Ok( () )
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn commit(&mut self) -> std::io::Result<()>
|
pub fn commit(&mut self) -> std::io::Result<()>
|
||||||
{
|
{
|
||||||
// add the END_OF_UPDATE command
|
self.socket.send(&self.packet)?;
|
||||||
self.add_command(0xFE, 0, 0, &[0u8; 4])?;
|
Ok( () )
|
||||||
|
|
||||||
self.send_packet()
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue