551 lines
22 KiB
Dart
551 lines
22 KiB
Dart
import 'dart:io';
|
|
|
|
import 'package:flutter/material.dart';
|
|
import 'package:flutter_kinetra/kt_model/kt_goods_bean.dart';
|
|
import 'package:flutter_kinetra/kt_utils/kt_string_extend.dart';
|
|
import 'package:flutter_kinetra/kt_utils/kt_utils.dart';
|
|
import 'package:flutter_screenutil/flutter_screenutil.dart';
|
|
|
|
import '../kt_model/kt_store_bean.dart';
|
|
|
|
///商店组件
|
|
class KtStoreWidget extends StatefulWidget {
|
|
final KtStoreBean store;
|
|
final bool onlyCoins;
|
|
final bool isStoreDialog;
|
|
final void Function(KtGoodsBean goods)? onItemTap; // 新增回调
|
|
|
|
const KtStoreWidget({
|
|
super.key,
|
|
required this.store,
|
|
this.onItemTap,
|
|
this.isStoreDialog = false,
|
|
this.onlyCoins = false,
|
|
});
|
|
|
|
@override
|
|
State<KtStoreWidget> createState() => _KtStoreWidgetState();
|
|
}
|
|
|
|
class _KtStoreWidgetState extends State<KtStoreWidget> {
|
|
int selVip = -1;
|
|
int selCoin = -1;
|
|
@override
|
|
Widget build(BuildContext context) {
|
|
return Column(
|
|
crossAxisAlignment: CrossAxisAlignment.start,
|
|
children: initWidget(),
|
|
);
|
|
}
|
|
|
|
Widget descView() {
|
|
return Text(
|
|
'''
|
|
1. Coins are virtual items and cannot be refunded. Use it for this product. \n
|
|
2. Gold coins will never expire, the reward coins will expire 24 hours a day.\n
|
|
3. Coins will be used first when unlocking episodes. If the amount is insufficient, reward coins will automatically be used. \n
|
|
4. The purchase has not been credited, click <Restore> to refresh. \n
|
|
5. For other questions, contact us via Profile>Help &feedback.\n
|
|
''',
|
|
style: TextStyle(fontSize: 12.sp, color: Color(0xFF848484), height: 0.95),
|
|
);
|
|
}
|
|
|
|
List<Widget> initWidget() {
|
|
// if (widget.onlyCoins) return [coinList()];
|
|
List<Widget> widgets = [SizedBox(height: 10.w)];
|
|
//
|
|
// int coinsIndex = widget.store.sort?.indexOf('list_coins') ?? 0;
|
|
// int vipIndex = widget.store.sort?.indexOf('list_sub_vip') ?? 0;
|
|
// if (coinsIndex < vipIndex) {
|
|
widgets.addAll([coinList(), SizedBox(height: 15.w), vipList()]);
|
|
// } else {
|
|
// widgets.addAll([vipList(), SizedBox(height: 15.w), coinList()]);
|
|
// }
|
|
|
|
widgets.addAll([
|
|
if (widget.store.payMode == 0 && widget.store.showType == 0)
|
|
SizedBox(height: 15.w),
|
|
descView(),
|
|
]);
|
|
|
|
return widgets;
|
|
}
|
|
|
|
List<KtGoodsBean> get smallList =>
|
|
widget.store.listCoins!.where((item) => item.size == 'small').toList();
|
|
|
|
List<KtGoodsBean> get bigList =>
|
|
widget.store.listCoins!.where((item) => item.size == 'big').toList();
|
|
|
|
Widget coinList() {
|
|
if (widget.store.listCoins?.isEmpty ?? true) return Container();
|
|
|
|
return Column(
|
|
crossAxisAlignment: CrossAxisAlignment.start,
|
|
children: [
|
|
if (!widget.onlyCoins)
|
|
Row(
|
|
children: [
|
|
Text(
|
|
'Go Coins',
|
|
style: TextStyle(
|
|
fontSize: 14.sp,
|
|
color: widget.isStoreDialog
|
|
? Color(0xFF1E1E20)
|
|
: Colors.white,
|
|
fontWeight: FontWeight.w600,
|
|
),
|
|
),
|
|
Text(
|
|
' | Limited-time coin packs',
|
|
style: TextStyle(
|
|
fontSize: 14.sp,
|
|
color: widget.isStoreDialog
|
|
? Color(0xFF1E1E20)
|
|
: Colors.white,
|
|
fontWeight: FontWeight.w200,
|
|
),
|
|
),
|
|
],
|
|
),
|
|
SizedBox(height: 10.w),
|
|
// big
|
|
// if (!onlyNewSubCoins)
|
|
Row(
|
|
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
|
children: [
|
|
...bigList.map((item) {
|
|
return GestureDetector(
|
|
onTap: () {
|
|
selCoin = item.id ?? -1;
|
|
setState(() {});
|
|
widget.onItemTap?.call(item); // 回调
|
|
},
|
|
child: Stack(
|
|
children: [
|
|
Container(
|
|
width: 167.w,
|
|
padding: EdgeInsets.fromLTRB(4.w, 17.w, 5.w, 3.w),
|
|
decoration: BoxDecoration(
|
|
image: DecorationImage(
|
|
image: AssetImage('coin_big_bg.png'.ktIcon),
|
|
fit: BoxFit.fill,
|
|
),
|
|
),
|
|
child: Column(
|
|
mainAxisAlignment: MainAxisAlignment.end,
|
|
children: [
|
|
Row(
|
|
mainAxisAlignment: MainAxisAlignment.center,
|
|
children: [
|
|
Image.asset('ic_coin.png'.ktIcon, width: 22.4.w),
|
|
Text(
|
|
'${item.coins ?? 0}',
|
|
style: TextStyle(
|
|
fontSize: 20.sp,
|
|
color: Color(0xFF1E1E20),
|
|
fontWeight: FontWeight.w500,
|
|
),
|
|
),
|
|
SizedBox(width: 4.w),
|
|
if ((item.sendCoins ?? 0) > 0)
|
|
Text(
|
|
'+${item.sendCoins}',
|
|
style: TextStyle(
|
|
fontSize: 12.sp,
|
|
fontWeight: FontWeight.w500,
|
|
color: Color(0xFFAD8502),
|
|
),
|
|
),
|
|
],
|
|
),
|
|
SizedBox(height: 6.w),
|
|
Container(
|
|
width: 160.w,
|
|
alignment: Alignment.center,
|
|
padding: EdgeInsets.symmetric(vertical: 6.w),
|
|
decoration: BoxDecoration(
|
|
color: Color(0xFF1E1E20),
|
|
borderRadius: BorderRadius.circular(8.w),
|
|
),
|
|
child: Text(
|
|
'${item.productDetails?.price ?? 0}',
|
|
style: TextStyle(
|
|
fontSize: 13.sp,
|
|
color: Color(0xFFFFD321),
|
|
fontWeight: FontWeight.w700,
|
|
fontStyle: FontStyle.italic,
|
|
),
|
|
),
|
|
),
|
|
],
|
|
),
|
|
),
|
|
if (!item.cornerMarker.isNullString)
|
|
Positioned(
|
|
top: 4.w,
|
|
left: 4.w,
|
|
child: Image.asset('ic_fire.png'.ktIcon, width: 16.w),
|
|
),
|
|
if ((item.sendCoins ?? 0) > 0)
|
|
Positioned(
|
|
right: 0,
|
|
top: 0,
|
|
child: Container(
|
|
width: 42.w,
|
|
height: 16.w,
|
|
padding: EdgeInsets.symmetric(horizontal: 3.w),
|
|
alignment: Alignment.center,
|
|
decoration: BoxDecoration(
|
|
gradient: LinearGradient(
|
|
begin: Alignment(0.50, 0.00),
|
|
end: Alignment(0.50, 1.00),
|
|
colors: [
|
|
const Color(0xFFFD9A68),
|
|
const Color(0xFFFF538D),
|
|
],
|
|
),
|
|
borderRadius: BorderRadius.only(
|
|
topLeft: Radius.circular(8.w),
|
|
topRight: Radius.circular(8.w),
|
|
bottomLeft: Radius.circular(8.w),
|
|
),
|
|
),
|
|
child: Text(
|
|
'+${((item.sendCoins ?? 0) / (item.coins ?? 1) * 100).toInt()}%',
|
|
style: TextStyle(
|
|
fontSize: 10.sp,
|
|
color: Colors.white,
|
|
fontWeight: FontWeight.w500,
|
|
),
|
|
),
|
|
),
|
|
),
|
|
],
|
|
),
|
|
);
|
|
}),
|
|
],
|
|
),
|
|
SizedBox(height: 10.w),
|
|
// if (!widget.onlyCoins) subCoinList(),
|
|
// small
|
|
// if (!onlyNewSubCoins)
|
|
GridView.builder(
|
|
shrinkWrap: true,
|
|
padding: EdgeInsets.zero,
|
|
physics: const NeverScrollableScrollPhysics(),
|
|
gridDelegate: SliverGridDelegateWithFixedCrossAxisCount(
|
|
crossAxisCount: 3,
|
|
mainAxisSpacing: 10.w,
|
|
crossAxisSpacing: 10.w,
|
|
childAspectRatio: 108 / 90,
|
|
),
|
|
itemBuilder: (_, index) {
|
|
var item = smallList[index];
|
|
return GestureDetector(
|
|
onTap: () {
|
|
selCoin = item.id ?? -1;
|
|
setState(() {});
|
|
widget.onItemTap?.call(item); // 回调
|
|
},
|
|
child: Stack(
|
|
children: [
|
|
Container(
|
|
width: 108.w,
|
|
padding: EdgeInsets.fromLTRB(5.w, 14.w, 5.w, 4.w),
|
|
decoration: BoxDecoration(
|
|
image: DecorationImage(
|
|
image: AssetImage('coin_small_bg.png'.ktIcon),
|
|
fit: BoxFit.fill,
|
|
),
|
|
),
|
|
child: Column(
|
|
mainAxisAlignment: MainAxisAlignment.end,
|
|
children: [
|
|
Column(
|
|
children: [
|
|
Row(
|
|
mainAxisAlignment: MainAxisAlignment.center,
|
|
children: [
|
|
Image.asset(
|
|
'ic_coin.png'.ktIcon,
|
|
width: 22.4.w,
|
|
),
|
|
Text(
|
|
'${item.coins ?? 0}',
|
|
style: TextStyle(
|
|
fontSize: 20.sp,
|
|
color: Color(0xFF1E1E20),
|
|
fontWeight: FontWeight.w500,
|
|
height: 0.8,
|
|
),
|
|
),
|
|
],
|
|
),
|
|
if ((item.sendCoins ?? 0) > 0)
|
|
Text(
|
|
'+${item.sendCoins}',
|
|
style: TextStyle(
|
|
fontSize: 12.sp,
|
|
fontWeight: FontWeight.w500,
|
|
color: Color(0xFF499C00),
|
|
),
|
|
),
|
|
],
|
|
),
|
|
const Spacer(),
|
|
Container(
|
|
alignment: Alignment.center,
|
|
padding: EdgeInsets.symmetric(vertical: 4.w),
|
|
decoration: BoxDecoration(
|
|
color: Color(0xFF1E1E20),
|
|
borderRadius: BorderRadius.circular(8.w),
|
|
),
|
|
child: Text(
|
|
'${item.productDetails?.price ?? 0}',
|
|
style: TextStyle(
|
|
fontSize: 13.sp,
|
|
color: Color(0xFF80FF00),
|
|
fontWeight: FontWeight.w700,
|
|
fontStyle: FontStyle.italic,
|
|
),
|
|
),
|
|
),
|
|
],
|
|
),
|
|
),
|
|
if (!item.cornerMarker.isNullString)
|
|
Positioned(
|
|
top: 4.w,
|
|
left: 4.w,
|
|
child: Image.asset('ic_fire.png'.ktIcon, width: 16.w),
|
|
),
|
|
if ((item.sendCoins ?? 0) > 0)
|
|
Positioned(
|
|
right: 0,
|
|
top: 0,
|
|
child: Container(
|
|
width: 42.w,
|
|
height: 16.w,
|
|
padding: EdgeInsets.symmetric(horizontal: 3.w),
|
|
alignment: Alignment.center,
|
|
decoration: BoxDecoration(
|
|
gradient: LinearGradient(
|
|
begin: Alignment(0.50, 0.00),
|
|
end: Alignment(0.50, 1.00),
|
|
colors: [
|
|
const Color(0xFFFD9A68),
|
|
const Color(0xFFFF538D),
|
|
],
|
|
),
|
|
borderRadius: BorderRadius.only(
|
|
topLeft: Radius.circular(8.w),
|
|
topRight: Radius.circular(8.w),
|
|
bottomLeft: Radius.circular(8.w),
|
|
),
|
|
),
|
|
child: Text(
|
|
'+${((item.sendCoins ?? 0) / (item.coins ?? 1) * 100).toInt()}%',
|
|
style: TextStyle(
|
|
fontSize: 10.sp,
|
|
color: Colors.white,
|
|
fontWeight: FontWeight.w500,
|
|
),
|
|
),
|
|
),
|
|
),
|
|
],
|
|
),
|
|
);
|
|
},
|
|
itemCount: smallList.length,
|
|
),
|
|
],
|
|
);
|
|
}
|
|
|
|
Widget vipList() {
|
|
if (widget.store.listSubVip?.isEmpty ?? true) return Container();
|
|
if (widget.store.payMode == 1) return Container();
|
|
final colors = {
|
|
"month": Color(0xFF00679A),
|
|
"week": Color(0xFF3D6D00),
|
|
"quarter": Color(0xFF5C5FB5),
|
|
"year": Color(0xFFAE6F00),
|
|
};
|
|
final textColors = {
|
|
"month": Color(0xFFBDEBFF),
|
|
"week": Color(0xFFE7FCCA),
|
|
"quarter": Color(0xFFDBDDFF),
|
|
"year": Color(0xFFFFF2DA),
|
|
};
|
|
return Column(
|
|
crossAxisAlignment: CrossAxisAlignment.start,
|
|
children: [
|
|
Text(
|
|
'Go VIP Premium | Auto renew, cancel anytime ',
|
|
style: TextStyle(
|
|
fontSize: 14.sp,
|
|
color: Colors.white,
|
|
fontWeight: FontWeight.w500,
|
|
),
|
|
),
|
|
SizedBox(height: 10.w),
|
|
ListView.separated(
|
|
padding: EdgeInsets.zero,
|
|
shrinkWrap: true,
|
|
physics: const NeverScrollableScrollPhysics(),
|
|
itemBuilder: (_, index) {
|
|
KtGoodsBean item = widget.store.listSubVip![index];
|
|
return GestureDetector(
|
|
onTap: () {
|
|
selVip = item.id ?? -1;
|
|
setState(() {});
|
|
widget.onItemTap?.call(item); // 回调
|
|
},
|
|
child: Container(
|
|
width: ScreenUtil().screenWidth - 30.w,
|
|
padding: EdgeInsets.fromLTRB(12.w, 19.w, 12.w, 5.w),
|
|
decoration: BoxDecoration(
|
|
image: DecorationImage(
|
|
image: AssetImage('vip_${item.vipTypeKey}_bg.png'.ktIcon),
|
|
fit: BoxFit.fill,
|
|
),
|
|
border: selVip == item.id
|
|
? Border.all(color: Colors.red, width: 1.5.w)
|
|
: null,
|
|
),
|
|
child: Column(
|
|
crossAxisAlignment: CrossAxisAlignment.start,
|
|
children: [
|
|
Text(
|
|
'${item.shortType ?? ''} VIP',
|
|
style: TextStyle(
|
|
fontSize: 14.sp,
|
|
color: Color(0xFF2A0428),
|
|
fontWeight: FontWeight.w500,
|
|
),
|
|
),
|
|
item.discountType != 0
|
|
? RichText(
|
|
text: TextSpan(
|
|
children: [
|
|
TextSpan(
|
|
text: Platform.isAndroid
|
|
? item.productDetails?.price
|
|
: KtUtils.getDiscountPrice(
|
|
item.productDetails,
|
|
),
|
|
style: TextStyle(
|
|
fontSize: 26.sp,
|
|
color: Color(0xFF2A0428),
|
|
fontStyle: FontStyle.italic,
|
|
),
|
|
),
|
|
TextSpan(
|
|
text: Platform.isIOS
|
|
? item.productDetails?.price
|
|
: KtUtils.getDiscountPrice(
|
|
item.productDetails,
|
|
),
|
|
style: TextStyle(
|
|
fontSize: 16.sp,
|
|
color: Color(0xFFC2C2C2),
|
|
decoration:
|
|
TextDecoration.lineThrough, // 中间横线
|
|
),
|
|
),
|
|
],
|
|
),
|
|
)
|
|
: RichText(
|
|
text: TextSpan(
|
|
children: [
|
|
// TextSpan(
|
|
// text: item.productDetails?.currencySymbol ?? '',
|
|
// style: TextStyle(fontSize: 16.sp, color: ColorResource.mainBlack),
|
|
// ),
|
|
TextSpan(
|
|
text: Platform.isIOS
|
|
? item.productDetails?.price
|
|
: KtUtils.getDiscountPrice(
|
|
item.productDetails,
|
|
),
|
|
style: TextStyle(
|
|
fontSize: 26.sp,
|
|
color: Color(0xFF2A0428),
|
|
fontStyle: FontStyle.italic,
|
|
),
|
|
),
|
|
TextSpan(
|
|
text:
|
|
'/${KtUtils.filterVipType(item.vipType ?? '')['shortName']}',
|
|
style: TextStyle(
|
|
fontSize: 16.sp,
|
|
color: Colors.black,
|
|
),
|
|
),
|
|
],
|
|
),
|
|
),
|
|
SizedBox(height: 4.w),
|
|
|
|
SizedBox(height: 2.w),
|
|
Row(
|
|
children: [
|
|
Text(
|
|
'Unlimited access to all series',
|
|
// item.description ?? '',
|
|
style: TextStyle(
|
|
fontSize: 10.sp,
|
|
color: Color(0xFF99889B),
|
|
),
|
|
),
|
|
const Spacer(),
|
|
if ((item.sendCoins ?? 0) > 0)
|
|
Stack(
|
|
alignment: Alignment.topCenter,
|
|
children: [
|
|
Container(
|
|
padding: EdgeInsets.only(top: 8.w),
|
|
child: Image.asset(
|
|
'${KtUtils.filterVipType(item.vipType ?? '')['shortName']}_text_bg.png'.ktIcon,
|
|
height: 10.w,
|
|
),
|
|
),
|
|
Row(
|
|
children: [
|
|
Text(
|
|
'+Extra ${item.sendCoins}',
|
|
style: TextStyle(
|
|
fontSize: 12.sp,
|
|
color: Color(0xFF1E1E20),
|
|
fontWeight: FontWeight.w500,
|
|
),
|
|
),
|
|
SizedBox(width: 2.w),
|
|
Image.asset(
|
|
'ic_coin.png'.ktIcon,
|
|
width: 15.w,
|
|
),
|
|
],
|
|
),
|
|
],
|
|
),
|
|
],
|
|
),
|
|
],
|
|
),
|
|
),
|
|
);
|
|
},
|
|
separatorBuilder: (_, __) => SizedBox(height: 10.w),
|
|
itemCount: widget.store.listSubVip?.length ?? 0,
|
|
),
|
|
],
|
|
);
|
|
}
|
|
}
|