internal/ops,gpu: remove transform fields from ops.Key

The transformation information in ops.Key is a layer violation.
Introduce a key type specific to package gpu and use that instead.

Signed-off-by: Elias Naur <mail@eliasnaur.com>
This commit is contained in:
Elias Naur
2021-07-19 16:37:06 +02:00
parent e4fe56c456
commit 62a8b80c81
3 changed files with 31 additions and 28 deletions
+5 -6
View File
@@ -6,7 +6,6 @@ import (
"fmt" "fmt"
"gioui.org/f32" "gioui.org/f32"
"gioui.org/internal/ops"
) )
type resourceCache struct { type resourceCache struct {
@@ -19,7 +18,7 @@ type resourceCache struct {
// since benchmarking showed them as a bottleneck. // since benchmarking showed them as a bottleneck.
type opCache struct { type opCache struct {
// store the index + 1 in cache this key is stored in // store the index + 1 in cache this key is stored in
index map[ops.Key]int index map[opKey]int
// list of indexes in cache that are free and can be used // list of indexes in cache that are free and can be used
freelist []int freelist []int
cache []opCacheValue cache []opCacheValue
@@ -32,7 +31,7 @@ type opCacheValue struct {
bounds f32.Rectangle bounds f32.Rectangle
// the fields below are handled by opCache // the fields below are handled by opCache
key ops.Key key opKey
keep bool keep bool
} }
@@ -83,13 +82,13 @@ func (r *resourceCache) release() {
func newOpCache() *opCache { func newOpCache() *opCache {
return &opCache{ return &opCache{
index: make(map[ops.Key]int), index: make(map[opKey]int),
freelist: make([]int, 0), freelist: make([]int, 0),
cache: make([]opCacheValue, 0), cache: make([]opCacheValue, 0),
} }
} }
func (r *opCache) get(key ops.Key) (o opCacheValue, exist bool) { func (r *opCache) get(key opKey) (o opCacheValue, exist bool) {
v := r.index[key] v := r.index[key]
if v == 0 { if v == 0 {
return return
@@ -98,7 +97,7 @@ func (r *opCache) get(key ops.Key) (o opCacheValue, exist bool) {
return r.cache[v-1], true return r.cache[v-1], true
} }
func (r *opCache) put(key ops.Key, val opCacheValue) { func (r *opCache) put(key opKey, val opCacheValue) {
v := r.index[key] v := r.index[key]
val.keep = true val.keep = true
val.key = key val.key = key
+23 -8
View File
@@ -122,7 +122,7 @@ type pathOp struct {
// later clip rectangles. // later clip rectangles.
clip image.Rectangle clip image.Rectangle
bounds f32.Rectangle bounds f32.Rectangle
pathKey ops.Key pathKey opKey
path bool path bool
pathVerts []byte pathVerts []byte
parent *pathOp parent *pathOp
@@ -154,10 +154,15 @@ func decodeStrokeOp(data []byte) clip.StrokeStyle {
} }
type quadsOp struct { type quadsOp struct {
key ops.Key key opKey
aux []byte aux []byte
} }
type opKey struct {
sx, hx, sy, hy float32
ops.Key
}
type material struct { type material struct {
material materialType material materialType
opaque bool opaque bool
@@ -829,7 +834,7 @@ func (d *drawOps) newPathOp() *pathOp {
return &d.pathOpCache[len(d.pathOpCache)-1] return &d.pathOpCache[len(d.pathOpCache)-1]
} }
func (d *drawOps) addClipPath(state *drawState, aux []byte, auxKey ops.Key, bounds f32.Rectangle, off f32.Point, tr f32.Affine2D, stroke clip.StrokeStyle) { func (d *drawOps) addClipPath(state *drawState, aux []byte, auxKey opKey, bounds f32.Rectangle, off f32.Point, tr f32.Affine2D, stroke clip.StrokeStyle) {
npath := d.newPathOp() npath := d.newPathOp()
*npath = pathOp{ *npath = pathOp{
parent: state.cpath, parent: state.cpath,
@@ -864,6 +869,15 @@ func (d *drawOps) save(id int, state drawState) {
d.states[id] = state d.states[id] = state
} }
func (k opKey) SetTransform(t f32.Affine2D) opKey {
sx, hx, _, hy, sy, _ := t.Elems()
k.sx = sx
k.hx = hx
k.hy = hy
k.sy = sy
return k
}
func (d *drawOps) collectOps(r *ops.Reader, state drawState) { func (d *drawOps) collectOps(r *ops.Reader, state drawState) {
var ( var (
quads quadsOp quads quadsOp
@@ -889,7 +903,7 @@ loop:
break loop break loop
} }
quads.aux = encOp.Data[opconst.TypeAuxLen:] quads.aux = encOp.Data[opconst.TypeAuxLen:]
quads.key = encOp.Key quads.key = opKey{Key: encOp.Key}
case opconst.TypeClip: case opconst.TypeClip:
var op clipOp var op clipOp
@@ -919,8 +933,8 @@ loop:
} }
} else { } else {
quads.aux, op.bounds, _ = d.boundsForTransformedRect(bounds, trans) quads.aux, op.bounds, _ = d.boundsForTransformedRect(bounds, trans)
quads.key = encOp.Key quads.key = opKey{Key: encOp.Key}
quads.key.SetTransform(trans) quads.key.SetTransform(trans) // TODO: This call has no effect.
} }
state.clip = state.clip.Intersect(op.bounds.Add(off)) state.clip = state.clip.Intersect(op.bounds.Add(off))
d.addClipPath(&state, quads.aux, quads.key, op.bounds, off, state.t, str) d.addClipPath(&state, quads.aux, quads.key, op.bounds, off, state.t, str)
@@ -962,8 +976,9 @@ loop:
if clipData != nil { if clipData != nil {
// The paint operation is sheared or rotated, add a clip path representing // The paint operation is sheared or rotated, add a clip path representing
// this transformed rectangle. // this transformed rectangle.
encOp.Key.SetTransform(trans) k := opKey{Key: encOp.Key}
d.addClipPath(&state, clipData, encOp.Key, bnd, off, state.t, clip.StrokeStyle{}) k.SetTransform(trans) // TODO: This call has no effect.
d.addClipPath(&state, clipData, k, bnd, off, state.t, clip.StrokeStyle{})
} }
bounds := boundRectF(cl) bounds := boundRectF(cl)
+3 -14
View File
@@ -5,7 +5,6 @@ package ops
import ( import (
"encoding/binary" "encoding/binary"
"gioui.org/f32"
"gioui.org/internal/opconst" "gioui.org/internal/opconst"
"gioui.org/op" "gioui.org/op"
) )
@@ -29,10 +28,9 @@ type EncodedOp struct {
// Key is a unique key for a given op. // Key is a unique key for a given op.
type Key struct { type Key struct {
ops *op.Ops ops *op.Ops
pc int pc int
version int version int
sx, hx, sy, hy float32
} }
// Shadow of op.MacroOp. // Shadow of op.MacroOp.
@@ -80,15 +78,6 @@ func NewPC(ops *op.Ops) PC {
} }
} }
func (k Key) SetTransform(t f32.Affine2D) Key {
sx, hx, _, hy, sy, _ := t.Elems()
k.sx = sx
k.hx = hx
k.hy = hy
k.sy = sy
return k
}
func (r *Reader) Decode() (EncodedOp, bool) { func (r *Reader) Decode() (EncodedOp, bool) {
if r.ops == nil { if r.ops == nil {
return EncodedOp{}, false return EncodedOp{}, false