Improve initial video geometry in media viewer.

This commit is contained in:
John Preston 2023-02-17 16:48:31 +04:00
parent 27d446bdda
commit 783d1cd4c1
2 changed files with 60 additions and 34 deletions

View file

@ -529,7 +529,7 @@ void OverlayWidget::setupWindow() {
_window->setAttribute(Qt::WA_TranslucentBackground, true); _window->setAttribute(Qt::WA_TranslucentBackground, true);
_window->setMinimumSize( _window->setMinimumSize(
{ st::windowDefaultWidth, st::windowDefaultHeight }); { st::windowMinHeight, st::windowMinWidth });
_window->shownValue( _window->shownValue(
) | rpl::start_with_next([=](bool shown) { ) | rpl::start_with_next([=](bool shown) {
@ -1305,15 +1305,29 @@ void OverlayWidget::contentSizeChanged() {
resizeContentByScreenSize(); resizeContentByScreenSize();
} }
void OverlayWidget::resizeContentByScreenSize() { void OverlayWidget::recountSkipTop() {
const auto bottom = (!_streamed || videoIsGifOrUserpic()) const auto bottom = (!_streamed || videoIsGifOrUserpic())
? height() ? height()
: (_streamed->controls.y() : (_streamed->controls.y() - st::mediaviewCaptionPadding.bottom());
- st::mediaviewCaptionPadding.bottom() const auto skipHeightBottom = (height() - bottom);
- st::mediaviewCaptionMargin.height()); _skipTop = std::min(
const auto skipHeight = (height() - bottom); std::max(
st::mediaviewCaptionMargin.height(),
height() - _height - skipHeightBottom),
skipHeightBottom);
_availableHeight = height() - skipHeightBottom - _skipTop;
if (_fullScreenVideo && skipHeightBottom > 0 && _width > 0) {
const auto h = width() * _height / _width;
const auto topAllFit = height() - skipHeightBottom - h;
if (_skipTop > topAllFit) {
_skipTop = std::max(topAllFit, 0);
}
}
}
void OverlayWidget::resizeContentByScreenSize() {
recountSkipTop();
const auto availableWidth = width(); const auto availableWidth = width();
const auto availableHeight = height() - 2 * skipHeight;
const auto countZoomFor = [&](int outerw, int outerh) { const auto countZoomFor = [&](int outerw, int outerh) {
auto result = float64(outerw) / _width; auto result = float64(outerw) / _width;
if (_height * result > outerh) { if (_height * result > outerh) {
@ -1327,13 +1341,13 @@ void OverlayWidget::resizeContentByScreenSize() {
return result; return result;
}; };
if (_width > 0 && _height > 0) { if (_width > 0 && _height > 0) {
_zoomToDefault = countZoomFor(availableWidth, availableHeight); _zoomToDefault = countZoomFor(availableWidth, _availableHeight);
_zoomToScreen = countZoomFor(width(), height()); _zoomToScreen = countZoomFor(width(), height());
} else { } else {
_zoomToDefault = _zoomToScreen = 0; _zoomToDefault = _zoomToScreen = 0;
} }
const auto usew = _fullScreenVideo ? width() : availableWidth; const auto usew = _fullScreenVideo ? width() : availableWidth;
const auto useh = _fullScreenVideo ? height() : availableHeight; const auto useh = _fullScreenVideo ? height() : _availableHeight;
if ((_width > usew) || (_height > useh) || _fullScreenVideo) { if ((_width > usew) || (_height > useh) || _fullScreenVideo) {
const auto use = _fullScreenVideo ? _zoomToScreen : _zoomToDefault; const auto use = _fullScreenVideo ? _zoomToScreen : _zoomToDefault;
_zoom = kZoomToScreenLevel; _zoom = kZoomToScreenLevel;
@ -1350,7 +1364,7 @@ void OverlayWidget::resizeContentByScreenSize() {
_h = _height; _h = _height;
} }
_x = (width() - _w) / 2; _x = (width() - _w) / 2;
_y = (height() - _h) / 2; _y = _skipTop + (_availableHeight - _h) / 2;
_geometryAnimation.stop(); _geometryAnimation.stop();
} }
@ -1482,7 +1496,7 @@ void OverlayWidget::zoomReset() {
newZoom = 0; newZoom = 0;
} }
_x = -_width / 2; _x = -_width / 2;
_y = -_height / 2; _y = _skipTop - (_height / 2);
float64 z = (_zoom == kZoomToScreenLevel) ? full : _zoom; float64 z = (_zoom == kZoomToScreenLevel) ? full : _zoom;
if (z >= 0) { if (z >= 0) {
_x = qRound(_x * (z + 1)); _x = qRound(_x * (z + 1));
@ -1492,7 +1506,7 @@ void OverlayWidget::zoomReset() {
_y = qRound(_y / (-z + 1)); _y = qRound(_y / (-z + 1));
} }
_x += width() / 2; _x += width() / 2;
_y += height() / 2; _y += _availableHeight / 2;
update(); update();
zoomUpdate(newZoom); zoomUpdate(newZoom);
} }
@ -3283,13 +3297,19 @@ void OverlayWidget::refreshClipControllerGeometry() {
_groupThumbs = nullptr; _groupThumbs = nullptr;
_groupThumbsRect = QRect(); _groupThumbsRect = QRect();
} }
const auto controllerBottom = _groupThumbs const auto controllerBottom = (_groupThumbs && !_fullScreenVideo)
? _groupThumbsTop ? _groupThumbsTop
: height(); : height();
_streamed->controls.resize(st::mediaviewControllerSize); const auto skip = st::mediaviewCaptionPadding.bottom();
const auto controllerWidth = std::min(
st::mediaviewControllerSize.width(),
width() - 2 * skip);
_streamed->controls.resize(
controllerWidth,
st::mediaviewControllerSize.height());
_streamed->controls.move( _streamed->controls.move(
(width() - _streamed->controls.width()) / 2, (width() - controllerWidth) / 2,
controllerBottom - _streamed->controls.height() - st::mediaviewCaptionPadding.bottom() - st::mediaviewCaptionMargin.height()); controllerBottom - _streamed->controls.height() - st::mediaviewCaptionPadding.bottom());
Ui::SendPendingMoveResizeEvents(&_streamed->controls); Ui::SendPendingMoveResizeEvents(&_streamed->controls);
} }
@ -3547,12 +3567,15 @@ void OverlayWidget::playbackToggleFullScreen() {
_fullScreenVideo = !_fullScreenVideo; _fullScreenVideo = !_fullScreenVideo;
if (_fullScreenVideo) { if (_fullScreenVideo) {
_fullScreenZoomCache = _zoom; _fullScreenZoomCache = _zoom;
setZoomLevel(kZoomToScreenLevel, true); }
} else { resizeCenteredControls();
setZoomLevel(_fullScreenZoomCache, true); recountSkipTop();
setZoomLevel(
_fullScreenVideo ? kZoomToScreenLevel : _fullScreenZoomCache,
true);
if (!_fullScreenVideo) {
_streamed->controls.showAnimated(); _streamed->controls.showAnimated();
} }
_streamed->controls.setInFullScreen(_fullScreenVideo); _streamed->controls.setInFullScreen(_fullScreenVideo);
_touchbarFullscreenToggled.fire_copy(_fullScreenVideo); _touchbarFullscreenToggled.fire_copy(_fullScreenVideo);
updateControls(); updateControls();
@ -4233,10 +4256,10 @@ void OverlayWidget::setZoomLevel(int newZoom, bool force) {
_h = contentSize.height(); _h = contentSize.height();
if (z >= 0) { if (z >= 0) {
nx = (_x - width() / 2.) / (z + 1); nx = (_x - width() / 2.) / (z + 1);
ny = (_y - height() / 2.) / (z + 1); ny = (_y - _availableHeight / 2.) / (z + 1);
} else { } else {
nx = (_x - width() / 2.) * (-z + 1); nx = (_x - width() / 2.) * (-z + 1);
ny = (_y - height() / 2.) * (-z + 1); ny = (_y - _availableHeight / 2.) * (-z + 1);
} }
_zoom = newZoom; _zoom = newZoom;
z = (_zoom == kZoomToScreenLevel) ? full : _zoom; z = (_zoom == kZoomToScreenLevel) ? full : _zoom;
@ -4244,12 +4267,12 @@ void OverlayWidget::setZoomLevel(int newZoom, bool force) {
_w = qRound(_w * (z + 1)); _w = qRound(_w * (z + 1));
_h = qRound(_h * (z + 1)); _h = qRound(_h * (z + 1));
_x = qRound(nx * (z + 1) + width() / 2.); _x = qRound(nx * (z + 1) + width() / 2.);
_y = qRound(ny * (z + 1) + height() / 2.); _y = qRound(ny * (z + 1) + _availableHeight / 2.);
} else { } else {
_w = qRound(_w / (-z + 1)); _w = qRound(_w / (-z + 1));
_h = qRound(_h / (-z + 1)); _h = qRound(_h / (-z + 1));
_x = qRound(nx / (-z + 1) + width() / 2.); _x = qRound(nx / (-z + 1) + width() / 2.);
_y = qRound(ny / (-z + 1) + height() / 2.); _y = qRound(ny / (-z + 1) + _availableHeight / 2.);
} }
snapXY(); snapXY();
if (_opengl) { if (_opengl) {
@ -4531,16 +4554,16 @@ bool OverlayWidget::handleDoubleClick(
} }
void OverlayWidget::snapXY() { void OverlayWidget::snapXY() {
int32 xmin = width() - _w, xmax = 0; auto xmin = width() - _w, xmax = 0;
int32 ymin = height() - _h, ymax = 0; auto ymin = height() - _h, ymax = 0;
if (xmin > (width() - _w) / 2) xmin = (width() - _w) / 2; accumulate_min(xmin, (width() - _w) / 2);
if (xmax < (width() - _w) / 2) xmax = (width() - _w) / 2; accumulate_max(xmax, (width() - _w) / 2);
if (ymin > (height() - _h) / 2) ymin = (height() - _h) / 2; accumulate_min(ymin, _skipTop + (_availableHeight - _h) / 2);
if (ymax < (height() - _h) / 2) ymax = (height() - _h) / 2; accumulate_max(ymax, _skipTop + (_availableHeight - _h) / 2);
if (_x < xmin) _x = xmin; accumulate_max(_x, xmin);
if (_x > xmax) _x = xmax; accumulate_min(_x, xmax);
if (_y < ymin) _y = ymin; accumulate_max(_y, ymin);
if (_y > ymax) _y = ymax; accumulate_min(_y, ymax);
} }
void OverlayWidget::handleMouseMove(QPoint position) { void OverlayWidget::handleMouseMove(QPoint position) {

View file

@ -315,6 +315,7 @@ private:
void resizeCenteredControls(); void resizeCenteredControls();
void resizeContentByScreenSize(); void resizeContentByScreenSize();
void recountSkipTop();
void displayPhoto(not_null<PhotoData*> photo); void displayPhoto(not_null<PhotoData*> photo);
void displayDocument( void displayDocument(
@ -509,6 +510,8 @@ private:
int _width = 0; int _width = 0;
int _height = 0; int _height = 0;
int _skipTop = 0;
int _availableHeight = 0;
int _x = 0, _y = 0, _w = 0, _h = 0; int _x = 0, _y = 0, _w = 0, _h = 0;
int _xStart = 0, _yStart = 0; int _xStart = 0, _yStart = 0;
int _zoom = 0; // < 0 - out, 0 - none, > 0 - in int _zoom = 0; // < 0 - out, 0 - none, > 0 - in