Skip to content

Commit c5c36c3

Browse files
Merge pull request #2109 from framer/fix/layout-animation-bug
Fixing layout animations after window resize
2 parents ea955e0 + 91b06ce commit c5c36c3

File tree

5 files changed

+56
-8
lines changed

5 files changed

+56
-8
lines changed

dev/tests/layout-resize.tsx

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,14 @@ export const App = () => {
1414
style={{ ...(state ? a : b) }}
1515
onClick={() => setState(!state)}
1616
transition={{ duration: 3 }}
17-
/>
17+
>
18+
<motion.div
19+
layout
20+
id="child"
21+
style={{ width: 100, height: 100, background: "blue" }}
22+
transition={{ duration: 3 }}
23+
/>
24+
</motion.div>
1825
)
1926
}
2027

@@ -33,7 +40,7 @@ const a = {
3340

3441
const b = {
3542
...box,
36-
width: 200,
43+
width: 400,
3744
height: 200,
3845
top: 100,
3946
left: 100,

lerna.json

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,6 @@
11
{
22
"version": "10.12.10",
3-
"packages": [
4-
"packages/*"
5-
],
3+
"packages": ["packages/*"],
64
"npmClient": "yarn",
75
"useWorkspaces": true
86
}

packages/framer-motion-3d/package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -60,5 +60,5 @@
6060
"@react-three/test-renderer": "^9.0.0",
6161
"@rollup/plugin-commonjs": "^22.0.1"
6262
},
63-
"gitHead": "23a64f5f7dec6bc2d2df3f7ea8a661b91ae239d7"
63+
"gitHead": "28d33ed46aab5c48a874ac9ab358d8ef0f7111f9"
6464
}

packages/framer-motion/cypress/integration/layout-resize.ts

Lines changed: 32 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,16 @@ describe("Resize window", () => {
2626
height: 100,
2727
})
2828
})
29+
.get("#child")
30+
.should(([$box]: any) => {
31+
expectBbox($box, {
32+
top: 0,
33+
left: 0,
34+
width: 100,
35+
height: 100,
36+
})
37+
})
38+
.get("#box")
2939
.trigger("click")
3040
.wait(50)
3141
.viewport(200, 200)
@@ -35,12 +45,32 @@ describe("Resize window", () => {
3545
expectBbox($box, {
3646
top: 100,
3747
left: 100,
38-
width: 200,
48+
width: 400,
3949
height: 200,
4050
})
4151
})
52+
.get("#child")
53+
.should(([$box]: any) => {
54+
expectBbox($box, {
55+
top: 100,
56+
left: 100,
57+
width: 100,
58+
height: 100,
59+
})
60+
})
61+
.get("#box")
4262
.trigger("click", { force: true })
4363
.wait(50)
64+
.get("#box")
65+
.should(([$box]: any) => {
66+
expectBbox($box, {
67+
top: 0,
68+
left: 0,
69+
width: 100,
70+
height: 100,
71+
})
72+
})
73+
.get("#child")
4474
.should(([$box]: any) => {
4575
expectBbox($box, {
4676
top: 0,
@@ -49,6 +79,7 @@ describe("Resize window", () => {
4979
height: 100,
5080
})
5181
})
82+
.get("#box")
5283
.wait(200)
5384
.trigger("click", { force: true })
5485
.wait(300)

packages/framer-motion/src/projection/node/create-projection-node.ts

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1238,7 +1238,18 @@ export function createProjectionNode<I>({
12381238

12391239
const { target } = lead
12401240

1241-
if (!target) return
1241+
if (!target) {
1242+
/**
1243+
* If we don't have a target to project into, but we were previously
1244+
* projecting, we want to remove the stored transform and schedule
1245+
* a render to ensure the elements reflect the removed transform.
1246+
*/
1247+
if (this.projectionTransform) {
1248+
this.projectionTransform = "none"
1249+
this.scheduleRender()
1250+
}
1251+
return
1252+
}
12421253

12431254
if (!this.projectionDelta) {
12441255
this.projectionDelta = createDelta()
@@ -1997,6 +2008,7 @@ function resetTransformStyle(node: IProjectionNode) {
19972008
function finishAnimation(node: IProjectionNode) {
19982009
node.finishAnimation()
19992010
node.targetDelta = node.relativeTarget = node.target = undefined
2011+
node.isProjectionDirty = true
20002012
}
20012013

20022014
function resolveTargetDelta(node: IProjectionNode) {

0 commit comments

Comments
 (0)