[vlc-devel] [PATCH 4/4] win32: Send fullscreen to specific monitor

Steve Lhomme robux4 at ycbcr.xyz
Thu Oct 24 15:11:36 CEST 2019


On 2019-10-24 15:01, Gabriel Luci wrote:
> I think this depends on what value is going to be in whatever setting we 
> end up deciding to use. If we store the device name (like 
> "\\.\DISPLAY2"), then you have to enumerate the displays to figure out 
> which one has that name, since there isn't any GetMonitorByName 
> function. But once you find it, you already have the MONITORINFOEX 
> struct that you need to go fullscreen. That's why I did what I did.
> 
> If you want to use the SetFullscreenOnMonitor, then the enumeration 
> would have to pass back just the handle to the monitor 
> and SetFullscreenOnMonitor would have to use the handle to go find the 
> monitor info again.

I guess you could pass the MONITORINFOEX to SetFullscreenOnMonitor then. 
We should read it in the current code as well.

> To Alexandre's point about switching monitors: This is a bug that exists 
> in VLC 3 too. I'm just testing this now in the current v4 code, and I 
> don't see any message at all sent to WinVoutEventProc when using 
> Win+Shift+Arrow. I would have expected to see WM_MOVE and figured we 
> could just check if we're in fullscreen mode and resize to the new 
> monitor. But as it is, I don't see VLC being notified at all that the 
> window moved. Any idea why?

This is weird and unexpected. Did you log all the messages received at 
the beginning of WinVoutEventProc() ? You may also check with Spy++ (or 
Spy32++?)

