File indexing completed on 2025-06-01 04:02:27
0001 from .. import base 0002 from lottie import objects, NVector 0003 from .test_helpers import TestTransform 0004 0005 0006 class TestAnimation(base.TestCase): 0007 def test_default(self): 0008 an = objects.Animation() 0009 self.assertDictEqual( 0010 an.to_dict(), 0011 { 0012 "ip": 0, 0013 "op": 60, 0014 "fr": 60, 0015 "w": 512, 0016 "h": 512, 0017 "ddd": 0, 0018 "v": objects.Animation._version, 0019 "layers": [], 0020 "assets": [], 0021 } 0022 ) 0023 0024 def test_name(self): 0025 an = objects.Animation() 0026 an.name = "Foobar" 0027 self.assertDictEqual( 0028 an.to_dict(), 0029 { 0030 "ip": 0, 0031 "op": 60, 0032 "fr": 60, 0033 "w": 512, 0034 "h": 512, 0035 "ddd": 0, 0036 "v": objects.Animation._version, 0037 "layers": [], 0038 "assets": [], 0039 "nm": "Foobar" 0040 } 0041 ) 0042 0043 def test_n_frames(self): 0044 an = objects.Animation(180) 0045 self.assertDictEqual( 0046 an.to_dict(), 0047 { 0048 "ip": 0, 0049 "op": 180, 0050 "fr": 60, 0051 "w": 512, 0052 "h": 512, 0053 "ddd": 0, 0054 "v": objects.Animation._version, 0055 "layers": [], 0056 "assets": [], 0057 } 0058 ) 0059 0060 def test_framerate(self): 0061 an = objects.Animation(60, 24) 0062 self.assertDictEqual( 0063 an.to_dict(), 0064 { 0065 "ip": 0, 0066 "op": 60, 0067 "fr": 24, 0068 "w": 512, 0069 "h": 512, 0070 "ddd": 0, 0071 "v": objects.Animation._version, 0072 "layers": [], 0073 "assets": [], 0074 } 0075 ) 0076 0077 def test_layers(self): 0078 an = objects.Animation() 0079 an.add_layer(objects.NullLayer()) 0080 an.add_layer(objects.ShapeLayer()) 0081 an.insert_layer(0, objects.NullLayer()) 0082 self.assertDictEqual( 0083 an.to_dict(), 0084 { 0085 "ip": 0, 0086 "op": 60, 0087 "fr": 60, 0088 "w": 512, 0089 "h": 512, 0090 "ddd": 0, 0091 "v": objects.Animation._version, 0092 "layers": [ 0093 { 0094 "ty": 3, 0095 "ks": TestTransform._plain_out, 0096 "ao": 0, 0097 "ddd": 0, 0098 "st": 0, 0099 "sr": 1, 0100 "ind": 2, 0101 "ip": 0, 0102 "op": 60, 0103 "bm": 0, 0104 }, 0105 { 0106 "ty": 3, 0107 "ks": TestTransform._plain_out, 0108 "ao": 0, 0109 "ddd": 0, 0110 "st": 0, 0111 "sr": 1, 0112 "ind": 0, 0113 "ip": 0, 0114 "op": 60, 0115 "bm": 0, 0116 }, 0117 { 0118 "ty": 4, 0119 "ks": TestTransform._plain_out, 0120 "ao": 0, 0121 "bm": 0, 0122 "ddd": 0, 0123 "st": 0, 0124 "sr": 1, 0125 "shapes": [], 0126 "ind": 1, 0127 "ip": 0, 0128 "op": 60, 0129 } 0130 ], 0131 "assets": [], 0132 } 0133 ) 0134 0135 def test_layers_preserve(self): 0136 an = objects.Animation() 0137 nl = objects.NullLayer() 0138 nl.index = 42 0139 nl.in_point = 10 0140 nl.out_point = 20 0141 an.add_layer(nl) 0142 self.assertDictEqual( 0143 an.to_dict(), 0144 { 0145 "ip": 0, 0146 "op": 60, 0147 "fr": 60, 0148 "w": 512, 0149 "h": 512, 0150 "ddd": 0, 0151 "v": objects.Animation._version, 0152 "layers": [ 0153 { 0154 "ty": 3, 0155 "ks": TestTransform._plain_out, 0156 "ao": 0, 0157 "ddd": 0, 0158 "st": 0, 0159 "sr": 1, 0160 "bm": 0, 0161 "ind": 42, 0162 "ip": 10, 0163 "op": 20, 0164 }, 0165 ], 0166 "assets": [], 0167 } 0168 ) 0169 0170 def test_clone_same(self): 0171 an = objects.Animation() 0172 nl = objects.NullLayer() 0173 nl.in_point = 10 0174 nl.out_point = 20 0175 an.add_layer(nl) 0176 an2 = an.clone() 0177 0178 self.assertDictEqual( 0179 an2.to_dict(), 0180 { 0181 "ip": 0, 0182 "op": 60, 0183 "fr": 60, 0184 "w": 512, 0185 "h": 512, 0186 "ddd": 0, 0187 "v": objects.Animation._version, 0188 "layers": [ 0189 { 0190 "ty": 3, 0191 "ks": TestTransform._plain_out, 0192 "ao": 0, 0193 "ddd": 0, 0194 "st": 0, 0195 "sr": 1, 0196 "bm": 0, 0197 "ind": 0, 0198 "ip": 10, 0199 "op": 20, 0200 }, 0201 ], 0202 "assets": [], 0203 } 0204 ) 0205 0206 def test_clone_noalias(self): 0207 an = objects.Animation() 0208 nl = objects.NullLayer() 0209 nl.in_point = 10 0210 nl.out_point = 20 0211 an.add_layer(nl) 0212 an2 = an.clone() 0213 0214 nl.in_point = 14 0215 nl.out_point = 24 0216 an.width = 100 0217 an.height = 200 0218 an.add_layer(objects.NullLayer()) 0219 0220 self.assertDictEqual( 0221 an2.to_dict(), 0222 { 0223 "ip": 0, 0224 "op": 60, 0225 "fr": 60, 0226 "w": 512, 0227 "h": 512, 0228 "ddd": 0, 0229 "v": objects.Animation._version, 0230 "layers": [ 0231 { 0232 "ty": 3, 0233 "ks": TestTransform._plain_out, 0234 "ao": 0, 0235 "ddd": 0, 0236 "st": 0, 0237 "sr": 1, 0238 "bm": 0, 0239 "ind": 0, 0240 "ip": 10, 0241 "op": 20, 0242 }, 0243 ], 0244 "assets": [], 0245 } 0246 ) 0247 0248 self.assertNotEqual(an2.to_dict(), an.to_dict()) 0249 0250 def test_sanitize_noanim(self): 0251 an = objects.Animation() 0252 an.add_layer(objects.NullLayer()) 0253 an.width = 128 0254 an.height = 256 0255 an.frame_rate = 69 0256 an.tgs_sanitize() 0257 self.assertEqual( 0258 an.to_dict(), 0259 { 0260 "ip": 0, 0261 "op": 60, 0262 "fr": 60, 0263 "w": 512, 0264 "h": 512, 0265 "ddd": 0, 0266 "v": objects.Animation._version, 0267 "layers": [ 0268 { 0269 "ty": 3, 0270 "ks": { 0271 "a": {"a": 0, "k": [0, 0]}, 0272 "p": {"a": 0, "k": [0, 0]}, 0273 "s": {"a": 0, "k": [200, 200]}, 0274 "r": {"a": 0, "k": 0}, 0275 "o": {"a": 0, "k": 100}, 0276 "sk": {"a": 0, "k": 0}, 0277 "sa": {"a": 0, "k": 0}, 0278 }, 0279 "ao": 0, 0280 "ddd": 0, 0281 "st": 0, 0282 "sr": 1, 0283 "bm": 0, 0284 "ind": 0, 0285 "ip": 0, 0286 "op": 60, 0287 }, 0288 ], 0289 "assets": [], 0290 } 0291 ) 0292 0293 def test_sanitize_noop(self): 0294 an = objects.Animation() 0295 an.add_layer(objects.NullLayer()) 0296 an.tgs_sanitize() 0297 self.assertEqual( 0298 an.to_dict(), 0299 { 0300 "ip": 0, 0301 "op": 60, 0302 "fr": 60, 0303 "w": 512, 0304 "h": 512, 0305 "ddd": 0, 0306 "v": objects.Animation._version, 0307 "layers": [ 0308 { 0309 "ty": 3, 0310 "ks": { 0311 "a": {"a": 0, "k": [0, 0]}, 0312 "p": {"a": 0, "k": [0, 0]}, 0313 "s": {"a": 0, "k": [100, 100]}, 0314 "r": {"a": 0, "k": 0}, 0315 "o": {"a": 0, "k": 100}, 0316 "sk": {"a": 0, "k": 0}, 0317 "sa": {"a": 0, "k": 0}, 0318 }, 0319 "ao": 0, 0320 "ddd": 0, 0321 "st": 0, 0322 "sr": 1, 0323 "bm": 0, 0324 "ind": 0, 0325 "ip": 0, 0326 "op": 60, 0327 }, 0328 ], 0329 "assets": [], 0330 } 0331 ) 0332 0333 def test_sanitize_anim(self): 0334 an = objects.Animation() 0335 nl = an.add_layer(objects.NullLayer()) 0336 nl.transform.scale.add_keyframe(0, NVector(50, 50)) 0337 nl.transform.scale.add_keyframe(60, NVector(200, 200)) 0338 nl.transform.scale.keyframes[-1].start = None 0339 an.width = 128 0340 an.height = 256 0341 an.frame_rate = 69 0342 an.tgs_sanitize() 0343 self.assertEqual( 0344 an.to_dict(), 0345 { 0346 "ip": 0, 0347 "op": 60, 0348 "fr": 60, 0349 "w": 512, 0350 "h": 512, 0351 "ddd": 0, 0352 "v": objects.Animation._version, 0353 "layers": [ 0354 { 0355 "ty": 3, 0356 "ks": { 0357 "a": {"a": 0, "k": [0, 0]}, 0358 "p": {"a": 0, "k": [0, 0]}, 0359 "s": {"a": 1, "k": [ 0360 { 0361 "s": [100, 100], 0362 "e": [400, 400], 0363 "t": 0, 0364 "o": {"x": [0], "y": [0]}, 0365 "i": {"x": [1], "y": [1]}, 0366 }, 0367 { 0368 "t": 60, 0369 }, 0370 ]}, 0371 "r": {"a": 0, "k": 0}, 0372 "o": {"a": 0, "k": 100}, 0373 "sk": {"a": 0, "k": 0}, 0374 "sa": {"a": 0, "k": 0}, 0375 }, 0376 "ao": 0, 0377 "ddd": 0, 0378 "st": 0, 0379 "sr": 1, 0380 "bm": 0, 0381 "ind": 0, 0382 "ip": 0, 0383 "op": 60, 0384 }, 0385 ], 0386 "assets": [], 0387 } 0388 ) 0389 0390 def test_sanitize_lowfr(self): 0391 an = objects.Animation() 0392 an.add_layer(objects.NullLayer()) 0393 an.frame_rate = 23 0394 an.tgs_sanitize() 0395 self.assertEqual( 0396 an.to_dict(), 0397 { 0398 "ip": 0, 0399 "op": 60, 0400 "fr": 30, 0401 "w": 512, 0402 "h": 512, 0403 "ddd": 0, 0404 "v": objects.Animation._version, 0405 "layers": [ 0406 { 0407 "ty": 3, 0408 "ks": { 0409 "a": {"a": 0, "k": [0, 0]}, 0410 "p": {"a": 0, "k": [0, 0]}, 0411 "s": {"a": 0, "k": [100, 100]}, 0412 "r": {"a": 0, "k": 0}, 0413 "o": {"a": 0, "k": 100}, 0414 "sk": {"a": 0, "k": 0}, 0415 "sa": {"a": 0, "k": 0}, 0416 }, 0417 "ao": 0, 0418 "ddd": 0, 0419 "st": 0, 0420 "sr": 1, 0421 "bm": 0, 0422 "ind": 0, 0423 "ip": 0, 0424 "op": 60, 0425 }, 0426 ], 0427 "assets": [], 0428 } 0429 ) 0430 0431 def test_remove_layer(self): 0432 an = objects.Animation() 0433 l0 = objects.layers.NullLayer() 0434 l1 = objects.layers.NullLayer() 0435 l2 = objects.layers.NullLayer() 0436 l3 = objects.layers.NullLayer() 0437 0438 an.add_layer(l0) 0439 an.add_layer(l1) 0440 an.add_layer(l2) 0441 an.add_layer(l3) 0442 0443 l2.parent = l1 0444 0445 self.assertIn(l0, an.layers) 0446 self.assertIn(l1, an.layers) 0447 self.assertIn(l2, an.layers) 0448 self.assertIn(l3, an.layers) 0449 0450 an.remove_layer(l1) 0451 0452 self.assertIn(l0, an.layers) 0453 self.assertNotIn(l1, an.layers) 0454 self.assertNotIn(l2, an.layers) 0455 self.assertIn(l3, an.layers)