adventofcode/2016/day11-add/main.go

177 lines
3.8 KiB
Go

package main
import (
"bufio"
"errors"
"fmt"
"os"
"strconv"
"strings"
"github.com/fatih/color"
termbox "github.com/nsf/termbox-go"
)
var elevatorFloor int
var floorInv [][]string
var componentRegistry []string
var cursorPosX, cursorPosY int
var selectItems []string
// This code requires oxford commas in the input
func main() {
input := stdinToStringSlice()
for i := range input {
listIdx := strings.Index(input[i], "a ")
if listIdx == -1 {
floorInv = append(floorInv, []string{})
continue
}
input[i] = input[i][listIdx:]
floorInv = append(floorInv, strings.Split(input[i], ", "))
}
for i := range floorInv {
for j := range floorInv[i] {
tp := "G"
if strings.Contains(floorInv[i][j], "microchip") {
tp = "M"
}
floorInv[i][j] = strings.TrimPrefix(floorInv[i][j], "a ")
floorInv[i][j] = strings.TrimPrefix(floorInv[i][j], "and a ")
ele := strings.ToUpper(floorInv[i][j][:2])
floorInv[i][j] = ele + ":" + tp
componentRegistry = append(componentRegistry, floorInv[i][j])
}
}
err := termbox.Init()
if err != nil {
fmt.Println("Error initializing termbox")
os.Exit(1)
}
defer termbox.Close()
eventQueue := make(chan termbox.Event)
go func() {
for {
eventQueue <- termbox.PollEvent()
}
}()
PrintScreen()
var doQuit bool
for {
select {
case ev := <-eventQueue:
if ev.Type == termbox.EventKey {
switch {
case ev.Key == termbox.KeyArrowLeft:
if cursorPosX > 0 {
cursorPosX--
}
case ev.Key == termbox.KeyArrowRight:
if cursorPosX < len(componentRegistry)-1 {
cursorPosX++
}
case ev.Ch == 'q':
doQuit = true
}
}
ClearScreen()
PrintScreen()
}
if doQuit {
break
}
}
//fmt.Println("Registered Components: ", componentRegistry)
// a microchip without it's generator cannot be on the same floor
// as a different microchip that _does_ have it's generator
// Look at what we have on the lowest floor with items
// For each microchip, find it's generator
// if it's on this floor, take them both up a floor
// If we have microchips, see where their generators are
// If they are with us, take both and move up
// If they are one floor above,
}
func SelectItem() error {
return nil
}
func FloorHasComponent(flr int, cmp string) bool {
for i := range floorInv[flr] {
if floorInv[flr][i] == cmp {
return true
}
}
return false
}
func MoveElevator(dir int, take []string) error {
if len(take) < 1 || len(take) > 2 {
return errors.New("Error tried to move with invalid number of items: " + itoa(len(take)))
}
// Are the requested items on the current floor?
// If so, move them to the floor we're going to
for j := range take {
if FloorHasComponent(elevatorFloor, take[j]) {
// TODO: Move the component
floorInv[elevatorFloor+dir] = append(floorInv[elevatorFloor+dir], take[j])
} else {
return errors.New("Elevator tried to take " + take[j] + " but it's not on floor " + itoa(elevatorFloor+1))
}
}
return nil
}
func ClearScreen() {
fmt.Print("\033[H\033[2J")
}
func PrintScreen() {
c := color.New(color.FgCyan)
w := color.New(color.FgWhite)
g := color.New(color.FgGreen)
g.Add(color.Bold)
for i := len(floorInv); i > 0; i-- {
c.Printf("F%d ", i)
if elevatorFloor == i-1 {
c.Print("E ")
} else {
w.Print(". ")
}
for cr := range componentRegistry {
out := ". "
for j := range floorInv[i-1] {
if floorInv[i-1][j] == componentRegistry[cr] {
out = componentRegistry[cr] + " "
break
}
}
if elevatorFloor == i-1 && cursorPosX == cr {
g.Print(out)
} else {
w.Print(out)
}
}
w.Println("")
}
w.Println("")
}
func stdinToStringSlice() []string {
var input []string
scanner := bufio.NewScanner(os.Stdin)
for scanner.Scan() {
input = append(input, scanner.Text())
}
return input
}
func itoa(i int) string {
return strconv.Itoa(i)
}