← back to 4 'counter rotation' effectscompare with ground truth →
model output
Claude Sonnet 4.6
4 'counter rotation' effects
A 0.79T 0.23
1Looking at the animation frames, I can see:
2
31. A 3x3 grid of colored squares (blue, red/crimson, white center) that periodically collapses into a diagonal line and reforms
42. The grid alternates between a 3x3 formation and a diagonal strip of ~5 squares
53. Colors: dark blue (#1e4d6b), crimson/dark red (#9b0030), white center
64. The animation cycles: grid → diagonal → grid → diagonal (opposite direction) → repeat
7
8<!DOCTYPE html>
9<html>
10<head>
11<style>
12 * { margin: 0; padding: 0; box-sizing: border-box; }
13 body { background: #1e1e1e; width: 100vw; height: 100vh; overflow: hidden; }
14 #container {
15 position: absolute;
16 left: 145px;
17 top: 85px;
18 width: 75px;
19 height: 75px;
20 }
21 .sq {
22 position: absolute;
23 width: 22px;
24 height: 22px;
25 border-radius: 5px;
26 }
27</style>
28</head>
29<body>
30<div id="container"></div>
31<script>
32const container = document.getElementById('container');
33
34// 3x3 grid layout
35// Colors pattern:
36// blue red blue
37// red white red
38// blue red blue
39const colors = [
40 '#1e4d6b','#9b0030','#1e4d6b',
41 '#9b0030','#ffffff','#9b0030',
42 '#1e4d6b','#9b0030','#1e4d6b'
43];
44
45const size = 22;
46const gap = 4;
47const step = size + gap;
48
49// Grid positions (3x3)
50const gridPos = [];
51for(let r=0;r<3;r++) for(let c=0;c<3;c++) {
52 gridPos.push({x: c*step, y: r*step});
53}
54
55// Diagonal positions - 5 squares along diagonal (top-right to bottom-left)
56// Frame 2 shows diagonal going from top-right to bottom-left
57// The 9 squares collapse to a diagonal strip of ~5 visible squares
58// Diagonal 1: top-right to bottom-left
59const diag1 = [
60 {x: 52, y: 0},
61 {x: 39, y: 13},
62 {x: 26, y: 26},
63 {x: 13, y: 39},
64 {x: 0, y: 52},
65 {x: 13, y: 39},
66 {x: 26, y: 26},
67 {x: 39, y: 13},
68 {x: 52, y: 0},
69];
70
71// Diagonal 2: top-left to bottom-right
72const diag2 = [
73 {x: 0, y: 0},
74 {x: 13, y: 13},
75 {x: 26, y: 26},
76 {x: 39, y: 39},
77 {x: 52, y: 52},
78 {x: 39, y: 39},
79 {x: 26, y: 26},
80 {x: 13, y: 13},
81 {x: 0, y: 0},
82];
83
84const squares = [];
85for(let i=0;i<9;i++){
86 const d = document.createElement('div');
87 d.className = 'sq';
88 d.style.background = colors[i];
89 d.style.left = gridPos[i].x + 'px';
90 d.style.top = gridPos[i].y + 'px';
91 container.appendChild(d);
92 squares.push(d);
93}
94
95function lerp(a,b,t){ return a+(b-a)*t; }
96function easeInOut(t){ return t<0.5?2*t*t:1-Math.pow(-2*t+2,2)/2; }
97
98let phase = 0; // 0=grid, 1=todiag1, 2=diag1, 3=fromdiag1, 4=grid2, 5=todiag2, 6=diag2, 7=fromdiag2
99let phaseTime = 0;
100const phaseDurations = [600, 400, 200, 400, 600, 400, 200, 400];
101let lastTime = null;
102
103function animate(ts){
104 if(!lastTime) lastTime = ts;
105 const dt = ts - lastTime;
106 lastTime = ts;
107 phaseTime += dt;
108
109 const dur = phaseDurations[phase];
110 let t = Math.min(phaseTime/dur, 1);
111 let et = easeInOut(t);
112
113 if(phase === 0 || phase === 4){
114 // show grid
115 for(let i=0;i<9;i++){
116 squares[i].style.left = gridPos[i].x+'px';
117 squares[i].style.top = gridPos[i].y+'px';
118 squares[i].style.opacity = 1;
119 }
120 } else if(phase === 1){
121 // grid -> diag1
122 for(let i=0;i<9;i++){
123 const x = lerp(gridPos[i].x, diag1[i].x, et);
124 const y = lerp(gridPos[i].y, diag1[i].y, et);
125 squares[i].style.left = x+'px';
126 squares[i].style.top = y+'px';
127 }
128 } else if(phase === 2){
129 for(let i=0;i<9;i++){
130 squares[i].style.left = diag1[i].x+'px';
131 squares[i].style.top = diag1[i].y+'px';
132 }
133 } else if(phase === 3){
134 // diag1 -> grid
135 for(let i=0;i<9;i++){
136 const x = lerp(diag1[i].x, gridPos[i].x, et);
137 const y = lerp(diag1[i].y, gridPos[i].y, et);
138 squares[i].style.left = x+'px';
139 squares[i].style.top = y+'px';
140 }
141 } else if(phase === 5){
142 // grid -> diag2
143 for(let i=0;i<9;i++){
144 const x = lerp(gridPos[i].x, diag2[i].x, et);
145 const y = lerp(gridPos[i].y, diag2[i].y, et);
146 squares[i].style.left = x+'px';
147 squares[i].style.top = y+'px';
148 }
149 } else if(phase === 6){
150 for(let i=0;i<9;i++){
151 squares[i].style.left = diag2[i].x+'px';
152 squares[i].style.top = diag2[i].y+'px';
153 }
154 } else if(phase === 7){
155 // diag2 -> grid
156 for(let i=0;i<9;i++){
157 const x = lerp(diag2[i].x, gridPos[i].x, et);
158 const y = lerp(diag2[i].y, gridPos[i].y, et);
159 squares[i].style.left = x+'px';
160 squares[i].style.top = y+'px';
161 }
162 }
163
164 if(phaseTime >= dur){
165 phaseTime -= dur;
166 phase = (phase+1)%8;
167 }
168
169 requestAnimationFrame(animate);
170}
171requestAnimationFrame(animate);
172</script>
173</body>
174</html>