Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Light refactoring in ContentManager and ContentManagerModel #1049

Merged
merged 9 commits into from
Mar 8, 2024
187 changes: 79 additions & 108 deletions src/contentmanager.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,12 @@
namespace
{


SettingsManager* getSettingsManager()
{
return KiwixApp::instance()->getSettingsManager();
}

class ContentManagerError : public std::runtime_error
{
public:
Expand Down Expand Up @@ -108,9 +114,9 @@ ContentManager::ContentManager(Library* library, kiwix::Downloader* downloader,
treeView->setColumnWidth(5, 120);
// TODO: set width for all columns based on viewport

setCurrentLanguage(KiwixApp::instance()->getSettingsManager()->getLanguageList());
setCurrentCategoryFilter(KiwixApp::instance()->getSettingsManager()->getCategoryList());
setCurrentContentTypeFilter(KiwixApp::instance()->getSettingsManager()->getContentType());
setCurrentLanguage(getSettingsManager()->getLanguageList());
setCurrentCategoryFilter(getSettingsManager()->getCategoryList());
setCurrentContentTypeFilter(getSettingsManager()->getContentType());
connect(mp_library, &Library::booksChanged, this, [=]() {emit(this->booksChanged());});
connect(this, &ContentManager::filterParamsChanged, this, &ContentManager::updateLibrary);
connect(this, &ContentManager::booksChanged, this, [=]() {
Expand Down Expand Up @@ -171,7 +177,7 @@ void ContentManager::onCustomContextMenu(const QPoint &point)
contextMenu.addAction(&menuCancelBook);
} else {
try {
const auto book = KiwixApp::instance()->getLibrary()->getBookById(id);
const auto book = mp_library->getBookById(id);
auto bookPath = QString::fromStdString(book.getPath());
contextMenu.addAction(&menuOpenBook);
contextMenu.addAction(&menuDeleteBook);
Expand Down Expand Up @@ -259,7 +265,56 @@ void ContentManager::setLanguages()
m_remoteLibraryManager.getLanguagesFromOpds();
}

#define ADD_V(KEY, METH) {if(key==KEY) values.insert(key, QString::fromStdString((b->METH())));}
namespace
{

QString getBookTags(const kiwix::Book& b)
{
QStringList tagList = QString::fromStdString(b.getTags()).split(';');
QMap<QString, bool> displayTagMap;
for(auto tag: tagList) {
if (tag[0] == '_') {
auto splitTag = tag.split(":");
displayTagMap[splitTag[0]] = splitTag[1] == "yes" ? true:false;
}
}
QStringList displayTagList;
if (displayTagMap["_videos"]) displayTagList << QObject::tr("Videos");
if (displayTagMap["_pictures"]) displayTagList << QObject::tr("Pictures");
if (!displayTagMap["_details"]) displayTagList << QObject::tr("Introduction only");
return displayTagList.join(", ");
}

QString getFaviconUrl(const kiwix::Book& b)
{
std::string url;
try {
auto item = b.getIllustration(48);
url = item->url;
} catch (...) {
}
return QString::fromStdString(url);
}

QVariant getBookAttribute(const kiwix::Book& b, const QString& a)
{
if ( a == "id" ) return QString::fromStdString(b.getId());
if ( a == "path" ) return QString::fromStdString(b.getPath());
if ( a == "title" ) return QString::fromStdString(b.getTitle());
if ( a == "description" ) return QString::fromStdString(b.getDescription());
if ( a == "date" ) return QString::fromStdString(b.getDate());
if ( a == "url" ) return QString::fromStdString(b.getUrl());
if ( a == "name" ) return QString::fromStdString(b.getName());
if ( a == "downloadId" ) return QString::fromStdString(b.getDownloadId());
if ( a == "faviconUrl") return getFaviconUrl(b);
if ( a == "size" ) return QString::number(b.getSize());
if ( a == "tags" ) return getBookTags(b);

return QVariant();
}

} // unnamed namespace

ContentManager::BookInfo ContentManager::getBookInfos(QString id, const QStringList &keys)
{
BookInfo values;
Expand All @@ -274,68 +329,12 @@ ContentManager::BookInfo ContentManager::getBookInfos(QString id, const QStringL
}
}();

if (nullptr == b){
for(auto& key:keys) {
(void) key;
values.insert(key, "");
}
return values;
}

for(auto& key: keys){
ADD_V("id", getId);
ADD_V("path", getPath);
ADD_V("title", getTitle);
ADD_V("description", getDescription);
ADD_V("date", getDate);
ADD_V("url", getUrl);
ADD_V("name", getName);
ADD_V("downloadId", getDownloadId);
if (key == "faviconMimeType") {
std::string mimeType;
try {
auto item = b->getIllustration(48);
mimeType = item->mimeType;
} catch (...) {
const kiwix::Book::Illustration tempIllustration;
mimeType = tempIllustration.mimeType;
}
values.insert(key, QString::fromStdString(mimeType));
}
if (key == "faviconUrl") {
std::string url;
try {
auto item = b->getIllustration(48);
url = item->url;
} catch (...) {
const kiwix::Book::Illustration tempIllustration;
url = tempIllustration.url;
}
values.insert(key, QString::fromStdString(url));
}
if (key == "size") {
values.insert(key, QString::number(b->getSize()));
}
if (key == "tags") {
QStringList tagList = QString::fromStdString(b->getTags()).split(';');
QMap<QString, bool> displayTagMap;
for(auto tag: tagList) {
if (tag[0] == '_') {
auto splitTag = tag.split(":");
displayTagMap[splitTag[0]] = splitTag[1] == "yes" ? true:false;
}
}
QStringList displayTagList;
if (displayTagMap["_videos"]) displayTagList << tr("Videos");
if (displayTagMap["_pictures"]) displayTagList << tr("Pictures");
if (!displayTagMap["_details"]) displayTagList << tr("Introduction only");
QString s = displayTagList.join(", ");
values.insert(key, s);
}
values.insert(key, b ? getBookAttribute(*b, key) : "");
}

return values;
}
#undef ADD_V

void ContentManager::openBookWithIndex(const QModelIndex &index)
{
Expand All @@ -344,7 +343,7 @@ void ContentManager::openBookWithIndex(const QModelIndex &index)
auto bookNode = static_cast<Node*>(index.internalPointer());
bookId = bookNode->getBookId();
// check if the book is available in local library, will throw std::out_of_range if it isn't.
KiwixApp::instance()->getLibrary()->getBookById(bookId);
mp_library->getBookById(bookId);
if (getBookInfos(bookId, {"downloadId"})["downloadId"] != "")
return;
openBook(bookId);
Expand Down Expand Up @@ -386,19 +385,6 @@ QString downloadStatus2QString(kiwix::Download::StatusResult status)
}
}

QString getDownloadInfo(const kiwix::Download& d, const QString& k)
{
if (k == "id") return QString::fromStdString(d.getDid());
if (k == "path") return QString::fromStdString(d.getPath());
if (k == "status") return downloadStatus2QString(d.getStatus());
if (k == "followedBy") return QString::fromStdString(d.getFollowedBy());
if (k == "totalLength") return QString::number(d.getTotalLength());
if (k == "downloadSpeed") return QString::number(d.getDownloadSpeed());
if (k == "verifiedLength") return QString::number(d.getVerifiedLength());
if (k == "completedLength") return QString::number(d.getCompletedLength());
return "";
}

} // unnamed namespace

void ContentManager::downloadStarted(const kiwix::Book& book, const std::string& downloadId)
Expand Down Expand Up @@ -445,38 +431,32 @@ void ContentManager::downloadCompleted(QString bookId, QString path)
}
}

