Skip to content

Commit

Permalink
feat: file table with finished states, customized styling
Browse files Browse the repository at this point in the history
- finished state for receiver shows **all** received files in the table
- finished state for both sender and receiver removes selection of cell
- styling of file table adjusted to Portal's orange color theme
  • Loading branch information
ZinoKader committed Feb 15, 2023
1 parent 6d2876d commit 1a40a29
Show file tree
Hide file tree
Showing 5 changed files with 80 additions and 30 deletions.
5 changes: 4 additions & 1 deletion ui/constants.go
Original file line number Diff line number Diff line change
Expand Up @@ -15,8 +15,9 @@ const (
MAX_WIDTH = 80
PRIMARY_COLOR = "#B8BABA"
SECONDARY_COLOR = "#626262"
DARK_COLOR = "#232323"
ELEMENT_COLOR = "#EE9F40"
SECONDARY_ELEMENT_COLOR = "#EE9F70"
SECONDARY_ELEMENT_COLOR = "#e87d3e"
ERROR_COLOR = "#CC0000"
WARNING_COLOR = "#EE9F5C"
CHECK_COLOR = "#34B233"
Expand Down Expand Up @@ -65,10 +66,12 @@ var Keys = KeyMap{
FileListUp: key.NewBinding(
key.WithKeys("up", "k"),
key.WithHelp("(↑/k)", "file summary up"),
key.WithDisabled(),
),
FileListDown: key.NewBinding(
key.WithKeys("down", "j"),
key.WithHelp("(↓/j)", "file summary down"),
key.WithDisabled(),
),
}

Expand Down
41 changes: 31 additions & 10 deletions ui/filetable/filetable.go
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ import (
)

const (
maxTableHeight = 4
defaultMaxTableHeight = 4
nameColumnWidthFactor float64 = 0.8
sizeColumnWidthFactor float64 = 1 - nameColumnWidthFactor
)
Expand All @@ -30,30 +30,34 @@ type fileRow struct {
}

type Model struct {
Width int
rows []fileRow
table table.Model
Width int
MaxHeight int
rows []fileRow
table table.Model
tableStyles table.Styles
}

func New(opts ...Option) Model {
m := Model{
MaxHeight: defaultMaxTableHeight,
table: table.New(
table.WithFocused(true),
table.WithHeight(maxTableHeight),
table.WithHeight(defaultMaxTableHeight),
),
}

s := table.DefaultStyles()
s.Header = s.Header.
BorderStyle(lipgloss.NormalBorder()).
BorderForeground(lipgloss.Color("240")).
BorderForeground(lipgloss.Color(ui.SECONDARY_COLOR)).
BorderBottom(true).
Bold(true)
s.Selected = s.Selected.
Foreground(lipgloss.Color("229")).
Background(lipgloss.Color("57")).
Foreground(lipgloss.Color(ui.DARK_COLOR)).
Background(lipgloss.Color(ui.SECONDARY_ELEMENT_COLOR)).
Bold(false)
m.table.SetStyles(s)
m.tableStyles = s
m.table.SetStyles(m.tableStyles)

m.updateColumns()
for _, opt := range opts {
Expand All @@ -75,12 +79,19 @@ func WithFiles(filePaths []string) Option {
}
m.rows = append(m.rows, fileRow{path: filePath, formattedSize: formattedSize})
}
m.table.SetHeight(int(math.Min(maxTableHeight, float64(len(filePaths)))))
m.table.SetHeight(int(math.Min(float64(m.MaxHeight), float64(len(filePaths)))))
m.updateColumns()
m.updateRows()
}
}

func WithMaxHeight(height int) Option {
return func(m *Model) {
m.MaxHeight = height
m.updateRows()
}
}

func (m *Model) getMaxWidth() int {
return int(math.Min(ui.MAX_WIDTH-2*ui.MARGIN, float64(m.Width)))
}
Expand Down Expand Up @@ -112,6 +123,16 @@ func (Model) Init() tea.Cmd {
return nil
}

func (m Model) Finalize() tea.Model {
m.table.Blur()

s := m.tableStyles
s.Selected = s.Selected.UnsetBackground().UnsetForeground()
m.table.SetStyles(s)

return m
}

