From a5366e8a68ed3a03529aa200083d4435e7aafcdc Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D8=B1=D8=B4=D9=8A=D8=AF?= <25085777+RachidTagzen@users.noreply.github.com> Date: Sat, 22 Jul 2023 16:00:18 +0100 Subject: [PATCH 01/14] RTL layout direction to feeds I added a feature that lets change the feed's articles from right to left for languages such as Arabic, Urdu, Hebrew, Farsi... To enable it : **The desired feed -> Edit selected item -> Articles -> Right-to-left layout**. ![LTR](https://github.com/martinrotter/rssguard/assets/25085777/a555d38d-a066-44d2-b0d0-158daae4ac2b) ![RTL](https://github.com/martinrotter/rssguard/assets/25085777/81cde3e3-f645-4c2b-a46a-d60aa5f54bd7) --- resources/sql/db_init_sqlite.sql | 5 +- resources/sql/db_update_sqlite_3_4.sql | 5 +- src/librssguard/database/databasequeries.cpp | 13 +++-- src/librssguard/database/databasequeries.h | 3 + src/librssguard/definitions/definitions.h | 11 ++-- .../gui/settings/settingsfeedsmessages.cpp | 9 +++ .../gui/settings/settingsfeedsmessages.ui | 48 +++++++++++++-- src/librssguard/miscellaneous/settings.cpp | 6 ++ src/librssguard/miscellaneous/settings.h | 6 ++ src/librssguard/services/abstract/feed.cpp | 37 ++++++++++++ src/librssguard/services/abstract/feed.h | 18 ++++++ .../services/abstract/gui/formfeeddetails.cpp | 13 +++++ .../services/abstract/gui/formfeeddetails.ui | 58 +++++++++++++++++++ .../services/abstract/serviceroot.cpp | 6 ++ .../services/standard/standardserviceroot.cpp | 17 ++++++ 15 files changed, 239 insertions(+), 16 deletions(-) diff --git a/resources/sql/db_init_sqlite.sql b/resources/sql/db_init_sqlite.sql index 9810a1034..ff77693df 100644 --- a/resources/sql/db_init_sqlite.sql +++ b/resources/sql/db_init_sqlite.sql @@ -43,6 +43,9 @@ CREATE TABLE Feeds ( update_interval INTEGER NOT NULL DEFAULT 900 CHECK (update_interval >= 1), is_off INTEGER NOT NULL DEFAULT 0 CHECK (is_off >= 0 AND is_off <= 1), is_quiet INTEGER NOT NULL DEFAULT 0 CHECK (is_quiet >= 0 AND is_quiet <= 1), + add_any_datetime_articles INTEGER NOT NULL DEFAULT 0 CHECK(add_any_datetime_articles >= 0 AND add_any_datetime_articles <= 1), + avoid_old_articles INTEGER NOT NULL DEFAULT 0 CHECK(avoid_old_articles >= 0 AND avoid_old_articles <= 1), + datetime_to_avoid BIGINT NOT NULL DEFAULT 0 CHECK (datetime_to_avoid >= 0), open_articles INTEGER NOT NULL DEFAULT 0 CHECK (open_articles >= 0 AND open_articles <= 1), account_id INTEGER NOT NULL, custom_id TEXT NOT NULL CHECK (custom_id != ''), /* Custom ID cannot be empty, it must contain either service-specific ID, or Feeds/id. */ @@ -97,4 +100,4 @@ CREATE TABLE Labels ( account_id INTEGER NOT NULL, FOREIGN KEY (account_id) REFERENCES Accounts (id) ON DELETE CASCADE -); \ No newline at end of file +); diff --git a/resources/sql/db_update_sqlite_3_4.sql b/resources/sql/db_update_sqlite_3_4.sql index c06a9035c..7378f28fb 100644 --- a/resources/sql/db_update_sqlite_3_4.sql +++ b/resources/sql/db_update_sqlite_3_4.sql @@ -13,6 +13,9 @@ CREATE TABLE Feeds ( update_interval INTEGER NOT NULL DEFAULT 900 CHECK (update_interval >= 1), is_off INTEGER NOT NULL DEFAULT 0 CHECK (is_off >= 0 AND is_off <= 1), is_quiet INTEGER NOT NULL DEFAULT 0 CHECK (is_quiet >= 0 AND is_quiet <= 1), + add_any_datetime_articles INTEGER NOT NULL DEFAULT 0 CHECK(add_any_datetime_articles >= 0 AND add_any_datetime_articles <= 1), + avoid_old_articles INTEGER NOT NULL DEFAULT 0 CHECK(avoid_old_articles >= 0 AND avoid_old_articles <= 1), + datetime_to_avoid BIGINT NOT NULL DEFAULT 0 CHECK (datetime_to_avoid >= 0), open_articles INTEGER NOT NULL DEFAULT 0 CHECK (open_articles >= 0 AND open_articles <= 1), account_id INTEGER NOT NULL, custom_id TEXT NOT NULL CHECK (custom_id != ''), /* Custom ID cannot be empty, it must contain either service-specific ID, or Feeds/id. */ @@ -26,4 +29,4 @@ INSERT INTO Feeds (id, ordr, title, description, date_created, icon, category, s SELECT id, ordr, title, description, date_created, icon, category, source, update_type, update_interval, is_off, open_articles, account_id, custom_id, custom_data FROM backup_Feeds; -- ! -DROP TABLE backup_Feeds; \ No newline at end of file +DROP TABLE backup_Feeds; diff --git a/src/librssguard/database/databasequeries.cpp b/src/librssguard/database/databasequeries.cpp index 933f07087..5a3e43584 100644 --- a/src/librssguard/database/databasequeries.cpp +++ b/src/librssguard/database/databasequeries.cpp @@ -2178,11 +2178,11 @@ void DatabaseQueries::createOverwriteFeed(const QSqlDatabase& db, Feed* feed, in q.prepare("UPDATE Feeds " "SET title = :title, ordr = :ordr, description = :description, date_created = :date_created, " - " icon = :icon, category = :category, source = :source, update_type = :update_type, " - " update_interval = :update_interval, is_off = :is_off, is_quiet = :is_quiet, open_articles = " - ":open_articles, " - " account_id = :account_id, custom_id = :custom_id, custom_data = :custom_data " - "WHERE id = :id;"); + " icon = :icon, category = :category, source = :source, update_type = :update_type," + " update_interval = :update_interval, is_off = :is_off, is_quiet = :is_quiet, open_articles =" + " :open_articles, add_any_datetime_articles = :add_any_datetime_articles," + " avoid_old_articles = :avoid_old_articles, datetime_to_avoid = :datetime_to_avoid, account_id" + " = :account_id, custom_id = :custom_id, custom_data = :custom_data WHERE id = :id;"); q.bindValue(QSL(":title"), feed->title()); q.bindValue(QSL(":description"), feed->description()); q.bindValue(QSL(":date_created"), feed->creationDate().toMSecsSinceEpoch()); @@ -2198,6 +2198,9 @@ void DatabaseQueries::createOverwriteFeed(const QSqlDatabase& db, Feed* feed, in q.bindValue(QSL(":is_off"), feed->isSwitchedOff()); q.bindValue(QSL(":is_quiet"), feed->isQuiet()); q.bindValue(QSL(":open_articles"), feed->openArticlesDirectly()); + q.bindValue(QSL(":add_any_datetime_articles"), feed->addAnyDatetimeArticles()); + q.bindValue(QSL(":avoid_old_articles"), feed->avoidOldArticles()); + q.bindValue(QSL(":datetime_to_avoid"), feed->datetimeToAvoid().toMSecsSinceEpoch()); auto custom_data = feed->customDatabaseData(); QString serialized_custom_data = serializeCustomData(custom_data); diff --git a/src/librssguard/database/databasequeries.h b/src/librssguard/database/databasequeries.h index 1a65e7df1..e7ee097f7 100644 --- a/src/librssguard/database/databasequeries.h +++ b/src/librssguard/database/databasequeries.h @@ -353,6 +353,9 @@ Assignment DatabaseQueries::getFeeds(const QSqlDatabase& db, feed->setAutoUpdateInterval(query.value(FDS_DB_UPDATE_INTERVAL_INDEX).toInt()); feed->setIsSwitchedOff(query.value(FDS_DB_IS_OFF_INDEX).toBool()); feed->setIsQuiet(query.value(FDS_DB_IS_QUIET_INDEX).toBool()); + feed->setAddAnyDatetimeArticles(query.value(FDS_DB_ADD_ANY_DATETIME_ARTICLES_INDEX).toBool()); + feed->setAvoidOldArticles(query.value(FDS_DB_AVOID_OLD_ARTICLES_INDEX).toBool()); + feed->setDatetimeToAvoid(query.value(FDS_DB_DATETIME_TO_AVOID_INDEX).toDateTime()); feed->setOpenArticlesDirectly(query.value(FDS_DB_OPEN_ARTICLES_INDEX).toBool()); qDebugNN << LOGSEC_CORE << "Custom ID of feed when loading from DB is" << QUOTE_W_SPACE_DOT(feed->customId()); diff --git a/src/librssguard/definitions/definitions.h b/src/librssguard/definitions/definitions.h index ec6af0b23..87a4e93a5 100644 --- a/src/librssguard/definitions/definitions.h +++ b/src/librssguard/definitions/definitions.h @@ -295,10 +295,13 @@ #define FDS_DB_UPDATE_INTERVAL_INDEX 9 #define FDS_DB_IS_OFF_INDEX 10 #define FDS_DB_IS_QUIET_INDEX 11 -#define FDS_DB_OPEN_ARTICLES_INDEX 12 -#define FDS_DB_ACCOUNT_ID_INDEX 13 -#define FDS_DB_CUSTOM_ID_INDEX 14 -#define FDS_DB_CUSTOM_DATA_INDEX 15 +#define FDS_DB_ADD_ANY_DATETIME_ARTICLES_INDEX 12 +#define FDS_DB_AVOID_OLD_ARTICLES_INDEX 13 +#define FDS_DB_DATETIME_TO_AVOID_INDEX 14 +#define FDS_DB_OPEN_ARTICLES_INDEX 15 +#define FDS_DB_ACCOUNT_ID_INDEX 16 +#define FDS_DB_CUSTOM_ID_INDEX 17 +#define FDS_DB_CUSTOM_DATA_INDEX 18 // Indexes of columns for feed models. #define FDS_MODEL_TITLE_INDEX 0 diff --git a/src/librssguard/gui/settings/settingsfeedsmessages.cpp b/src/librssguard/gui/settings/settingsfeedsmessages.cpp index 48c4cd5ec..0e8523a40 100644 --- a/src/librssguard/gui/settings/settingsfeedsmessages.cpp +++ b/src/librssguard/gui/settings/settingsfeedsmessages.cpp @@ -197,6 +197,11 @@ SettingsFeedsMessages::SettingsFeedsMessages(Settings* settings, QWidget* parent m_ui->m_spinFeedUpdateTimeout->setSuffix(QSL(" ") + m_ui->m_spinFeedUpdateTimeout->suffix()); } + connect(m_ui->m_gbAvoidOldArticles, &QGroupBox::toggled, this, &SettingsFeedsMessages::dirtifySettings); + + connect(m_ui->m_dtDateTimeToAvoid, &QDateTimeEdit::dateTimeChanged, this, &SettingsFeedsMessages::dirtifySettings); + + m_ui->m_spinRelativeArticleTime->setValue(-1); } @@ -260,6 +265,8 @@ void SettingsFeedsMessages::loadSettings() { ->setChecked(settings()->value(GROUP(Feeds), SETTING(Feeds::AutoUpdateOnlyUnfocused)).toBool()); m_ui->m_spinAutoUpdateInterval->setValue(settings()->value(GROUP(Feeds), SETTING(Feeds::AutoUpdateInterval)).toInt()); m_ui->m_spinFeedUpdateTimeout->setValue(settings()->value(GROUP(Feeds), SETTING(Feeds::UpdateTimeout)).toInt()); + m_ui->m_gbAvoidOldArticles->setChecked(settings()->value(GROUP(Messages), SETTING(Messages::AvoidOldArticles)).toBool()); + m_ui->m_dtDateTimeToAvoid->setDateTime(settings()->value(GROUP(Messages), SETTING(Messages::DateTimeToAvoidArticle)).toDateTime()); m_ui->m_cmbFastAutoUpdate->setChecked(settings()->value(GROUP(Feeds), SETTING(Feeds::FastAutoUpdate)).toBool()); m_ui->m_checkUpdateAllFeedsOnStartup ->setChecked(settings()->value(GROUP(Feeds), SETTING(Feeds::FeedsUpdateOnStartup)).toBool()); @@ -346,6 +353,8 @@ void SettingsFeedsMessages::saveSettings() { settings()->setValue(GROUP(Feeds), Feeds::AutoUpdateOnlyUnfocused, m_ui->m_checkAutoUpdateOnlyUnfocused->isChecked()); settings()->setValue(GROUP(Feeds), Feeds::AutoUpdateInterval, m_ui->m_spinAutoUpdateInterval->value()); settings()->setValue(GROUP(Feeds), Feeds::UpdateTimeout, m_ui->m_spinFeedUpdateTimeout->value()); + settings()->setValue(GROUP(Messages), Messages::AvoidOldArticles, m_ui->m_gbAvoidOldArticles->isChecked()); + settings()->setValue(GROUP(Messages), Messages::DateTimeToAvoidArticle, m_ui->m_dtDateTimeToAvoid->dateTime()); settings()->setValue(GROUP(Feeds), Feeds::FastAutoUpdate, m_ui->m_cmbFastAutoUpdate->isChecked()); settings()->setValue(GROUP(Feeds), Feeds::FeedsUpdateOnStartup, m_ui->m_checkUpdateAllFeedsOnStartup->isChecked()); settings()->setValue(GROUP(Feeds), Feeds::FeedsUpdateStartupDelay, m_ui->m_spinStartupUpdateDelay->value()); diff --git a/src/librssguard/gui/settings/settingsfeedsmessages.ui b/src/librssguard/gui/settings/settingsfeedsmessages.ui index b5c85383e..f0229890a 100644 --- a/src/librssguard/gui/settings/settingsfeedsmessages.ui +++ b/src/librssguard/gui/settings/settingsfeedsmessages.ui @@ -6,7 +6,7 @@ 0 0 - 558 + 570 531 @@ -80,6 +80,13 @@ + + + + Support very fast auto-fetching intervals (under 10 seconds) + + + @@ -115,11 +122,42 @@ - - - - Support very fast auto-fetching intervals (under 10 seconds) + + + + Avoid adding articles before this date into the database + + true + + + false + + + + + + dd/MM/yyyy HH:mm + + + true + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + diff --git a/src/librssguard/miscellaneous/settings.cpp b/src/librssguard/miscellaneous/settings.cpp index 12ff844c8..b382c93c1 100644 --- a/src/librssguard/miscellaneous/settings.cpp +++ b/src/librssguard/miscellaneous/settings.cpp @@ -130,6 +130,12 @@ DVALUE(int) Messages::MessageHeadImageHeightDef = 36; DKEY Messages::DisplayEnclosuresInMessage = "show_enclosures_in_message"; DVALUE(bool) Messages::DisplayEnclosuresInMessageDef = false; +DKEY Messages::AvoidOldArticles = "avoid_old_articles"; +DVALUE(bool) Messages::AvoidOldArticlesDef = false; + +DKEY Messages::DateTimeToAvoidArticle = "datetime_to_avoid_article"; +DVALUE(QDateTime) Messages::DateTimeToAvoidArticleDef = QDateTime::currentDateTime(); + DKEY Messages::AlwaysDisplayItemPreview = "always_display_preview"; DVALUE(bool) Messages::AlwaysDisplayItemPreviewDef = true; diff --git a/src/librssguard/miscellaneous/settings.h b/src/librssguard/miscellaneous/settings.h index 1fb5f1299..81fd66941 100644 --- a/src/librssguard/miscellaneous/settings.h +++ b/src/librssguard/miscellaneous/settings.h @@ -129,6 +129,12 @@ namespace Messages { KEY DisplayEnclosuresInMessage; VALUE(bool) DisplayEnclosuresInMessageDef; + KEY AvoidOldArticles; + VALUE(bool) AvoidOldArticlesDef; + + KEY DateTimeToAvoidArticle; + VALUE(QDateTime) DateTimeToAvoidArticleDef; + KEY AlwaysDisplayItemPreview; VALUE(bool) AlwaysDisplayItemPreviewDef; diff --git a/src/librssguard/services/abstract/feed.cpp b/src/librssguard/services/abstract/feed.cpp index 5a98c9ff6..3ce146d06 100644 --- a/src/librssguard/services/abstract/feed.cpp +++ b/src/librssguard/services/abstract/feed.cpp @@ -21,6 +21,7 @@ Feed::Feed(RootItem* parent) : RootItem(parent), m_source(QString()), m_status(Status::Normal), m_statusString(QString()), m_autoUpdateType(AutoUpdateType::DefaultAutoUpdate), m_autoUpdateInterval(DEFAULT_AUTO_UPDATE_INTERVAL), m_lastUpdated(QDateTime::currentDateTimeUtc()), m_isSwitchedOff(false), m_isQuiet(false), + m_addAnyDatetimeArticles(false), m_avoidOldArticles(false), m_datetimeToAvoid(QDateTime::currentDateTime()), m_openArticlesDirectly(false), m_messageFilters(QList>()) { setKind(RootItem::Kind::Feed); } @@ -43,6 +44,10 @@ Feed::Feed(const Feed& other) : RootItem(other) { setLastUpdated(other.lastUpdated()); setMessageFilters(other.messageFilters()); setOpenArticlesDirectly(other.openArticlesDirectly()); + setAddAnyDatetimeArticles(other.addAnyDatetimeArticles()); + setAvoidOldArticles(other.avoidOldArticles()); + setAvoidOldArticlesEnabled(other.isAvoidOldArticlesEnabled()); + setDatetimeToAvoid(other.datetimeToAvoid()); setIsSwitchedOff(other.isSwitchedOff()); setIsQuiet(other.isQuiet()); } @@ -189,6 +194,38 @@ void Feed::setOpenArticlesDirectly(bool opn) { m_openArticlesDirectly = opn; } +bool Feed::addAnyDatetimeArticles() const { + return m_addAnyDatetimeArticles; +} + +void Feed::setAddAnyDatetimeArticles(bool addAnyDatetimeArticles) { + m_addAnyDatetimeArticles = addAnyDatetimeArticles; +} + +bool Feed::avoidOldArticles() const { + return m_avoidOldArticles; +} + +void Feed::setAvoidOldArticles(bool avoidDateArticles) { + m_avoidOldArticles = avoidDateArticles; +} + +bool Feed::isAvoidOldArticlesEnabled() const { + return m_avoidOldArticlesEnabled; +} + +void Feed::setAvoidOldArticlesEnabled(bool newAvoidOldArticlesEnabled) { + m_avoidOldArticlesEnabled = newAvoidOldArticlesEnabled; +} + +QDateTime Feed::datetimeToAvoid() const { + return m_datetimeToAvoid; +} + +void Feed::setDatetimeToAvoid(const QDateTime &dateTime) { + m_datetimeToAvoid = dateTime; +} + void Feed::appendMessageFilter(MessageFilter* filter) { m_messageFilters.append(QPointer(filter)); } diff --git a/src/librssguard/services/abstract/feed.h b/src/librssguard/services/abstract/feed.h index 28ce3d983..428ed303c 100644 --- a/src/librssguard/services/abstract/feed.h +++ b/src/librssguard/services/abstract/feed.h @@ -82,6 +82,20 @@ class Feed : public RootItem { QDateTime lastUpdated() const; void setLastUpdated(const QDateTime& last_updated); + + bool addAnyDatetimeArticles() const; + void setAddAnyDatetimeArticles(bool addAnyDatetimeArticles); + + bool avoidOldArticles() const; + void setAvoidOldArticles(bool avoidDateArticles); + + bool isAvoidOldArticlesEnabled() const; + void setAvoidOldArticlesEnabled(bool newAvoidOldArticlesEnabled); + + QDateTime datetimeToAvoid() const; + void setDatetimeToAvoid(const QDateTime &dateTime); + + public slots: virtual void updateCounts(bool including_total_count); @@ -99,6 +113,10 @@ class Feed : public RootItem { bool m_isSwitchedOff; bool m_isQuiet; bool m_openArticlesDirectly; + bool m_addAnyDatetimeArticles; + bool m_avoidOldArticles; + bool m_avoidOldArticlesEnabled; + QDateTime m_datetimeToAvoid; int m_totalCount{}; int m_unreadCount{}; QList> m_messageFilters; diff --git a/src/librssguard/services/abstract/gui/formfeeddetails.cpp b/src/librssguard/services/abstract/gui/formfeeddetails.cpp index 4adb9b1f5..15cf6c93e 100644 --- a/src/librssguard/services/abstract/gui/formfeeddetails.cpp +++ b/src/librssguard/services/abstract/gui/formfeeddetails.cpp @@ -49,6 +49,9 @@ void FormFeedDetails::apply() { .toInt())); m_feed->setAutoUpdateInterval(int(m_ui->m_spinAutoUpdateInterval->value())); m_feed->setOpenArticlesDirectly(m_ui->m_cbOpenArticlesAutomatically->isChecked()); + m_feed->setAddAnyDatetimeArticles(m_ui->m_cbAddAnyDateArticles->isChecked()); + m_feed->setAvoidOldArticles(m_ui->m_gbAvoidOldArticles->isChecked()); + m_feed->setDatetimeToAvoid(m_ui->m_dtDateTimeToAvoid->dateTime()); m_feed->setIsSwitchedOff(m_ui->m_cbDisableFeed->isChecked()); m_feed->setIsQuiet(m_ui->m_cbSuppressFeed->isChecked()); @@ -81,6 +84,12 @@ void FormFeedDetails::createConnections() { static_cast(&QComboBox::currentIndexChanged), this, &FormFeedDetails::onAutoUpdateTypeChanged); + + connect(m_ui->m_cbAddAnyDateArticles, &QCheckBox::toggled, this, [this](bool checked) { + m_ui->m_gbAvoidOldArticles->setEnabled(!checked); + m_feed->setAvoidOldArticlesEnabled(!checked); + }); + } void FormFeedDetails::loadFeedData() { @@ -97,6 +106,10 @@ void FormFeedDetails::loadFeedData() { ->setCurrentIndex(m_ui->m_cmbAutoUpdateType->findData(QVariant::fromValue(int(m_feed->autoUpdateType())))); m_ui->m_spinAutoUpdateInterval->setValue(m_feed->autoUpdateInterval()); m_ui->m_cbOpenArticlesAutomatically->setChecked(m_feed->openArticlesDirectly()); + m_ui->m_cbAddAnyDateArticles->setChecked(m_feed->addAnyDatetimeArticles()); + m_ui->m_gbAvoidOldArticles->setChecked(m_feed->avoidOldArticles()); + m_ui->m_gbAvoidOldArticles->setEnabled(!m_feed->addAnyDatetimeArticles()); + m_ui->m_dtDateTimeToAvoid->setDateTime(m_feed->datetimeToAvoid()); m_ui->m_cbDisableFeed->setChecked(m_feed->isSwitchedOff()); m_ui->m_cbSuppressFeed->setChecked(m_feed->isQuiet()); } diff --git a/src/librssguard/services/abstract/gui/formfeeddetails.ui b/src/librssguard/services/abstract/gui/formfeeddetails.ui index f874c739a..9062906a1 100644 --- a/src/librssguard/services/abstract/gui/formfeeddetails.ui +++ b/src/librssguard/services/abstract/gui/formfeeddetails.ui @@ -59,6 +59,64 @@ + + + + Qt::Horizontal + + + + + + + Add articles with any date into the database + + + true + + + + + + + true + + + Avoid adding articles before this date into the database : + + + true + + + false + + + + + + dd/MM/yyyy HH:mm + + + true + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + diff --git a/src/librssguard/services/abstract/serviceroot.cpp b/src/librssguard/services/abstract/serviceroot.cpp index 37e27df21..2b377010c 100644 --- a/src/librssguard/services/abstract/serviceroot.cpp +++ b/src/librssguard/services/abstract/serviceroot.cpp @@ -384,6 +384,9 @@ QMap ServiceRoot::storeCustomFeedsData() { feed_custom_data.insert(QSL("is_off"), feed->isSwitchedOff()); feed_custom_data.insert(QSL("is_quiet"), feed->isQuiet()); feed_custom_data.insert(QSL("open_articles_directly"), feed->openArticlesDirectly()); + feed_custom_data.insert(QSL("add_any_datetime_articles"), feed->addAnyDatetimeArticles()); + feed_custom_data.insert(QSL("avoid_old_articles"), feed->avoidOldArticles()); + feed_custom_data.insert(QSL("datetime_to_avoid"), feed->datetimeToAvoid().toMSecsSinceEpoch()); // NOTE: This is here specifically to be able to restore custom sort order. // Otherwise the information is lost when list of feeds/folders is refreshed from remote @@ -433,6 +436,9 @@ void ServiceRoot::restoreCustomFeedsData(const QMap& data, feed->setIsSwitchedOff(feed_custom_data.value(QSL("is_off")).toBool()); feed->setIsQuiet(feed_custom_data.value(QSL("is_quiet")).toBool()); feed->setOpenArticlesDirectly(feed_custom_data.value(QSL("open_articles_directly")).toBool()); + feed->setAddAnyDatetimeArticles(feed_custom_data.value(QSL("add_any_datetime_articles")).toBool()); + feed->setAvoidOldArticles(feed_custom_data.value(QSL("avoid_date_message")).toBool()); + feed->setDatetimeToAvoid(feed_custom_data.value(QSL("avoid_message_datetime")).toDateTime()); } } } diff --git a/src/librssguard/services/standard/standardserviceroot.cpp b/src/librssguard/services/standard/standardserviceroot.cpp index bb1177070..6181525bd 100644 --- a/src/librssguard/services/standard/standardserviceroot.cpp +++ b/src/librssguard/services/standard/standardserviceroot.cpp @@ -256,6 +256,23 @@ QList StandardServiceRoot::obtainNewMessages(Feed* feed, mess.m_feedId = feed->customId(); } + + if (!feed->addAnyDatetimeArticles()) { + + QDateTime datetimeToAvoid; + + if (feed->isAvoidOldArticlesEnabled() && feed->avoidOldArticles()) + datetimeToAvoid = feed->datetimeToAvoid(); + else if (qApp->settings()->value(GROUP(Messages), SETTING(Messages::AvoidOldArticles)).toBool()) + datetimeToAvoid = qApp->settings()->value(GROUP(Messages), SETTING(Messages::DateTimeToAvoidArticle)).toDateTime(); + else + return messages; + + for (int i = 0; i < messages.size(); i++) + if (messages.at(i).m_created < datetimeToAvoid) + messages.removeAt(i--); + } + return messages; } From a8a0f789e9271ec60fce9334d6ce8cd3174fa671 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D8=B1=D8=B4=D9=8A=D8=AF?= <25085777+RachidTagzen@users.noreply.github.com> Date: Sat, 22 Jul 2023 16:21:23 +0100 Subject: [PATCH 02/14] New Feature: Right-to-Left Layout for Feed Articles in RTL Languages I added a feature that lets change the feed's articles from right to left for languages such as Arabic, Urdu, Hebrew, Farsi... To enable it : **The desired feed -> Edit selected item -> Articles -> Right-to-left layout**. ![LTR](https://github.com/martinrotter/rssguard/assets/25085777/a555d38d-a066-44d2-b0d0-158daae4ac2b) ![RTL](https://github.com/martinrotter/rssguard/assets/25085777/81cde3e3-f645-4c2b-a46a-d60aa5f54bd7) --- resources/sql/db_init_sqlite.sql | 1 + resources/sql/db_update_sqlite_3_4.sql | 1 + src/librssguard/database/databasequeries.cpp | 3 ++- src/librssguard/database/databasequeries.h | 1 + src/librssguard/definitions/definitions.h | 15 ++++++++------- src/librssguard/gui/feedsview.cpp | 4 ++++ src/librssguard/gui/messagesview.cpp | 7 +++++++ src/librssguard/services/abstract/feed.cpp | 13 +++++++++++-- src/librssguard/services/abstract/feed.h | 4 ++++ .../services/abstract/gui/formfeeddetails.cpp | 2 ++ .../services/abstract/gui/formfeeddetails.ui | 11 +++++++++-- src/librssguard/services/abstract/serviceroot.cpp | 2 ++ 12 files changed, 52 insertions(+), 12 deletions(-) diff --git a/resources/sql/db_init_sqlite.sql b/resources/sql/db_init_sqlite.sql index ff77693df..76f9b38c2 100644 --- a/resources/sql/db_init_sqlite.sql +++ b/resources/sql/db_init_sqlite.sql @@ -43,6 +43,7 @@ CREATE TABLE Feeds ( update_interval INTEGER NOT NULL DEFAULT 900 CHECK (update_interval >= 1), is_off INTEGER NOT NULL DEFAULT 0 CHECK (is_off >= 0 AND is_off <= 1), is_quiet INTEGER NOT NULL DEFAULT 0 CHECK (is_quiet >= 0 AND is_quiet <= 1), + is_rtl INTEGER NOT NULL DEFAULT 0 CHECK (is_rtl >= 0 AND is_rtl <= 1), add_any_datetime_articles INTEGER NOT NULL DEFAULT 0 CHECK(add_any_datetime_articles >= 0 AND add_any_datetime_articles <= 1), avoid_old_articles INTEGER NOT NULL DEFAULT 0 CHECK(avoid_old_articles >= 0 AND avoid_old_articles <= 1), datetime_to_avoid BIGINT NOT NULL DEFAULT 0 CHECK (datetime_to_avoid >= 0), diff --git a/resources/sql/db_update_sqlite_3_4.sql b/resources/sql/db_update_sqlite_3_4.sql index 7378f28fb..fcb7c4704 100644 --- a/resources/sql/db_update_sqlite_3_4.sql +++ b/resources/sql/db_update_sqlite_3_4.sql @@ -13,6 +13,7 @@ CREATE TABLE Feeds ( update_interval INTEGER NOT NULL DEFAULT 900 CHECK (update_interval >= 1), is_off INTEGER NOT NULL DEFAULT 0 CHECK (is_off >= 0 AND is_off <= 1), is_quiet INTEGER NOT NULL DEFAULT 0 CHECK (is_quiet >= 0 AND is_quiet <= 1), + is_rtl INTEGER NOT NULL DEFAULT 0 CHECK (is_rtl >= 0 AND is_rtl <= 1), add_any_datetime_articles INTEGER NOT NULL DEFAULT 0 CHECK(add_any_datetime_articles >= 0 AND add_any_datetime_articles <= 1), avoid_old_articles INTEGER NOT NULL DEFAULT 0 CHECK(avoid_old_articles >= 0 AND avoid_old_articles <= 1), datetime_to_avoid BIGINT NOT NULL DEFAULT 0 CHECK (datetime_to_avoid >= 0), diff --git a/src/librssguard/database/databasequeries.cpp b/src/librssguard/database/databasequeries.cpp index 5a3e43584..9e662489b 100644 --- a/src/librssguard/database/databasequeries.cpp +++ b/src/librssguard/database/databasequeries.cpp @@ -2180,7 +2180,7 @@ void DatabaseQueries::createOverwriteFeed(const QSqlDatabase& db, Feed* feed, in "SET title = :title, ordr = :ordr, description = :description, date_created = :date_created, " " icon = :icon, category = :category, source = :source, update_type = :update_type," " update_interval = :update_interval, is_off = :is_off, is_quiet = :is_quiet, open_articles =" - " :open_articles, add_any_datetime_articles = :add_any_datetime_articles," + " :open_articles, is_rtl = :is_rtl, add_any_datetime_articles = :add_any_datetime_articles," " avoid_old_articles = :avoid_old_articles, datetime_to_avoid = :datetime_to_avoid, account_id" " = :account_id, custom_id = :custom_id, custom_data = :custom_data WHERE id = :id;"); q.bindValue(QSL(":title"), feed->title()); @@ -2198,6 +2198,7 @@ void DatabaseQueries::createOverwriteFeed(const QSqlDatabase& db, Feed* feed, in q.bindValue(QSL(":is_off"), feed->isSwitchedOff()); q.bindValue(QSL(":is_quiet"), feed->isQuiet()); q.bindValue(QSL(":open_articles"), feed->openArticlesDirectly()); + q.bindValue(QSL(":is_rtl"), feed->isRTL()); q.bindValue(QSL(":add_any_datetime_articles"), feed->addAnyDatetimeArticles()); q.bindValue(QSL(":avoid_old_articles"), feed->avoidOldArticles()); q.bindValue(QSL(":datetime_to_avoid"), feed->datetimeToAvoid().toMSecsSinceEpoch()); diff --git a/src/librssguard/database/databasequeries.h b/src/librssguard/database/databasequeries.h index e7ee097f7..833f849ad 100644 --- a/src/librssguard/database/databasequeries.h +++ b/src/librssguard/database/databasequeries.h @@ -353,6 +353,7 @@ Assignment DatabaseQueries::getFeeds(const QSqlDatabase& db, feed->setAutoUpdateInterval(query.value(FDS_DB_UPDATE_INTERVAL_INDEX).toInt()); feed->setIsSwitchedOff(query.value(FDS_DB_IS_OFF_INDEX).toBool()); feed->setIsQuiet(query.value(FDS_DB_IS_QUIET_INDEX).toBool()); + feed->setIsRTL(query.value(FDS_DB_IS_RTL_INDEX).toBool()); feed->setAddAnyDatetimeArticles(query.value(FDS_DB_ADD_ANY_DATETIME_ARTICLES_INDEX).toBool()); feed->setAvoidOldArticles(query.value(FDS_DB_AVOID_OLD_ARTICLES_INDEX).toBool()); feed->setDatetimeToAvoid(query.value(FDS_DB_DATETIME_TO_AVOID_INDEX).toDateTime()); diff --git a/src/librssguard/definitions/definitions.h b/src/librssguard/definitions/definitions.h index 87a4e93a5..a2e9b9815 100644 --- a/src/librssguard/definitions/definitions.h +++ b/src/librssguard/definitions/definitions.h @@ -295,13 +295,14 @@ #define FDS_DB_UPDATE_INTERVAL_INDEX 9 #define FDS_DB_IS_OFF_INDEX 10 #define FDS_DB_IS_QUIET_INDEX 11 -#define FDS_DB_ADD_ANY_DATETIME_ARTICLES_INDEX 12 -#define FDS_DB_AVOID_OLD_ARTICLES_INDEX 13 -#define FDS_DB_DATETIME_TO_AVOID_INDEX 14 -#define FDS_DB_OPEN_ARTICLES_INDEX 15 -#define FDS_DB_ACCOUNT_ID_INDEX 16 -#define FDS_DB_CUSTOM_ID_INDEX 17 -#define FDS_DB_CUSTOM_DATA_INDEX 18 +#define FDS_DB_IS_RTL_INDEX 12 +#define FDS_DB_ADD_ANY_DATETIME_ARTICLES_INDEX 13 +#define FDS_DB_AVOID_OLD_ARTICLES_INDEX 14 +#define FDS_DB_DATETIME_TO_AVOID_INDEX 15 +#define FDS_DB_OPEN_ARTICLES_INDEX 16 +#define FDS_DB_ACCOUNT_ID_INDEX 17 +#define FDS_DB_CUSTOM_ID_INDEX 18 +#define FDS_DB_CUSTOM_DATA_INDEX 19 // Indexes of columns for feed models. #define FDS_MODEL_TITLE_INDEX 0 diff --git a/src/librssguard/gui/feedsview.cpp b/src/librssguard/gui/feedsview.cpp index dabe3a187..ff3087d81 100644 --- a/src/librssguard/gui/feedsview.cpp +++ b/src/librssguard/gui/feedsview.cpp @@ -231,6 +231,10 @@ void FeedsView::editSelectedItem() { QSystemTrayIcon::MessageIcon::Warning}); } + RootItem* selected_item = selectedItem(); + emit itemSelected(selected_item); + + // Changes are done, unlock the update master lock. qApp->feedUpdateLock()->unlock(); } diff --git a/src/librssguard/gui/messagesview.cpp b/src/librssguard/gui/messagesview.cpp index e36d6bd39..f77ea6a56 100644 --- a/src/librssguard/gui/messagesview.cpp +++ b/src/librssguard/gui/messagesview.cpp @@ -516,6 +516,13 @@ void MessagesView::loadItem(RootItem* item) { sort(col, ord, false, true, false, true); m_sourceModel->loadMessages(item); + if (item->toFeed() != nullptr) { + if (item->toFeed()->isRTL()) + setLayoutDirection(Qt::RightToLeft); + else + setLayoutDirection(Qt::LeftToRight); + } + // Messages are loaded, make sure that previously // active message is not shown in browser. emit currentMessageRemoved(m_sourceModel->loadedItem()); diff --git a/src/librssguard/services/abstract/feed.cpp b/src/librssguard/services/abstract/feed.cpp index 3ce146d06..9e2483206 100644 --- a/src/librssguard/services/abstract/feed.cpp +++ b/src/librssguard/services/abstract/feed.cpp @@ -21,8 +21,8 @@ Feed::Feed(RootItem* parent) : RootItem(parent), m_source(QString()), m_status(Status::Normal), m_statusString(QString()), m_autoUpdateType(AutoUpdateType::DefaultAutoUpdate), m_autoUpdateInterval(DEFAULT_AUTO_UPDATE_INTERVAL), m_lastUpdated(QDateTime::currentDateTimeUtc()), m_isSwitchedOff(false), m_isQuiet(false), - m_addAnyDatetimeArticles(false), m_avoidOldArticles(false), m_datetimeToAvoid(QDateTime::currentDateTime()), - m_openArticlesDirectly(false), m_messageFilters(QList>()) { + m_isRTL(false), m_addAnyDatetimeArticles(false), m_avoidOldArticles(false), m_openArticlesDirectly(false), + m_datetimeToAvoid(QDateTime::currentDateTime()), m_messageFilters(QList>()) { setKind(RootItem::Kind::Feed); } @@ -48,6 +48,7 @@ Feed::Feed(const Feed& other) : RootItem(other) { setAvoidOldArticles(other.avoidOldArticles()); setAvoidOldArticlesEnabled(other.isAvoidOldArticlesEnabled()); setDatetimeToAvoid(other.datetimeToAvoid()); + setIsRTL(other.isRTL()); setIsSwitchedOff(other.isSwitchedOff()); setIsQuiet(other.isQuiet()); } @@ -194,6 +195,14 @@ void Feed::setOpenArticlesDirectly(bool opn) { m_openArticlesDirectly = opn; } +bool Feed::isRTL() const { + return m_isRTL; +} + +void Feed::setIsRTL(bool rtl) { + m_isRTL = rtl; +} + bool Feed::addAnyDatetimeArticles() const { return m_addAnyDatetimeArticles; } diff --git a/src/librssguard/services/abstract/feed.h b/src/librssguard/services/abstract/feed.h index 428ed303c..aec96f2d6 100644 --- a/src/librssguard/services/abstract/feed.h +++ b/src/librssguard/services/abstract/feed.h @@ -83,6 +83,9 @@ class Feed : public RootItem { QDateTime lastUpdated() const; void setLastUpdated(const QDateTime& last_updated); + bool isRTL() const; + void setIsRTL(bool rtl); + bool addAnyDatetimeArticles() const; void setAddAnyDatetimeArticles(bool addAnyDatetimeArticles); @@ -113,6 +116,7 @@ class Feed : public RootItem { bool m_isSwitchedOff; bool m_isQuiet; bool m_openArticlesDirectly; + bool m_isRTL; bool m_addAnyDatetimeArticles; bool m_avoidOldArticles; bool m_avoidOldArticlesEnabled; diff --git a/src/librssguard/services/abstract/gui/formfeeddetails.cpp b/src/librssguard/services/abstract/gui/formfeeddetails.cpp index 15cf6c93e..b164b41b7 100644 --- a/src/librssguard/services/abstract/gui/formfeeddetails.cpp +++ b/src/librssguard/services/abstract/gui/formfeeddetails.cpp @@ -49,6 +49,7 @@ void FormFeedDetails::apply() { .toInt())); m_feed->setAutoUpdateInterval(int(m_ui->m_spinAutoUpdateInterval->value())); m_feed->setOpenArticlesDirectly(m_ui->m_cbOpenArticlesAutomatically->isChecked()); + m_feed->setIsRTL(m_ui->m_cbFeedRTL->isChecked()); m_feed->setAddAnyDatetimeArticles(m_ui->m_cbAddAnyDateArticles->isChecked()); m_feed->setAvoidOldArticles(m_ui->m_gbAvoidOldArticles->isChecked()); m_feed->setDatetimeToAvoid(m_ui->m_dtDateTimeToAvoid->dateTime()); @@ -106,6 +107,7 @@ void FormFeedDetails::loadFeedData() { ->setCurrentIndex(m_ui->m_cmbAutoUpdateType->findData(QVariant::fromValue(int(m_feed->autoUpdateType())))); m_ui->m_spinAutoUpdateInterval->setValue(m_feed->autoUpdateInterval()); m_ui->m_cbOpenArticlesAutomatically->setChecked(m_feed->openArticlesDirectly()); + m_ui->m_cbFeedRTL->setChecked(m_feed->isRTL()); m_ui->m_cbAddAnyDateArticles->setChecked(m_feed->addAnyDatetimeArticles()); m_ui->m_gbAvoidOldArticles->setChecked(m_feed->avoidOldArticles()); m_ui->m_gbAvoidOldArticles->setEnabled(!m_feed->addAnyDatetimeArticles()); diff --git a/src/librssguard/services/abstract/gui/formfeeddetails.ui b/src/librssguard/services/abstract/gui/formfeeddetails.ui index 9062906a1..8714606f0 100644 --- a/src/librssguard/services/abstract/gui/formfeeddetails.ui +++ b/src/librssguard/services/abstract/gui/formfeeddetails.ui @@ -60,13 +60,20 @@ + + + Right-to-left layout + + + + Qt::Horizontal - + Add articles with any date into the database @@ -76,7 +83,7 @@ - + true diff --git a/src/librssguard/services/abstract/serviceroot.cpp b/src/librssguard/services/abstract/serviceroot.cpp index 2b377010c..d28811068 100644 --- a/src/librssguard/services/abstract/serviceroot.cpp +++ b/src/librssguard/services/abstract/serviceroot.cpp @@ -384,6 +384,7 @@ QMap ServiceRoot::storeCustomFeedsData() { feed_custom_data.insert(QSL("is_off"), feed->isSwitchedOff()); feed_custom_data.insert(QSL("is_quiet"), feed->isQuiet()); feed_custom_data.insert(QSL("open_articles_directly"), feed->openArticlesDirectly()); + feed_custom_data.insert(QSL("is_rtl"), feed->isRTL()); feed_custom_data.insert(QSL("add_any_datetime_articles"), feed->addAnyDatetimeArticles()); feed_custom_data.insert(QSL("avoid_old_articles"), feed->avoidOldArticles()); feed_custom_data.insert(QSL("datetime_to_avoid"), feed->datetimeToAvoid().toMSecsSinceEpoch()); @@ -436,6 +437,7 @@ void ServiceRoot::restoreCustomFeedsData(const QMap& data, feed->setIsSwitchedOff(feed_custom_data.value(QSL("is_off")).toBool()); feed->setIsQuiet(feed_custom_data.value(QSL("is_quiet")).toBool()); feed->setOpenArticlesDirectly(feed_custom_data.value(QSL("open_articles_directly")).toBool()); + feed->setIsRTL(feed_custom_data.value(QSL("is_rtl")).toBool()); feed->setAddAnyDatetimeArticles(feed_custom_data.value(QSL("add_any_datetime_articles")).toBool()); feed->setAvoidOldArticles(feed_custom_data.value(QSL("avoid_date_message")).toBool()); feed->setDatetimeToAvoid(feed_custom_data.value(QSL("avoid_message_datetime")).toDateTime()); From a0102833c9558b8c4370c08273738d165f3a5b19 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D8=B1=D8=B4=D9=8A=D8=AF?= <25085777+RachidTagzen@users.noreply.github.com> Date: Sat, 22 Jul 2023 17:07:45 +0100 Subject: [PATCH 03/14] Update db_update_sqlite_3_4.sql --- resources/sql/db_update_sqlite_3_4.sql | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/resources/sql/db_update_sqlite_3_4.sql b/resources/sql/db_update_sqlite_3_4.sql index fcb7c4704..25b277189 100644 --- a/resources/sql/db_update_sqlite_3_4.sql +++ b/resources/sql/db_update_sqlite_3_4.sql @@ -26,8 +26,8 @@ CREATE TABLE Feeds ( FOREIGN KEY (account_id) REFERENCES Accounts (id) ON DELETE CASCADE ); -- ! -INSERT INTO Feeds (id, ordr, title, description, date_created, icon, category, source, update_type, update_interval, is_off, open_articles, account_id, custom_id, custom_data) -SELECT id, ordr, title, description, date_created, icon, category, source, update_type, update_interval, is_off, open_articles, account_id, custom_id, custom_data +INSERT INTO Feeds (id, ordr, title, description, date_created, icon, category, source, update_type, update_interval, is_off, is_quiet, is_rtl , add_any_datetime_articles, avoid_old_articles, datetime_to_avoid, open_articles, account_id, custom_id, custom_data) +SELECT id, ordr, title, description, date_created, icon, category, source, update_type, update_interval, is_off, is_quiet, is_rtl , add_any_datetime_articles, avoid_old_articles, datetime_to_avoid, open_articles, account_id, custom_id, custom_data FROM backup_Feeds; -- ! DROP TABLE backup_Feeds; From dbad3978a515c26fdcccf2367d33342452322e40 Mon Sep 17 00:00:00 2001 From: Martin Rotter Date: Wed, 26 Jul 2023 09:09:42 +0200 Subject: [PATCH 04/14] some initial fixes and refactorings for the PR --- resources/sql.qrc | 2 + resources/sql/db_init_sqlite.sql | 37 +++++++++-------- resources/sql/db_update_mysql_5_6.sql | 8 ++++ resources/sql/db_update_sqlite_3_4.sql | 10 ++--- resources/sql/db_update_sqlite_5_6.sql | 32 +++++++++++++++ src/librssguard/database/databasequeries.cpp | 5 +-- src/librssguard/database/databasequeries.h | 3 +- src/librssguard/definitions/definitions.h | 13 +++--- src/librssguard/gui/feedsview.cpp | 8 ++-- src/librssguard/gui/messagesview.cpp | 10 +++-- src/librssguard/services/abstract/feed.cpp | 40 +++++-------------- src/librssguard/services/abstract/feed.h | 17 +++----- .../services/abstract/gui/formfeeddetails.cpp | 8 +--- .../services/abstract/serviceroot.cpp | 8 ++-- .../services/standard/standardserviceroot.cpp | 19 +++++---- 15 files changed, 115 insertions(+), 105 deletions(-) create mode 100755 resources/sql/db_update_mysql_5_6.sql create mode 100755 resources/sql/db_update_sqlite_5_6.sql diff --git a/resources/sql.qrc b/resources/sql.qrc index 88d7f8529..d15d562c4 100644 --- a/resources/sql.qrc +++ b/resources/sql.qrc @@ -5,11 +5,13 @@ sql/db_update_mysql_2_3.sql sql/db_update_mysql_3_4.sql sql/db_update_mysql_4_5.sql + sql/db_update_mysql_5_6.sql sql/db_init_sqlite.sql sql/db_update_sqlite_1_2.sql sql/db_update_sqlite_2_3.sql sql/db_update_sqlite_3_4.sql sql/db_update_sqlite_4_5.sql + sql/db_update_sqlite_5_6.sql \ No newline at end of file diff --git a/resources/sql/db_init_sqlite.sql b/resources/sql/db_init_sqlite.sql index 76f9b38c2..5dc63086a 100644 --- a/resources/sql/db_init_sqlite.sql +++ b/resources/sql/db_init_sqlite.sql @@ -31,25 +31,24 @@ CREATE TABLE Categories ( ); -- ! CREATE TABLE Feeds ( - id $$, - ordr INTEGER NOT NULL CHECK (ordr >= 0), - title TEXT NOT NULL CHECK (title != ''), - description TEXT, - date_created BIGINT, - icon ^^, - category INTEGER NOT NULL CHECK (category >= -1), /* Physical category ID, also root feeds contain -1 here. */ - source TEXT, - update_type INTEGER NOT NULL CHECK (update_type >= 0), - update_interval INTEGER NOT NULL DEFAULT 900 CHECK (update_interval >= 1), - is_off INTEGER NOT NULL DEFAULT 0 CHECK (is_off >= 0 AND is_off <= 1), - is_quiet INTEGER NOT NULL DEFAULT 0 CHECK (is_quiet >= 0 AND is_quiet <= 1), - is_rtl INTEGER NOT NULL DEFAULT 0 CHECK (is_rtl >= 0 AND is_rtl <= 1), - add_any_datetime_articles INTEGER NOT NULL DEFAULT 0 CHECK(add_any_datetime_articles >= 0 AND add_any_datetime_articles <= 1), - avoid_old_articles INTEGER NOT NULL DEFAULT 0 CHECK(avoid_old_articles >= 0 AND avoid_old_articles <= 1), - datetime_to_avoid BIGINT NOT NULL DEFAULT 0 CHECK (datetime_to_avoid >= 0), - open_articles INTEGER NOT NULL DEFAULT 0 CHECK (open_articles >= 0 AND open_articles <= 1), - account_id INTEGER NOT NULL, - custom_id TEXT NOT NULL CHECK (custom_id != ''), /* Custom ID cannot be empty, it must contain either service-specific ID, or Feeds/id. */ + id $$, + ordr INTEGER NOT NULL CHECK (ordr >= 0), + title TEXT NOT NULL CHECK (title != ''), + description TEXT, + date_created BIGINT, + icon ^^, + category INTEGER NOT NULL CHECK (category >= -1), /* Physical category ID, also root feeds contain -1 here. */ + source TEXT, + update_type INTEGER NOT NULL CHECK (update_type >= 0), + update_interval INTEGER NOT NULL DEFAULT 900 CHECK (update_interval >= 1), + is_off INTEGER NOT NULL DEFAULT 0 CHECK (is_off >= 0 AND is_off <= 1), + is_quiet INTEGER NOT NULL DEFAULT 0 CHECK (is_quiet >= 0 AND is_quiet <= 1), + is_rtl INTEGER NOT NULL DEFAULT 0 CHECK (is_rtl >= 0 AND is_rtl <= 1), + add_any_datetime_articles INTEGER NOT NULL DEFAULT 1 CHECK (add_any_datetime_articles >= 0 AND add_any_datetime_articles <= 1), + datetime_to_avoid BIGINT NOT NULL DEFAULT 0 CHECK (datetime_to_avoid >= 0), + open_articles INTEGER NOT NULL DEFAULT 0 CHECK (open_articles >= 0 AND open_articles <= 1), + account_id INTEGER NOT NULL, + custom_id TEXT NOT NULL CHECK (custom_id != ''), /* Custom ID cannot be empty, it must contain either service-specific ID, or Feeds/id. */ /* Custom column for (serialized) custom account-specific data. */ custom_data TEXT, diff --git a/resources/sql/db_update_mysql_5_6.sql b/resources/sql/db_update_mysql_5_6.sql new file mode 100755 index 000000000..6dbe7a0ee --- /dev/null +++ b/resources/sql/db_update_mysql_5_6.sql @@ -0,0 +1,8 @@ +USE ##; +-- ! +SET FOREIGN_KEY_CHECKS = 0; +-- ! +!! db_update_sqlite_5_6.sql +-- ! +SET FOREIGN_KEY_CHECKS = 1; +-- ! \ No newline at end of file diff --git a/resources/sql/db_update_sqlite_3_4.sql b/resources/sql/db_update_sqlite_3_4.sql index 25b277189..c06a9035c 100644 --- a/resources/sql/db_update_sqlite_3_4.sql +++ b/resources/sql/db_update_sqlite_3_4.sql @@ -13,10 +13,6 @@ CREATE TABLE Feeds ( update_interval INTEGER NOT NULL DEFAULT 900 CHECK (update_interval >= 1), is_off INTEGER NOT NULL DEFAULT 0 CHECK (is_off >= 0 AND is_off <= 1), is_quiet INTEGER NOT NULL DEFAULT 0 CHECK (is_quiet >= 0 AND is_quiet <= 1), - is_rtl INTEGER NOT NULL DEFAULT 0 CHECK (is_rtl >= 0 AND is_rtl <= 1), - add_any_datetime_articles INTEGER NOT NULL DEFAULT 0 CHECK(add_any_datetime_articles >= 0 AND add_any_datetime_articles <= 1), - avoid_old_articles INTEGER NOT NULL DEFAULT 0 CHECK(avoid_old_articles >= 0 AND avoid_old_articles <= 1), - datetime_to_avoid BIGINT NOT NULL DEFAULT 0 CHECK (datetime_to_avoid >= 0), open_articles INTEGER NOT NULL DEFAULT 0 CHECK (open_articles >= 0 AND open_articles <= 1), account_id INTEGER NOT NULL, custom_id TEXT NOT NULL CHECK (custom_id != ''), /* Custom ID cannot be empty, it must contain either service-specific ID, or Feeds/id. */ @@ -26,8 +22,8 @@ CREATE TABLE Feeds ( FOREIGN KEY (account_id) REFERENCES Accounts (id) ON DELETE CASCADE ); -- ! -INSERT INTO Feeds (id, ordr, title, description, date_created, icon, category, source, update_type, update_interval, is_off, is_quiet, is_rtl , add_any_datetime_articles, avoid_old_articles, datetime_to_avoid, open_articles, account_id, custom_id, custom_data) -SELECT id, ordr, title, description, date_created, icon, category, source, update_type, update_interval, is_off, is_quiet, is_rtl , add_any_datetime_articles, avoid_old_articles, datetime_to_avoid, open_articles, account_id, custom_id, custom_data +INSERT INTO Feeds (id, ordr, title, description, date_created, icon, category, source, update_type, update_interval, is_off, open_articles, account_id, custom_id, custom_data) +SELECT id, ordr, title, description, date_created, icon, category, source, update_type, update_interval, is_off, open_articles, account_id, custom_id, custom_data FROM backup_Feeds; -- ! -DROP TABLE backup_Feeds; +DROP TABLE backup_Feeds; \ No newline at end of file diff --git a/resources/sql/db_update_sqlite_5_6.sql b/resources/sql/db_update_sqlite_5_6.sql new file mode 100755 index 000000000..e1703ae1d --- /dev/null +++ b/resources/sql/db_update_sqlite_5_6.sql @@ -0,0 +1,32 @@ +ALTER TABLE Feeds RENAME TO backup_Feeds; +-- ! +CREATE TABLE Feeds ( + id $$, + ordr INTEGER NOT NULL CHECK (ordr >= 0), + title TEXT NOT NULL CHECK (title != ''), + description TEXT, + date_created BIGINT, + icon ^^, + category INTEGER NOT NULL CHECK (category >= -1), /* Physical category ID, also root feeds contain -1 here. */ + source TEXT, + update_type INTEGER NOT NULL CHECK (update_type >= 0), + update_interval INTEGER NOT NULL DEFAULT 900 CHECK (update_interval >= 1), + is_off INTEGER NOT NULL DEFAULT 0 CHECK (is_off >= 0 AND is_off <= 1), + is_quiet INTEGER NOT NULL DEFAULT 0 CHECK (is_quiet >= 0 AND is_quiet <= 1), + is_rtl INTEGER NOT NULL DEFAULT 0 CHECK (is_rtl >= 0 AND is_rtl <= 1), + add_any_datetime_articles INTEGER NOT NULL DEFAULT 1 CHECK (add_any_datetime_articles >= 0 AND add_any_datetime_articles <= 1), + datetime_to_avoid BIGINT NOT NULL DEFAULT 0 CHECK (datetime_to_avoid >= 0), + open_articles INTEGER NOT NULL DEFAULT 0 CHECK (open_articles >= 0 AND open_articles <= 1), + account_id INTEGER NOT NULL, + custom_id TEXT NOT NULL CHECK (custom_id != ''), /* Custom ID cannot be empty, it must contain either service-specific ID, or Feeds/id. */ + /* Custom column for (serialized) custom account-specific data. */ + custom_data TEXT, + + FOREIGN KEY (account_id) REFERENCES Accounts (id) ON DELETE CASCADE +); +-- ! +INSERT INTO Feeds (id, ordr, title, description, date_created, icon, category, source, update_type, update_interval, is_off, is_quiet, open_articles, account_id, custom_id, custom_data) +SELECT id, ordr, title, description, date_created, icon, category, source, update_type, update_interval, is_off, is_quiet, open_articles, account_id, custom_id, custom_data +FROM backup_Feeds; +-- ! +DROP TABLE backup_Feeds; \ No newline at end of file diff --git a/src/librssguard/database/databasequeries.cpp b/src/librssguard/database/databasequeries.cpp index 9e662489b..ee0d5f9a3 100644 --- a/src/librssguard/database/databasequeries.cpp +++ b/src/librssguard/database/databasequeries.cpp @@ -2181,7 +2181,7 @@ void DatabaseQueries::createOverwriteFeed(const QSqlDatabase& db, Feed* feed, in " icon = :icon, category = :category, source = :source, update_type = :update_type," " update_interval = :update_interval, is_off = :is_off, is_quiet = :is_quiet, open_articles =" " :open_articles, is_rtl = :is_rtl, add_any_datetime_articles = :add_any_datetime_articles," - " avoid_old_articles = :avoid_old_articles, datetime_to_avoid = :datetime_to_avoid, account_id" + " datetime_to_avoid = :datetime_to_avoid, account_id" " = :account_id, custom_id = :custom_id, custom_data = :custom_data WHERE id = :id;"); q.bindValue(QSL(":title"), feed->title()); q.bindValue(QSL(":description"), feed->description()); @@ -2198,9 +2198,8 @@ void DatabaseQueries::createOverwriteFeed(const QSqlDatabase& db, Feed* feed, in q.bindValue(QSL(":is_off"), feed->isSwitchedOff()); q.bindValue(QSL(":is_quiet"), feed->isQuiet()); q.bindValue(QSL(":open_articles"), feed->openArticlesDirectly()); - q.bindValue(QSL(":is_rtl"), feed->isRTL()); + q.bindValue(QSL(":is_rtl"), feed->isRtl()); q.bindValue(QSL(":add_any_datetime_articles"), feed->addAnyDatetimeArticles()); - q.bindValue(QSL(":avoid_old_articles"), feed->avoidOldArticles()); q.bindValue(QSL(":datetime_to_avoid"), feed->datetimeToAvoid().toMSecsSinceEpoch()); auto custom_data = feed->customDatabaseData(); diff --git a/src/librssguard/database/databasequeries.h b/src/librssguard/database/databasequeries.h index 833f849ad..b8434031d 100644 --- a/src/librssguard/database/databasequeries.h +++ b/src/librssguard/database/databasequeries.h @@ -353,9 +353,8 @@ Assignment DatabaseQueries::getFeeds(const QSqlDatabase& db, feed->setAutoUpdateInterval(query.value(FDS_DB_UPDATE_INTERVAL_INDEX).toInt()); feed->setIsSwitchedOff(query.value(FDS_DB_IS_OFF_INDEX).toBool()); feed->setIsQuiet(query.value(FDS_DB_IS_QUIET_INDEX).toBool()); - feed->setIsRTL(query.value(FDS_DB_IS_RTL_INDEX).toBool()); + feed->setIsRtl(query.value(FDS_DB_IS_RTL_INDEX).toBool()); feed->setAddAnyDatetimeArticles(query.value(FDS_DB_ADD_ANY_DATETIME_ARTICLES_INDEX).toBool()); - feed->setAvoidOldArticles(query.value(FDS_DB_AVOID_OLD_ARTICLES_INDEX).toBool()); feed->setDatetimeToAvoid(query.value(FDS_DB_DATETIME_TO_AVOID_INDEX).toDateTime()); feed->setOpenArticlesDirectly(query.value(FDS_DB_OPEN_ARTICLES_INDEX).toBool()); diff --git a/src/librssguard/definitions/definitions.h b/src/librssguard/definitions/definitions.h index a2e9b9815..20b4ac480 100644 --- a/src/librssguard/definitions/definitions.h +++ b/src/librssguard/definitions/definitions.h @@ -214,7 +214,7 @@ #define APP_DB_SQLITE_FILE "database.db" // Keep this in sync with schema versions declared in SQL initialization code. -#define APP_DB_SCHEMA_VERSION "5" +#define APP_DB_SCHEMA_VERSION "6" #define APP_DB_UPDATE_FILE_PATTERN "db_update_%1_%2_%3.sql" #define APP_DB_COMMENT_SPLIT "-- !\n" #define APP_DB_INCLUDE_PLACEHOLDER "!!" @@ -297,12 +297,11 @@ #define FDS_DB_IS_QUIET_INDEX 11 #define FDS_DB_IS_RTL_INDEX 12 #define FDS_DB_ADD_ANY_DATETIME_ARTICLES_INDEX 13 -#define FDS_DB_AVOID_OLD_ARTICLES_INDEX 14 -#define FDS_DB_DATETIME_TO_AVOID_INDEX 15 -#define FDS_DB_OPEN_ARTICLES_INDEX 16 -#define FDS_DB_ACCOUNT_ID_INDEX 17 -#define FDS_DB_CUSTOM_ID_INDEX 18 -#define FDS_DB_CUSTOM_DATA_INDEX 19 +#define FDS_DB_DATETIME_TO_AVOID_INDEX 14 +#define FDS_DB_OPEN_ARTICLES_INDEX 15 +#define FDS_DB_ACCOUNT_ID_INDEX 16 +#define FDS_DB_CUSTOM_ID_INDEX 17 +#define FDS_DB_CUSTOM_DATA_INDEX 18 // Indexes of columns for feed models. #define FDS_MODEL_TITLE_INDEX 0 diff --git a/src/librssguard/gui/feedsview.cpp b/src/librssguard/gui/feedsview.cpp index ff3087d81..a54b1f578 100644 --- a/src/librssguard/gui/feedsview.cpp +++ b/src/librssguard/gui/feedsview.cpp @@ -231,12 +231,12 @@ void FeedsView::editSelectedItem() { QSystemTrayIcon::MessageIcon::Warning}); } - RootItem* selected_item = selectedItem(); - emit itemSelected(selected_item); - - // Changes are done, unlock the update master lock. qApp->feedUpdateLock()->unlock(); + + // TODO: NOTE: Make sure to refresh article list if RTL is changed? + // RootItem* selected_item = selectedItem(); + // emit itemSelected(selected_item); } void FeedsView::deleteSelectedItem() { diff --git a/src/librssguard/gui/messagesview.cpp b/src/librssguard/gui/messagesview.cpp index f77ea6a56..c56fa5099 100644 --- a/src/librssguard/gui/messagesview.cpp +++ b/src/librssguard/gui/messagesview.cpp @@ -517,10 +517,12 @@ void MessagesView::loadItem(RootItem* item) { m_sourceModel->loadMessages(item); if (item->toFeed() != nullptr) { - if (item->toFeed()->isRTL()) - setLayoutDirection(Qt::RightToLeft); - else - setLayoutDirection(Qt::LeftToRight); + if (item->toFeed()->isRtl()) { + setLayoutDirection(Qt::LayoutDirection::RightToLeft); + } + else { + setLayoutDirection(Qt::LayoutDirection::LeftToRight); + } } // Messages are loaded, make sure that previously diff --git a/src/librssguard/services/abstract/feed.cpp b/src/librssguard/services/abstract/feed.cpp index 9e2483206..b1d87b36f 100644 --- a/src/librssguard/services/abstract/feed.cpp +++ b/src/librssguard/services/abstract/feed.cpp @@ -20,8 +20,8 @@ Feed::Feed(RootItem* parent) : RootItem(parent), m_source(QString()), m_status(Status::Normal), m_statusString(QString()), m_autoUpdateType(AutoUpdateType::DefaultAutoUpdate), m_autoUpdateInterval(DEFAULT_AUTO_UPDATE_INTERVAL), - m_lastUpdated(QDateTime::currentDateTimeUtc()), m_isSwitchedOff(false), m_isQuiet(false), - m_isRTL(false), m_addAnyDatetimeArticles(false), m_avoidOldArticles(false), m_openArticlesDirectly(false), + m_lastUpdated(QDateTime::currentDateTimeUtc()), m_isSwitchedOff(false), m_isQuiet(false), m_isRtl(false), + m_addAnyDatetimeArticles(false), m_avoidOldArticles(false), m_openArticlesDirectly(false), m_datetimeToAvoid(QDateTime::currentDateTime()), m_messageFilters(QList>()) { setKind(RootItem::Kind::Feed); } @@ -45,10 +45,8 @@ Feed::Feed(const Feed& other) : RootItem(other) { setMessageFilters(other.messageFilters()); setOpenArticlesDirectly(other.openArticlesDirectly()); setAddAnyDatetimeArticles(other.addAnyDatetimeArticles()); - setAvoidOldArticles(other.avoidOldArticles()); - setAvoidOldArticlesEnabled(other.isAvoidOldArticlesEnabled()); setDatetimeToAvoid(other.datetimeToAvoid()); - setIsRTL(other.isRTL()); + setIsRtl(other.isRtl()); setIsSwitchedOff(other.isSwitchedOff()); setIsQuiet(other.isQuiet()); } @@ -195,44 +193,28 @@ void Feed::setOpenArticlesDirectly(bool opn) { m_openArticlesDirectly = opn; } -bool Feed::isRTL() const { - return m_isRTL; +bool Feed::isRtl() const { + return m_isRtl; } -void Feed::setIsRTL(bool rtl) { - m_isRTL = rtl; +void Feed::setIsRtl(bool rtl) { + m_isRtl = rtl; } bool Feed::addAnyDatetimeArticles() const { return m_addAnyDatetimeArticles; } -void Feed::setAddAnyDatetimeArticles(bool addAnyDatetimeArticles) { - m_addAnyDatetimeArticles = addAnyDatetimeArticles; -} - -bool Feed::avoidOldArticles() const { - return m_avoidOldArticles; -} - -void Feed::setAvoidOldArticles(bool avoidDateArticles) { - m_avoidOldArticles = avoidDateArticles; -} - -bool Feed::isAvoidOldArticlesEnabled() const { - return m_avoidOldArticlesEnabled; -} - -void Feed::setAvoidOldArticlesEnabled(bool newAvoidOldArticlesEnabled) { - m_avoidOldArticlesEnabled = newAvoidOldArticlesEnabled; +void Feed::setAddAnyDatetimeArticles(bool add_any_articles) { + m_addAnyDatetimeArticles = add_any_articles; } QDateTime Feed::datetimeToAvoid() const { return m_datetimeToAvoid; } -void Feed::setDatetimeToAvoid(const QDateTime &dateTime) { - m_datetimeToAvoid = dateTime; +void Feed::setDatetimeToAvoid(const QDateTime& dt) { + m_datetimeToAvoid = dt; } void Feed::appendMessageFilter(MessageFilter* filter) { diff --git a/src/librssguard/services/abstract/feed.h b/src/librssguard/services/abstract/feed.h index aec96f2d6..5cb16ddea 100644 --- a/src/librssguard/services/abstract/feed.h +++ b/src/librssguard/services/abstract/feed.h @@ -83,21 +83,14 @@ class Feed : public RootItem { QDateTime lastUpdated() const; void setLastUpdated(const QDateTime& last_updated); - bool isRTL() const; - void setIsRTL(bool rtl); + bool isRtl() const; + void setIsRtl(bool rtl); bool addAnyDatetimeArticles() const; - void setAddAnyDatetimeArticles(bool addAnyDatetimeArticles); - - bool avoidOldArticles() const; - void setAvoidOldArticles(bool avoidDateArticles); - - bool isAvoidOldArticlesEnabled() const; - void setAvoidOldArticlesEnabled(bool newAvoidOldArticlesEnabled); + void setAddAnyDatetimeArticles(bool add_any_articles); QDateTime datetimeToAvoid() const; - void setDatetimeToAvoid(const QDateTime &dateTime); - + void setDatetimeToAvoid(const QDateTime& dt); public slots: virtual void updateCounts(bool including_total_count); @@ -116,7 +109,7 @@ class Feed : public RootItem { bool m_isSwitchedOff; bool m_isQuiet; bool m_openArticlesDirectly; - bool m_isRTL; + bool m_isRtl; bool m_addAnyDatetimeArticles; bool m_avoidOldArticles; bool m_avoidOldArticlesEnabled; diff --git a/src/librssguard/services/abstract/gui/formfeeddetails.cpp b/src/librssguard/services/abstract/gui/formfeeddetails.cpp index b164b41b7..df691bc0b 100644 --- a/src/librssguard/services/abstract/gui/formfeeddetails.cpp +++ b/src/librssguard/services/abstract/gui/formfeeddetails.cpp @@ -49,9 +49,8 @@ void FormFeedDetails::apply() { .toInt())); m_feed->setAutoUpdateInterval(int(m_ui->m_spinAutoUpdateInterval->value())); m_feed->setOpenArticlesDirectly(m_ui->m_cbOpenArticlesAutomatically->isChecked()); - m_feed->setIsRTL(m_ui->m_cbFeedRTL->isChecked()); + m_feed->setIsRtl(m_ui->m_cbFeedRTL->isChecked()); m_feed->setAddAnyDatetimeArticles(m_ui->m_cbAddAnyDateArticles->isChecked()); - m_feed->setAvoidOldArticles(m_ui->m_gbAvoidOldArticles->isChecked()); m_feed->setDatetimeToAvoid(m_ui->m_dtDateTimeToAvoid->dateTime()); m_feed->setIsSwitchedOff(m_ui->m_cbDisableFeed->isChecked()); m_feed->setIsQuiet(m_ui->m_cbSuppressFeed->isChecked()); @@ -88,9 +87,7 @@ void FormFeedDetails::createConnections() { connect(m_ui->m_cbAddAnyDateArticles, &QCheckBox::toggled, this, [this](bool checked) { m_ui->m_gbAvoidOldArticles->setEnabled(!checked); - m_feed->setAvoidOldArticlesEnabled(!checked); }); - } void FormFeedDetails::loadFeedData() { @@ -107,9 +104,8 @@ void FormFeedDetails::loadFeedData() { ->setCurrentIndex(m_ui->m_cmbAutoUpdateType->findData(QVariant::fromValue(int(m_feed->autoUpdateType())))); m_ui->m_spinAutoUpdateInterval->setValue(m_feed->autoUpdateInterval()); m_ui->m_cbOpenArticlesAutomatically->setChecked(m_feed->openArticlesDirectly()); - m_ui->m_cbFeedRTL->setChecked(m_feed->isRTL()); + m_ui->m_cbFeedRTL->setChecked(m_feed->isRtl()); m_ui->m_cbAddAnyDateArticles->setChecked(m_feed->addAnyDatetimeArticles()); - m_ui->m_gbAvoidOldArticles->setChecked(m_feed->avoidOldArticles()); m_ui->m_gbAvoidOldArticles->setEnabled(!m_feed->addAnyDatetimeArticles()); m_ui->m_dtDateTimeToAvoid->setDateTime(m_feed->datetimeToAvoid()); m_ui->m_cbDisableFeed->setChecked(m_feed->isSwitchedOff()); diff --git a/src/librssguard/services/abstract/serviceroot.cpp b/src/librssguard/services/abstract/serviceroot.cpp index d28811068..01ba15084 100644 --- a/src/librssguard/services/abstract/serviceroot.cpp +++ b/src/librssguard/services/abstract/serviceroot.cpp @@ -384,9 +384,8 @@ QMap ServiceRoot::storeCustomFeedsData() { feed_custom_data.insert(QSL("is_off"), feed->isSwitchedOff()); feed_custom_data.insert(QSL("is_quiet"), feed->isQuiet()); feed_custom_data.insert(QSL("open_articles_directly"), feed->openArticlesDirectly()); - feed_custom_data.insert(QSL("is_rtl"), feed->isRTL()); + feed_custom_data.insert(QSL("is_rtl"), feed->isRtl()); feed_custom_data.insert(QSL("add_any_datetime_articles"), feed->addAnyDatetimeArticles()); - feed_custom_data.insert(QSL("avoid_old_articles"), feed->avoidOldArticles()); feed_custom_data.insert(QSL("datetime_to_avoid"), feed->datetimeToAvoid().toMSecsSinceEpoch()); // NOTE: This is here specifically to be able to restore custom sort order. @@ -437,10 +436,9 @@ void ServiceRoot::restoreCustomFeedsData(const QMap& data, feed->setIsSwitchedOff(feed_custom_data.value(QSL("is_off")).toBool()); feed->setIsQuiet(feed_custom_data.value(QSL("is_quiet")).toBool()); feed->setOpenArticlesDirectly(feed_custom_data.value(QSL("open_articles_directly")).toBool()); - feed->setIsRTL(feed_custom_data.value(QSL("is_rtl")).toBool()); + feed->setIsRtl(feed_custom_data.value(QSL("is_rtl")).toBool()); feed->setAddAnyDatetimeArticles(feed_custom_data.value(QSL("add_any_datetime_articles")).toBool()); - feed->setAvoidOldArticles(feed_custom_data.value(QSL("avoid_date_message")).toBool()); - feed->setDatetimeToAvoid(feed_custom_data.value(QSL("avoid_message_datetime")).toDateTime()); + feed->setDatetimeToAvoid(feed_custom_data.value(QSL("datetime_to_avoid")).toDateTime()); } } } diff --git a/src/librssguard/services/standard/standardserviceroot.cpp b/src/librssguard/services/standard/standardserviceroot.cpp index 6181525bd..d820413d1 100644 --- a/src/librssguard/services/standard/standardserviceroot.cpp +++ b/src/librssguard/services/standard/standardserviceroot.cpp @@ -256,21 +256,26 @@ QList StandardServiceRoot::obtainNewMessages(Feed* feed, mess.m_feedId = feed->customId(); } - if (!feed->addAnyDatetimeArticles()) { QDateTime datetimeToAvoid; - if (feed->isAvoidOldArticlesEnabled() && feed->avoidOldArticles()) + if (feed->datetimeToAvoid().isValid()) { datetimeToAvoid = feed->datetimeToAvoid(); - else if (qApp->settings()->value(GROUP(Messages), SETTING(Messages::AvoidOldArticles)).toBool()) - datetimeToAvoid = qApp->settings()->value(GROUP(Messages), SETTING(Messages::DateTimeToAvoidArticle)).toDateTime(); - else + } + else if (qApp->settings()->value(GROUP(Messages), SETTING(Messages::AvoidOldArticles)).toBool()) { + datetimeToAvoid = + qApp->settings()->value(GROUP(Messages), SETTING(Messages::DateTimeToAvoidArticle)).toDateTime(); + } + else { return messages; + } - for (int i = 0; i < messages.size(); i++) - if (messages.at(i).m_created < datetimeToAvoid) + for (int i = 0; i < messages.size(); i++) { + if (messages.at(i).m_createdFromFeed && messages.at(i).m_created < datetimeToAvoid) { messages.removeAt(i--); + } + } } return messages; From 05a28d0cad9d82641c1d322e32d6cd11c905654e Mon Sep 17 00:00:00 2001 From: Martin Rotter Date: Wed, 26 Jul 2023 09:26:29 +0200 Subject: [PATCH 05/14] bit better logic for dt article decisions --- src/librssguard/gui/settings/settingsfeedsmessages.cpp | 10 ++++++---- .../services/standard/standardserviceroot.cpp | 10 ++++------ 2 files changed, 10 insertions(+), 10 deletions(-) diff --git a/src/librssguard/gui/settings/settingsfeedsmessages.cpp b/src/librssguard/gui/settings/settingsfeedsmessages.cpp index 0e8523a40..cee73900a 100644 --- a/src/librssguard/gui/settings/settingsfeedsmessages.cpp +++ b/src/librssguard/gui/settings/settingsfeedsmessages.cpp @@ -197,11 +197,11 @@ SettingsFeedsMessages::SettingsFeedsMessages(Settings* settings, QWidget* parent m_ui->m_spinFeedUpdateTimeout->setSuffix(QSL(" ") + m_ui->m_spinFeedUpdateTimeout->suffix()); } + m_ui->m_dtDateTimeToAvoid->setDisplayFormat(qApp->localization()->loadedLocale().dateFormat()); + connect(m_ui->m_gbAvoidOldArticles, &QGroupBox::toggled, this, &SettingsFeedsMessages::dirtifySettings); - connect(m_ui->m_dtDateTimeToAvoid, &QDateTimeEdit::dateTimeChanged, this, &SettingsFeedsMessages::dirtifySettings); - m_ui->m_spinRelativeArticleTime->setValue(-1); } @@ -265,8 +265,10 @@ void SettingsFeedsMessages::loadSettings() { ->setChecked(settings()->value(GROUP(Feeds), SETTING(Feeds::AutoUpdateOnlyUnfocused)).toBool()); m_ui->m_spinAutoUpdateInterval->setValue(settings()->value(GROUP(Feeds), SETTING(Feeds::AutoUpdateInterval)).toInt()); m_ui->m_spinFeedUpdateTimeout->setValue(settings()->value(GROUP(Feeds), SETTING(Feeds::UpdateTimeout)).toInt()); - m_ui->m_gbAvoidOldArticles->setChecked(settings()->value(GROUP(Messages), SETTING(Messages::AvoidOldArticles)).toBool()); - m_ui->m_dtDateTimeToAvoid->setDateTime(settings()->value(GROUP(Messages), SETTING(Messages::DateTimeToAvoidArticle)).toDateTime()); + m_ui->m_gbAvoidOldArticles + ->setChecked(settings()->value(GROUP(Messages), SETTING(Messages::AvoidOldArticles)).toBool()); + m_ui->m_dtDateTimeToAvoid + ->setDateTime(settings()->value(GROUP(Messages), SETTING(Messages::DateTimeToAvoidArticle)).toDateTime()); m_ui->m_cmbFastAutoUpdate->setChecked(settings()->value(GROUP(Feeds), SETTING(Feeds::FastAutoUpdate)).toBool()); m_ui->m_checkUpdateAllFeedsOnStartup ->setChecked(settings()->value(GROUP(Feeds), SETTING(Feeds::FeedsUpdateOnStartup)).toBool()); diff --git a/src/librssguard/services/standard/standardserviceroot.cpp b/src/librssguard/services/standard/standardserviceroot.cpp index d820413d1..9361bb3a2 100644 --- a/src/librssguard/services/standard/standardserviceroot.cpp +++ b/src/librssguard/services/standard/standardserviceroot.cpp @@ -257,22 +257,20 @@ QList StandardServiceRoot::obtainNewMessages(Feed* feed, } if (!feed->addAnyDatetimeArticles()) { - - QDateTime datetimeToAvoid; + QDateTime dt_to_avoid; if (feed->datetimeToAvoid().isValid()) { - datetimeToAvoid = feed->datetimeToAvoid(); + dt_to_avoid = feed->datetimeToAvoid(); } else if (qApp->settings()->value(GROUP(Messages), SETTING(Messages::AvoidOldArticles)).toBool()) { - datetimeToAvoid = - qApp->settings()->value(GROUP(Messages), SETTING(Messages::DateTimeToAvoidArticle)).toDateTime(); + dt_to_avoid = qApp->settings()->value(GROUP(Messages), SETTING(Messages::DateTimeToAvoidArticle)).toDateTime(); } else { return messages; } for (int i = 0; i < messages.size(); i++) { - if (messages.at(i).m_createdFromFeed && messages.at(i).m_created < datetimeToAvoid) { + if (messages.at(i).m_createdFromFeed && messages.at(i).m_created < dt_to_avoid) { messages.removeAt(i--); } } From 020f8241008d901a85756371d9d898d002301112 Mon Sep 17 00:00:00 2001 From: Martin Rotter Date: Wed, 26 Jul 2023 09:34:42 +0200 Subject: [PATCH 06/14] move rtl checkbox to another tab --- .../services/abstract/gui/formfeeddetails.ui | 37 ++++++++++--------- 1 file changed, 19 insertions(+), 18 deletions(-) diff --git a/src/librssguard/services/abstract/gui/formfeeddetails.ui b/src/librssguard/services/abstract/gui/formfeeddetails.ui index 8714606f0..06cbe7ebb 100644 --- a/src/librssguard/services/abstract/gui/formfeeddetails.ui +++ b/src/librssguard/services/abstract/gui/formfeeddetails.ui @@ -60,30 +60,20 @@ - - - Right-to-left layout - - - - Qt::Horizontal - + Add articles with any date into the database - - true - - + true @@ -131,17 +121,24 @@ Miscellaneous - + + + + Ignore notifications for this feed + + + + Disable this feed - - + + - Ignore notifications for this feed + Right-to-left layout @@ -176,8 +173,12 @@ m_cmbAutoUpdateType m_spinAutoUpdateInterval m_cbOpenArticlesAutomatically + m_cbAddAnyDateArticles + m_gbAvoidOldArticles + m_dtDateTimeToAvoid m_cbSuppressFeed m_cbDisableFeed + m_cbFeedRTL @@ -188,8 +189,8 @@ reject() - 331 - 556 + 340 + 580 286 From 43cdc5f128a007c69b42ceb453940c76fd6d8ffb Mon Sep 17 00:00:00 2001 From: Martin Rotter Date: Wed, 26 Jul 2023 11:03:59 +0200 Subject: [PATCH 07/14] make feed settings consistent with database --- src/librssguard/database/databasequeries.cpp | 3 ++- src/librssguard/database/databasequeries.h | 6 +++++- src/librssguard/services/abstract/gui/formfeeddetails.cpp | 5 +++-- 3 files changed, 10 insertions(+), 4 deletions(-) diff --git a/src/librssguard/database/databasequeries.cpp b/src/librssguard/database/databasequeries.cpp index ee0d5f9a3..7d4eaf8bd 100644 --- a/src/librssguard/database/databasequeries.cpp +++ b/src/librssguard/database/databasequeries.cpp @@ -2200,7 +2200,8 @@ void DatabaseQueries::createOverwriteFeed(const QSqlDatabase& db, Feed* feed, in q.bindValue(QSL(":open_articles"), feed->openArticlesDirectly()); q.bindValue(QSL(":is_rtl"), feed->isRtl()); q.bindValue(QSL(":add_any_datetime_articles"), feed->addAnyDatetimeArticles()); - q.bindValue(QSL(":datetime_to_avoid"), feed->datetimeToAvoid().toMSecsSinceEpoch()); + q.bindValue(QSL(":datetime_to_avoid"), + feed->datetimeToAvoid().isValid() ? feed->datetimeToAvoid().toMSecsSinceEpoch() : 0); auto custom_data = feed->customDatabaseData(); QString serialized_custom_data = serializeCustomData(custom_data); diff --git a/src/librssguard/database/databasequeries.h b/src/librssguard/database/databasequeries.h index b8434031d..78dc8f12b 100644 --- a/src/librssguard/database/databasequeries.h +++ b/src/librssguard/database/databasequeries.h @@ -355,7 +355,11 @@ Assignment DatabaseQueries::getFeeds(const QSqlDatabase& db, feed->setIsQuiet(query.value(FDS_DB_IS_QUIET_INDEX).toBool()); feed->setIsRtl(query.value(FDS_DB_IS_RTL_INDEX).toBool()); feed->setAddAnyDatetimeArticles(query.value(FDS_DB_ADD_ANY_DATETIME_ARTICLES_INDEX).toBool()); - feed->setDatetimeToAvoid(query.value(FDS_DB_DATETIME_TO_AVOID_INDEX).toDateTime()); + + auto dt_avoid = query.value(FDS_DB_DATETIME_TO_AVOID_INDEX).value(); + + feed->setDatetimeToAvoid(dt_avoid > 0 ? TextFactory::parseDateTime(dt_avoid) : QDateTime()); + feed->setOpenArticlesDirectly(query.value(FDS_DB_OPEN_ARTICLES_INDEX).toBool()); qDebugNN << LOGSEC_CORE << "Custom ID of feed when loading from DB is" << QUOTE_W_SPACE_DOT(feed->customId()); diff --git a/src/librssguard/services/abstract/gui/formfeeddetails.cpp b/src/librssguard/services/abstract/gui/formfeeddetails.cpp index df691bc0b..0bf8a27aa 100644 --- a/src/librssguard/services/abstract/gui/formfeeddetails.cpp +++ b/src/librssguard/services/abstract/gui/formfeeddetails.cpp @@ -51,7 +51,8 @@ void FormFeedDetails::apply() { m_feed->setOpenArticlesDirectly(m_ui->m_cbOpenArticlesAutomatically->isChecked()); m_feed->setIsRtl(m_ui->m_cbFeedRTL->isChecked()); m_feed->setAddAnyDatetimeArticles(m_ui->m_cbAddAnyDateArticles->isChecked()); - m_feed->setDatetimeToAvoid(m_ui->m_dtDateTimeToAvoid->dateTime()); + m_feed->setDatetimeToAvoid(m_ui->m_gbAvoidOldArticles->isChecked() ? m_ui->m_dtDateTimeToAvoid->dateTime() + : QDateTime()); m_feed->setIsSwitchedOff(m_ui->m_cbDisableFeed->isChecked()); m_feed->setIsQuiet(m_ui->m_cbSuppressFeed->isChecked()); @@ -106,7 +107,7 @@ void FormFeedDetails::loadFeedData() { m_ui->m_cbOpenArticlesAutomatically->setChecked(m_feed->openArticlesDirectly()); m_ui->m_cbFeedRTL->setChecked(m_feed->isRtl()); m_ui->m_cbAddAnyDateArticles->setChecked(m_feed->addAnyDatetimeArticles()); - m_ui->m_gbAvoidOldArticles->setEnabled(!m_feed->addAnyDatetimeArticles()); + m_ui->m_gbAvoidOldArticles->setChecked(m_feed->datetimeToAvoid().isValid()); m_ui->m_dtDateTimeToAvoid->setDateTime(m_feed->datetimeToAvoid()); m_ui->m_cbDisableFeed->setChecked(m_feed->isSwitchedOff()); m_ui->m_cbSuppressFeed->setChecked(m_feed->isQuiet()); From 21a8210124410a1d4db084e50cc6fda24afa31dc Mon Sep 17 00:00:00 2001 From: Martin Rotter Date: Wed, 26 Jul 2023 11:15:21 +0200 Subject: [PATCH 08/14] log removed articles --- src/librssguard/services/standard/standardserviceroot.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/src/librssguard/services/standard/standardserviceroot.cpp b/src/librssguard/services/standard/standardserviceroot.cpp index 9361bb3a2..73f7b0312 100644 --- a/src/librssguard/services/standard/standardserviceroot.cpp +++ b/src/librssguard/services/standard/standardserviceroot.cpp @@ -271,6 +271,7 @@ QList StandardServiceRoot::obtainNewMessages(Feed* feed, for (int i = 0; i < messages.size(); i++) { if (messages.at(i).m_createdFromFeed && messages.at(i).m_created < dt_to_avoid) { + qDebugNN << LOGSEC_CORE << "Removing message" << QUOTE_W_SPACE(messages.at(i).m_title) << "for being too old."; messages.removeAt(i--); } } From 126ed60b04cece2d70194ab739ae34f4196c251c Mon Sep 17 00:00:00 2001 From: Martin Rotter Date: Wed, 26 Jul 2023 13:46:31 +0200 Subject: [PATCH 09/14] save --- src/librssguard/gui/messagesview.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/librssguard/gui/messagesview.cpp b/src/librssguard/gui/messagesview.cpp index c56fa5099..7a73f68e2 100644 --- a/src/librssguard/gui/messagesview.cpp +++ b/src/librssguard/gui/messagesview.cpp @@ -516,7 +516,7 @@ void MessagesView::loadItem(RootItem* item) { sort(col, ord, false, true, false, true); m_sourceModel->loadMessages(item); - if (item->toFeed() != nullptr) { + if (item->kind() == RootItem::Kind::Feed) { if (item->toFeed()->isRtl()) { setLayoutDirection(Qt::LayoutDirection::RightToLeft); } From 166ffccf828db8c16067214113339b639fa0e300 Mon Sep 17 00:00:00 2001 From: Martin Rotter Date: Thu, 27 Jul 2023 06:34:59 +0200 Subject: [PATCH 10/14] save --- src/librssguard/gui/messagepreviewer.cpp | 1 - .../gui/webviewers/qtextbrowser/textbrowserviewer.cpp | 6 ++++++ 2 files changed, 6 insertions(+), 1 deletion(-) diff --git a/src/librssguard/gui/messagepreviewer.cpp b/src/librssguard/gui/messagepreviewer.cpp index 1384fe6aa..198629210 100644 --- a/src/librssguard/gui/messagepreviewer.cpp +++ b/src/librssguard/gui/messagepreviewer.cpp @@ -175,7 +175,6 @@ void MessagePreviewer::loadMessage(const Message& message, RootItem* root) { } else { ensureDefaultBrowserVisible(); - m_msgBrowser->loadMessages({message}, m_root); } } diff --git a/src/librssguard/gui/webviewers/qtextbrowser/textbrowserviewer.cpp b/src/librssguard/gui/webviewers/qtextbrowser/textbrowserviewer.cpp index 5593a67b1..73640b380 100644 --- a/src/librssguard/gui/webviewers/qtextbrowser/textbrowserviewer.cpp +++ b/src/librssguard/gui/webviewers/qtextbrowser/textbrowserviewer.cpp @@ -302,6 +302,12 @@ void TextBrowserViewer::loadMessages(const QList& messages, RootItem* r // auto html_messages = qApp->skins()->generateHtmlOfArticles(messages, root); setHtml(html_messages.m_html, html_messages.m_baseUrl); + + // TODO: pokračovat + QTextOption op; + op.setTextDirection(Qt::RightToLeft); + document()->setDefaultTextOption(op); + emit loadingFinished(true); } From 73d28d23e2c554b26a14e055e1dd919d1c7304ec Mon Sep 17 00:00:00 2001 From: Martin Rotter Date: Fri, 28 Jul 2023 08:36:06 +0200 Subject: [PATCH 11/14] make old article dropping work across all plugins, also syncable plugins would have to take this into account for more efficient way so that those article sare even not downloaded needlessly --- src/librssguard/core/feeddownloader.cpp | 22 +++++++++++++++++++ .../services/standard/standardserviceroot.cpp | 21 ------------------ 2 files changed, 22 insertions(+), 21 deletions(-) diff --git a/src/librssguard/core/feeddownloader.cpp b/src/librssguard/core/feeddownloader.cpp index 181d49fcc..caefdef2e 100644 --- a/src/librssguard/core/feeddownloader.cpp +++ b/src/librssguard/core/feeddownloader.cpp @@ -238,6 +238,28 @@ void FeedDownloader::updateOneFeed(ServiceRoot* acc, msg.sanitize(feed, fix_future_datetimes); } + if (!feed->addAnyDatetimeArticles()) { + QDateTime dt_to_avoid; + + if (feed->datetimeToAvoid().isValid()) { + dt_to_avoid = feed->datetimeToAvoid(); + } + else if (qApp->settings()->value(GROUP(Messages), SETTING(Messages::AvoidOldArticles)).toBool()) { + dt_to_avoid = qApp->settings()->value(GROUP(Messages), SETTING(Messages::DateTimeToAvoidArticle)).toDateTime(); + } + + if (dt_to_avoid.isValid()) { + for (int i = 0; i < msgs.size(); i++) { + const auto& mss = msgs.at(i); + + if (mss.m_createdFromFeed && mss.m_created < dt_to_avoid) { + qDebugNN << LOGSEC_CORE << "Removing message" << QUOTE_W_SPACE(mss.m_title) << "for being too old."; + msgs.removeAt(i--); + } + } + } + } + if (!feed->messageFilters().isEmpty()) { tmr.restart(); diff --git a/src/librssguard/services/standard/standardserviceroot.cpp b/src/librssguard/services/standard/standardserviceroot.cpp index 73f7b0312..bb1177070 100644 --- a/src/librssguard/services/standard/standardserviceroot.cpp +++ b/src/librssguard/services/standard/standardserviceroot.cpp @@ -256,27 +256,6 @@ QList StandardServiceRoot::obtainNewMessages(Feed* feed, mess.m_feedId = feed->customId(); } - if (!feed->addAnyDatetimeArticles()) { - QDateTime dt_to_avoid; - - if (feed->datetimeToAvoid().isValid()) { - dt_to_avoid = feed->datetimeToAvoid(); - } - else if (qApp->settings()->value(GROUP(Messages), SETTING(Messages::AvoidOldArticles)).toBool()) { - dt_to_avoid = qApp->settings()->value(GROUP(Messages), SETTING(Messages::DateTimeToAvoidArticle)).toDateTime(); - } - else { - return messages; - } - - for (int i = 0; i < messages.size(); i++) { - if (messages.at(i).m_createdFromFeed && messages.at(i).m_created < dt_to_avoid) { - qDebugNN << LOGSEC_CORE << "Removing message" << QUOTE_W_SPACE(messages.at(i).m_title) << "for being too old."; - messages.removeAt(i--); - } - } - } - return messages; } From 066221e2ef8b7bd60f55bf8613ee0e9e0344a74d Mon Sep 17 00:00:00 2001 From: Martin Rotter Date: Fri, 28 Jul 2023 11:07:57 +0200 Subject: [PATCH 12/14] make article previewers support RTL too, atleast naive approach at this point --- .../skins/nudus-base/html_single_message.html | 2 +- .../qtextbrowser/textbrowserviewer.cpp | 15 +++------------ src/librssguard/miscellaneous/skinfactory.cpp | 17 +++++++++++------ 3 files changed, 15 insertions(+), 19 deletions(-) diff --git a/resources/skins/nudus-base/html_single_message.html b/resources/skins/nudus-base/html_single_message.html index f675f11fd..7aa4c3e5d 100644 --- a/resources/skins/nudus-base/html_single_message.html +++ b/resources/skins/nudus-base/html_single_message.html @@ -1,4 +1,4 @@ -
+
%7
diff --git a/src/librssguard/gui/webviewers/qtextbrowser/textbrowserviewer.cpp b/src/librssguard/gui/webviewers/qtextbrowser/textbrowserviewer.cpp index 73640b380..f958c53af 100644 --- a/src/librssguard/gui/webviewers/qtextbrowser/textbrowserviewer.cpp +++ b/src/librssguard/gui/webviewers/qtextbrowser/textbrowserviewer.cpp @@ -303,9 +303,10 @@ void TextBrowserViewer::loadMessages(const QList& messages, RootItem* r setHtml(html_messages.m_html, html_messages.m_baseUrl); - // TODO: pokračovat + bool is_rtl_feed = root != nullptr && root->kind() == RootItem::Kind::Feed && qobject_cast(root)->isRtl(); + QTextOption op; - op.setTextDirection(Qt::RightToLeft); + op.setTextDirection(is_rtl_feed ? Qt::LayoutDirection::RightToLeft : Qt::LayoutDirection::LeftToRight); document()->setDefaultTextOption(op); emit loadingFinished(true); @@ -550,16 +551,6 @@ void TextBrowserViewer::setHtml(const QString& html, const QUrl& base_url) { } setVerticalScrollBarPosition(0.0); - - // TODO: implement RTL for viewers somehow? - /* - auto to = document()->defaultTextOption(); - - to.setTextDirection(Qt::LayoutDirection::RightToLeft); - to.setAlignment(Qt::AlignmentFlag::AlignRight); - - document()->setDefaultTextOption(to); - */ } void TextBrowserViewer::setHtmlPrivate(const QString& html, const QUrl& base_url) { diff --git a/src/librssguard/miscellaneous/skinfactory.cpp b/src/librssguard/miscellaneous/skinfactory.cpp index ee6c6c708..1ea080271 100644 --- a/src/librssguard/miscellaneous/skinfactory.cpp +++ b/src/librssguard/miscellaneous/skinfactory.cpp @@ -231,6 +231,15 @@ PreparedHtml SkinFactory::generateHtmlOfArticles(const QList& messages, const auto forced_img_size = qApp->settings()->value(GROUP(Messages), SETTING(Messages::MessageHeadImageHeight)).toInt(); + auto* feed = root != nullptr + ? root->getParentServiceRoot() + ->getItemFromSubTree([messages](const RootItem* it) { + return it->kind() == RootItem::Kind::Feed && it->customId() == messages.at(0).m_feedId; + }) + ->toFeed() + : nullptr; + bool is_rtl_feed = feed != nullptr && feed->isRtl(); + for (const Message& message : messages) { QString enclosures; QString enclosure_images; @@ -274,17 +283,13 @@ PreparedHtml SkinFactory::generateHtmlOfArticles(const QList& messages, msg_date, enclosures, enclosure_images, - QString::number(message.m_id))); + QString::number(message.m_id), + is_rtl_feed ? QSL("rtl") : QSL("ltr"))); } QString msg_contents = skin.m_layoutMarkupWrapper.arg(messages.size() == 1 ? messages.at(0).m_title : tr("Newspaper view"), messages_layout); - auto* feed = root->getParentServiceRoot() - ->getItemFromSubTree([messages](const RootItem* it) { - return it->kind() == RootItem::Kind::Feed && it->customId() == messages.at(0).m_feedId; - }) - ->toFeed(); QString base_url; if (feed != nullptr) { From 8133fce9e8bba32a962106d2efbc748a443a2c1a Mon Sep 17 00:00:00 2001 From: Martin Rotter Date: Mon, 31 Jul 2023 08:33:04 +0200 Subject: [PATCH 13/14] correctly use RTL text for rtl feeds --- src/librssguard/definitions/definitions.h | 3 ++- src/librssguard/gui/messagesview.cpp | 3 +++ .../gui/reusable/styleditemdelegatewithoutfocus.cpp | 6 ++++++ src/librssguard/services/abstract/feed.cpp | 3 +++ 4 files changed, 14 insertions(+), 1 deletion(-) diff --git a/src/librssguard/definitions/definitions.h b/src/librssguard/definitions/definitions.h index 20b4ac480..a9e846812 100644 --- a/src/librssguard/definitions/definitions.h +++ b/src/librssguard/definitions/definitions.h @@ -50,7 +50,8 @@ #define MSG_SCORE_MIN 0.0 #define LOWER_TITLE_ROLE 64 -#define HIGHLIGHTED_FOREGROUND_TITLE_ROLE 128 +#define HIGHLIGHTED_FOREGROUND_TITLE_ROLE 65 +#define TEXT_DIRECTION_ROLE 66 #define SOUNDS_BUILTIN_DIRECTORY ":/sounds" #define ARGUMENTS_LIST_SEPARATOR "\n" diff --git a/src/librssguard/gui/messagesview.cpp b/src/librssguard/gui/messagesview.cpp index 7a73f68e2..a80b15573 100644 --- a/src/librssguard/gui/messagesview.cpp +++ b/src/librssguard/gui/messagesview.cpp @@ -524,6 +524,9 @@ void MessagesView::loadItem(RootItem* item) { setLayoutDirection(Qt::LayoutDirection::LeftToRight); } } + else { + setLayoutDirection(Qt::LayoutDirection::LeftToRight); + } // Messages are loaded, make sure that previously // active message is not shown in browser. diff --git a/src/librssguard/gui/reusable/styleditemdelegatewithoutfocus.cpp b/src/librssguard/gui/reusable/styleditemdelegatewithoutfocus.cpp index 1b1c09d7c..bf26fbffe 100644 --- a/src/librssguard/gui/reusable/styleditemdelegatewithoutfocus.cpp +++ b/src/librssguard/gui/reusable/styleditemdelegatewithoutfocus.cpp @@ -16,6 +16,12 @@ void StyledItemDelegateWithoutFocus::paint(QPainter* painter, item_option.state = item_option.state ^ QStyle::StateFlag::State_HasFocus; } + bool rtl = index.data(TEXT_DIRECTION_ROLE).value() == Qt::LayoutDirection::RightToLeft; + + if (rtl) { + item_option.direction = Qt::LayoutDirection::RightToLeft; + } + if ((item_option.state & QStyle::StateFlag::State_Selected) == QStyle::StateFlag::State_Selected && index.data(Qt::ItemDataRole::ForegroundRole).isValid()) { item_option.palette.setColor(QPalette::ColorRole::HighlightedText, diff --git a/src/librssguard/services/abstract/feed.cpp b/src/librssguard/services/abstract/feed.cpp index b1d87b36f..0aea35c6a 100644 --- a/src/librssguard/services/abstract/feed.cpp +++ b/src/librssguard/services/abstract/feed.cpp @@ -82,6 +82,9 @@ QVariant Feed::data(int column, int role) const { return QVariant(); } + case TEXT_DIRECTION_ROLE: + return isRtl() ? Qt::LayoutDirection::RightToLeft : Qt::LayoutDirection::LayoutDirectionAuto; + case Qt::ItemDataRole::ForegroundRole: switch (status()) { case Status::NewMessages: From 388c9297ac47d063e05aed8477d820ee73c11461 Mon Sep 17 00:00:00 2001 From: Martin Rotter Date: Mon, 31 Jul 2023 09:49:37 +0200 Subject: [PATCH 14/14] even better implementation of RTL which now works even when parent node is selected and RTL is automatically correctly decided for each individual article --- src/librssguard/core/feedsproxymodel.cpp | 2 ++ src/librssguard/core/message.cpp | 10 ++++++--- src/librssguard/core/message.h | 1 + src/librssguard/core/messagesmodel.cpp | 22 +++++++++++++++++-- .../core/messagesmodelsqllayer.cpp | 4 +++- src/librssguard/database/databasequeries.cpp | 3 ++- src/librssguard/definitions/definitions.h | 7 +++--- src/librssguard/gui/messagesview.cpp | 3 +++ .../qtextbrowser/textbrowserviewer.cpp | 13 +++++++++-- src/librssguard/miscellaneous/skinfactory.cpp | 4 +++- .../services/gmail/gui/emailpreviewer.cpp | 2 -- 11 files changed, 56 insertions(+), 15 deletions(-) diff --git a/src/librssguard/core/feedsproxymodel.cpp b/src/librssguard/core/feedsproxymodel.cpp index 69db2a21d..b82fd016f 100644 --- a/src/librssguard/core/feedsproxymodel.cpp +++ b/src/librssguard/core/feedsproxymodel.cpp @@ -322,9 +322,11 @@ bool FeedsProxyModel::lessThan(const QModelIndex& left, const QModelIndex& right bool FeedsProxyModel::filterAcceptsRow(int source_row, const QModelIndex& source_parent) const { bool should_show = filterAcceptsRowInternal(source_row, source_parent); + /* qDebugNN << LOGSEC_CORE << "Filter accepts row" << QUOTE_W_SPACE(m_sourceModel->itemForIndex(m_sourceModel->index(source_row, 0, source_parent))->title()) << "and filter result is:" << QUOTE_W_SPACE_DOT(should_show); + */ /* if (should_show && (!filterRegularExpression().pattern().isEmpty() || diff --git a/src/librssguard/core/message.cpp b/src/librssguard/core/message.cpp index 74de1be48..8ec33f85a 100644 --- a/src/librssguard/core/message.cpp +++ b/src/librssguard/core/message.cpp @@ -68,7 +68,7 @@ Message::Message() { m_categories = QList(); m_accountId = m_id = 0; m_score = 0.0; - m_isRead = m_isImportant = m_isDeleted = false; + m_isRead = m_isImportant = m_isDeleted = m_isRtl = false; m_assignedLabels = QList(); m_assignedLabelsByFilter = QList(); m_deassignedLabelsByFilter = QList(); @@ -140,6 +140,7 @@ Message Message::fromSqlRecord(const QSqlRecord& record, bool* result) { message.m_contents = record.value(MSG_DB_CONTENTS_INDEX).toString(); message.m_enclosures = Enclosures::decodeEnclosuresFromString(record.value(MSG_DB_ENCLOSURES_INDEX).toString()); message.m_score = record.value(MSG_DB_SCORE_INDEX).toDouble(); + message.m_isRtl = record.value(MSG_DB_FEED_IS_RTL_INDEX).toBool(); message.m_accountId = record.value(MSG_DB_ACCOUNT_ID_INDEX).toInt(); message.m_customId = record.value(MSG_DB_CUSTOM_ID_INDEX).toString(); message.m_customHash = record.value(MSG_DB_CUSTOM_HASH_INDEX).toString(); @@ -179,7 +180,7 @@ QString Message::generateRawAtomContents(const Message& msg) { QDataStream& operator<<(QDataStream& out, const Message& my_obj) { out << my_obj.m_accountId << my_obj.m_customHash << my_obj.m_customId << my_obj.m_feedId << my_obj.m_id - << my_obj.m_isImportant << my_obj.m_isRead << my_obj.m_isDeleted << my_obj.m_score; + << my_obj.m_isImportant << my_obj.m_isRead << my_obj.m_isDeleted << my_obj.m_score << my_obj.m_isRtl; return out; } @@ -193,9 +194,11 @@ QDataStream& operator>>(QDataStream& in, Message& my_obj) { bool is_important; bool is_read; bool is_deleted; + bool is_rtl; double score; - in >> account_id >> custom_hash >> custom_id >> feed_id >> id >> is_important >> is_read >> is_deleted >> score; + in >> account_id >> custom_hash >> custom_id >> feed_id >> id >> is_important >> is_read >> is_deleted >> score >> + is_rtl; my_obj.m_accountId = account_id; my_obj.m_customHash = custom_hash; @@ -206,6 +209,7 @@ QDataStream& operator>>(QDataStream& in, Message& my_obj) { my_obj.m_isRead = is_read; my_obj.m_isDeleted = is_deleted; my_obj.m_score = score; + my_obj.m_isRtl = is_rtl; return in; } diff --git a/src/librssguard/core/message.h b/src/librssguard/core/message.h index a8824e125..d04640c66 100644 --- a/src/librssguard/core/message.h +++ b/src/librssguard/core/message.h @@ -80,6 +80,7 @@ class RSSGUARD_DLLSPEC Message { bool m_isImportant; bool m_isDeleted; double m_score; + bool m_isRtl; QList m_enclosures; // List of assigned labels. diff --git a/src/librssguard/core/messagesmodel.cpp b/src/librssguard/core/messagesmodel.cpp index 0e202ac5f..c23c09dfc 100644 --- a/src/librssguard/core/messagesmodel.cpp +++ b/src/librssguard/core/messagesmodel.cpp @@ -294,6 +294,7 @@ void MessagesModel::setupHeaderData() { /*: Tooltip for custom ID of message.*/ tr("Custom ID") << /*: Tooltip for custom hash string of message.*/ tr("Custom hash") << /*: Tooltip for name of feed for message.*/ tr("Feed") << + /*: Tooltip for indication whether article is RTL or not.*/ tr("RTL") << /*: Tooltip for indication of presence of enclosures.*/ tr("Has enclosures") << /*: Tooltip for indication of labels of message.*/ tr("Assigned labels") << /*: Tooltip for indication of label IDs of message.*/ tr("Assigned label IDs"); @@ -305,8 +306,8 @@ void MessagesModel::setupHeaderData() { << tr("Contents of the article.") << tr("List of attachments.") << tr("Score of the article.") << tr("Account ID of the article.") << tr("Custom ID of the article.") << tr("Custom hash of the article.") << tr("Name of feed of the article.") - << tr("Indication of enclosures presence within the article.") << tr("Labels assigned to the article.") - << tr("Label IDs assigned to the article."); + << tr("Layout direction of the article") << tr("Indication of enclosures presence within the article.") + << tr("Labels assigned to the article.") << tr("Label IDs assigned to the article."); } Qt::ItemFlags MessagesModel::flags(const QModelIndex& index) const { @@ -409,6 +410,23 @@ QVariant MessagesModel::data(const QModelIndex& idx, int role) const { } } + case TEXT_DIRECTION_ROLE: { + int index_column = idx.column(); + + if (index_column != MSG_DB_TITLE_INDEX && index_column != MSG_DB_FEED_TITLE_INDEX && + index_column != MSG_DB_AUTHOR_INDEX) { + return Qt::LayoutDirection::LayoutDirectionAuto; + } + else { + return (m_cache->containsData(idx.row()) + ? m_cache->data(index(idx.row(), MSG_DB_FEED_IS_RTL_INDEX)) + : QSqlQueryModel::data(index(idx.row(), MSG_DB_FEED_IS_RTL_INDEX), Qt::ItemDataRole::EditRole)) + .toInt() == 0 + ? Qt::LayoutDirection::LayoutDirectionAuto + : Qt::LayoutDirection::RightToLeft; + } + } + case LOWER_TITLE_ROLE: return m_cache->containsData(idx.row()) ? m_cache->data(idx).toString().toLower() diff --git a/src/librssguard/core/messagesmodelsqllayer.cpp b/src/librssguard/core/messagesmodelsqllayer.cpp index d177b32bc..802de6d52 100644 --- a/src/librssguard/core/messagesmodelsqllayer.cpp +++ b/src/librssguard/core/messagesmodelsqllayer.cpp @@ -32,12 +32,14 @@ MessagesModelSqlLayer::MessagesModelSqlLayer() m_orderByNames[MSG_DB_CUSTOM_ID_INDEX] = QSL("Messages.custom_id"); m_orderByNames[MSG_DB_CUSTOM_HASH_INDEX] = QSL("Messages.custom_hash"); m_orderByNames[MSG_DB_FEED_TITLE_INDEX] = QSL("Feeds.title"); + m_orderByNames[MSG_DB_FEED_IS_RTL_INDEX] = QSL("Feeds.is_rtl"); m_orderByNames[MSG_DB_HAS_ENCLOSURES] = QSL("has_enclosures"); m_orderByNames[MSG_DB_LABELS] = QSL("msg_labels"); m_orderByNames[MSG_DB_LABELS_IDS] = QSL("Messages.labels"); m_numericColumns << MSG_DB_ID_INDEX << MSG_DB_READ_INDEX << MSG_DB_DELETED_INDEX << MSG_DB_PDELETED_INDEX - << MSG_DB_IMPORTANT_INDEX << MSG_DB_ACCOUNT_ID_INDEX << MSG_DB_DCREATED_INDEX << MSG_DB_SCORE_INDEX; + << MSG_DB_IMPORTANT_INDEX << MSG_DB_ACCOUNT_ID_INDEX << MSG_DB_DCREATED_INDEX << MSG_DB_SCORE_INDEX + << MSG_DB_FEED_IS_RTL_INDEX; } void MessagesModelSqlLayer::addSortState(int column, Qt::SortOrder order, bool ignore_multicolumn_sorting) { diff --git a/src/librssguard/database/databasequeries.cpp b/src/librssguard/database/databasequeries.cpp index 7d4eaf8bd..6cec2b2cb 100644 --- a/src/librssguard/database/databasequeries.cpp +++ b/src/librssguard/database/databasequeries.cpp @@ -33,7 +33,8 @@ QMap DatabaseQueries::messageTableAttributes(bool only_msg_table, field_names[MSG_DB_CUSTOM_ID_INDEX] = QSL("Messages.custom_id"); field_names[MSG_DB_CUSTOM_HASH_INDEX] = QSL("Messages.custom_hash"); field_names[MSG_DB_FEED_TITLE_INDEX] = only_msg_table ? QSL("Messages.feed") : QSL("Feeds.title"); - field_names[MSG_DB_HAS_ENCLOSURES] = QSL("CASE WHEN length(Messages.enclosures) > 10 " + field_names[MSG_DB_FEED_IS_RTL_INDEX] = QSL("Feeds.is_rtl"); + field_names[MSG_DB_HAS_ENCLOSURES] = QSL("CASE WHEN LENGTH(Messages.enclosures) > 10 " "THEN 'true' " "ELSE 'false' " "END AS has_enclosures"); diff --git a/src/librssguard/definitions/definitions.h b/src/librssguard/definitions/definitions.h index a9e846812..0aa4b3c5c 100644 --- a/src/librssguard/definitions/definitions.h +++ b/src/librssguard/definitions/definitions.h @@ -268,9 +268,10 @@ #define MSG_DB_CUSTOM_ID_INDEX 14 #define MSG_DB_CUSTOM_HASH_INDEX 15 #define MSG_DB_FEED_TITLE_INDEX 16 -#define MSG_DB_HAS_ENCLOSURES 17 -#define MSG_DB_LABELS 18 -#define MSG_DB_LABELS_IDS 19 +#define MSG_DB_FEED_IS_RTL_INDEX 17 +#define MSG_DB_HAS_ENCLOSURES 18 +#define MSG_DB_LABELS 19 +#define MSG_DB_LABELS_IDS 20 // Indexes of columns as they are DEFINED IN THE TABLE for CATEGORIES. #define CAT_DB_ID_INDEX 0 diff --git a/src/librssguard/gui/messagesview.cpp b/src/librssguard/gui/messagesview.cpp index a80b15573..a3a377d08 100644 --- a/src/librssguard/gui/messagesview.cpp +++ b/src/librssguard/gui/messagesview.cpp @@ -516,6 +516,7 @@ void MessagesView::loadItem(RootItem* item) { sort(col, ord, false, true, false, true); m_sourceModel->loadMessages(item); + /* if (item->kind() == RootItem::Kind::Feed) { if (item->toFeed()->isRtl()) { setLayoutDirection(Qt::LayoutDirection::RightToLeft); @@ -527,6 +528,7 @@ void MessagesView::loadItem(RootItem* item) { else { setLayoutDirection(Qt::LayoutDirection::LeftToRight); } + */ // Messages are loaded, make sure that previously // active message is not shown in browser. @@ -838,6 +840,7 @@ void MessagesView::adjustColumns() { hideColumn(MSG_DB_CUSTOM_HASH_INDEX); hideColumn(MSG_DB_FEED_CUSTOM_ID_INDEX); hideColumn(MSG_DB_FEED_TITLE_INDEX); + hideColumn(MSG_DB_FEED_IS_RTL_INDEX); hideColumn(MSG_DB_HAS_ENCLOSURES); hideColumn(MSG_DB_LABELS); diff --git a/src/librssguard/gui/webviewers/qtextbrowser/textbrowserviewer.cpp b/src/librssguard/gui/webviewers/qtextbrowser/textbrowserviewer.cpp index f958c53af..5bb986f06 100644 --- a/src/librssguard/gui/webviewers/qtextbrowser/textbrowserviewer.cpp +++ b/src/librssguard/gui/webviewers/qtextbrowser/textbrowserviewer.cpp @@ -303,10 +303,19 @@ void TextBrowserViewer::loadMessages(const QList& messages, RootItem* r setHtml(html_messages.m_html, html_messages.m_baseUrl); - bool is_rtl_feed = root != nullptr && root->kind() == RootItem::Kind::Feed && qobject_cast(root)->isRtl(); + /* + auto* feed = root != nullptr + ? root->getParentServiceRoot() + ->getItemFromSubTree([messages](const RootItem* it) { + return it->kind() == RootItem::Kind::Feed && it->customId() == messages.at(0).m_feedId; + }) + ->toFeed() + : nullptr; + bool is_rtl_feed = feed != nullptr && feed->isRtl(); + */ QTextOption op; - op.setTextDirection(is_rtl_feed ? Qt::LayoutDirection::RightToLeft : Qt::LayoutDirection::LeftToRight); + op.setTextDirection(messages.at(0).m_isRtl ? Qt::LayoutDirection::RightToLeft : Qt::LayoutDirection::LeftToRight); document()->setDefaultTextOption(op); emit loadingFinished(true); diff --git a/src/librssguard/miscellaneous/skinfactory.cpp b/src/librssguard/miscellaneous/skinfactory.cpp index 1ea080271..ef058416b 100644 --- a/src/librssguard/miscellaneous/skinfactory.cpp +++ b/src/librssguard/miscellaneous/skinfactory.cpp @@ -238,7 +238,9 @@ PreparedHtml SkinFactory::generateHtmlOfArticles(const QList& messages, }) ->toFeed() : nullptr; + /* bool is_rtl_feed = feed != nullptr && feed->isRtl(); + */ for (const Message& message : messages) { QString enclosures; @@ -284,7 +286,7 @@ PreparedHtml SkinFactory::generateHtmlOfArticles(const QList& messages, enclosures, enclosure_images, QString::number(message.m_id), - is_rtl_feed ? QSL("rtl") : QSL("ltr"))); + message.m_isRtl ? QSL("rtl") : QSL("ltr"))); } QString msg_contents = diff --git a/src/librssguard/services/gmail/gui/emailpreviewer.cpp b/src/librssguard/services/gmail/gui/emailpreviewer.cpp index d35b722f8..b00ff50ab 100644 --- a/src/librssguard/services/gmail/gui/emailpreviewer.cpp +++ b/src/librssguard/services/gmail/gui/emailpreviewer.cpp @@ -49,8 +49,6 @@ void EmailPreviewer::clear() { } void EmailPreviewer::loadMessage(const Message& msg, RootItem* selected_item) { - Q_UNUSED(selected_item) - m_message = msg; m_webView->loadMessages({msg}, selected_item);