DownloadInfo ContentManager::getDownloadInfo(QString bookId, const QStringList &keys) const
DownloadInfo ContentManager::getDownloadInfo(QString bookId) const
{
DownloadInfo values;
if (!mp_downloader) {
for(auto& key: keys) {
values.insert(key, "");
}
return values;
}

auto& b = mp_library->getBookById(bookId);
std::shared_ptr<kiwix::Download> d;
try {
d = mp_downloader->getDownload(b.getDownloadId());
} catch(...) {
return values;
return {};
}

d->updateStatus(true);

for(auto& key: keys){
values.insert(key, ::getDownloadInfo(*d, key));
}

return values;
return {
{ "status" , downloadStatus2QString(d->getStatus()) },
{ "completedLength" , QString::number(d->getCompletedLength()) },
{ "totalLength" , QString::number(d->getTotalLength()) },
{ "downloadSpeed" , QString::number(d->getDownloadSpeed()) },
{ "path" , QString::fromStdString(d->getPath()) }
};
}

void ContentManager::updateDownload(QString bookId)
{
const auto downloadState = m_downloads.value(bookId);
if ( downloadState && !downloadState->paused ) {
const auto downloadInfo = getDownloadInfo(bookId, {"status", "completedLength", "totalLength", "downloadSpeed", "path"});
const auto downloadInfo = getDownloadInfo(bookId);

if ( downloadInfo.isEmpty() ) {
downloadCancelled(bookId);
Expand Down Expand Up @@ -534,7 +514,7 @@ const kiwix::Book& ContentManager::getRemoteOrLocalBook(const QString &id)

std::string ContentManager::startDownload(const kiwix::Book& book)
{
auto downloadPath = KiwixApp::instance()->getSettingsManager()->getDownloadDir();
auto downloadPath = getSettingsManager()->getDownloadDir();
checkEnoughStorageAvailable(book, downloadPath);

typedef std::vector<std::pair<std::string, std::string>> DownloadOptions;
Expand Down Expand Up @@ -601,15 +581,15 @@ void ContentManager::reallyEraseBook(const QString& id, bool moveToTrash)
} else {
emit(oneBookChanged(id));
}
KiwixApp::instance()->getSettingsManager()->deleteSettings(id);
getSettingsManager()->deleteSettings(id);
emit booksChanged();
}

void ContentManager::eraseBook(const QString& id)
{
auto text = gt("delete-book-text");
#if QT_VERSION >= QT_VERSION_CHECK(5, 15, 0)
const auto moveToTrash = KiwixApp::instance()->getSettingsManager()->getMoveToTrash();
const auto moveToTrash = getSettingsManager()->getMoveToTrash();
#else
const auto moveToTrash = false; // we do not support move to trash functionality for qt versions below 5.15
#endif
Expand All @@ -632,9 +612,6 @@ void ContentManager::pauseBook(const QString& id, QModelIndex index)

void ContentManager::pauseBook(const QString& id)
{
if (!mp_downloader) {
return;
}
auto& b = mp_library->getBookById(id);
auto download = mp_downloader->getDownload(b.getDownloadId());
if (download->getStatus() == kiwix::Download::K_ACTIVE) {
Expand All @@ -651,9 +628,6 @@ void ContentManager::resumeBook(const QString& id, QModelIndex index)

void ContentManager::resumeBook(const QString& id)
{
if (!mp_downloader) {
return;
}
auto& b = mp_library->getBookById(id);
auto download = mp_downloader->getDownload(b.getDownloadId());
if (download->getStatus() == kiwix::Download::K_PAUSED) {
Expand All @@ -674,9 +648,6 @@ void ContentManager::cancelBook(const QString& id, QModelIndex index)

void ContentManager::cancelBook(const QString& id)
{
if (!mp_downloader) {
return;
}
auto& b = mp_library->getBookById(id);
auto download = mp_downloader->getDownload(b.getDownloadId());
if (download->getStatus() != kiwix::Download::K_COMPLETE) {
Expand Down Expand Up @@ -712,7 +683,7 @@ void ContentManager::setCurrentLanguage(FilterList langPairList)
if (m_currentLanguage == newLanguage)
return;
m_currentLanguage = newLanguage;
KiwixApp::instance()->getSettingsManager()->setLanguage(langPairList);
getSettingsManager()->setLanguage(langPairList);
emit(currentLangChanged());
emit(filterParamsChanged());
}
Expand All @@ -727,7 +698,7 @@ void ContentManager::setCurrentCategoryFilter(FilterList categoryPairList)
if (m_categoryFilter == categoryList.join(","))
return;
m_categoryFilter = categoryList.join(",");
KiwixApp::instance()->getSettingsManager()->setCategory(categoryPairList);
getSettingsManager()->setCategory(categoryPairList);
emit(filterParamsChanged());
}

Expand All @@ -738,7 +709,7 @@ void ContentManager::setCurrentContentTypeFilter(FilterList contentTypeFiltersPa
contentTypeFilters.append(ctfPair.second);
}
m_contentTypeFilters = contentTypeFilters;
KiwixApp::instance()->getSettingsManager()->setContentType(contentTypeFiltersPairList);
getSettingsManager()->setContentType(contentTypeFiltersPairList);
emit(filterParamsChanged());
}

Expand Down
2 changes: 1 addition & 1 deletion src/contentmanager.h
Original file line number Diff line number Diff line change
Expand Up @@ -88,7 +88,7 @@ public slots:
void downloadStarted(const kiwix::Book& book, const std::string& downloadId);
void downloadCancelled(QString bookId);
void downloadCompleted(QString bookId, QString path);
DownloadInfo getDownloadInfo(QString bookId, const QStringList& keys) const;
DownloadInfo getDownloadInfo(QString bookId) const;

private: // data
Library* mp_library;
Expand Down
21 changes: 14 additions & 7 deletions src/contentmanagermodel.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -111,9 +111,8 @@ void ContentManagerModel::setBooksData(const BookInfoList& data)
emit dataChanged(QModelIndex(), QModelIndex());
}

std::shared_ptr<RowNode> ContentManagerModel::createNode(BookInfo bookItem, QMap<QString, QByteArray> iconMap) const
QByteArray ContentManagerModel::getThumbnail(const BookInfo& bookItem) const
{
const auto faviconUrl = bookItem["faviconUrl"].toString();
QString id = bookItem["id"].toString();
QByteArray bookIcon;
try {
Expand All @@ -124,10 +123,18 @@ std::shared_ptr<RowNode> ContentManagerModel::createNode(BookInfo bookItem, QMap
bookIcon = QByteArray::fromRawData(reinterpret_cast<const char*>(favicon.data()), favicon.size());
bookIcon.detach(); // deep copy
} catch (...) {
if (iconMap.contains(faviconUrl)) {
bookIcon = iconMap[faviconUrl];
const auto faviconUrl = bookItem["faviconUrl"].toString();
if (m_iconMap.contains(faviconUrl)) {
bookIcon = m_iconMap[faviconUrl];
}
}
return bookIcon;
}

std::shared_ptr<RowNode> ContentManagerModel::createNode(BookInfo bookItem) const
{
QString id = bookItem["id"].toString();
const QByteArray bookIcon = getThumbnail(bookItem);
std::weak_ptr<RowNode> weakRoot = rootNode;
auto rowNodePtr = std::shared_ptr<RowNode>(new
RowNode({bookIcon, bookItem["title"],
Expand All @@ -147,7 +154,7 @@ void ContentManagerModel::setupNodes()
beginResetModel();
bookIdToRowMap.clear();
for (auto bookItem : m_data) {
const auto rowNode = createNode(bookItem, iconMap);
const auto rowNode = createNode(bookItem);

// Restore download state during model updates (filtering, etc)
const auto downloadIter = m_downloads.constFind(rowNode->getBookId());
Expand Down Expand Up @@ -175,7 +182,7 @@ void ContentManagerModel::refreshIcons()
auto book = app->getLibrary()->getBookById(id);
auto item = book.getIllustration(48);
} catch (...) {
if (faviconUrl != "" && !iconMap.contains(faviconUrl)) {
if (faviconUrl != "" && !m_iconMap.contains(faviconUrl)) {
td.addDownload(faviconUrl, id);
}
}
Expand Down Expand Up @@ -240,7 +247,7 @@ void ContentManagerModel::updateImage(QString bookId, QString url, QByteArray im
const size_t row = it.value();
const auto item = static_cast<RowNode*>(rootNode->child(row).get());
item->setIconData(imageData);
iconMap[url] = imageData;
m_iconMap[url] = imageData;
const QModelIndex index = this->index(row, 0);
emit dataChanged(index, index);
}
Expand Down
Loading
Loading