import 'dart:convert';
|
import 'dart:io';
|
import 'dart:math';
|
|
import 'package:flutter/material.dart';
|
import 'package:flutter_module/utils/ui_utils.dart';
|
import 'package:flutter_swiper_null_safety/flutter_swiper_null_safety.dart';
|
import '../../ui/widget/ad_express.dart';
|
import '../../ui/widget/refresh_listview.dart';
|
import '../../utils/ad_util.dart';
|
import '../../utils/pageutils.dart';
|
import '../../utils/ui_constant.dart';
|
|
import '../../model/video/home_type_model.dart';
|
import '../../model/video/search_special_model.dart';
|
import 'api/video_api.dart';
|
import 'model/video/home_ad_model.dart';
|
import 'ui/widget/video_item.dart';
|
import 'utils/jump_page.dart';
|
|
class HomePage extends StatefulWidget {
|
HomePage({Key? key, required this.title}) : super(key: key);
|
|
final String title;
|
|
@override
|
_HomePageState createState() => _HomePageState();
|
}
|
|
class _HomePageState extends State<HomePage>
|
with SingleTickerProviderStateMixin {
|
final MyRefreshController _refreshController =
|
MyRefreshController(initialRefresh: false);
|
List<HomeAdModel> bannerList = [];
|
List homeTypeList = [];
|
int page = 1;
|
int totalCount = 0;
|
List<SearchSpecialModel> categoryList = [];
|
bool hasDYHot = true;
|
String searchKw = "";
|
|
//信息流广告
|
Widget? expressAd;
|
AdType? expressAdType;
|
String? expressPid;
|
|
ExpressAdController _expressAdController = ExpressAdController();
|
|
@override
|
void initState() {
|
super.initState();
|
init();
|
AdUtil.getAdType(AdPosition.other).then((value) {
|
setState(() {
|
expressAdType = value;
|
});
|
if (expressAdType == AdType.csj) {
|
expressPid = CSJADConstant.PID_RECOMMEND_BIG_PICTURE;
|
} else if (expressAdType == AdType.gdt) {
|
expressPid = GDTADConstant.PID_RECOMMEND_BIG_PICTURE;
|
}
|
});
|
|
// Future.delayed(Duration(seconds: 5),(){
|
uiMethodChannel.invokeMethod("setStatusBarLight");
|
// });
|
}
|
|
void init() {
|
getHomeAd();
|
getHomeType(page);
|
getSearchSpecial();
|
getHotSearch();
|
//刷新
|
_expressAdController.refresh;
|
}
|
|
void jumpPage(String name, dynamic params) {
|
JumpPageUtil.jumpPage(name, context,
|
params: params, native: true, callback: (data) {});
|
}
|
|
@override
|
Widget build(BuildContext context) {
|
return Scaffold(
|
backgroundColor: Colors.white,
|
body: Column(children: [
|
Container(
|
color: ColorConstant.theme,
|
padding: const EdgeInsets.fromLTRB(10, 12, 10, 12),
|
child: InkWell(
|
onTap: () {
|
jumpPage("SearchPage", {"title": searchKw});
|
},
|
child: Container(
|
height: 32,
|
decoration: BoxDecoration(
|
color: Colors.white,
|
borderRadius: BorderRadius.circular(16)),
|
child: Row(
|
children: [
|
Container(
|
width: 12,
|
),
|
Image.asset(
|
"assets/imgs/icon_search_home.png",
|
height: 17,
|
),
|
Container(
|
width: 10,
|
),
|
Text(
|
searchKw,
|
style: TextStyle(
|
color: const Color(0xFF787878), fontSize: 14),
|
)
|
],
|
),
|
)),
|
),
|
Expanded(
|
child: RefreshListView(
|
refreshController: _refreshController,
|
content: CustomScrollView(slivers: [
|
SliverList(
|
delegate: SliverChildBuilderDelegate(
|
(content, index) {
|
if (index == 0) {
|
return bannerList.isEmpty ? Container() : getBannerView();
|
} else if (index == 1) {
|
return categoryList.isEmpty
|
? Container()
|
: getCategoryView();
|
} else if (index == 2) {
|
return getAdView();
|
} else {
|
return getHomeTypeView(index - 3, context);
|
}
|
},
|
childCount: homeTypeList.length + 3,
|
))
|
]),
|
refresh: () {
|
page = 1;
|
init();
|
},
|
loadMore: () {
|
getHomeType(page + 1);
|
},
|
))
|
]));
|
}
|
|
void getHomeAd() async {
|
Map<String, dynamic>? result =
|
await HomeApiUtil.getHomeAd(context, "recommend", "1628826741158");
|
if (result == null) {
|
return;
|
}
|
if (result["IsPost"] == "true") {
|
List<dynamic> list = result["Data"]["data"];
|
List<HomeAdModel> adList = [];
|
for (var element in list) {
|
adList.add(HomeAdModel.fromJson(element));
|
}
|
setState(() {
|
bannerList = adList;
|
});
|
}
|
}
|
|
void getHomeType(int _page) async {
|
page = _page;
|
Map<String, dynamic>? result = await HomeApiUtil.getHomeTypes(
|
context, "recommend", "1628826741158", _page);
|
_refreshController.refreshCompleted(resetFooterState: true);
|
//请求失败了
|
if (result == null) {
|
if (page > 1) {
|
page = page - 1;
|
}
|
if (homeTypeList.isEmpty) {
|
_refreshController.apiError!();
|
}
|
|
return;
|
}
|
if (result["IsPost"] == "true") {
|
List<dynamic> list = result["Data"]["data"];
|
totalCount = int.parse(result["Data"]["count"]);
|
List<HomeTypeModel> tempHomeTypeList = [];
|
for (var element in list) {
|
tempHomeTypeList.add(HomeTypeModel.fromJson(element));
|
}
|
setState(() {
|
if (_page == 1) {
|
homeTypeList = tempHomeTypeList;
|
} else {
|
if (tempHomeTypeList.isNotEmpty) {
|
homeTypeList.addAll(tempHomeTypeList);
|
}
|
}
|
});
|
|
if (totalCount <= homeTypeList.length) {
|
_refreshController.loadNoData();
|
} else {
|
if (_page > 1) {
|
_refreshController.loadComplete();
|
}
|
}
|
if (homeTypeList.isEmpty) {
|
_refreshController.dataEmpty!();
|
} else {
|
//正常的状态
|
_refreshController.dataNormal!();
|
}
|
}
|
}
|
|
void getSearchSpecial() async {
|
Map<String, dynamic>? result =
|
await HomeApiUtil.getRecommendSearchSpecial(context);
|
_refreshController.refreshCompleted(resetFooterState: true);
|
//请求失败了
|
if (result == null) {
|
if (page > 1) {
|
page = page - 1;
|
}
|
return;
|
}
|
if (result["IsPost"] == "true") {
|
List<dynamic> list = result["Data"];
|
List<SearchSpecialModel> tempList = [];
|
for (var element in list) {
|
tempList.add(SearchSpecialModel.fromJson(element));
|
}
|
// tempList.add(SearchSpecialModel(
|
// id: "novel",
|
// icon: "assets/imgs/home/icon_home_category_novel.png",
|
// name: "小说"));
|
setState(() {
|
categoryList = tempList;
|
});
|
}
|
}
|
|
void getHotSearch() async {
|
Map<String, dynamic>? result = await SearchApiUtil.getHotSearch(context);
|
if (result == null) {
|
return;
|
}
|
if (result["IsPost"] == "true") {
|
List<dynamic> list = result["Data"]["data"];
|
setState(() {
|
searchKw = list[Random().nextInt(list.length)];
|
});
|
}
|
}
|
|
Widget getBannerView() {
|
double width = MediaQuery.of(context).size.width;
|
double itemWidth = width - 40;
|
double itemHeight = itemWidth * 0.4382;
|
CustomLayoutOption customLayoutOption =
|
CustomLayoutOption(startIndex: -1, stateCount: 3);
|
customLayoutOption.addTranslate([
|
Offset(-(width - 65), 0),
|
const Offset(0.0, 0.0),
|
Offset(width - 65, 0)
|
]);
|
customLayoutOption.addScale([0.8, 1, 0.8], Alignment.center);
|
|
return KeepAliveWrapper(
|
child: bannerList.isNotEmpty
|
? Container(
|
padding: EdgeInsets.only(top: 10),
|
child: SizedBox(
|
width: width,
|
height: itemHeight,
|
child: Swiper(
|
itemBuilder: (BuildContext context, int index) {
|
return ClipRRect(
|
child: VideoImage(
|
bannerList[index].picture,
|
),
|
borderRadius: BorderRadius.circular(8),
|
);
|
},
|
layout: SwiperLayout.DEFAULT,
|
customLayoutOption: customLayoutOption,
|
indicatorLayout: PageIndicatorLayout.COLOR,
|
autoplay: true,
|
duration: 500,
|
itemCount: bannerList.length,
|
pagination: const SwiperPagination(
|
margin: EdgeInsets.all(10),
|
builder: DotSwiperPaginationBuilder(
|
size: 8,
|
activeColor: ColorConstant.theme,
|
color: Colors.grey)),
|
itemWidth: itemWidth,
|
outer: false,
|
scale: 0.86,
|
viewportFraction: 0.86,
|
// containerHeight: itemHeight-30,
|
// containerWidth:width,
|
itemHeight: itemHeight,
|
onTap: (index) {
|
print("banner点击:$index");
|
if (bannerList[index].linkType == 1) {
|
jumpPage("VideoDetailPage", {
|
"video": bannerList[index].video!.toJson(),
|
});
|
} else if (bannerList[index].linkType == 2) {
|
dynamic json = jsonDecode(bannerList[index].params!);
|
String url = json["url"];
|
jumpPage("BrowserPage", {
|
"url": url,
|
});
|
}
|
},
|
)),
|
)
|
: Container());
|
}
|
|
Widget getCategoryView() {
|
return categoryList.isNotEmpty
|
? Container(
|
padding: const EdgeInsets.fromLTRB(10, 20, 10, 10),
|
child: Row(
|
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
children: categoryList
|
.map((e) => InkWell(
|
onTap: () {
|
jumpPage(
|
"VideoListPage", {"kw": e.id!, "title": e.name});
|
},
|
child: Column(children: [
|
CommonImage(
|
e.icon!,
|
width: MediaQuery.of(context).size.width * 55 / 375,
|
),
|
Text(
|
e.name!,
|
style: const TextStyle(
|
color: Color(0xFF3B3B3B), fontSize: 12),
|
)
|
])))
|
.toList()))
|
: Container();
|
}
|
|
Widget getAdView() {
|
return expressAdType != null
|
? Container(
|
padding: const EdgeInsets.fromLTRB(10, 10, 10, 10),
|
child: Column(
|
crossAxisAlignment: CrossAxisAlignment.start,
|
children: [
|
// const Text(
|
// "今日热点",
|
// style: TextStyle(color: Color(0xFF5F5F5F), fontSize: 16),
|
// ),
|
SizedBox(
|
height: (MediaQuery.of(context).size.width - 20) * 0.75,
|
width: MediaQuery.of(context).size.width,
|
child: _nativeView(),
|
)
|
],
|
),
|
)
|
: Container();
|
}
|
|
Widget _nativeView() {
|
return expressAdType == AdType.csj
|
? CSJEXpressAd(
|
expressPid!,
|
MediaQuery.of(context).size.width - 20,
|
(MediaQuery.of(context).size.width - 20) * 0.8,
|
controller: _expressAdController,
|
close: () {
|
setState(() {
|
expressAdType = null;
|
});
|
},
|
loadFail: () {
|
setState(() {
|
expressAdType = null;
|
});
|
},
|
)
|
: GDTEXpressAd(
|
expressPid!,
|
MediaQuery.of(context).size.width - 20,
|
(MediaQuery.of(context).size.width - 20) * 0.8,
|
controller: _expressAdController,
|
close: () {
|
setState(() {
|
expressAdType = null;
|
});
|
},
|
loadFail: () {
|
setState(() {
|
expressAdType = null;
|
});
|
},
|
);
|
}
|
|
Widget getHomeTypeView(index, BuildContext context) {
|
HomeTypeModel homeType = homeTypeList[index];
|
double mx = MediaQuery.of(context).size.width;
|
return VideoListUIUtil.getHomeTypeItem(mx, homeType, context);
|
}
|
}
|