This ignores --video-align-{x,y} when the video is smaller than the window in the respective direction. After zooming in, panning and zooming out, this is useful to recenter the video in the window. Unlike doing this by observing osd-dimensions in a script, this is done before rerendering, so you don't see the image being rendered uncentered for an instant after zooming out, before being rerendered centered. Also update --video-align docs while at it. This doesn't work well with --video-pan-{x,y} because you can move the output rectangle far away from the image, and when zooming out pan is abruptly reset to the center. It doesn't feel like natural like zooming out after changing --video-align-{x,y}. So this commit doesn't set pan to 0. Also this leaves a way to move scaled images within the window even with --video-recenter.
Unified · Split
| @@ -0,0 +1 @@ | ||
| 1 | +add `--video-recenter` option | |
| @@ -1652,17 +1652,37 @@ Video · 1651 unmodified lines | ||
| 1652 | 1652 | ``--keepaspect=no`` is used. |
| 1653 | 1653 | |
| 1654 | 1654 | ``--video-align-x=<-1-1>``, ``--video-align-y=<-1-1>`` |
| 1655 | − Moves the video rectangle within the black borders, which are usually added | |
| 1656 | − to pad the video to screen if video and screen aspect ratios are different. | |
| 1657 | − ``--video-align-y=-1`` would move the video to the top of the screen | |
| 1658 | − (leaving a border only on the bottom), a value of ``0`` centers it | |
| 1659 | − (default), and a value of ``1`` would put the video at the bottom of the | |
| 1660 | − screen. | |
| 1655 | + When the video is bigger than the window, these move the displayed rectangle | |
| 1656 | + to show different parts of the video. ``--video-align-y=-1`` would display | |
| 1657 | + the top of the video, ``0`` would display the center (default), and ``1`` | |
| 1658 | + would display the bottom. | |
| 1659 | + | |
| 1660 | + When the video is smaller than the window and ``--video-recenter`` is | |
| 1661 | + disabled, these move the video rectangle within the black borders, which are | |
| 1662 | + usually added to pad the video to the window if video and window aspect | |
| 1663 | + ratios are different. ``--video-align-y=-1`` would move the video to the top | |
| 1664 | + of the window (leaving a border only on the bottom), ``0`` would center it, | |
| 1665 | + and ``1`` would put the video at the bottom of the window. | |
| 1661 | 1666 | |
| 1662 | 1667 | If video and screen aspect match perfectly, these options do nothing. |
| 1663 | 1668 | |
| 1669 | + Unlike ``--video-pan-x`` and ``--video-pan-y``, these don't go beyond the | |
| 1670 | + video's or window's boundaries or make the displayed rectangle drift off | |
| 1671 | + after zooming. | |
| 1672 | + | |
| 1664 | 1673 | This option is disabled if ``--keepaspect=no`` is used. |
| 1665 | 1674 | |
| 1675 | +``--video-recenter=<yes|no>`` | |
| 1676 | + Whether to behave as if ``--video-align-x`` and ``--video-align-y`` were 0 | |
| 1677 | + when the video becomes smaller than the window in the respective direction | |
| 1678 | + | |
| 1679 | + After zooming in until the video is bigger the window, panning with | |
| 1680 | + `--video-align-x` and/or `--video-align-y`, and zooming out until the video | |
| 1681 | + is smaller than the window, this is useful to recenter the video in the | |
| 1682 | + window. | |
| 1683 | + | |
| 1684 | + Default: no. | |
| 1685 | + | |
| 1666 | 1686 | ``--video-margin-ratio-left=<val>``, ``--video-margin-ratio-right=<val>``, ``--video-margin-ratio-top=<val>``, ``--video-margin-ratio-bottom=<val>`` |
| 1667 | 1687 | Set extra video margins on each border (default: 0). Each value is a ratio |
| 1668 | 1688 | of the window size, using a range 0.0-1.0. For example, setting the option |
| @@ -165,6 +165,7 @@ static const m_option_t mp_vo_opt_list[] = { · 164 unmodified lines | ||
| 165 | 165 | {"video-crop", OPT_RECT(video_crop), .flags = UPDATE_IMGPAR}, |
| 166 | 166 | {"video-unscaled", OPT_CHOICE(unscaled, |
| 167 | 167 | {"no", 0}, {"yes", 1}, {"downscale-big", 2})}, |
| 168 | + {"video-recenter", OPT_BOOL(recenter)}, | |
| 168 | 169 | {"wid", OPT_INT64(WinID)}, |
| 169 | 170 | {"screen", OPT_CHOICE(screen_id, {"default", -1}), M_RANGE(0, 32)}, |
| 170 | 171 | {"screen-name", OPT_STRING(screen_name)}, |
| @@ -58,6 +58,7 @@ typedef struct mp_vo_opts { · 57 unmodified lines | ||
| 58 | 58 | double window_scale; |
| 59 | 59 | |
| 60 | 60 | bool auto_window_resize; |
| 61 | + bool recenter; | |
| 61 | 62 | bool keepaspect; |
| 62 | 63 | bool keepaspect_window; |
| 63 | 64 | bool hidpi_window_scale; |
| @@ -76,12 +76,15 @@ static void clamp_size(int size, int *start, int *end) · 75 unmodified lines | ||
| 76 | 76 | static void src_dst_split_scaling(int src_size, int dst_size, |
| 77 | 77 | int scaled_src_size, |
| 78 | 78 | float zoom, float align, float pan, float scale, |
| 79 | + bool recenter, | |
| 79 | 80 | int *src_start, int *src_end, |
| 80 | 81 | int *dst_start, int *dst_end, |
| 81 | 82 | int *osd_margin_a, int *osd_margin_b) |
| 82 | 83 | { |
| 83 | 84 | scaled_src_size *= powf(2, zoom) * scale; |
| 84 | 85 | scaled_src_size = MPMAX(scaled_src_size, 1); |
| 86 | + if (recenter && dst_size >= scaled_src_size) | |
| 87 | + align = 0; | |
| 85 | 88 | align = (align + 1) / 2; |
| 86 | 89 | |
| 87 | 90 | *dst_start = (dst_size - scaled_src_size) * align + pan * scaled_src_size; |
| @@ -173,10 +176,12 @@ void mp_get_src_dst_rects(struct mp_log *log, struct mp_vo_opts *opts, · 85 unmodified lines | ||
| 173 | 176 | &scaled_width, &scaled_height); |
| 174 | 177 | src_dst_split_scaling(src_w, vid_window_w, scaled_width, |
| 175 | 178 | opts->zoom, opts->align_x, opts->pan_x, opts->scale_x, |
| 179 | + opts->recenter, | |
| 176 | 180 | &src.x0, &src.x1, &dst.x0, &dst.x1, |
| 177 | 181 | &osd.ml, &osd.mr); |
| 178 | 182 | src_dst_split_scaling(src_h, vid_window_h, scaled_height, |
| 179 | 183 | opts->zoom, opts->align_y, opts->pan_y, opts->scale_y, |
| 184 | + opts->recenter, | |
| 180 | 185 | &src.y0, &src.y1, &dst.y0, &dst.y1, |
| 181 | 186 | &osd.mt, &osd.mb); |
| 182 | 187 | } |