package main import ( "citrons.xyz/talk/proto" "citrons.xyz/talk/tui" "sort" ) type channelList []channelListEntry type channelListEntry struct { name string location channelLocation clicked bool } func (cl *channelList) Len() int { return len(*cl) } func (cl *channelList) Less(i, j int) bool { return (*cl)[i].name < (*cl)[j].name } func (cl *channelList) Swap(i, j int) { x := (*cl)[i] (*cl)[i] = (*cl)[j] (*cl)[j] = x } func (cl *channelList) setChannels(cs []proto.Object) { *cl = nil for _, c := range cs { *cl = append(*cl, channelListEntry { c.Fields[""], channelLocation {c.Id}, false, }) } sort.Sort(cl) } func (cl *channelList) remove(location channelLocation) { for i := len(*cl) - 1; i >= 0; i-- { if (*cl)[i].location != location { continue } if i < len(*cl) - 1 { *cl = append((*cl)[:i], (*cl)[i + 1:]...) } else { *cl = (*cl)[:i] } break } } func (cl *channelList) traverse(direction int) int { if len(*cl) == 0 { return 0 } var i int for i = 0; i < len(*cl); i++ { if (*cl)[i].location == globalApp.currentWindow { break } } if i == len(*cl) { i = 0 } else { i += direction i %= len(*cl) if i < 0 { i = len(*cl) + i } } globalApp.goTo((*cl)[i].location) return i } func (cl *channelList) add(name string, location channelLocation) { cl.remove(location) entry := channelListEntry {name, location, false} *cl = append([]channelListEntry {entry}, *cl...) } func (cl *channelList) show(scroll *tui.ScrollState) { mouse := tui.Push("channel list", tui.Box { Width: 12, Height: tui.Fill, Overflow: true, Scroll: scroll, }) scroll.ByMouse(mouse, false) for i, entry := range *cl { var style *tui.Style if entry.location == globalApp.currentWindow { style = &tui.Style {Fg: tui.Black, Bg: tui.White} } else if entry.clicked { style = &tui.Style {Fg: tui.Black, Bg: tui.BrightBlack} } mouse := tui.Push("channel list." + entry.location.id, tui.Box { Width: tui.Fill, Height: 1, NoWrap: true, Style: style, }) if mouse.Button == 0 { if mouse.Pressed { globalApp.redraw = true entry.clicked = true } if mouse.Released { globalApp.redraw = true if entry.clicked { globalApp.goTo(entry.location) } else { for j, entry2 := range *cl { if entry2.clicked { entry2.clicked = false (*cl)[j] = entry entry = entry2 } } } } } ch := globalApp.cache.Get(entry.location.id) if ch != nil { entry.name = ch.Fields[""] } tui.Text(entry.name, nil) tui.Pop() (*cl)[i] = entry } if mouse.Button == 0 && mouse.ReleasedAnywhere { for i, entry := range *cl { globalApp.redraw = globalApp.redraw || entry.clicked entry.clicked = false (*cl)[i] = entry } } tui.Pop() }