package main import ( "fmt" "log" "time" webserver "git.martyn.berlin/martyn/LEDController/internal/webserver" queue "git.martyn.berlin/martyn/LEDController/internal/queue" remapping "git.martyn.berlin/martyn/LEDController/internal/remapping" patterns "git.martyn.berlin/martyn/LEDController/internal/patterns" "github.com/Hundemeier/go-sacn/sacn" ) type RGBcolor = [3]byte var currentFrame [2][512]byte var channels [2]chan<-[512]byte var sema = make(chan struct{}, 1) // a binary semaphore guarding currentFrame var currentEffect queue.QueueItem; var globalEffectChannel = make(chan queue.QueueItem, 1024) func foreverLoop() { for /*ever*/ { time.Sleep(40 * time.Millisecond) //25fps for u := 0; u < 2; u++ { sema <- struct{}{} // acquire token channels[u] <- currentFrame[u] <- sema } } } func main() { go func() { fmt.Printf("Starting webserver on port %s\n", "5353") webserver.HandleHTTP(globalEffectChannel) }() //instead of "" you could provide an ip-address that the socket should bind to trans, err := sacn.NewTransmitter("", [16]byte{1, 2}, "test") if err != nil { log.Fatal(err) } //activates the universes for i := 0; i < 2; i++ { channels[i], err = trans.Activate(uint16(i+1)) //deactivate the channel on exit defer close(channels[i]) trans.SetMulticast(uint16(i+1), false) //this specific setup will not multicast on windows, trans.SetDestinations(uint16(i+1), []string{"192.168.1.139"}) } // Plasma for start frame rearranged := remapping.SliceRearrange(68, 4, true, remapping.XYGridToLinear(68, 4, patterns.PlasmaPanel(68, 4, 40))) currentFrame[0] = remapping.Slice512(rearranged[0]) currentFrame[1] = remapping.Slice512(rearranged[1]) var e queue.QueueItem e.Effect = "red" e.Duration = 40 * 50 globalEffectChannel <- e e.Effect = "plasma" e.Duration = 0 e.Speed = 40 globalEffectChannel <- e go func() { for /*ever*/ { if currentEffect.Duration > 0 { currentEffect.Duration -= 40 } else { if len(globalEffectChannel) > 0 { currentEffect = <- globalEffectChannel } } var rearranged [][]byte switch currentEffect.Effect { case "line": rearranged = remapping.SliceRearrange(68, 4, true, remapping.XYGridToLinear(68, 4, patterns.ZigZag(68, 4))) case "plasma": rearranged = remapping.SliceRearrange(68, 4, true, remapping.XYGridToLinear(68, 4, patterns.PlasmaPanel(68, 4, currentEffect.Speed))) case "red": rearranged = remapping.SliceRearrange(68, 4, false, remapping.XYGridToLinear(68, 4, patterns.RedPanel(68,4))) case "random": rearranged = remapping.SliceRearrange(68, 4, false, remapping.XYGridToLinear(68, 4, patterns.RandomColourPanel(68,4,currentEffect.Speed))) case "linearplasma": rearranged = remapping.SliceRearrange(68, 4, false, patterns.LinearPlasma(68*4)) case "gradientred": rearranged = remapping.SliceRearrange(68, 4, false, patterns.Gradient(255, 0, 0, 0, 0, 255, 0, 68*4)) case "sine": var black patterns.RGBcolor var red patterns.RGBcolor red[0] = 255 rearranged = remapping.SliceRearrange(68, 4, true, remapping.XYGridToLinear(68, 4, patterns.Sinewave(68, 4, black, red, currentEffect.Speed))) case "sinechase": var black patterns.RGBcolor var red patterns.RGBcolor red[0] = 255 rearranged = remapping.SliceRearrange(68, 4, true, remapping.XYGridToLinear(68, 4, patterns.SineChase(68, 4, black, red, currentEffect.Speed))) default: rearranged = remapping.SliceRearrange(68, 4, false, remapping.XYGridToLinear(68, 4, patterns.FillPanel(68,4, 128,0,128))) } //rearranged := remapping.SliceRearrange(68,4,true,linearPlasma(68*4)) sema <- struct{}{} // acquire token currentFrame[0] = remapping.Slice512(rearranged[0]) currentFrame[1] = remapping.Slice512(rearranged[1]) <- sema time.Sleep(40 * time.Millisecond) } }() foreverLoop(); }