> If you move from a larger resolution monitor to a smaller one, you see 
> WM_SIZE because Windows resizes the window to the new display, but minus 
> the taskbar. But you see no notifications at all if you move from a 
> smaller monitor to a larger one.
> 
> On Thu, Oct 24, 2019 at 7:32 AM Steve Lhomme <robux4 at ycbcr.xyz 
> <mailto:robux4 at ycbcr.xyz>> wrote:
> 
>     Here's a patch that allows going fullscreen on a given HMONITOR. Thats'
>     what this patch should use in the end and the logo+shift+arrow patch.
> 
>     On 2019-10-24 13:17, Steve Lhomme wrote:
>      > On 2019-10-24 13:14, Steve Lhomme wrote:
>      >> On 2019-10-24 12:21, Alexandre Janniaux wrote:
>      >>> When in fullscreen, the window can be moved to another
>      >>> screen by using logo+shift+arrow key. When doing so on
>      >>> screens which are not the same size, the window is not
>      >>> resized and keep the size from the former screen. It should
>      >>> probably keep the resize state somewhere and resize
>      >>> adequatly while using vout_window_ReportSize() so that
>      >>> video outputs can be resized too.
>      >>>
>      >>> I don't know if you want to add this to your patch too, as
>      >>> the behaviour is already present without yours, but maybe
>      >>> Windows dev here can provide advice for this?
>      >>
>      >> I should be able to fix it. We probably need to handle the WM_MOVE
>      >> and, when in fullscreen, adapt the size of the window if the
>     monitor
>      >> changed.
>      >>
>      >> It's probably better to apply a fix after this change as it would
>      >> impact how we apply the fullscreen based on the selected
>     monitor. In
>      >> this case it wouldn't come the core anymore but from the local
>      >> detection of the monitor. That means the monitor from the core
>     should
>      >> return just a
>      >
>      > the monitor *selection* (based on the screen from the core)
>      >
>      >> HMONITOR, which is always what we'll use when we use the one
>     forced by
>      >> the OS.
>      >>
>      >>> PS: just for giving context, I used your patch in a VR demo
>      >>> so as to force a VR sidebyside output to the HMD screen and
>      >>> a classic 360° pano output to the main screen.
>      >>>
>      >>> On Sat, Oct 12, 2019 at 11:58:31PM -0400, Gabriel Luci wrote:
>      >>>> This reads the id parameter as the name of the monitor that
>     should be
>      >>>> used. If anything goes wrong, it will fall back to the monitor the
>      >>>> window is already on (which is what it always did before).
>      >>>>
>      >>>> ---
>      >>>>   modules/video_output/win32/window.c | 72
>      >>>> +++++++++++++++++++++++++++++++++----
>      >>>>   1 file changed, 65 insertions(+), 7 deletions(-)
>      >>>>
>      >>>> diff --git a/modules/video_output/win32/window.c
>      >>>> b/modules/video_output/win32/window.c
>      >>>> index 50e172b9b4..eefaed256e 100644
>      >>>> --- a/modules/video_output/win32/window.c
>      >>>> +++ b/modules/video_output/win32/window.c
>      >>>> @@ -37,6 +37,7 @@
>      >>>>   #include <vlc_actions.h>
>      >>>>
>      >>>>   #include
>     <shellapi.h>                                         /*
>      >>>> ExtractIcon */
>      >>>> +#include <vlc_charset.h>                                      /*
>      >>>> FromWide */
>      >>>>
>      >>>>   #define RECTWidth(r)   (LONG)((r).right - (r).left)
>      >>>>   #define RECTHeight(r)  (LONG)((r).bottom - (r).top)
>      >>>> @@ -153,9 +154,37 @@ static void SetTitle(vout_window_t *wnd,
>     const
>      >>>> char *title)
>      >>>>       PostMessage( sys->hwnd, WM_VLC_CHANGE_TEXT, 0, 0 );
>      >>>>   }
>      >>>>
>      >>>> +typedef struct enum_monitors_callback_params_t {
>      >>>> +    bool is_monitor_found;
>      >>>> +    const char *psz_name_to_find;
>      >>>> +    MONITORINFOEX *found_monitor_info;
>      >>>> +} enum_monitors_callback_params_t;
>      >>>> +
>      >>>> +static BOOL CALLBACK EnumDisplayMonitorsCallback(HMONITOR
>     hMonitor,
>      >>>> HDC hdcMonitor, LPRECT lprcMonitor, LPARAM dwData)
>      >>>> +{
>      >>>> +    /* this is called for each active monitor */
>      >>>> +
>      >>>> +    VLC_UNUSED(hdcMonitor);
>      >>>> +    VLC_UNUSED(lprcMonitor);
>      >>>> +
>      >>>> +    MONITORINFOEX mi;
>      >>>> +    mi.cbSize = sizeof(MONITORINFOEX);
>      >>>> +    if (!GetMonitorInfo(hMonitor, (LPMONITORINFO) &mi))
>     return true;
>      >>>> +
>      >>>> +    enum_monitors_callback_params_t *params =
>      >>>> (enum_monitors_callback_params_t*) dwData;
>      >>>> +    char *psz_monitor_name = FromWide(mi.szDevice);
>      >>>> +    if (!strcmp(psz_monitor_name, params->psz_name_to_find))
>      >>>> +    {
>      >>>> +        /* the monitor name matches what we're looking for */
>      >>>> +        params->is_monitor_found = true;
>      >>>> +        params->found_monitor_info = &mi;
>      >>>> +    }
>      >>>> +    free(psz_monitor_name);
>      >>>> +    return !params->is_monitor_found;
>      >>>> +}
>      >>>> +
>      >>>>   static void SetFullscreen(vout_window_t *wnd, const char *id)
>      >>>>   {
>      >>>> -    VLC_UNUSED(id);
>      >>>>       msg_Dbg(wnd, "entering fullscreen mode");
>      >>>>       vout_window_sys_t *sys = wnd->sys;
>      >>>>
>      >>>> @@ -167,12 +196,41 @@ static void SetFullscreen(vout_window_t
>     *wnd,
>      >>>> const char *id)
>      >>>>       /* Change window style, no borders and no title bar */
>      >>>>       SetWindowLong(sys->hwnd, GWL_STYLE, WS_CLIPCHILDREN |
>      >>>> WS_VISIBLE);
>      >>>>
>      >>>> -    /* Retrieve current window position so fullscreen will happen
>      >>>> -     * on the right screen */
>      >>>> -    HMONITOR hmon = MonitorFromWindow(sys->hwnd,
>      >>>> MONITOR_DEFAULTTONEAREST);
>      >>>> -    MONITORINFO mi;
>      >>>> -    mi.cbSize = sizeof(MONITORINFO);
>      >>>> -    if (GetMonitorInfo(hmon, &mi))
>      >>>> +    /* Figure out which monitor we should be using */
>      >>>> +    MONITORINFOEX mi;
>      >>>> +    bool is_monitor_found = false;
>      >>>> +
>      >>>> +    if (id)
>      >>>> +    {
>      >>>> +        /* We're being told to use a specific monitor, so see
>     if we
>      >>>> can find an
>      >>>> +         * active monitor with the same name */
>      >>>> +        enum_monitors_callback_params_t params = {
>      >>>> +            .is_monitor_found = false,
>      >>>> +            .psz_name_to_find = id
>      >>>> +        };
>      >>>> +        EnumDisplayMonitors(NULL, NULL,
>      >>>> &EnumDisplayMonitorsCallback, (LPARAM) &params);
>      >>>> +
>      >>>> +        if (params.is_monitor_found)
>      >>>> +        {
>      >>>> +            is_monitor_found = true;
>      >>>> +            mi = *(params.found_monitor_info);
>      >>>> +        }
>      >>>> +        else
>      >>>> +        {
>      >>>> +            msg_Dbg(wnd, "display device with name \"%s\" was
>      >>>> requested, but no such device exists. Falling back to
>     primary", id);
>      >>>> +        }
>      >>>> +    }
>      >>>> +
>      >>>> +    if (!is_monitor_found)
>      >>>> +    {
>      >>>> +        /* fall back to using the screen the window is currently
>      >>>> mostly on */
>      >>>> +        HMONITOR hmon;
>      >>>> +        hmon = MonitorFromWindow(sys->hwnd,
>     MONITOR_DEFAULTTONEAREST);
>      >>>> +        mi.cbSize = sizeof(MONITORINFOEX);
>      >>>> +        is_monitor_found = GetMonitorInfo(hmon,
>     (LPMONITORINFO) &mi);
>      >>>> +    }
>      >>>> +
>      >>>> +    if (is_monitor_found)
>      >>>>           SetWindowPos(sys->hwnd, 0,
>      >>>>                        mi.rcMonitor.left,
>      >>>>                        mi.rcMonitor.top,
>      >>>> --
>      >>>> 2.11.0
>      >>>>
>      >>>> _______________________________________________
>      >>>> vlc-devel mailing list
>      >>>> To unsubscribe or modify your subscription options:
>      >>>> https://mailman.videolan.org/listinfo/vlc-devel
>      >>> _______________________________________________
>      >>> vlc-devel mailing list
>      >>> To unsubscribe or modify your subscription options:
>      >>> https://mailman.videolan.org/listinfo/vlc-devel
>      >>>
>      >> _______________________________________________
>      >> vlc-devel mailing list
>      >> To unsubscribe or modify your subscription options:
>      >> https://mailman.videolan.org/listinfo/vlc-devel
>      > _______________________________________________
>      > vlc-devel mailing list
>      > To unsubscribe or modify your subscription options:
>      > https://mailman.videolan.org/listinfo/vlc-devel
>     _______________________________________________
>     vlc-devel mailing list
>     To unsubscribe or modify your subscription options:
>     https://mailman.videolan.org/listinfo/vlc-devel
> 
> 
> _______________________________________________
> vlc-devel mailing list
> To unsubscribe or modify your subscription options:
> https://mailman.videolan.org/listinfo/vlc-devel
> 


More information about the vlc-devel mailing list