/* * @author dx * @date 2019-09-17 **/ import 'dart:async'; import 'package:cached_network_image/cached_network_image.dart'; import 'package:flutter/material.dart' as IMAGE; import 'package:flutter_screenutil/flutter_screenutil.dart'; import 'package:gmalpha_flutter/WebModel/service/remote/entity/ActivityReportEntity.dart'; import 'package:flutter/material.dart'; import 'package:gmalpha_flutter/WebModel/page/ActivityReportModel.dart'; import 'package:gmalpha_flutter/Annotations/RouterCenterRestore.mark.dart'; import 'package:gmalpha_flutter/commonModel/GMBase.dart'; import 'package:gmalpha_flutter/res/GMRes.dart'; final _goldenColor = Color(0xFFB9A689); ActivityReportState state; class ActivityReportPage extends StatefulWidget { ActivityReportModel _model; ActivityReportPage(int id, int type, String fromPage) { _model = new ActivityReportModel(id, type, fromPage); } @override State<StatefulWidget> createState() => ActivityReportState(_model); } class ActivityReportState extends BasePage<ActivityReportPage> { ActivityReportModel _model; ActivityReportState(this._model); @override void initState() { super.initState(); state = this; _model.init(context); } @override Widget build(BuildContext context) { ScreenUtil.instance = ScreenUtil(width: 375, height: 667)..init(context); return Scaffold( appBar: baseAppBar( backClick: () { RouterCenterImpl() .findBuriedRouter() ?.onClick(pageName(), "return"); Navigator.pop(context, ""); // jumpToNative("search", null); }, action: <Widget>[ GestureDetector( child: Container( margin: EdgeInsets.only(right: 30), child: Center( child: Text( '再测一次', style: TextStyle( color: ALColors.Color323232, fontSize: 14, fontWeight: FontWeight.bold), ))), onTap: () { RouterCenterImpl() .findBuriedRouter() ?.onClick(pageName(), "test_again"); Navigator.pop(context, ""); jumpToH5("question", {"template_id": _model.type}); }, ) ], ), body: StreamBuilder<ActivityReportEntity>( stream: _model.activityReportLive.stream, initialData: _model.activityReportLive.data, builder: (context, data) { if (data.data == null) { return loadingItem(); } if (data.data.error != 0 || data.data.data == null) { return errorItem(data.data.message); } return Container( color: Color(0xfff5f5f5), padding: EdgeInsets.only( left: ScreenUtil.instance.setWidth(16), right: ScreenUtil.instance.setWidth(16)), child: SingleChildScrollView( child: Column( children: <Widget>[ TopCard(share: data.data.data.report?.share), SizedBox(height: ScreenUtil.instance.setHeight(8)), PictorialCard( this, _model, pictorialList: data.data.data.report?.cards, id: _model.id, ), SizedBox(height: ScreenUtil.instance.setHeight(38)) ], ), ), ); }, )); } Widget errorItem(String reason) { return Center( child: Text("$reason"), ); } Widget loadingItem() { return Center(child: CircularProgressIndicator()); } @override void dispose() { super.dispose(); animationNumberState.clearState(); animationCharacterState.clearState(); _model.dispose(); // jumpToNative("search", null); } @override String pageName() { return "brand_report"; } @override String referrer() { return _model.fromPage; } } class TopCard extends StatelessWidget { final share; TopCard({Key key, this.share}) : super(key: key); _moneyContainer(val) { return Container( child: Column( children: <Widget>[ Container( decoration: BoxDecoration( border: Border( bottom: BorderSide(color: Color(0xffeeeeee), width: 1.0))), margin: EdgeInsets.only(left: 18, right: 18), height: ScreenUtil.instance.setHeight(62), child: Row(children: <Widget>[ Text('¥', style: TextStyle( fontSize: 28, color: _goldenColor, fontWeight: FontWeight.bold)), SizedBox(width: 8), Text('$val', style: TextStyle( color: _goldenColor, fontSize: ScreenUtil.instance.setSp(45), fontWeight: FontWeight.bold)), ]), ) ], )); } _percentageContainer(val) { return Container( height: ScreenUtil.instance.setHeight(28), child: Row( children: <Widget>[ Text( '$val%', style: TextStyle( fontSize: ScreenUtil.instance.setSp(20), color: _goldenColor, fontWeight: FontWeight.bold), ), SizedBox(width: 4), Text( '的全国同龄人', style: TextStyle( fontSize: 11, color: _goldenColor, fontWeight: FontWeight.bold), ) ], )); } _rankingContainer(val) { return Container( height: ScreenUtil.instance.setHeight(28), child: Row( children: <Widget>[ SizedBox(width: 4), Text( '$val', style: TextStyle( fontSize: ScreenUtil.instance.setSp(20), color: _goldenColor, fontWeight: FontWeight.bold), ), SizedBox(width: 4), Text( '名', style: TextStyle( fontSize: 11, color: _goldenColor, fontWeight: FontWeight.bold), ) ], ), ); } @override Widget build(BuildContext context) { if (share == null) { return Container(); } return Container( color: Colors.white, width: ScreenUtil.instance.setWidth(343), height: ScreenUtil.instance.setHeight(277), child: Container( width: ScreenUtil.instance.setWidth(343), height: ScreenUtil.instance.setHeight(277), decoration: BoxDecoration( border: Border.all( color: ALColors.Color323232, width: ScreenUtil.instance.setWidth(2))), child: Column( crossAxisAlignment: CrossAxisAlignment.start, children: <Widget>[ SizedBox( height: ScreenUtil.instance.setHeight(8.5), child: Container( margin: EdgeInsets.only(top: ScreenUtil.instance.setHeight(.5)), color: ALColors.Color323232, ), ), Padding( padding: EdgeInsets.only( left: ScreenUtil.instance.setWidth(18), top: ScreenUtil.instance.setHeight(20)), child: Text( '你一年的颜值氪金约为:', textAlign: TextAlign.left, style: TextStyle( color: ALColors.Color323232, fontSize: ScreenUtil.instance.setSp(12), height: 17 / 12, fontWeight: FontWeight.bold, letterSpacing: 1.5, ), )), AnimationNumber( targetNmber: share.totalCost.toDouble(), delay: 400, container: _moneyContainer), Container( padding: EdgeInsets.only( left: ScreenUtil.instance.setWidth(18), right: ScreenUtil.instance.setWidth(18), top: ScreenUtil.instance.setHeight(14)), child: AnimationCharacter(targetNmber: share.beat, delay: 1000)), Container( padding: EdgeInsets.only( left: ScreenUtil.instance.setWidth(18), right: ScreenUtil.instance.setHeight(18), top: ScreenUtil.instance.setHeight(16)), child: Row( mainAxisAlignment: MainAxisAlignment.spaceBetween, children: <Widget>[ Container( color: Color(0xFFF6F6F6), width: ScreenUtil.instance.setWidth(140), height: ScreenUtil.instance.setHeight(55), child: Column( mainAxisAlignment: MainAxisAlignment.start, crossAxisAlignment: CrossAxisAlignment.start, children: <Widget>[ Container( height: ScreenUtil.instance.setHeight(15), margin: EdgeInsets.only( left: ScreenUtil.instance.setWidth(8), top: ScreenUtil.instance.setHeight(4)), child: Text('你的氪金量超过了', style: TextStyle( fontSize: ScreenUtil.instance.setSp(11), color: ALColors.Color8E8E8E, fontWeight: FontWeight.bold)), ), SizedBox( width: double.maxFinite, height: ScreenUtil.instance.setHeight(4), ), Stack( children: <Widget>[ Container( width: double.maxFinite, height: ScreenUtil.instance.setHeight(28), ), Positioned( right: ScreenUtil.instance.setWidth(4), child: AnimationNumber( targetNmber: share.beat.toDouble(), delay: 1000, container: _percentageContainer)) ], ) ], ), ), Container( color: Color(0xFFF6F6F6), width: ScreenUtil.instance.setWidth(140), height: ScreenUtil.instance.setHeight(55), child: Column( mainAxisAlignment: MainAxisAlignment.start, crossAxisAlignment: CrossAxisAlignment.start, children: <Widget>[ Container( height: ScreenUtil.instance.setHeight(15), margin: EdgeInsets.only( top: ScreenUtil.instance.setHeight(4), left: ScreenUtil.instance.setWidth(8)), child: Text('你的氪金排名为全国', style: TextStyle( fontSize: ScreenUtil.instance.setSp(11), color: Color(0xFF8E8E8E), fontWeight: FontWeight.bold))), SizedBox( width: double.maxFinite, height: ScreenUtil.instance.setHeight(4), ), Stack( children: <Widget>[ Container( width: double.maxFinite, height: ScreenUtil.instance.setHeight(28), ), Positioned( right: ScreenUtil.instance.setWidth(6), child: AnimationNumber( targetNmber: share.rank.toDouble(), delay: 1000, container: _rankingContainer), ) ], ) ], ), ) ], )) ], ), )); } } class PictorialCard extends StatelessWidget { final List<Cards> pictorialList; final id; final ActivityReportModel _model; final ActivityReportState state; PictorialCard(this.state, this._model, {Key key, this.pictorialList, this.id}) : super(key: key); Widget _gridViewItemUI(BuildContext context, item) { return Container( width: ScreenUtil.instance.setWidth(110), height: ScreenUtil.instance.setWidth(110), margin: EdgeInsets.only(bottom: ScreenUtil.instance.setHeight(3)), child: CachedNetworkImage( imageUrl: '${item.image}', width: ScreenUtil.instance.setWidth(110), fit: BoxFit.cover, )); } Widget _listViewUI(BuildContext context, item) { var indexOf = pictorialList.indexOf(item); List<Widget> list = []; item.drafts.forEach((item) { list.add(_gridViewItemUI(context, item)); }); return Container( margin: EdgeInsets.only(top: ScreenUtil.instance.setHeight(32)), child: GestureDetector( onTap: () { RouterCenterImpl() .findBuriedRouter() ?.onClick("brand_report", "recommand_${indexOf + 1}"); state.pageStop(); jumpToNative("pictorial", {"url": '${item.protocol}&survey_record_id=$id'}); }, child: Column( crossAxisAlignment: CrossAxisAlignment.start, children: <Widget>[ Container( width: ScreenUtil.instance.setWidth(343), padding: EdgeInsets.only( bottom: ScreenUtil.instance.setHeight(11.0)), child: Wrap(spacing: 6, children: list), ), Container( width: ScreenUtil.instance.setWidth(343), height: 53, color: Colors.white, child: Column( mainAxisAlignment: MainAxisAlignment.center, crossAxisAlignment: CrossAxisAlignment.center, children: <Widget>[ Stack( children: <Widget>[ Container( padding: EdgeInsets.only( right: ScreenUtil.instance.setWidth(12)), child: Text( '${item.guide}', style: TextStyle( color: Color(0xFF323232), fontWeight: FontWeight.bold, fontSize: ScreenUtil.instance.setSp(14)), ), ), Positioned( width: ScreenUtil.instance.setWidth(10), height: ScreenUtil.instance.setHeight(20), top: ScreenUtil.instance.setHeight(-2), right: 0, child: IMAGE.Image.asset('images/right_icon.png', width: ScreenUtil.instance.setWidth(10), height: ScreenUtil.instance.setHeight(20)), ) ], ) ], )) ], ))); } @override Widget build(BuildContext context) { if (pictorialList == null) { return Container(); } return Column( children: pictorialList.map((item) { return _listViewUI(context, item); }).toList(), ); } } AnimationNumberState animationNumberState; class AnimationNumber extends StatefulWidget { final targetNmber; final delay; final container; AnimationNumber({Key key, this.targetNmber, this.delay, this.container}) : super(key: key); AnimationNumberState createState() { animationNumberState = AnimationNumberState(); return animationNumberState; } } class AnimationNumberState extends State<AnimationNumber> with TickerProviderStateMixin { AnimationController _animationController; var _timer; @override void initState() { super.initState(); _animationController = AnimationController( duration: Duration(milliseconds: widget.delay), lowerBound: 0, upperBound: widget.targetNmber, vsync: this); _animationController.addListener(() { setState(() {}); }); } clearState() { _timer.dispose(); super.dispose(); _animationController.dispose(); } @override Widget build(BuildContext context) { _timer = Timer(Duration(seconds: 1), () { if (_animationController != null) { _animationController.forward(); } }); return widget.container(_animationController.value.toInt()); } } AnimationCharacterState animationCharacterState; class AnimationCharacter extends StatefulWidget { final targetNmber; final delay; AnimationCharacter({Key key, this.targetNmber, this.delay}) : super(key: key); AnimationCharacterState createState() { animationCharacterState = AnimationCharacterState(); return animationCharacterState; } } class AnimationCharacterState extends State<AnimationCharacter> with TickerProviderStateMixin { AnimationController _animationController; var _timer; List peopleList; double margin = 10; @override void initState() { super.initState(); _animationController = AnimationController( duration: Duration(milliseconds: widget.delay), lowerBound: 0, upperBound: 10, vsync: this); peopleList = [ {'url': 'images/light_grey_person.png', 'width': 14.0, 'height': 36.0}, {'url': 'images/light_grey_person.png', 'width': 14.0, 'height': 36.0}, {'url': 'images/light_grey_person.png', 'width': 14.0, 'height': 36.0}, {'url': 'images/light_grey_person.png', 'width': 14.0, 'height': 36.0}, {'url': 'images/light_grey_person.png', 'width': 14.0, 'height': 36.0}, {'url': 'images/light_grey_person.png', 'width': 14.0, 'height': 36.0}, {'url': 'images/light_grey_person.png', 'width': 14.0, 'height': 36.0}, {'url': 'images/light_grey_person.png', 'width': 14.0, 'height': 36.0}, {'url': 'images/light_grey_person.png', 'width': 14.0, 'height': 36.0}, {'url': 'images/light_grey_person.png', 'width': 14.0, 'height': 36.0}, {'url': 'images/light_grey_person.png', 'width': 14.0, 'height': 36.0} ]; final target = (widget.targetNmber / 10).ceil(); _animationController?.addListener(() { var value = _animationController?.value; double percent = value / 10; double frist = target / 10; int nowValue; setState(() { peopleList.forEach((item) { int index = peopleList.indexOf(item); if (percent < frist) { double tempPercent = percent / frist; nowValue = (target * tempPercent).ceil(); margin = ScreenUtil.instance.setWidth(10.0 + (25.8 * nowValue).ceil()); if (index != nowValue) { item['url'] = 'images/dark_grey_person.png'; } else { item['url'] = 'images/golden_person.png'; } } else { double tempPercent = (percent - frist) / (1 - frist); nowValue = (target + (11 - target) * tempPercent).ceil(); if (index > target && index <= nowValue) { item['url'] = 'images/black_person.png'; } } }); }); }); } clearState() { _timer.dispose(); super.dispose(); _animationController.dispose(); } Widget _peopleViewUI(BuildContext context, item) { var index = peopleList.indexOf(item); return Container( margin: index != 0 ? EdgeInsets.only(left: ScreenUtil.instance.setWidth(12)) : EdgeInsets.all(0), child: IMAGE.Image.asset(item['url'], width: ScreenUtil.instance.setWidth(item['width']), height: ScreenUtil.instance.setHeight(item['height']))); } @override Widget build(BuildContext context) { _timer = Timer(Duration(seconds: 1), () { if (_animationController != null) { _animationController.forward(); } }); return Column( children: <Widget>[ _youContainer(), Row( mainAxisAlignment: MainAxisAlignment.start, children: peopleList.map((item) { return _peopleViewUI(context, item); }).toList()) ], ); } _youContainer() { return Container( child: Stack(children: <Widget>[ Container( width: double.maxFinite, height: ScreenUtil.instance.setHeight(19), margin: EdgeInsets.only(bottom: ScreenUtil.instance.setHeight(4)), ), Positioned( child: Container( margin: EdgeInsets.only(left: margin), width: ScreenUtil.instance.setWidth(32), height: ScreenUtil.instance.setHeight(19), child: IMAGE.Image.asset('images/you_icon.png'), )) ])); } }