Hibok
Vous ne pouvez pas sélectionner plus de 25 sujets Les noms de sujets doivent commencer par une lettre ou un nombre, peuvent contenir des tirets ('-') et peuvent comporter jusqu'à 35 caractères.
 
 
 
 
 
 

573 lignes
18 KiB

  1. import 'dart:io';
  2. import 'dart:typed_data';
  3. import 'package:chat/data/UserData.dart';
  4. import 'package:chat/data/constants.dart';
  5. import 'package:chat/generated/i18n.dart';
  6. import 'package:chat/home/rich_title.dart';
  7. import 'package:chat/models/UserInfo.dart';
  8. import 'package:chat/models/money_change.dart';
  9. import 'package:chat/models/ref_name_provider.dart';
  10. import 'package:chat/utils/ChargeMoney.dart';
  11. import 'package:chat/utils/CustomUI.dart';
  12. import 'package:chat/utils/HttpUtil.dart';
  13. import 'package:chat/utils/MessageMgr.dart';
  14. import 'package:chat/utils/PicSwiper.dart';
  15. import 'package:chat/utils/TokenMgr.dart';
  16. import 'package:chat/utils/file_cache_mgr.dart';
  17. import 'package:chat/utils/screen.dart';
  18. import 'package:dio/dio.dart';
  19. import 'package:flutter/cupertino.dart';
  20. import 'package:flutter/material.dart';
  21. import 'package:multi_image_picker/multi_image_picker.dart';
  22. import 'package:oktoast/oktoast.dart';
  23. import 'package:provider/provider.dart';
  24. import 'VerificationCenter.dart';
  25. import 'VipPage.dart';
  26. import 'money_picture_view.dart';
  27. const double LeftSize = 80;
  28. const MaxImgSize = 20;
  29. class PhotoPage extends StatefulWidget {
  30. @required
  31. final UserInfo userInfo;
  32. PhotoPage({Key key, this.userInfo}) : super(key: key);
  33. @override
  34. _PhotoPageState createState() => new _PhotoPageState();
  35. }
  36. class _PhotoPageState extends State<PhotoPage> {
  37. bool isMyself = false;
  38. bool isMan = false;
  39. Map imgList = {};
  40. bool isLoadingFinish = false;
  41. double imgWidth = (Screen.width - LeftSize - 60) / 3;
  42. var resultList = [];
  43. bool isBuyPicture = false;
  44. @override
  45. void initState() {
  46. super.initState();
  47. isMyself = widget.userInfo.userId == UserData().basicInfo.userId;
  48. isMan = widget.userInfo.sex == 1;
  49. isBuyPicture = (isMyself ||
  50. widget.userInfo.photoAut == 0 ||
  51. widget.userInfo.payStatus == 1);
  52. getImg();
  53. MessageMgr().on('refresh_photo', msgRefreshPhoto);
  54. }
  55. msgRefreshPhoto(data) {
  56. getImg();
  57. }
  58. void getImg() async {
  59. Map data = {
  60. "visitUserId": UserData().basicInfo.userId,
  61. "userId": widget.userInfo.userId,
  62. };
  63. data['sign'] = TokenMgr().getSign(data);
  64. Response res = await HttpUtil().post('user/personal/album', data: data);
  65. if (res == null) {
  66. return;
  67. }
  68. isLoadingFinish = true;
  69. Map resData = res.data;
  70. if (resData['code'] == 0) {
  71. imgList = {};
  72. resultList = resData['data'] ?? [];
  73. for (int i = 0; i < resultList.length; i++) {
  74. var temp = DateTime.parse(resultList[i]['CreatTime']);
  75. if (imgList[temp.year] == null) {
  76. imgList[temp.year] = {
  77. 1: [],
  78. 2: [],
  79. 3: [],
  80. 4: [],
  81. 5: [],
  82. 6: [],
  83. 7: [],
  84. 8: [],
  85. 9: [],
  86. 10: [],
  87. 11: [],
  88. 12: [],
  89. };
  90. }
  91. imgList[temp.year][temp.month].add(resultList[i]);
  92. }
  93. if (isMyself) {
  94. UserData().picNum = 0;
  95. for (int i = 0; i < resultList.length; i++) {
  96. if (resultList[i]['Status'] == 1) {
  97. UserData().picNum++;
  98. }
  99. if (resultList[i]['Status'] == 0 || resultList[i]['Status'] == 2) {
  100. UserData().haveReview = true;
  101. }
  102. }
  103. }
  104. if (mounted) {
  105. setState(() {});
  106. }
  107. }
  108. }
  109. @override
  110. Widget build(BuildContext context) {
  111. var content = Scaffold(
  112. appBar: AppBar(
  113. title: !isMyself
  114. ? Text(
  115. (isMyself
  116. ? I18n.of(context).my_album
  117. : (isMan
  118. ? I18n.of(context).his_photo
  119. : I18n.of(context).her_photo)),
  120. textScaleFactor: 1.0,
  121. style: TextStyle(
  122. color: AppColors.NewAppbarTextColor, fontSize: 20),
  123. )
  124. : Column(children: <Widget>[
  125. Text(
  126. (isMyself
  127. ? I18n.of(context).my_album
  128. : (isMan
  129. ? I18n.of(context).his_photo
  130. : I18n.of(context).her_photo)),
  131. textScaleFactor: 1.0,
  132. style: TextStyle(
  133. color: AppColors.NewAppbarTextColor, fontSize: 20),
  134. ),
  135. Text(
  136. '${resultList.length}/$MaxImgSize',
  137. style: TextStyle(fontSize: 11),
  138. )
  139. ]),
  140. leading: CustomUI.buildCustomLeading(context),
  141. titleSpacing: -10,
  142. centerTitle: true,
  143. elevation: 1,
  144. actions: <Widget>[
  145. !isMan && isMyself
  146. ? Container(
  147. alignment: Alignment.center,
  148. child: new InkWell(
  149. child: new Padding(
  150. padding: EdgeInsets.only(
  151. right: 15, left: 15, top: 10, bottom: 10),
  152. child: new Text(
  153. I18n.of(context).set_photo,
  154. textScaleFactor: 1.0,
  155. style: TextStyle(color: Constants.BlueTextColor,fontSize: 12),
  156. ),
  157. ),
  158. onTap: () {
  159. if (!widget.userInfo.isAttestation) {
  160. _buildNotTrue();
  161. return;
  162. }
  163. if (imgList.length == 0) {
  164. showToast(I18n.of(context).no_photos);
  165. return;
  166. }
  167. var moneyList = [];
  168. for (int i = 0; i < resultList.length; i++) {
  169. if (resultList[i]['Status'] == 1) {
  170. moneyList.add(resultList[i]);
  171. }
  172. }
  173. Navigator.of(context)
  174. .push(new MaterialPageRoute(builder: (context) {
  175. return MoneyPicture(
  176. imageList: moneyList,
  177. );
  178. }));
  179. },
  180. ),
  181. )
  182. : Container()
  183. ]),
  184. backgroundColor: Colors.white,
  185. body: SafeArea(
  186. child: SingleChildScrollView(
  187. child: Column(children: _buildBody()),
  188. )),
  189. );
  190. return CustomUI.buildPageLoading(context, content, !isLoadingFinish);
  191. }
  192. void _buildNotTrue() {
  193. CustomUI.buildOneConfirm(context, I18n.of(context).moneyPageTip,
  194. I18n.of(context).authenticate_now, () {
  195. Navigator.pop(context);
  196. Navigator.of(context).push(
  197. new MaterialPageRoute(
  198. builder: (context) {
  199. return VerificationCenterPage();
  200. },
  201. ),
  202. );
  203. });
  204. }
  205. buyPhoto() {
  206. //女性用户付费,男性用户会员的话免费解锁,非会员付费解锁
  207. becomeVip() {
  208. Navigator.of(context).push(
  209. new MaterialPageRoute(
  210. builder: (context) {
  211. return VipPage();
  212. },
  213. ),
  214. );
  215. }
  216. payCallback() {
  217. if (Provider.of<MoneyChangeProvider>(context).money <
  218. widget.userInfo.price) {
  219. Navigator.of(context).pop();
  220. CustomUI.buildOneConfirm(context, I18n.of(context).balance_insufficien,
  221. I18n.of(context).recharge, () {
  222. Navigator.of(context).pop();
  223. ChargeMoney.showChargeSheet(context, () {
  224. setState(() {});
  225. });
  226. });
  227. return;
  228. }
  229. Navigator.of(context).pop();
  230. HttpUtil().buyPictures(
  231. widget.userInfo.price, widget.userInfo.userId, context, () {
  232. setState(() {
  233. isBuyPicture = true;
  234. widget.userInfo.payStatus = 1;
  235. });
  236. });
  237. }
  238. freeTime() {
  239. HttpUtil().userFreeTime(context, widget.userInfo.userId, 1, () {
  240. UserData().basicInfo.usedNum++;
  241. Navigator.of(context).pop();
  242. setState(() {
  243. isBuyPicture = true;
  244. widget.userInfo.payStatus = 1;
  245. });
  246. });
  247. }
  248. String title = I18n.of(context).unlock_user.replaceFirst(
  249. '/s1',
  250. Provider.of<RefNameProvider>(context)
  251. .getRefName(widget.userInfo.userId, widget.userInfo.nickName),
  252. );
  253. if (!UserData().isMan()) {
  254. CustomUI.buildOneConfirm(
  255. context,
  256. title,
  257. I18n.of(context)
  258. .pay_unlock
  259. .replaceFirst('/s1', widget.userInfo.price.toString()),
  260. payCallback);
  261. } else if (UserData().isVip) {
  262. if (UserData().basicInfo.freeNum < UserData().basicInfo.usedNum) {
  263. CustomUI.buildOneConfirm(
  264. context,
  265. title,
  266. I18n.of(context)
  267. .pay_unlock
  268. .replaceFirst('/s1', widget.userInfo.price.toString()),
  269. payCallback);
  270. } else {
  271. CustomUI.buildOneConfirm(
  272. context, title, I18n.of(context).unlock_choose, freeTime);
  273. }
  274. } else {
  275. CustomUI.buildTowConfirm(
  276. context,
  277. title,
  278. I18n.of(context).become_member,
  279. becomeVip,
  280. I18n.of(context)
  281. .pay_unlock
  282. .replaceFirst('/s1', widget.userInfo.price.toString()),
  283. payCallback);
  284. }
  285. }
  286. Widget _buildLockWidget() {
  287. TitleItem title;
  288. if (!isMan) {
  289. title = UserData().isVip
  290. ? TitleItem(
  291. title: I18n.of(context).unlock_user,
  292. name: Provider.of<RefNameProvider>(context)
  293. .getRefName(widget.userInfo.userId, widget.userInfo.nickName),
  294. )
  295. : TitleItem(
  296. title: I18n.of(context).free_unlock,
  297. name: widget.userInfo.price.toString() +
  298. I18n.of(context).mask_coin);
  299. } else {
  300. title = TitleItem(
  301. title: I18n.of(context).pay_unlock,
  302. name: widget.userInfo.price.toString());
  303. }
  304. return Container(
  305. height: Screen.height * 0.7,
  306. alignment: Alignment.center,
  307. child: Column(
  308. mainAxisAlignment: MainAxisAlignment.center,
  309. children: <Widget>[
  310. Image.asset(
  311. 'assets/images/lock_photo.png',
  312. width: 160,
  313. //color: Colors.grey[700],
  314. ),
  315. Container(
  316. margin: EdgeInsets.only(top: 20),
  317. alignment: Alignment.center,
  318. child: Text(
  319. isMan ? I18n.of(context).set_lock : I18n.of(context).set_lock2,
  320. textScaleFactor: 1.0,
  321. style: TextStyle(
  322. color: Colors.grey[700],
  323. fontSize: 15,
  324. fontWeight: FontWeight.bold),
  325. ),
  326. ),
  327. Container(
  328. margin: EdgeInsets.only(top: 8),
  329. alignment: Alignment.center,
  330. child: RichText(
  331. text: TextSpan(
  332. children: RichTitle.getRichText(title,
  333. titleStyle:
  334. TextStyle(color: Colors.grey[700], fontSize: 13),
  335. nameStyle: TextStyle(color: Colors.red, fontSize: 13))),
  336. ),
  337. ),
  338. InkWell(
  339. onTap: buyPhoto,
  340. child: Container(
  341. margin: EdgeInsets.only(top: 30),
  342. padding: EdgeInsets.only(top: 6, bottom: 6),
  343. width: 100,
  344. alignment: Alignment.center,
  345. decoration: Constants.ConfirmBUttonBoxDecoration,
  346. child: Text(
  347. I18n.of(context).unlock,
  348. textScaleFactor: 1.0,
  349. style: TextStyle(color: Colors.white, fontSize: 18),
  350. ),
  351. )),
  352. ],
  353. ));
  354. }
  355. List<Widget> _buildBody() {
  356. List<Widget> list = [_buildUpload()];
  357. if (imgList.length == 0 && isLoadingFinish && !isMyself) {
  358. list.add(CustomUI.buildNoData(context));
  359. return list;
  360. }
  361. if (!isBuyPicture) {
  362. list.add(_buildLockWidget());
  363. return list;
  364. }
  365. imgList.keys.forEach((k) {
  366. list.add(_buildYear(k));
  367. });
  368. return list;
  369. }
  370. //上传相册
  371. void _uploadPhoto() async {
  372. int leftLength = MaxImgSize - imgList.length;
  373. if (leftLength <= 0) {
  374. showToast(I18n.of(context)
  375. .max_upload_size
  376. .replaceFirst('/s1', MaxImgSize.toString()));
  377. return;
  378. }
  379. List<Asset> resultList = List<Asset>();
  380. resultList = await MultiImagePicker.pickImages(
  381. maxImages: leftLength > 9 ? 9 : leftLength,
  382. enableCamera: false,
  383. selectedAssets: [],
  384. cupertinoOptions: CupertinoOptions(takePhotoIcon: "chat"),
  385. materialOptions: MaterialOptions(
  386. actionBarColor: "#50A7F9",
  387. actionBarTitle: "Hibok",
  388. allViewTitle: "",
  389. useDetailsView: true,
  390. selectCircleStrokeColor: "#000000",
  391. ),
  392. );
  393. if (resultList != null && resultList.length > 0) {
  394. List<File> fileList = [];
  395. for (var i = 0; i < resultList.length; i++) {
  396. Asset photoEntity = resultList[i];
  397. print('名字:${photoEntity.name}');
  398. ByteData byteData = await photoEntity.getByteData();
  399. File file = await FileCacheMgr().writeFile(
  400. 'temp-photo-${DateTime.now().millisecondsSinceEpoch}.png',
  401. byteData.buffer.asInt8List(0));
  402. fileList.add(file);
  403. }
  404. print('文件列表${fileList.length}');
  405. Map data = {"type": 2, "userId": UserData().basicInfo.userId};
  406. data['sign'] = TokenMgr().getSign(data);
  407. data['sex'] = UserData().basicInfo.sex;
  408. data['isBurn'] = 0;
  409. Response res = await HttpUtil().uploadFiles(
  410. fileList, data, 'upload/post/postfiles', 'image',
  411. isShowLoading: true);
  412. var resData = res.data;
  413. if (resData['code'] == 0) {
  414. if (resData['data']['msg'] != '' && resData['data']['msg'] != null) {
  415. showToast(resData['data']['msg']);
  416. }
  417. if (resData['msg'].split('|').length != fileList.length) {
  418. showToast(I18n.of(context).hava_error_photo);
  419. }
  420. //MessageMgr().emit('refresh_photo');
  421. getImg();
  422. } else {
  423. showToast(resData['msg']);
  424. }
  425. }
  426. }
  427. Widget _buildUpload() {
  428. return isMyself
  429. ? Container(
  430. margin: EdgeInsets.only(top: 20),
  431. child: Row(
  432. crossAxisAlignment: CrossAxisAlignment.start,
  433. children: <Widget>[
  434. Container(
  435. alignment: Alignment.centerRight,
  436. margin: EdgeInsets.only(right: 15),
  437. width: LeftSize,
  438. child: Text(
  439. I18n.of(context).upload1,
  440. style:
  441. TextStyle(fontSize: 15, fontWeight: FontWeight.w600),
  442. )),
  443. InkWell(
  444. onTap: _uploadPhoto,
  445. child: Container(
  446. width: imgWidth,
  447. height: imgWidth,
  448. margin: EdgeInsets.all(5),
  449. decoration: BoxDecoration(
  450. color: Color(0xFFEDEDED),
  451. borderRadius: BorderRadius.circular(10)),
  452. child: Icon(
  453. IconData(0xe686, fontFamily: Constants.IconFontFamily),
  454. size: 35,
  455. color: Colors.white,
  456. ),
  457. ))
  458. ],
  459. ),
  460. )
  461. : Container();
  462. }
  463. Widget _buildYear(int year) {
  464. var list = [_buildYearTips(year)];
  465. imgList[year].keys.forEach((k) {
  466. if (imgList[year][k].length > 0) {
  467. list.add(_buildMonth(year, k));
  468. }
  469. });
  470. return Container(
  471. width: Screen.width,
  472. child: Column(
  473. crossAxisAlignment: CrossAxisAlignment.start,
  474. children: list,
  475. ));
  476. }
  477. Widget _buildYearTips(int year) {
  478. return Container(
  479. alignment: Alignment.centerRight,
  480. margin: EdgeInsets.only(right: 15, top: 20, bottom: 18),
  481. width: LeftSize,
  482. child: Text(
  483. '$year${I18n.of(context).year}',
  484. style: TextStyle(fontSize: 15, fontWeight: FontWeight.w600),
  485. ));
  486. }
  487. Widget _buildMonth(int year, int month) {
  488. if (imgList[year] == null || imgList[year][month] == null) {
  489. return Container();
  490. }
  491. List<PicSwiperItem> pisc = [];
  492. imgList[year][month].forEach((f) {
  493. pisc.add(PicSwiperItem(
  494. f['ImgUrl'],
  495. id: f['Id'],
  496. type: f['Type'],
  497. isWatch: f['IsCheck'] == 1,
  498. userId: widget.userInfo.userId,
  499. isBuy: f['PayStatus'] == 1,
  500. isCheck: f['Status'] == 0,
  501. ));
  502. });
  503. List<Widget> list = [];
  504. imgList[year][month].forEach((data) {
  505. bool isWatch = data['IsCheck'] == 1;
  506. double raduis = 10;
  507. list.add(CustomUI.buildImgCover(data['Id'], pisc, data['ImgUrl'],
  508. imgWidth, raduis, isWatch, context, data['Type'],
  509. isMyself: isMyself,
  510. payStatus: data['PayStatus'],
  511. state: isMan ? 1 : data['Status']));
  512. });
  513. return Row(
  514. crossAxisAlignment: CrossAxisAlignment.start,
  515. children: <Widget>[
  516. Container(
  517. alignment: Alignment.centerRight,
  518. margin: EdgeInsets.only(right: 15, top: 1),
  519. width: LeftSize,
  520. child: Text(
  521. '$month${I18n.of(context).month}',
  522. style: TextStyle(fontSize: 15, fontWeight: FontWeight.w600),
  523. )),
  524. Container(
  525. width: Screen.width - LeftSize - 15,
  526. child: Wrap(
  527. crossAxisAlignment: WrapCrossAlignment.start,
  528. children: list,
  529. ))
  530. ],
  531. );
  532. }
  533. @override
  534. void dispose() {
  535. super.dispose();
  536. MessageMgr().off('refresh_photo', msgRefreshPhoto);
  537. }
  538. }