Merge pull request #4313 from hardening/dyn_res_update
disp: implement dynamic resolution for X11
This commit is contained in:
commit
71fd6f3116
@ -98,7 +98,6 @@ UINT disp_send_display_control_monitor_layout_pdu(DISP_CHANNEL_CALLBACK* callbac
|
||||
type = DISPLAY_CONTROL_PDU_TYPE_MONITOR_LAYOUT;
|
||||
|
||||
s = Stream_New(NULL, length);
|
||||
|
||||
if(!s)
|
||||
{
|
||||
WLog_ERR(TAG, "Stream_New failed!");
|
||||
@ -112,10 +111,9 @@ UINT disp_send_display_control_monitor_layout_pdu(DISP_CHANNEL_CALLBACK* callbac
|
||||
NumMonitors = disp->MaxNumMonitors;
|
||||
|
||||
Stream_Write_UINT32(s, MonitorLayoutSize); /* MonitorLayoutSize (4 bytes) */
|
||||
|
||||
Stream_Write_UINT32(s, NumMonitors); /* NumMonitors (4 bytes) */
|
||||
|
||||
//WLog_ERR(TAG, "NumMonitors: %"PRIu32"", NumMonitors);
|
||||
WLog_DBG(TAG, "disp_send_display_control_monitor_layout_pdu: NumMonitors=%"PRIu32"", NumMonitors);
|
||||
|
||||
for (index = 0; index < NumMonitors; index++)
|
||||
{
|
||||
@ -147,16 +145,11 @@ UINT disp_send_display_control_monitor_layout_pdu(DISP_CHANNEL_CALLBACK* callbac
|
||||
Stream_Write_UINT32(s, Monitors[index].DesktopScaleFactor); /* DesktopScaleFactor (4 bytes) */
|
||||
Stream_Write_UINT32(s, Monitors[index].DeviceScaleFactor); /* DeviceScaleFactor (4 bytes) */
|
||||
|
||||
#if 0
|
||||
WLog_DBG(TAG, "\t: Flags: 0x%08"PRIX32"", Monitors[index].Flags);
|
||||
WLog_DBG(TAG, "\t: Left: %"PRId32"", Monitors[index].Left);
|
||||
WLog_DBG(TAG, "\t: Top: %"PRId32"", Monitors[index].Top);
|
||||
WLog_DBG(TAG, "\t: Width: %"PRIu32"", Monitors[index].Width);
|
||||
WLog_DBG(TAG, "\t: Height: %"PRIu32"", Monitors[index].Height);
|
||||
WLog_DBG(TAG, "\t: PhysicalWidth: %"PRIu32"", Monitors[index].PhysicalWidth);
|
||||
WLog_DBG(TAG, "\t: PhysicalHeight: %"PRIu32"", Monitors[index].PhysicalHeight);
|
||||
WLog_DBG(TAG, "\t: Orientation: %"PRIu32"", Monitors[index].Orientation);
|
||||
#endif
|
||||
WLog_DBG(TAG, "\t%d : Flags: 0x%08"PRIX32" Left/Top: (%"PRId32",%"PRId32") W/H=%"PRIu32"x%"PRIu32")", index,
|
||||
Monitors[index].Flags, Monitors[index].Left, Monitors[index].Top, Monitors[index].Width,
|
||||
Monitors[index].Height);
|
||||
WLog_DBG(TAG, "\t PhysicalWidth: %"PRIu32" PhysicalHeight: %"PRIu32" Orientation: %"PRIu32"",
|
||||
Monitors[index].PhysicalWidth, Monitors[index].PhysicalHeight, Monitors[index].Orientation);
|
||||
}
|
||||
|
||||
Stream_SealLength(s);
|
||||
@ -364,11 +357,9 @@ UINT DVCPluginEntry(IDRDYNVC_ENTRY_POINTS* pEntryPoints)
|
||||
DispClientContext* context;
|
||||
|
||||
disp = (DISP_PLUGIN*) pEntryPoints->GetPlugin(pEntryPoints, "disp");
|
||||
|
||||
if (!disp)
|
||||
{
|
||||
disp = (DISP_PLUGIN*) calloc(1, sizeof(DISP_PLUGIN));
|
||||
|
||||
if (!disp)
|
||||
{
|
||||
WLog_ERR(TAG, "calloc failed!");
|
||||
@ -379,9 +370,11 @@ UINT DVCPluginEntry(IDRDYNVC_ENTRY_POINTS* pEntryPoints)
|
||||
disp->iface.Connected = NULL;
|
||||
disp->iface.Disconnected = NULL;
|
||||
disp->iface.Terminated = disp_plugin_terminated;
|
||||
disp->MaxNumMonitors = 16;
|
||||
disp->MaxMonitorAreaFactorA = 8192;
|
||||
disp->MaxMonitorAreaFactorB = 8192;
|
||||
|
||||
context = (DispClientContext*) calloc(1, sizeof(DispClientContext));
|
||||
|
||||
if (!context)
|
||||
{
|
||||
WLog_ERR(TAG, "calloc failed!");
|
||||
@ -390,15 +383,10 @@ UINT DVCPluginEntry(IDRDYNVC_ENTRY_POINTS* pEntryPoints)
|
||||
}
|
||||
|
||||
context->handle = (void*) disp;
|
||||
|
||||
context->SendMonitorLayout = disp_send_monitor_layout;
|
||||
|
||||
disp->iface.pInterface = (void*) context;
|
||||
|
||||
disp->MaxNumMonitors = 16;
|
||||
disp->MaxMonitorAreaFactorA = 8192;
|
||||
disp->MaxMonitorAreaFactorB = 8192;
|
||||
|
||||
error = pEntryPoints->RegisterPlugin(pEntryPoints, "disp", (IWTSPlugin*) disp);
|
||||
}
|
||||
else
|
||||
|
@ -44,6 +44,8 @@ set(${MODULE_PREFIX}_SRCS
|
||||
xf_cliprdr.h
|
||||
xf_monitor.c
|
||||
xf_monitor.h
|
||||
xf_disp.c
|
||||
xf_disp.h
|
||||
xf_graphics.c
|
||||
xf_graphics.h
|
||||
xf_keyboard.c
|
||||
|
@ -30,6 +30,8 @@
|
||||
#include "xf_tsmf.h"
|
||||
#include "xf_rail.h"
|
||||
#include "xf_cliprdr.h"
|
||||
#include "xf_disp.h"
|
||||
|
||||
|
||||
void xf_OnChannelConnectedEventHandler(rdpContext* context, ChannelConnectedEventArgs* e)
|
||||
{
|
||||
@ -63,6 +65,10 @@ void xf_OnChannelConnectedEventHandler(rdpContext* context, ChannelConnectedEven
|
||||
{
|
||||
xf_encomsp_init(xfc, (EncomspClientContext*) e->pInterface);
|
||||
}
|
||||
else if (strcmp(e->name, DISP_DVC_CHANNEL_NAME) == 0)
|
||||
{
|
||||
xf_disp_init(xfc, (DispClientContext*)e->pInterface);
|
||||
}
|
||||
}
|
||||
|
||||
void xf_OnChannelDisconnectedEventHandler(rdpContext* context, ChannelDisconnectedEventArgs* e)
|
||||
|
@ -28,6 +28,7 @@
|
||||
#include <freerdp/client/cliprdr.h>
|
||||
#include <freerdp/client/rdpgfx.h>
|
||||
#include <freerdp/client/encomsp.h>
|
||||
#include <freerdp/client/disp.h>
|
||||
|
||||
int xf_on_channel_connected(freerdp* instance, const char* name, void* pInterface);
|
||||
int xf_on_channel_disconnected(freerdp* instance, const char* name, void* pInterface);
|
||||
|
@ -94,6 +94,7 @@
|
||||
#include "xf_event.h"
|
||||
#include "xf_input.h"
|
||||
#include "xf_cliprdr.h"
|
||||
#include "xf_disp.h"
|
||||
#include "xf_monitor.h"
|
||||
#include "xf_graphics.h"
|
||||
#include "xf_keyboard.h"
|
||||
@ -222,8 +223,7 @@ void xf_draw_screen(xfContext* xfc, int x, int y, int w, int h)
|
||||
}
|
||||
|
||||
#endif
|
||||
XCopyArea(xfc->display, xfc->primary, xfc->window->handle, xfc->gc, x, y, w, h,
|
||||
x, y);
|
||||
XCopyArea(xfc->display, xfc->primary, xfc->window->handle, xfc->gc, x, y, w, h, x, y);
|
||||
}
|
||||
|
||||
static BOOL xf_desktop_resize(rdpContext* context)
|
||||
@ -259,8 +259,7 @@ static BOOL xf_desktop_resize(rdpContext* context)
|
||||
|
||||
if (!xfc->fullscreen)
|
||||
{
|
||||
xf_ResizeDesktopWindow(xfc, xfc->window, settings->DesktopWidth,
|
||||
settings->DesktopHeight);
|
||||
xf_ResizeDesktopWindow(xfc, xfc->window, settings->DesktopWidth, settings->DesktopHeight);
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -282,6 +281,9 @@ static BOOL xf_desktop_resize(rdpContext* context)
|
||||
xfc->window->height);
|
||||
}
|
||||
|
||||
if (xfc->xfDisp)
|
||||
xf_disp_resized(xfc->xfDisp);
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
@ -1269,6 +1271,12 @@ static BOOL xf_post_connect(freerdp* instance)
|
||||
if (!(xfc->clipboard = xf_clipboard_new(xfc)))
|
||||
return FALSE;
|
||||
|
||||
if (!(xfc->xfDisp = xf_disp_new(xfc)))
|
||||
{
|
||||
xf_clipboard_free(xfc->clipboard);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
EventArgsInit(&e, "xfreerdp");
|
||||
e.width = settings->DesktopWidth;
|
||||
e.height = settings->DesktopHeight;
|
||||
@ -1294,6 +1302,12 @@ static void xf_post_disconnect(freerdp* instance)
|
||||
xfc->clipboard = NULL;
|
||||
}
|
||||
|
||||
if (xfc->xfDisp)
|
||||
{
|
||||
xf_disp_free(xfc->xfDisp);
|
||||
xfc->xfDisp = NULL;
|
||||
}
|
||||
|
||||
xf_window_free(xfc);
|
||||
xf_keyboard_free(xfc);
|
||||
}
|
||||
@ -1452,6 +1466,7 @@ static void* xf_client_thread(void* param)
|
||||
HANDLE inputEvent = NULL;
|
||||
HANDLE inputThread = NULL;
|
||||
rdpSettings* settings;
|
||||
|
||||
exit_code = 0;
|
||||
instance = (freerdp*) param;
|
||||
context = instance->context;
|
||||
|
211
client/X11/xf_disp.c
Normal file
211
client/X11/xf_disp.c
Normal file
@ -0,0 +1,211 @@
|
||||
/**
|
||||
* FreeRDP: A Remote Desktop Protocol Implementation
|
||||
* X11 Display Control channel
|
||||
*
|
||||
* Copyright 2017 David Fort <contact@hardening-consulting.com>
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#include <X11/Xutil.h>
|
||||
|
||||
#ifdef WITH_XRANDR
|
||||
#include <X11/extensions/Xrandr.h>
|
||||
#include <X11/extensions/randr.h>
|
||||
#endif
|
||||
|
||||
#include "xf_disp.h"
|
||||
#include "xf_monitor.h"
|
||||
|
||||
|
||||
#define TAG CLIENT_TAG("x11disp")
|
||||
|
||||
struct _xfDispContext
|
||||
{
|
||||
xfContext *xfc;
|
||||
BOOL haveXRandr;
|
||||
int eventBase, errorBase;
|
||||
int lastWidth, lastHeight;
|
||||
BOOL activated;
|
||||
BOOL waitingResize;
|
||||
};
|
||||
|
||||
xfDispContext *xf_disp_new(xfContext* xfc)
|
||||
{
|
||||
xfDispContext *ret = calloc(1, sizeof(xfDispContext));
|
||||
if (!ret)
|
||||
return NULL;
|
||||
|
||||
ret->xfc = xfc;
|
||||
#ifdef WITH_XRANDR
|
||||
if (XRRQueryExtension(xfc->display, &ret->eventBase, &ret->errorBase))
|
||||
{
|
||||
ret->haveXRandr = TRUE;
|
||||
}
|
||||
#endif
|
||||
ret->lastWidth = xfc->context.settings->DesktopWidth;
|
||||
ret->lastHeight = xfc->context.settings->DesktopHeight;
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
void xf_disp_free(xfDispContext *disp)
|
||||
{
|
||||
free(disp);
|
||||
}
|
||||
|
||||
static UINT xf_disp_sendLayout(DispClientContext *disp, rdpMonitor *monitors, int nmonitors)
|
||||
{
|
||||
UINT ret = CHANNEL_RC_OK;
|
||||
DISPLAY_CONTROL_MONITOR_LAYOUT *layouts;
|
||||
int i;
|
||||
|
||||
layouts = calloc(nmonitors, sizeof(DISPLAY_CONTROL_MONITOR_LAYOUT));
|
||||
if (!layouts)
|
||||
return CHANNEL_RC_NO_MEMORY;
|
||||
|
||||
for (i = 0; i < nmonitors; i++)
|
||||
{
|
||||
layouts[i].Flags = (monitors[i].is_primary ? DISPLAY_CONTROL_MONITOR_PRIMARY : 0);
|
||||
layouts[i].Left = monitors[i].x;
|
||||
layouts[i].Top = monitors[i].y;
|
||||
layouts[i].Width = monitors[i].width;
|
||||
layouts[i].Height = monitors[i].height;
|
||||
layouts[i].Orientation = ORIENTATION_LANDSCAPE;
|
||||
layouts[i].PhysicalWidth = monitors[i].width;
|
||||
layouts[i].PhysicalHeight = monitors[i].height;
|
||||
layouts[i].DesktopScaleFactor = 100;
|
||||
layouts[i].DeviceScaleFactor = 100;
|
||||
|
||||
}
|
||||
|
||||
ret = disp->SendMonitorLayout(disp, nmonitors, layouts);
|
||||
|
||||
free(layouts);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
BOOL xf_disp_handle_xevent(xfContext *xfc, XEvent *event)
|
||||
{
|
||||
xfDispContext *xfDisp = xfc->xfDisp;
|
||||
rdpSettings *settings = xfc->context.settings;
|
||||
UINT32 maxWidth, maxHeight;
|
||||
|
||||
if (!xfDisp->haveXRandr)
|
||||
return TRUE;
|
||||
|
||||
#ifdef WITH_XRANDR
|
||||
if (event->type != xfDisp->eventBase + RRScreenChangeNotify)
|
||||
return TRUE;
|
||||
#endif
|
||||
|
||||
xf_detect_monitors(xfc, &maxWidth, &maxHeight);
|
||||
return xf_disp_sendLayout(xfc->disp, settings->MonitorDefArray, settings->MonitorCount) == CHANNEL_RC_OK;
|
||||
}
|
||||
|
||||
BOOL xf_disp_handle_resize(xfContext *xfc, int width, int height)
|
||||
{
|
||||
DISPLAY_CONTROL_MONITOR_LAYOUT layout;
|
||||
xfDispContext *xfDisp = xfc->xfDisp;
|
||||
|
||||
if (xfDisp->lastWidth == width && xfDisp->lastHeight == height)
|
||||
return TRUE;
|
||||
|
||||
if (xfDisp->waitingResize || !xfDisp->activated)
|
||||
return TRUE;
|
||||
|
||||
xfDisp->lastWidth = width;
|
||||
xfDisp->lastHeight = height;
|
||||
xfDisp->waitingResize = TRUE;
|
||||
|
||||
layout.Flags = DISPLAY_CONTROL_MONITOR_PRIMARY;
|
||||
layout.Top = layout.Left = 0;
|
||||
layout.Width = width;
|
||||
layout.Height = height;
|
||||
layout.Orientation = ORIENTATION_LANDSCAPE;
|
||||
layout.DesktopScaleFactor = 100;
|
||||
layout.DeviceScaleFactor = 100;
|
||||
layout.PhysicalWidth = width;
|
||||
layout.PhysicalHeight = height;
|
||||
|
||||
return xfc->disp->SendMonitorLayout(xfc->disp, 1, &layout) == CHANNEL_RC_OK;
|
||||
}
|
||||
|
||||
BOOL xf_disp_set_window_resizable(xfDispContext *xfDisp)
|
||||
{
|
||||
XSizeHints *size_hints;
|
||||
|
||||
if (!(size_hints = XAllocSizeHints()))
|
||||
return FALSE;
|
||||
|
||||
size_hints->flags = PMinSize | PMaxSize | PWinGravity;
|
||||
size_hints->win_gravity = NorthWestGravity;
|
||||
size_hints->min_width = size_hints->min_height = 320;
|
||||
size_hints->max_width = size_hints->max_height = 8192;
|
||||
XSetWMNormalHints(xfDisp->xfc->display, xfDisp->xfc->window->handle, size_hints);
|
||||
XFree(size_hints);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
void xf_disp_resized(xfDispContext *xfDisp)
|
||||
{
|
||||
rdpSettings *settings = xfDisp->xfc->context.settings;
|
||||
|
||||
xfDisp->waitingResize = FALSE;
|
||||
|
||||
if (xfDisp->activated && !settings->Fullscreen)
|
||||
{
|
||||
xf_disp_set_window_resizable(xfDisp);
|
||||
}
|
||||
}
|
||||
|
||||
UINT xf_DisplayControlCaps(DispClientContext *disp, UINT32 maxNumMonitors, UINT32 maxMonitorAreaFactorA, UINT32 maxMonitorAreaFactorB)
|
||||
{
|
||||
/* we're called only if dynamic resolution update is activated */
|
||||
xfDispContext *xfDisp = (xfDispContext *)disp->custom;
|
||||
rdpSettings *settings = xfDisp->xfc->context.settings;
|
||||
|
||||
WLog_DBG(TAG, "DisplayControlCapsPdu: MaxNumMonitors: %"PRIu32" MaxMonitorAreaFactorA: %"PRIu32" MaxMonitorAreaFactorB: %"PRIu32"",
|
||||
maxNumMonitors, maxMonitorAreaFactorA, maxMonitorAreaFactorB);
|
||||
|
||||
xfDisp->activated = TRUE;
|
||||
|
||||
if (settings->Fullscreen)
|
||||
return CHANNEL_RC_OK;
|
||||
|
||||
WLog_DBG(TAG, "DisplayControlCapsPdu: setting the window as resizeable");
|
||||
return xf_disp_set_window_resizable(xfDisp) ? CHANNEL_RC_OK : CHANNEL_RC_NO_MEMORY;
|
||||
}
|
||||
|
||||
BOOL xf_disp_init(xfContext* xfc, DispClientContext *disp)
|
||||
{
|
||||
rdpSettings *settings = xfc->context.settings;
|
||||
xfc->disp = disp;
|
||||
disp->custom = (void*) xfc->xfDisp;
|
||||
|
||||
if (settings->DynamicResolutionUpdate)
|
||||
{
|
||||
disp->DisplayControlCaps = xf_DisplayControlCaps;
|
||||
#ifdef WITH_XRANDR
|
||||
if (settings->Fullscreen)
|
||||
{
|
||||
/* ask X11 to notify us of screen changes */
|
||||
XRRSelectInput(xfc->display, DefaultRootWindow(xfc->display), RRScreenChangeNotifyMask);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
38
client/X11/xf_disp.h
Normal file
38
client/X11/xf_disp.h
Normal file
@ -0,0 +1,38 @@
|
||||
/**
|
||||
* FreeRDP: A Remote Desktop Protocol Implementation
|
||||
* X11 Display Control channel
|
||||
*
|
||||
* Copyright 2017 David Fort <contact@hardening-consulting.com>
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
#ifndef FREERDP_CLIENT_X11_DISP_H
|
||||
#define FREERDP_CLIENT_X11_DISP_H
|
||||
|
||||
#include <freerdp/types.h>
|
||||
#include <freerdp/client/disp.h>
|
||||
|
||||
#include "xf_client.h"
|
||||
#include "xfreerdp.h"
|
||||
|
||||
typedef struct _xfDispContext xfDispContext;
|
||||
|
||||
FREERDP_API BOOL xf_disp_init(xfContext* xfc, DispClientContext *disp);
|
||||
|
||||
xfDispContext *xf_disp_new(xfContext* xfc);
|
||||
void xf_disp_free(xfDispContext *disp);
|
||||
BOOL xf_disp_handle_xevent(xfContext *xfc, XEvent *event);
|
||||
BOOL xf_disp_handle_resize(xfContext *xfc, int width, int height);
|
||||
void xf_disp_resized(xfDispContext *disp);
|
||||
|
||||
#endif /* FREERDP_CLIENT_X11_DISP_H */
|
@ -30,6 +30,7 @@
|
||||
#include "xf_rail.h"
|
||||
#include "xf_window.h"
|
||||
#include "xf_cliprdr.h"
|
||||
#include "xf_disp.h"
|
||||
#include "xf_input.h"
|
||||
#include "xf_gfx.h"
|
||||
|
||||
@ -664,6 +665,17 @@ static BOOL xf_event_ConfigureNotify(xfContext* xfc, XEvent* event, BOOL app)
|
||||
#endif
|
||||
}
|
||||
|
||||
if (settings->DynamicResolutionUpdate)
|
||||
{
|
||||
int alignedWidth, alignedHeight;
|
||||
|
||||
alignedWidth = (xfc->window->width / 2) * 2;
|
||||
alignedHeight = (xfc->window->height / 2) * 2;
|
||||
|
||||
/* ask the server to resize using the display channel */
|
||||
xf_disp_handle_resize(xfc, alignedWidth, alignedHeight);
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
@ -948,6 +960,7 @@ BOOL xf_event_process(freerdp* instance, XEvent* event)
|
||||
BOOL status = TRUE;
|
||||
xfAppWindow* appWindow;
|
||||
xfContext* xfc = (xfContext*) instance->context;
|
||||
rdpSettings *settings = xfc->context.settings;
|
||||
|
||||
if (xfc->remote_app)
|
||||
{
|
||||
@ -1047,11 +1060,17 @@ BOOL xf_event_process(freerdp* instance, XEvent* event)
|
||||
case PropertyNotify:
|
||||
status = xf_event_PropertyNotify(xfc, event, xfc->remote_app);
|
||||
break;
|
||||
|
||||
default:
|
||||
if (settings->SupportDisplayControl && xfc->xfDisp)
|
||||
xf_disp_handle_xevent(xfc, event);
|
||||
break;
|
||||
}
|
||||
|
||||
xf_cliprdr_handle_xevent(xfc, event);
|
||||
|
||||
xf_input_handle_event(xfc, event);
|
||||
|
||||
XSync(xfc->display, FALSE);
|
||||
return status;
|
||||
}
|
||||
|
@ -297,11 +297,10 @@ BOOL xf_detect_monitors(xfContext* xfc, UINT32* pMaxWidth, UINT32* pMaxHeight)
|
||||
|
||||
settings->MonitorDefArray[nmonitors].x = vscreen->monitors[i].area.left;
|
||||
settings->MonitorDefArray[nmonitors].y = vscreen->monitors[i].area.top;
|
||||
settings->MonitorDefArray[nmonitors].width = MIN(vscreen->monitors[i].area.right
|
||||
- vscreen->monitors[i].area.left + 1, *pMaxWidth);
|
||||
settings->MonitorDefArray[nmonitors].height = MIN(
|
||||
vscreen->monitors[i].area.bottom - vscreen->monitors[i].area.top + 1,
|
||||
*pMaxHeight);
|
||||
settings->MonitorDefArray[nmonitors].width =
|
||||
MIN(vscreen->monitors[i].area.right - vscreen->monitors[i].area.left + 1, *pMaxWidth);
|
||||
settings->MonitorDefArray[nmonitors].height =
|
||||
MIN(vscreen->monitors[i].area.bottom - vscreen->monitors[i].area.top + 1, *pMaxHeight);
|
||||
settings->MonitorDefArray[nmonitors].orig_screen = i;
|
||||
|
||||
if (i == settings->MonitorIds[0])
|
||||
|
@ -480,6 +480,7 @@ void xf_ResizeDesktopWindow(xfContext* xfc, xfWindow* window, int width,
|
||||
int height)
|
||||
{
|
||||
XSizeHints* size_hints;
|
||||
rdpSettings *settings = xfc->context.settings;
|
||||
|
||||
if (!xfc || !window)
|
||||
return;
|
||||
@ -493,13 +494,15 @@ void xf_ResizeDesktopWindow(xfContext* xfc, xfWindow* window, int width,
|
||||
size_hints->max_width = size_hints->max_height = 16384;
|
||||
XSetWMNormalHints(xfc->display, window->handle, size_hints);
|
||||
XResizeWindow(xfc->display, window->handle, width, height);
|
||||
#ifdef WITH_XRENDER
|
||||
|
||||
if (!xfc->context.settings->SmartSizing)
|
||||
#ifdef WITH_XRENDER
|
||||
if (!settings->SmartSizing)
|
||||
#endif
|
||||
{
|
||||
if (!xfc->fullscreen)
|
||||
{
|
||||
/* min == max is an hint for the WM to indicate that the window should
|
||||
* not be resizable */
|
||||
size_hints->min_width = size_hints->max_width = width;
|
||||
size_hints->min_height = size_hints->max_height = height;
|
||||
XSetWMNormalHints(xfc->display, window->handle, size_hints);
|
||||
|
@ -81,6 +81,7 @@ struct xf_glyph
|
||||
typedef struct xf_glyph xfGlyph;
|
||||
|
||||
typedef struct xf_clipboard xfClipboard;
|
||||
typedef struct _xfDispContext xfDispContext;
|
||||
|
||||
/* Value of the first logical button number in X11 which must be */
|
||||
/* subtracted to go from a button number in X11 to an index into */
|
||||
@ -171,9 +172,6 @@ struct xf_context
|
||||
BOOL complex_regions;
|
||||
VIRTUAL_SCREEN vscreen;
|
||||
void* xv_context;
|
||||
TsmfClientContext* tsmf;
|
||||
xfClipboard* clipboard;
|
||||
CliprdrClientContext* cliprdr;
|
||||
|
||||
Atom UTF8_STRING;
|
||||
|
||||
@ -209,9 +207,14 @@ struct xf_context
|
||||
Atom WM_DELETE_WINDOW;
|
||||
|
||||
/* Channels */
|
||||
TsmfClientContext* tsmf;
|
||||
xfClipboard* clipboard;
|
||||
CliprdrClientContext* cliprdr;
|
||||
RdpeiClientContext* rdpei;
|
||||
RdpgfxClientContext* gfx;
|
||||
EncomspClientContext* encomsp;
|
||||
xfDispContext *xfDisp;
|
||||
DispClientContext *disp;
|
||||
|
||||
RailClientContext* rail;
|
||||
wHashTable* railWindows;
|
||||
|
@ -88,6 +88,7 @@ static COMMAND_LINE_ARGUMENT_A args[] =
|
||||
{ "drive", COMMAND_LINE_VALUE_REQUIRED, "<name>,<path>", NULL, NULL, -1, NULL, "Redirect directory <path> as named share <name>" },
|
||||
{ "drives", COMMAND_LINE_VALUE_BOOL, NULL, BoolValueFalse, NULL, -1, NULL, "Redirect all mount points as shares" },
|
||||
{ "dvc", COMMAND_LINE_VALUE_REQUIRED, "<channel>[,<options>]", NULL, NULL, -1, NULL, "Dynamic virtual channel" },
|
||||
{ "dynamic-resolution", COMMAND_LINE_VALUE_FLAG, NULL, NULL, NULL, -1, NULL, "Send resolution updates when the window is resized" },
|
||||
{ "echo", COMMAND_LINE_VALUE_FLAG, NULL, NULL, NULL, -1, "echo", "Echo channel" },
|
||||
{ "encryption", COMMAND_LINE_VALUE_BOOL, NULL, BoolValueTrue, NULL, -1, NULL, "Encryption (experimental)" },
|
||||
{ "encryption-methods", COMMAND_LINE_VALUE_REQUIRED, "[40,][56,][128,][FIPS]", NULL, NULL, -1, NULL, "RDP standard security encryption methods" },
|
||||
@ -1752,8 +1753,24 @@ int freerdp_client_settings_parse_command_line_arguments(rdpSettings* settings,
|
||||
{
|
||||
settings->Decorations = arg->Value ? TRUE : FALSE;
|
||||
}
|
||||
CommandLineSwitchCase(arg, "dynamic-resolution")
|
||||
{
|
||||
if (settings->SmartSizing)
|
||||
{
|
||||
WLog_ERR(TAG, "Smart sizing and dynamic resolution are mutually exclusive options");
|
||||
return COMMAND_LINE_ERROR_UNEXPECTED_VALUE;
|
||||
}
|
||||
settings->SupportDisplayControl = TRUE;
|
||||
settings->DynamicResolutionUpdate = TRUE;
|
||||
}
|
||||
CommandLineSwitchCase(arg, "smart-sizing")
|
||||
{
|
||||
if (settings->DynamicResolutionUpdate)
|
||||
{
|
||||
WLog_ERR(TAG, "Smart sizing and dynamic resolution are mutually exclusive options");
|
||||
return COMMAND_LINE_ERROR_UNEXPECTED_VALUE;
|
||||
}
|
||||
|
||||
settings->SmartSizing = TRUE;
|
||||
|
||||
if (arg->Value)
|
||||
|
@ -1104,7 +1104,8 @@ struct rdp_settings
|
||||
ALIGN64 UINT32 SmartSizingHeight; /* 1555 */
|
||||
ALIGN64 BOOL PercentScreenUseWidth; /* 1556 */
|
||||
ALIGN64 BOOL PercentScreenUseHeight; /* 1557 */
|
||||
UINT64 padding1601[1601 - 1558]; /* 1558 */
|
||||
ALIGN64 BOOL DynamicResolutionUpdate; /* 1558 */
|
||||
UINT64 padding1601[1601 - 1559]; /* 1559 */
|
||||
|
||||
/* Miscellaneous */
|
||||
ALIGN64 BOOL SoftwareGdi; /* 1601 */
|
||||
|
Loading…
Reference in New Issue
Block a user