internal static GradientStroke NewInstance(JsonObject json, LottieComposition composition) { var name = json.GetNamedString("nm"); var jsonColor = json.GetNamedObject("g", null); if (jsonColor != null && jsonColor.ContainsKey("k")) { jsonColor = jsonColor.GetNamedObject("k"); } AnimatableGradientColorValue color = null; if (jsonColor != null) { color = AnimatableGradientColorValue.Factory.NewInstance(jsonColor, composition); } var jsonOpacity = json.GetNamedObject("o", null); AnimatableIntegerValue opacity = null; if (jsonOpacity != null) { opacity = AnimatableIntegerValue.Factory.NewInstance(jsonOpacity, composition); } var gradientTypeInt = (int)json.GetNamedNumber("t", 1); var gradientType = gradientTypeInt == 1 ? GradientType.Linear : GradientType.Radial; var jsonStartPoint = json.GetNamedObject("s", null); AnimatablePointValue startPoint = null; if (jsonStartPoint != null) { startPoint = AnimatablePointValue.Factory.NewInstance(jsonStartPoint, composition); } var jsonEndPoint = json.GetNamedObject("e", null); AnimatablePointValue endPoint = null; if (jsonEndPoint != null) { endPoint = AnimatablePointValue.Factory.NewInstance(jsonEndPoint, composition); } var width = AnimatableFloatValue.Factory.NewInstance(json.GetNamedObject("w"), composition); var capType = (ShapeStroke.LineCapType)(int)(json.GetNamedNumber("lc") - 1); var joinType = (ShapeStroke.LineJoinType)(int)(json.GetNamedNumber("lj") - 1); AnimatableFloatValue offset = null; var lineDashPattern = new List <AnimatableFloatValue>(); if (json.ContainsKey("d")) { var dashesJson = json.GetNamedArray("d"); for (var i = 0; i < dashesJson.Count; i++) { var dashJson = dashesJson[i].GetObject(); var n = dashJson.GetNamedString("n"); if (n.Equals("o")) { var value = dashJson.GetNamedObject("v"); offset = AnimatableFloatValue.Factory.NewInstance(value, composition); } else if (n.Equals("d") || n.Equals("g")) { var value = dashJson.GetNamedObject("v"); lineDashPattern.Add(AnimatableFloatValue.Factory.NewInstance(value, composition)); } } if (lineDashPattern.Count == 1) { // If there is only 1 value then it is assumed to be equal parts on and off. lineDashPattern.Add(lineDashPattern[0]); } } return(new GradientStroke(name, gradientType, color, opacity, startPoint, endPoint, width, capType, joinType, lineDashPattern, offset)); }
private ShapeTrimPath(string name, Type type, AnimatableFloatValue start, AnimatableFloatValue end, AnimatableFloatValue offset) { Name = name; _type = type; _start = start; _end = end; _offset = offset; }
internal AnimatableSplitDimensionPathValue(AnimatableFloatValue animatableXDimension, AnimatableFloatValue animatableYDimension) { _animatableXDimension = animatableXDimension; _animatableYDimension = animatableYDimension; }
private GradientStroke(string name, GradientType gradientType, AnimatableGradientColorValue gradientColor, AnimatableIntegerValue opacity, AnimatablePointValue startPoint, AnimatablePointValue endPoint, AnimatableFloatValue width, ShapeStroke.LineCapType capType, ShapeStroke.LineJoinType joinType, List <AnimatableFloatValue> lineDashPattern, AnimatableFloatValue dashOffset) { Name = name; GradientType = gradientType; GradientColor = gradientColor; Opacity = opacity; StartPoint = startPoint; EndPoint = endPoint; Width = width; CapType = capType; JoinType = joinType; LineDashPattern = lineDashPattern; DashOffset = dashOffset; }
internal static AnimatableTransform NewInstance(JsonObject json, LottieComposition composition) { AnimatablePathValue anchorPoint; IAnimatableValue <PointF> position = null; AnimatableScaleValue scale; AnimatableFloatValue rotation = null; AnimatableIntegerValue opacity; AnimatableFloatValue startOpacity = null; AnimatableFloatValue endOpacity = null; var anchorJson = json.GetNamedObject("a", null); if (anchorJson != null) { anchorPoint = new AnimatablePathValue(anchorJson["k"], composition); } else { // Cameras don't have an anchor point property. Although we don't support them, at least // we won't crash. Debug.WriteLine("Layer has no transform property. You may be using an unsupported " + "layer type such as a camera.", LottieLog.Tag); anchorPoint = new AnimatablePathValue(); } var positionJson = json.GetNamedObject("p", null); if (positionJson != null) { position = AnimatablePathValue.CreateAnimatablePathOrSplitDimensionPath(positionJson, composition); } else { ThrowMissingTransform("position"); } var scaleJson = json.GetNamedObject("s", null); if (scaleJson != null) { scale = AnimatableScaleValue.Factory.NewInstance(scaleJson, composition); } else { // Repeaters have start/end opacity instead of opacity scale = new AnimatableScaleValue(new List <IKeyframe <ScaleXy> >(), new ScaleXy()); } var rotationJson = json.GetNamedObject("r", null); if (rotationJson == null) { rotationJson = json.GetNamedObject("rz", null); } if (rotationJson != null) { rotation = AnimatableFloatValue.Factory.NewInstance(rotationJson, composition, false); } else { ThrowMissingTransform("rotation"); } var opacityJson = json.GetNamedObject("o", null); if (opacityJson != null) { opacity = AnimatableIntegerValue.Factory.NewInstance(opacityJson, composition); } else { // Somehow some community animations don't have opacity in the transform. opacity = new AnimatableIntegerValue(new List <IKeyframe <int?> >(), 100); } var startOpacityJson = json.GetNamedObject("so", null); if (startOpacityJson != null) { startOpacity = AnimatableFloatValue.Factory.NewInstance(startOpacityJson, composition, false); } var endOpacityJson = json.GetNamedObject("eo", null); if (endOpacityJson != null) { endOpacity = AnimatableFloatValue.Factory.NewInstance(endOpacityJson, composition, false); } return(new AnimatableTransform(anchorPoint, position, scale, rotation, opacity, startOpacity, endOpacity)); }
private AnimatableTransform(AnimatablePathValue anchorPoint, IAnimatableValue <PointF> position, AnimatableScaleValue scale, AnimatableFloatValue rotation, AnimatableIntegerValue opacity, AnimatableFloatValue startOpacity, AnimatableFloatValue endOpacity) { AnchorPoint = anchorPoint; Position = position; Scale = scale; Rotation = rotation; Opacity = opacity; StartOpacity = startOpacity; EndOpacity = endOpacity; }
internal BaseStrokeContent(LottieDrawable lottieDrawable, BaseLayer layer, PenLineCap cap, PenLineJoin join, AnimatableIntegerValue opacity, AnimatableFloatValue width, IList <AnimatableFloatValue> dashPattern, AnimatableFloatValue offset) { _lottieDrawable = lottieDrawable; Paint.Style = Paint.PaintStyle.Stroke; Paint.StrokeCap = cap; Paint.StrokeJoin = join; _opacityAnimation = opacity.CreateAnimation(); _widthAnimation = width.CreateAnimation(); if (offset == null) { _dashPatternOffsetAnimation = null; } else { _dashPatternOffsetAnimation = offset.CreateAnimation(); } _dashPatternAnimations = new List <IBaseKeyframeAnimation <float?> >(dashPattern.Count); _dashPatternValues = new double[dashPattern.Count]; for (var i = 0; i < dashPattern.Count; i++) { _dashPatternAnimations.Add(dashPattern[i].CreateAnimation()); } layer.AddAnimation(_opacityAnimation); layer.AddAnimation(_widthAnimation); for (var i = 0; i < _dashPatternAnimations.Count; i++) { layer.AddAnimation(_dashPatternAnimations[i]); } if (_dashPatternOffsetAnimation != null) { layer.AddAnimation(_dashPatternOffsetAnimation); } _opacityAnimation.ValueChanged += OnValueChanged; _widthAnimation.ValueChanged += OnValueChanged; for (var i = 0; i < dashPattern.Count; i++) { _dashPatternAnimations[i].ValueChanged += OnValueChanged; } if (_dashPatternOffsetAnimation != null) { _dashPatternOffsetAnimation.ValueChanged += OnValueChanged; } }
private GradientFill(string name, GradientType gradientType, PathFillType fillType, AnimatableGradientColorValue gradientColor, AnimatableIntegerValue opacity, AnimatablePointValue startPoint, AnimatablePointValue endPoint, AnimatableFloatValue highlightLength, AnimatableFloatValue highlightAngle) { GradientType = gradientType; FillType = fillType; GradientColor = gradientColor; Opacity = opacity; StartPoint = startPoint; EndPoint = endPoint; Name = name; HighlightLength = highlightLength; HighlightAngle = highlightAngle; }
private PolystarShape(string name, Type type, AnimatableFloatValue points, IAnimatableValue <PointF> position, AnimatableFloatValue rotation, AnimatableFloatValue innerRadius, AnimatableFloatValue outerRadius, AnimatableFloatValue innerRoundedness, AnimatableFloatValue outerRoundedness) { Name = name; _type = type; Points = points; Position = position; Rotation = rotation; InnerRadius = innerRadius; OuterRadius = outerRadius; InnerRoundedness = innerRoundedness; OuterRoundedness = outerRoundedness; }
private Layer(List <IContentModel> shapes, LottieComposition composition, string layerName, long layerId, LayerType layerType, long parentId, string refId, IList <Mask> masks, AnimatableTransform transform, int solidWidth, int solidHeight, Color solidColor, float timeStretch, float startProgress, int preCompWidth, int preCompHeight, AnimatableTextFrame text, AnimatableTextProperties textProperties, List <IKeyframe <float?> > inOutKeyframes, MatteType matteType, AnimatableFloatValue timeRemapping) { _shapes = shapes; _composition = composition; Name = layerName; Id = layerId; _layerType = layerType; ParentId = parentId; RefId = refId; Masks = masks; Transform = transform; SolidWidth = solidWidth; SolidHeight = solidHeight; SolidColor = solidColor; TimeStretch = timeStretch; StartProgress = startProgress; PreCompWidth = preCompWidth; PreCompHeight = preCompHeight; Text = text; TextProperties = textProperties; InOutKeyframes = inOutKeyframes; _matteType = matteType; TimeRemapping = timeRemapping; }
internal static Layer NewInstance(JsonObject json, LottieComposition composition) { var layerName = json.GetNamedString("nm"); var refId = json.GetNamedString("refId", string.Empty); if (layerName.EndsWith(".ai") || json.GetNamedString("cl", "").Equals("ai")) { composition.AddWarning("Convert your Illustrator layers to shape layers."); } var layerId = (long)json.GetNamedNumber("ind"); var solidWidth = 0; var solidHeight = 0; Color solidColor; var preCompWidth = 0; var preCompHeight = 0; LayerType layerType; var layerTypeInt = (int)json.GetNamedNumber("ty", -1); if (layerTypeInt < (int)LayerType.Unknown) { layerType = (LayerType)layerTypeInt; } else { layerType = LayerType.Unknown; } if (layerType == LayerType.Text && !Utils.IsAtLeastVersion(composition, 4, 8, 0)) { layerType = LayerType.Unknown; composition.AddWarning("Text is only supported on bodymovin >= 4.8.0"); } var parentId = (long)json.GetNamedNumber("parent", -1); if (layerType == LayerType.Solid) { solidWidth = (int)(json.GetNamedNumber("sw") * composition.DpScale); solidHeight = (int)(json.GetNamedNumber("sh") * composition.DpScale); solidColor = Utils.GetSolidColorBrush(json.GetNamedString("sc")); Debug.WriteLine("\tSolid=" + string.Format("{0:X}", solidColor) + " " + solidWidth + "x" + solidHeight + " " + composition.Bounds, Tag); } var transform = AnimatableTransform.Factory.NewInstance(json.GetNamedObject("ks"), composition); var matteType = (MatteType)(int)json.GetNamedNumber("tt", 0); var masks = new List <Mask>(); var inOutKeyframes = new List <IKeyframe <float?> >(); var jsonMasks = json.GetNamedArray("masksProperties", null); if (jsonMasks != null) { for (var i = 0; i < jsonMasks.Count; i++) { var mask = Mask.Factory.NewMask(jsonMasks[i].GetObject(), composition); masks.Add(mask); } } var shapes = new List <IContentModel>(); var shapesJson = json.GetNamedArray("shapes", null); if (shapesJson != null) { for (var i = 0; i < shapesJson.Count; i++) { var shape = ShapeGroup.ShapeItemWithJson(shapesJson[i].GetObject(), composition); if (shape != null) { shapes.Add(shape); } } } AnimatableTextFrame text = null; AnimatableTextProperties textProperties = null; var textJson = json.GetNamedObject("t", null); if (textJson != null) { text = AnimatableTextFrame.Factory.NewInstance(textJson.GetNamedObject("d", null), composition); var namedArray = textJson.GetNamedArray("a", null); var propertiesJson = namedArray?.Count > 0 ? namedArray.GetObjectAt(0) : null; textProperties = AnimatableTextProperties.Factory.NewInstance(propertiesJson, composition); } if (json.ContainsKey("ef")) { composition.AddWarning("Lottie doesn't support layer effects. If you are using them for " + " fills, strokes, trim paths etc. then try adding them directly as contents " + " in your shape."); } var timeStretch = (float)json.GetNamedNumber("sr", 1.0); var startFrame = (float)json.GetNamedNumber("st"); var frames = composition.DurationFrames; var startProgress = startFrame / frames; if (layerType == LayerType.PreComp) { preCompWidth = (int)(json.GetNamedNumber("w") * composition.DpScale); preCompHeight = (int)(json.GetNamedNumber("h") * composition.DpScale); } // Bodymovin pre-scales the in frame and out frame by the time stretch. However, that will // cause the stretch to be double counted since the in out animation gets treated the same // as all other animations and will have stretch applied to it again. var inFrame = (float)json.GetNamedNumber("ip") / timeStretch; var outFrame = (float)json.GetNamedNumber("op") / timeStretch; // Before the in frame if (inFrame > 0) { var preKeyframe = new Keyframe <float?>(composition, 0f, 0f, null, 0f, inFrame); inOutKeyframes.Add(preKeyframe); } // The + 1 is because the animation should be visible on the out frame itself. outFrame = outFrame > 0 ? outFrame : composition.EndFrame + 1; var visibleKeyframe = new Keyframe <float?>(composition, 1f, 1f, null, inFrame, outFrame); inOutKeyframes.Add(visibleKeyframe); var outKeyframe = new Keyframe <float?>(composition, 0f, 0f, null, outFrame, float.MaxValue); inOutKeyframes.Add(outKeyframe); AnimatableFloatValue timeRemapping = null; if (json.ContainsKey("tm")) { timeRemapping = AnimatableFloatValue.Factory.NewInstance(json.GetNamedObject("tm", null), composition, false); } return(new Layer(shapes, composition, layerName, layerId, layerType, parentId, refId, masks, transform, solidWidth, solidHeight, solidColor, timeStretch, startProgress, preCompWidth, preCompHeight, text, textProperties, inOutKeyframes, matteType, timeRemapping)); }
private ShapeStroke(string name, AnimatableFloatValue offset, IList <AnimatableFloatValue> lineDashPattern, AnimatableColorValue color, AnimatableIntegerValue opacity, AnimatableFloatValue width, LineCapType capType, LineJoinType joinType) { Name = name; DashOffset = offset; LineDashPattern = lineDashPattern; Color = color; Opacity = opacity; Width = width; CapType = capType; JoinType = joinType; }
private RectangleShape(string name, IAnimatableValue <Vector2?> position, AnimatablePointValue size, AnimatableFloatValue cornerRadius) { Name = name; _position = position; _size = size; _cornerRadius = cornerRadius; }