mirror of
https://github.com/AyuGram/AyuGramDesktop.git
synced 2025-04-16 14:17:12 +02:00
Generate album mini previews with up-to-three images.
This commit is contained in:
parent
8cdd2f113f
commit
992d636680
7 changed files with 84 additions and 18 deletions
|
@ -7,7 +7,9 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
|||
*/
|
||||
#include "data/data_groups.h"
|
||||
|
||||
#include "history/history.h"
|
||||
#include "history/history_item.h"
|
||||
#include "dialogs/ui/dialogs_message_view.h"
|
||||
#include "data/data_media_types.h"
|
||||
#include "data/data_session.h"
|
||||
|
||||
|
@ -140,8 +142,13 @@ const Group *Groups::find(not_null<const HistoryItem*> item) const {
|
|||
}
|
||||
|
||||
void Groups::refreshViews(const HistoryItemsList &items) {
|
||||
if (items.empty()) {
|
||||
return;
|
||||
}
|
||||
const auto history = items.front()->history();
|
||||
for (const auto &item : items) {
|
||||
_data->requestItemViewRefresh(item);
|
||||
history->lastItemDialogsView.itemInvalidated(item);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -15,7 +15,6 @@ class Session;
|
|||
|
||||
struct Group {
|
||||
HistoryItemsList items;
|
||||
|
||||
};
|
||||
|
||||
class Groups {
|
||||
|
|
|
@ -60,6 +60,7 @@ namespace Data {
|
|||
namespace {
|
||||
|
||||
constexpr auto kFastRevokeRestriction = 24 * 60 * TimeId(60);
|
||||
constexpr auto kMaxPreviewImages = 3;
|
||||
|
||||
using ItemPreview = HistoryView::ItemPreview;
|
||||
|
||||
|
@ -406,6 +407,52 @@ std::unique_ptr<HistoryView::Media> Media::createView(
|
|||
return createView(message, message->data(), replacing);
|
||||
}
|
||||
|
||||
ItemPreview Media::toGroupPreview(
|
||||
const HistoryItemsList &items,
|
||||
ToPreviewOptions options) const {
|
||||
const auto genericText = textcmdLink(
|
||||
1,
|
||||
TextUtilities::Clean(tr::lng_in_dlg_album(tr::now)));
|
||||
auto result = ItemPreview();
|
||||
auto loadingContext = std::vector<std::any>();
|
||||
for (const auto &item : items) {
|
||||
if (const auto media = item->media()) {
|
||||
auto copy = options;
|
||||
copy.ignoreGroup = true;
|
||||
const auto already = int(result.images.size());
|
||||
const auto left = kMaxPreviewImages - already;
|
||||
auto single = left ? media->toPreview(copy) : ItemPreview();
|
||||
if (!single.images.empty()) {
|
||||
while (single.images.size() > left) {
|
||||
single.images.pop_back();
|
||||
}
|
||||
result.images.insert(
|
||||
end(result.images),
|
||||
std::make_move_iterator(begin(single.images)),
|
||||
std::make_move_iterator(end(single.images)));
|
||||
}
|
||||
if (single.loadingContext.has_value()) {
|
||||
loadingContext.push_back(std::move(single.loadingContext));
|
||||
}
|
||||
const auto original = item->originalText().text;
|
||||
if (!original.isEmpty()) {
|
||||
if (result.text.isEmpty()) {
|
||||
result.text = TextUtilities::Clean(original);
|
||||
} else {
|
||||
result.text = genericText;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
if (result.text.isEmpty()) {
|
||||
result.text = genericText;
|
||||
}
|
||||
if (!loadingContext.empty()) {
|
||||
result.loadingContext = std::move(loadingContext);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
MediaPhoto::MediaPhoto(
|
||||
not_null<HistoryItem*> parent,
|
||||
not_null<PhotoData*> photo)
|
||||
|
@ -478,11 +525,17 @@ QString MediaPhoto::notificationText() const {
|
|||
}
|
||||
|
||||
ItemPreview MediaPhoto::toPreview(ToPreviewOptions options) const {
|
||||
const auto item = parent();
|
||||
if (!options.ignoreGroup && item->groupId()) {
|
||||
if (const auto group = item->history()->owner().groups().find(item)
|
||||
; group && group->items.size() > 1) {
|
||||
return toGroupPreview(group->items, options);
|
||||
}
|
||||
}
|
||||
const auto caption = options.hideCaption
|
||||
? QString()
|
||||
: parent()->originalText().text;
|
||||
auto images = std::vector<QImage>();
|
||||
// #TODO minis support albums
|
||||
const auto media = _photo->createMediaView();
|
||||
const auto radius = _chat
|
||||
? ImageRoundRadius::Ellipse
|
||||
|
@ -666,6 +719,13 @@ bool MediaFile::replyPreviewLoaded() const {
|
|||
}
|
||||
|
||||
ItemPreview MediaFile::toPreview(ToPreviewOptions options) const {
|
||||
const auto item = parent();
|
||||
if (!options.ignoreGroup && item->groupId()) {
|
||||
if (const auto group = item->history()->owner().groups().find(item)
|
||||
; group && group->items.size() > 1) {
|
||||
return toGroupPreview(group->items, options);
|
||||
}
|
||||
}
|
||||
if (const auto sticker = _document->sticker()) {
|
||||
return Media::toPreview(options);
|
||||
}
|
||||
|
@ -690,7 +750,6 @@ ItemPreview MediaFile::toPreview(ToPreviewOptions options) const {
|
|||
const auto caption = options.hideCaption
|
||||
? QString()
|
||||
: parent()->originalText().text;
|
||||
// #TODO minis support albums
|
||||
auto images = std::vector<QImage>();
|
||||
const auto media = TryFilePreview(_document)
|
||||
? _document->createMediaView()
|
||||
|
|
|
@ -127,6 +127,11 @@ public:
|
|||
not_null<HistoryView::Element*> message,
|
||||
HistoryView::Element *replacing = nullptr);
|
||||
|
||||
protected:
|
||||
[[nodiscard]] ItemPreview toGroupPreview(
|
||||
const HistoryItemsList &items,
|
||||
ToPreviewOptions options) const;
|
||||
|
||||
private:
|
||||
const not_null<HistoryItem*> _parent;
|
||||
|
||||
|
|
|
@ -78,7 +78,8 @@ struct MessageView::LoadingContext {
|
|||
};
|
||||
|
||||
MessageView::MessageView()
|
||||
: _textCache(st::dialogsTextWidthMin) {
|
||||
: _senderCache(st::dialogsTextWidthMin)
|
||||
, _textCache(st::dialogsTextWidthMin) {
|
||||
}
|
||||
|
||||
MessageView::~MessageView() = default;
|
||||
|
@ -111,6 +112,8 @@ void MessageView::paint(
|
|||
preview.text.mid(0, preview.imagesInTextPosition).trimmed(),
|
||||
DialogTextOptions());
|
||||
preview.text = preview.text.mid(preview.imagesInTextPosition);
|
||||
} else {
|
||||
_senderCache = { st::dialogsTextWidthMin };
|
||||
}
|
||||
_textCache.setText(
|
||||
st::dialogsTextStyle,
|
||||
|
|
|
@ -205,14 +205,14 @@ void HistoryItem::applyServiceDateEdition(const MTPDmessageService &data) {
|
|||
}
|
||||
|
||||
void HistoryItem::finishEdition(int oldKeyboardTop) {
|
||||
_history->owner().requestItemViewRefresh(this);
|
||||
invalidateChatListEntry();
|
||||
if (const auto group = _history->owner().groups().find(this)) {
|
||||
const auto leader = group->items.front();
|
||||
if (leader != this) {
|
||||
_history->owner().requestItemViewRefresh(leader);
|
||||
leader->invalidateChatListEntry();
|
||||
for (const auto &item : group->items) {
|
||||
_history->owner().requestItemViewRefresh(item);
|
||||
item->invalidateChatListEntry();
|
||||
}
|
||||
} else {
|
||||
_history->owner().requestItemViewRefresh(this);
|
||||
invalidateChatListEntry();
|
||||
}
|
||||
|
||||
// Should be completely redesigned as the oldTop no longer exists.
|
||||
|
@ -942,14 +942,6 @@ QString HistoryItem::notificationText() const {
|
|||
ItemPreview HistoryItem::toPreview(ToPreviewOptions options) const {
|
||||
auto result = [&]() -> ItemPreview {
|
||||
if (_media) {
|
||||
if (_groupId) {
|
||||
// #TODO minis generate albums correctly
|
||||
return {
|
||||
.text = textcmdLink(
|
||||
1,
|
||||
TextUtilities::Clean(tr::lng_in_dlg_album(tr::now))),
|
||||
};
|
||||
}
|
||||
return _media->toPreview(options);
|
||||
} else if (!emptyText()) {
|
||||
return { .text = TextUtilities::Clean(_text.toString()) };
|
||||
|
|
|
@ -61,6 +61,7 @@ struct ToPreviewOptions {
|
|||
bool hideSender = false;
|
||||
bool hideCaption = false;
|
||||
bool generateImages = true;
|
||||
bool ignoreGroup = false;
|
||||
};
|
||||
|
||||
struct ItemPreview {
|
||||
|
|
Loading…
Add table
Reference in a new issue