Skip to content

Commit

Permalink
Add a transform.ChangeParent(child, parent, keepWorldPosition) Functi…
Browse files Browse the repository at this point in the history
…on (#111)

* add change parent

* fix tests

* fix children test
  • Loading branch information
PKuebler authored Nov 1, 2023
1 parent d9268f9 commit 5f480b5
Show file tree
Hide file tree
Showing 4 changed files with 126 additions and 0 deletions.
43 changes: 43 additions & 0 deletions features/hierarchy/example_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -172,6 +172,49 @@ func TestFindChildren(t *testing.T) {
}
}

func TestChangeParent(t *testing.T) {
w := donburi.NewWorld()

parent1 := donburi.NewTag().SetName("parent1")
parent2 := donburi.NewTag().SetName("parent2")
child := donburi.NewTag().SetName("child")

p1e := w.Entry(w.Create(parent1))
p2e := w.Entry(w.Create(parent2))
ce := w.Entry(w.Create(child))

// no parent exists
ChangeParent(ce, p1e)
testChildren(t, []childrenTest{
{
Parent: p1e,
Children: []*donburi.Entry{ce},
},
})

// change to same parent
ChangeParent(ce, p1e)
testChildren(t, []childrenTest{
{
Parent: p1e,
Children: []*donburi.Entry{ce},
},
})

// change parent
ChangeParent(ce, p2e)
testChildren(t, []childrenTest{
{
Parent: p1e,
Children: []*donburi.Entry{},
},
{
Parent: p2e,
Children: []*donburi.Entry{ce},
},
})
}

type childrenTest struct {
Parent *donburi.Entry
Children []*donburi.Entry
Expand Down
33 changes: 33 additions & 0 deletions features/hierarchy/parent.go
Original file line number Diff line number Diff line change
Expand Up @@ -89,6 +89,39 @@ func HasParent(entry *donburi.Entry) bool {
return entry.HasComponent(parentComponent)
}

// ChangeParent changes a parent of the entry.
func ChangeParent(child *donburi.Entry, newParent *donburi.Entry) {
if !newParent.Valid() {
panic("newParent is not valid")
}
if !child.Valid() {
panic("child is not valid")
}
if !newParent.HasComponent(childrenComponent) {
newParent.AddComponent(childrenComponent)
}

if oldParent, ok := GetParent(child); ok {
if oldParent == newParent {
return
}

if oldParent.Valid() {
oldChildren := donburi.Get[childrenData](oldParent, childrenComponent)
for i, c := range oldChildren.Children {
if c == child {
oldChildren.Children = append(oldChildren.Children[:i], oldChildren.Children[i+1:]...)
break
}
}
}

child.RemoveComponent(parentComponent)
}

SetParent(child, newParent)
}

func getParentData(entry *donburi.Entry) (*parentData, bool) {
if HasParent(entry) {
p := donburi.Get[parentData](entry, parentComponent)
Expand Down
34 changes: 34 additions & 0 deletions features/transform/transform.go
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,16 @@ func AppendChild(parent, child *donburi.Entry, keepWorldPosition bool) {
SetParent(child, parent, keepWorldPosition)
}

// ChangeParent changes parent of the entry.
func ChangeParent(child, parent *donburi.Entry, keepWorldPosition bool) {
if !child.HasComponent(Transform) {
panic("entry does not have transform component")
}
RemoveParent(child, keepWorldPosition)
hierarchy.ChangeParent(child, parent)
SetParent(child, parent, keepWorldPosition)
}

// SetParent sets parent to the entry.
func SetParent(entry, parent *donburi.Entry, keepWorldPosition bool) {
if !entry.HasComponent(Transform) {
Expand Down Expand Up @@ -73,6 +83,30 @@ func GetParent(entry *donburi.Entry) (*donburi.Entry, bool) {
return hierarchy.GetParent(entry)
}

// RemoveParent removes parent of the entry.
func RemoveParent(entry *donburi.Entry, keepWorldPosition bool) {
d := GetTransform(entry)
if !d.hasParent {
return
}
parent, _ := GetParent(entry)
d.hasParent = false
if keepWorldPosition {
parentPos := WorldPosition(parent)

d.LocalPosition = d.LocalPosition.Add(parentPos)
d.LocalRotation += WorldRotation(parent)

ws := WorldScale(parent)
if ws.X != 0 {
d.LocalScale.X = d.LocalScale.X * ws.X
}
if ws.Y != 0 {
d.LocalScale.Y = d.LocalScale.Y * ws.Y
}
}
}

// GetChildren returns children of the entry.
func GetChildren(entry *donburi.Entry) ([]*donburi.Entry, bool) {
return hierarchy.GetChildren(entry)
Expand Down
16 changes: 16 additions & 0 deletions features/transform/transform_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,14 @@ func TestTransform(t *testing.T) {
Rotation: 180,
Scale: dmath.Vec2{X: 2, Y: 3},
})

transform.RemoveParent(parent, false)

testWorldTransform(t, child, &testTransform{
Position: dmath.Vec2{X: 1, Y: 2},
Rotation: 180,
Scale: dmath.Vec2{X: 2, Y: 3},
})
}

func TestTransformKeepWorldPosition(t *testing.T) {
Expand All @@ -64,6 +72,14 @@ func TestTransformKeepWorldPosition(t *testing.T) {
Rotation: 90,
Scale: dmath.Vec2{X: 1.5, Y: 1.5},
})

transform.RemoveParent(parent, true)

testWorldTransform(t, child, &testTransform{
Position: dmath.Vec2{X: 1, Y: 2},
Rotation: 90,
Scale: dmath.Vec2{X: 1.5, Y: 1.5},
})
}

func TestTransformDefaultValue(t *testing.T) {
Expand Down

0 comments on commit 5f480b5

Please sign in to comment.