mirror of
https://git.sr.ht/~eliasnaur/gio
synced 2026-07-06 09:55:40 +00:00
ui/layout: make List more friendly to for loops
With this change, a List l can be iterated with
for l.Init(...); l.More(); l.Next() {
l.Elem(..., l.Constraints(), l.Index())
}
instead of
l.Init(...)
for {
i, cs, ok := l.Next()
if !ok {
break
}
l.End(..., cs, i))
}
Signed-off-by: Elias Naur <mail@eliasnaur.com>
This commit is contained in:
+41
-12
@@ -40,6 +40,10 @@ type List struct {
|
|||||||
maxSize int
|
maxSize int
|
||||||
children []scrollChild
|
children []scrollChild
|
||||||
dir iterationDir
|
dir iterationDir
|
||||||
|
|
||||||
|
// Iterator state.
|
||||||
|
index int
|
||||||
|
more bool
|
||||||
}
|
}
|
||||||
|
|
||||||
type iterationDir uint8
|
type iterationDir uint8
|
||||||
@@ -50,7 +54,11 @@ const (
|
|||||||
iterateBackward
|
iterateBackward
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// Init prepares the list for iterating through its elements with Next.
|
||||||
func (l *List) Init(ops *ui.Ops, cs Constraints, len int) {
|
func (l *List) Init(ops *ui.Ops, cs Constraints, len int) {
|
||||||
|
if l.more {
|
||||||
|
panic("unfinished element")
|
||||||
|
}
|
||||||
l.update()
|
l.update()
|
||||||
l.ops = ops
|
l.ops = ops
|
||||||
l.dir = iterateNone
|
l.dir = iterateNone
|
||||||
@@ -58,10 +66,12 @@ func (l *List) Init(ops *ui.Ops, cs Constraints, len int) {
|
|||||||
l.children = l.children[:0]
|
l.children = l.children[:0]
|
||||||
l.cs = cs
|
l.cs = cs
|
||||||
l.len = len
|
l.len = len
|
||||||
|
l.more = true
|
||||||
if l.first > len {
|
if l.first > len {
|
||||||
l.first = len
|
l.first = len
|
||||||
}
|
}
|
||||||
ops.Begin()
|
ops.Begin()
|
||||||
|
l.Next()
|
||||||
}
|
}
|
||||||
|
|
||||||
func (l *List) Dragging() bool {
|
func (l *List) Dragging() bool {
|
||||||
@@ -79,20 +89,35 @@ func (l *List) update() {
|
|||||||
l.offset += d
|
l.offset += d
|
||||||
}
|
}
|
||||||
|
|
||||||
func (l *List) Next() (int, Constraints, bool) {
|
// Next advances the list to the next element.
|
||||||
if l.dir != iterateNone {
|
func (l *List) Next() {
|
||||||
panic("a previous Next was not finished with Elem")
|
if !l.more {
|
||||||
|
panic("end of list reached")
|
||||||
|
}
|
||||||
|
i, more := l.next()
|
||||||
|
l.more = more
|
||||||
|
if !more {
|
||||||
|
return
|
||||||
}
|
}
|
||||||
i, ok := l.next()
|
|
||||||
if l.Invert {
|
if l.Invert {
|
||||||
i = l.len - 1 - i
|
i = l.len - 1 - i
|
||||||
}
|
}
|
||||||
var cs Constraints
|
l.index = i
|
||||||
if ok {
|
l.ops.Begin()
|
||||||
cs = axisConstraints(l.Axis, Constraint{Max: ui.Inf}, l.crossConstraintChild(l.cs))
|
}
|
||||||
l.ops.Begin()
|
|
||||||
}
|
// Index is the current element index.
|
||||||
return i, cs, ok
|
func (l *List) Index() int {
|
||||||
|
return l.index
|
||||||
|
}
|
||||||
|
|
||||||
|
// Constraints is the constraints for the current element.
|
||||||
|
func (l *List) Constraints() Constraints {
|
||||||
|
return axisConstraints(l.Axis, Constraint{Max: ui.Inf}, l.crossConstraintChild(l.cs))
|
||||||
|
}
|
||||||
|
|
||||||
|
func (l *List) More() bool {
|
||||||
|
return l.more
|
||||||
}
|
}
|
||||||
|
|
||||||
func (l *List) next() (int, bool) {
|
func (l *List) next() (int, bool) {
|
||||||
@@ -119,7 +144,8 @@ func (l *List) next() (int, bool) {
|
|||||||
return 0, false
|
return 0, false
|
||||||
}
|
}
|
||||||
|
|
||||||
func (l *List) End(dims Dimens) {
|
// Elem completes an element.
|
||||||
|
func (l *List) Elem(dims Dimens) {
|
||||||
block := l.ops.End()
|
block := l.ops.End()
|
||||||
child := scrollChild{dims.Size, block}
|
child := scrollChild{dims.Size, block}
|
||||||
switch l.dir {
|
switch l.dir {
|
||||||
@@ -134,12 +160,15 @@ func (l *List) End(dims Dimens) {
|
|||||||
l.maxSize += mainSize
|
l.maxSize += mainSize
|
||||||
l.children = append([]scrollChild{child}, l.children...)
|
l.children = append([]scrollChild{child}, l.children...)
|
||||||
default:
|
default:
|
||||||
panic("call Next before End")
|
panic("call Next before Elem")
|
||||||
}
|
}
|
||||||
l.dir = iterateNone
|
l.dir = iterateNone
|
||||||
}
|
}
|
||||||
|
|
||||||
func (l *List) Layout() Dimens {
|
func (l *List) Layout() Dimens {
|
||||||
|
if l.more {
|
||||||
|
panic("unfinished element")
|
||||||
|
}
|
||||||
mainc := axisMainConstraint(l.Axis, l.cs)
|
mainc := axisMainConstraint(l.Axis, l.cs)
|
||||||
for len(l.children) > 0 {
|
for len(l.children) > 0 {
|
||||||
sz := l.children[0].size
|
sz := l.children[0].size
|
||||||
|
|||||||
Reference in New Issue
Block a user