Mercurial > minori
comparison src/gui/pages/anime_list.cc @ 118:39521c47c7a3
*: another huge megacommit, SORRY
The torrents page works a lot better now
Added the edit option to the anime list right click menu
Vectorized currently playing files
Available player and extensions are now loaded at runtime
from files in (dotpath)/players.json and (dotpath)/extensions.json
These paths are not permanent and will likely be moved to
(dotpath)/recognition
...
...
...
author | Paper <mrpapersonic@gmail.com> |
---|---|
date | Tue, 07 Nov 2023 23:40:54 -0500 |
parents | ab191e28e69d |
children | bc8d2ccff09c |
comparison
equal
deleted
inserted
replaced
117:2c1b6782e1d0 | 118:39521c47c7a3 |
---|---|
106 case Qt::DisplayRole: | 106 case Qt::DisplayRole: |
107 switch (index.column()) { | 107 switch (index.column()) { |
108 case AL_TITLE: return QString::fromUtf8(list[index.row()].GetUserPreferredTitle().c_str()); | 108 case AL_TITLE: return QString::fromUtf8(list[index.row()].GetUserPreferredTitle().c_str()); |
109 case AL_PROGRESS: | 109 case AL_PROGRESS: |
110 return QString::number(list[index.row()].GetUserProgress()) + "/" + | 110 return QString::number(list[index.row()].GetUserProgress()) + "/" + |
111 QString::number(list[index.row()].GetEpisodes()); | 111 QString::number(list[index.row()].GetEpisodes()); |
112 case AL_EPISODES: return list[index.row()].GetEpisodes(); | 112 case AL_EPISODES: return list[index.row()].GetEpisodes(); |
113 case AL_SCORE: return list[index.row()].GetUserScore(); | 113 case AL_SCORE: return list[index.row()].GetUserScore(); |
114 case AL_TYPE: return Strings::ToQString(Translate::ToString(list[index.row()].GetFormat())); | 114 case AL_TYPE: return Strings::ToQString(Translate::ToString(list[index.row()].GetFormat())); |
115 case AL_SEASON: | 115 case AL_SEASON: |
116 return Strings::ToQString(Translate::ToString(list[index.row()].GetSeason())) + " " + | 116 return Strings::ToQString(Translate::ToString(list[index.row()].GetSeason())) + " " + |
117 QString::number(list[index.row()].GetAirDate().GetYear()); | 117 QString::number(list[index.row()].GetAirDate().GetYear()); |
118 case AL_AVG_SCORE: return QString::number(list[index.row()].GetAudienceScore()) + "%"; | 118 case AL_AVG_SCORE: return QString::number(list[index.row()].GetAudienceScore()) + "%"; |
119 case AL_STARTED: return list[index.row()].GetUserDateStarted().GetAsQDate(); | 119 case AL_STARTED: return list[index.row()].GetUserDateStarted().GetAsQDate(); |
120 case AL_COMPLETED: return list[index.row()].GetUserDateCompleted().GetAsQDate(); | 120 case AL_COMPLETED: return list[index.row()].GetUserDateCompleted().GetAsQDate(); |
121 case AL_UPDATED: { | 121 case AL_UPDATED: { |
122 if (list[index.row()].GetUserTimeUpdated() == 0) | 122 if (list[index.row()].GetUserTimeUpdated() == 0) |
161 Anime::Anime* AnimeListPageModel::GetAnimeFromIndex(QModelIndex index) { | 161 Anime::Anime* AnimeListPageModel::GetAnimeFromIndex(QModelIndex index) { |
162 return &list.at(index.row()); | 162 return &list.at(index.row()); |
163 } | 163 } |
164 | 164 |
165 void AnimeListPageModel::RefreshList() { | 165 void AnimeListPageModel::RefreshList() { |
166 bool has_children = !!rowCount(index(0)); | 166 /* equivalent to hasChildren()... */ |
167 if (!has_children) { | 167 if (!rowCount(index(0))) { |
168 beginInsertRows(QModelIndex(), 0, 0); | 168 beginInsertRows(QModelIndex(), 0, 0); |
169 endInsertRows(); | 169 endInsertRows(); |
170 } | 170 } |
171 | 171 |
172 beginResetModel(); | 172 beginResetModel(); |
231 | 231 |
232 for (int i = 0; i < AnimeListPageModel::NB_COLUMNS; i++) { | 232 for (int i = 0; i < AnimeListPageModel::NB_COLUMNS; i++) { |
233 if (i == AnimeListPageModel::AL_TITLE) | 233 if (i == AnimeListPageModel::AL_TITLE) |
234 continue; | 234 continue; |
235 const auto column_name = | 235 const auto column_name = |
236 sort_models[tab_bar->currentIndex()]->headerData(i, Qt::Horizontal, Qt::DisplayRole).toString(); | 236 sort_models[tab_bar->currentIndex()]->headerData(i, Qt::Horizontal, Qt::DisplayRole).toString(); |
237 | |
237 QAction* action = menu->addAction(column_name, this, [this, i](const bool checked) { | 238 QAction* action = menu->addAction(column_name, this, [this, i](const bool checked) { |
238 if (!checked && (VisibleColumnsCount() <= 1)) | 239 if (!checked && (VisibleColumnsCount() <= 1)) |
239 return; | 240 return; |
240 | 241 |
241 tree_view->setColumnHidden(i, !checked); | 242 tree_view->setColumnHidden(i, !checked); |
243 if (checked && (tree_view->columnWidth(i) <= 5)) | 244 if (checked && (tree_view->columnWidth(i) <= 5)) |
244 tree_view->resizeColumnToContents(i); | 245 tree_view->resizeColumnToContents(i); |
245 | 246 |
246 // SaveSettings(); | 247 // SaveSettings(); |
247 }); | 248 }); |
249 | |
248 action->setCheckable(true); | 250 action->setCheckable(true); |
249 action->setChecked(!tree_view->isColumnHidden(i)); | 251 action->setChecked(!tree_view->isColumnHidden(i)); |
250 } | 252 } |
251 | 253 |
252 menu->addSeparator(); | 254 menu->addSeparator(); |
264 menu->setAttribute(Qt::WA_DeleteOnClose); | 266 menu->setAttribute(Qt::WA_DeleteOnClose); |
265 menu->setTitle(tr("Column visibility")); | 267 menu->setTitle(tr("Column visibility")); |
266 menu->setToolTipsVisible(true); | 268 menu->setToolTipsVisible(true); |
267 | 269 |
268 AnimeListPageModel* source_model = | 270 AnimeListPageModel* source_model = |
269 reinterpret_cast<AnimeListPageModel*>(sort_models[tab_bar->currentIndex()]->sourceModel()); | 271 reinterpret_cast<AnimeListPageModel*>(sort_models[tab_bar->currentIndex()]->sourceModel()); |
270 const QItemSelection selection = | 272 const QItemSelection selection = |
271 sort_models[tab_bar->currentIndex()]->mapSelectionToSource(tree_view->selectionModel()->selection()); | 273 sort_models[tab_bar->currentIndex()]->mapSelectionToSource(tree_view->selectionModel()->selection()); |
272 | 274 |
273 std::set<Anime::Anime*> animes; | 275 std::set<Anime::Anime*> animes; |
274 for (const auto& index : selection.indexes()) { | 276 for (const auto& index : selection.indexes()) { |
275 if (!index.isValid()) | 277 if (!index.isValid()) |
276 continue; | 278 continue; |
279 animes.insert(anime); | 281 animes.insert(anime); |
280 } | 282 } |
281 | 283 |
282 menu->addAction(tr("Information"), [this, animes] { | 284 menu->addAction(tr("Information"), [this, animes] { |
283 for (auto& anime : animes) { | 285 for (auto& anime : animes) { |
284 InformationDialog* dialog = new InformationDialog( | 286 InformationDialog* dialog = new InformationDialog(*anime, [this, anime] { |
285 *anime, [this, anime] { UpdateAnime(anime->GetId()); }, this); | 287 UpdateAnime(anime->GetId()); |
288 }, InformationDialog::PAGE_MAIN_INFO, this); | |
286 | 289 |
287 dialog->show(); | 290 dialog->show(); |
288 dialog->raise(); | 291 dialog->raise(); |
289 dialog->activateWindow(); | 292 dialog->activateWindow(); |
290 } | 293 } |
291 }); | 294 }); |
292 menu->addSeparator(); | 295 menu->addSeparator(); |
296 menu->addAction(tr("Edit"), [this, animes] { | |
297 for (auto& anime : animes) { | |
298 InformationDialog* dialog = new InformationDialog(*anime, [this, anime] { | |
299 UpdateAnime(anime->GetId()); | |
300 }, InformationDialog::PAGE_MY_LIST, this); | |
301 | |
302 dialog->show(); | |
303 dialog->raise(); | |
304 dialog->activateWindow(); | |
305 } | |
306 }); | |
293 menu->addAction(tr("Delete from list..."), [this, animes] { | 307 menu->addAction(tr("Delete from list..."), [this, animes] { |
294 for (auto& anime : animes) { | 308 for (auto& anime : animes) { |
295 RemoveAnime(anime->GetId()); | 309 RemoveAnime(anime->GetId()); |
296 } | 310 } |
297 }); | 311 }); |
299 } | 313 } |
300 | 314 |
301 void AnimeListPage::ItemDoubleClicked() { | 315 void AnimeListPage::ItemDoubleClicked() { |
302 /* throw out any other garbage */ | 316 /* throw out any other garbage */ |
303 const QItemSelection selection = | 317 const QItemSelection selection = |
304 sort_models[tab_bar->currentIndex()]->mapSelectionToSource(tree_view->selectionModel()->selection()); | 318 sort_models[tab_bar->currentIndex()]->mapSelectionToSource(tree_view->selectionModel()->selection()); |
305 if (!selection.indexes().first().isValid()) { | 319 if (!selection.indexes().first().isValid()) { |
306 return; | 320 return; |
307 } | 321 } |
308 | 322 |
309 AnimeListPageModel* source_model = | 323 AnimeListPageModel* source_model = |
310 reinterpret_cast<AnimeListPageModel*>(sort_models[tab_bar->currentIndex()]->sourceModel()); | 324 reinterpret_cast<AnimeListPageModel*>(sort_models[tab_bar->currentIndex()]->sourceModel()); |
311 | 325 |
312 const QModelIndex index = source_model->index(selection.indexes().first().row()); | 326 const QModelIndex index = source_model->index(selection.indexes().first().row()); |
313 Anime::Anime* anime = source_model->GetAnimeFromIndex(index); | 327 Anime::Anime* anime = source_model->GetAnimeFromIndex(index); |
314 | 328 |
315 InformationDialog* dialog = new InformationDialog( | 329 InformationDialog* dialog = new InformationDialog(*anime, [this, anime] { |
316 *anime, [this, anime] { UpdateAnime(anime->GetId()); }, this); | 330 UpdateAnime(anime->GetId()); |
331 }, InformationDialog::PAGE_MAIN_INFO, this); | |
317 | 332 |
318 dialog->show(); | 333 dialog->show(); |
319 dialog->raise(); | 334 dialog->raise(); |
320 dialog->activateWindow(); | 335 dialog->activateWindow(); |
321 } | 336 } |
326 } | 341 } |
327 | 342 |
328 void AnimeListPage::RefreshTabs() { | 343 void AnimeListPage::RefreshTabs() { |
329 for (unsigned int i = 0; i < sort_models.size(); i++) | 344 for (unsigned int i = 0; i < sort_models.size(); i++) |
330 tab_bar->setTabText(i, Strings::ToQString(Translate::ToString(Anime::ListStatuses[i])) + " (" + | 345 tab_bar->setTabText(i, Strings::ToQString(Translate::ToString(Anime::ListStatuses[i])) + " (" + |
331 QString::number(Anime::db.GetListsAnimeAmount(Anime::ListStatuses[i])) + ")"); | 346 QString::number(Anime::db.GetListsAnimeAmount(Anime::ListStatuses[i])) + ")"); |
332 } | 347 } |
333 | 348 |
334 void AnimeListPage::Refresh() { | 349 void AnimeListPage::Refresh() { |
335 RefreshList(); | 350 RefreshList(); |
336 RefreshTabs(); | 351 RefreshTabs(); |
421 tree_view->setContextMenuPolicy(Qt::CustomContextMenu); | 436 tree_view->setContextMenuPolicy(Qt::CustomContextMenu); |
422 tree_view->setFrameShape(QFrame::NoFrame); | 437 tree_view->setFrameShape(QFrame::NoFrame); |
423 | 438 |
424 for (unsigned int i = 0; i < sort_models.size(); i++) { | 439 for (unsigned int i = 0; i < sort_models.size(); i++) { |
425 tab_bar->addTab(Strings::ToQString(Translate::ToString(Anime::ListStatuses[i])) + " (" + | 440 tab_bar->addTab(Strings::ToQString(Translate::ToString(Anime::ListStatuses[i])) + " (" + |
426 QString::number(Anime::db.GetListsAnimeAmount(Anime::ListStatuses[i])) + ")"); | 441 QString::number(Anime::db.GetListsAnimeAmount(Anime::ListStatuses[i])) + ")"); |
427 sort_models[i] = new AnimeListPageSortFilter(tree_view); | 442 sort_models[i] = new AnimeListPageSortFilter(tree_view); |
428 sort_models[i]->setSourceModel(new AnimeListPageModel(this, Anime::ListStatuses[i])); | 443 sort_models[i]->setSourceModel(new AnimeListPageModel(this, Anime::ListStatuses[i])); |
429 sort_models[i]->setSortRole(Qt::UserRole); | 444 sort_models[i]->setSortRole(Qt::UserRole); |
430 sort_models[i]->setSortCaseSensitivity(Qt::CaseInsensitive); | 445 sort_models[i]->setSortCaseSensitivity(Qt::CaseInsensitive); |
431 } | 446 } |
439 connect(tree_view, &QAbstractItemView::doubleClicked, this, &AnimeListPage::ItemDoubleClicked); | 454 connect(tree_view, &QAbstractItemView::doubleClicked, this, &AnimeListPage::ItemDoubleClicked); |
440 connect(tree_view, &QWidget::customContextMenuRequested, this, &AnimeListPage::DisplayListMenu); | 455 connect(tree_view, &QWidget::customContextMenuRequested, this, &AnimeListPage::DisplayListMenu); |
441 | 456 |
442 /* Enter & return keys */ | 457 /* Enter & return keys */ |
443 connect(new QShortcut(Qt::Key_Return, tree_view, nullptr, nullptr, Qt::WidgetShortcut), &QShortcut::activated, this, | 458 connect(new QShortcut(Qt::Key_Return, tree_view, nullptr, nullptr, Qt::WidgetShortcut), &QShortcut::activated, this, |
444 &AnimeListPage::ItemDoubleClicked); | 459 &AnimeListPage::ItemDoubleClicked); |
445 | 460 |
446 connect(new QShortcut(Qt::Key_Enter, tree_view, nullptr, nullptr, Qt::WidgetShortcut), &QShortcut::activated, this, | 461 connect(new QShortcut(Qt::Key_Enter, tree_view, nullptr, nullptr, Qt::WidgetShortcut), &QShortcut::activated, this, |
447 &AnimeListPage::ItemDoubleClicked); | 462 &AnimeListPage::ItemDoubleClicked); |
448 | 463 |
449 tree_view->header()->setStretchLastSection(false); | 464 tree_view->header()->setStretchLastSection(false); |
450 tree_view->header()->setContextMenuPolicy(Qt::CustomContextMenu); | 465 tree_view->header()->setContextMenuPolicy(Qt::CustomContextMenu); |
451 connect(tree_view->header(), &QWidget::customContextMenuRequested, this, &AnimeListPage::DisplayColumnHeaderMenu); | 466 connect(tree_view->header(), &QWidget::customContextMenuRequested, this, &AnimeListPage::DisplayColumnHeaderMenu); |
452 | 467 |