File indexing completed on 2025-01-19 03:59:52

0001 from .base import LottieObject, LottieProp, PseudoBool, Index
0002 from .layers import Layer
0003 from .assets import Asset, Chars, Precomp
0004 from .text import FontList
0005 from .composition import Composition
0006 
0007 ##\defgroup Lottie Lottie
0008 #
0009 # Objects of the lottie file structure.
0010 
0011 ## \defgroup LottieCheck Lottie (to check)
0012 #
0013 # Lottie objects that have not been tested
0014 
0015 
0016 ## @ingroup Lottie
0017 class Animation(Composition):
0018     """!
0019     Top level object, describing the animation
0020 
0021     @see http://docs.aenhancers.com/items/compitem/
0022     """
0023     _props = [
0024         LottieProp("version", "v", str, False),
0025         LottieProp("frame_rate", "fr", float, False),
0026         LottieProp("in_point", "ip", float, False),
0027         LottieProp("out_point", "op", float, False),
0028         LottieProp("width", "w", int, False),
0029         LottieProp("height", "h", int, False),
0030         LottieProp("name", "nm", str, False),
0031         LottieProp("threedimensional", "ddd", PseudoBool, False),
0032         LottieProp("assets", "assets", Asset, True),
0033         #LottieProp("comps", "comps", Animation, True),
0034         LottieProp("fonts", "fonts", FontList),
0035         LottieProp("chars", "chars", Chars, True),
0036         #LottieProp("markers", "markers", Marker, True),
0037         #LottieProp("motion_blur", "mb", MotionBlur, False),
0038     ]
0039     _version = "5.5.2"
0040 
0041     def __init__(self, n_frames=60, framerate=60):
0042         super().__init__()
0043         ## The time when the composition work area begins, in frames.
0044         self.in_point = 0
0045         ## The time when the composition work area ends.
0046         ## Sets the final Frame of the animation
0047         self.out_point = n_frames
0048         ## Frames per second
0049         self.frame_rate = framerate
0050         ## Composition Width
0051         self.width = 512
0052         ## Composition has 3-D layers
0053         self.threedimensional = False
0054         ## Composition Height
0055         self.height = 512
0056         ## Bodymovin Version
0057         self.version = self._version
0058         ## Composition name
0059         self.name = None
0060         ## source items that can be used in multiple places. Comps and Images for now.
0061         self.assets = [] # Image, Precomp
0062         ## source chars for text layers
0063         self.chars = None
0064         ## Available fonts
0065         self.fonts = None
0066 
0067     def precomp(self, name):
0068         for ass in self.assets:
0069             if isinstance(ass, Precomp) and ass.id == name:
0070                 return ass
0071         return None
0072 
0073     def _on_prepare_layer(self, layer):
0074         if layer.in_point is None:
0075             layer.in_point = self.in_point
0076         if layer.out_point is None:
0077             layer.out_point = self.out_point
0078 
0079     def tgs_sanitize(self):
0080         """!
0081         Cleans up some things to ensure it works as a telegram sticker
0082         """
0083         if self.width != 512 or self.height != 512:
0084             scale = min(512/self.width, 512/self.height)
0085             self.width = self.height = 512
0086 
0087             for layer in self.layers:
0088                 if layer.parent_index:
0089                     continue
0090 
0091                 if layer.transform.scale.animated:
0092                     for kf in layer.transform.scale.keyframes:
0093                         if kf.start is not None:
0094                             kf.start *= scale
0095                         if kf.end is not None:
0096                             kf.end *= scale
0097                 else:
0098                     layer.transform.scale.value *= scale
0099 
0100                 if layer.transform.position.animated:
0101                     for kf in layer.transform.position.keyframes:
0102                         if kf.start is not None:
0103                             kf.start *= scale
0104                         if kf.end is not None:
0105                             kf.end *= scale
0106                 else:
0107                     layer.transform.position.value *= scale
0108 
0109         if self.frame_rate < 45:
0110             self.frame_rate = 30
0111         else:
0112             self.frame_rate = 60
0113 
0114     def _fixup(self):
0115         super()._fixup()
0116         if self.assets:
0117             for ass in self.assets:
0118                 if isinstance(ass, Precomp):
0119                     ass.animation = self
0120                     ass._fixup()
0121 
0122     def __str__(self):
0123         return self.name or super().__str__()