mod: 代码整理
This commit is contained in:
@ -27,9 +27,6 @@ class VideoCardHSkeleton extends StatelessWidget {
|
||||
aspectRatio: StyleString.aspectRatio,
|
||||
child: LayoutBuilder(
|
||||
builder: (context, boxConstraints) {
|
||||
double maxWidth = boxConstraints.maxWidth;
|
||||
double maxHeight = boxConstraints.maxHeight;
|
||||
double PR = MediaQuery.of(context).devicePixelRatio;
|
||||
return Container(
|
||||
decoration: BoxDecoration(
|
||||
color: Theme.of(context)
|
||||
|
@ -13,7 +13,6 @@ class AppBarWidget extends StatelessWidget implements PreferredSizeWidget {
|
||||
final bool visible;
|
||||
|
||||
@override
|
||||
// TODO: implement preferredSize
|
||||
Size get preferredSize => child.preferredSize;
|
||||
|
||||
@override
|
||||
|
@ -1,9 +1,9 @@
|
||||
import 'package:flutter/material.dart';
|
||||
|
||||
class HttpError extends StatelessWidget {
|
||||
HttpError({required this.errMsg, required this.fn, super.key});
|
||||
const HttpError({required this.errMsg, required this.fn, super.key});
|
||||
|
||||
String errMsg = '';
|
||||
final String? errMsg;
|
||||
final Function()? fn;
|
||||
|
||||
@override
|
||||
@ -16,7 +16,7 @@ class HttpError extends StatelessWidget {
|
||||
mainAxisAlignment: MainAxisAlignment.center,
|
||||
children: [
|
||||
Text(
|
||||
errMsg,
|
||||
errMsg ?? '请求异常',
|
||||
textAlign: TextAlign.center,
|
||||
style: Theme.of(context).textTheme.titleMedium,
|
||||
),
|
||||
|
@ -6,9 +6,10 @@ import 'package:pilipala/pages/rcmd/controller.dart';
|
||||
import 'package:pilipala/utils/utils.dart';
|
||||
|
||||
class LiveCard extends StatelessWidget {
|
||||
var liveItem;
|
||||
// ignore: prefer_typing_uninitialized_variables
|
||||
final liveItem;
|
||||
|
||||
LiveCard({
|
||||
const LiveCard({
|
||||
Key? key,
|
||||
required this.liveItem,
|
||||
}) : super(key: key);
|
||||
@ -37,14 +38,11 @@ class LiveCard extends StatelessWidget {
|
||||
child: LayoutBuilder(builder: (context, boxConstraints) {
|
||||
double maxWidth = boxConstraints.maxWidth;
|
||||
double maxHeight = boxConstraints.maxHeight;
|
||||
double PR = MediaQuery.of(context).devicePixelRatio;
|
||||
return Stack(
|
||||
children: [
|
||||
Hero(
|
||||
tag: heroTag,
|
||||
child: NetworkImgLayer(
|
||||
// 指定图片尺寸
|
||||
// src: videoItem.pic + '@${(maxWidth * 2).toInt()}w',
|
||||
src: liveItem.cover + '@.webp',
|
||||
type: 'emote',
|
||||
width: maxWidth,
|
||||
@ -79,6 +77,7 @@ class LiveCard extends StatelessWidget {
|
||||
}
|
||||
|
||||
class LiveContent extends StatelessWidget {
|
||||
// ignore: prefer_typing_uninitialized_variables
|
||||
final liveItem;
|
||||
const LiveContent({Key? key, required this.liveItem}) : super(key: key);
|
||||
@override
|
||||
@ -140,19 +139,19 @@ class LiveStat extends StatelessWidget {
|
||||
child: Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
children: [
|
||||
Row(
|
||||
children: [
|
||||
// StatView(
|
||||
// theme: 'white',
|
||||
// view: view,
|
||||
// ),
|
||||
// const SizedBox(width: 8),
|
||||
// StatDanMu(
|
||||
// theme: 'white',
|
||||
// danmu: danmaku,
|
||||
// ),
|
||||
],
|
||||
),
|
||||
// Row(
|
||||
// children: [
|
||||
// StatView(
|
||||
// theme: 'white',
|
||||
// view: view,
|
||||
// ),
|
||||
// const SizedBox(width: 8),
|
||||
// StatDanMu(
|
||||
// theme: 'white',
|
||||
// danmu: danmaku,
|
||||
// ),
|
||||
// ],
|
||||
// ),
|
||||
Text(
|
||||
online.toString(),
|
||||
style: const TextStyle(fontSize: 11, color: Colors.white),
|
||||
|
@ -3,8 +3,8 @@ import 'package:pilipala/common/constants.dart';
|
||||
import 'package:pilipala/common/widgets/network_img_layer.dart';
|
||||
|
||||
class OverlayPop extends StatelessWidget {
|
||||
var videoItem;
|
||||
OverlayPop({super.key, this.videoItem});
|
||||
final dynamic videoItem;
|
||||
const OverlayPop({super.key, this.videoItem});
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
|
@ -1,3 +1,5 @@
|
||||
// ignore_for_file: depend_on_referenced_packages
|
||||
|
||||
import 'dart:math';
|
||||
import 'dart:ui' as ui show Image;
|
||||
|
||||
@ -15,7 +17,8 @@ class PullToRefreshHeader extends StatelessWidget {
|
||||
this.info,
|
||||
this.lastRefreshTime, {
|
||||
this.color,
|
||||
});
|
||||
Key? key,
|
||||
}) : super(key: key);
|
||||
|
||||
final PullToRefreshScrollNotificationInfo? info;
|
||||
final DateTime? lastRefreshTime;
|
||||
@ -23,21 +26,21 @@ class PullToRefreshHeader extends StatelessWidget {
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
final PullToRefreshScrollNotificationInfo? _info = info;
|
||||
if (_info == null) {
|
||||
final PullToRefreshScrollNotificationInfo? infos = info;
|
||||
if (infos == null) {
|
||||
return Container();
|
||||
}
|
||||
String text = '';
|
||||
if (_info.mode == PullToRefreshIndicatorMode.armed) {
|
||||
if (infos.mode == PullToRefreshIndicatorMode.armed) {
|
||||
text = 'Release to refresh';
|
||||
} else if (_info.mode == PullToRefreshIndicatorMode.refresh ||
|
||||
_info.mode == PullToRefreshIndicatorMode.snap) {
|
||||
} else if (infos.mode == PullToRefreshIndicatorMode.refresh ||
|
||||
infos.mode == PullToRefreshIndicatorMode.snap) {
|
||||
text = 'Loading...';
|
||||
} else if (_info.mode == PullToRefreshIndicatorMode.done) {
|
||||
} else if (infos.mode == PullToRefreshIndicatorMode.done) {
|
||||
text = 'Refresh completed.';
|
||||
} else if (_info.mode == PullToRefreshIndicatorMode.drag) {
|
||||
} else if (infos.mode == PullToRefreshIndicatorMode.drag) {
|
||||
text = 'Pull to refresh';
|
||||
} else if (_info.mode == PullToRefreshIndicatorMode.canceled) {
|
||||
} else if (infos.mode == PullToRefreshIndicatorMode.canceled) {
|
||||
text = 'Cancel refresh';
|
||||
}
|
||||
|
||||
@ -67,16 +70,15 @@ class PullToRefreshHeader extends StatelessWidget {
|
||||
Expanded(
|
||||
child: Container(
|
||||
alignment: Alignment.centerRight,
|
||||
child: RefreshImage(top),
|
||||
margin: const EdgeInsets.only(right: 12.0),
|
||||
child: RefreshImage(top, null),
|
||||
),
|
||||
),
|
||||
Column(
|
||||
children: <Widget>[
|
||||
Text(text, style: ts),
|
||||
Text(
|
||||
'Last updated:' +
|
||||
DateFormat('yyyy-MM-dd hh:mm').format(time),
|
||||
'Last updated:${DateFormat('yyyy-MM-dd hh:mm').format(time)}',
|
||||
style: ts.copyWith(fontSize: 14),
|
||||
)
|
||||
],
|
||||
@ -92,7 +94,7 @@ class PullToRefreshHeader extends StatelessWidget {
|
||||
}
|
||||
|
||||
class RefreshImage extends StatelessWidget {
|
||||
const RefreshImage(this.top);
|
||||
const RefreshImage(this.top, Key? key) : super(key: key);
|
||||
|
||||
final double top;
|
||||
|
||||
|
@ -1,4 +1,3 @@
|
||||
import 'package:flutter/cupertino.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:pilipala/utils/utils.dart';
|
||||
|
||||
|
@ -1,4 +1,3 @@
|
||||
import 'package:flutter/cupertino.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:pilipala/utils/utils.dart';
|
||||
|
||||
|
@ -12,11 +12,11 @@ import 'package:pilipala/common/widgets/network_img_layer.dart';
|
||||
// 视频卡片 - 水平布局
|
||||
class VideoCardH extends StatelessWidget {
|
||||
// ignore: prefer_typing_uninitialized_variables
|
||||
var videoItem;
|
||||
Function()? longPress;
|
||||
Function()? longPressEnd;
|
||||
final videoItem;
|
||||
final Function()? longPress;
|
||||
final Function()? longPressEnd;
|
||||
|
||||
VideoCardH({
|
||||
const VideoCardH({
|
||||
Key? key,
|
||||
required this.videoItem,
|
||||
this.longPress,
|
||||
@ -71,21 +71,16 @@ class VideoCardH extends StatelessWidget {
|
||||
builder: (context, boxConstraints) {
|
||||
double maxWidth = boxConstraints.maxWidth;
|
||||
double maxHeight = boxConstraints.maxHeight;
|
||||
double PR =
|
||||
MediaQuery.of(context).devicePixelRatio;
|
||||
return Stack(
|
||||
children: [
|
||||
Hero(
|
||||
tag: heroTag,
|
||||
child: NetworkImgLayer(
|
||||
// src: videoItem['pic'] +
|
||||
// '@${(maxWidth * 2).toInt()}w',
|
||||
src: videoItem.pic + '@.webp',
|
||||
width: maxWidth,
|
||||
height: maxHeight,
|
||||
),
|
||||
),
|
||||
// Image.network( videoItem['pic'], width: double.infinity, height: double.infinity,),
|
||||
pBadge(Utils.timeFormat(videoItem.duration!),
|
||||
context, null, 6.0, 6.0, null,
|
||||
type: 'gray'),
|
||||
@ -119,6 +114,7 @@ class VideoCardH extends StatelessWidget {
|
||||
}
|
||||
|
||||
class VideoContent extends StatelessWidget {
|
||||
// ignore: prefer_typing_uninitialized_variables
|
||||
final videoItem;
|
||||
const VideoContent({super.key, required this.videoItem});
|
||||
|
||||
@ -186,7 +182,7 @@ class VideoContent extends StatelessWidget {
|
||||
Text(
|
||||
videoItem.owner.name,
|
||||
style: TextStyle(
|
||||
fontSize: Theme.of(context).textTheme.labelSmall!.fontSize,
|
||||
fontSize: Theme.of(context).textTheme.labelMedium!.fontSize,
|
||||
color: Theme.of(context).colorScheme.outline,
|
||||
),
|
||||
),
|
||||
|
@ -6,16 +6,16 @@ import 'package:pilipala/common/widgets/stat/view.dart';
|
||||
import 'package:pilipala/pages/rcmd/index.dart';
|
||||
import 'package:pilipala/utils/id_utils.dart';
|
||||
import 'package:pilipala/utils/utils.dart';
|
||||
import 'package:pilipala/pages/home/controller.dart';
|
||||
import 'package:pilipala/common/widgets/network_img_layer.dart';
|
||||
|
||||
// 视频卡片 - 垂直布局
|
||||
class VideoCardV extends StatelessWidget {
|
||||
var videoItem;
|
||||
Function()? longPress;
|
||||
Function()? longPressEnd;
|
||||
// ignore: prefer_typing_uninitialized_variables
|
||||
final videoItem;
|
||||
final Function()? longPress;
|
||||
final Function()? longPressEnd;
|
||||
|
||||
VideoCardV({
|
||||
const VideoCardV({
|
||||
Key? key,
|
||||
required this.videoItem,
|
||||
this.longPress,
|
||||
@ -67,14 +67,11 @@ class VideoCardV extends StatelessWidget {
|
||||
child: LayoutBuilder(builder: (context, boxConstraints) {
|
||||
double maxWidth = boxConstraints.maxWidth;
|
||||
double maxHeight = boxConstraints.maxHeight;
|
||||
double PR = MediaQuery.of(context).devicePixelRatio;
|
||||
return Stack(
|
||||
children: [
|
||||
Hero(
|
||||
tag: heroTag,
|
||||
child: NetworkImgLayer(
|
||||
// 指定图片尺寸
|
||||
// src: videoItem.pic + '@${(maxWidth * 2).toInt()}w',
|
||||
src: videoItem.pic + '@.webp',
|
||||
width: maxWidth,
|
||||
height: maxHeight,
|
||||
@ -111,6 +108,7 @@ class VideoCardV extends StatelessWidget {
|
||||
}
|
||||
|
||||
class VideoContent extends StatelessWidget {
|
||||
// ignore: prefer_typing_uninitialized_variables
|
||||
final videoItem;
|
||||
const VideoContent({Key? key, required this.videoItem}) : super(key: key);
|
||||
@override
|
||||
|
@ -151,7 +151,7 @@ class Request {
|
||||
cancelToken: cancelToken,
|
||||
);
|
||||
return response;
|
||||
} on DioError catch (e) {
|
||||
} on DioException catch (e) {
|
||||
print('get error: $e');
|
||||
return Future.error(await ApiInterceptor.dioError(e));
|
||||
}
|
||||
@ -173,7 +173,7 @@ class Request {
|
||||
);
|
||||
print('post success: ${response.data}');
|
||||
return response;
|
||||
} on DioError catch (e) {
|
||||
} on DioException catch (e) {
|
||||
print('post error: $e');
|
||||
return Future.error(await ApiInterceptor.dioError(e));
|
||||
}
|
||||
@ -193,7 +193,7 @@ class Request {
|
||||
print('downloadFile success: ${response.data}');
|
||||
|
||||
return response.data;
|
||||
} on DioError catch (e) {
|
||||
} on DioException catch (e) {
|
||||
print('downloadFile error: $e');
|
||||
return Future.error(ApiInterceptor.dioError(e));
|
||||
}
|
||||
|
@ -1,12 +1,12 @@
|
||||
import 'package:dio/dio.dart';
|
||||
import 'package:connectivity_plus/connectivity_plus.dart';
|
||||
import 'package:flutter_smart_dialog/flutter_smart_dialog.dart';
|
||||
import 'package:get/get.dart' hide Response;
|
||||
// import 'package:get/get.dart' hide Response;
|
||||
|
||||
class ApiInterceptor extends Interceptor {
|
||||
@override
|
||||
void onRequest(RequestOptions options, RequestInterceptorHandler handler) {
|
||||
print("请求之前");
|
||||
// print("请求之前");
|
||||
// 在请求之前添加头部或认证信息
|
||||
// options.headers['Authorization'] = 'Bearer token';
|
||||
// options.headers['Content-Type'] = 'application/json';
|
||||
@ -19,30 +19,30 @@ class ApiInterceptor extends Interceptor {
|
||||
}
|
||||
|
||||
@override
|
||||
void onError(DioError err, ErrorInterceptorHandler handler) async {
|
||||
void onError(DioException err, ErrorInterceptorHandler handler) async {
|
||||
// 处理网络请求错误
|
||||
// handler.next(err);
|
||||
SmartDialog.showToast(await dioError(err));
|
||||
super.onError(err, handler);
|
||||
}
|
||||
|
||||
static Future dioError(DioError error) async {
|
||||
static Future dioError(DioException error) async {
|
||||
switch (error.type) {
|
||||
case DioErrorType.badCertificate:
|
||||
case DioExceptionType.badCertificate:
|
||||
return '证书有误!';
|
||||
case DioErrorType.badResponse:
|
||||
case DioExceptionType.badResponse:
|
||||
return '服务器异常,请稍后重试!';
|
||||
case DioErrorType.cancel:
|
||||
case DioExceptionType.cancel:
|
||||
return "请求已被取消,请重新请求";
|
||||
case DioErrorType.connectionError:
|
||||
case DioExceptionType.connectionError:
|
||||
return '连接错误,请检查网络设置';
|
||||
case DioErrorType.connectionTimeout:
|
||||
case DioExceptionType.connectionTimeout:
|
||||
return "网络连接超时,请检查网络设置";
|
||||
case DioErrorType.receiveTimeout:
|
||||
case DioExceptionType.receiveTimeout:
|
||||
return "响应超时,请稍后重试!";
|
||||
case DioErrorType.sendTimeout:
|
||||
case DioExceptionType.sendTimeout:
|
||||
return "发送请求超时,请检查网络设置";
|
||||
case DioErrorType.unknown:
|
||||
case DioExceptionType.unknown:
|
||||
var res = await checkConect();
|
||||
return res + " \n 网络异常,请稍后重试!";
|
||||
default:
|
||||
|
@ -1,5 +1,3 @@
|
||||
import 'dart:developer';
|
||||
|
||||
import 'package:pilipala/http/index.dart';
|
||||
import 'package:pilipala/models/bangumi/info.dart';
|
||||
import 'package:pilipala/models/common/search_type.dart';
|
||||
@ -57,7 +55,7 @@ class SearchHttp {
|
||||
'page': page
|
||||
});
|
||||
if (res.data['code'] == 0 && res.data['data']['numPages'] > 0) {
|
||||
var data;
|
||||
Object data;
|
||||
switch (searchType) {
|
||||
case SearchType.video:
|
||||
data = SearchVideoModel.fromJson(res.data['data']);
|
||||
|
@ -1,5 +1,3 @@
|
||||
import 'dart:developer';
|
||||
|
||||
import 'package:pilipala/http/api.dart';
|
||||
import 'package:pilipala/http/init.dart';
|
||||
import 'package:pilipala/models/model_hot_video_item.dart';
|
||||
|
@ -125,7 +125,6 @@ class VideoHttp {
|
||||
return {'status': false, 'data': []};
|
||||
}
|
||||
} catch (err) {
|
||||
print('🐯:$err');
|
||||
return {'status': false, 'data': [], 'msg': err};
|
||||
}
|
||||
}
|
||||
@ -338,7 +337,7 @@ class VideoHttp {
|
||||
|
||||
// 视频播放进度
|
||||
static Future heartBeat({bvid, cid, progress, realtime}) async {
|
||||
var res = await Request().post(Api.heartBeat, queryParameters: {
|
||||
await Request().post(Api.heartBeat, queryParameters: {
|
||||
// 'aid': aid,
|
||||
'bvid': bvid,
|
||||
'cid': cid,
|
||||
|
@ -193,7 +193,7 @@ class SearchUserItemModel {
|
||||
usign = json['usign'];
|
||||
fans = json['fans'];
|
||||
videos = json['videos'];
|
||||
upic = 'https:' + json['upic'];
|
||||
upic = 'https:${json['upic']}';
|
||||
faceNft = json['face_nft'];
|
||||
faceNftType = json['face_nft_type'];
|
||||
verifyInfo = json['verify_info'];
|
||||
|
@ -31,7 +31,7 @@ class SearchSuggestItem {
|
||||
SearchSuggestItem.fromJson(Map<String, dynamic> json, String inputTerm) {
|
||||
value = json['value'];
|
||||
term = json['term'];
|
||||
String reg = '<em class=\"suggest_high_light\">$inputTerm</em>';
|
||||
String reg = '<em class="suggest_high_light">$inputTerm</em>';
|
||||
try {
|
||||
if (json['name'].indexOf(inputTerm) != -1) {
|
||||
String str = json['name'].replaceAll(reg, '^');
|
||||
|
@ -1,5 +1,3 @@
|
||||
import 'package:get/get.dart';
|
||||
|
||||
class ReplyMember {
|
||||
ReplyMember({
|
||||
this.mid,
|
||||
|
@ -1,3 +1,5 @@
|
||||
// ignore_for_file: avoid_print
|
||||
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_smart_dialog/flutter_smart_dialog.dart';
|
||||
import 'package:get/get.dart';
|
||||
@ -7,7 +9,6 @@ import 'package:pilipala/models/common/dynamics_type.dart';
|
||||
import 'package:pilipala/models/dynamics/result.dart';
|
||||
import 'package:pilipala/models/dynamics/up.dart';
|
||||
import 'package:pilipala/models/live/item.dart';
|
||||
import 'package:pilipala/utils/utils.dart';
|
||||
|
||||
class DynamicsController extends GetxController {
|
||||
int page = 1;
|
||||
|
@ -1,14 +1,13 @@
|
||||
import 'package:get/get.dart';
|
||||
import 'package:pilipala/http/reply.dart';
|
||||
import 'package:pilipala/models/common/reply_sort_type.dart';
|
||||
import 'package:pilipala/models/video/reply/data.dart';
|
||||
import 'package:pilipala/models/video/reply/item.dart';
|
||||
|
||||
class DynamicDetailController extends GetxController {
|
||||
DynamicDetailController(this.oid, this.type);
|
||||
int? oid;
|
||||
int? type;
|
||||
var item;
|
||||
dynamic item;
|
||||
int? floor;
|
||||
int currentPage = 0;
|
||||
bool isLoadingMore = false;
|
||||
|
@ -1,13 +1,11 @@
|
||||
import 'package:custom_sliding_segmented_control/custom_sliding_segmented_control.dart';
|
||||
import 'package:flutter/cupertino.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_smart_dialog/flutter_smart_dialog.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'package:hive/hive.dart';
|
||||
import 'package:pilipala/common/skeleton/dynamic_card.dart';
|
||||
import 'package:pilipala/common/widgets/http_error.dart';
|
||||
import 'package:pilipala/common/widgets/network_img_layer.dart';
|
||||
import 'package:pilipala/models/common/dynamics_type.dart';
|
||||
import 'package:pilipala/models/dynamics/result.dart';
|
||||
import 'package:pilipala/pages/mine/index.dart';
|
||||
import 'package:pilipala/utils/storage.dart';
|
||||
@ -55,6 +53,7 @@ class _DynamicsPageState extends State<DynamicsPage>
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
super.build(context);
|
||||
return Scaffold(
|
||||
appBar: AppBar(
|
||||
elevation: 0,
|
||||
|
@ -8,11 +8,12 @@ import 'package:pilipala/models/dynamics/result.dart';
|
||||
import 'package:pilipala/pages/dynamics/index.dart';
|
||||
|
||||
class ActionPanel extends StatefulWidget {
|
||||
ActionPanel({
|
||||
const ActionPanel({
|
||||
super.key,
|
||||
this.item,
|
||||
});
|
||||
var item;
|
||||
// ignore: prefer_typing_uninitialized_variables
|
||||
final item;
|
||||
|
||||
@override
|
||||
State<ActionPanel> createState() => _ActionPanelState();
|
||||
|
@ -153,12 +153,12 @@ Widget addWidget(item, context, type, {floor = 1}) {
|
||||
),
|
||||
));
|
||||
case 'ADDITIONAL_TYPE_MATCH':
|
||||
return SizedBox();
|
||||
return const SizedBox();
|
||||
case 'ADDITIONAL_TYPE_COMMON':
|
||||
return SizedBox();
|
||||
return const SizedBox();
|
||||
case 'ADDITIONAL_TYPE_VOTE':
|
||||
return SizedBox();
|
||||
return const SizedBox();
|
||||
default:
|
||||
return Text('11');
|
||||
return const Text('11');
|
||||
}
|
||||
}
|
||||
|
@ -7,8 +7,8 @@ import 'content_panel.dart';
|
||||
import 'forward_panel.dart';
|
||||
|
||||
class DynamicPanel extends StatelessWidget {
|
||||
var item;
|
||||
String? source;
|
||||
final dynamic item;
|
||||
final String? source;
|
||||
DynamicPanel({this.item, this.source, Key? key}) : super(key: key);
|
||||
final DynamicsController _dynamicsController = Get.put(DynamicsController());
|
||||
|
||||
|
@ -1,6 +1,5 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'package:pilipala/common/constants.dart';
|
||||
import 'package:pilipala/common/widgets/network_img_layer.dart';
|
||||
import 'package:pilipala/utils/utils.dart';
|
||||
|
||||
|
@ -90,7 +90,7 @@ InlineSpan richNode(item, context) {
|
||||
'/webview',
|
||||
parameters: {
|
||||
'url':
|
||||
'https://t.bilibili.com/vote/h5/index/#/result?vote_id=${i.rid}&dynamic_id=${dynamicId}&isWeb=1',
|
||||
'https://t.bilibili.com/vote/h5/index/#/result?vote_id=${i.rid}&dynamic_id=$dynamicId&isWeb=1',
|
||||
'type': 'vote',
|
||||
'pageTitle': '投票'
|
||||
},
|
||||
|
@ -1,5 +1,4 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_smart_dialog/flutter_smart_dialog.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'package:hive/hive.dart';
|
||||
import 'package:pilipala/common/widgets/network_img_layer.dart';
|
||||
@ -10,8 +9,8 @@ import 'package:pilipala/utils/storage.dart';
|
||||
import 'package:pilipala/utils/utils.dart';
|
||||
|
||||
class UpPanel extends StatefulWidget {
|
||||
FollowUpModel? upData;
|
||||
UpPanel(this.upData, {Key? key}) : super(key: key);
|
||||
final FollowUpModel? upData;
|
||||
const UpPanel(this.upData, {Key? key}) : super(key: key);
|
||||
|
||||
@override
|
||||
State<UpPanel> createState() => _UpPanelState();
|
||||
@ -168,7 +167,9 @@ class _UpPanelState extends State<UpPanel> {
|
||||
smallSize: 8,
|
||||
label: data.type == 'live' ? const Text('Live') : null,
|
||||
textColor: Theme.of(context).colorScheme.onSecondaryContainer,
|
||||
alignment: AlignmentDirectional.bottomCenter,
|
||||
alignment: data.type == 'live'
|
||||
? AlignmentDirectional.topCenter
|
||||
: AlignmentDirectional.topEnd,
|
||||
padding: const EdgeInsets.only(left: 6, right: 6),
|
||||
isLabelVisible: data.type == 'live' ||
|
||||
(data.type == 'up' && (data.hasUpdate ?? false)),
|
||||
|
@ -44,7 +44,11 @@ class _FansPageState extends State<FansPage> {
|
||||
elevation: 0,
|
||||
scrolledUnderElevation: 0,
|
||||
centerTitle: false,
|
||||
title: const Text('我的粉丝'),
|
||||
titleSpacing: 0,
|
||||
title: Text(
|
||||
'我的粉丝',
|
||||
style: Theme.of(context).textTheme.titleMedium,
|
||||
),
|
||||
),
|
||||
body: RefreshIndicator(
|
||||
onRefresh: () async => await _fansController.queryFans('init'),
|
||||
@ -57,7 +61,7 @@ class _FansPageState extends State<FansPage> {
|
||||
List<FansItemModel> list = _fansController.fansList;
|
||||
return Obx(
|
||||
() => list.length == 1
|
||||
? SizedBox()
|
||||
? const SizedBox()
|
||||
: ListView.builder(
|
||||
controller: scrollController,
|
||||
itemCount: list.length,
|
||||
@ -74,7 +78,7 @@ class _FansPageState extends State<FansPage> {
|
||||
}
|
||||
} else {
|
||||
// 骨架屏
|
||||
return SizedBox();
|
||||
return const SizedBox();
|
||||
}
|
||||
},
|
||||
),
|
||||
|
@ -5,8 +5,9 @@ import 'package:pilipala/common/widgets/network_img_layer.dart';
|
||||
import 'package:pilipala/utils/utils.dart';
|
||||
|
||||
class FavItem extends StatelessWidget {
|
||||
var favFolderItem;
|
||||
FavItem({super.key, required this.favFolderItem});
|
||||
// ignore: prefer_typing_uninitialized_variables
|
||||
final favFolderItem;
|
||||
const FavItem({super.key, required this.favFolderItem});
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
@ -38,7 +39,6 @@ class FavItem extends StatelessWidget {
|
||||
builder: (context, boxConstraints) {
|
||||
double maxWidth = boxConstraints.maxWidth;
|
||||
double maxHeight = boxConstraints.maxHeight;
|
||||
double PR = MediaQuery.of(context).devicePixelRatio;
|
||||
return Hero(
|
||||
tag: heroTag,
|
||||
child: NetworkImgLayer(
|
||||
@ -62,7 +62,7 @@ class FavItem extends StatelessWidget {
|
||||
}
|
||||
|
||||
class VideoContent extends StatelessWidget {
|
||||
final favFolderItem;
|
||||
final dynamic favFolderItem;
|
||||
const VideoContent({super.key, required this.favFolderItem});
|
||||
|
||||
@override
|
||||
|
@ -11,7 +11,7 @@ import '../controller.dart';
|
||||
|
||||
// 收藏视频卡片 - 水平布局
|
||||
class FavVideoCardH extends StatelessWidget {
|
||||
var videoItem;
|
||||
final dynamic videoItem;
|
||||
final FavDetailController _favDetailController =
|
||||
Get.put(FavDetailController());
|
||||
|
||||
@ -28,9 +28,9 @@ class FavVideoCardH extends StatelessWidget {
|
||||
decoration: BoxDecoration(
|
||||
color: Theme.of(context).colorScheme.errorContainer,
|
||||
),
|
||||
child: Row(
|
||||
child: const Row(
|
||||
mainAxisAlignment: MainAxisAlignment.center,
|
||||
children: const [
|
||||
children: [
|
||||
Icon(Icons.clear_all_rounded),
|
||||
SizedBox(width: 6),
|
||||
Text('取消收藏')
|
||||
@ -51,7 +51,8 @@ class FavVideoCardH extends StatelessWidget {
|
||||
child: Column(
|
||||
children: [
|
||||
Padding(
|
||||
padding: const EdgeInsets.fromLTRB(12, 5, 12, 5),
|
||||
padding: const EdgeInsets.fromLTRB(
|
||||
StyleString.safeSpace, 5, StyleString.safeSpace, 5),
|
||||
child: LayoutBuilder(
|
||||
builder: (context, boxConstraints) {
|
||||
double width =
|
||||
@ -68,21 +69,16 @@ class FavVideoCardH extends StatelessWidget {
|
||||
builder: (context, boxConstraints) {
|
||||
double maxWidth = boxConstraints.maxWidth;
|
||||
double maxHeight = boxConstraints.maxHeight;
|
||||
double PR =
|
||||
MediaQuery.of(context).devicePixelRatio;
|
||||
return Stack(
|
||||
children: [
|
||||
Hero(
|
||||
tag: heroTag,
|
||||
child: NetworkImgLayer(
|
||||
// src: videoItem['pic'] +
|
||||
// '@${(maxWidth * 2).toInt()}w',
|
||||
src: videoItem.pic + '@.webp',
|
||||
width: maxWidth,
|
||||
height: maxHeight,
|
||||
),
|
||||
),
|
||||
// Image.network( videoItem['pic'], width: double.infinity, height: double.infinity,),
|
||||
Positioned(
|
||||
right: 4,
|
||||
bottom: 4,
|
||||
@ -121,7 +117,7 @@ class FavVideoCardH extends StatelessWidget {
|
||||
}
|
||||
|
||||
class VideoContent extends StatelessWidget {
|
||||
final videoItem;
|
||||
final dynamic videoItem;
|
||||
const VideoContent({super.key, required this.videoItem});
|
||||
|
||||
@override
|
||||
@ -147,10 +143,11 @@ class VideoContent extends StatelessWidget {
|
||||
Text(
|
||||
videoItem.owner.name,
|
||||
style: TextStyle(
|
||||
fontSize: Theme.of(context).textTheme.labelSmall!.fontSize,
|
||||
fontSize: Theme.of(context).textTheme.labelMedium!.fontSize,
|
||||
color: Theme.of(context).colorScheme.outline,
|
||||
),
|
||||
),
|
||||
const SizedBox(height: 2),
|
||||
Row(
|
||||
children: [
|
||||
StatView(
|
||||
|
@ -62,7 +62,7 @@ class _FollowPageState extends State<FollowPage> {
|
||||
List<FollowItemModel> list = _followController.followList;
|
||||
return Obx(
|
||||
() => list.length == 1
|
||||
? SizedBox()
|
||||
? const SizedBox()
|
||||
: ListView.builder(
|
||||
controller: scrollController,
|
||||
itemCount: list.length,
|
||||
@ -79,7 +79,7 @@ class _FollowPageState extends State<FollowPage> {
|
||||
}
|
||||
} else {
|
||||
// 骨架屏
|
||||
return SizedBox();
|
||||
return const SizedBox();
|
||||
}
|
||||
},
|
||||
)),
|
||||
|
@ -10,8 +10,8 @@ import 'package:pilipala/utils/id_utils.dart';
|
||||
import 'package:pilipala/utils/utils.dart';
|
||||
|
||||
class HistoryItem extends StatelessWidget {
|
||||
var videoItem;
|
||||
HistoryItem({super.key, required this.videoItem});
|
||||
final dynamic videoItem;
|
||||
const HistoryItem({super.key, required this.videoItem});
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
@ -76,14 +76,11 @@ class HistoryItem extends StatelessWidget {
|
||||
builder: (context, boxConstraints) {
|
||||
double maxWidth = boxConstraints.maxWidth;
|
||||
double maxHeight = boxConstraints.maxHeight;
|
||||
double PR = MediaQuery.of(context).devicePixelRatio;
|
||||
return Stack(
|
||||
children: [
|
||||
Hero(
|
||||
tag: heroTag,
|
||||
child: NetworkImgLayer(
|
||||
// src: videoItem['pic'] +
|
||||
// '@${(maxWidth * 2).toInt()}w',
|
||||
src: (videoItem.cover != ''
|
||||
? videoItem.cover
|
||||
: videoItem.covers.first) +
|
||||
@ -137,7 +134,7 @@ class HistoryItem extends StatelessWidget {
|
||||
}
|
||||
|
||||
class VideoContent extends StatelessWidget {
|
||||
final videoItem;
|
||||
final dynamic videoItem;
|
||||
const VideoContent({super.key, required this.videoItem});
|
||||
|
||||
@override
|
||||
@ -164,7 +161,7 @@ class VideoContent extends StatelessWidget {
|
||||
videoItem.showTitle,
|
||||
textAlign: TextAlign.start,
|
||||
style: TextStyle(
|
||||
fontSize: Theme.of(context).textTheme.titleSmall!.fontSize,
|
||||
fontSize: Theme.of(context).textTheme.labelMedium!.fontSize,
|
||||
fontWeight: FontWeight.w400,
|
||||
color: Theme.of(context).colorScheme.outline),
|
||||
maxLines: 2,
|
||||
@ -176,7 +173,7 @@ class VideoContent extends StatelessWidget {
|
||||
Text(
|
||||
videoItem.authorName,
|
||||
style: TextStyle(
|
||||
fontSize: Theme.of(context).textTheme.labelSmall!.fontSize,
|
||||
fontSize: Theme.of(context).textTheme.labelMedium!.fontSize,
|
||||
color: Theme.of(context).colorScheme.outline,
|
||||
),
|
||||
),
|
||||
@ -187,7 +184,8 @@ class VideoContent extends StatelessWidget {
|
||||
Text(
|
||||
Utils.dateFormat(videoItem.viewAt!),
|
||||
style: TextStyle(
|
||||
fontSize: 11,
|
||||
fontSize:
|
||||
Theme.of(context).textTheme.labelMedium!.fontSize,
|
||||
color: Theme.of(context).colorScheme.outline),
|
||||
)
|
||||
],
|
||||
|
@ -1,7 +1,5 @@
|
||||
import 'dart:io';
|
||||
import 'package:flutter/cupertino.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:font_awesome_flutter/font_awesome_flutter.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'package:hive/hive.dart';
|
||||
import 'package:pilipala/common/widgets/network_img_layer.dart';
|
||||
|
@ -86,7 +86,7 @@ class _HotPageState extends State<HotPage> with AutomaticKeepAliveClientMixin {
|
||||
return SliverList(
|
||||
delegate: SliverChildBuilderDelegate((context, index) {
|
||||
return const VideoCardHSkeleton();
|
||||
}, childCount: 5),
|
||||
}, childCount: 10),
|
||||
);
|
||||
}
|
||||
},
|
||||
|
@ -19,9 +19,6 @@ class LivePage extends StatefulWidget {
|
||||
class _LivePageState extends State<LivePage> {
|
||||
final LiveController _liveController = Get.put(LiveController());
|
||||
|
||||
@override
|
||||
bool get wantKeepAlive => true;
|
||||
|
||||
@override
|
||||
void initState() {
|
||||
super.initState();
|
||||
|
@ -8,11 +8,11 @@ import 'package:pilipala/common/widgets/network_img_layer.dart';
|
||||
|
||||
// 视频卡片 - 垂直布局
|
||||
class LiveCardV extends StatelessWidget {
|
||||
LiveItemModel liveItem;
|
||||
Function()? longPress;
|
||||
Function()? longPressEnd;
|
||||
final LiveItemModel liveItem;
|
||||
final Function()? longPress;
|
||||
final Function()? longPressEnd;
|
||||
|
||||
LiveCardV({
|
||||
const LiveCardV({
|
||||
Key? key,
|
||||
required this.liveItem,
|
||||
this.longPress,
|
||||
@ -97,7 +97,7 @@ class LiveCardV extends StatelessWidget {
|
||||
}
|
||||
|
||||
class LiveContent extends StatelessWidget {
|
||||
final liveItem;
|
||||
final dynamic liveItem;
|
||||
const LiveContent({Key? key, required this.liveItem}) : super(key: key);
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
@ -123,7 +123,7 @@ class LiveContent extends StatelessWidget {
|
||||
const SizedBox(height: 4),
|
||||
Row(
|
||||
children: [
|
||||
UpTag(),
|
||||
const UpTag(),
|
||||
Expanded(
|
||||
child: Text(
|
||||
liveItem.uname,
|
||||
|
@ -8,7 +8,7 @@ import 'package:pilipala/models/live/room_info.dart';
|
||||
class LiveRoomController extends GetxController {
|
||||
String cover = '';
|
||||
late int roomId;
|
||||
var liveItem;
|
||||
dynamic liveItem;
|
||||
late String heroTag;
|
||||
double volume = 0.0;
|
||||
// 静音状态
|
||||
@ -75,6 +75,5 @@ class LiveRoomController extends GetxController {
|
||||
volumeOff.value = true;
|
||||
meeduPlayerController.setVolume(0);
|
||||
}
|
||||
print('🌹:${volumeOff.value}');
|
||||
}
|
||||
}
|
||||
|
@ -1,9 +1,6 @@
|
||||
import 'dart:async';
|
||||
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_meedu_media_kit/meedu_player.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'dart:ui';
|
||||
import 'package:pilipala/common/widgets/network_img_layer.dart';
|
||||
|
||||
import 'controller.dart';
|
||||
@ -18,7 +15,6 @@ class LiveRoomPage extends StatefulWidget {
|
||||
class _LiveRoomPageState extends State<LiveRoomPage> {
|
||||
final LiveRoomController _liveRoomController = Get.put(LiveRoomController());
|
||||
MeeduPlayerController? _meeduPlayerController;
|
||||
StreamSubscription? _playerEventSubs;
|
||||
|
||||
bool isShowCover = true;
|
||||
bool isPlay = true;
|
||||
@ -27,7 +23,7 @@ class _LiveRoomPageState extends State<LiveRoomPage> {
|
||||
void initState() {
|
||||
super.initState();
|
||||
_meeduPlayerController = _liveRoomController.meeduPlayerController;
|
||||
_playerEventSubs = _meeduPlayerController!.onPlayerStatusChanged.listen(
|
||||
_meeduPlayerController!.onPlayerStatusChanged.listen(
|
||||
(PlayerStatus status) {
|
||||
if (status == PlayerStatus.playing) {
|
||||
isShowCover = false;
|
||||
@ -45,7 +41,6 @@ class _LiveRoomPageState extends State<LiveRoomPage> {
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
final double statusBarHeight = MediaQuery.of(context).padding.top;
|
||||
final videoHeight = MediaQuery.of(context).size.width * 9 / 16;
|
||||
|
||||
return Scaffold(
|
||||
@ -97,8 +92,8 @@ class _LiveRoomPageState extends State<LiveRoomPage> {
|
||||
aspectRatio: 16 / 9,
|
||||
child: MeeduVideoPlayer(
|
||||
header: (BuildContext context,
|
||||
MeeduPlayerController _meeduPlayerController,
|
||||
Responsive) {
|
||||
MeeduPlayerController meeduPlayerController,
|
||||
Responsive responsive) {
|
||||
return AppBar(
|
||||
backgroundColor: Colors.transparent,
|
||||
primary: false,
|
||||
@ -115,7 +110,7 @@ class _LiveRoomPageState extends State<LiveRoomPage> {
|
||||
height: 38,
|
||||
child: IconButton(
|
||||
onPressed: () =>
|
||||
_meeduPlayerController.enterPip(context),
|
||||
meeduPlayerController.enterPip(context),
|
||||
icon: const Icon(
|
||||
Icons.branding_watermark_outlined,
|
||||
size: 19,
|
||||
|
@ -1,19 +1,12 @@
|
||||
import 'package:flutter/cupertino.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:hive/hive.dart';
|
||||
import 'package:pilipala/common/widgets/network_img_layer.dart';
|
||||
import 'package:pilipala/pages/dynamics/index.dart';
|
||||
import 'package:pilipala/pages/home/view.dart';
|
||||
import 'package:pilipala/pages/hot/view.dart';
|
||||
import 'package:pilipala/pages/media/index.dart';
|
||||
import 'package:pilipala/pages/mine/index.dart';
|
||||
import 'package:pilipala/utils/storage.dart';
|
||||
|
||||
class MainController extends GetxController {
|
||||
List<Widget> pages = <Widget>[
|
||||
const HomePage(),
|
||||
// const HotPage(),
|
||||
const DynamicsPage(),
|
||||
const MediaPage(),
|
||||
];
|
||||
@ -25,13 +18,6 @@ class MainController extends GetxController {
|
||||
),
|
||||
'label': "推荐",
|
||||
},
|
||||
// {
|
||||
// 'icon': const Icon(
|
||||
// Icons.eco,
|
||||
// size: 20,
|
||||
// ),
|
||||
// 'label': "热门",
|
||||
// },
|
||||
{
|
||||
'icon': const Icon(
|
||||
Icons.bolt,
|
||||
|
@ -155,7 +155,7 @@ class MediaPage extends StatelessWidget {
|
||||
}
|
||||
} else {
|
||||
// 骨架屏
|
||||
return SizedBox();
|
||||
return const SizedBox();
|
||||
}
|
||||
}),
|
||||
),
|
||||
@ -165,9 +165,9 @@ class MediaPage extends StatelessWidget {
|
||||
}
|
||||
|
||||
class FavFolderItem extends StatelessWidget {
|
||||
FavFolderItem({super.key, this.item, this.index});
|
||||
FavFolderItemData? item;
|
||||
int? index;
|
||||
const FavFolderItem({super.key, this.item, this.index});
|
||||
final FavFolderItemData? item;
|
||||
final int? index;
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
String heroTag = Utils.makeHeroTag(item!.fid);
|
||||
|
@ -24,6 +24,7 @@ class _ArchivePanelState extends State<ArchivePanel>
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
super.build(context);
|
||||
return PullToRefreshNotification(
|
||||
onRefresh: () async {
|
||||
await Future.delayed(const Duration(seconds: 1));
|
||||
|
@ -7,7 +7,6 @@ import 'package:pilipala/http/video.dart';
|
||||
import 'package:pilipala/models/member/archive.dart';
|
||||
import 'package:pilipala/models/member/info.dart';
|
||||
import 'package:pilipala/utils/storage.dart';
|
||||
import 'package:pilipala/utils/wbi_sign.dart';
|
||||
|
||||
class MemberController extends GetxController {
|
||||
late int mid;
|
||||
@ -48,13 +47,13 @@ class MemberController extends GetxController {
|
||||
return res;
|
||||
}
|
||||
|
||||
Future getMemberCardInfo() async {
|
||||
var res = await MemberHttp.memberCardInfo(mid: mid);
|
||||
if (res['status']) {
|
||||
print(userStat);
|
||||
}
|
||||
return res;
|
||||
}
|
||||
// Future getMemberCardInfo() async {
|
||||
// var res = await MemberHttp.memberCardInfo(mid: mid);
|
||||
// if (res['status']) {
|
||||
// print(userStat);
|
||||
// }
|
||||
// return res;
|
||||
// }
|
||||
|
||||
// 关注/取关up
|
||||
Future actionRelationMod() async {
|
||||
|
@ -2,12 +2,8 @@ import 'package:extended_nested_scroll_view/extended_nested_scroll_view.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:font_awesome_flutter/font_awesome_flutter.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'package:loading_more_list/loading_more_list.dart';
|
||||
import 'package:pilipala/common/widgets/network_img_layer.dart';
|
||||
import 'package:pilipala/models/live/item.dart';
|
||||
import 'package:pilipala/pages/member/archive/view.dart';
|
||||
import 'package:pilipala/pages/member/index.dart';
|
||||
import 'package:pilipala/utils/utils.dart';
|
||||
|
||||
import 'widgets/profile.dart';
|
||||
|
||||
@ -231,7 +227,7 @@ class _MemberPageState extends State<MemberPage>
|
||||
),
|
||||
);
|
||||
} else {
|
||||
return SizedBox();
|
||||
return const SizedBox();
|
||||
}
|
||||
} else {
|
||||
// 骨架屏
|
||||
|
@ -1,3 +1,5 @@
|
||||
// ignore_for_file: no_leading_underscores_for_local_identifiers
|
||||
|
||||
import 'package:flutter/cupertino.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:get/get.dart';
|
||||
@ -321,11 +323,11 @@ class MinePage extends StatelessWidget {
|
||||
}
|
||||
|
||||
class ActionItem extends StatelessWidget {
|
||||
Icon? icon;
|
||||
Function? onTap;
|
||||
String? text;
|
||||
final Icon? icon;
|
||||
final Function? onTap;
|
||||
final String? text;
|
||||
|
||||
ActionItem({
|
||||
const ActionItem({
|
||||
Key? key,
|
||||
this.icon,
|
||||
this.onTap,
|
||||
|
@ -7,7 +7,6 @@ import 'package:dio/dio.dart';
|
||||
import 'package:path_provider/path_provider.dart';
|
||||
import 'package:permission_handler/permission_handler.dart';
|
||||
import 'package:image_gallery_saver/image_gallery_saver.dart';
|
||||
import 'package:pilipala/utils/utils.dart';
|
||||
import 'package:share_plus/share_plus.dart';
|
||||
|
||||
class PreviewController extends GetxController {
|
||||
@ -36,10 +35,8 @@ class PreviewController extends GetxController {
|
||||
// Permission.photos
|
||||
].request();
|
||||
|
||||
final info = statuses[Permission.storage].toString();
|
||||
statuses[Permission.storage].toString();
|
||||
// final photosInfo = statuses[Permission.photos].toString();
|
||||
|
||||
print('授权状态:$info');
|
||||
}
|
||||
|
||||
// 图片保存
|
||||
@ -52,6 +49,7 @@ class PreviewController extends GetxController {
|
||||
name: "pic_vvex${DateTime.now().toString().split('-').join()}");
|
||||
if (result != null) {
|
||||
if (result['isSuccess']) {
|
||||
// ignore: avoid_print
|
||||
print('已保存到相册');
|
||||
}
|
||||
}
|
||||
|
@ -1,8 +1,9 @@
|
||||
// ignore_for_file: library_private_types_in_public_api
|
||||
|
||||
import 'package:dismissible_page/dismissible_page.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:extended_image/extended_image.dart';
|
||||
import 'package:pilipala/common/widgets/appbar.dart';
|
||||
import 'controller.dart';
|
||||
|
||||
typedef DoubleClickAnimationListener = void Function();
|
||||
@ -145,6 +146,8 @@ class _ImagePreviewState extends State<ImagePreview>
|
||||
],
|
||||
),
|
||||
);
|
||||
} else {
|
||||
return const SizedBox();
|
||||
}
|
||||
},
|
||||
initGestureConfigHandler: (ExtendedImageState state) {
|
||||
@ -168,7 +171,8 @@ class _ImagePreviewState extends State<ImagePreview>
|
||||
bottom: 0,
|
||||
child: Container(
|
||||
// height: 45,
|
||||
padding: EdgeInsets.only(bottom: MediaQuery.of(context).padding.bottom, top: 20),
|
||||
padding: EdgeInsets.only(
|
||||
bottom: MediaQuery.of(context).padding.bottom, top: 20),
|
||||
decoration: const BoxDecoration(
|
||||
gradient: LinearGradient(
|
||||
begin: Alignment.topCenter,
|
||||
@ -186,23 +190,29 @@ class _ImagePreviewState extends State<ImagePreview>
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
children: [
|
||||
Obx(
|
||||
() => Text.rich(
|
||||
() => Text.rich(
|
||||
TextSpan(
|
||||
style: const TextStyle(
|
||||
color: Colors.white,
|
||||
fontSize: 18
|
||||
),
|
||||
style: const TextStyle(
|
||||
color: Colors.white, fontSize: 18),
|
||||
children: [
|
||||
TextSpan(text: _previewController.currentPage.toString()),
|
||||
const TextSpan(text: ' / '),
|
||||
TextSpan(text: _previewController.imgList.length.toString()),
|
||||
]),
|
||||
TextSpan(
|
||||
text:
|
||||
_previewController.currentPage.toString()),
|
||||
const TextSpan(text: ' / '),
|
||||
TextSpan(
|
||||
text: _previewController.imgList.length
|
||||
.toString()),
|
||||
]),
|
||||
),
|
||||
),
|
||||
const Spacer(),
|
||||
ElevatedButton(onPressed: () => _previewController.onShareImg(), child: Text('分享')),
|
||||
ElevatedButton(
|
||||
onPressed: () => _previewController.onShareImg(),
|
||||
child: const Text('分享')),
|
||||
const SizedBox(width: 10),
|
||||
ElevatedButton(onPressed: () => _previewController.onSaveImg(), child: Text('保存'))
|
||||
ElevatedButton(
|
||||
onPressed: () => _previewController.onSaveImg(),
|
||||
child: const Text('保存'))
|
||||
],
|
||||
),
|
||||
),
|
||||
|
@ -41,6 +41,7 @@ class _RcmdPageState extends State<RcmdPage>
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
super.build(context);
|
||||
return RefreshIndicator(
|
||||
onRefresh: () async {
|
||||
return await _rcmdController.onRefresh();
|
||||
|
@ -1,10 +1,9 @@
|
||||
import 'package:flutter/cupertino.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_smart_dialog/flutter_smart_dialog.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'package:pilipala/common/widgets/http_error.dart';
|
||||
import 'controller.dart';
|
||||
import 'widgets/hotKeyword.dart';
|
||||
import 'widgets/hot_keyword.dart';
|
||||
import 'widgets/search_text.dart';
|
||||
|
||||
class SearchPage extends StatefulWidget {
|
||||
|
@ -1,7 +1,6 @@
|
||||
// ignore: file_names
|
||||
import 'package:cached_network_image/cached_network_image.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:pilipala/common/widgets/network_img_layer.dart';
|
||||
|
||||
class HotKeyword extends StatelessWidget {
|
||||
final double? width;
|
@ -1,10 +1,11 @@
|
||||
import 'package:flutter/material.dart';
|
||||
|
||||
class SearchText extends StatelessWidget {
|
||||
String? searchText;
|
||||
Function? onSelect;
|
||||
int? searchTextIdx;
|
||||
SearchText({super.key, this.searchText, this.onSelect, this.searchTextIdx});
|
||||
final String? searchText;
|
||||
final Function? onSelect;
|
||||
final int? searchTextIdx;
|
||||
const SearchText(
|
||||
{super.key, this.searchText, this.onSelect, this.searchTextIdx});
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
|
@ -11,10 +11,10 @@ import 'widgets/user_panel.dart';
|
||||
import 'widgets/video_panel.dart';
|
||||
|
||||
class SearchPanel extends StatefulWidget {
|
||||
String? keyword;
|
||||
SearchType? searchType;
|
||||
String? tag;
|
||||
SearchPanel(
|
||||
final String? keyword;
|
||||
final SearchType? searchType;
|
||||
final String? tag;
|
||||
const SearchPanel(
|
||||
{required this.keyword, required this.searchType, this.tag, Key? key})
|
||||
: super(key: key);
|
||||
|
||||
@ -57,6 +57,7 @@ class _SearchPanelState extends State<SearchPanel>
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
super.build(context);
|
||||
return RefreshIndicator(
|
||||
onRefresh: () async {
|
||||
await _searchPanelController!.onRefresh();
|
||||
|
@ -37,7 +37,6 @@ Widget searchLivePanel(BuildContext context, ctr, list) {
|
||||
child: LayoutBuilder(builder: (context, boxConstraints) {
|
||||
double maxWidth = boxConstraints.maxWidth;
|
||||
double maxHeight = boxConstraints.maxHeight;
|
||||
double PR = MediaQuery.of(context).devicePixelRatio;
|
||||
return Stack(
|
||||
children: [
|
||||
Hero(
|
||||
@ -79,7 +78,7 @@ Widget searchLivePanel(BuildContext context, ctr, list) {
|
||||
}
|
||||
|
||||
class LiveContent extends StatelessWidget {
|
||||
final liveItem;
|
||||
final dynamic liveItem;
|
||||
const LiveContent({Key? key, required this.liveItem}) : super(key: key);
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
|
@ -71,7 +71,6 @@ Widget searchUserPanel(BuildContext context, ctr, list) {
|
||||
),
|
||||
),
|
||||
);
|
||||
;
|
||||
},
|
||||
);
|
||||
}
|
||||
|
@ -5,6 +5,7 @@ import 'package:pilipala/pages/setting/index.dart';
|
||||
class SettingPage extends StatelessWidget {
|
||||
const SettingPage({super.key});
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
final SettingController settingController = Get.put(SettingController());
|
||||
return Scaffold(
|
||||
|
@ -1,6 +1,4 @@
|
||||
import 'dart:async';
|
||||
import 'dart:developer';
|
||||
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_meedu_media_kit/meedu_player.dart';
|
||||
import 'package:get/get.dart';
|
||||
|
@ -105,7 +105,6 @@ class VideoIntroController extends GetxController {
|
||||
// 获取up主粉丝数
|
||||
Future queryUserStat() async {
|
||||
var result = await UserHttp.userStat(mid: videoDetail.value.owner!.mid!);
|
||||
print('🌹:$result');
|
||||
if (result['status']) {
|
||||
userStat = result['data'];
|
||||
}
|
||||
@ -238,7 +237,6 @@ class VideoIntroController extends GetxController {
|
||||
onPressed: () async {
|
||||
var res = await VideoHttp.coinVideo(
|
||||
bvid: bvid, multiply: _tempThemeValue);
|
||||
print(res);
|
||||
if (res['status']) {
|
||||
SmartDialog.showToast('投币成功');
|
||||
} else {
|
||||
@ -263,7 +261,10 @@ class VideoIntroController extends GetxController {
|
||||
delMediaIdsNew.add(i.id);
|
||||
}
|
||||
}
|
||||
} catch (e) {}
|
||||
} catch (e) {
|
||||
// ignore: avoid_print
|
||||
print(e);
|
||||
}
|
||||
var result = await VideoHttp.favVideo(
|
||||
aid: IdUtils.bv2av(bvid),
|
||||
addIds: addMediaIdsNew.join(','),
|
||||
@ -282,10 +283,8 @@ class VideoIntroController extends GetxController {
|
||||
|
||||
// 分享视频
|
||||
Future actionShareVideo() async {
|
||||
var result =
|
||||
await Share.share('${HttpString.baseUrl}/video/$bvid').whenComplete(() {
|
||||
print("share completion block ");
|
||||
});
|
||||
var result = await Share.share('${HttpString.baseUrl}/video/$bvid')
|
||||
.whenComplete(() {});
|
||||
return result;
|
||||
}
|
||||
|
||||
|
@ -4,8 +4,8 @@ import 'package:font_awesome_flutter/font_awesome_flutter.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:hive/hive.dart';
|
||||
import 'package:pilipala/common/constants.dart';
|
||||
import 'package:pilipala/common/widgets/http_error.dart';
|
||||
import 'package:pilipala/pages/fav/index.dart';
|
||||
import 'package:pilipala/pages/video/detail/index.dart';
|
||||
import 'package:pilipala/common/widgets/network_img_layer.dart';
|
||||
import 'package:pilipala/common/widgets/stat/danmu.dart';
|
||||
@ -53,6 +53,7 @@ class _VideoIntroPanelState extends State<VideoIntroPanel>
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
super.build(context);
|
||||
return FutureBuilder(
|
||||
future: videoIntroController.queryVideoIntro(),
|
||||
builder: (context, snapshot) {
|
||||
@ -77,10 +78,10 @@ class _VideoIntroPanelState extends State<VideoIntroPanel>
|
||||
}
|
||||
|
||||
class VideoInfo extends StatefulWidget {
|
||||
bool loadingStatus = false;
|
||||
VideoDetailData? videoDetail;
|
||||
final bool loadingStatus;
|
||||
final VideoDetailData? videoDetail;
|
||||
|
||||
VideoInfo({Key? key, required this.loadingStatus, this.videoDetail})
|
||||
const VideoInfo({Key? key, this.loadingStatus = false, this.videoDetail})
|
||||
: super(key: key);
|
||||
|
||||
@override
|
||||
@ -93,14 +94,6 @@ class _VideoInfoState extends State<VideoInfo> with TickerProviderStateMixin {
|
||||
Get.put(VideoIntroController(), tag: Get.arguments['heroTag']);
|
||||
bool isExpand = false;
|
||||
|
||||
/// 手动控制动画的控制器
|
||||
late AnimationController? _manualController;
|
||||
|
||||
/// 手动控制
|
||||
late Animation<double>? _manualAnimation;
|
||||
|
||||
final FavController _favController = Get.put(FavController());
|
||||
|
||||
late VideoDetailController? videoDetailCtr;
|
||||
Box localCache = GStrorage.localCache;
|
||||
late double sheetHeight;
|
||||
@ -109,13 +102,6 @@ class _VideoInfoState extends State<VideoInfo> with TickerProviderStateMixin {
|
||||
void initState() {
|
||||
super.initState();
|
||||
|
||||
/// 不设置重复,使用代码控制进度,动画时间1秒
|
||||
_manualController = AnimationController(
|
||||
vsync: this,
|
||||
duration: const Duration(milliseconds: 400),
|
||||
);
|
||||
_manualAnimation =
|
||||
Tween<double>(begin: 0.5, end: 1.5).animate(_manualController!);
|
||||
videoDetailCtr =
|
||||
Get.find<VideoDetailController>(tag: Get.arguments['heroTag']);
|
||||
sheetHeight = localCache.get('sheetHeight');
|
||||
@ -139,56 +125,70 @@ class _VideoInfoState extends State<VideoInfo> with TickerProviderStateMixin {
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return SliverPadding(
|
||||
padding: const EdgeInsets.only(left: 12, right: 12, top: 15),
|
||||
padding: const EdgeInsets.only(
|
||||
left: StyleString.safeSpace, right: StyleString.safeSpace, top: 15),
|
||||
sliver: SliverToBoxAdapter(
|
||||
child: !widget.loadingStatus || videoItem.isNotEmpty
|
||||
? Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Row(
|
||||
children: [
|
||||
Expanded(
|
||||
child: Text(
|
||||
!widget.loadingStatus
|
||||
? widget.videoDetail!.title
|
||||
: videoItem['title'],
|
||||
style: Theme.of(context)
|
||||
.textTheme
|
||||
.titleMedium!
|
||||
.copyWith(
|
||||
letterSpacing: 0.5,
|
||||
fontWeight: FontWeight.w500),
|
||||
maxLines: 2,
|
||||
overflow: TextOverflow.ellipsis,
|
||||
),
|
||||
),
|
||||
const SizedBox(width: 20),
|
||||
SizedBox(
|
||||
width: 34,
|
||||
height: 34,
|
||||
child: IconButton(
|
||||
style: ButtonStyle(
|
||||
padding: MaterialStateProperty.all(EdgeInsets.zero),
|
||||
backgroundColor:
|
||||
MaterialStateProperty.resolveWith((states) {
|
||||
return Theme.of(context)
|
||||
.highlightColor
|
||||
.withOpacity(0.2);
|
||||
}),
|
||||
GestureDetector(
|
||||
onTap: () {
|
||||
showBottomSheet(
|
||||
context: context,
|
||||
enableDrag: true,
|
||||
builder: (BuildContext context) {
|
||||
return IntroDetail(videoDetail: widget.videoDetail!);
|
||||
},
|
||||
);
|
||||
},
|
||||
child: Row(
|
||||
children: [
|
||||
Expanded(
|
||||
child: Text(
|
||||
!widget.loadingStatus
|
||||
? widget.videoDetail!.title
|
||||
: videoItem['title'],
|
||||
style: Theme.of(context)
|
||||
.textTheme
|
||||
.titleMedium!
|
||||
.copyWith(
|
||||
letterSpacing: 0.5,
|
||||
fontWeight: FontWeight.w500),
|
||||
maxLines: 2,
|
||||
overflow: TextOverflow.ellipsis,
|
||||
),
|
||||
onPressed: () {
|
||||
showBottomSheet(
|
||||
),
|
||||
const SizedBox(width: 20),
|
||||
SizedBox(
|
||||
width: 34,
|
||||
height: 34,
|
||||
child: IconButton(
|
||||
style: ButtonStyle(
|
||||
padding:
|
||||
MaterialStateProperty.all(EdgeInsets.zero),
|
||||
backgroundColor:
|
||||
MaterialStateProperty.resolveWith((states) {
|
||||
return Theme.of(context)
|
||||
.highlightColor
|
||||
.withOpacity(0.2);
|
||||
}),
|
||||
),
|
||||
onPressed: () {
|
||||
showBottomSheet(
|
||||
context: context,
|
||||
enableDrag: true,
|
||||
builder: (BuildContext context) {
|
||||
return IntroDetail(
|
||||
videoDetail: widget.videoDetail!);
|
||||
});
|
||||
},
|
||||
icon: const Icon(Icons.more_horiz),
|
||||
},
|
||||
);
|
||||
},
|
||||
icon: const Icon(Icons.more_horiz),
|
||||
),
|
||||
),
|
||||
),
|
||||
],
|
||||
],
|
||||
),
|
||||
),
|
||||
const SizedBox(height: 6),
|
||||
Row(
|
||||
@ -222,7 +222,7 @@ class _VideoInfoState extends State<VideoInfo> with TickerProviderStateMixin {
|
||||
),
|
||||
// 点赞收藏转发
|
||||
Padding(
|
||||
padding: const EdgeInsets.only(top: 20),
|
||||
padding: const EdgeInsets.only(top: 15),
|
||||
child: SingleChildScrollView(
|
||||
scrollDirection: Axis.horizontal,
|
||||
child: actionRow(
|
||||
@ -270,25 +270,24 @@ class _VideoInfoState extends State<VideoInfo> with TickerProviderStateMixin {
|
||||
fadeOutDuration: Duration.zero,
|
||||
),
|
||||
const SizedBox(width: 10),
|
||||
Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Text(!widget.loadingStatus
|
||||
? widget.videoDetail!.owner!.name
|
||||
: videoItem['owner'].name),
|
||||
// const SizedBox(width: 10),
|
||||
Text(
|
||||
widget.loadingStatus
|
||||
? '- 粉丝'
|
||||
: '${Utils.numFormat(videoIntroController.userStat['follower'])}粉丝',
|
||||
style: TextStyle(
|
||||
fontSize: Theme.of(context)
|
||||
.textTheme
|
||||
.labelSmall!
|
||||
.fontSize,
|
||||
color: Theme.of(context).colorScheme.outline),
|
||||
),
|
||||
],
|
||||
Text(
|
||||
!widget.loadingStatus
|
||||
? widget.videoDetail!.owner!.name
|
||||
: videoItem['owner'].name,
|
||||
style: const TextStyle(fontSize: 12.5),
|
||||
),
|
||||
const SizedBox(width: 10),
|
||||
Text(
|
||||
widget.loadingStatus
|
||||
? '- 粉丝'
|
||||
: Utils.numFormat(
|
||||
videoIntroController.userStat['follower']),
|
||||
style: TextStyle(
|
||||
fontSize: Theme.of(context)
|
||||
.textTheme
|
||||
.labelSmall!
|
||||
.fontSize,
|
||||
color: Theme.of(context).colorScheme.outline),
|
||||
),
|
||||
const Spacer(),
|
||||
AnimatedOpacity(
|
||||
@ -418,14 +417,14 @@ class _VideoInfoState extends State<VideoInfo> with TickerProviderStateMixin {
|
||||
),
|
||||
const SizedBox(width: 8),
|
||||
ActionRowItem(
|
||||
icon: const Icon(FontAwesomeIcons.share),
|
||||
onTap: () => videoIntroController.actionShareVideo(),
|
||||
selectStatus: false,
|
||||
loadingStatus: widget.loadingStatus,
|
||||
text: !widget.loadingStatus
|
||||
? widget.videoDetail!.stat!.share!.toString()
|
||||
: '-',
|
||||
),
|
||||
icon: const Icon(FontAwesomeIcons.share),
|
||||
onTap: () => videoIntroController.actionShareVideo(),
|
||||
selectStatus: false,
|
||||
loadingStatus: widget.loadingStatus,
|
||||
// text: !widget.loadingStatus
|
||||
// ? widget.videoDetail!.stat!.share!.toString()
|
||||
// : '-',
|
||||
text: '转发'),
|
||||
]);
|
||||
}
|
||||
|
||||
|
@ -2,21 +2,21 @@ import 'package:flutter/material.dart';
|
||||
import 'package:pilipala/common/constants.dart';
|
||||
|
||||
class ActionItem extends StatelessWidget {
|
||||
Icon? icon;
|
||||
Icon? selectIcon;
|
||||
Function? onTap;
|
||||
bool? loadingStatus;
|
||||
String? text;
|
||||
bool selectStatus = false;
|
||||
final Icon? icon;
|
||||
final Icon? selectIcon;
|
||||
final Function? onTap;
|
||||
final bool? loadingStatus;
|
||||
final String? text;
|
||||
final bool selectStatus;
|
||||
|
||||
ActionItem({
|
||||
const ActionItem({
|
||||
Key? key,
|
||||
this.icon,
|
||||
this.selectIcon,
|
||||
this.onTap,
|
||||
this.loadingStatus,
|
||||
this.text,
|
||||
required this.selectStatus,
|
||||
this.selectStatus = false,
|
||||
}) : super(key: key);
|
||||
|
||||
@override
|
||||
|
@ -1,22 +1,21 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:pilipala/common/constants.dart';
|
||||
|
||||
class ActionRowItem extends StatelessWidget {
|
||||
Icon? icon;
|
||||
Icon? selectIcon;
|
||||
Function? onTap;
|
||||
bool? loadingStatus;
|
||||
String? text;
|
||||
bool selectStatus = false;
|
||||
final Icon? icon;
|
||||
final Icon? selectIcon;
|
||||
final Function? onTap;
|
||||
final bool? loadingStatus;
|
||||
final String? text;
|
||||
final bool selectStatus;
|
||||
|
||||
ActionRowItem({
|
||||
const ActionRowItem({
|
||||
Key? key,
|
||||
this.icon,
|
||||
this.selectIcon,
|
||||
this.onTap,
|
||||
this.loadingStatus,
|
||||
this.text,
|
||||
required this.selectStatus,
|
||||
this.selectStatus = false,
|
||||
}) : super(key: key);
|
||||
|
||||
@override
|
||||
|
@ -5,8 +5,8 @@ import 'package:pilipala/common/widgets/http_error.dart';
|
||||
import 'package:pilipala/utils/storage.dart';
|
||||
|
||||
class FavPanel extends StatefulWidget {
|
||||
var ctr;
|
||||
FavPanel({this.ctr});
|
||||
final dynamic ctr;
|
||||
const FavPanel({super.key, this.ctr});
|
||||
|
||||
@override
|
||||
State<FavPanel> createState() => _FavPanelState();
|
||||
@ -112,7 +112,7 @@ class _FavPanelState extends State<FavPanel> {
|
||||
}
|
||||
} else {
|
||||
// 骨架屏
|
||||
return Text('请求中');
|
||||
return const Text('请求中');
|
||||
}
|
||||
},
|
||||
),
|
||||
|
@ -11,9 +11,9 @@ Box localCache = GStrorage.localCache;
|
||||
late double sheetHeight;
|
||||
|
||||
class IntroDetail extends StatelessWidget {
|
||||
var videoDetail;
|
||||
final dynamic videoDetail;
|
||||
|
||||
IntroDetail({
|
||||
const IntroDetail({
|
||||
Key? key,
|
||||
this.videoDetail,
|
||||
}) : super(key: key);
|
||||
@ -28,11 +28,11 @@ class IntroDetail extends StatelessWidget {
|
||||
child: Column(
|
||||
children: [
|
||||
Container(
|
||||
height: 40,
|
||||
height: 35,
|
||||
padding: const EdgeInsets.only(bottom: 2),
|
||||
child: Center(
|
||||
child: Container(
|
||||
width: 40,
|
||||
width: 32,
|
||||
height: 3,
|
||||
decoration: BoxDecoration(
|
||||
color: Theme.of(context)
|
||||
|
@ -1,8 +1,8 @@
|
||||
import 'package:flutter/material.dart';
|
||||
|
||||
class MenuRow extends StatelessWidget {
|
||||
bool? loadingStatus;
|
||||
MenuRow({
|
||||
final bool? loadingStatus;
|
||||
const MenuRow({
|
||||
Key? key,
|
||||
this.loadingStatus,
|
||||
}) : super(key: key);
|
||||
|
@ -1,5 +1,4 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'package:pilipala/models/video_detail_res.dart';
|
||||
|
||||
Widget seasonPanel(UgcSeason ugcSeason, cid, sheetHeight) {
|
||||
|
@ -114,6 +114,7 @@ class _VideoReplyPanelState extends State<VideoReplyPanel>
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
super.build(context);
|
||||
return RefreshIndicator(
|
||||
onRefresh: () async {
|
||||
_videoReplyController.currentPage = 0;
|
||||
|
@ -12,21 +12,21 @@ import 'package:pilipala/utils/utils.dart';
|
||||
import 'zan.dart';
|
||||
|
||||
class ReplyItem extends StatelessWidget {
|
||||
ReplyItem({
|
||||
super.key,
|
||||
const ReplyItem({
|
||||
this.replyItem,
|
||||
this.addReply,
|
||||
this.replyLevel,
|
||||
this.showReplyRow,
|
||||
this.showReplyRow = true,
|
||||
this.replyReply,
|
||||
this.replyType,
|
||||
});
|
||||
ReplyItemModel? replyItem;
|
||||
Function? addReply;
|
||||
String? replyLevel;
|
||||
bool? showReplyRow = true;
|
||||
Function? replyReply;
|
||||
ReplyType? replyType;
|
||||
Key? key,
|
||||
}) : super(key: key);
|
||||
final ReplyItemModel? replyItem;
|
||||
final Function? addReply;
|
||||
final String? replyLevel;
|
||||
final bool? showReplyRow;
|
||||
final Function? replyReply;
|
||||
final ReplyType? replyType;
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
@ -118,7 +118,7 @@ class ReplyItem extends StatelessWidget {
|
||||
height: 11,
|
||||
),
|
||||
const SizedBox(width: 6),
|
||||
if (replyItem!.isUp!) UpTag(),
|
||||
if (replyItem!.isUp!) const UpTag(),
|
||||
],
|
||||
),
|
||||
Positioned(
|
||||
@ -186,7 +186,7 @@ class ReplyItem extends StatelessWidget {
|
||||
TextSpan(
|
||||
children: [
|
||||
if (replyItem!.isTop!)
|
||||
WidgetSpan(child: UpTag(tagText: 'TOP')),
|
||||
const WidgetSpan(child: UpTag(tagText: 'TOP')),
|
||||
buildContent(context, replyItem!, replyReply, null),
|
||||
],
|
||||
),
|
||||
@ -204,7 +204,7 @@ class ReplyItem extends StatelessWidget {
|
||||
child: ReplyItemRow(
|
||||
replies: replyItem!.replies,
|
||||
replyControl: replyItem!.replyControl,
|
||||
f_rpid: replyItem!.rpid,
|
||||
// f_rpid: replyItem!.rpid,
|
||||
replyItem: replyItem,
|
||||
replyReply: replyReply,
|
||||
),
|
||||
@ -216,7 +216,6 @@ class ReplyItem extends StatelessWidget {
|
||||
|
||||
// 感谢、回复、复制
|
||||
Widget bottonAction(context, replyControl) {
|
||||
var color = Theme.of(context).colorScheme.outline;
|
||||
return Row(
|
||||
children: [
|
||||
const SizedBox(width: 48),
|
||||
@ -297,13 +296,13 @@ class ReplyItemRow extends StatelessWidget {
|
||||
super.key,
|
||||
this.replies,
|
||||
this.replyControl,
|
||||
this.f_rpid,
|
||||
// this.f_rpid,
|
||||
this.replyItem,
|
||||
this.replyReply,
|
||||
});
|
||||
List? replies;
|
||||
ReplyControl? replyControl;
|
||||
int? f_rpid;
|
||||
// int? f_rpid;
|
||||
ReplyItemModel? replyItem;
|
||||
Function? replyReply;
|
||||
|
||||
@ -361,7 +360,7 @@ class ReplyItemRow extends StatelessWidget {
|
||||
},
|
||||
),
|
||||
if (replies![i].isUp)
|
||||
WidgetSpan(
|
||||
const WidgetSpan(
|
||||
child: UpTag(),
|
||||
),
|
||||
buildContent(
|
||||
@ -439,16 +438,14 @@ InlineSpan buildContent(
|
||||
color: Theme.of(context).colorScheme.primary,
|
||||
),
|
||||
recognizer: TapGestureRecognizer()
|
||||
..onTap = () => {
|
||||
Get.toNamed(
|
||||
'/webview',
|
||||
parameters: {
|
||||
'url': content.vote['url'],
|
||||
'type': 'vote',
|
||||
'pageTitle': content.vote['title'],
|
||||
},
|
||||
)
|
||||
},
|
||||
..onTap = () => Get.toNamed(
|
||||
'/webview',
|
||||
parameters: {
|
||||
'url': content.vote['url'],
|
||||
'type': 'vote',
|
||||
'pageTitle': content.vote['title'],
|
||||
},
|
||||
),
|
||||
),
|
||||
);
|
||||
return '';
|
||||
@ -554,11 +551,9 @@ InlineSpan buildContent(
|
||||
color: Theme.of(context).colorScheme.primary,
|
||||
),
|
||||
recognizer: TapGestureRecognizer()
|
||||
..onTap = () => {
|
||||
Get.toNamed('/searchResult', parameters: {
|
||||
'keyword': content.jumpUrl[matchStr]['title']
|
||||
})
|
||||
},
|
||||
..onTap = () => Get.toNamed('/searchResult', parameters: {
|
||||
'keyword': content.jumpUrl[matchStr]['title']
|
||||
}),
|
||||
),
|
||||
);
|
||||
spanChilds.add(
|
||||
@ -718,16 +713,14 @@ InlineSpan buildContent(
|
||||
color: Theme.of(context).colorScheme.primary,
|
||||
),
|
||||
recognizer: TapGestureRecognizer()
|
||||
..onTap = () => {
|
||||
Get.toNamed(
|
||||
'/webview',
|
||||
parameters: {
|
||||
'url': content.richText['note']['click_url'],
|
||||
'type': 'note',
|
||||
'pageTitle': '笔记预览'
|
||||
},
|
||||
)
|
||||
},
|
||||
..onTap = () => Get.toNamed(
|
||||
'/webview',
|
||||
parameters: {
|
||||
'url': content.richText['note']['click_url'],
|
||||
'type': 'note',
|
||||
'pageTitle': '笔记预览'
|
||||
},
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
@ -736,8 +729,8 @@ InlineSpan buildContent(
|
||||
}
|
||||
|
||||
class UpTag extends StatelessWidget {
|
||||
String? tagText;
|
||||
UpTag({super.key, this.tagText = 'UP'});
|
||||
final String? tagText;
|
||||
const UpTag({super.key, this.tagText = 'UP'});
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
Color primary = Theme.of(context).colorScheme.primary;
|
||||
|
@ -6,13 +6,13 @@ import 'package:pilipala/models/common/reply_type.dart';
|
||||
import 'package:pilipala/models/video/reply/item.dart';
|
||||
|
||||
class ZanButton extends StatefulWidget {
|
||||
ZanButton({
|
||||
const ZanButton({
|
||||
super.key,
|
||||
this.replyItem,
|
||||
this.replyType,
|
||||
});
|
||||
|
||||
ReplyItemModel? replyItem;
|
||||
final ReplyItemModel? replyItem;
|
||||
final ReplyType? replyType;
|
||||
|
||||
@override
|
||||
|
@ -1,5 +1,4 @@
|
||||
import 'dart:async';
|
||||
import 'dart:developer';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_smart_dialog/flutter_smart_dialog.dart';
|
||||
import 'package:get/get.dart';
|
||||
@ -10,13 +9,14 @@ import 'package:pilipala/models/video/reply/item.dart';
|
||||
import 'package:pilipala/utils/storage.dart';
|
||||
|
||||
class VideoReplyNewDialog extends StatefulWidget {
|
||||
int? oid;
|
||||
int? root;
|
||||
int? parent;
|
||||
ReplyType? replyType;
|
||||
ReplyItemModel? replyItem;
|
||||
final int? oid;
|
||||
final int? root;
|
||||
final int? parent;
|
||||
final ReplyType? replyType;
|
||||
final ReplyItemModel? replyItem;
|
||||
|
||||
VideoReplyNewDialog({
|
||||
const VideoReplyNewDialog({
|
||||
super.key,
|
||||
this.oid,
|
||||
this.root,
|
||||
this.parent,
|
||||
@ -56,7 +56,9 @@ class _VideoReplyNewDialogState extends State<VideoReplyNewDialog>
|
||||
|
||||
_autoFocus() async {
|
||||
await Future.delayed(const Duration(milliseconds: 300));
|
||||
FocusScope.of(context).requestFocus(replyContentFocusNode);
|
||||
if (context.mounted) {
|
||||
FocusScope.of(context).requestFocus(replyContentFocusNode);
|
||||
}
|
||||
}
|
||||
|
||||
_printLatestValue() {
|
||||
@ -91,9 +93,8 @@ class _VideoReplyNewDialogState extends State<VideoReplyNewDialog>
|
||||
super.didChangeMetrics();
|
||||
WidgetsBinding.instance.addPostFrameCallback((_) {
|
||||
// 键盘高度
|
||||
final viewInsets = EdgeInsets.fromWindowPadding(
|
||||
WidgetsBinding.instance.window.viewInsets,
|
||||
WidgetsBinding.instance.window.devicePixelRatio);
|
||||
final viewInsets = EdgeInsets.fromViewPadding(
|
||||
View.of(context).viewInsets, View.of(context).devicePixelRatio);
|
||||
_debouncer.run(() {
|
||||
if (mounted) {
|
||||
setState(() {
|
||||
@ -197,7 +198,7 @@ class _VideoReplyNewDialogState extends State<VideoReplyNewDialog>
|
||||
}
|
||||
}
|
||||
|
||||
typedef void DebounceCallback();
|
||||
typedef DebounceCallback = void Function();
|
||||
|
||||
class Debouncer {
|
||||
DebounceCallback? callback;
|
||||
|
@ -173,8 +173,8 @@ class _VideoDetailPageState extends State<VideoDetailPage>
|
||||
controller: _meeduPlayerController!,
|
||||
header: (BuildContext context,
|
||||
MeeduPlayerController
|
||||
_meeduPlayerController,
|
||||
Responsive) {
|
||||
meeduPlayerController,
|
||||
Responsive responsive) {
|
||||
return AppBar(
|
||||
toolbarHeight: 40,
|
||||
backgroundColor: Colors.transparent,
|
||||
@ -278,7 +278,8 @@ class _VideoDetailPageState extends State<VideoDetailPage>
|
||||
pinned: true,
|
||||
delegate: SliverHeaderDelegate(
|
||||
height: 50,
|
||||
child: MenuRow(loadingStatus: false),
|
||||
child:
|
||||
const MenuRow(loadingStatus: false),
|
||||
),
|
||||
),
|
||||
const RelatedVideoPanel(),
|
||||
@ -306,6 +307,7 @@ class _VideoDetailPageState extends State<VideoDetailPage>
|
||||
snapshot.data!.toDouble(),
|
||||
continuePlay,
|
||||
playerStatus,
|
||||
null,
|
||||
);
|
||||
}),
|
||||
)
|
||||
|
@ -3,14 +3,15 @@ import 'package:flutter_meedu_media_kit/meedu_player.dart';
|
||||
|
||||
class ScrollAppBar extends StatelessWidget {
|
||||
final double scrollVal;
|
||||
Function callback;
|
||||
final Function callback;
|
||||
final PlayerStatus playerStatus;
|
||||
|
||||
ScrollAppBar(
|
||||
const ScrollAppBar(
|
||||
this.scrollVal,
|
||||
this.callback,
|
||||
this.playerStatus,
|
||||
);
|
||||
Key? key,
|
||||
) : super(key: key);
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
|
@ -1,16 +1,20 @@
|
||||
// ignore_for_file: library_private_types_in_public_api
|
||||
|
||||
import 'package:flutter/material.dart';
|
||||
|
||||
class ExpandedSection extends StatefulWidget {
|
||||
final Widget child;
|
||||
final Widget? child;
|
||||
final bool expand;
|
||||
double begin = 0.0;
|
||||
double end = 1.0;
|
||||
final double begin;
|
||||
final double end;
|
||||
|
||||
ExpandedSection(
|
||||
{this.expand = false,
|
||||
required this.child,
|
||||
required this.begin,
|
||||
required this.end});
|
||||
const ExpandedSection({
|
||||
super.key,
|
||||
this.expand = false,
|
||||
this.child,
|
||||
this.begin = 0.0,
|
||||
this.end = 1.0,
|
||||
});
|
||||
|
||||
@override
|
||||
_ExpandedSectionState createState() => _ExpandedSectionState();
|
||||
|
@ -1,3 +1,5 @@
|
||||
// ignore_for_file: avoid_print
|
||||
|
||||
import 'package:flutter_smart_dialog/flutter_smart_dialog.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'package:hive/hive.dart';
|
||||
@ -5,7 +7,6 @@ import 'package:pilipala/http/constants.dart';
|
||||
import 'package:pilipala/http/init.dart';
|
||||
import 'package:pilipala/http/user.dart';
|
||||
import 'package:pilipala/pages/dynamics/index.dart';
|
||||
import 'package:pilipala/pages/home/index.dart';
|
||||
import 'package:pilipala/pages/mine/index.dart';
|
||||
import 'package:pilipala/pages/rcmd/controller.dart';
|
||||
import 'package:pilipala/utils/cookie.dart';
|
||||
|
@ -67,6 +67,6 @@ class Routes {
|
||||
// 用户中心
|
||||
GetPage(name: '/member', page: () => const MemberPage()),
|
||||
// 二级回复
|
||||
GetPage(name: '/replyReply', page: () => VideoReplyReplyPanel()),
|
||||
GetPage(name: '/replyReply', page: () => const VideoReplyReplyPanel()),
|
||||
];
|
||||
}
|
||||
|
@ -1,3 +1,5 @@
|
||||
// ignore_for_file: constant_identifier_names
|
||||
|
||||
import 'dart:math';
|
||||
|
||||
import 'package:flutter/material.dart';
|
||||
|
@ -1,4 +1,6 @@
|
||||
// 工具函数
|
||||
// ignore_for_file: non_constant_identifier_names
|
||||
|
||||
import 'dart:async';
|
||||
import 'dart:io';
|
||||
import 'dart:math';
|
||||
@ -52,7 +54,7 @@ class Utils {
|
||||
// 当前时间
|
||||
int time = (DateTime.now().millisecondsSinceEpoch / 1000).round();
|
||||
// 对比
|
||||
int _distance = (time - timeStamp).toInt();
|
||||
int distance = (time - timeStamp).toInt();
|
||||
// 当前年日期
|
||||
String currentYearStr = 'MM月DD日 hh:mm';
|
||||
String lastYearStr = 'YY年MM月DD日 hh:mm';
|
||||
@ -65,12 +67,12 @@ class Utils {
|
||||
toInt: false,
|
||||
formatType: formatType);
|
||||
}
|
||||
if (_distance <= 60) {
|
||||
if (distance <= 60) {
|
||||
return '刚刚';
|
||||
} else if (_distance <= 3600) {
|
||||
return '${(_distance / 60).floor()}分钟前';
|
||||
} else if (_distance <= 43200) {
|
||||
return '${(_distance / 60 / 60).floor()}小时前';
|
||||
} else if (distance <= 3600) {
|
||||
return '${(distance / 60).floor()}分钟前';
|
||||
} else if (distance <= 43200) {
|
||||
return '${(distance / 60 / 60).floor()}小时前';
|
||||
} else if (DateTime.fromMillisecondsSinceEpoch(time * 1000).year ==
|
||||
DateTime.fromMillisecondsSinceEpoch(timeStamp * 1000).year) {
|
||||
return CustomStamp_str(
|
||||
|
Reference in New Issue
Block a user