Files
video/app/lib/models/video_item.dart
2026-10-15 20:36:59 +08:00

118 lines
3.7 KiB
Dart

/// Feed 视频项(GET /videos/feed 列表项,对应服务端 video_service 输出)
class VideoItem {
VideoItem({
required this.videoId,
this.title = '',
this.coverUrl = '',
this.videoUrl = '',
this.duration = 0,
required this.author,
this.categoryId = 0,
this.viewCount = 0,
this.likeCount = 0,
this.commentCount = 0,
this.favoriteCount = 0,
this.tags = const [],
this.isLiked = false,
this.isFavorited = false,
this.description = '',
this.status = -1,
this.statusText = '',
this.rejectReason = '',
});
final int videoId;
final String title;
final String coverUrl;
final String videoUrl; // m3u8
final int duration; // 秒
final VideoAuthor author;
final int categoryId;
final int viewCount;
final int likeCount;
final int commentCount;
final int favoriteCount;
final List<String> tags;
final bool isLiked;
final bool isFavorited;
final String description;
/// 作品状态(仅「我的作品」接口返回):-1 未提供;0转码中 1待审核 2已发布 3拒绝 4下架 5转码失败
final int status;
final String statusText;
final String rejectReason;
/// 拷贝更新(点赞/收藏乐观更新用)
VideoItem copyWith({
bool? isLiked,
bool? isFavorited,
int? likeCount,
int? favoriteCount,
int? commentCount,
}) =>
VideoItem(
videoId: videoId,
title: title,
coverUrl: coverUrl,
videoUrl: videoUrl,
duration: duration,
author: author,
categoryId: categoryId,
viewCount: viewCount,
likeCount: likeCount ?? this.likeCount,
commentCount: commentCount ?? this.commentCount,
favoriteCount: favoriteCount ?? this.favoriteCount,
tags: tags,
isLiked: isLiked ?? this.isLiked,
isFavorited: isFavorited ?? this.isFavorited,
description: description,
status: status,
statusText: statusText,
rejectReason: rejectReason,
);
factory VideoItem.fromJson(Map<String, dynamic> json) => VideoItem(
videoId: json['video_id'] as int,
title: (json['title'] as String?) ?? '',
coverUrl: (json['cover_url'] as String?) ?? '',
videoUrl: (json['video_url'] as String?) ?? '',
duration: (json['duration'] as num?)?.toInt() ?? 0,
categoryId: (json['category_id'] as num?)?.toInt() ?? 0,
author: VideoAuthor.fromJson(
(json['author'] as Map<String, dynamic>?) ?? const {},
),
viewCount: (json['view_count'] as num?)?.toInt() ?? 0,
likeCount: (json['like_count'] as num?)?.toInt() ?? 0,
commentCount: (json['comment_count'] as num?)?.toInt() ?? 0,
favoriteCount: (json['favorite_count'] as num?)?.toInt() ?? 0,
tags: ((json['tags'] as List?) ?? const [])
.map((e) => e.toString())
.toList(),
isLiked: (json['is_liked'] as bool?) ?? false,
isFavorited: (json['is_favorited'] as bool?) ?? false,
description: (json['description'] as String?) ?? '',
status: (json['status'] as num?)?.toInt() ?? -1,
statusText: (json['status_text'] as String?) ?? '',
rejectReason: (json['reject_reason'] as String?) ?? '',
);
}
/// 作者简要信息
class VideoAuthor {
VideoAuthor({
required this.userId,
this.nickname = '',
this.avatarUrl = '',
});
final int userId;
final String nickname;
final String avatarUrl;
factory VideoAuthor.fromJson(Map<String, dynamic> json) => VideoAuthor(
userId: (json['user_id'] as num?)?.toInt() ?? 0,
nickname: (json['nickname'] as String?) ?? '',
avatarUrl: (json['avatar_url'] as String?) ?? '',
);
}