Skip to content

Instantly share code, notes, and snippets.

@doyle-flutter
Created August 19, 2021 15:09
Show Gist options
  • Save doyle-flutter/8267834dda05552c1db490e9792d6fc0 to your computer and use it in GitHub Desktop.
Save doyle-flutter/8267834dda05552c1db490e9792d6fc0 to your computer and use it in GitHub Desktop.
Flutter Anim 01
import 'package:flutter/foundation.dart';
import 'package:flutter/material.dart';
void main() => runApp(App());
class App extends StatelessWidget {
const App({Key? key}) : super(key: key);
@override
Widget build(BuildContext context) {
return MaterialApp(home: Main(),);
}
}
class Main extends StatelessWidget {
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(title: Text("Animation & Matrix444"),),
body: SingleChildScrollView(
child: Container(
width: MediaQuery.of(context).size.width,
child: Column(
children: [
Floor(
animSec: 1,
wallImageSrc: "https://cdn.pixabay.com/photo/2015/12/26/05/53/wood-1108307__340.jpg",
doorImageSrc: "https://cdn.pixabay.com/photo/2014/12/21/23/55/door-576355__340.png",
doorPosition: DoorPosition(bottom: 0, right: 20),
wallSize: Size(0, MediaQuery.of(context).size.height*0.30),
doorSize: Size(170, 250),
),
Floor(
animSec: 2,
wallImageSrc: "https://cdn.pixabay.com/photo/2012/03/03/23/06/wall-21534__340.jpg",
doorImageSrc: "https://cdn.pixabay.com/photo/2014/12/21/23/45/door-575979__480.png",
doorPosition: DoorPosition(bottom: 0, left: 50),
wallSize: Size(0, MediaQuery.of(context).size.height*0.30),
doorSize: Size(125, 250),
),
Floor(
animSec: 1,
wallImageSrc: "https://cdn.pixabay.com/photo/2015/12/26/05/53/wood-1108307__340.jpg",
doorImageSrc: "https://cdn.pixabay.com/photo/2014/12/21/23/55/door-576355__340.png",
doorPosition: DoorPosition(bottom: 0, right: 20),
wallSize: Size(0, MediaQuery.of(context).size.height*0.30),
doorSize: Size(170, 250),
),
Floor(
animSec: 2,
wallImageSrc: "https://cdn.pixabay.com/photo/2012/03/03/23/06/wall-21534__340.jpg",
doorImageSrc: "https://cdn.pixabay.com/photo/2014/12/21/23/45/door-575979__480.png",
doorPosition: DoorPosition(bottom: 0, left: 50),
wallSize: Size(0, MediaQuery.of(context).size.height*0.30),
doorSize: Size(125, 250),
),
],
),
),
),
);
}
}
class DoorPosition{
final double? top;
final double? bottom;
final double? left;
final double? right;
const DoorPosition({
this.top,
this.bottom,
this.left,
this.right
});
}
class Floor extends StatelessWidget {
final Size wallSize;
final Size doorSize;
final String wallImageSrc;
final String doorImageSrc;
final DoorPosition doorPosition;
final int animSec;
const Floor({
required this.wallImageSrc,
required this.doorImageSrc,
required this.wallSize,
required this.doorSize,
required this.doorPosition,
required this.animSec,
});
@override
Widget build(BuildContext context) {
return Stack(
children: [
Container(
height: this.wallSize.height,
decoration: BoxDecoration(
image: DecorationImage(
fit: BoxFit.cover,
image: NetworkImage(this.wallImageSrc)
)
),
),
Positioned(
bottom: this.doorPosition.bottom,
right: this.doorPosition.right,
left: this.doorPosition.left,
top: this.doorPosition.top,
child: Door(
isShadow: true,
size: this.doorSize,
imgSrc: this.doorImageSrc,
),
),
Positioned(
bottom: this.doorPosition.bottom,
right: this.doorPosition.right,
left: this.doorPosition.left,
top: this.doorPosition.top,
child: Door(
animSec: this.animSec,
func: (bool check, AnimationController? ct) async{
if(ct == null) return;
if(ct.isAnimating) return;
if(ct.isCompleted){
ct.reverse();
return;
}
ct.forward();
return;
},
size: this.doorSize,
imgSrc: this.doorImageSrc,
),
)
],
);
}
}
class Door extends StatefulWidget {
final int? animSec;
final Size size;
final String imgSrc;
final bool isShadow;
final Future<void> Function(bool, AnimationController?)? func;
const Door({Key? key, required this.size, required this.imgSrc, this.func, this.isShadow = false, this.animSec}) : super(key: key);
@override
_DoorState createState() => _DoorState();
}
class _DoorState extends State<Door> with SingleTickerProviderStateMixin {
AnimationController? _at;
Animation<double>? _anim;
@override
void initState() {
if(widget.animSec != null){
this._at = AnimationController(vsync: this, duration: Duration(seconds: widget.animSec!))
..addListener(() {
if(!this.mounted) return;
setState(() {});
});
this._anim = Tween<double>(begin: 0, end: 1.2).animate(_at!);
if(!this.mounted) return;
setState(() {});
}
super.initState();
}
@override
Widget build(BuildContext context) {
return GestureDetector(
onTap: (widget.isShadow || widget.func == null) ? null : (){
bool loadCheck = this._anim != null || this._anim != null;
widget.func!(loadCheck, _at);
},
child: Container(
transform: Matrix4(
1,0,0,0,
0,1,0,0,
0,0,1,0,
0,0,0,1,
)..rotateY(this._anim?.value ?? 0),
width: widget.size.width,
height: widget.size.height,
decoration: BoxDecoration(
image: DecorationImage(
fit: BoxFit.cover,
colorFilter: widget.isShadow
? ColorFilter.mode(
Colors.black,
BlendMode.srcIn
)
: null,
image: NetworkImage(widget.imgSrc)
)
),
)
);
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment