mirror of https://github.com/procxx/kepka.git
Show animated previews for GIFs in SendFilesBox.
This commit is contained in:
parent
a1b53c660e
commit
6c00b7efde
|
@ -123,6 +123,8 @@ void SendFilesBox::prepareSingleFileLayout() {
|
||||||
image = Images::prepareOpaque(std::move(image));
|
image = Images::prepareOpaque(std::move(image));
|
||||||
_preview = App::pixmapFromImageInPlace(std::move(image));
|
_preview = App::pixmapFromImageInPlace(std::move(image));
|
||||||
_preview.setDevicePixelRatio(cRetinaFactor());
|
_preview.setDevicePixelRatio(cRetinaFactor());
|
||||||
|
|
||||||
|
prepareGifPreview();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (_preview.isNull()) {
|
if (_preview.isNull()) {
|
||||||
|
@ -130,6 +132,49 @@ void SendFilesBox::prepareSingleFileLayout() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void SendFilesBox::prepareGifPreview() {
|
||||||
|
auto createGifPreview = [this] {
|
||||||
|
if (!_information) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
if (auto video = base::get_if<FileLoadTask::Video>(&_information->media)) {
|
||||||
|
return video->isGifv;
|
||||||
|
}
|
||||||
|
// Plain old .gif animation.
|
||||||
|
return _animated;
|
||||||
|
};
|
||||||
|
if (createGifPreview()) {
|
||||||
|
_gifPreview = Media::Clip::MakeReader(FileLocation(_files.front()), QByteArray(), [this](Media::Clip::Notification notification) {
|
||||||
|
clipCallback(notification);
|
||||||
|
});
|
||||||
|
if (_gifPreview) _gifPreview->setAutoplay();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void SendFilesBox::clipCallback(Media::Clip::Notification notification) {
|
||||||
|
using namespace Media::Clip;
|
||||||
|
switch (notification) {
|
||||||
|
case NotificationReinit: {
|
||||||
|
if (_gifPreview && _gifPreview->state() == State::Error) {
|
||||||
|
_gifPreview.setBad();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (_gifPreview && _gifPreview->ready() && !_gifPreview->started()) {
|
||||||
|
auto s = QSize(_previewWidth, _previewHeight);
|
||||||
|
_gifPreview->start(s.width(), s.height(), s.width(), s.height(), ImageRoundRadius::None, ImageRoundCorner::None);
|
||||||
|
}
|
||||||
|
|
||||||
|
update();
|
||||||
|
} break;
|
||||||
|
|
||||||
|
case NotificationRepaint: {
|
||||||
|
if (_gifPreview && !_gifPreview->currentDisplayed()) {
|
||||||
|
update();
|
||||||
|
}
|
||||||
|
} break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void SendFilesBox::prepareDocumentLayout() {
|
void SendFilesBox::prepareDocumentLayout() {
|
||||||
auto filepath = _files.front();
|
auto filepath = _files.front();
|
||||||
if (filepath.isEmpty()) {
|
if (filepath.isEmpty()) {
|
||||||
|
@ -283,8 +328,14 @@ void SendFilesBox::paintEvent(QPaintEvent *e) {
|
||||||
if (_previewLeft + _previewWidth < width() - st::boxPhotoPadding.right()) {
|
if (_previewLeft + _previewWidth < width() - st::boxPhotoPadding.right()) {
|
||||||
p.fillRect(_previewLeft + _previewWidth, st::boxPhotoPadding.top(), width() - st::boxPhotoPadding.right() - _previewLeft - _previewWidth, _previewHeight, st::confirmBg);
|
p.fillRect(_previewLeft + _previewWidth, st::boxPhotoPadding.top(), width() - st::boxPhotoPadding.right() - _previewLeft - _previewWidth, _previewHeight, st::confirmBg);
|
||||||
}
|
}
|
||||||
p.drawPixmap(_previewLeft, st::boxPhotoPadding.top(), _preview);
|
if (_gifPreview && _gifPreview->started()) {
|
||||||
if (_animated) {
|
auto s = QSize(_previewWidth, _previewHeight);
|
||||||
|
auto frame = _gifPreview->current(s.width(), s.height(), s.width(), s.height(), ImageRoundRadius::None, ImageRoundCorner::None, getms());
|
||||||
|
p.drawPixmap(_previewLeft, st::boxPhotoPadding.top(), frame);
|
||||||
|
} else {
|
||||||
|
p.drawPixmap(_previewLeft, st::boxPhotoPadding.top(), _preview);
|
||||||
|
}
|
||||||
|
if (_animated && !_gifPreview) {
|
||||||
auto inner = QRect(_previewLeft + (_previewWidth - st::msgFileSize) / 2, st::boxPhotoPadding.top() + (_previewHeight - st::msgFileSize) / 2, st::msgFileSize, st::msgFileSize);
|
auto inner = QRect(_previewLeft + (_previewWidth - st::msgFileSize) / 2, st::boxPhotoPadding.top() + (_previewHeight - st::msgFileSize) / 2, st::msgFileSize, st::msgFileSize);
|
||||||
p.setPen(Qt::NoPen);
|
p.setPen(Qt::NoPen);
|
||||||
p.setBrush(st::msgDateImgBg);
|
p.setBrush(st::msgDateImgBg);
|
||||||
|
@ -400,9 +451,9 @@ EditCaptionBox::EditCaptionBox(QWidget*, HistoryItem *msg)
|
||||||
QSize dimensions;
|
QSize dimensions;
|
||||||
ImagePtr image;
|
ImagePtr image;
|
||||||
QString caption;
|
QString caption;
|
||||||
DocumentData *doc = 0;
|
DocumentData *doc = nullptr;
|
||||||
if (HistoryMedia *media = msg->getMedia()) {
|
if (auto media = msg->getMedia()) {
|
||||||
HistoryMediaType t = media->type();
|
auto t = media->type();
|
||||||
switch (t) {
|
switch (t) {
|
||||||
case MediaTypeGif: {
|
case MediaTypeGif: {
|
||||||
_animated = true;
|
_animated = true;
|
||||||
|
@ -480,6 +531,7 @@ EditCaptionBox::EditCaptionBox(QWidget*, HistoryItem *msg)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
_thumb = image->pixNoCache(maxW * cIntRetinaFactor(), maxH * cIntRetinaFactor(), Images::Option::Smooth | Images::Option::Blurred, maxW, maxH);
|
_thumb = image->pixNoCache(maxW * cIntRetinaFactor(), maxH * cIntRetinaFactor(), Images::Option::Smooth | Images::Option::Blurred, maxW, maxH);
|
||||||
|
prepareGifPreview(doc);
|
||||||
} else {
|
} else {
|
||||||
maxW = dimensions.width();
|
maxW = dimensions.width();
|
||||||
maxH = dimensions.height();
|
maxH = dimensions.height();
|
||||||
|
@ -520,6 +572,42 @@ EditCaptionBox::EditCaptionBox(QWidget*, HistoryItem *msg)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void EditCaptionBox::prepareGifPreview(DocumentData *document) {
|
||||||
|
auto createGifPreview = [document] {
|
||||||
|
return (document && document->isAnimation());
|
||||||
|
};
|
||||||
|
if (createGifPreview()) {
|
||||||
|
_gifPreview = Media::Clip::MakeReader(document->location(), document->data(), [this](Media::Clip::Notification notification) {
|
||||||
|
clipCallback(notification);
|
||||||
|
});
|
||||||
|
if (_gifPreview) _gifPreview->setAutoplay();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void EditCaptionBox::clipCallback(Media::Clip::Notification notification) {
|
||||||
|
using namespace Media::Clip;
|
||||||
|
switch (notification) {
|
||||||
|
case NotificationReinit: {
|
||||||
|
if (_gifPreview && _gifPreview->state() == State::Error) {
|
||||||
|
_gifPreview.setBad();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (_gifPreview && _gifPreview->ready() && !_gifPreview->started()) {
|
||||||
|
auto s = QSize(_thumbw, _thumbh);
|
||||||
|
_gifPreview->start(s.width(), s.height(), s.width(), s.height(), ImageRoundRadius::None, ImageRoundCorner::None);
|
||||||
|
}
|
||||||
|
|
||||||
|
update();
|
||||||
|
} break;
|
||||||
|
|
||||||
|
case NotificationRepaint: {
|
||||||
|
if (_gifPreview && !_gifPreview->currentDisplayed()) {
|
||||||
|
update();
|
||||||
|
}
|
||||||
|
} break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
bool EditCaptionBox::canEdit(HistoryItem *message) {
|
bool EditCaptionBox::canEdit(HistoryItem *message) {
|
||||||
if (auto media = message->getMedia()) {
|
if (auto media = message->getMedia()) {
|
||||||
switch (media->type()) {
|
switch (media->type()) {
|
||||||
|
@ -580,8 +668,14 @@ void EditCaptionBox::paintEvent(QPaintEvent *e) {
|
||||||
if (_thumbx + _thumbw < width() - st::boxPhotoPadding.right()) {
|
if (_thumbx + _thumbw < width() - st::boxPhotoPadding.right()) {
|
||||||
p.fillRect(_thumbx + _thumbw, st::boxPhotoPadding.top(), width() - st::boxPhotoPadding.right() - _thumbx - _thumbw, _thumbh, st::confirmBg);
|
p.fillRect(_thumbx + _thumbw, st::boxPhotoPadding.top(), width() - st::boxPhotoPadding.right() - _thumbx - _thumbw, _thumbh, st::confirmBg);
|
||||||
}
|
}
|
||||||
p.drawPixmap(_thumbx, st::boxPhotoPadding.top(), _thumb);
|
if (_gifPreview && _gifPreview->started()) {
|
||||||
if (_animated) {
|
auto s = QSize(_thumbw, _thumbh);
|
||||||
|
auto frame = _gifPreview->current(s.width(), s.height(), s.width(), s.height(), ImageRoundRadius::None, ImageRoundCorner::None, getms());
|
||||||
|
p.drawPixmap(_thumbx, st::boxPhotoPadding.top(), frame);
|
||||||
|
} else {
|
||||||
|
p.drawPixmap(_thumbx, st::boxPhotoPadding.top(), _thumb);
|
||||||
|
}
|
||||||
|
if (_animated && !_gifPreview) {
|
||||||
QRect inner(_thumbx + (_thumbw - st::msgFileSize) / 2, st::boxPhotoPadding.top() + (_thumbh - st::msgFileSize) / 2, st::msgFileSize, st::msgFileSize);
|
QRect inner(_thumbx + (_thumbw - st::msgFileSize) / 2, st::boxPhotoPadding.top() + (_thumbh - st::msgFileSize) / 2, st::msgFileSize, st::msgFileSize);
|
||||||
p.setPen(Qt::NoPen);
|
p.setPen(Qt::NoPen);
|
||||||
p.setBrush(st::msgDateImgBg);
|
p.setBrush(st::msgDateImgBg);
|
||||||
|
|
|
@ -66,6 +66,8 @@ private:
|
||||||
void prepareSingleFileLayout();
|
void prepareSingleFileLayout();
|
||||||
void prepareDocumentLayout();
|
void prepareDocumentLayout();
|
||||||
void tryToReadSingleFile();
|
void tryToReadSingleFile();
|
||||||
|
void prepareGifPreview();
|
||||||
|
void clipCallback(Media::Clip::Notification notification);
|
||||||
|
|
||||||
void updateTitleText();
|
void updateTitleText();
|
||||||
void updateBoxSize();
|
void updateBoxSize();
|
||||||
|
@ -84,6 +86,7 @@ private:
|
||||||
int _previewLeft = 0;
|
int _previewLeft = 0;
|
||||||
int _previewWidth = 0;
|
int _previewWidth = 0;
|
||||||
int _previewHeight = 0;
|
int _previewHeight = 0;
|
||||||
|
Media::Clip::ReaderPointer _gifPreview;
|
||||||
|
|
||||||
QPixmap _fileThumb;
|
QPixmap _fileThumb;
|
||||||
Text _nameText;
|
Text _nameText;
|
||||||
|
@ -131,6 +134,8 @@ protected:
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void updateBoxSize();
|
void updateBoxSize();
|
||||||
|
void prepareGifPreview(DocumentData *document);
|
||||||
|
void clipCallback(Media::Clip::Notification notification);
|
||||||
|
|
||||||
void saveDone(const MTPUpdates &updates);
|
void saveDone(const MTPUpdates &updates);
|
||||||
bool saveFail(const RPCError &error);
|
bool saveFail(const RPCError &error);
|
||||||
|
@ -141,6 +146,7 @@ private:
|
||||||
bool _doc = false;
|
bool _doc = false;
|
||||||
|
|
||||||
QPixmap _thumb;
|
QPixmap _thumb;
|
||||||
|
Media::Clip::ReaderPointer _gifPreview;
|
||||||
|
|
||||||
object_ptr<Ui::InputArea> _field = { nullptr };
|
object_ptr<Ui::InputArea> _field = { nullptr };
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue