DirectoryView selects and de-selects files

This commit is contained in:
Sasha Koshka 2023-03-23 14:11:42 -04:00
parent 68341517f7
commit f74f6a43f8
2 changed files with 84 additions and 7 deletions

View File

@ -4,6 +4,7 @@ import "io/fs"
import "image" import "image"
import "path/filepath" import "path/filepath"
import "git.tebibyte.media/sashakoshka/tomo/theme" import "git.tebibyte.media/sashakoshka/tomo/theme"
import "git.tebibyte.media/sashakoshka/tomo/input"
import "git.tebibyte.media/sashakoshka/tomo/artist" import "git.tebibyte.media/sashakoshka/tomo/artist"
import "git.tebibyte.media/sashakoshka/tomo/canvas" import "git.tebibyte.media/sashakoshka/tomo/canvas"
import "git.tebibyte.media/sashakoshka/tomo/config" import "git.tebibyte.media/sashakoshka/tomo/config"
@ -76,7 +77,6 @@ func (element *DirectoryView) SetLocation (
// Update refreshes the directory's contents. // Update refreshes the directory's contents.
func (element *DirectoryView) Update () error { func (element *DirectoryView) Update () error {
defer element.redoAll()
entries, err := element.filesystem.ReadDir(element.location) entries, err := element.filesystem.ReadDir(element.location)
// disown all entries // disown all entries
@ -95,17 +95,18 @@ func (element *DirectoryView) Update () error {
file, err := NewFile ( file, err := NewFile (
filePath, filePath,
element.filesystem) element.filesystem)
if err != nil { return err } if err != nil { continue }
file.SetParent(element) file.SetParent(element)
element.children[index].File = file file.OnChoose (func () {
element.children[index].DirEntry = entry
element.OnChoose (func (filepath string) {
if element.onChoose != nil { if element.onChoose != nil {
element.onChoose(filePath) element.onChoose(filePath)
} }
}) })
element.children[index].File = file
element.children[index].DirEntry = entry
} }
element.redoAll()
return err return err
} }
@ -127,6 +128,19 @@ func (element *DirectoryView) Child (index int) (child elements.Element) {
return element.children[index].File return element.children[index].File
} }
func (element *DirectoryView) HandleMouseDown (x, y int, button input.Button) {
var file *File
for _, entry := range element.children {
if image.Pt(x, y).In(entry.Bounds) {
file = entry.File
}
}
if file != nil {
file.SetSelected(!file.Selected())
}
element.Propagator.HandleMouseDown(x, y, button)
}
func (element *DirectoryView) redoAll () { func (element *DirectoryView) redoAll () {
if !element.core.HasImage() { return } if !element.core.HasImage() { return }

View File

@ -1,7 +1,9 @@
package fileElements package fileElements
import "time"
import "io/fs" import "io/fs"
import "image" import "image"
import "git.tebibyte.media/sashakoshka/tomo/input"
import "git.tebibyte.media/sashakoshka/tomo/theme" import "git.tebibyte.media/sashakoshka/tomo/theme"
import "git.tebibyte.media/sashakoshka/tomo/artist" import "git.tebibyte.media/sashakoshka/tomo/artist"
import "git.tebibyte.media/sashakoshka/tomo/config" import "git.tebibyte.media/sashakoshka/tomo/config"
@ -17,10 +19,14 @@ type File struct {
config config.Wrapped config config.Wrapped
theme theme.Wrapped theme theme.Wrapped
lastClick time.Time
pressed bool
iconID theme.Icon iconID theme.Icon
filesystem fs.StatFS filesystem fs.StatFS
location string location string
selected bool
onChoose func () onChoose func ()
} }
@ -79,15 +85,68 @@ func (element *File) Update () error {
return err return err
} }
func (element *File) Selected () bool {
return element.selected
}
func (element *File) SetSelected (selected bool) {
if element.selected == selected { return }
element.selected = selected
element.drawAndPush()
}
func (element *File) HandleKeyDown (key input.Key, modifiers input.Modifiers) {
if !element.Enabled() { return }
if key == input.KeyEnter {
element.pressed = true
element.drawAndPush()
}
}
func (element *File) HandleKeyUp(key input.Key, modifiers input.Modifiers) {
if key == input.KeyEnter && element.pressed {
element.pressed = false
element.drawAndPush()
if !element.Enabled() { return }
if element.onChoose != nil {
element.onChoose()
}
}
}
func (element *File) OnChoose (callback func ()) { func (element *File) OnChoose (callback func ()) {
element.onChoose = callback element.onChoose = callback
} }
func (element *File) HandleMouseDown (x, y int, button input.Button) {
if !element.Enabled() { return }
if !element.Focused() { element.Focus() }
if button != input.ButtonLeft { return }
element.pressed = true
element.drawAndPush()
}
func (element *File) HandleMouseUp (x, y int, button input.Button) {
if button != input.ButtonLeft { return }
element.pressed = false
within := image.Point { x, y }.
In(element.Bounds())
if time.Since(element.lastClick) < time.Second / 2 {
if element.Enabled() && within && element.onChoose != nil {
element.onChoose()
}
} else {
element.lastClick = time.Now()
}
element.drawAndPush()
}
func (element *File) state () theme.State { func (element *File) state () theme.State {
return theme.State { return theme.State {
Disabled: !element.Enabled(), Disabled: !element.Enabled(),
Focused: element.Focused(), Focused: element.Focused(),
// Pressed: element.pressed, Pressed: element.pressed,
On: element.selected,
} }
} }
@ -119,6 +178,7 @@ func (element *File) drawAll () {
// background // background
state := element.state() state := element.state()
bounds := element.Bounds() bounds := element.Bounds()
sink := element.theme.Sink(theme.PatternButton)
element.theme. element.theme.
Pattern(theme.PatternButton, state). Pattern(theme.PatternButton, state).
Draw(element.core, bounds) Draw(element.core, bounds)
@ -130,6 +190,9 @@ func (element *File) drawAll () {
offset := image.Pt ( offset := image.Pt (
(bounds.Dx() - iconBounds.Dx()) / 2, (bounds.Dx() - iconBounds.Dx()) / 2,
(bounds.Dy() - iconBounds.Dy()) / 2) (bounds.Dy() - iconBounds.Dy()) / 2)
if element.pressed {
offset = offset.Add(sink)
}
icon.Draw ( icon.Draw (
element.core, element.core,
element.theme.Color ( element.theme.Color (