aboutsummaryrefslogtreecommitdiff
path: root/ui/widget
diff options
context:
space:
mode:
authorTulir Asokan <tulir@maunium.net>2018-03-23 17:26:06 +0200
committerTulir Asokan <tulir@maunium.net>2018-03-23 17:26:15 +0200
commit7dc773c9907adac23540b8cb8c58cd68b60f9524 (patch)
treec5ef6766a0223244b8a1b49f662135e7fd787936 /ui/widget
parent03e9a0d5ac5329a6e74f3e3bf34ef590c863a6d3 (diff)
Render scroll position and indicate if at end/beginning of history. Fixes #9
Diffstat (limited to 'ui/widget')
-rw-r--r--ui/widget/message-view.go43
1 files changed, 32 insertions, 11 deletions
diff --git a/ui/widget/message-view.go b/ui/widget/message-view.go
index dc0cde5..e482b25 100644
--- a/ui/widget/message-view.go
+++ b/ui/widget/message-view.go
@@ -19,6 +19,7 @@ package widget
import (
"encoding/gob"
"fmt"
+ "math"
"os"
"time"
@@ -37,7 +38,6 @@ type MessageView struct {
DateFormat string
TimestampFormat string
TimestampWidth int
- Separator rune
LoadingMessages bool
widestSender int
@@ -59,7 +59,6 @@ func NewMessageView() *MessageView {
DateFormat: "January _2, 2006",
TimestampFormat: "15:04:05",
TimestampWidth: 8,
- Separator: '|',
ScrollOffset: 0,
messages: make([]*types.Message, 0),
@@ -307,12 +306,9 @@ func (view *MessageView) Draw(screen tcell.Screen) {
return
}
- usernameOffsetX := view.TimestampWidth + TimestampSenderGap
- messageOffsetX := usernameOffsetX + view.widestSender + SenderMessageGap
- separatorX := x + usernameOffsetX + view.widestSender + SenderSeparatorGap
- for separatorY := y; separatorY < y+height; separatorY++ {
- screen.SetContent(separatorX, separatorY, view.Separator, nil, tcell.StyleDefault)
- }
+ usernameX := x + view.TimestampWidth + TimestampSenderGap
+ messageX := usernameX + view.widestSender + SenderMessageGap
+ separatorX := usernameX + view.widestSender + SenderSeparatorGap
indexOffset := len(view.textBuffer) - view.ScrollOffset - height
if indexOffset <= -PaddingAtTop {
@@ -320,7 +316,7 @@ func (view *MessageView) Draw(screen tcell.Screen) {
if view.LoadingMessages {
message = "Loading more messages..."
}
- view.writeLine(screen, message, x+messageOffsetX, y, tcell.ColorGreen)
+ view.writeLine(screen, message, messageX, y, tcell.ColorGreen)
}
if len(view.textBuffer) != len(view.metaBuffer) {
@@ -328,7 +324,15 @@ func (view *MessageView) Draw(screen tcell.Screen) {
return
}
+ totalHeight := float64(len(view.textBuffer))
+ // ceil(height / (totalHeight / height))
+ scrollBarHeight := int(math.Ceil(float64(height) / (totalHeight / float64(height))))
+ // height - ceil(scrollOffset) / totalHeight * height
+ scrollBarPos := height - int(math.Ceil(float64(view.ScrollOffset) / totalHeight * float64(height)))
+
var prevMeta types.MessageMeta
+ firstLine := true
+
for line := 0; line < height; line++ {
index := indexOffset + line
if index < 0 {
@@ -336,6 +340,23 @@ func (view *MessageView) Draw(screen tcell.Screen) {
} else if index >= len(view.textBuffer) {
break
}
+
+ borderChar := '│'
+ borderStyle := tcell.StyleDefault
+ if firstLine && view.ScrollOffset+height >= len(view.textBuffer) {
+ // At top of loaded message history
+ borderChar = '┬'
+ } else if line == height-1 && view.ScrollOffset == 0 {
+ // At bottom of message history
+ borderChar = '┴'
+ } else if line >= scrollBarPos && line < scrollBarPos + scrollBarHeight {
+ // Scroll bar
+ borderChar = '║'
+ borderStyle = borderStyle.Foreground(tcell.ColorGreen)
+ }
+ firstLine = false
+ screen.SetContent(separatorX, y+line, borderChar, nil, borderStyle)
+
text, meta := view.textBuffer[index], view.metaBuffer[index]
if meta != prevMeta {
if len(meta.GetTimestamp()) > 0 {
@@ -344,11 +365,11 @@ func (view *MessageView) Draw(screen tcell.Screen) {
if prevMeta == nil || meta.GetSender() != prevMeta.GetSender() {
view.writeLineRight(
screen, meta.GetSender(),
- x+usernameOffsetX, y+line,
+ usernameX, y+line,
view.widestSender, meta.GetSenderColor())
}
prevMeta = meta
}
- view.writeLine(screen, text, x+messageOffsetX, y+line, meta.GetTextColor())
+ view.writeLine(screen, text, messageX, y+line, meta.GetTextColor())
}
}