Compare commits
44
Commits
git-release
...
v0.2.2
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
b4f6e57d2c | ||
|
|
854cdb796e | ||
|
|
504c452568 | ||
|
|
ee54711ceb | ||
|
|
3ac568714c | ||
|
|
d64b165b2a | ||
|
|
78a57135f9 | ||
|
|
09f00db142 | ||
|
|
673919df7d | ||
|
|
d2fc1534c8 | ||
|
|
10c3b71720 | ||
|
|
0ba3760745 | ||
|
|
1dbbd845a4 | ||
|
|
131fad8bc9 | ||
|
|
6af87017d1 | ||
|
|
bd70c32504 | ||
|
|
4c88ac3434 | ||
|
|
4cd36b999f | ||
|
|
1b3155cf51 | ||
|
|
ace9a4b6c6 | ||
|
|
84cd043f85 | ||
|
|
6cdc5627f0 | ||
|
|
cb355443dc | ||
|
|
cc2b5c16fa | ||
|
|
bf345136b9 | ||
|
|
6b525b84bb | ||
|
|
ea17adcd66 | ||
|
|
31cdb96474 | ||
|
|
b3233fa3ff | ||
|
|
132528ff67 | ||
|
|
efc32ac0df | ||
|
|
042302fa65 | ||
|
|
93ce083bd8 | ||
|
|
97c93918fe | ||
|
|
7078df4f5e | ||
|
|
8e642809bf | ||
|
|
8c4cf5ce84 | ||
|
|
16cbc4a014 | ||
|
|
2aff8b7523 | ||
|
|
5d9353f0d5 | ||
|
|
6f139ad981 | ||
|
|
0052445e86 | ||
|
|
2cf8d4ffdb | ||
|
|
e6236e22db |
No files matched your search
@@ -1045,9 +1045,14 @@ OPTIONS
|
|||||||
|
|
||||||
``mpv --heartbeat-cmd="gnome-screensaver-command -p" file``
|
``mpv --heartbeat-cmd="gnome-screensaver-command -p" file``
|
||||||
|
|
||||||
|
|
||||||
``--heartbeat-interval=<sec>``
|
``--heartbeat-interval=<sec>``
|
||||||
Time between ``--heartbeat-cmd`` invocations in seconds (default: 30).
|
Time between ``--heartbeat-cmd`` invocations in seconds (default: 30).
|
||||||
|
|
||||||
|
.. note::
|
||||||
|
|
||||||
|
This does not affect the normal screensaver operation in any way.
|
||||||
|
|
||||||
``--help``
|
``--help``
|
||||||
Show short summary of options.
|
Show short summary of options.
|
||||||
|
|
||||||
@@ -2108,7 +2113,7 @@ OPTIONS
|
|||||||
``--stop-screensaver``, ``--no-stop-screensaver``
|
``--stop-screensaver``, ``--no-stop-screensaver``
|
||||||
Turns off the screensaver (or screen blanker and similar mechanisms) at
|
Turns off the screensaver (or screen blanker and similar mechanisms) at
|
||||||
startup and turns it on again on exit (default: yes). The screensaver is
|
startup and turns it on again on exit (default: yes). The screensaver is
|
||||||
always reenabled when the player is paused.
|
always re-enabled when the player is paused.
|
||||||
|
|
||||||
This is not supported on all video outputs or platforms. Sometimes it is
|
This is not supported on all video outputs or platforms. Sometimes it is
|
||||||
implemented, but does not work (happens often on GNOME). You might be able
|
implemented, but does not work (happens often on GNOME). You might be able
|
||||||
|
|||||||
+3
-3
@@ -422,8 +422,8 @@ Available video output drivers are:
|
|||||||
Selects the internal format of textures used for FBOs. The format can
|
Selects the internal format of textures used for FBOs. The format can
|
||||||
influence performance and quality of the video output. (FBOs are not
|
influence performance and quality of the video output. (FBOs are not
|
||||||
always used, and typically only when using extended scalers.)
|
always used, and typically only when using extended scalers.)
|
||||||
``fmt`` can be one of: rgb, rgba, rgb8, rgb10, rgb16, rgb16f, rgb32f,
|
``fmt`` can be one of: rgb, rgba, rgb8, rgb10, rgb10_a2, rgb16, rgb16f,
|
||||||
rgba12, rgba16, rgba16f, rgba32f.
|
rgb32f, rgba12, rgba16, rgba16f, rgba32f.
|
||||||
Default: rgb.
|
Default: rgb.
|
||||||
|
|
||||||
``gamma``
|
``gamma``
|
||||||
@@ -776,4 +776,4 @@ Available video output drivers are:
|
|||||||
|
|
||||||
``alpha``
|
``alpha``
|
||||||
Use a buffer format that supports videos and images with alpha
|
Use a buffer format that supports videos and images with alpha
|
||||||
informations
|
information
|
||||||
@@ -63,6 +63,13 @@ mpv's configure script is greedy and automatically enables features as a result
|
|||||||
of autodetection. The cases where you may want to use `--enable-*` are very
|
of autodetection. The cases where you may want to use `--enable-*` are very
|
||||||
limited.
|
limited.
|
||||||
|
|
||||||
|
FFmpeg vs. Libav
|
||||||
|
----------------
|
||||||
|
|
||||||
|
Generally, mpv should work with the latest release as well as the git version
|
||||||
|
of both FFmpeg and Libav. But FFmpeg is preferred, and some mpv features work
|
||||||
|
with FFmpeg only. See the [wiki article][ffmpeg_vs_libav] about the issue.
|
||||||
|
|
||||||
Bug reports
|
Bug reports
|
||||||
-----------
|
-----------
|
||||||
|
|
||||||
@@ -97,3 +104,4 @@ To contact the `mpv` team in private write to `mpv-team@googlegroups.com`.
|
|||||||
[issue-tracker]: https://github.com/mpv-player/mpv/issues
|
[issue-tracker]: https://github.com/mpv-player/mpv/issues
|
||||||
[mpv-users]: https://groups.google.com/forum/?hl=en#!forum/mpv-users
|
[mpv-users]: https://groups.google.com/forum/?hl=en#!forum/mpv-users
|
||||||
[mpv-devel]: https://groups.google.com/forum/?hl=en#!forum/mpv-devel
|
[mpv-devel]: https://groups.google.com/forum/?hl=en#!forum/mpv-devel
|
||||||
|
[ffmpeg_vs_libav]: https://github.com/mpv-player/mpv/wiki/FFmpeg-versus-Libav
|
||||||
@@ -41,6 +41,7 @@
|
|||||||
#define avresample_alloc_context swr_alloc
|
#define avresample_alloc_context swr_alloc
|
||||||
#define avresample_open swr_init
|
#define avresample_open swr_init
|
||||||
#define avresample_close(x) do { } while(0)
|
#define avresample_close(x) do { } while(0)
|
||||||
|
#define avresample_free swr_free
|
||||||
#define avresample_available(x) 0
|
#define avresample_available(x) 0
|
||||||
#define avresample_convert(ctx, out, out_planesize, out_samples, in, in_planesize, in_samples) \
|
#define avresample_convert(ctx, out, out_planesize, out_samples, in, in_planesize, in_samples) \
|
||||||
swr_convert(ctx, out, out_samples, (const uint8_t**)(in), in_samples)
|
swr_convert(ctx, out, out_samples, (const uint8_t**)(in), in_samples)
|
||||||
@@ -275,8 +276,10 @@ static void uninit(struct af_instance *af)
|
|||||||
struct af_resample *s = af->priv;
|
struct af_resample *s = af->priv;
|
||||||
if (s->avrctx)
|
if (s->avrctx)
|
||||||
avresample_close(s->avrctx);
|
avresample_close(s->avrctx);
|
||||||
|
avresample_free(&s->avrctx);
|
||||||
if (s->avrctx_out)
|
if (s->avrctx_out)
|
||||||
avresample_close(s->avrctx_out);
|
avresample_close(s->avrctx_out);
|
||||||
|
avresample_free(&s->avrctx_out);
|
||||||
}
|
}
|
||||||
|
|
||||||
static bool needs_reorder(int *reorder, int num_ch)
|
static bool needs_reorder(int *reorder, int num_ch)
|
||||||
|
|||||||
@@ -33,7 +33,6 @@
|
|||||||
#include <ctype.h>
|
#include <ctype.h>
|
||||||
#include <math.h>
|
#include <math.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
#include <alloca.h>
|
|
||||||
|
|
||||||
#include "config.h"
|
#include "config.h"
|
||||||
#include "mpvcore/options.h"
|
#include "mpvcore/options.h"
|
||||||
|
|||||||
@@ -125,7 +125,6 @@ static int init(struct ao *ao)
|
|||||||
case AF_FORMAT_S24_LE:
|
case AF_FORMAT_S24_LE:
|
||||||
case AF_FORMAT_S32_LE:
|
case AF_FORMAT_S32_LE:
|
||||||
case AF_FORMAT_FLOAT_LE:
|
case AF_FORMAT_FLOAT_LE:
|
||||||
case AF_FORMAT_AC3_BE:
|
|
||||||
case AF_FORMAT_AC3_LE:
|
case AF_FORMAT_AC3_LE:
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
|
|||||||
@@ -147,7 +147,6 @@ static const struct format_map {
|
|||||||
};
|
};
|
||||||
|
|
||||||
static const int speaker_map[][2] = {
|
static const int speaker_map[][2] = {
|
||||||
{PA_CHANNEL_POSITION_MONO, MP_SPEAKER_ID_FC},
|
|
||||||
{PA_CHANNEL_POSITION_FRONT_LEFT, MP_SPEAKER_ID_FL},
|
{PA_CHANNEL_POSITION_FRONT_LEFT, MP_SPEAKER_ID_FL},
|
||||||
{PA_CHANNEL_POSITION_FRONT_RIGHT, MP_SPEAKER_ID_FR},
|
{PA_CHANNEL_POSITION_FRONT_RIGHT, MP_SPEAKER_ID_FR},
|
||||||
{PA_CHANNEL_POSITION_FRONT_CENTER, MP_SPEAKER_ID_FC},
|
{PA_CHANNEL_POSITION_FRONT_CENTER, MP_SPEAKER_ID_FC},
|
||||||
@@ -174,6 +173,10 @@ static bool chmap_pa_from_mp(pa_channel_map *dst, struct mp_chmap *src)
|
|||||||
if (src->num > PA_CHANNELS_MAX)
|
if (src->num > PA_CHANNELS_MAX)
|
||||||
return false;
|
return false;
|
||||||
dst->channels = src->num;
|
dst->channels = src->num;
|
||||||
|
if (mp_chmap_equals(src, &(const struct mp_chmap)MP_CHMAP_INIT_MONO)) {
|
||||||
|
dst->map[0] = PA_CHANNEL_POSITION_MONO;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
for (int n = 0; n < src->num; n++) {
|
for (int n = 0; n < src->num; n++) {
|
||||||
int mp_speaker = src->speaker[n];
|
int mp_speaker = src->speaker[n];
|
||||||
int pa_speaker = PA_CHANNEL_POSITION_INVALID;
|
int pa_speaker = PA_CHANNEL_POSITION_INVALID;
|
||||||
|
|||||||
@@ -68,6 +68,7 @@ ovcopts = qscale=4
|
|||||||
profile-desc = "H.264 (x264)"
|
profile-desc = "H.264 (x264)"
|
||||||
ovc = libx264
|
ovc = libx264
|
||||||
ovcopts = preset=medium,crf=23,threads=0
|
ovcopts = preset=medium,crf=23,threads=0
|
||||||
|
vf-add = noformat=444p,noformat=444p9,noformat=444p10,noformat=422p,noformat=422p9,noformat=422p10
|
||||||
|
|
||||||
[enc-v-mpeg2]
|
[enc-v-mpeg2]
|
||||||
profile-desc = "MPEG-2 Video (FFmpeg)"
|
profile-desc = "MPEG-2 Video (FFmpeg)"
|
||||||
@@ -152,15 +153,14 @@ profile-desc = "MP4 for Blackberry Bold 9000"
|
|||||||
profile = enc-f-mp4
|
profile = enc-f-mp4
|
||||||
vf-add = dsize=480:360:0:2,scale=w=0:h=0,dsize=-1:-1 # native screen res, letterbox
|
vf-add = dsize=480:360:0:2,scale=w=0:h=0,dsize=-1:-1 # native screen res, letterbox
|
||||||
ovcopts-add = maxrate=1500k,bufsize=1000k,rc_init_occupancy=900k,refs=1,profile=baseline
|
ovcopts-add = maxrate=1500k,bufsize=1000k,rc_init_occupancy=900k,refs=1,profile=baseline
|
||||||
vf-add=noformat=444p,noformat=444p9,noformat=444p10,noformat=422p,noformat=422p9,noformat=422p10
|
|
||||||
omaxfps = 30
|
omaxfps = 30
|
||||||
|
|
||||||
[enc-to-nok-n900]
|
[enc-to-nok-n900]
|
||||||
profile-desc = "MP4 for Nokia N900"
|
profile-desc = "MP4 for Nokia N900"
|
||||||
profile = enc-f-mp4
|
profile = enc-f-mp4
|
||||||
vf-add = dsize=800:480:0:2,scale=w=0:h=0:noup=1 # native screen res, letterbox
|
# DW = 800, DH = 480, SAR = 1
|
||||||
|
vf-add = lavfi=graph="scale=floor(min(min(800\,dar*480)\,in_w*max(1\,sar))/2+0.5)*2:floor(min(min(800/dar\,480)\,in_h*max(1/sar\,1))/2+0.5)*2,setsar=1"
|
||||||
ovcopts-add = profile=baseline,level=30,maxrate=10000k,bufsize=10000k,rc_init_occupancy=9000k,refs=5
|
ovcopts-add = profile=baseline,level=30,maxrate=10000k,bufsize=10000k,rc_init_occupancy=9000k,refs=5
|
||||||
vf-add=noformat=444p,noformat=444p9,noformat=444p10,noformat=422p,noformat=422p9,noformat=422p10
|
|
||||||
omaxfps = 30
|
omaxfps = 30
|
||||||
|
|
||||||
[enc-to-nok-6300]
|
[enc-to-nok-6300]
|
||||||
@@ -180,14 +180,12 @@ vf-add = scale=w=480:h=272,dsize=480:270
|
|||||||
srate = 48000
|
srate = 48000
|
||||||
channels = 2
|
channels = 2
|
||||||
ovcopts-add = b=512k,profile=baseline
|
ovcopts-add = b=512k,profile=baseline
|
||||||
vf-add=noformat=444p,noformat=444p9,noformat=444p10,noformat=422p,noformat=422p9,noformat=422p10
|
|
||||||
|
|
||||||
[enc-to-iphone-noscale]
|
[enc-to-iphone-noscale]
|
||||||
profile-desc = "MP4 for iPhone (no scaling)"
|
profile-desc = "MP4 for iPhone (no scaling)"
|
||||||
profile = enc-f-mp4
|
profile = enc-f-mp4
|
||||||
oautofps = yes # iphone supports 30fps max
|
oautofps = yes # iphone supports 30fps max
|
||||||
ovcopts-add = maxrate=2500k,bufsize=1000k,rc_init_occupancy=900k,level=30,profile=baseline
|
ovcopts-add = maxrate=2500k,bufsize=1000k,rc_init_occupancy=900k,level=30,profile=baseline
|
||||||
vf-add=noformat=444p,noformat=444p9,noformat=444p10,noformat=422p,noformat=422p9,noformat=422p10
|
|
||||||
omaxfps = 30
|
omaxfps = 30
|
||||||
|
|
||||||
[enc-to-iphone]
|
[enc-to-iphone]
|
||||||
@@ -207,3 +205,51 @@ profile-desc = "MP4 for iPhone 5 (1136x640)"
|
|||||||
profile = enc-to-iphone-noscale
|
profile = enc-to-iphone-noscale
|
||||||
vf-add = dsize=1136:480:1:2,scale=w=0:h=0,dsize=-1:-1 # panscan
|
vf-add = dsize=1136:480:1:2,scale=w=0:h=0,dsize=-1:-1 # panscan
|
||||||
omaxfps = 30
|
omaxfps = 30
|
||||||
|
|
||||||
|
[enc-to-hp-slate-7]
|
||||||
|
profile-desc = "MP4 for HP Slate 7 (1024x600, crazy aspect)"
|
||||||
|
profile = enc-f-mp4
|
||||||
|
omaxfps = 30
|
||||||
|
ovcopts-add = profile=high
|
||||||
|
# DW = 1024, DH = 600, DAR = 97:54 (=> SAR = 2425:2304)
|
||||||
|
vf-add = lavfi=graph="scale=floor(min(1024*min(1\,dar*54/97)\,in_w*max(1\,sar*2304/2425))/2+0.5)*2:floor(min(600*min(97/54/dar\,1)\,in_h*max(2425/2304/sar\,1))/2+0.5)*2,setsar=1"
|
||||||
|
|
||||||
|
# Advanced scaling for specific output devices - how it works:
|
||||||
|
# DW = display width (px) (1024)
|
||||||
|
# DH = display height (px) (600)
|
||||||
|
# SAR = display sample aspect ratio, i.e. DAR * DH / DW (2425:2304)
|
||||||
|
# DAR = display aspect ratio, i.e. SAR * DW / DH (97:54)
|
||||||
|
# Variant: zoomed out
|
||||||
|
# vf-add = lavfi=graph="scale=floor(min(DW*min(1\,dar/DAR)\,in_w*max(1\,sar/SAR))/2+0.5)*2:floor(min(DH*min(DAR/dar\,1)\,in_h*max(SAR/sar\,1))/2+0.5)*2,setsar=1"
|
||||||
|
# Variant: zoomed in
|
||||||
|
# vf-add = lavfi=graph="scale=floor(min(DW*max(1\,dar/DAR)\,in_w*max(1\,sar/SAR))/2+0.5)*2:floor(min(DH*max(DAR/dar\,1)\,in_h*max(SAR/sar\,1))/2+0.5)*2,setsar=1"
|
||||||
|
# How it works:
|
||||||
|
# 1a: DW, DH*dar/DAR - fit to display width
|
||||||
|
# 1b: DH*DAR/dar, DH - fit to display height
|
||||||
|
# 1: the min of 1a and 1b these (i.e. fit inside both width and height); for zoomed in view, use the max
|
||||||
|
# 2a: in_w, in_h*SAR/sar - fit to original width
|
||||||
|
# 2b: in_w*sar/SAR, in_h - fit to original height
|
||||||
|
# 2: the max of 2a and 2b (i.e. avoid enlarging both dimensions - let HW scaling handle this)
|
||||||
|
# output: the min of 1 and 2 (i.e. fulfill both constraints)
|
||||||
|
# setsar=1 to prevent scaling on the device (skip this if the device actually wants the proper SAR to be specified for not performing needless scaling)
|
||||||
|
#
|
||||||
|
# Simplified special case for SAR == 1, DAR == DW/DH:
|
||||||
|
# Variant: zoomed out
|
||||||
|
# vf-add = lavfi=graph="scale=floor(min(min(DW\,dar*DH)\,in_w*max(1\,sar))/2+0.5)*2:floor(min(min(DW/dar\,DH)\,in_h*max(1/sar\,1))/2+0.5)*2,setsar=1"
|
||||||
|
# Variant: zoomed in
|
||||||
|
# vf-add = lavfi=graph="scale=floor(min(max(DW\,dar*DH)\,in_w*max(1\,sar))/2+0.5)*2:floor(min(max(DW/dar\,DH)\,in_h*max(1/sar\,1))/2+0.5)*2,setsar=1"
|
||||||
|
# setsar=1 to prevent nasty almost-1 SAR to be passed to the codec due to the rounding which can fail
|
||||||
|
#
|
||||||
|
# If the device supports file SAR properly, we can make use of it to avoid
|
||||||
|
# upscaling. Note that setsar cannot be used to fake a different output SAR by
|
||||||
|
# applying a multiplier to the original one, so e..g it can't be used for the
|
||||||
|
# HP Slate 7!
|
||||||
|
# Variant: zoomed out
|
||||||
|
# vf-add = lavfi=graph="scale=floor(min(DW*min(1\,dar/DAR)\,in_w)/2+0.5)*2:floor(min(DH*min(DAR/dar\,1)\,in_h)/2+0.5)*2"
|
||||||
|
# Variant: zoomed in
|
||||||
|
# vf-add = lavfi=graph="scale=floor(min(DW*max(1\,dar/DAR)\,in_w)/2+0.5)*2:floor(min(DH*max(DAR/dar\,1)\,in_h)/2+0.5)*2"
|
||||||
|
# Simplified special case for SAR == 1, DAR == DW/DH:
|
||||||
|
# Variant: zoomed out
|
||||||
|
# vf-add = lavfi=graph="scale=floor(min(min(DW\,dar*DH)\,in_w)/2+0.5)*2:floor(min(min(DW/dar\,DH)\,in_h)/2+0.5)*2"
|
||||||
|
# Variant: zoomed in
|
||||||
|
# vf-add = lavfi=graph="scale=floor(min(max(DW\,dar*DH)\,in_w)/2+0.5)*2:floor(min(max(DW/dar\,DH)\,in_h)/2+0.5)*2"
|
||||||
+3
-1
@@ -3,6 +3,7 @@ Type=Application
|
|||||||
Name=mpv Media Player
|
Name=mpv Media Player
|
||||||
Name[ca]=Reproductor multimèdia mpv
|
Name[ca]=Reproductor multimèdia mpv
|
||||||
Name[pl]=mpv odtwarzacz multimedialny
|
Name[pl]=mpv odtwarzacz multimedialny
|
||||||
|
Name[ru]=Проигрыватель mpv
|
||||||
GenericName=Multimedia player
|
GenericName=Multimedia player
|
||||||
Comment=Play movies and songs
|
Comment=Play movies and songs
|
||||||
Comment[ca]=Reproduïu vídeos i cançons
|
Comment[ca]=Reproduïu vídeos i cançons
|
||||||
@@ -10,8 +11,9 @@ Comment[de]=Filme und Musik abspielen
|
|||||||
Comment[es]=Reproduzca vídeos y canciones
|
Comment[es]=Reproduzca vídeos y canciones
|
||||||
Comment[fr]=Lecteur multimédia
|
Comment[fr]=Lecteur multimédia
|
||||||
Comment[it]=Lettore multimediale
|
Comment[it]=Lettore multimediale
|
||||||
Comment[zh]=多媒体播放器
|
|
||||||
Comment[pl]=Odtwarzaj filmy i muzykę
|
Comment[pl]=Odtwarzaj filmy i muzykę
|
||||||
|
Comment[ru]=Воспроизвести фильмы и музыку
|
||||||
|
Comment[zh]=多媒体播放器
|
||||||
Icon=mpv
|
Icon=mpv
|
||||||
TryExec=mpv
|
TryExec=mpv
|
||||||
Exec=mpv --really-quiet --force-window -- %F
|
Exec=mpv --really-quiet --force-window -- %F
|
||||||
|
|||||||
@@ -1783,7 +1783,7 @@ static void input_wait_read(struct input_ctx *ictx, int time)
|
|||||||
*/
|
*/
|
||||||
static void read_events(struct input_ctx *ictx, int time)
|
static void read_events(struct input_ctx *ictx, int time)
|
||||||
{
|
{
|
||||||
if (ictx->num_key_down) {
|
if (ictx->num_key_down && ictx->ar_rate > 0) {
|
||||||
time = FFMIN(time, 1000 / ictx->ar_rate);
|
time = FFMIN(time, 1000 / ictx->ar_rate);
|
||||||
time = FFMIN(time, ictx->ar_delay);
|
time = FFMIN(time, ictx->ar_delay);
|
||||||
}
|
}
|
||||||
|
|||||||
+10
-4
@@ -52,7 +52,7 @@ local osc_styles = {
|
|||||||
|
|
||||||
-- internal states, do not touch
|
-- internal states, do not touch
|
||||||
local state = {
|
local state = {
|
||||||
showtime, -- time of last invokation (last mouse move)
|
showtime, -- time of last invocation (last mouse move)
|
||||||
osc_visible = false,
|
osc_visible = false,
|
||||||
anistart, -- time when the animation started
|
anistart, -- time when the animation started
|
||||||
anitype, -- current type of animation
|
anitype, -- current type of animation
|
||||||
@@ -636,7 +636,7 @@ function osc_init()
|
|||||||
-- kill old Elements
|
-- kill old Elements
|
||||||
elements = {}
|
elements = {}
|
||||||
|
|
||||||
-- set canvas resolution acording to display aspect and scaling setting
|
-- set canvas resolution according to display aspect and scaling setting
|
||||||
local baseResY = 720
|
local baseResY = 720
|
||||||
local display_w, display_h, display_aspect = mp.get_screen_size()
|
local display_w, display_h, display_aspect = mp.get_screen_size()
|
||||||
local scale = 1
|
local scale = 1
|
||||||
@@ -650,13 +650,19 @@ function osc_init()
|
|||||||
end
|
end
|
||||||
|
|
||||||
|
|
||||||
if user_opts.vidscale == true then
|
if user_opts.vidscale then
|
||||||
osc_param.playresy = baseResY / scale
|
osc_param.playresy = baseResY / scale
|
||||||
else
|
else
|
||||||
osc_param.playresy = display_h / scale
|
osc_param.playresy = display_h / scale
|
||||||
end
|
end
|
||||||
osc_param.playresx = osc_param.playresy * display_aspect
|
osc_param.playresx = osc_param.playresy * display_aspect
|
||||||
|
|
||||||
|
-- make sure the OSC actually fits into the video
|
||||||
|
if (osc_param.playresx < (osc_param.osc_w + (2 * osc_param.osc_p))) then
|
||||||
|
osc_param.playresy = (osc_param.osc_w + (2 * osc_param.osc_p)) / display_aspect
|
||||||
|
osc_param.playresx = osc_param.playresy * display_aspect
|
||||||
|
end
|
||||||
|
|
||||||
-- position of the controller according to video aspect and valignment
|
-- position of the controller according to video aspect and valignment
|
||||||
osc_param.posX = math.floor(get_align(user_opts.halign, osc_param.playresx, osc_param.osc_w, 0))
|
osc_param.posX = math.floor(get_align(user_opts.halign, osc_param.playresx, osc_param.osc_w, 0))
|
||||||
osc_param.posY = math.floor(get_align(user_opts.valign, osc_param.playresy, osc_param.osc_h, 0))
|
osc_param.posY = math.floor(get_align(user_opts.valign, osc_param.playresy, osc_param.osc_h, 0))
|
||||||
@@ -999,7 +1005,7 @@ end
|
|||||||
|
|
||||||
function show_osc()
|
function show_osc()
|
||||||
|
|
||||||
--remember last time of invokation (mouse move)
|
--remember last time of invocation (mouse move)
|
||||||
state.showtime = mp.get_timer()
|
state.showtime = mp.get_timer()
|
||||||
|
|
||||||
state.osc_visible = true
|
state.osc_visible = true
|
||||||
|
|||||||
+5
-1
@@ -185,6 +185,7 @@ static const char av_desync_help_text[] = _(
|
|||||||
" Download the file instead.\n"
|
" Download the file instead.\n"
|
||||||
"- Try to find out whether audio or video is causing this by experimenting\n"
|
"- Try to find out whether audio or video is causing this by experimenting\n"
|
||||||
" with --no-video and --no-audio.\n"
|
" with --no-video and --no-audio.\n"
|
||||||
|
"- If you swiched audio or video tracks, try seeking to force synchronization.\n"
|
||||||
"If none of this helps you, file a bug report.\n\n");
|
"If none of this helps you, file a bug report.\n\n");
|
||||||
|
|
||||||
|
|
||||||
@@ -240,7 +241,8 @@ static double get_play_end_pts(struct MPContext *mpctx)
|
|||||||
if (opts->play_end.type) {
|
if (opts->play_end.type) {
|
||||||
return rel_time_to_abs(mpctx, opts->play_end, MP_NOPTS_VALUE);
|
return rel_time_to_abs(mpctx, opts->play_end, MP_NOPTS_VALUE);
|
||||||
} else if (opts->play_length.type) {
|
} else if (opts->play_length.type) {
|
||||||
double start = rel_time_to_abs(mpctx, opts->play_start, 0);
|
double startpts = get_start_time(mpctx);
|
||||||
|
double start = rel_time_to_abs(mpctx, opts->play_start, startpts);
|
||||||
double length = rel_time_to_abs(mpctx, opts->play_length, -1);
|
double length = rel_time_to_abs(mpctx, opts->play_length, -1);
|
||||||
if (start != -1 && length != -1)
|
if (start != -1 && length != -1)
|
||||||
return start + length;
|
return start + length;
|
||||||
@@ -4251,6 +4253,8 @@ static void add_subtitle_fonts_from_sources(struct MPContext *mpctx)
|
|||||||
static struct mp_resolve_result *resolve_url(const char *filename,
|
static struct mp_resolve_result *resolve_url(const char *filename,
|
||||||
struct MPOpts *opts)
|
struct MPOpts *opts)
|
||||||
{
|
{
|
||||||
|
if (!mp_is_url(bstr0(filename)))
|
||||||
|
return NULL;
|
||||||
#if defined(CONFIG_LIBQUVI) || defined(CONFIG_LIBQUVI9)
|
#if defined(CONFIG_LIBQUVI) || defined(CONFIG_LIBQUVI9)
|
||||||
return mp_resolve_quvi(filename, opts);
|
return mp_resolve_quvi(filename, opts);
|
||||||
#else
|
#else
|
||||||
|
|||||||
+5
-2
@@ -34,6 +34,7 @@
|
|||||||
#ifdef CONFIG_IOCTL
|
#ifdef CONFIG_IOCTL
|
||||||
#include <sys/ioctl.h>
|
#include <sys/ioctl.h>
|
||||||
#endif
|
#endif
|
||||||
|
#include <errno.h>
|
||||||
|
|
||||||
#ifdef HAVE_TERMIOS
|
#ifdef HAVE_TERMIOS
|
||||||
#ifdef HAVE_TERMIOS_H
|
#ifdef HAVE_TERMIOS_H
|
||||||
@@ -369,8 +370,10 @@ bool getch2(struct input_ctx *input_ctx)
|
|||||||
* happen if the terminal state change done in getch2_enable()
|
* happen if the terminal state change done in getch2_enable()
|
||||||
* works.
|
* works.
|
||||||
*/
|
*/
|
||||||
if (retval < 1)
|
if (retval == 0)
|
||||||
return retval;
|
return false;
|
||||||
|
if (retval == -1)
|
||||||
|
return errno != EBADF && errno != EINVAL;
|
||||||
getch2_len += retval;
|
getch2_len += retval;
|
||||||
|
|
||||||
static enum {
|
static enum {
|
||||||
|
|||||||
@@ -77,6 +77,7 @@ static NSString *escape_loadfile_name(NSString *input)
|
|||||||
@synthesize inputContext = _input_context;
|
@synthesize inputContext = _input_context;
|
||||||
@synthesize eventsResponder = _events_responder;
|
@synthesize eventsResponder = _events_responder;
|
||||||
@synthesize menuItems = _menu_items;
|
@synthesize menuItems = _menu_items;
|
||||||
|
@synthesize input_ready = _input_ready;
|
||||||
|
|
||||||
- (void)sendEvent:(NSEvent *)event
|
- (void)sendEvent:(NSEvent *)event
|
||||||
{
|
{
|
||||||
@@ -94,6 +95,7 @@ static NSString *escape_loadfile_name(NSString *input)
|
|||||||
self.argumentsList = [[[NSMutableArray alloc] init] autorelease];
|
self.argumentsList = [[[NSMutableArray alloc] init] autorelease];
|
||||||
self.eventsResponder = [[[EventsResponder alloc] init] autorelease];
|
self.eventsResponder = [[[EventsResponder alloc] init] autorelease];
|
||||||
self.willStopOnOpenEvent = NO;
|
self.willStopOnOpenEvent = NO;
|
||||||
|
self.input_ready = [[[NSCondition alloc] init] autorelease];
|
||||||
|
|
||||||
[NSEvent addLocalMonitorForEventsMatchingMask:NSKeyDownMask|NSKeyUpMask
|
[NSEvent addLocalMonitorForEventsMatchingMask:NSKeyDownMask|NSKeyUpMask
|
||||||
handler:^(NSEvent *event) {
|
handler:^(NSEvent *event) {
|
||||||
@@ -325,6 +327,11 @@ int cocoa_main(mpv_main_fn mpv_main, int argc, char *argv[])
|
|||||||
init_cocoa_application();
|
init_cocoa_application();
|
||||||
macosx_finder_args_preinit(&argc, &argv);
|
macosx_finder_args_preinit(&argc, &argv);
|
||||||
pthread_create(&playback_thread_id, NULL, playback_thread, &ctx);
|
pthread_create(&playback_thread_id, NULL, playback_thread, &ctx);
|
||||||
|
|
||||||
|
[mpv_shared_app().input_ready lock];
|
||||||
|
[mpv_shared_app().input_ready wait];
|
||||||
|
[mpv_shared_app().input_ready unlock];
|
||||||
|
|
||||||
cocoa_run_runloop();
|
cocoa_run_runloop();
|
||||||
|
|
||||||
// This should never be reached: cocoa_run_runloop blocks until the
|
// This should never be reached: cocoa_run_runloop blocks until the
|
||||||
@@ -380,6 +387,12 @@ void cocoa_stop_runloop(void)
|
|||||||
|
|
||||||
void cocoa_set_input_context(struct input_ctx *input_context)
|
void cocoa_set_input_context(struct input_ctx *input_context)
|
||||||
{
|
{
|
||||||
|
if (input_context) {
|
||||||
|
[mpv_shared_app().input_ready lock];
|
||||||
|
[mpv_shared_app().input_ready signal];
|
||||||
|
[mpv_shared_app().input_ready unlock];
|
||||||
|
}
|
||||||
|
|
||||||
mpv_shared_app().inputContext = input_context;
|
mpv_shared_app().inputContext = input_context;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -450,10 +463,15 @@ static bool bundle_started_from_finder(int argc, char **argv)
|
|||||||
bool bundle_detected = [[NSBundle mainBundle] bundleIdentifier];
|
bool bundle_detected = [[NSBundle mainBundle] bundleIdentifier];
|
||||||
int major, minor, bugfix;
|
int major, minor, bugfix;
|
||||||
get_system_version(&major, &minor, &bugfix);
|
get_system_version(&major, &minor, &bugfix);
|
||||||
|
bool without_psn = bundle_detected && argc==1;
|
||||||
|
bool with_psn = bundle_detected && argc==2 && is_psn_argument(argv[1]);
|
||||||
|
|
||||||
if ((major == 10) && (minor >= 9)) {
|
if ((major == 10) && (minor >= 9)) {
|
||||||
return bundle_detected && argc==1;
|
// Looks like opening quarantined files from the finder inserts the
|
||||||
|
// -psn argument while normal files do not. Hurr.
|
||||||
|
return with_psn || without_psn;
|
||||||
} else {
|
} else {
|
||||||
return bundle_detected && argc==2 && is_psn_argument(argv[1]);
|
return with_psn;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -43,6 +43,7 @@
|
|||||||
@property(nonatomic, retain) NSArray *files;
|
@property(nonatomic, retain) NSArray *files;
|
||||||
@property(nonatomic, retain) NSMutableArray *argumentsList;
|
@property(nonatomic, retain) NSMutableArray *argumentsList;
|
||||||
@property(nonatomic, assign) BOOL willStopOnOpenEvent;
|
@property(nonatomic, assign) BOOL willStopOnOpenEvent;
|
||||||
|
@property(nonatomic, retain) NSCondition *input_ready;
|
||||||
@end
|
@end
|
||||||
|
|
||||||
Application *mpv_shared_app(void);
|
Application *mpv_shared_app(void);
|
||||||
@@ -19,7 +19,6 @@
|
|||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include <sys/time.h>
|
#include <sys/time.h>
|
||||||
#include <alloca.h>
|
|
||||||
|
|
||||||
#include "config.h"
|
#include "config.h"
|
||||||
|
|
||||||
|
|||||||
@@ -136,6 +136,12 @@ static void decode(struct sd *sd, struct demux_packet *packet)
|
|||||||
AVSubtitle sub;
|
AVSubtitle sub;
|
||||||
AVPacket pkt;
|
AVPacket pkt;
|
||||||
|
|
||||||
|
// libavformat sets duration==0, even if the duration is unknown.
|
||||||
|
// Assume there are no bitmap subs that actually use duration==0 for
|
||||||
|
// hidden subtitle events.
|
||||||
|
if (duration == 0)
|
||||||
|
duration = -1;
|
||||||
|
|
||||||
clear(priv);
|
clear(priv);
|
||||||
av_init_packet(&pkt);
|
av_init_packet(&pkt);
|
||||||
pkt.data = packet->buffer;
|
pkt.data = packet->buffer;
|
||||||
|
|||||||
@@ -26,6 +26,12 @@
|
|||||||
#define TA_TYPEOF(t) void *
|
#define TA_TYPEOF(t) void *
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
// Broken crap with __USE_MINGW_ANSI_STDIO
|
||||||
|
#ifdef __MINGW32__
|
||||||
|
#undef TA_PRF
|
||||||
|
#define TA_PRF(a1, a2) __attribute__ ((format (gnu_printf, a1, a2)))
|
||||||
|
#endif
|
||||||
|
|
||||||
#define TA_STRINGIFY_(x) # x
|
#define TA_STRINGIFY_(x) # x
|
||||||
#define TA_STRINGIFY(x) TA_STRINGIFY_(x)
|
#define TA_STRINGIFY(x) TA_STRINGIFY_(x)
|
||||||
|
|
||||||
|
|||||||
+13
-7
@@ -349,7 +349,6 @@ static void init_avctx(sh_video_t *sh, const char *decoder,
|
|||||||
ctx->image_params = (struct mp_image_params){0};
|
ctx->image_params = (struct mp_image_params){0};
|
||||||
ctx->vo_image_params = (struct mp_image_params){0};
|
ctx->vo_image_params = (struct mp_image_params){0};
|
||||||
ctx->hwdec = hwdec;
|
ctx->hwdec = hwdec;
|
||||||
ctx->pic = avcodec_alloc_frame();
|
|
||||||
ctx->avctx = avcodec_alloc_context3(lavc_codec);
|
ctx->avctx = avcodec_alloc_context3(lavc_codec);
|
||||||
AVCodecContext *avctx = ctx->avctx;
|
AVCodecContext *avctx = ctx->avctx;
|
||||||
avctx->opaque = sh;
|
avctx->opaque = sh;
|
||||||
@@ -358,6 +357,14 @@ static void init_avctx(sh_video_t *sh, const char *decoder,
|
|||||||
|
|
||||||
avctx->thread_count = lavc_param->threads;
|
avctx->thread_count = lavc_param->threads;
|
||||||
|
|
||||||
|
|
||||||
|
#if HAVE_AVUTIL_REFCOUNTING
|
||||||
|
avctx->refcounted_frames = 1;
|
||||||
|
ctx->pic = av_frame_alloc();
|
||||||
|
#else
|
||||||
|
ctx->pic = avcodec_alloc_frame();
|
||||||
|
#endif
|
||||||
|
|
||||||
if (ctx->hwdec && ctx->hwdec->allocate_image) {
|
if (ctx->hwdec && ctx->hwdec->allocate_image) {
|
||||||
ctx->do_hw_dr1 = true;
|
ctx->do_hw_dr1 = true;
|
||||||
avctx->thread_count = 1;
|
avctx->thread_count = 1;
|
||||||
@@ -369,9 +376,7 @@ static void init_avctx(sh_video_t *sh, const char *decoder,
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
#if HAVE_AVUTIL_REFCOUNTING
|
#if !HAVE_AVUTIL_REFCOUNTING
|
||||||
avctx->refcounted_frames = 1;
|
|
||||||
#else
|
|
||||||
if (lavc_codec->capabilities & CODEC_CAP_DR1) {
|
if (lavc_codec->capabilities & CODEC_CAP_DR1) {
|
||||||
ctx->do_dr1 = true;
|
ctx->do_dr1 = true;
|
||||||
avctx->get_buffer = mp_codec_get_buffer;
|
avctx->get_buffer = mp_codec_get_buffer;
|
||||||
@@ -449,12 +454,14 @@ static void uninit_avctx(sh_video_t *sh)
|
|||||||
}
|
}
|
||||||
|
|
||||||
av_freep(&ctx->avctx);
|
av_freep(&ctx->avctx);
|
||||||
avcodec_free_frame(&ctx->pic);
|
|
||||||
|
|
||||||
if (ctx->hwdec && ctx->hwdec->uninit)
|
if (ctx->hwdec && ctx->hwdec->uninit)
|
||||||
ctx->hwdec->uninit(ctx);
|
ctx->hwdec->uninit(ctx);
|
||||||
|
|
||||||
#if !HAVE_AVUTIL_REFCOUNTING
|
#if HAVE_AVUTIL_REFCOUNTING
|
||||||
|
av_frame_free(&ctx->pic);
|
||||||
|
#else
|
||||||
|
avcodec_free_frame(&ctx->pic);
|
||||||
mp_buffer_pool_free(&ctx->dr1_buffer_pool);
|
mp_buffer_pool_free(&ctx->dr1_buffer_pool);
|
||||||
#endif
|
#endif
|
||||||
ctx->last_sample_aspect_ratio = (AVRational){0, 0};
|
ctx->last_sample_aspect_ratio = (AVRational){0, 0};
|
||||||
@@ -603,7 +610,6 @@ static int get_buffer2_hwdec(AVCodecContext *avctx, AVFrame *pic, int flags)
|
|||||||
static void setup_refcounting_hw(AVCodecContext *avctx)
|
static void setup_refcounting_hw(AVCodecContext *avctx)
|
||||||
{
|
{
|
||||||
avctx->get_buffer2 = get_buffer2_hwdec;
|
avctx->get_buffer2 = get_buffer2_hwdec;
|
||||||
avctx->refcounted_frames = 1;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#else /* HAVE_AVUTIL_REFCOUNTING */
|
#else /* HAVE_AVUTIL_REFCOUNTING */
|
||||||
|
|||||||
@@ -257,6 +257,7 @@ static struct mp_image *process_image(struct lavc_ctx *ctx, struct mp_image *img
|
|||||||
}
|
}
|
||||||
|
|
||||||
const struct vd_lavc_hwdec mp_vd_lavc_vdpau_old = {
|
const struct vd_lavc_hwdec mp_vd_lavc_vdpau_old = {
|
||||||
|
.type = HWDEC_VDPAU,
|
||||||
.image_formats = (const int[]) {
|
.image_formats = (const int[]) {
|
||||||
IMGFMT_VDPAU_MPEG1, IMGFMT_VDPAU_MPEG2, IMGFMT_VDPAU_H264,
|
IMGFMT_VDPAU_MPEG1, IMGFMT_VDPAU_MPEG2, IMGFMT_VDPAU_H264,
|
||||||
IMGFMT_VDPAU_WMV3, IMGFMT_VDPAU_VC1, IMGFMT_VDPAU_MPEG4,
|
IMGFMT_VDPAU_WMV3, IMGFMT_VDPAU_VC1, IMGFMT_VDPAU_MPEG4,
|
||||||
|
|||||||
@@ -361,7 +361,7 @@ static int control(struct vf_instance *vf, int request, void *data)
|
|||||||
break;
|
break;
|
||||||
return CONTROL_TRUE;
|
return CONTROL_TRUE;
|
||||||
case VFCTRL_SET_EQUALIZER:
|
case VFCTRL_SET_EQUALIZER:
|
||||||
if (mp_sws_get_vf_equalizer(sws, data) < 1)
|
if (mp_sws_set_vf_equalizer(sws, data) < 1)
|
||||||
break;
|
break;
|
||||||
return CONTROL_TRUE;
|
return CONTROL_TRUE;
|
||||||
default:
|
default:
|
||||||
|
|||||||
@@ -15,6 +15,8 @@
|
|||||||
* with mpv. If not, see <http://www.gnu.org/licenses/>.
|
* with mpv. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
#include <libavutil/common.h>
|
||||||
|
|
||||||
#include "mpvcore/input/keycodes.h"
|
#include "mpvcore/input/keycodes.h"
|
||||||
|
|
||||||
#include "osdep/macosx_application.h"
|
#include "osdep/macosx_application.h"
|
||||||
@@ -29,6 +31,7 @@
|
|||||||
@implementation MpvVideoWindow {
|
@implementation MpvVideoWindow {
|
||||||
NSSize _queued_video_size;
|
NSSize _queued_video_size;
|
||||||
bool _fs_resize_scheduled;
|
bool _fs_resize_scheduled;
|
||||||
|
bool _recenter_window_during_constraint;
|
||||||
}
|
}
|
||||||
|
|
||||||
@synthesize adapter = _adapter;
|
@synthesize adapter = _adapter;
|
||||||
@@ -115,17 +118,27 @@
|
|||||||
CGFloat dx = (f.size.width - ns.width) / 2;
|
CGFloat dx = (f.size.width - ns.width) / 2;
|
||||||
CGFloat dy = (f.size.height - ns.height - [self titleHeight]) / 2;
|
CGFloat dy = (f.size.height - ns.height - [self titleHeight]) / 2;
|
||||||
NSRect nf = NSRectFromCGRect(CGRectInset(NSRectToCGRect(f), dx, dy));
|
NSRect nf = NSRectFromCGRect(CGRectInset(NSRectToCGRect(f), dx, dy));
|
||||||
|
self->_recenter_window_during_constraint = true;
|
||||||
[self setFrame:nf display:NO animate:NO];
|
[self setFrame:nf display:NO animate:NO];
|
||||||
}
|
}
|
||||||
|
|
||||||
- (NSRect)constrainFrameRect:(NSRect)nf toScreen:(NSScreen *)screen
|
- (NSRect)constrainFrameRect:(NSRect)nf toScreen:(NSScreen *)screen
|
||||||
{
|
{
|
||||||
NSRect s = [[self screen] visibleFrame];
|
NSRect s = [[self screen] visibleFrame];
|
||||||
if (nf.origin.y + nf.size.height > s.origin.y + s.size.height)
|
if (nf.origin.y + nf.size.height > s.origin.y + s.size.height) {
|
||||||
|
if (self->_recenter_window_during_constraint)
|
||||||
|
nf.size.height = s.size.height;
|
||||||
nf.origin.y = s.origin.y + s.size.height - nf.size.height;
|
nf.origin.y = s.origin.y + s.size.height - nf.size.height;
|
||||||
|
}
|
||||||
return nf;
|
return nf;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
- (void)setFrame:(NSRect)frame display:(BOOL)display animate:(BOOL)animate
|
||||||
|
{
|
||||||
|
[super setFrame:frame display:display animate:animate];
|
||||||
|
self->_recenter_window_during_constraint = false;
|
||||||
|
}
|
||||||
|
|
||||||
- (void)queueNewVideoSize:(NSSize)new_size
|
- (void)queueNewVideoSize:(NSSize)new_size
|
||||||
{
|
{
|
||||||
NSSize prev_size = self->_queued_video_size;
|
NSSize prev_size = self->_queued_video_size;
|
||||||
|
|||||||
@@ -438,16 +438,16 @@ void vo_cocoa_set_current_context(struct vo *vo, bool current)
|
|||||||
{
|
{
|
||||||
struct vo_cocoa_state *s = vo->cocoa;
|
struct vo_cocoa_state *s = vo->cocoa;
|
||||||
|
|
||||||
if (s->inside_sync_section) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (current) {
|
if (current) {
|
||||||
[s->lock lock];
|
if (!s->inside_sync_section)
|
||||||
|
[s->lock lock];
|
||||||
|
|
||||||
[s->gl_ctx makeCurrentContext];
|
[s->gl_ctx makeCurrentContext];
|
||||||
} else {
|
} else {
|
||||||
[NSOpenGLContext clearCurrentContext];
|
[NSOpenGLContext clearCurrentContext];
|
||||||
[s->lock unlock];
|
|
||||||
|
if (!s->inside_sync_section)
|
||||||
|
[s->lock unlock];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -944,8 +944,13 @@ bool mpgl_config_window(struct MPGLContext *ctx, int gl_caps, uint32_t d_width,
|
|||||||
|
|
||||||
MP_WARN(ctx->vo, "Missing OpenGL features:");
|
MP_WARN(ctx->vo, "Missing OpenGL features:");
|
||||||
list_features(missing, ctx->vo->log, MSGL_WARN, false);
|
list_features(missing, ctx->vo->log, MSGL_WARN, false);
|
||||||
if (missing & MPGL_CAP_NO_SW)
|
if (missing & MPGL_CAP_NO_SW) {
|
||||||
MP_WARN(ctx->vo, "Rejecting suspected software OpenGL renderer.\n");
|
MP_WARN(ctx->vo, "Rejecting suspected software OpenGL renderer.\n");
|
||||||
|
} else if ((missing & MPGL_CAP_GL21) &&
|
||||||
|
(ctx->gl->mpgl_caps & MPGL_CAP_GL_LEGACY))
|
||||||
|
{
|
||||||
|
MP_WARN(ctx->vo, "OpenGL version too old. Try: --vo=opengl-old\n");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
MP_ERR(ctx->vo, "OpenGL context creation failed!\n");
|
MP_ERR(ctx->vo, "OpenGL context creation failed!\n");
|
||||||
|
|||||||
@@ -37,7 +37,7 @@
|
|||||||
|
|
||||||
#include "video/mp_image.h"
|
#include "video/mp_image.h"
|
||||||
|
|
||||||
#if defined(CONFIG_GL_COCOA) && !defined(CONFIG_GL_X11)
|
#if defined(CONFIG_GL_COCOA)
|
||||||
#ifdef GL_VERSION_3_0
|
#ifdef GL_VERSION_3_0
|
||||||
#include <OpenGL/gl3.h>
|
#include <OpenGL/gl3.h>
|
||||||
#else
|
#else
|
||||||
|
|||||||
@@ -304,6 +304,7 @@ const struct m_sub_options gl_video_conf = {
|
|||||||
{"rgba", GL_RGBA},
|
{"rgba", GL_RGBA},
|
||||||
{"rgb8", GL_RGB8},
|
{"rgb8", GL_RGB8},
|
||||||
{"rgb10", GL_RGB10},
|
{"rgb10", GL_RGB10},
|
||||||
|
{"rgb10_a2", GL_RGB10_A2},
|
||||||
{"rgb16", GL_RGB16},
|
{"rgb16", GL_RGB16},
|
||||||
{"rgb16f", GL_RGB16F},
|
{"rgb16f", GL_RGB16F},
|
||||||
{"rgb32f", GL_RGB32F},
|
{"rgb32f", GL_RGB32F},
|
||||||
|
|||||||
+1
-1
@@ -123,7 +123,7 @@ static bool create_context_x11_gl3(struct MPGLContext *ctx, bool debug)
|
|||||||
glx_ctx->fbc, 0, True,
|
glx_ctx->fbc, 0, True,
|
||||||
context_attribs);
|
context_attribs);
|
||||||
if (!context) {
|
if (!context) {
|
||||||
MP_FATAL(vo, "Could not create GLX context!\n");
|
MP_ERR(vo, "Could not create GL3 context. Retrying with legacy context.\n");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
+24
-6
@@ -114,7 +114,7 @@ static const struct fmt_entry fmt_table[] = {
|
|||||||
{0}
|
{0}
|
||||||
};
|
};
|
||||||
|
|
||||||
static void allocate_xvimage(struct vo *, int);
|
static bool allocate_xvimage(struct vo *, int);
|
||||||
static void deallocate_xvimage(struct vo *vo, int foo);
|
static void deallocate_xvimage(struct vo *vo, int foo);
|
||||||
static struct mp_image get_xv_buffer(struct vo *vo, int buf_index);
|
static struct mp_image get_xv_buffer(struct vo *vo, int buf_index);
|
||||||
|
|
||||||
@@ -473,8 +473,12 @@ static int config(struct vo *vo, uint32_t width, uint32_t height,
|
|||||||
|
|
||||||
ctx->num_buffers = 2;
|
ctx->num_buffers = 2;
|
||||||
|
|
||||||
for (i = 0; i < ctx->num_buffers; i++)
|
for (i = 0; i < ctx->num_buffers; i++) {
|
||||||
allocate_xvimage(vo, i);
|
if (!allocate_xvimage(vo, i)) {
|
||||||
|
MP_FATAL(vo, "could not allocate Xv image data\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
ctx->current_buf = 0;
|
ctx->current_buf = 0;
|
||||||
ctx->current_ip_buf = 0;
|
ctx->current_ip_buf = 0;
|
||||||
@@ -485,7 +489,7 @@ static int config(struct vo *vo, uint32_t width, uint32_t height,
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void allocate_xvimage(struct vo *vo, int foo)
|
static bool allocate_xvimage(struct vo *vo, int foo)
|
||||||
{
|
{
|
||||||
struct xvctx *ctx = vo->priv;
|
struct xvctx *ctx = vo->priv;
|
||||||
struct vo_x11_state *x11 = vo->x11;
|
struct vo_x11_state *x11 = vo->x11;
|
||||||
@@ -506,12 +510,16 @@ static void allocate_xvimage(struct vo *vo, int foo)
|
|||||||
ctx->xv_format, NULL,
|
ctx->xv_format, NULL,
|
||||||
aligned_w, ctx->image_height,
|
aligned_w, ctx->image_height,
|
||||||
&ctx->Shminfo[foo]);
|
&ctx->Shminfo[foo]);
|
||||||
|
if (!ctx->xvimage[foo])
|
||||||
|
return false;
|
||||||
|
|
||||||
ctx->Shminfo[foo].shmid = shmget(IPC_PRIVATE,
|
ctx->Shminfo[foo].shmid = shmget(IPC_PRIVATE,
|
||||||
ctx->xvimage[foo]->data_size,
|
ctx->xvimage[foo]->data_size,
|
||||||
IPC_CREAT | 0777);
|
IPC_CREAT | 0777);
|
||||||
ctx->Shminfo[foo].shmaddr = (char *) shmat(ctx->Shminfo[foo].shmid, 0,
|
ctx->Shminfo[foo].shmaddr = (char *) shmat(ctx->Shminfo[foo].shmid, 0,
|
||||||
0);
|
0);
|
||||||
|
if (ctx->Shminfo[foo].shmaddr == (void *)-1)
|
||||||
|
return false;
|
||||||
ctx->Shminfo[foo].readOnly = False;
|
ctx->Shminfo[foo].readOnly = False;
|
||||||
|
|
||||||
ctx->xvimage[foo]->data = ctx->Shminfo[foo].shmaddr;
|
ctx->xvimage[foo]->data = ctx->Shminfo[foo].shmaddr;
|
||||||
@@ -525,13 +533,17 @@ static void allocate_xvimage(struct vo *vo, int foo)
|
|||||||
(XvImage *) XvCreateImage(x11->display, ctx->xv_port,
|
(XvImage *) XvCreateImage(x11->display, ctx->xv_port,
|
||||||
ctx->xv_format, NULL, aligned_w,
|
ctx->xv_format, NULL, aligned_w,
|
||||||
ctx->image_height);
|
ctx->image_height);
|
||||||
|
if (!ctx->xvimage[foo])
|
||||||
|
return false;
|
||||||
ctx->xvimage[foo]->data = av_malloc(ctx->xvimage[foo]->data_size);
|
ctx->xvimage[foo]->data = av_malloc(ctx->xvimage[foo]->data_size);
|
||||||
|
if (!ctx->xvimage[foo]->data)
|
||||||
|
return false;
|
||||||
XSync(x11->display, False);
|
XSync(x11->display, False);
|
||||||
}
|
}
|
||||||
struct mp_image img = get_xv_buffer(vo, foo);
|
struct mp_image img = get_xv_buffer(vo, foo);
|
||||||
img.w = aligned_w;
|
img.w = aligned_w;
|
||||||
mp_image_clear(&img, 0, 0, img.w, img.h);
|
mp_image_clear(&img, 0, 0, img.w, img.h);
|
||||||
return;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void deallocate_xvimage(struct vo *vo, int foo)
|
static void deallocate_xvimage(struct vo *vo, int foo)
|
||||||
@@ -546,7 +558,13 @@ static void deallocate_xvimage(struct vo *vo, int foo)
|
|||||||
{
|
{
|
||||||
av_free(ctx->xvimage[foo]->data);
|
av_free(ctx->xvimage[foo]->data);
|
||||||
}
|
}
|
||||||
XFree(ctx->xvimage[foo]);
|
if (ctx->xvimage[foo])
|
||||||
|
XFree(ctx->xvimage[foo]);
|
||||||
|
|
||||||
|
ctx->xvimage[foo] = NULL;
|
||||||
|
#ifdef HAVE_SHM
|
||||||
|
ctx->Shminfo[foo] = (XShmSegmentInfo){0};
|
||||||
|
#endif
|
||||||
|
|
||||||
XSync(vo->x11->display, False);
|
XSync(vo->x11->display, False);
|
||||||
return;
|
return;
|
||||||
|
|||||||
+39
-24
@@ -313,6 +313,9 @@ static void pointer_handle_enter(void *data,
|
|||||||
wl->cursor.serial = serial;
|
wl->cursor.serial = serial;
|
||||||
wl->cursor.pointer = pointer;
|
wl->cursor.pointer = pointer;
|
||||||
|
|
||||||
|
/* Release the left button on pointer enter again
|
||||||
|
* because after moving the shell surface no release event is sent */
|
||||||
|
mp_input_put_key(wl->vo->input_ctx, MP_MOUSE_BTN0 | MP_KEY_STATE_UP);
|
||||||
show_cursor(wl);
|
show_cursor(wl);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -334,9 +337,11 @@ static void pointer_handle_motion(void *data,
|
|||||||
struct vo_wayland_state *wl = data;
|
struct vo_wayland_state *wl = data;
|
||||||
|
|
||||||
wl->cursor.pointer = pointer;
|
wl->cursor.pointer = pointer;
|
||||||
|
wl->window.surf_x = wl_fixed_to_int(sx_w);
|
||||||
|
wl->window.surf_y = wl_fixed_to_int(sy_w);
|
||||||
|
|
||||||
vo_mouse_movement(wl->vo, wl_fixed_to_int(sx_w),
|
vo_mouse_movement(wl->vo, wl->window.surf_x,
|
||||||
wl_fixed_to_int(sy_w));
|
wl->window.surf_y);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void pointer_handle_button(void *data,
|
static void pointer_handle_button(void *data,
|
||||||
@@ -351,6 +356,10 @@ static void pointer_handle_button(void *data,
|
|||||||
mp_input_put_key(wl->vo->input_ctx, MP_MOUSE_BTN0 + (button - BTN_LEFT) |
|
mp_input_put_key(wl->vo->input_ctx, MP_MOUSE_BTN0 + (button - BTN_LEFT) |
|
||||||
((state == WL_POINTER_BUTTON_STATE_PRESSED)
|
((state == WL_POINTER_BUTTON_STATE_PRESSED)
|
||||||
? MP_KEY_STATE_DOWN : MP_KEY_STATE_UP));
|
? MP_KEY_STATE_DOWN : MP_KEY_STATE_UP));
|
||||||
|
|
||||||
|
if (!mp_input_test_dragging(wl->vo->input_ctx, wl->window.surf_x, wl->window.surf_y) &&
|
||||||
|
(button == BTN_LEFT) && (state == WL_POINTER_BUTTON_STATE_PRESSED))
|
||||||
|
wl_shell_surface_move(wl->window.shell_surface, wl->input.seat, serial);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void pointer_handle_axis(void *data,
|
static void pointer_handle_axis(void *data,
|
||||||
@@ -538,32 +547,34 @@ static void shedule_resize(struct vo_wayland_state *wl,
|
|||||||
if (height < minimum_size)
|
if (height < minimum_size)
|
||||||
height = minimum_size;
|
height = minimum_size;
|
||||||
|
|
||||||
/* if only the height is changed we have to calculate the width
|
// don't keep the aspect ration in fullscreen mode, because the compositor
|
||||||
* in any other case we calculate the height */
|
// shows the desktop in the border regions if the video has not the same
|
||||||
switch (edges) {
|
// aspect ration as the screen
|
||||||
case WL_SHELL_SURFACE_RESIZE_TOP:
|
if (!wl->window.is_fullscreen) {
|
||||||
case WL_SHELL_SURFACE_RESIZE_BOTTOM:
|
/* if only the height is changed we have to calculate the width
|
||||||
width = wl->window.aspect * height;
|
* in any other case we calculate the height */
|
||||||
break;
|
switch (edges) {
|
||||||
case WL_SHELL_SURFACE_RESIZE_LEFT:
|
case WL_SHELL_SURFACE_RESIZE_TOP:
|
||||||
case WL_SHELL_SURFACE_RESIZE_RIGHT:
|
case WL_SHELL_SURFACE_RESIZE_BOTTOM:
|
||||||
case WL_SHELL_SURFACE_RESIZE_TOP_LEFT: // just a preference
|
|
||||||
case WL_SHELL_SURFACE_RESIZE_TOP_RIGHT:
|
|
||||||
case WL_SHELL_SURFACE_RESIZE_BOTTOM_LEFT:
|
|
||||||
case WL_SHELL_SURFACE_RESIZE_BOTTOM_RIGHT:
|
|
||||||
height = (1 / wl->window.aspect) * width;
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
if (wl->window.aspect < temp_aspect)
|
|
||||||
width = wl->window.aspect * height;
|
width = wl->window.aspect * height;
|
||||||
else
|
break;
|
||||||
|
case WL_SHELL_SURFACE_RESIZE_LEFT:
|
||||||
|
case WL_SHELL_SURFACE_RESIZE_RIGHT:
|
||||||
|
case WL_SHELL_SURFACE_RESIZE_TOP_LEFT: // just a preference
|
||||||
|
case WL_SHELL_SURFACE_RESIZE_TOP_RIGHT:
|
||||||
|
case WL_SHELL_SURFACE_RESIZE_BOTTOM_LEFT:
|
||||||
|
case WL_SHELL_SURFACE_RESIZE_BOTTOM_RIGHT:
|
||||||
height = (1 / wl->window.aspect) * width;
|
height = (1 / wl->window.aspect) * width;
|
||||||
break;
|
break;
|
||||||
|
default:
|
||||||
|
if (wl->window.aspect < temp_aspect)
|
||||||
|
width = wl->window.aspect * height;
|
||||||
|
else
|
||||||
|
height = (1 / wl->window.aspect) * width;
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
wl->vo->dwidth = width;
|
|
||||||
wl->vo->dheight = height;
|
|
||||||
|
|
||||||
if (edges & WL_SHELL_SURFACE_RESIZE_LEFT)
|
if (edges & WL_SHELL_SURFACE_RESIZE_LEFT)
|
||||||
x = wl->window.width - width;
|
x = wl->window.width - width;
|
||||||
else
|
else
|
||||||
@@ -579,6 +590,8 @@ static void shedule_resize(struct vo_wayland_state *wl,
|
|||||||
wl->window.sh_x = x;
|
wl->window.sh_x = x;
|
||||||
wl->window.sh_y = y;
|
wl->window.sh_y = y;
|
||||||
wl->window.events |= VO_EVENT_RESIZE;
|
wl->window.events |= VO_EVENT_RESIZE;
|
||||||
|
wl->vo->dwidth = width;
|
||||||
|
wl->vo->dheight = height;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -765,6 +778,7 @@ static void vo_wayland_fullscreen (struct vo *vo)
|
|||||||
|
|
||||||
if (vo->opts->fullscreen) {
|
if (vo->opts->fullscreen) {
|
||||||
MP_DBG(wl, "going fullscreen\n");
|
MP_DBG(wl, "going fullscreen\n");
|
||||||
|
wl->window.is_fullscreen = true;
|
||||||
wl->window.p_width = wl->window.width;
|
wl->window.p_width = wl->window.width;
|
||||||
wl->window.p_height = wl->window.height;
|
wl->window.p_height = wl->window.height;
|
||||||
wl_shell_surface_set_fullscreen(wl->window.shell_surface,
|
wl_shell_surface_set_fullscreen(wl->window.shell_surface,
|
||||||
@@ -774,6 +788,7 @@ static void vo_wayland_fullscreen (struct vo *vo)
|
|||||||
|
|
||||||
else {
|
else {
|
||||||
MP_DBG(wl, "leaving fullscreen\n");
|
MP_DBG(wl, "leaving fullscreen\n");
|
||||||
|
wl->window.is_fullscreen = false;
|
||||||
wl_shell_surface_set_toplevel(wl->window.shell_surface);
|
wl_shell_surface_set_toplevel(wl->window.shell_surface);
|
||||||
shedule_resize(wl, 0, wl->window.p_width, wl->window.p_height);
|
shedule_resize(wl, 0, wl->window.p_width, wl->window.p_height);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -70,7 +70,11 @@ struct vo_wayland_state {
|
|||||||
int32_t sh_y;
|
int32_t sh_y;
|
||||||
float aspect;
|
float aspect;
|
||||||
|
|
||||||
|
bool is_fullscreen; // don't keep aspect ratio in fullscreen mode
|
||||||
|
|
||||||
struct wl_surface *surface;
|
struct wl_surface *surface;
|
||||||
|
int32_t surf_x;
|
||||||
|
int32_t surf_y;
|
||||||
struct wl_shell_surface *shell_surface;
|
struct wl_shell_surface *shell_surface;
|
||||||
int events; /* mplayer events (VO_EVENT_RESIZE) */
|
int events; /* mplayer events (VO_EVENT_RESIZE) */
|
||||||
} window;
|
} window;
|
||||||
|
|||||||
@@ -605,7 +605,7 @@ static void vo_x11_decoration(struct vo *vo, int d)
|
|||||||
|
|
||||||
vo_MotifHints = XInternAtom(x11->display, "_MOTIF_WM_HINTS", 0);
|
vo_MotifHints = XInternAtom(x11->display, "_MOTIF_WM_HINTS", 0);
|
||||||
if (vo_MotifHints != None) {
|
if (vo_MotifHints != None) {
|
||||||
if (!d) {
|
if (!x11->got_motif_hints) {
|
||||||
MotifWmHints *mhints = NULL;
|
MotifWmHints *mhints = NULL;
|
||||||
|
|
||||||
XGetWindowProperty(x11->display, x11->window,
|
XGetWindowProperty(x11->display, x11->window,
|
||||||
@@ -620,6 +620,7 @@ static void vo_x11_decoration(struct vo *vo, int d)
|
|||||||
XFree(mhints);
|
XFree(mhints);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
x11->got_motif_hints = true;
|
||||||
|
|
||||||
memset(&vo_MotifWmHints, 0, sizeof(MotifWmHints));
|
memset(&vo_MotifWmHints, 0, sizeof(MotifWmHints));
|
||||||
vo_MotifWmHints.flags =
|
vo_MotifWmHints.flags =
|
||||||
@@ -667,7 +668,7 @@ void vo_x11_uninit(struct vo *vo)
|
|||||||
XFreeGC(vo->x11->display, x11->f_gc);
|
XFreeGC(vo->x11->display, x11->f_gc);
|
||||||
if (x11->vo_gc != None)
|
if (x11->vo_gc != None)
|
||||||
XFreeGC(vo->x11->display, x11->vo_gc);
|
XFreeGC(vo->x11->display, x11->vo_gc);
|
||||||
if (x11->window != None) {
|
if (x11->window != None && x11->window != x11->rootwin) {
|
||||||
XClearWindow(x11->display, x11->window);
|
XClearWindow(x11->display, x11->window);
|
||||||
XUnmapWindow(x11->display, x11->window);
|
XUnmapWindow(x11->display, x11->window);
|
||||||
|
|
||||||
@@ -1140,6 +1141,8 @@ void vo_x11_config_vo_window(struct vo *vo, XVisualInfo *vis, int x, int y,
|
|||||||
struct vo_x11_state *x11 = vo->x11;
|
struct vo_x11_state *x11 = vo->x11;
|
||||||
|
|
||||||
if (opts->WinID >= 0) {
|
if (opts->WinID >= 0) {
|
||||||
|
if (opts->WinID == 0)
|
||||||
|
x11->window = x11->rootwin;
|
||||||
XSelectInput(x11->display, opts->WinID, StructureNotifyMask);
|
XSelectInput(x11->display, opts->WinID, StructureNotifyMask);
|
||||||
vo_x11_update_geometry(vo);
|
vo_x11_update_geometry(vo);
|
||||||
x = x11->win_x; y = x11->win_y;
|
x = x11->win_x; y = x11->win_y;
|
||||||
@@ -1373,7 +1376,7 @@ static void vo_x11_update_geometry(struct vo *vo)
|
|||||||
unsigned w, h, dummy_uint;
|
unsigned w, h, dummy_uint;
|
||||||
int dummy_int;
|
int dummy_int;
|
||||||
Window dummy_win;
|
Window dummy_win;
|
||||||
Window win = vo->opts->WinID >= 0 ? vo->opts->WinID : x11->window;
|
Window win = vo->opts->WinID > 0 ? vo->opts->WinID : x11->window;
|
||||||
XGetGeometry(x11->display, win, &dummy_win, &dummy_int, &dummy_int,
|
XGetGeometry(x11->display, win, &dummy_win, &dummy_int, &dummy_int,
|
||||||
&w, &h, &dummy_int, &dummy_uint);
|
&w, &h, &dummy_int, &dummy_uint);
|
||||||
if (w <= INT_MAX && h <= INT_MAX) {
|
if (w <= INT_MAX && h <= INT_MAX) {
|
||||||
@@ -1498,7 +1501,7 @@ static void vo_x11_ontop(struct vo *vo)
|
|||||||
static void vo_x11_border(struct vo *vo)
|
static void vo_x11_border(struct vo *vo)
|
||||||
{
|
{
|
||||||
vo->opts->border = !vo->opts->border;
|
vo->opts->border = !vo->opts->border;
|
||||||
vo_x11_decoration(vo, vo->opts->border && !vo->x11->fs);
|
vo_x11_decoration(vo, vo->opts->border);
|
||||||
}
|
}
|
||||||
|
|
||||||
int vo_x11_control(struct vo *vo, int *events, int request, void *arg)
|
int vo_x11_control(struct vo *vo, int *events, int request, void *arg)
|
||||||
@@ -1543,7 +1546,7 @@ static void xscreensaver_heartbeat(struct vo_x11_state *x11)
|
|||||||
double time = mp_time_sec();
|
double time = mp_time_sec();
|
||||||
|
|
||||||
if (x11->display && x11->screensaver_off &&
|
if (x11->display && x11->screensaver_off &&
|
||||||
(time - x11->screensaver_time_last) > 30)
|
(time - x11->screensaver_time_last) >= 10)
|
||||||
{
|
{
|
||||||
x11->screensaver_time_last = time;
|
x11->screensaver_time_last = time;
|
||||||
|
|
||||||
|
|||||||
@@ -90,8 +90,10 @@ struct vo_x11_state {
|
|||||||
bool size_changed_during_fs;
|
bool size_changed_during_fs;
|
||||||
bool pos_changed_during_fs;
|
bool pos_changed_during_fs;
|
||||||
|
|
||||||
|
bool got_motif_hints;
|
||||||
unsigned int olddecor;
|
unsigned int olddecor;
|
||||||
unsigned int oldfuncs;
|
unsigned int oldfuncs;
|
||||||
|
|
||||||
XComposeStatus compose_status;
|
XComposeStatus compose_status;
|
||||||
|
|
||||||
/* XShm stuff */
|
/* XShm stuff */
|
||||||
|
|||||||
+2
-1
@@ -24,6 +24,7 @@
|
|||||||
|
|
||||||
#include "sws_utils.h"
|
#include "sws_utils.h"
|
||||||
|
|
||||||
|
#include "mpvcore/mp_common.h"
|
||||||
#include "video/mp_image.h"
|
#include "video/mp_image.h"
|
||||||
#include "video/img_format.h"
|
#include "video/img_format.h"
|
||||||
#include "fmt-conversion.h"
|
#include "fmt-conversion.h"
|
||||||
@@ -327,7 +328,7 @@ int mp_sws_set_vf_equalizer(struct mp_sws_context *sws, struct vf_seteq *eq)
|
|||||||
if (!strcmp(eq->item, "brightness"))
|
if (!strcmp(eq->item, "brightness"))
|
||||||
sws->brightness = ((eq->value << 16) + 50) / 100;
|
sws->brightness = ((eq->value << 16) + 50) / 100;
|
||||||
else if (!strcmp(eq->item, "contrast"))
|
else if (!strcmp(eq->item, "contrast"))
|
||||||
sws->contrast = (((eq->value + 100) << 16) + 50) / 100;
|
sws->contrast = MPMAX(1, (((eq->value + 100) << 16) + 50) / 100);
|
||||||
else if (!strcmp(eq->item, "saturation"))
|
else if (!strcmp(eq->item, "saturation"))
|
||||||
sws->saturation = (((eq->value + 100) << 16) + 50) / 100;
|
sws->saturation = (((eq->value + 100) << 16) + 50) / 100;
|
||||||
else
|
else
|
||||||
|
|||||||
Reference in new issue
Block a user