Skip to content

Commit

Permalink
Merge branch 'dev-note-recent-anime'
Browse files Browse the repository at this point in the history
  • Loading branch information
linyi102 committed Dec 30, 2023
2 parents c718f87 + 006f1d6 commit 0aa88df
Show file tree
Hide file tree
Showing 30 changed files with 491 additions and 128 deletions.
1 change: 1 addition & 0 deletions lib/components/note_img_grid.dart
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@ class NoteImgGrid extends StatelessWidget {
return Container(
padding: const EdgeInsets.fromLTRB(15, 5, 15, 15),
child: Responsive(
responsiveWidthSource: ResponsiveWidthSource.constraints,
// mobile: _buildMobileView(),
mobile: _buildView(columnCnt: 3, maxDisplayCount: 9),
tablet: _buildView(columnCnt: 5, maxDisplayCount: 10),
Expand Down
14 changes: 11 additions & 3 deletions lib/dao/anime_dao.dart
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import 'package:flutter_test_future/dao/anime_series_dao.dart';
import 'package:flutter_test_future/models/anime_episode_info.dart';
import 'package:flutter_test_future/models/params/page_params.dart';
import 'package:flutter_test_future/utils/escape_util.dart';
import 'package:flutter_test_future/utils/sqlite_util.dart';
Expand Down Expand Up @@ -467,13 +468,13 @@ class AnimeDao {
''');
}

static Future<bool> updateEpisodeCntAndStartNumberByAnimeId(
int animeId, int episodeCnt, int episodeStartNumber) async {
static Future<bool> updateEpisodeInfoByAnimeId(
int animeId, AnimeEpisodeInfo episodeInfo) async {
Log.info("sql: updateEpisodeCntAndStartNumberByAnimeId");

return await db.rawUpdate('''
update anime
set anime_episode_cnt = $episodeCnt, episode_start_number = $episodeStartNumber
set anime_episode_cnt = ${episodeInfo.totalCnt}, episode_start_number = ${episodeInfo.startNumber}, cal_episode_number_from_one = ${episodeInfo.calNumberFromOne ? 1 : 0}
where anime_id = $animeId;
''') > 0;
}
Expand Down Expand Up @@ -557,6 +558,8 @@ class AnimeDao {
animeName: row['anime_name'] as String? ?? '',
animeEpisodeCnt: row['anime_episode_cnt'] as int? ?? 0,
episodeStartNumber: row['episode_start_number'] as int? ?? 1,
calEpisodeNumberFromOne:
int2Bool(row['cal_episode_number_from_one'] as int?),
animeDesc: row['anime_desc'] as String? ?? "",
animeCoverUrl: row['anime_cover_url'] as String? ?? "",
tagName: row['tag_name'] as String? ?? '未知',
Expand Down Expand Up @@ -591,6 +594,11 @@ class AnimeDao {
return anime;
}

/// int转bool
static bool int2Bool(int? val) {
return val == null || val == 0 ? false : true;
}

/// 转义后,单个单引号会变为两个单引号存放在数据库,查询的时候得到的是两个单引号,因此也需要恢复
static Anime _restoreEscapeAnime(Anime anime) {
anime.animeName = EscapeUtil.restoreEscapeStr(anime.animeName);
Expand Down
38 changes: 38 additions & 0 deletions lib/dao/episode_note_dao.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
import 'package:flutter_test_future/models/anime.dart';
import 'package:flutter_test_future/models/enum/note_type.dart';
import 'package:flutter_test_future/utils/sqlite_util.dart';

class EpisodeNoteDao {
/// 获取最近创建笔记的动漫
static getAnimesRecentlyCreateNote({NoteType? noteType}) async {
String whereSql = '';
switch (noteType) {
case NoteType.episode:
whereSql = 'where episode_number > 0';
break;
case NoteType.rate:
whereSql = 'where episode_number = 0';
break;
default:
}

final rows = await SqliteUtil.database.rawQuery('''
select distinct episode_note.anime_id from episode_note
$whereSql
order by episode_note.note_id desc
''');
List<Anime> animes = [];

for (final row in rows) {
int? animeId = row['anime_id'] as int?;
if (animeId == null) continue;

final anime = await SqliteUtil.getAnimeByAnimeId(animeId);
if (anime.isCollected()) {
animes.add(anime);
}
}

return animes;
}
}
12 changes: 7 additions & 5 deletions lib/dao/history_dao.dart
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import 'package:flutter_test_future/dao/anime_dao.dart';
import 'package:flutter_test_future/utils/episode.dart';
import 'package:flutter_test_future/utils/log.dart';

import '../models/anime.dart';
Expand Down Expand Up @@ -39,7 +40,7 @@ class HistoryDao {

static _getHistoryRecordsByDate(String date) async {
var list = await SqliteUtil.database.rawQuery('''
select distinct anime.anime_id, anime.anime_name, anime.anime_cover_url, anime.episode_start_number
select distinct anime.anime_id, anime.anime_name, anime.anime_cover_url, anime.episode_start_number, anime.cal_episode_number_from_one
from history, anime
where date like '$date%' and history.anime_id = anime.anime_id
order by date desc; -- 倒序
Expand Down Expand Up @@ -91,10 +92,11 @@ class HistoryDao {
int endEpisodeNumber = list[0]['end'] as int;
// Log.info("$date: [$startEpisodeNumber-$endEpisodeNumber]");
AnimeHistoryRecord record = AnimeHistoryRecord(
anime,
reviewNumber,
anime.episodeStartNumber - 1 + startEpisodeNumber,
anime.episodeStartNumber - 1 + endEpisodeNumber);
anime,
reviewNumber,
EpisodeUtil.getFixedEpisodeNumber(anime, startEpisodeNumber),
EpisodeUtil.getFixedEpisodeNumber(anime, endEpisodeNumber),
);
return record;
}

Expand Down
37 changes: 30 additions & 7 deletions lib/dao/note_dao.dart
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import 'package:flutter_test_future/dao/anime_dao.dart';
import 'package:flutter_test_future/models/note.dart';
import 'package:flutter_test_future/models/params/page_params.dart';
import 'package:flutter_test_future/utils/episode.dart';
import 'package:flutter_test_future/utils/sqlite_util.dart';
import 'package:flutter_test_future/utils/log.dart';
import 'package:flutter_test_future/utils/time_util.dart';
Expand Down Expand Up @@ -37,12 +38,14 @@ class NoteDao {

// 所有评价列表。分页
static Future<List<Note>> getRateNotes(
{required PageParams pageParams, required NoteFilter noteFilter}) async {
{required PageParams pageParams, NoteFilter? noteFilter}) async {
Log.info("sql: getRateNotes");
List<Note> rateNotes = [];

int? animeId = noteFilter?.animeId;
List<Map<String, Object?>> list = await database.rawQuery('''
select anime_id, note_id, note_content, create_time, update_time from episode_note
where episode_number = 0 order by create_time desc limit ${pageParams.pageSize} offset ${pageParams.getOffset()};
where ${animeId != null ? 'anime_id=$animeId and' : ''} episode_number = 0 order by create_time desc limit ${pageParams.pageSize} offset ${pageParams.getOffset()};
''');
for (Map row in list) {
rateNotes.add(await row2bean(row, searchAnime: true));
Expand Down Expand Up @@ -297,7 +300,7 @@ class NoteDao {
Episode episode = Episode(
item['episode_number'] as int, item['review_number'] as int,
dateTime: item['date'] as String,
startNumber: anime.episodeStartNumber);
startNumber: EpisodeUtil.getFakeEpisodeStartNumber(anime));
List<RelativeLocalImage> relativeLocalImages =
await getRelativeLocalImgsByNoteId(item['note_id'] as int);
Note episodeNote = Note(
Expand Down Expand Up @@ -344,19 +347,39 @@ class NoteDao {
static Future<int> getEpisodeNoteTotal() async {
Log.info('sql: getEpisodeNoteTotal');

var cols = await database.rawQuery('''
var rows = await database.rawQuery('''
select count(note_id) total from episode_note where episode_number > 0;
''');
return cols.first['total'] as int;
return rows.first['total'] as int;
}

/// 非空的笔记数量
static Future<int> getNotEmptyEpisodeNoteTotal() async {
Log.info('sql: getEpisodeNoteTotal');

// 内容不为空的笔记数量
final rows1 = await database.rawQuery('''
select count(note_id) total from episode_note where episode_number > 0 and length(note_content) != 0;
''');
int notEmptyContentNoteCnt = rows1.first['total'] as int;

// 内容为空,但添加了图片的笔记数量
final rows2 = await database.rawQuery('''
select count(distinct note_id) total from image where note_id in
(select note_id from episode_note where episode_number > 0 and length(note_content) = 0)
''');
int emptyContentButExistImageNoteCnt = rows2.first['total'] as int;

return notEmptyContentNoteCnt + emptyContentButExistImageNoteCnt;
}

/// 评价数量
static Future<int> getRateNoteTotal() async {
Log.info('sql: getRateNoteTotal');

var cols = await database.rawQuery('''
var rows = await database.rawQuery('''
select count(note_id) total from episode_note where episode_number == 0;
''');
return cols.first['total'] as int;
return rows.first['total'] as int;
}
}
39 changes: 25 additions & 14 deletions lib/models/anime.dart
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ class Anime {
String animeName;
int animeEpisodeCnt; // 总集数
int episodeStartNumber; // 起始集
bool calEpisodeNumberFromOne; // 从第1集开始计算
String tagName;
String animeDesc;
String animeCoverUrl;
Expand Down Expand Up @@ -55,24 +56,11 @@ class Anime {
this.climbFinished = false,
this.tempInfo,
this.hasJoinedSeries = false,
this.calEpisodeNumberFromOne = false,
});

@override
String toString() {
return "Anime=[animeId=$animeId, animeName=$animeName, "
"animeEpisodeCnt=$animeEpisodeCnt, episodeStartNumber=$episodeStartNumber, tagName=$tagName, "
"checkedEpisodeCnt=$checkedEpisodeCnt, animeCoverUrl=$animeCoverUrl, "
"animeUrl=$animeUrl, premiereTime=$premiereTime, "
"animeDesc=${reduceStr(animeDesc)}, playStatus=$playStatus, "
"category=$category, area=$area, rate=$rate]";
}

DateTime? get premiereDateTime => DateTime.tryParse(premiereTime);

String reduceStr(String str) {
return str.length > 15 ? str.substring(0, 15) : str;
}

String getAnimeInfoFirstLine() {
var list = [];
if (area.isNotEmpty) {
Expand Down Expand Up @@ -151,6 +139,7 @@ class Anime {
String? animeName,
int? animeEpisodeCnt,
int? episodeStartNumber,
bool? calEpisodeNumberFromOne,
String? tagName,
String? animeDesc,
String? animeCoverUrl,
Expand All @@ -167,12 +156,17 @@ class Anime {
String? playStatus,
String? productionCompany,
String? officialSite,
bool? climbFinished,
String? tempInfo,
bool? hasJoinedSeries,
}) {
return Anime(
animeId: animeId ?? this.animeId,
animeName: animeName ?? this.animeName,
animeEpisodeCnt: animeEpisodeCnt ?? this.animeEpisodeCnt,
episodeStartNumber: episodeStartNumber ?? this.episodeStartNumber,
calEpisodeNumberFromOne:
calEpisodeNumberFromOne ?? this.calEpisodeNumberFromOne,
tagName: tagName ?? this.tagName,
animeDesc: animeDesc ?? this.animeDesc,
animeCoverUrl: animeCoverUrl ?? this.animeCoverUrl,
Expand All @@ -189,6 +183,23 @@ class Anime {
playStatus: playStatus ?? this.playStatus,
productionCompany: productionCompany ?? this.productionCompany,
officialSite: officialSite ?? this.officialSite,
climbFinished: climbFinished ?? this.climbFinished,
tempInfo: tempInfo ?? this.tempInfo,
hasJoinedSeries: hasJoinedSeries ?? this.hasJoinedSeries,
);
}

@override
String toString() {
return "Anime=[animeId=$animeId, animeName=$animeName, "
"animeEpisodeCnt=$animeEpisodeCnt, episodeStartNumber=$episodeStartNumber, tagName=$tagName, "
"checkedEpisodeCnt=$checkedEpisodeCnt, animeCoverUrl=$animeCoverUrl, "
"animeUrl=$animeUrl, premiereTime=$premiereTime, "
"animeDesc=${reduceStr(animeDesc)}, playStatus=$playStatus, "
"category=$category, area=$area, rate=$rate]";
}

String reduceStr(String str) {
return str.length > 15 ? str.substring(0, 15) : str;
}
}
11 changes: 11 additions & 0 deletions lib/models/anime_episode_info.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
class AnimeEpisodeInfo {
int totalCnt; // 总集数
int startNumber; // 起始集
bool calNumberFromOne; // 是否从1开始计算

AnimeEpisodeInfo({
this.totalCnt = 0,
this.startNumber = 1,
this.calNumberFromOne = false,
});
}
7 changes: 7 additions & 0 deletions lib/models/enum/note_type.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
enum NoteType {
episode('笔记'),
rate('评价');

final String title;
const NoteType(this.title);
}
11 changes: 7 additions & 4 deletions lib/models/note_filter.dart
Original file line number Diff line number Diff line change
@@ -1,14 +1,17 @@
class NoteFilter {
int? animeId;
String animeNameKeyword;
String noteContentKeyword;

NoteFilter({this.animeNameKeyword = "", this.noteContentKeyword = ""});
NoteFilter(
{this.animeNameKeyword = "", this.noteContentKeyword = "", this.animeId});

bool hasFilter() =>
animeNameKeyword.isNotEmpty || noteContentKeyword.isNotEmpty;

String get valueKeyStr => toString();

@override
String toString() {
return "NoteFilter[animeNameKeyword=$animeNameKeyword, noteContentKeyword=$noteContentKeyword]";
}
String toString() =>
'NoteFilter(animeId: $animeId, animeNameKeyword: $animeNameKeyword, noteContentKeyword: $noteContentKeyword)';
}
3 changes: 2 additions & 1 deletion lib/pages/anime_collection/anime_list_page.dart
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ import 'package:flutter_test_future/utils/sp_util.dart';
import 'package:flutter_test_future/utils/sqlite_util.dart';
import 'package:flutter_test_future/values/values.dart';
import 'package:flutter_test_future/widgets/common_scaffold_body.dart';
import 'package:flutter_test_future/widgets/common_tab_bar_view.dart';
import 'package:get/get.dart';
import 'package:flutter_test_future/utils/log.dart';

Expand Down Expand Up @@ -99,7 +100,7 @@ class _AnimeListPageState extends State<AnimeListPage> {
),
body: CommonScaffoldBody(
child: loadOk
? TabBarView(
? CommonTabBarView(
controller: _tabController,
children: _getAnimesPlus(),
)
Expand Down
26 changes: 6 additions & 20 deletions lib/pages/anime_detail/controllers/anime_controller.dart
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import 'package:flutter_test_future/dao/anime_label_dao.dart';
import 'package:flutter_test_future/dao/episode_desc_dao.dart';
import 'package:flutter_test_future/dao/note_dao.dart';
import 'package:flutter_test_future/models/anime.dart';
import 'package:flutter_test_future/models/anime_episode_info.dart';
import 'package:flutter_test_future/models/episode.dart';
import 'package:flutter_test_future/models/label.dart';
import 'package:flutter_test_future/pages/anime_detail/widgets/episode_form.dart';
Expand Down Expand Up @@ -385,7 +386,7 @@ class AnimeController extends GetxController {
void showDialogModEpisodeCntAndStartNumber(BuildContext context) async {
if (!isCollected) return;

Map<String, int>? result = await showDialog(
AnimeEpisodeInfo? result = await showDialog(
context: context,
builder: (context) => EpisodeForm(anime: anime),
);
Expand All @@ -395,26 +396,11 @@ class AnimeController extends GetxController {
return;
}

int? episodeCnt = result['episodeCnt'];
int? episodeStartNumber = result['episodeStartNumber'];

if (episodeCnt == null || episodeStartNumber == null) {
Log.error("没有收到episodeCnt或episodeStartNumber值");
return;
}

if (episodeCnt == anime.animeEpisodeCnt &&
episodeStartNumber == anime.episodeStartNumber) {
Log.info("没有修改,直接返回");
return;
}

AnimeDao.updateEpisodeCntAndStartNumberByAnimeId(
anime.animeId, episodeCnt, episodeStartNumber)
.then((value) {
AnimeDao.updateEpisodeInfoByAnimeId(anime.animeId, result).then((value) {
// 修改数据
anime.animeEpisodeCnt = episodeCnt;
anime.episodeStartNumber = episodeStartNumber;
anime.animeEpisodeCnt = result.totalCnt;
anime.episodeStartNumber = result.startNumber;
anime.calEpisodeNumberFromOne = result.calNumberFromOne;
// 重绘
updateAnimeInfo(); // 重绘信息行中显示的集数
loadEpisode(); // 重绘集信息
Expand Down
Loading

0 comments on commit 0aa88df

Please sign in to comment.