package sim import ( "time" "github.com/jordanorelli/astro-domu/internal/math" ) type entity struct { ID int `json:"id"` Position math.Vec `json:"pos"` Glyph rune `json:"glyph"` name string description string solid bool `json:"-"` overlapped map[int]*entity behavior } func (e *entity) overlapping(others ...*entity) { idx := make(map[int]*entity, len(others)) for i, _ := range others { e2 := others[i] if e2 == e { continue } idx[e2.ID] = e2 } for _, e2 := range e.overlapped { if idx[e2.ID] == nil { e.stopOverlap(e2) } } for _, e2 := range idx { e.overlap(e2) } e.overlapped = idx } func (e *entity) overlap(e2 *entity) { if e.overlapped == nil { e.overlapped = make(map[int]*entity, 4) } type overlapStarter interface { onStartOverlap(*entity) } if e.behavior != nil && e.overlapped[e2.ID] == nil { if b, ok := e.behavior.(overlapStarter); ok { b.onStartOverlap(e2) } } type overlapper interface { onOverlap(*entity) } if e.behavior != nil { if b, ok := e.behavior.(overlapper); ok { b.onOverlap(e2) } } } func (e *entity) stopOverlap(e2 *entity) { type overlapStopper interface { onStopOverlap(*entity) } if e.behavior != nil { if b, ok := e.behavior.(overlapStopper); ok { b.onStopOverlap(e2) } } } type behavior interface { // update is the standard tick function update(time.Duration) } type doNothing struct{} func (d doNothing) update(time.Duration) {}