progress
This commit is contained in:
parent
787a05e493
commit
9a9dcd0d40
4 changed files with 42 additions and 10 deletions
|
@ -56,7 +56,7 @@ func (d *DrawDAG) Draw(screen *ebiten.Image, opts *ebiten.DrawImageOptions) {
|
|||
}
|
||||
// Draw everything in d.dag, where not hidden (itself or any parent)
|
||||
// TODO: handle descendant DrawLayers
|
||||
d.dag.topIterate(func(x Drawer) {
|
||||
d.dag.topWalk(func(x Drawer) {
|
||||
// Is d hidden itself?
|
||||
if h, ok := x.(Hider); ok && h.Hidden() {
|
||||
cache[x] = state{hidden: true}
|
||||
|
@ -351,10 +351,10 @@ func (d *dag) removeVertex(v Drawer) {
|
|||
delete(d.all, v)
|
||||
}
|
||||
|
||||
// topIterate visits each vertex in topological order, in time O(|V| + |E|) and
|
||||
// topWalk visits each vertex in topological order, in time O(|V| + |E|) and
|
||||
// O(|V|) temporary memory.
|
||||
func (d *dag) topIterate(visit func(Drawer)) {
|
||||
// Count indegrees - indegree(v) = len(d.in[v]) for each v.
|
||||
func (d *dag) topWalk(visit func(Drawer)) {
|
||||
// Count indegrees - indegree(v) = len(d.in[v]) for each vertex v.
|
||||
// If indegree(v) = 0, enqueue. Total: O(|V|).
|
||||
queue := make([]Drawer, 0, len(d.in))
|
||||
indegree := make(map[Drawer]int)
|
||||
|
|
|
@ -145,6 +145,32 @@ func (g *Game) Parent(c interface{}) interface{} {
|
|||
return g.par[c]
|
||||
}
|
||||
|
||||
// WalkUp visits the component, its parent, its parent, ..., and then g.
|
||||
func (g *Game) WalkUp(component interface{}, visit func(interface{}) error) error {
|
||||
for p := component; p != nil; p = g.Parent(p) {
|
||||
if err := visit(p); err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// WalkDown visits g, the subcomponent of g, ..., and then the component.
|
||||
func (g *Game) WalkDown(component interface{}, visit func(interface{}) error) error {
|
||||
var stack []interface{}
|
||||
g.dbmu.RLock()
|
||||
for p := component; p != nil; p = g.Parent(p) {
|
||||
stack = append(stack, p)
|
||||
}
|
||||
g.dbmu.RUnlock()
|
||||
for _, p := range stack {
|
||||
if err := visit(p); err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// Query looks for components having both a given ancestor and implementing
|
||||
// a given behaviour (see Behaviors in interface.go). This only returns sensible
|
||||
// values after LoadAndPrepare. Note that every component is its own ancestor.
|
||||
|
|
11
game/aw.go
11
game/aw.go
|
@ -126,13 +126,14 @@ func (aw *Awakeman) realUpdate() error {
|
|||
return err
|
||||
}
|
||||
par := aw.game.Parent(aw)
|
||||
for p := interface{}(aw); p != nil; p = aw.game.Parent(p) {
|
||||
if r, ok := p.(engine.Registrar); ok {
|
||||
if err := r.Register(bubble, par); err != nil {
|
||||
if err := aw.game.WalkDown(par, func(c interface{}) error {
|
||||
if r, ok := c.(engine.Registrar); ok {
|
||||
return r.Register(bubble, par)
|
||||
}
|
||||
return nil
|
||||
}); err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
}
|
||||
if err := engine.PreorderWalk(bubble, func(c, _ interface{}) error {
|
||||
if p, ok := c.(engine.Prepper); ok {
|
||||
return p.Prepare(aw.game)
|
||||
|
|
|
@ -71,7 +71,12 @@ func (b *Bubble) Prepare(g *engine.Game) error {
|
|||
func (b *Bubble) Update() error {
|
||||
b.Life--
|
||||
if b.Life <= 0 {
|
||||
if err := b.game.WalkUp(b, func(c interface{}) error {
|
||||
b.game.Unregister(b)
|
||||
return nil
|
||||
}); err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
if false { // not using MoveX/MoveY/... because collisions are unnecessary -
|
||||
// this is an effect particle, if it overlaps a solid, who cares
|
||||
|
|
Loading…
Reference in a new issue