| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211 |
- /*
- This file is part of Telegram Desktop,
- the official desktop application for the Telegram messaging service.
- For license and copyright information please follow this link:
- https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
- */
- #pragma once
- #include "base/timer.h"
- namespace Ui {
- struct DownloadBarProgress;
- struct DownloadBarContent;
- } // namespace Ui
- namespace Main {
- class Session;
- } // namespace Main
- namespace Data {
- // Used in serialization!
- enum class DownloadType {
- Document,
- Photo,
- };
- // unixtime * 1000.
- using DownloadDate = int64;
- [[nodiscard]] inline TimeId DateFromDownloadDate(DownloadDate date) {
- return date / 1000;
- }
- struct DownloadId {
- uint64 objectId = 0;
- DownloadType type = DownloadType::Document;
- };
- struct DownloadProgress {
- int64 ready = 0;
- int64 total = 0;
- };
- inline constexpr bool operator==(
- const DownloadProgress &a,
- const DownloadProgress &b) {
- return (a.ready == b.ready) && (a.total == b.total);
- }
- struct DownloadObject {
- not_null<HistoryItem*> item;
- DocumentData *document = nullptr;
- PhotoData *photo = nullptr;
- };
- struct DownloadedId {
- DownloadId download;
- DownloadDate started = 0;
- QString path;
- int64 size = 0;
- FullMsgId itemId;
- uint64 peerAccessHash = 0;
- std::unique_ptr<DownloadObject> object;
- };
- struct DownloadingId {
- DownloadObject object;
- DownloadDate started = 0;
- QString path;
- int64 ready = 0;
- int64 total = 0;
- bool hiddenByView = false;
- bool done = false;
- };
- class DownloadManager final {
- public:
- DownloadManager();
- ~DownloadManager();
- [[nodiscard]] bool empty() const;
- void trackSession(not_null<Main::Session*> session);
- void itemVisibilitiesUpdated(not_null<Main::Session*> session);
- [[nodiscard]] DownloadDate computeNextStartDate();
- void addLoading(DownloadObject object);
- void addLoaded(
- DownloadObject object,
- const QString &path,
- DownloadDate started);
- void clearIfFinished();
- void deleteFiles(const std::vector<GlobalMsgId> &ids);
- void deleteAll();
- [[nodiscard]] bool loadedHasNonCloudFile() const;
- [[nodiscard]] auto loadingList() const
- -> ranges::any_view<const DownloadingId*, ranges::category::input>;
- [[nodiscard]] DownloadProgress loadingProgress() const;
- [[nodiscard]] rpl::producer<> loadingListChanges() const;
- [[nodiscard]] auto loadingProgressValue() const
- -> rpl::producer<DownloadProgress>;
- [[nodiscard]] bool loadingInProgress(
- Main::Session *onlyInSession = nullptr) const;
- void loadingStopWithConfirmation(
- Fn<void()> callback,
- Main::Session *onlyInSession = nullptr);
- [[nodiscard]] auto loadedList()
- -> ranges::any_view<const DownloadedId*, ranges::category::input>;
- [[nodiscard]] auto loadedAdded() const
- -> rpl::producer<not_null<const DownloadedId*>>;
- [[nodiscard]] auto loadedRemoved() const
- -> rpl::producer<not_null<const HistoryItem*>>;
- [[nodiscard]] rpl::producer<> loadedResolveDone() const;
- private:
- struct DeleteFilesDescriptor;
- struct SessionData {
- std::vector<DownloadedId> downloaded;
- std::vector<DownloadingId> downloading;
- int resolveNeeded = 0;
- int resolveSentRequests = 0;
- int resolveSentTotal = 0;
- rpl::lifetime lifetime;
- };
- void check(not_null<const HistoryItem*> item);
- void check(not_null<DocumentData*> document);
- void check(
- SessionData &data,
- std::vector<DownloadingId>::iterator i);
- void changed(not_null<const HistoryItem*> item);
- void removed(not_null<const HistoryItem*> item);
- void detach(DownloadedId &id);
- void untrack(not_null<Main::Session*> session);
- void remove(
- SessionData &data,
- std::vector<DownloadingId>::iterator i);
- void cancel(
- SessionData &data,
- std::vector<DownloadingId>::iterator i);
- void clearLoading();
- [[nodiscard]] SessionData &sessionData(not_null<Main::Session*> session);
- [[nodiscard]] const SessionData &sessionData(
- not_null<Main::Session*> session) const;
- [[nodiscard]] SessionData &sessionData(
- not_null<const HistoryItem*> item);
- [[nodiscard]] SessionData &sessionData(not_null<DocumentData*> document);
- void resolve(not_null<Main::Session*> session, SessionData &data);
- void resolveRequestsFinished(
- not_null<Main::Session*> session,
- SessionData &data);
- void checkFullResolveDone();
- [[nodiscard]] not_null<HistoryItem*> regenerateItem(
- const DownloadObject &previous);
- [[nodiscard]] not_null<HistoryItem*> generateFakeItem(
- not_null<DocumentData*> document);
- [[nodiscard]] not_null<HistoryItem*> generateItem(
- HistoryItem *previousItem,
- DocumentData *document,
- PhotoData *photo);
- void generateEntry(not_null<Main::Session*> session, DownloadedId &id);
- [[nodiscard]] HistoryItem *lookupLoadingItem(
- Main::Session *onlyInSession) const;
- void loadingStop(Main::Session *onlyInSession);
- void finishFilesDelete(DeleteFilesDescriptor &&descriptor);
- void writePostponed(not_null<Main::Session*> session);
- [[nodiscard]] Fn<std::optional<QByteArray>()> serializator(
- not_null<Main::Session*> session) const;
- [[nodiscard]] std::vector<DownloadedId> deserialize(
- not_null<Main::Session*> session) const;
- base::flat_map<not_null<Main::Session*>, SessionData> _sessions;
- base::flat_set<not_null<const HistoryItem*>> _loading;
- base::flat_set<not_null<DocumentData*>> _loadingDocuments;
- base::flat_set<not_null<const HistoryItem*>> _loadingDone;
- base::flat_set<not_null<const HistoryItem*>> _loaded;
- base::flat_set<not_null<HistoryItem*>> _generated;
- base::flat_set<not_null<DocumentData*>> _generatedDocuments;
- TimeId _lastStartedBase = 0;
- int _lastStartedAdded = 0;
- rpl::event_stream<> _loadingListChanges;
- rpl::variable<DownloadProgress> _loadingProgress;
- rpl::event_stream<not_null<const DownloadedId*>> _loadedAdded;
- rpl::event_stream<not_null<const HistoryItem*>> _loadedRemoved;
- rpl::variable<bool> _loadedResolveDone;
- base::Timer _clearLoadingTimer;
- };
- [[nodiscard]] auto MakeDownloadBarProgress()
- -> rpl::producer<Ui::DownloadBarProgress>;
- [[nodiscard]] rpl::producer<Ui::DownloadBarContent> MakeDownloadBarContent();
- } // namespace Data
|