diff --git a/Telegram/SourceFiles/boxes/dictionaries_manager.cpp b/Telegram/SourceFiles/boxes/dictionaries_manager.cpp index 4beab9046..46f809fe1 100644 --- a/Telegram/SourceFiles/boxes/dictionaries_manager.cpp +++ b/Telegram/SourceFiles/boxes/dictionaries_manager.cpp @@ -41,34 +41,19 @@ using Dictionaries = std::vector; using namespace Storage::CloudBlob; using Loading = MTP::DedicatedLoader::Progress; -using DictState = base::variant< - Available, - Ready, - Active, - Failed, - Loading>; +using DictState = BlobState; -class Loader : public QObject { +class Loader : public BlobLoader { public: - Loader(QObject *parent, int id); + Loader( + QObject *parent, + int id, + MTP::DedicatedLoader::Location location, + const QString &folder, + int size); - int id() const; - - rpl::producer state() const; - void destroy(); - -private: - void setImplementation(std::unique_ptr loader); - void unpack(const QString &path); - void finalize(const QString &path); - void fail(); - - int _id = 0; - int _size = 0; - rpl::variable _state; - - MTP::WeakInstance _mtproto; - std::unique_ptr _implementation; + void destroy() override; + void unpack(const QString &path) override; }; @@ -109,10 +94,10 @@ int GetDownloadSize(int id) { } MTP::DedicatedLoader::Location GetDownloadLocation(int id) { - constexpr auto kUsername = "tdhbcfiles"; + const auto username = kCloudLocationUsername.utf16(); const auto sets = Spellchecker::Dictionaries(); const auto i = ranges::find(sets, id, &Spellchecker::Dict::id); - return MTP::DedicatedLoader::Location{ kUsername, i->postId }; + return MTP::DedicatedLoader::Location{ username, i->postId }; } DictState ComputeState(int id) { @@ -147,60 +132,18 @@ QString StateDescription(const DictState &state) { }); } -Loader::Loader(QObject *parent, int id) -: QObject(parent) -, _id(id) -, _size(GetDownloadSize(_id)) -, _state(Loading{ 0, _size }) -, _mtproto(Core::App().activeAccount().mtp()) { - const auto ready = [=](std::unique_ptr loader) { - if (loader) { - setImplementation(std::move(loader)); - } else { - fail(); - } - }; - const auto location = GetDownloadLocation(id); - const auto folder = Spellchecker::DictPathByLangId(id); - MTP::StartDedicatedLoader(&_mtproto, location, folder, ready); -} - -int Loader::id() const { - return _id; -} - -rpl::producer Loader::state() const { - return _state.value(); -} - -void Loader::setImplementation( - std::unique_ptr loader) { - _implementation = std::move(loader); - auto convert = [](auto value) { - return DictState(value); - }; - _state = _implementation->progress( - ) | rpl::map([](const Loading &state) { - return DictState(state); - }); - _implementation->failed( - ) | rpl::start_with_next([=] { - fail(); - }, _implementation->lifetime()); - - _implementation->ready( - ) | rpl::start_with_next([=](const QString &filepath) { - unpack(filepath); - }, _implementation->lifetime()); - - QDir(Spellchecker::DictPathByLangId(_id)).removeRecursively(); - _implementation->start(); +Loader::Loader( + QObject *parent, + int id, + MTP::DedicatedLoader::Location location, + const QString &folder, + int size) : BlobLoader(parent, id, location, folder, size) { } void Loader::unpack(const QString &path) { const auto weak = Ui::MakeWeak(this); crl::async([=] { - if (Spellchecker::UnpackDictionary(path, _id)) { + if (Spellchecker::UnpackDictionary(path, id())) { QFile(path).remove(); crl::on_main(weak, [=] { destroy(); @@ -213,13 +156,6 @@ void Loader::unpack(const QString &path) { }); } -void Loader::finalize(const QString &path) { -} - -void Loader::fail() { - _state = Failed(); -} - void Loader::destroy() { Expects(GlobalLoader == this); @@ -329,7 +265,12 @@ auto AddButtonWithLoader( ) | rpl::start_with_next([=](bool toggled) { const auto &state = buttonState->current(); if (toggled && (state.is() || state.is())) { - SetGlobalLoader(base::make_unique_q(App::main(), id)); + SetGlobalLoader(base::make_unique_q( + App::main(), + id, + GetDownloadLocation(id), + Spellchecker::DictPathByLangId(id), + GetDownloadSize(id))); } else if (!toggled && state.is()) { if (GlobalLoader && GlobalLoader->id() == id) { GlobalLoader->destroy(); diff --git a/Telegram/SourceFiles/chat_helpers/emoji_sets_manager.cpp b/Telegram/SourceFiles/chat_helpers/emoji_sets_manager.cpp index 190c7fbc4..c41fac066 100644 --- a/Telegram/SourceFiles/chat_helpers/emoji_sets_manager.cpp +++ b/Telegram/SourceFiles/chat_helpers/emoji_sets_manager.cpp @@ -53,34 +53,19 @@ auto Sets() { } using Loading = MTP::DedicatedLoader::Progress; -using SetState = base::variant< - Available, - Ready, - Active, - Loading, - Failed>; +using SetState = BlobState; -class Loader : public QObject { +class Loader : public BlobLoader { public: - Loader(QObject *parent, int id); + Loader( + QObject *parent, + int id, + MTP::DedicatedLoader::Location location, + const QString &folder, + int size); - int id() const; - - rpl::producer state() const; - void destroy(); - -private: - void setImplementation(std::unique_ptr loader); - void unpack(const QString &path); - void finalize(const QString &path); - void fail(); - - int _id = 0; - int _size = 0; - rpl::variable _state; - - MTP::WeakInstance _mtproto; - std::unique_ptr _implementation; + void destroy() override; + void unpack(const QString &path) override; }; @@ -148,10 +133,10 @@ int GetDownloadSize(int id) { } MTP::DedicatedLoader::Location GetDownloadLocation(int id) { - constexpr auto kUsername = "tdhbcfiles"; + const auto username = kCloudLocationUsername.utf16(); const auto sets = Sets(); const auto i = ranges::find(sets, id, &Set::id); - return MTP::DedicatedLoader::Location{ kUsername, i->postId }; + return MTP::DedicatedLoader::Location{ username, i->postId }; } SetState ComputeState(int id) { @@ -195,63 +180,21 @@ bool UnpackSet(const QString &path, const QString &folder) { return UnpackBlob(path, folder, GoodSetPartName); } -Loader::Loader(QObject *parent, int id) -: QObject(parent) -, _id(id) -, _size(GetDownloadSize(_id)) -, _state(Loading{ 0, _size }) -, _mtproto(Core::App().activeAccount().mtp()) { - const auto ready = [=](std::unique_ptr loader) { - if (loader) { - setImplementation(std::move(loader)); - } else { - fail(); - } - }; - const auto location = GetDownloadLocation(id); - const auto folder = internal::SetDataPath(id); - MTP::StartDedicatedLoader(&_mtproto, location, folder, ready); -} - -int Loader::id() const { - return _id; -} - -rpl::producer Loader::state() const { - return _state.value(); -} - -void Loader::setImplementation( - std::unique_ptr loader) { - _implementation = std::move(loader); - auto convert = [](auto value) { - return SetState(value); - }; - _state = _implementation->progress( - ) | rpl::map([](const Loading &state) { - return SetState(state); - }); - _implementation->failed( - ) | rpl::start_with_next([=] { - fail(); - }, _implementation->lifetime()); - - _implementation->ready( - ) | rpl::start_with_next([=](const QString &filepath) { - unpack(filepath); - }, _implementation->lifetime()); - - QDir(internal::SetDataPath(_id)).removeRecursively(); - _implementation->start(); +Loader::Loader( + QObject *parent, + int id, + MTP::DedicatedLoader::Location location, + const QString &folder, + int size) : BlobLoader(parent, id, location, folder, size) { } void Loader::unpack(const QString &path) { - const auto folder = internal::SetDataPath(_id); + const auto folder = internal::SetDataPath(id()); const auto weak = Ui::MakeWeak(this); crl::async([=] { if (UnpackSet(path, folder)) { QFile(path).remove(); - SwitchToSet(_id, crl::guard(weak, [=](bool success) { + SwitchToSet(id(), crl::guard(weak, [=](bool success) { if (success) { destroy(); } else { @@ -266,13 +209,6 @@ void Loader::unpack(const QString &path) { }); } -void Loader::finalize(const QString &path) { -} - -void Loader::fail() { - _state = Failed(); -} - void Loader::destroy() { Expects(GlobalLoader == this); @@ -491,7 +427,12 @@ void Row::setupHandler() { } void Row::load() { - SetGlobalLoader(base::make_unique_q(App::main(), _id)); + SetGlobalLoader(base::make_unique_q( + App::main(), + _id, + GetDownloadLocation(_id), + internal::SetDataPath(_id), + GetDownloadSize(_id))); } void Row::setupLabels(const Set &set) { diff --git a/Telegram/SourceFiles/storage/storage_cloud_blob.cpp b/Telegram/SourceFiles/storage/storage_cloud_blob.cpp index a90635462..3707cc8cb 100644 --- a/Telegram/SourceFiles/storage/storage_cloud_blob.cpp +++ b/Telegram/SourceFiles/storage/storage_cloud_blob.cpp @@ -8,6 +8,8 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL #include "storage/storage_cloud_blob.h" #include "base/zlib_help.h" +#include "core/application.h" +#include "main/main_account.h" namespace Storage::CloudBlob { @@ -64,4 +66,61 @@ bool UnpackBlob( return true; } +BlobLoader::BlobLoader( + QObject *parent, + int id, + MTP::DedicatedLoader::Location location, + const QString &folder, + int size) +: QObject(parent) +, _folder(folder) +, _id(id) +, _state(Loading{ 0, size }) +, _mtproto(Core::App().activeAccount().mtp()) { + const auto ready = [=](std::unique_ptr loader) { + if (loader) { + setImplementation(std::move(loader)); + } else { + fail(); + } + }; + MTP::StartDedicatedLoader(&_mtproto, location, _folder, ready); +} + +int BlobLoader::id() const { + return _id; +} + +rpl::producer BlobLoader::state() const { + return _state.value(); +} + +void BlobLoader::setImplementation( + std::unique_ptr loader) { + _implementation = std::move(loader); + auto convert = [](auto value) { + return BlobState(value); + }; + _state = _implementation->progress( + ) | rpl::map([](const Loading &state) { + return BlobState(state); + }); + _implementation->failed( + ) | rpl::start_with_next([=] { + fail(); + }, _implementation->lifetime()); + + _implementation->ready( + ) | rpl::start_with_next([=](const QString &filepath) { + unpack(filepath); + }, _implementation->lifetime()); + + QDir(_folder).removeRecursively(); + _implementation->start(); +} + +void BlobLoader::fail() { + _state = Failed(); +} + } // namespace Storage::CloudBlob diff --git a/Telegram/SourceFiles/storage/storage_cloud_blob.h b/Telegram/SourceFiles/storage/storage_cloud_blob.h index e34705f2c..a0533eee7 100644 --- a/Telegram/SourceFiles/storage/storage_cloud_blob.h +++ b/Telegram/SourceFiles/storage/storage_cloud_blob.h @@ -7,8 +7,12 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL */ #pragma once +#include "mtproto/dedicated_file_loader.h" + namespace Storage::CloudBlob { +constexpr auto kCloudLocationUsername = "tdhbcfiles"_cs; + struct Blob { int id = 0; int postId = 0; @@ -51,9 +55,48 @@ struct Failed { } }; +using Loading = MTP::DedicatedLoader::Progress; +using BlobState = base::variant< + Available, + Ready, + Active, + Failed, + Loading>; + bool UnpackBlob( const QString &path, const QString &folder, Fn checkNameCallback); +class BlobLoader : public QObject { +public: + BlobLoader( + QObject *parent, + int id, + MTP::DedicatedLoader::Location location, + const QString &folder, + int size); + + int id() const; + + rpl::producer state() const; + virtual void destroy() = 0; + virtual void unpack(const QString &path) = 0; + +protected: + void fail(); + + const QString _folder; + +private: + void setImplementation(std::unique_ptr loader); + + int _id = 0; + rpl::variable _state; + + MTP::WeakInstance _mtproto; + std::unique_ptr _implementation; + +}; + } // namespace Storage::CloudBlob