Gio news, January 2020

Message ID
DKIM signature
Download raw message
	Simpler Flex and Stack API

The Flex and Stack APIs were unnecessary complex because of a low level
issue blocking a garbage-free simpler API. The new CallOp operation
(described below) resolved that issue, and both layouts have been
reduced to just a single Layout call, similar to layout.List. In
particular, you no longer need to use temporary variables to hold Flex
and Stack children, and you don't need to mind the ordering between
rigid and flexed or stacked children.

For example:

        layout.Flexed(0.5, func() { w2.Layout(gtx) }),
        layout.Rigid(func() { w1.Layout(gtx) }),

is the simplified version of

	f := layout.Flex{}
	c2 := f.Rigid(gtx, func() { w1.Layout(gtx) })
	c1 := f.Flex(gtx, func() { w1.Layout(gtx) })
	f.Layout(gtx, c1, c2)

Notice that in the old API, rigid children (c2 in the example) had to be
first in the code, even when they were needed in a different order in
the Layout call. The new Stack and Flex APIs still lay out rigid
children first, but do so automatically.

The new unified Layout methods also avoid a common misuse of the old,
split API. For example, the following wrong way of insetting a Flex is
no longer possible:

	f := layout.Flex{}
	c2 := f.Rigid(gtx, func() { w1.Layout(gtx) })
	c1 := f.Flex(gtx, func() { w1.Layout(gtx) })
	layout.UniformInset(unit.Dp(8)).Layout(gtx, func() {
		f.Layout(gtx, c1, c2)

(the Rigid and Flex calls had to be inside the Inset Layout method to work

See commits


for the implementation and


for the updates to the examples.

 	New CallOp operation

It is sometimes useful to cache a list of operations for later re-use.
For example, text layouts use cached op.Ops lists to store their
computed layouts, in hope of re-using them when static text is redrawn
in a future frame.

It is also useful to be able to record a list of operations and replay
them after applying modifying operations. All non-trivial layouts do so:
record the layout of a widget, and use its dimensions to compute and
apply an offset before replaying its operations.

The old op.MacroOp did both: it records a list of operations, and the
resulting macro could be replayed from a different op.Ops list.

Unfortunately, the ability to invoke a different operations list also
made the macro escape to the heap when used, blocking the simpler and
garbage-free layout APIs described above.

The new specialized CallOp operation splits out the ability to replay an
operation list, leaving MacroOp with just the ability to record and
replay a particular range of operations on the same list.

See commit


for the implementation.

	New Sponsors

This month saw 4 new sponsors:

	Tom Ingleby (@tingleby)
	Roy E (@royge)
	Vitaliy F. (@funvit)

If you also find my work useful, please consider sponsoring me on


or by reaching out to me directly.

My full-time work on Gio and related open source projects is 100% funded by
donations and sponsorships.
Reply to thread Export thread (mbox)