func (m Model) Update(msg tea.Msg) (tea.Model, tea.Cmd) {
var cmd tea.Cmd

Expand Down
36 changes: 23 additions & 13 deletions ui/receiver/receiver.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ package receiver

import (
"fmt"
"math"
"os"
"time"

Expand All @@ -11,14 +12,13 @@ import (
"github.com/SpatiumPortae/portal/internal/semver"
"github.com/SpatiumPortae/portal/protocol/transfer"
"github.com/SpatiumPortae/portal/ui"
"github.com/SpatiumPortae/portal/ui/filetable"
"github.com/SpatiumPortae/portal/ui/transferprogress"
"github.com/charmbracelet/bubbles/help"
"github.com/charmbracelet/bubbles/key"
"github.com/charmbracelet/bubbles/spinner"
tea "github.com/charmbracelet/bubbletea"
"github.com/charmbracelet/lipgloss"
"github.com/muesli/reflow/indent"
"github.com/muesli/reflow/wordwrap"
)

// ------------------------------------------------------ Ui State -----------------------------------------------------
Expand Down Expand Up @@ -79,6 +79,7 @@ type model struct {
width int
spinner spinner.Model
transferProgress transferprogress.Model
fileTable filetable.Model
help help.Model
keys ui.KeyMap
}
Expand All @@ -88,6 +89,7 @@ func New(addr string, password string, opts ...Option) *tea.Program {
m := model{
transferProgress: transferprogress.New(),
msgs: make(chan interface{}, 10),
fileTable: filetable.New(),
password: password,
rendezvousAddr: addr,
help: help.New(),
Expand Down Expand Up @@ -174,12 +176,17 @@ func (m model) Update(msg tea.Msg) (tea.Model, tea.Cmd) {
time.Since(m.transferProgress.TransferStartTime).Round(time.Millisecond).String(),
ui.ByteCountSI(m.transferProgress.TransferSpeedEstimateBps),
)

filetable.WithMaxHeight(math.MaxInt)(&m.fileTable)
m.fileTable = m.fileTable.Finalize().(filetable.Model)
return m, ui.TaskCmd(message, tea.Batch(m.spinner.Tick, decompressCmd(msg.temp)))

case decompressionDoneMsg:
m.state = showFinished
m.receivedFiles = msg.filenames
m.decompressedPayloadSize = msg.decompressedPayloadSize

filetable.WithFiles(m.receivedFiles)(&m.fileTable)
return m, ui.QuitCmd()

case ui.ErrorMsg:
Expand All @@ -192,13 +199,19 @@ func (m model) Update(msg tea.Msg) (tea.Model, tea.Cmd) {
case key.Matches(msg, m.keys.Quit):
return m, tea.Quit
}
return m, nil

fileTableModel, fileTableCmd := m.fileTable.Update(msg)
m.fileTable = fileTableModel.(filetable.Model)

return m, fileTableCmd

case tea.WindowSizeMsg:
m.width = msg.Width
transferProgressModel, cmd := m.transferProgress.Update(msg)
transferProgressModel, transferProgressCmd := m.transferProgress.Update(msg)
m.transferProgress = transferProgressModel.(transferprogress.Model)
return m, cmd
fileTableModel, fileTableCmd := m.fileTable.Update(msg)
m.fileTable = fileTableModel.(filetable.Model)
return m, tea.Batch(transferProgressCmd, fileTableCmd)

default:
var cmd tea.Cmd
Expand Down Expand Up @@ -240,18 +253,15 @@ func (m model) View() string {
ui.PadText + m.help.View(m.keys) + "\n\n"

case showFinished:
indentedWrappedFiles := indent.String(fmt.Sprintf("Received: %s", wordwrap.String(ui.ItalicText(ui.TopLevelFilesText(m.receivedFiles)), ui.MAX_WIDTH)), ui.MARGIN)

var oneOrMoreFiles string
oneOrMoreFiles := "object"
if len(m.receivedFiles) > 1 {
oneOrMoreFiles = "objects"
} else {
oneOrMoreFiles = "object"
oneOrMoreFiles += "s"
}
finishedText := fmt.Sprintf("Received %d %s (%s compressed)\n\n%s", len(m.receivedFiles), oneOrMoreFiles, ui.ByteCountSI(m.payloadSize), indentedWrappedFiles)
finishedText := fmt.Sprintf("Received %d %s (%s compressed)", len(m.receivedFiles), oneOrMoreFiles, ui.ByteCountSI(m.payloadSize))
return ui.PadText + ui.LogSeparator(m.width) +
ui.PadText + ui.InfoStyle(finishedText) + "\n\n" +
ui.PadText + m.transferProgress.View() + "\n\n"
ui.PadText + m.transferProgress.View() + "\n\n" +
m.fileTable.View()

case showError:
return ui.ErrorText(m.errorMessage)
Expand Down
9 changes: 7 additions & 2 deletions ui/sender/sender.go
Original file line number Diff line number Diff line change
Expand Up @@ -105,6 +105,8 @@ func New(filenames []string, addr string, opts ...Option) *tea.Program {
keys: ui.Keys,
copyMessageTimer: timer.NewWithInterval(ui.TEMP_UI_MESSAGE_DURATION, 100*time.Millisecond),
}
m.keys.FileListUp.SetEnabled(true)
m.keys.FileListDown.SetEnabled(true)
for _, opt := range opts {
opt(&m)
}
Expand Down Expand Up @@ -236,6 +238,8 @@ func (m model) Update(msg tea.Msg) (tea.Model, tea.Cmd) {
time.Since(m.transferProgress.TransferStartTime).Round(time.Millisecond).String(),
ui.ByteCountSI(m.transferProgress.TransferSpeedEstimateBps),
)

m.fileTable = m.fileTable.Finalize().(filetable.Model)
return m, ui.TaskCmd(message, ui.QuitCmd())

case ui.ErrorMsg:
Expand Down Expand Up @@ -267,7 +271,6 @@ func (m model) Update(msg tea.Msg) (tea.Model, tea.Cmd) {
m.width = msg.Width
transferProgressModel, transferProgressCmd := m.transferProgress.Update(msg)
m.transferProgress = transferProgressModel.(transferprogress.Model)

fileTableModel, fileTableCmd := m.fileTable.Update(msg)
m.fileTable = fileTableModel.(filetable.Model)
return m, tea.Batch(transferProgressCmd, fileTableCmd)
Expand Down Expand Up @@ -326,13 +329,15 @@ func (m model) View() string {
return ui.PadText + ui.LogSeparator(m.width) +
ui.PadText + ui.InfoStyle(statusText) + "\n\n" +
ui.PadText + m.transferProgress.View() + "\n\n" +
m.fileTable.View() +
ui.PadText + m.help.View(m.keys) + "\n\n"

case showFinished:
finishedText := fmt.Sprintf("Sent %d object(s) (%s compressed)", len(m.fileNames), ui.ByteCountSI(m.payloadSize))
return ui.PadText + ui.LogSeparator(m.width) +
ui.PadText + ui.InfoStyle(finishedText) + "\n\n" +
ui.PadText + m.transferProgress.View() + "\n\n"
ui.PadText + m.transferProgress.View() + "\n\n" +
m.fileTable.View()

case showError:
return ui.ErrorText(m.errorMessage)
Expand Down
19 changes: 15 additions & 4 deletions ui/transferprogress/transferprogress.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ package transferprogress
import (
"fmt"
"math"
"strings"
"time"

"github.com/SpatiumPortae/portal/ui"
Expand Down Expand Up @@ -46,12 +47,22 @@ func (Model) Init() tea.Cmd {
}

func (m Model) View() string {
bytesProgress := fmt.Sprintf("(%s/%s, %s/s)",
ui.ByteCountSI(m.bytesTransferred), ui.ByteCountSI(m.PayloadSize), ui.ByteCountSI(m.TransferSpeedEstimateBps))
eta := fmt.Sprintf("%v remaining", m.estimatedRemainingDuration.Round(time.Second).String())
bytesProgress := strings.Builder{}
bytesProgress.WriteRune('(')
bytesProgress.WriteString(fmt.Sprintf("%s/%s", ui.ByteCountSI(m.bytesTransferred), ui.ByteCountSI(m.PayloadSize)))
if m.TransferSpeedEstimateBps > 0 {
bytesProgress.WriteString(fmt.Sprintf(", %s/s", ui.ByteCountSI(m.TransferSpeedEstimateBps)))
}
bytesProgress.WriteRune(')')

secondsRemaining := m.estimatedRemainingDuration.Round(time.Second)
var eta string
if secondsRemaining > 0 {
eta = fmt.Sprintf("%v remaining", secondsRemaining.String())
}
progressBar := m.progressBar.ViewAs(m.progress)

return bytesProgress + "\t\t" + eta + "\n\n" +
return bytesProgress.String() + "\t\t" + eta + "\n\n" +
ui.PadText + progressBar
}

Expand Down

0 comments on commit 1a40a29

Please sign in to comment.