batch-add albums to infinite scroll grid to slightly improve smoothness

This commit is contained in:
Drew Weymouth
2023-01-28 09:04:17 -08:00
parent e4d2ad00fb
commit fe86cfda47
2 changed files with 34 additions and 54 deletions
+20 -35
View File
@@ -10,7 +10,6 @@ import (
type AlbumIterator interface { type AlbumIterator interface {
Next() *subsonic.AlbumID3 Next() *subsonic.AlbumID3
NextN(int, func(*subsonic.AlbumID3))
} }
type LibraryManager struct { type LibraryManager struct {
@@ -164,18 +163,6 @@ func (r *baseIter) Next() *subsonic.AlbumID3 {
return r.prefetched[0] return r.prefetched[0]
} }
func (r *baseIter) NextN(n int, cb func(*subsonic.AlbumID3)) {
go func() {
for i := 0; i < n; i++ {
a := r.Next()
cb(a)
if a == nil {
break
}
}
}()
}
type searchIter struct { type searchIter struct {
query string query string
artistOffset int artistOffset int
@@ -263,18 +250,6 @@ func (s *searchIter) Next() *subsonic.AlbumID3 {
return nil return nil
} }
func (s *searchIter) NextN(n int, cb func(*subsonic.AlbumID3)) {
go func() {
for i := 0; i < n; i++ {
a := s.Next()
cb(a)
if a == nil {
break
}
}
}()
}
func (s *searchIter) addNewAlbums(al []*subsonic.AlbumID3) { func (s *searchIter) addNewAlbums(al []*subsonic.AlbumID3) {
for _, album := range al { for _, album := range al {
if _, have := s.albumIDset[album.ID]; have { if _, have := s.albumIDset[album.ID]; have {
@@ -386,14 +361,24 @@ func (r *randomIter) Next() *subsonic.AlbumID3 {
return nil return nil
} }
func (r *randomIter) NextN(n int, cb func(*subsonic.AlbumID3)) { type BatchingIterator struct {
go func() { iter AlbumIterator
for i := 0; i < n; i++ { }
a := r.Next()
cb(a) func NewBatchingIterator(iter AlbumIterator) *BatchingIterator {
if a == nil { return &BatchingIterator{iter}
break }
}
} func (b *BatchingIterator) NextN(n int) []*subsonic.AlbumID3 {
}() results := make([]*subsonic.AlbumID3, 0, n)
i := 0
for i < n {
album := b.iter.Next()
if album == nil {
break
}
results = append(results, album)
i++
}
return results
} }
+14 -19
View File
@@ -4,6 +4,7 @@ import (
"context" "context"
"image" "image"
"log" "log"
"supersonic/backend"
"fyne.io/fyne/v2" "fyne.io/fyne/v2"
"fyne.io/fyne/v2/widget" "fyne.io/fyne/v2/widget"
@@ -15,10 +16,6 @@ type ImageFetcher interface {
GetAlbumThumbnail(string) (image.Image, error) GetAlbumThumbnail(string) (image.Image, error)
} }
type AlbumIterator interface {
NextN(int, func(*subsonic.AlbumID3))
}
type AlbumGrid struct { type AlbumGrid struct {
widget.BaseWidget widget.BaseWidget
@@ -29,7 +26,7 @@ type AlbumGrid struct {
type AlbumGridState struct { type AlbumGridState struct {
albums []*subsonic.AlbumID3 albums []*subsonic.AlbumID3
iter AlbumIterator iter *backend.BatchingIterator
fetching bool fetching bool
done bool done bool
showYear bool showYear bool
@@ -58,10 +55,10 @@ func NewFixedAlbumGrid(albums []*subsonic.AlbumID3, fetch ImageFetcher, showYear
return ag return ag
} }
func NewAlbumGrid(iter AlbumIterator, fetch ImageFetcher, showYear bool) *AlbumGrid { func NewAlbumGrid(iter backend.AlbumIterator, fetch ImageFetcher, showYear bool) *AlbumGrid {
ag := &AlbumGrid{ ag := &AlbumGrid{
AlbumGridState: AlbumGridState{ AlbumGridState: AlbumGridState{
iter: iter, iter: backend.NewBatchingIterator(iter),
imageFetcher: fetch, imageFetcher: fetch,
}, },
} }
@@ -94,11 +91,11 @@ func (ag *AlbumGrid) Clear() {
ag.done = true ag.done = true
} }
func (ag *AlbumGrid) Reset(iter AlbumIterator) { func (ag *AlbumGrid) Reset(iter backend.AlbumIterator) {
ag.albums = nil ag.albums = nil
ag.fetching = false ag.fetching = false
ag.done = false ag.done = false
ag.iter = iter ag.iter = backend.NewBatchingIterator(iter)
ag.fetchMoreAlbums(36) ag.fetchMoreAlbums(36)
} }
@@ -182,20 +179,18 @@ func (a *AlbumGrid) fetchMoreAlbums(count int) {
if a.iter == nil { if a.iter == nil {
a.done = true a.done = true
} }
i := 0
a.fetching = true a.fetching = true
a.iter.NextN(count, func(al *subsonic.AlbumID3) { go func() {
if al == nil { albums := a.iter.NextN(count)
a.albums = append(a.albums, albums...)
if len(albums) < count {
a.done = true a.done = true
return
} }
a.albums = append(a.albums, al) a.fetching = false
i++ if len(albums) > 0 {
if i == count { a.Refresh()
a.fetching = false
} }
a.Refresh() }()
})
} }
func (a *AlbumGrid) CreateRenderer() fyne.WidgetRenderer { func (a *AlbumGrid) CreateRenderer() fyne.WidgetRenderer {