| @@ -0,0 +1,24 @@ | |||
| import 'package:flutter/material.dart'; | |||
| class HotRankingPage extends StatefulWidget { | |||
| @override | |||
| _HotRankingPageState createState() => _HotRankingPageState(); | |||
| } | |||
| class _HotRankingPageState extends State<HotRankingPage> { | |||
| @override | |||
| Widget build(BuildContext context) { | |||
| print('hot_ranking_page build'); | |||
| // | |||
| // List<Widget> contentWidgets = tabs.map((item) { | |||
| // BaseTabModel model = BaseTabModel.fromJson(item); | |||
| // return PageFactory.create(model.skipIdentifier, item); | |||
| // }).toList(); | |||
| // if (_currentIndex >= contentWidgets.length) { | |||
| // _currentIndex = 0; | |||
| // } | |||
| return Scaffold(); | |||
| } | |||
| } | |||
| @@ -0,0 +1,44 @@ | |||
| import 'dart:async'; | |||
| import 'package:zhiying_comm/util/base_bloc.dart'; | |||
| import 'package:zhiying_comm/zhiying_comm.dart'; | |||
| class HotRankingPage extends BlocBase { | |||
| List<Map<String, dynamic>> _pageData = List(); | |||
| StreamController<List<Map<String, dynamic>>> _dataController = | |||
| StreamController<List<Map<String, dynamic>>>(); | |||
| Stream<List<Map<String, dynamic>>> get outData => _dataController.stream; | |||
| @override | |||
| void dispose() { | |||
| _dataController.close(); | |||
| _dataController = null; | |||
| } | |||
| void loadData(int id) { | |||
| NetUtil.request('/api/v1/mod', | |||
| method: NetMethod.POST, | |||
| params: Map<String, dynamic>.from({ | |||
| 'ids': [id] | |||
| }), onCache: (data) { | |||
| _loadData(id, data); | |||
| }, onSuccess: (data) { | |||
| _loadData(id, data); | |||
| }); | |||
| } | |||
| void _loadData(int id, dynamic data) { | |||
| String key = id.toString(); | |||
| Map<String, dynamic> json = Map<String, dynamic>.from(data); | |||
| if (json.containsKey(key)) { | |||
| List<dynamic> list = json[key]; | |||
| _pageData = list.map((item) { | |||
| return Map<String, dynamic>.from(item); | |||
| }).toList(); | |||
| } | |||
| _dataController.add(_pageData); | |||
| } | |||
| } | |||
| @@ -0,0 +1,44 @@ | |||
| import 'dart:async'; | |||
| import 'package:zhiying_comm/util/base_bloc.dart'; | |||
| import 'package:zhiying_comm/zhiying_comm.dart'; | |||
| class HotRankingBloc extends BlocBase { | |||
| List<Map<String, dynamic>> _pageData = List(); | |||
| StreamController<List<Map<String, dynamic>>> _dataController = | |||
| StreamController<List<Map<String, dynamic>>>(); | |||
| Stream<List<Map<String, dynamic>>> get outData => _dataController.stream; | |||
| @override | |||
| void dispose() { | |||
| _dataController.close(); | |||
| _dataController = null; | |||
| } | |||
| void loadData(int id) { | |||
| NetUtil.request('/api/v1/mod', | |||
| method: NetMethod.POST, | |||
| params: Map<String, dynamic>.from({ | |||
| 'ids': [id] | |||
| }), onCache: (data) { | |||
| _loadData(id, data); | |||
| }, onSuccess: (data) { | |||
| _loadData(id, data); | |||
| }); | |||
| } | |||
| void _loadData(int id, dynamic data) { | |||
| String key = id.toString(); | |||
| Map<String, dynamic> json = Map<String, dynamic>.from(data); | |||
| if (json.containsKey(key)) { | |||
| List<dynamic> list = json[key]; | |||
| _pageData = list.map((item) { | |||
| return Map<String, dynamic>.from(item); | |||
| }).toList(); | |||
| } | |||
| _dataController.add(_pageData); | |||
| } | |||
| } | |||
| @@ -0,0 +1,91 @@ | |||
| import 'package:flutter/material.dart'; | |||
| import 'package:zhiying_base_widget/widgets/hot_ranking/hot_ranking_bloc.dart'; | |||
| import 'package:zhiying_base_widget/widgets/hot_ranking/hot_ranking_goods/hot_ranking_goods.dart'; | |||
| import 'package:zhiying_base_widget/widgets/hot_ranking/hot_ranking_sk.dart'; | |||
| class HotRankingContainer extends StatefulWidget { | |||
| final Map<String, dynamic> data; | |||
| const HotRankingContainer({Key key, this.data}) : super(key: key); | |||
| @override | |||
| _HotRankingState createState() => _HotRankingState(); | |||
| } | |||
| class _HotRankingState extends State<HotRankingContainer> | |||
| with TickerProviderStateMixin { | |||
| HotRankingBloc _bloc; | |||
| TabController _tabController; | |||
| @override | |||
| void initState() { | |||
| _bloc = HotRankingBloc(); | |||
| super.initState(); | |||
| } | |||
| _buildTabs() { | |||
| List<Widget> listWidget = List(); | |||
| for (int index = 0; index < 4; index++) { | |||
| listWidget.add(Tab( | |||
| text: "hahah", | |||
| )); | |||
| } | |||
| return listWidget; | |||
| } | |||
| @override | |||
| void dispose() { | |||
| _tabController.dispose(); | |||
| super.dispose(); | |||
| } | |||
| ///构建 | |||
| void createTabController() { | |||
| _tabController = TabController(length: 4, vsync: this); | |||
| } | |||
| ///构建TabView | |||
| _buildTabView() { | |||
| List<Widget> listWidget = List(); | |||
| for (var index = 0; index < 4; index++) { | |||
| listWidget.add(ListView.builder( | |||
| padding: EdgeInsets.all(0), | |||
| itemCount: 10, | |||
| itemBuilder: (context, index) { | |||
| return Container( | |||
| child: HotRankingGoods(), | |||
| ); | |||
| })); | |||
| } | |||
| return listWidget; | |||
| } | |||
| @override | |||
| Widget build(BuildContext context) { | |||
| return StreamBuilder( | |||
| stream: _bloc.outData, | |||
| builder: (context, snapshot) { | |||
| if (snapshot.data != null) { | |||
| return HotRankingSkeleton(); | |||
| } else { | |||
| createTabController(); | |||
| return Container( | |||
| child: Column( | |||
| children: <Widget>[ | |||
| TabBar( | |||
| controller: _tabController, | |||
| isScrollable: true, | |||
| tabs: _buildTabs(), | |||
| ), | |||
| Expanded( | |||
| child: TabBarView( | |||
| controller: _tabController, | |||
| children: _buildTabView())) | |||
| ], | |||
| ), | |||
| ); | |||
| } | |||
| }); | |||
| } | |||
| } | |||
| @@ -0,0 +1,218 @@ | |||
| import 'package:flutter/material.dart'; | |||
| import 'package:flutter_screenutil/flutter_screenutil.dart'; | |||
| import 'package:zhiying_base_widget/widgets/home/home_quick_entry/cached_network_image_util.dart'; | |||
| import 'package:zhiying_comm/zhiying_comm.dart'; | |||
| import 'package:cached_network_image/cached_network_image.dart'; | |||
| class HotRankingGoods extends StatelessWidget { | |||
| @override | |||
| Widget build(BuildContext context) { | |||
| return Stack( | |||
| children: <Widget>[ | |||
| Container( | |||
| padding: EdgeInsets.all(15.w), | |||
| margin: | |||
| EdgeInsets.only(top: 8.w, bottom: 8.w, left: 25.w, right: 25.w), | |||
| decoration: BoxDecoration( | |||
| color: Colors.white, borderRadius: BorderRadius.circular(15.w)), | |||
| child: Row( | |||
| crossAxisAlignment: CrossAxisAlignment.start, | |||
| children: <Widget>[ | |||
| Container( | |||
| width: 254.w, | |||
| height: 254.w, | |||
| color: Colors.amber, | |||
| ), | |||
| Expanded( | |||
| child: Container( | |||
| margin: EdgeInsets.only(left: 20.w), | |||
| child: Column( | |||
| mainAxisSize: MainAxisSize.max, | |||
| children: <Widget>[ | |||
| Container( | |||
| height: 70.h, | |||
| child: Row( | |||
| children: <Widget>[ | |||
| Expanded( | |||
| child: RichText( | |||
| overflow: TextOverflow.ellipsis, | |||
| maxLines: 2, | |||
| text: TextSpan(children: <InlineSpan>[ | |||
| WidgetSpan( | |||
| child: Container( | |||
| decoration: BoxDecoration( | |||
| color: Colors.red, | |||
| borderRadius: | |||
| BorderRadius.circular(4)), | |||
| child: Padding( | |||
| padding: EdgeInsets.only( | |||
| left: 4.w, right: 4.w), | |||
| child: Text( | |||
| "京东", | |||
| style: TextStyle( | |||
| color: HexColor.fromHex( | |||
| "#FFFFFF", | |||
| ), | |||
| fontSize: 18.sp), | |||
| ), | |||
| ), | |||
| )), | |||
| WidgetSpan( | |||
| child: SizedBox( | |||
| width: 4.h, | |||
| )), | |||
| TextSpan( | |||
| text: | |||
| "Segway Ninebot mini Pro九号平衡车智能代步...", | |||
| style: TextStyle( | |||
| color: Colors.black, | |||
| fontSize: 30.sp)) | |||
| ]))) | |||
| ], | |||
| ), | |||
| ), | |||
| Row( | |||
| children: <Widget>[ | |||
| Container( | |||
| margin: EdgeInsets.only(top: 4, bottom: 4), | |||
| decoration: BoxDecoration(color: Colors.red), | |||
| child: Padding( | |||
| padding: const EdgeInsets.only( | |||
| left: 8, right: 8, top: 2, bottom: 2), | |||
| child: Text( | |||
| "50元券", | |||
| style: TextStyle( | |||
| color: Colors.white, fontSize: 22.sp), | |||
| ), | |||
| ), | |||
| ), | |||
| SizedBox( | |||
| width: 10.sp, | |||
| ), | |||
| Container( | |||
| margin: EdgeInsets.only(top: 4, bottom: 4), | |||
| decoration: BoxDecoration(color: Colors.red), | |||
| child: Padding( | |||
| padding: const EdgeInsets.only( | |||
| left: 8, right: 8, top: 2, bottom: 2), | |||
| child: Text( | |||
| "50元券", | |||
| style: TextStyle( | |||
| color: Colors.white, fontSize: 22.sp), | |||
| ), | |||
| ), | |||
| ) | |||
| ], | |||
| ), | |||
| Padding( | |||
| padding: const EdgeInsets.only(top: 4, bottom: 4), | |||
| child: Row( | |||
| crossAxisAlignment: CrossAxisAlignment.end, | |||
| children: <Widget>[ | |||
| Padding( | |||
| padding: EdgeInsets.only(bottom: 6.sp), | |||
| child: Text( | |||
| "¥", | |||
| style: | |||
| TextStyle(color: Colors.red, fontSize: 20.sp), | |||
| ), | |||
| ), | |||
| Text( | |||
| "1409", | |||
| style: | |||
| TextStyle(color: Colors.red, fontSize: 40.sp), | |||
| ), | |||
| SizedBox( | |||
| width: 6, | |||
| ), | |||
| Padding( | |||
| padding: EdgeInsets.only(bottom: 4.sp), | |||
| child: Text( | |||
| "¥1409", | |||
| style: TextStyle( | |||
| color: Colors.red, | |||
| fontSize: 22.sp, | |||
| decoration: TextDecoration.lineThrough), | |||
| ), | |||
| ), | |||
| ], | |||
| ), | |||
| ), | |||
| Row( | |||
| children: <Widget>[ | |||
| Expanded( | |||
| child: Stack( | |||
| alignment: Alignment.centerLeft, | |||
| children: <Widget>[ | |||
| Row( | |||
| children: <Widget>[ | |||
| Expanded( | |||
| child: Container( | |||
| height: 40.w, | |||
| padding: EdgeInsets.only( | |||
| left: 64.w, | |||
| ), | |||
| margin: EdgeInsets.only(right: 20), | |||
| color: Colors.red, | |||
| child: Text( | |||
| "热销1231.1万件", | |||
| style: TextStyle( | |||
| color: Colors.white, fontSize: 22.sp), | |||
| ), | |||
| )) | |||
| ], | |||
| ), | |||
| Container( | |||
| color: Colors.amber, | |||
| width: 48.w, | |||
| height: 48.w, | |||
| child: CachedNetworkImage( | |||
| imageUrl: "", | |||
| width: 48.w, | |||
| height: 48.w, | |||
| placeholder: (context, _) => | |||
| Container(color: Colors.yellow), | |||
| fit: BoxFit.fill, | |||
| ), | |||
| ), | |||
| Align( | |||
| alignment: Alignment.centerRight, | |||
| child: Container( | |||
| decoration: BoxDecoration( | |||
| color: Colors.amber, | |||
| borderRadius: BorderRadius.circular(20)), | |||
| margin: EdgeInsets.only(right: 0), | |||
| child: Padding( | |||
| padding: EdgeInsets.only( | |||
| left: 16, right: 16, top: 4, bottom: 4), | |||
| child: Text( | |||
| "马上抢", | |||
| style: TextStyle( | |||
| color: Colors.white, fontSize: 26.sp), | |||
| ), | |||
| ), | |||
| ), | |||
| ) | |||
| ], | |||
| )) | |||
| ], | |||
| ) | |||
| ], | |||
| ), | |||
| )) | |||
| ], | |||
| ), | |||
| ), | |||
| Align( | |||
| alignment: Alignment.topLeft, | |||
| child: Container( | |||
| margin: EdgeInsets.only(left: 40.w, top: 8.h), | |||
| color: Colors.red, | |||
| height: 60.w, | |||
| width: 60.w, | |||
| ), | |||
| ) | |||
| ], | |||
| ); | |||
| } | |||
| } | |||
| @@ -0,0 +1,8 @@ | |||
| class HotRankingModel{ | |||
| ResHotRankingModel resHotRankingModel; | |||
| } | |||
| class ResHotRankingModel{ | |||
| } | |||
| @@ -0,0 +1,85 @@ | |||
| import 'package:flutter/material.dart'; | |||
| import 'package:shimmer/shimmer.dart'; | |||
| class HotRankingSkeleton extends StatelessWidget { | |||
| @override | |||
| Widget build(BuildContext context) { | |||
| return Shimmer.fromColors( | |||
| baseColor: Colors.grey[300], | |||
| highlightColor: Colors.grey[100], | |||
| child: Column( | |||
| children: <Widget>[ | |||
| Container( | |||
| width: double.infinity, | |||
| margin: EdgeInsets.all(16), | |||
| height: 48, | |||
| child: Row( | |||
| children: _buildTopRow(), | |||
| )), | |||
| Expanded( | |||
| child: Container( | |||
| child: Column( | |||
| children: _buildBottomListItem(), | |||
| ), | |||
| )) | |||
| ], | |||
| ), | |||
| ); | |||
| } | |||
| _buildBottomListItem() { | |||
| List<Widget> listWidget = List(); | |||
| for (var index = 0; index < 3; index++) { | |||
| listWidget.add(Container( | |||
| margin: EdgeInsets.only(left: 16,top: 10,bottom: 10), | |||
| child: Row( | |||
| children: <Widget>[ | |||
| Container( | |||
| width: 127, | |||
| height: 127, | |||
| color: Colors.white, | |||
| ), | |||
| Container( | |||
| height: 127, | |||
| margin: EdgeInsets.only(left: 10), | |||
| child: Column( | |||
| mainAxisAlignment: MainAxisAlignment.spaceBetween, | |||
| crossAxisAlignment: CrossAxisAlignment.start, | |||
| children: <Widget>[ | |||
| Container( | |||
| height: 40, | |||
| width: 200, | |||
| color: Colors.white, | |||
| ), | |||
| Container( | |||
| height: 30, | |||
| width: 100, | |||
| color: Colors.grey, | |||
| ), | |||
| Container( | |||
| height: 30, | |||
| width: 200, | |||
| color: Colors.grey, | |||
| ) | |||
| ], | |||
| ), | |||
| ) | |||
| ], | |||
| ), | |||
| )); | |||
| } | |||
| return listWidget; | |||
| } | |||
| _buildTopRow() { | |||
| List<Widget> listWidget = List(); | |||
| for (var index = 0; index < 5; index++) { | |||
| listWidget.add(Container( | |||
| width: 50, | |||
| color: Colors.white, | |||
| margin: EdgeInsets.all(10), | |||
| )); | |||
| } | |||
| return listWidget; | |||
| } | |||
| } | |||
| @@ -0,0 +1,20 @@ | |||
| import 'package:flutter/material.dart'; | |||
| import 'package:zhiying_base_widget/widgets/hot_ranking/hot_ranking_container.dart'; | |||
| import 'package:zhiying_base_widget/widgets/hot_ranking/hot_ranking_sk.dart'; | |||
| import 'package:flutter_screenutil/flutter_screenutil.dart'; | |||
| class HotTest extends StatefulWidget { | |||
| @override | |||
| _HotTestState createState() => _HotTestState(); | |||
| } | |||
| class _HotTestState extends State<HotTest> { | |||
| @override | |||
| Widget build(BuildContext context) { | |||
| // 屏幕适配初始化 | |||
| ScreenUtil.init(context, width: 750, height: 1334); | |||
| return Scaffold( | |||
| body: HotRankingContainer(), | |||
| ); | |||
| } | |||
| } | |||