Compare commits
6 Commits
Author | SHA1 | Date | |
---|---|---|---|
66e644d043 | |||
3dab382b76 | |||
078e661fd4 | |||
336890cafe | |||
35ca2dc972 | |||
78aeed452f |
30
CHANGELOG.md
@ -1,44 +1,50 @@
|
|||||||
## [0.3.1] - 2020-03-05
|
## [0.3.3]
|
||||||
|
- Fix a bug with rounded rectangle shape
|
||||||
|
|
||||||
|
## [0.3.2]
|
||||||
|
- Fix a bug with "repeater" content
|
||||||
|
|
||||||
|
## [0.3.1]
|
||||||
- Support dashed path
|
- Support dashed path
|
||||||
|
|
||||||
## [0.3.0+1] - 2020-03-05
|
## [0.3.0+1]
|
||||||
- Specify a version range for the dependency on `characters`.
|
- Specify a version range for the dependency on `characters`.
|
||||||
|
|
||||||
## [0.3.0] - 2020-03-05
|
## [0.3.0]
|
||||||
- Add `LottieDelegates` a group of options to customize the lottie animation at runtime.
|
- Add `LottieDelegates` a group of options to customize the lottie animation at runtime.
|
||||||
ie: Dynamically modify color, position, size, text... of every elements of the animation.
|
ie: Dynamically modify color, position, size, text... of every elements of the animation.
|
||||||
- Correctly display Linear and Radial Gradients
|
- Correctly display Linear and Radial Gradients
|
||||||
- Integrate latest changes from Lottie-android
|
- Integrate latest changes from Lottie-android
|
||||||
|
|
||||||
## [0.2.2] - 2020-02-21
|
## [0.2.2]
|
||||||
- Add a [repeat] parameter to specify if the automatic animation should loop.
|
- Add a [repeat] parameter to specify if the automatic animation should loop.
|
||||||
- Add the [animate], [reverse], [repeat] properties on `LottieBuilder`
|
- Add the [animate], [reverse], [repeat] properties on `LottieBuilder`
|
||||||
- Fix bug with `onLoaded` callback when the `LottieProvider` is changed
|
- Fix bug with `onLoaded` callback when the `LottieProvider` is changed
|
||||||
|
|
||||||
## [0.2.1] - 2020-02-11
|
## [0.2.1]
|
||||||
- Fix a big bug in the path transformation code. A lot more animations look correct now.
|
- Fix a big bug in the path transformation code. A lot more animations look correct now.
|
||||||
|
|
||||||
## [0.2.0+1] - 2020-02-04
|
## [0.2.0+1]
|
||||||
- Improve readme
|
- Improve readme
|
||||||
- (internal) Add golden tests
|
- (internal) Add golden tests
|
||||||
|
|
||||||
## [0.2.0] - 2020-02-02
|
## [0.2.0]
|
||||||
- Support loading the animation and its images from a zip file
|
- Support loading the animation and its images from a zip file
|
||||||
- Breaking: `LottieComposition.fromBytes` and `fromByteData` are now asynchronous.
|
- Breaking: `LottieComposition.fromBytes` and `fromByteData` are now asynchronous.
|
||||||
|
|
||||||
## [0.1.4] - 2020-02-02
|
## [0.1.4]
|
||||||
- Support images in animation
|
- Support images in animation
|
||||||
- Basic support for text in animation (work in progress)
|
- Basic support for text in animation (work in progress)
|
||||||
|
|
||||||
## [0.1.3] - 2020-02-01
|
## [0.1.3]
|
||||||
- Support Polystar shape
|
- Support Polystar shape
|
||||||
- Reorganize examples.
|
- Reorganize examples.
|
||||||
|
|
||||||
## [0.1.2] - 2020-01-31
|
## [0.1.2]
|
||||||
- Implement `Lottie.network`, `Lottie.file` and `Lottie.memory`
|
- Implement `Lottie.network`, `Lottie.file` and `Lottie.memory`
|
||||||
|
|
||||||
## [0.1.1] - 2020-01-31
|
## [0.1.1]
|
||||||
- Fix analysis lints
|
- Fix analysis lints
|
||||||
|
|
||||||
## [0.1.0] - 2020-01-31
|
## [0.1.0]
|
||||||
- Initial conversion of [lottie-android](https://github.com/airbnb/lottie-android) to Dart/Flutter
|
- Initial conversion of [lottie-android](https://github.com/airbnb/lottie-android) to Dart/Flutter
|
||||||
|
43
README.md
@ -82,8 +82,8 @@ class _MyAppState extends State<MyApp> with TickerProviderStateMixin {
|
|||||||
home: Scaffold(
|
home: Scaffold(
|
||||||
body: ListView(
|
body: ListView(
|
||||||
children: [
|
children: [
|
||||||
Lottie.network(
|
Lottie.asset(
|
||||||
'https://raw.githubusercontent.com/xvrh/lottie-flutter/master/example/assets/Mobilo/C.json',
|
'assets/LottieLogo1.json',
|
||||||
controller: _controller,
|
controller: _controller,
|
||||||
onLoaded: (composition) {
|
onLoaded: (composition) {
|
||||||
// Configure the AnimationController with the duration of the
|
// Configure the AnimationController with the duration of the
|
||||||
@ -182,14 +182,13 @@ class CustomDrawer extends StatelessWidget {
|
|||||||
}
|
}
|
||||||
|
|
||||||
class _Painter extends CustomPainter {
|
class _Painter extends CustomPainter {
|
||||||
final LottieComposition composition;
|
final LottieDrawable drawable;
|
||||||
|
|
||||||
_Painter(this.composition);
|
_Painter(LottieComposition composition)
|
||||||
|
: drawable = LottieDrawable(composition);
|
||||||
|
|
||||||
@override
|
@override
|
||||||
void paint(Canvas canvas, Size size) {
|
void paint(Canvas canvas, Size size) {
|
||||||
var drawable = LottieDrawable(composition);
|
|
||||||
|
|
||||||
var frameCount = 40;
|
var frameCount = 40;
|
||||||
var columns = 10;
|
var columns = 10;
|
||||||
for (var i = 0; i < frameCount; i++) {
|
for (var i = 0; i < frameCount; i++) {
|
||||||
@ -219,22 +218,22 @@ class _Animation extends StatelessWidget {
|
|||||||
return Lottie.asset(
|
return Lottie.asset(
|
||||||
'assets/Tests/Shapes.json',
|
'assets/Tests/Shapes.json',
|
||||||
delegates: LottieDelegates(
|
delegates: LottieDelegates(
|
||||||
text: (initialText) => translate(initialText),
|
text: (initialText) => '**$initialText**',
|
||||||
values: [
|
values: [
|
||||||
ValueDelegate.color(
|
ValueDelegate.color(
|
||||||
const ['Shape Layer 1', 'Rectangle', 'Fill 1'],
|
const ['Shape Layer 1', 'Rectangle', 'Fill 1'],
|
||||||
value: Colors.red,
|
value: Colors.red,
|
||||||
),
|
),
|
||||||
ValueDelegate.opacity(
|
ValueDelegate.opacity(
|
||||||
const ['Shape Layer 1', 'Rectangle'],
|
const ['Shape Layer 1', 'Rectangle'],
|
||||||
callback: (frameInfo) =>
|
callback: (frameInfo) => (frameInfo.overallProgress * 100).round(),
|
||||||
(frameInfo.overallProgress * 100).round(),
|
),
|
||||||
),
|
ValueDelegate.position(
|
||||||
ValueDelegate.position(
|
const ['Shape Layer 1', 'Rectangle', '**'],
|
||||||
const ['Shape Layer 1', 'Rectangle'],
|
relative: Offset(100, 200),
|
||||||
relative: Offset(100, 200),
|
),
|
||||||
),
|
],
|
||||||
]),
|
),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
1458
example/assets/17297-fireworks.json
Normal file
@ -30,8 +30,8 @@ class _MyAppState extends State<MyApp> with TickerProviderStateMixin {
|
|||||||
home: Scaffold(
|
home: Scaffold(
|
||||||
body: ListView(
|
body: ListView(
|
||||||
children: [
|
children: [
|
||||||
Lottie.network(
|
Lottie.asset(
|
||||||
'https://raw.githubusercontent.com/xvrh/lottie-flutter/master/example/assets/Mobilo/C.json',
|
'assets/LottieLogo1.json',
|
||||||
controller: _controller,
|
controller: _controller,
|
||||||
onLoaded: (composition) {
|
onLoaded: (composition) {
|
||||||
// Configure the AnimationController with the duration of the
|
// Configure the AnimationController with the duration of the
|
||||||
|
@ -69,14 +69,13 @@ class CustomDrawer extends StatelessWidget {
|
|||||||
}
|
}
|
||||||
|
|
||||||
class _Painter extends CustomPainter {
|
class _Painter extends CustomPainter {
|
||||||
final LottieComposition composition;
|
final LottieDrawable drawable;
|
||||||
|
|
||||||
_Painter(this.composition);
|
_Painter(LottieComposition composition)
|
||||||
|
: drawable = LottieDrawable(composition);
|
||||||
|
|
||||||
@override
|
@override
|
||||||
void paint(Canvas canvas, Size size) {
|
void paint(Canvas canvas, Size size) {
|
||||||
var drawable = LottieDrawable(composition);
|
|
||||||
|
|
||||||
var frameCount = 40;
|
var frameCount = 40;
|
||||||
var columns = 10;
|
var columns = 10;
|
||||||
for (var i = 0; i < frameCount; i++) {
|
for (var i = 0; i < frameCount; i++) {
|
||||||
|
@ -16,8 +16,6 @@ class MyApp extends StatelessWidget {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
String translate(String input) => '**$input**';
|
|
||||||
|
|
||||||
//--- example
|
//--- example
|
||||||
class _Animation extends StatelessWidget {
|
class _Animation extends StatelessWidget {
|
||||||
@override
|
@override
|
||||||
@ -25,22 +23,22 @@ class _Animation extends StatelessWidget {
|
|||||||
return Lottie.asset(
|
return Lottie.asset(
|
||||||
'assets/Tests/Shapes.json',
|
'assets/Tests/Shapes.json',
|
||||||
delegates: LottieDelegates(
|
delegates: LottieDelegates(
|
||||||
text: (initialText) => translate(initialText),
|
text: (initialText) => '**$initialText**',
|
||||||
values: [
|
values: [
|
||||||
ValueDelegate.color(
|
ValueDelegate.color(
|
||||||
const ['Shape Layer 1', 'Rectangle', 'Fill 1'],
|
const ['Shape Layer 1', 'Rectangle', 'Fill 1'],
|
||||||
value: Colors.red,
|
value: Colors.red,
|
||||||
),
|
),
|
||||||
ValueDelegate.opacity(
|
ValueDelegate.opacity(
|
||||||
const ['Shape Layer 1', 'Rectangle'],
|
const ['Shape Layer 1', 'Rectangle'],
|
||||||
callback: (frameInfo) =>
|
callback: (frameInfo) => (frameInfo.overallProgress * 100).round(),
|
||||||
(frameInfo.overallProgress * 100).round(),
|
),
|
||||||
),
|
ValueDelegate.position(
|
||||||
ValueDelegate.position(
|
const ['Shape Layer 1', 'Rectangle', '**'],
|
||||||
const ['Shape Layer 1', 'Rectangle'],
|
relative: Offset(100, 200),
|
||||||
relative: Offset(100, 200),
|
),
|
||||||
),
|
],
|
||||||
]),
|
),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -7,28 +7,28 @@ packages:
|
|||||||
name: archive
|
name: archive
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "2.0.11"
|
version: "2.0.13"
|
||||||
args:
|
args:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: args
|
name: args
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.5.2"
|
version: "1.6.0"
|
||||||
async:
|
async:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: async
|
name: async
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "2.4.0"
|
version: "2.4.1"
|
||||||
boolean_selector:
|
boolean_selector:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: boolean_selector
|
name: boolean_selector
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.0.5"
|
version: "2.0.0"
|
||||||
characters:
|
characters:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
@ -42,14 +42,14 @@ packages:
|
|||||||
name: charcode
|
name: charcode
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.1.2"
|
version: "1.1.3"
|
||||||
collection:
|
collection:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: collection
|
name: collection
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.14.11"
|
version: "1.14.12"
|
||||||
convert:
|
convert:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
@ -63,7 +63,7 @@ packages:
|
|||||||
name: crypto
|
name: crypto
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "2.1.3"
|
version: "2.1.4"
|
||||||
flutter:
|
flutter:
|
||||||
dependency: "direct main"
|
dependency: "direct main"
|
||||||
description: flutter
|
description: flutter
|
||||||
@ -94,7 +94,7 @@ packages:
|
|||||||
name: image
|
name: image
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "2.1.4"
|
version: "2.1.12"
|
||||||
logging:
|
logging:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
@ -108,7 +108,7 @@ packages:
|
|||||||
path: ".."
|
path: ".."
|
||||||
relative: true
|
relative: true
|
||||||
source: path
|
source: path
|
||||||
version: "0.3.1"
|
version: "0.3.3"
|
||||||
matcher:
|
matcher:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
@ -150,7 +150,7 @@ packages:
|
|||||||
name: quiver
|
name: quiver
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "2.0.5"
|
version: "2.1.3"
|
||||||
sky_engine:
|
sky_engine:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description: flutter
|
description: flutter
|
||||||
@ -162,7 +162,7 @@ packages:
|
|||||||
name: source_span
|
name: source_span
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.5.5"
|
version: "1.7.0"
|
||||||
stack_trace:
|
stack_trace:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
@ -218,7 +218,7 @@ packages:
|
|||||||
name: xml
|
name: xml
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "3.5.0"
|
version: "3.6.1"
|
||||||
sdks:
|
sdks:
|
||||||
dart: ">=2.7.0 <3.0.0"
|
dart: ">=2.7.0 <3.0.0"
|
||||||
flutter: ">=1.5.4 <2.0.0"
|
flutter: ">=1.5.4 <2.0.0"
|
||||||
|
1
example/test/data/loading_indicator.json
Normal file
1850
example/test/data/warningShimmer.json
Normal file
@ -4,6 +4,7 @@ import 'package:flutter/material.dart';
|
|||||||
import 'package:flutter/painting.dart';
|
import 'package:flutter/painting.dart';
|
||||||
import 'package:flutter_test/flutter_test.dart';
|
import 'package:flutter_test/flutter_test.dart';
|
||||||
import 'package:lottie/lottie.dart';
|
import 'package:lottie/lottie.dart';
|
||||||
|
import 'utils.dart';
|
||||||
|
|
||||||
void main() {
|
void main() {
|
||||||
LottieComposition composition;
|
LottieComposition composition;
|
||||||
@ -290,4 +291,54 @@ void main() {
|
|||||||
.round()),
|
.round()),
|
||||||
progress: progress);
|
progress: progress);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
testWidgets('warningShimmer', (tester) async {
|
||||||
|
var size = Size(500, 400);
|
||||||
|
tester.binding.window.physicalSizeTestValue = size;
|
||||||
|
tester.binding.window.devicePixelRatioTestValue = 1.0;
|
||||||
|
|
||||||
|
var composition = await LottieComposition.fromBytes(
|
||||||
|
File('test/data/warningShimmer.json').readAsBytesSync());
|
||||||
|
|
||||||
|
var delegates = <String, List<ValueDelegate>>{
|
||||||
|
'1': [
|
||||||
|
for (var i in ['1', '2', '5'])
|
||||||
|
ValueDelegate.color(['Layer $i Outlines', '**'], value: Colors.red),
|
||||||
|
for (var i in ['3', '4'])
|
||||||
|
ValueDelegate.color(['Layer $i Outlines', '**'],
|
||||||
|
value: Colors.greenAccent),
|
||||||
|
],
|
||||||
|
'2': [
|
||||||
|
for (var i in ['1', '2', '5'])
|
||||||
|
ValueDelegate.color(['Layer $i Outlines', 'Group 1', '*'],
|
||||||
|
value: Colors.red),
|
||||||
|
for (var i in ['3', '4'])
|
||||||
|
ValueDelegate.color(['Layer $i Outlines', 'Group 1', '*'],
|
||||||
|
value: Colors.greenAccent),
|
||||||
|
],
|
||||||
|
'3': [
|
||||||
|
for (var i in ['1', '2', '5'])
|
||||||
|
ValueDelegate.color(['Layer $i Outlines', 'Group 1', 'Fill 1'],
|
||||||
|
value: Colors.red),
|
||||||
|
for (var i in ['3', '4'])
|
||||||
|
ValueDelegate.color(['Layer $i Outlines', 'Group 1', 'Fill 1'],
|
||||||
|
value: Colors.greenAccent),
|
||||||
|
],
|
||||||
|
};
|
||||||
|
|
||||||
|
for (var variant in delegates.entries) {
|
||||||
|
await tester.pumpWidget(
|
||||||
|
FilmStrip(
|
||||||
|
composition,
|
||||||
|
size: size,
|
||||||
|
delegates: LottieDelegates(
|
||||||
|
values: variant.value,
|
||||||
|
),
|
||||||
|
),
|
||||||
|
);
|
||||||
|
|
||||||
|
await expectLater(find.byType(FilmStrip),
|
||||||
|
matchesGoldenFile('goldens/warningShimmer_${variant.key}.png'));
|
||||||
|
}
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
23
example/test/fireworks_test.dart
Normal file
@ -0,0 +1,23 @@
|
|||||||
|
import 'dart:io';
|
||||||
|
import 'dart:ui';
|
||||||
|
import 'package:flutter/material.dart';
|
||||||
|
import 'package:flutter_test/flutter_test.dart';
|
||||||
|
import 'package:lottie/lottie.dart';
|
||||||
|
import 'package:path/path.dart' as p;
|
||||||
|
import 'utils.dart';
|
||||||
|
|
||||||
|
void main() {
|
||||||
|
testWidgets('Animations with stroke', (tester) async {
|
||||||
|
var size = Size(500, 400);
|
||||||
|
tester.binding.window.physicalSizeTestValue = size;
|
||||||
|
tester.binding.window.devicePixelRatioTestValue = 1.0;
|
||||||
|
|
||||||
|
var composition = await LottieComposition.fromBytes(
|
||||||
|
File('assets/17297-fireworks.json').readAsBytesSync());
|
||||||
|
|
||||||
|
await tester.pumpWidget(FilmStrip(composition, size: size));
|
||||||
|
|
||||||
|
await expectLater(find.byType(FilmStrip),
|
||||||
|
matchesGoldenFile(p.join('goldens/fireworks.png')));
|
||||||
|
});
|
||||||
|
}
|
Before Width: | Height: | Size: 38 KiB After Width: | Height: | Size: 42 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 38 KiB After Width: | Height: | Size: 42 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 41 KiB After Width: | Height: | Size: 45 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 41 KiB After Width: | Height: | Size: 45 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 38 KiB After Width: | Height: | Size: 43 KiB |
Before Width: | Height: | Size: 42 KiB After Width: | Height: | Size: 42 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 40 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 43 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 40 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 39 KiB After Width: | Height: | Size: 43 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 35 KiB After Width: | Height: | Size: 39 KiB |
Before Width: | Height: | Size: 38 KiB After Width: | Height: | Size: 43 KiB |
Before Width: | Height: | Size: 41 KiB After Width: | Height: | Size: 45 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 40 KiB After Width: | Height: | Size: 44 KiB |
Before Width: | Height: | Size: 36 KiB After Width: | Height: | Size: 41 KiB |
Before Width: | Height: | Size: 37 KiB After Width: | Height: | Size: 41 KiB |
BIN
example/test/goldens/fireworks.png
Normal file
After Width: | Height: | Size: 22 KiB |
Before Width: | Height: | Size: 9.5 KiB After Width: | Height: | Size: 9.5 KiB |
Before Width: | Height: | Size: 20 KiB After Width: | Height: | Size: 20 KiB |
Before Width: | Height: | Size: 44 KiB After Width: | Height: | Size: 47 KiB |
BIN
example/test/goldens/strokes/loading_indicator.png
Normal file
After Width: | Height: | Size: 8.7 KiB |
Before Width: | Height: | Size: 17 KiB After Width: | Height: | Size: 21 KiB |
BIN
example/test/goldens/warningShimmer_1.png
Normal file
After Width: | Height: | Size: 39 KiB |
BIN
example/test/goldens/warningShimmer_2.png
Normal file
After Width: | Height: | Size: 39 KiB |
BIN
example/test/goldens/warningShimmer_3.png
Normal file
After Width: | Height: | Size: 39 KiB |
@ -23,6 +23,7 @@ void main() {
|
|||||||
'assets/lottiefiles/little_girl_jumping_-_loader.json',
|
'assets/lottiefiles/little_girl_jumping_-_loader.json',
|
||||||
'assets/lottiefiles/playing.json',
|
'assets/lottiefiles/playing.json',
|
||||||
'assets/lottiefiles/win_result_2.json',
|
'assets/lottiefiles/win_result_2.json',
|
||||||
|
'test/data/loading_indicator.json',
|
||||||
]) {
|
]) {
|
||||||
var composition =
|
var composition =
|
||||||
await LottieComposition.fromBytes(File(asset).readAsBytesSync());
|
await LottieComposition.fromBytes(File(asset).readAsBytesSync());
|
||||||
|
@ -3,30 +3,35 @@ import 'package:lottie/lottie.dart';
|
|||||||
|
|
||||||
class FilmStrip extends StatelessWidget {
|
class FilmStrip extends StatelessWidget {
|
||||||
final LottieComposition composition;
|
final LottieComposition composition;
|
||||||
|
final LottieDelegates delegates;
|
||||||
final Size size;
|
final Size size;
|
||||||
|
|
||||||
const FilmStrip(this.composition, {Key key, @required this.size})
|
const FilmStrip(this.composition,
|
||||||
|
{Key key, @required this.size, this.delegates})
|
||||||
: super(key: key);
|
: super(key: key);
|
||||||
|
|
||||||
@override
|
@override
|
||||||
Widget build(BuildContext context) {
|
Widget build(BuildContext context) {
|
||||||
return CustomPaint(
|
return CustomPaint(
|
||||||
size: size,
|
size: size,
|
||||||
painter: _CustomerPainter(composition),
|
painter: _CustomerPainter(this),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class _CustomerPainter extends CustomPainter {
|
class _CustomerPainter extends CustomPainter {
|
||||||
static const _columns = 5;
|
static const _columns = 5;
|
||||||
final LottieComposition composition;
|
final FilmStrip parent;
|
||||||
|
|
||||||
_CustomerPainter(this.composition);
|
_CustomerPainter(this.parent);
|
||||||
|
|
||||||
@override
|
@override
|
||||||
void paint(Canvas canvas, Size size) {
|
void paint(Canvas canvas, Size size) {
|
||||||
var thumbSize = Size(size.width / _columns, size.width / _columns);
|
var thumbSize = Size(size.width / _columns, size.width / _columns);
|
||||||
var drawable = LottieDrawable(composition);
|
var drawable = LottieDrawable(parent.composition);
|
||||||
|
if (parent.delegates != null) {
|
||||||
|
drawable.delegates = parent.delegates;
|
||||||
|
}
|
||||||
|
|
||||||
var index = 0;
|
var index = 0;
|
||||||
for (var progress = 0.0; progress <= 1; progress += 0.05) {
|
for (var progress = 0.0; progress <= 1; progress += 0.05) {
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
import 'dart:math';
|
import 'dart:math';
|
||||||
import 'dart:ui';
|
import 'dart:ui';
|
||||||
|
import 'package:vector_math/vector_math_64.dart';
|
||||||
import '../../lottie_drawable.dart';
|
import '../../lottie_drawable.dart';
|
||||||
import '../../lottie_property.dart';
|
import '../../lottie_property.dart';
|
||||||
import '../../model/content/rectangle_shape.dart';
|
import '../../model/content/rectangle_shape.dart';
|
||||||
@ -95,13 +96,13 @@ class RectangleContent implements KeyPathElementContent, PathContent {
|
|||||||
|
|
||||||
if (radius > 0) {
|
if (radius > 0) {
|
||||||
_path.arcTo(
|
_path.arcTo(
|
||||||
Rect.fromLTWH(
|
Rect.fromLTRB(
|
||||||
position.dx + halfWidth - 2 * radius,
|
position.dx + halfWidth - 2 * radius,
|
||||||
position.dy + halfHeight - 2 * radius,
|
position.dy + halfHeight - 2 * radius,
|
||||||
position.dx + halfWidth,
|
position.dx + halfWidth,
|
||||||
position.dy + halfHeight),
|
position.dy + halfHeight),
|
||||||
0,
|
0,
|
||||||
90,
|
radians(90),
|
||||||
false);
|
false);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -109,13 +110,13 @@ class RectangleContent implements KeyPathElementContent, PathContent {
|
|||||||
|
|
||||||
if (radius > 0) {
|
if (radius > 0) {
|
||||||
_path.arcTo(
|
_path.arcTo(
|
||||||
Rect.fromLTWH(
|
Rect.fromLTRB(
|
||||||
position.dx - halfWidth,
|
position.dx - halfWidth,
|
||||||
position.dy + halfHeight - 2 * radius,
|
position.dy + halfHeight - 2 * radius,
|
||||||
position.dx - halfWidth + 2 * radius,
|
position.dx - halfWidth + 2 * radius,
|
||||||
position.dy + halfHeight),
|
position.dy + halfHeight),
|
||||||
90,
|
radians(90),
|
||||||
90,
|
radians(90),
|
||||||
false);
|
false);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -123,13 +124,13 @@ class RectangleContent implements KeyPathElementContent, PathContent {
|
|||||||
|
|
||||||
if (radius > 0) {
|
if (radius > 0) {
|
||||||
_path.arcTo(
|
_path.arcTo(
|
||||||
Rect.fromLTWH(
|
Rect.fromLTRB(
|
||||||
position.dx - halfWidth,
|
position.dx - halfWidth,
|
||||||
position.dy - halfHeight,
|
position.dy - halfHeight,
|
||||||
position.dx - halfWidth + 2 * radius,
|
position.dx - halfWidth + 2 * radius,
|
||||||
position.dy - halfHeight + 2 * radius),
|
position.dy - halfHeight + 2 * radius),
|
||||||
180,
|
radians(180),
|
||||||
90,
|
radians(90),
|
||||||
false);
|
false);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -137,13 +138,13 @@ class RectangleContent implements KeyPathElementContent, PathContent {
|
|||||||
|
|
||||||
if (radius > 0) {
|
if (radius > 0) {
|
||||||
_path.arcTo(
|
_path.arcTo(
|
||||||
Rect.fromLTWH(
|
Rect.fromLTRB(
|
||||||
position.dx + halfWidth - 2 * radius,
|
position.dx + halfWidth - 2 * radius,
|
||||||
position.dy - halfHeight,
|
position.dy - halfHeight,
|
||||||
position.dx + halfWidth,
|
position.dx + halfWidth,
|
||||||
position.dy - halfHeight + 2 * radius),
|
position.dy - halfHeight + 2 * radius),
|
||||||
270,
|
radians(270),
|
||||||
90,
|
radians(90),
|
||||||
false);
|
false);
|
||||||
}
|
}
|
||||||
_path.close();
|
_path.close();
|
||||||
|
@ -71,10 +71,8 @@ class RepeaterContent
|
|||||||
var newContents = <Content>[];
|
var newContents = <Content>[];
|
||||||
while (index >= 0) {
|
while (index >= 0) {
|
||||||
var content = contents[index];
|
var content = contents[index];
|
||||||
if (content is PathContent) {
|
newContents.add(content);
|
||||||
newContents.add(content);
|
contents.removeAt(index);
|
||||||
contents.removeAt(index);
|
|
||||||
}
|
|
||||||
--index;
|
--index;
|
||||||
}
|
}
|
||||||
newContents = newContents.reversed.toList();
|
newContents = newContents.reversed.toList();
|
||||||
|
@ -158,23 +158,25 @@ class TransformKeyframeAnimation {
|
|||||||
Matrix4 getMatrixForRepeater(double amount) {
|
Matrix4 getMatrixForRepeater(double amount) {
|
||||||
final position = _position?.value;
|
final position = _position?.value;
|
||||||
final scale = _scale?.value;
|
final scale = _scale?.value;
|
||||||
final rotation = _rotation?.value;
|
|
||||||
|
|
||||||
_matrix.setIdentity();
|
_matrix.setIdentity();
|
||||||
|
|
||||||
if (position != null) {
|
if (position != null) {
|
||||||
_matrix.translate(position.dx, position.dy);
|
_matrix.translate(position.dx * amount, position.dy * amount);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (scale != null) {
|
if (scale != null) {
|
||||||
_matrix.scale(scale.dx, scale.dy);
|
_matrix.scale(
|
||||||
|
pow(scale.dx, amount).toDouble(), pow(scale.dy, amount).toDouble());
|
||||||
}
|
}
|
||||||
|
|
||||||
if (rotation != null) {
|
if (_rotation != null) {
|
||||||
final anchorPoint = _anchorPoint?.value ?? Offset.zero;
|
var rotation = _rotation.value;
|
||||||
_matrix.translate(anchorPoint.dx, anchorPoint.dy);
|
var anchorPoint = _anchorPoint?.value;
|
||||||
_matrix.rotateZ(rotation * pi / 180.0);
|
_matrix.rotate(
|
||||||
_matrix.translate(-anchorPoint.dx, -anchorPoint.dy);
|
Vector3(anchorPoint == null ? 0.0 : anchorPoint.dx,
|
||||||
|
anchorPoint == null ? 0.0 : anchorPoint.dy, 1.0),
|
||||||
|
radians(rotation * amount));
|
||||||
}
|
}
|
||||||
|
|
||||||
return _matrix;
|
return _matrix;
|
||||||
|
@ -158,7 +158,7 @@ class AnimatableTransformParser {
|
|||||||
|
|
||||||
static bool isPositionIdentity(AnimatableValue<Offset, Offset> position) {
|
static bool isPositionIdentity(AnimatableValue<Offset, Offset> position) {
|
||||||
return position == null ||
|
return position == null ||
|
||||||
(!(position is AnimatableSplitDimensionPathValue) &&
|
(position is! AnimatableSplitDimensionPathValue &&
|
||||||
position.isStatic &&
|
position.isStatic &&
|
||||||
position.keyframes.first.startValue == Offset.zero);
|
position.keyframes.first.startValue == Offset.zero);
|
||||||
}
|
}
|
||||||
|
22
pubspec.lock
@ -21,28 +21,28 @@ packages:
|
|||||||
name: archive
|
name: archive
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "2.0.11"
|
version: "2.0.13"
|
||||||
args:
|
args:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: args
|
name: args
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.5.2"
|
version: "1.6.0"
|
||||||
async:
|
async:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: async
|
name: async
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "2.4.0"
|
version: "2.4.1"
|
||||||
boolean_selector:
|
boolean_selector:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: boolean_selector
|
name: boolean_selector
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.0.5"
|
version: "2.0.0"
|
||||||
characters:
|
characters:
|
||||||
dependency: "direct main"
|
dependency: "direct main"
|
||||||
description:
|
description:
|
||||||
@ -56,14 +56,14 @@ packages:
|
|||||||
name: charcode
|
name: charcode
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.1.2"
|
version: "1.1.3"
|
||||||
collection:
|
collection:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: collection
|
name: collection
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.14.11"
|
version: "1.14.12"
|
||||||
convert:
|
convert:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
@ -77,7 +77,7 @@ packages:
|
|||||||
name: crypto
|
name: crypto
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "2.1.3"
|
version: "2.1.4"
|
||||||
csslib:
|
csslib:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
@ -122,7 +122,7 @@ packages:
|
|||||||
name: image
|
name: image
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "2.1.4"
|
version: "2.1.12"
|
||||||
js:
|
js:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
@ -213,7 +213,7 @@ packages:
|
|||||||
name: quiver
|
name: quiver
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "2.0.5"
|
version: "2.1.3"
|
||||||
sky_engine:
|
sky_engine:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description: flutter
|
description: flutter
|
||||||
@ -225,7 +225,7 @@ packages:
|
|||||||
name: source_span
|
name: source_span
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.5.5"
|
version: "1.7.0"
|
||||||
stack_trace:
|
stack_trace:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
@ -288,7 +288,7 @@ packages:
|
|||||||
name: xml
|
name: xml
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "3.5.0"
|
version: "3.6.1"
|
||||||
yaml:
|
yaml:
|
||||||
dependency: "direct dev"
|
dependency: "direct dev"
|
||||||
description:
|
description:
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
name: lottie
|
name: lottie
|
||||||
description: Render After Effects animations natively on Flutter. This package is a pure Dart implementation of a Lottie player.
|
description: Render After Effects animations natively on Flutter. This package is a pure Dart implementation of a Lottie player.
|
||||||
version: 0.3.1
|
version: 0.3.3
|
||||||
homepage: https://github.com/xvrh/lottie-flutter
|
homepage: https://github.com/xvrh/lottie-flutter
|
||||||
|
|
||||||
environment:
|
environment:
|
||||||
|