[win32 surface sharing] win32 surface sharing using window reparenting
This commit is contained in:
parent
731e5b1ae8
commit
653ddec978
|
@ -2,7 +2,7 @@
|
||||||
*
|
*
|
||||||
* file: glsl_shaders.h
|
* file: glsl_shaders.h
|
||||||
* note: string literals auto-generated by embed_text.py
|
* note: string literals auto-generated by embed_text.py
|
||||||
* date: 02/032023
|
* date: 03/032023
|
||||||
*
|
*
|
||||||
**********************************************************************/
|
**********************************************************************/
|
||||||
#ifndef __GLSL_SHADERS_H__
|
#ifndef __GLSL_SHADERS_H__
|
||||||
|
|
|
@ -496,6 +496,8 @@ mg_surface mg_surface_create_host(mp_window window)
|
||||||
mg_surface_data* surface = 0;
|
mg_surface_data* surface = 0;
|
||||||
#if OS_MACOS
|
#if OS_MACOS
|
||||||
surface = mg_osx_surface_create_host(window);
|
surface = mg_osx_surface_create_host(window);
|
||||||
|
#elif OS_WIN64
|
||||||
|
surface = mg_win32_surface_create_host(window);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
if(surface)
|
if(surface)
|
||||||
|
|
|
@ -22,7 +22,7 @@ typedef enum {
|
||||||
MG_BACKEND_METAL,
|
MG_BACKEND_METAL,
|
||||||
MG_BACKEND_GL,
|
MG_BACKEND_GL,
|
||||||
MG_BACKEND_GLES,
|
MG_BACKEND_GLES,
|
||||||
MG_BACKEND_REMOTE } mg_backend_id;
|
MG_BACKEND_HOST } mg_backend_id;
|
||||||
|
|
||||||
//NOTE: these macros are used to select which backend to include when building milepost
|
//NOTE: these macros are used to select which backend to include when building milepost
|
||||||
// they can be overridden by passing them to the compiler command line
|
// they can be overridden by passing them to the compiler command line
|
||||||
|
|
|
@ -68,8 +68,6 @@
|
||||||
#include"egl_surface.c"
|
#include"egl_surface.c"
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#include"win32_surface_sharing.c"
|
|
||||||
|
|
||||||
#elif defined(OS_MACOS)
|
#elif defined(OS_MACOS)
|
||||||
//NOTE: macos application layer and graphics backends are defined in milepost.m
|
//NOTE: macos application layer and graphics backends are defined in milepost.m
|
||||||
#else
|
#else
|
||||||
|
|
|
@ -1832,6 +1832,7 @@ void mg_osx_surface_host_connect(mg_surface_data* surface, mg_surface_id remoteI
|
||||||
void mg_surface_init_host(mg_surface_data* surface, mp_window_data* window)
|
void mg_surface_init_host(mg_surface_data* surface, mp_window_data* window)
|
||||||
{@autoreleasepool{
|
{@autoreleasepool{
|
||||||
|
|
||||||
|
surface->backend = MG_BACKEND_HOST;
|
||||||
surface->nativeLayer = mg_osx_surface_native_layer;
|
surface->nativeLayer = mg_osx_surface_native_layer;
|
||||||
surface->contentsScaling = mg_osx_surface_contents_scaling;
|
surface->contentsScaling = mg_osx_surface_contents_scaling;
|
||||||
surface->getFrame = mg_osx_surface_get_frame;
|
surface->getFrame = mg_osx_surface_get_frame;
|
||||||
|
|
|
@ -115,7 +115,6 @@ typedef struct mg_wgl_surface
|
||||||
{
|
{
|
||||||
mg_surface_data interface;
|
mg_surface_data interface;
|
||||||
|
|
||||||
mp_layer layer;
|
|
||||||
HDC hDC;
|
HDC hDC;
|
||||||
HGLRC glContext;
|
HGLRC glContext;
|
||||||
|
|
||||||
|
@ -134,7 +133,7 @@ void mg_wgl_surface_destroy(mg_surface_data* interface)
|
||||||
}
|
}
|
||||||
wglDeleteContext(surface->glContext);
|
wglDeleteContext(surface->glContext);
|
||||||
|
|
||||||
mp_layer_cleanup(&surface->layer);
|
mg_surface_cleanup(interface);
|
||||||
|
|
||||||
free(surface);
|
free(surface);
|
||||||
}
|
}
|
||||||
|
@ -159,42 +158,6 @@ void mg_wgl_surface_swap_interval(mg_surface_data* interface, int swap)
|
||||||
wglSwapIntervalEXT(swap);
|
wglSwapIntervalEXT(swap);
|
||||||
}
|
}
|
||||||
|
|
||||||
vec2 mg_wgl_surface_contents_scaling(mg_surface_data* interface)
|
|
||||||
{
|
|
||||||
mg_wgl_surface* surface = (mg_wgl_surface*)interface;
|
|
||||||
return(mp_layer_contents_scaling(&surface->layer));
|
|
||||||
}
|
|
||||||
|
|
||||||
mp_rect mg_wgl_surface_get_frame(mg_surface_data* interface)
|
|
||||||
{
|
|
||||||
mg_wgl_surface* surface = (mg_wgl_surface*)interface;
|
|
||||||
return(mp_layer_get_frame(&surface->layer));
|
|
||||||
}
|
|
||||||
|
|
||||||
void mg_wgl_surface_set_frame(mg_surface_data* interface, mp_rect frame)
|
|
||||||
{
|
|
||||||
mg_wgl_surface* surface = (mg_wgl_surface*)interface;
|
|
||||||
mp_layer_set_frame(&surface->layer, frame);
|
|
||||||
}
|
|
||||||
|
|
||||||
void mg_wgl_surface_set_hidden(mg_surface_data* interface, bool hidden)
|
|
||||||
{
|
|
||||||
mg_wgl_surface* surface = (mg_wgl_surface*)interface;
|
|
||||||
mp_layer_set_hidden(&surface->layer, hidden);
|
|
||||||
}
|
|
||||||
|
|
||||||
bool mg_wgl_surface_get_hidden(mg_surface_data* interface)
|
|
||||||
{
|
|
||||||
mg_wgl_surface* surface = (mg_wgl_surface*)interface;
|
|
||||||
return(mp_layer_get_hidden(&surface->layer));
|
|
||||||
}
|
|
||||||
|
|
||||||
void* mg_wgl_surface_native_layer(mg_surface_data* interface)
|
|
||||||
{
|
|
||||||
mg_wgl_surface* surface = (mg_wgl_surface*)interface;
|
|
||||||
return(mp_layer_native_surface(&surface->layer));
|
|
||||||
}
|
|
||||||
|
|
||||||
void* mg_wgl_get_proc(const char* name)
|
void* mg_wgl_get_proc(const char* name)
|
||||||
{
|
{
|
||||||
void* p = wglGetProcAddress(name);
|
void* p = wglGetProcAddress(name);
|
||||||
|
@ -224,19 +187,15 @@ mg_surface_data* mg_wgl_surface_create_for_window(mp_window window)
|
||||||
mg_wgl_surface* surface = malloc_type(mg_wgl_surface);
|
mg_wgl_surface* surface = malloc_type(mg_wgl_surface);
|
||||||
if(surface)
|
if(surface)
|
||||||
{
|
{
|
||||||
|
mg_surface_init_for_window((mg_surface_data*)surface, windowData);
|
||||||
|
|
||||||
surface->interface.backend = MG_BACKEND_GL;
|
surface->interface.backend = MG_BACKEND_GL;
|
||||||
surface->interface.destroy = mg_wgl_surface_destroy;
|
surface->interface.destroy = mg_wgl_surface_destroy;
|
||||||
surface->interface.prepare = mg_wgl_surface_prepare;
|
surface->interface.prepare = mg_wgl_surface_prepare;
|
||||||
surface->interface.present = mg_wgl_surface_present;
|
surface->interface.present = mg_wgl_surface_present;
|
||||||
surface->interface.swapInterval = mg_wgl_surface_swap_interval;
|
surface->interface.swapInterval = mg_wgl_surface_swap_interval;
|
||||||
surface->interface.contentsScaling = mg_wgl_surface_contents_scaling;
|
|
||||||
surface->interface.getFrame = mg_wgl_surface_get_frame;
|
|
||||||
surface->interface.setFrame = mg_wgl_surface_set_frame;
|
|
||||||
surface->interface.getHidden = mg_wgl_surface_get_hidden;
|
|
||||||
surface->interface.setHidden = mg_wgl_surface_set_hidden;
|
|
||||||
|
|
||||||
mp_layer_init_for_window(&surface->layer, windowData);
|
surface->hDC = GetDC(surface->interface.layer.hWnd);
|
||||||
surface->hDC = GetDC(surface->layer.hWnd);
|
|
||||||
|
|
||||||
//NOTE(martin): create the pixel format and gl context
|
//NOTE(martin): create the pixel format and gl context
|
||||||
PIXELFORMATDESCRIPTOR pixelFormatDesc =
|
PIXELFORMATDESCRIPTOR pixelFormatDesc =
|
||||||
|
|
189
src/win32_app.c
189
src/win32_app.c
|
@ -777,10 +777,107 @@ mp_rect mp_window_get_content_rect(mp_window window)
|
||||||
return(rect);
|
return(rect);
|
||||||
}
|
}
|
||||||
|
|
||||||
///////////////////////////////////////////
|
//--------------------------------------------------------------------------------
|
||||||
|
// win32 surfaces
|
||||||
|
//--------------------------------------------------------------------------------
|
||||||
|
|
||||||
void mp_layer_init_for_window(mp_layer* layer, mp_window_data* window)
|
#include"graphics_internal.h"
|
||||||
|
|
||||||
|
vec2 mg_win32_surface_contents_scaling(mg_surface_data* surface)
|
||||||
{
|
{
|
||||||
|
u32 dpi = GetDpiForWindow(surface->layer.hWnd);
|
||||||
|
vec2 contentsScaling = (vec2){(float)dpi/96., (float)dpi/96.};
|
||||||
|
return(contentsScaling);
|
||||||
|
}
|
||||||
|
|
||||||
|
mp_rect mg_win32_surface_get_frame(mg_surface_data* surface)
|
||||||
|
{
|
||||||
|
RECT rect = {0};
|
||||||
|
GetClientRect(surface->layer.hWnd, &rect);
|
||||||
|
|
||||||
|
vec2 scale = mg_win32_surface_contents_scaling(surface);
|
||||||
|
|
||||||
|
mp_rect res = {rect.left/scale.x,
|
||||||
|
rect.bottom/scale.y,
|
||||||
|
(rect.right - rect.left)/scale.x,
|
||||||
|
(rect.bottom - rect.top)/scale.y};
|
||||||
|
return(res);
|
||||||
|
}
|
||||||
|
|
||||||
|
void mg_win32_surface_set_frame(mg_surface_data* surface, mp_rect frame)
|
||||||
|
{
|
||||||
|
HWND parent = GetParent(surface->layer.hWnd);
|
||||||
|
RECT parentContentRect;
|
||||||
|
|
||||||
|
GetClientRect(parent, &parentContentRect);
|
||||||
|
int parentHeight = parentContentRect.bottom - parentContentRect.top;
|
||||||
|
|
||||||
|
vec2 scale = mg_win32_surface_contents_scaling(surface);
|
||||||
|
|
||||||
|
SetWindowPos(surface->layer.hWnd,
|
||||||
|
HWND_TOP,
|
||||||
|
frame.x * scale.x,
|
||||||
|
parentHeight - (frame.y + frame.h) * scale.y,
|
||||||
|
frame.w * scale.x,
|
||||||
|
frame.h * scale.y,
|
||||||
|
SWP_NOACTIVATE | SWP_NOZORDER);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool mg_win32_surface_get_hidden(mg_surface_data* surface)
|
||||||
|
{
|
||||||
|
bool hidden = !IsWindowVisible(surface->layer.hWnd);
|
||||||
|
return(hidden);
|
||||||
|
}
|
||||||
|
|
||||||
|
void mg_win32_surface_set_hidden(mg_surface_data* surface, bool hidden)
|
||||||
|
{
|
||||||
|
ShowWindow(surface->layer.hWnd, hidden ? SW_HIDE : SW_NORMAL);
|
||||||
|
}
|
||||||
|
|
||||||
|
void* mg_win32_surface_native_layer(mg_surface_data* surface)
|
||||||
|
{
|
||||||
|
return((void*)surface->layer.hWnd);
|
||||||
|
}
|
||||||
|
|
||||||
|
mg_surface_id mg_win32_surface_remote_id(mg_surface_data* surface)
|
||||||
|
{
|
||||||
|
return((mg_surface_id)surface->layer.hWnd);
|
||||||
|
}
|
||||||
|
|
||||||
|
void mg_win32_surface_host_connect(mg_surface_data* surface, mg_surface_id remoteID)
|
||||||
|
{
|
||||||
|
HWND dstWnd = surface->layer.hWnd;
|
||||||
|
HWND srcWnd = (HWND)remoteID;
|
||||||
|
|
||||||
|
RECT dstRect;
|
||||||
|
GetClientRect(dstWnd, &dstRect);
|
||||||
|
|
||||||
|
SetParent(srcWnd, dstWnd);
|
||||||
|
ShowWindow(srcWnd, SW_NORMAL);
|
||||||
|
|
||||||
|
SetWindowPos(srcWnd,
|
||||||
|
HWND_TOP,
|
||||||
|
0,
|
||||||
|
0,
|
||||||
|
dstRect.right - dstRect.left,
|
||||||
|
dstRect.bottom - dstRect.top,
|
||||||
|
SWP_NOACTIVATE | SWP_NOZORDER);
|
||||||
|
}
|
||||||
|
|
||||||
|
void mg_surface_cleanup(mg_surface_data* surface)
|
||||||
|
{
|
||||||
|
DestroyWindow(surface->layer.hWnd);
|
||||||
|
}
|
||||||
|
|
||||||
|
void mg_surface_init_for_window(mg_surface_data* surface, mp_window_data* window)
|
||||||
|
{
|
||||||
|
surface->contentsScaling = mg_win32_surface_contents_scaling;
|
||||||
|
surface->getFrame = mg_win32_surface_get_frame;
|
||||||
|
surface->setFrame = mg_win32_surface_set_frame;
|
||||||
|
surface->getHidden = mg_win32_surface_get_hidden;
|
||||||
|
surface->setHidden = mg_win32_surface_set_hidden;
|
||||||
|
surface->nativeLayer = mg_win32_surface_native_layer;
|
||||||
|
|
||||||
//NOTE(martin): create a child window for the surface
|
//NOTE(martin): create a child window for the surface
|
||||||
WNDCLASS layerWindowClass = {.style = CS_HREDRAW | CS_VREDRAW | CS_OWNDC,
|
WNDCLASS layerWindowClass = {.style = CS_HREDRAW | CS_VREDRAW | CS_OWNDC,
|
||||||
.lpfnWndProc = DefWindowProc,
|
.lpfnWndProc = DefWindowProc,
|
||||||
|
@ -795,7 +892,7 @@ void mp_layer_init_for_window(mp_layer* layer, mp_window_data* window)
|
||||||
int width = parentRect.right - parentRect.left;
|
int width = parentRect.right - parentRect.left;
|
||||||
int height = parentRect.bottom - parentRect.top;
|
int height = parentRect.bottom - parentRect.top;
|
||||||
|
|
||||||
layer->hWnd = CreateWindow("layer_window_class", "layer",
|
surface->layer.hWnd = CreateWindow("layer_window_class", "layer",
|
||||||
WS_CHILD | WS_VISIBLE,
|
WS_CHILD | WS_VISIBLE,
|
||||||
0, 0, width, height,
|
0, 0, width, height,
|
||||||
window->win32.hWnd,
|
window->win32.hWnd,
|
||||||
|
@ -804,8 +901,16 @@ void mp_layer_init_for_window(mp_layer* layer, mp_window_data* window)
|
||||||
0);
|
0);
|
||||||
}
|
}
|
||||||
|
|
||||||
void mp_layer_init_for_sharing(mp_layer* layer, u32 width, u32 height)
|
void mg_surface_init_remote(mg_surface_data* surface, u32 width, u32 height)
|
||||||
{
|
{
|
||||||
|
surface->contentsScaling = mg_win32_surface_contents_scaling;
|
||||||
|
surface->getFrame = mg_win32_surface_get_frame;
|
||||||
|
surface->setFrame = mg_win32_surface_set_frame;
|
||||||
|
surface->getHidden = mg_win32_surface_get_hidden;
|
||||||
|
surface->setHidden = mg_win32_surface_set_hidden;
|
||||||
|
surface->nativeLayer = mg_win32_surface_native_layer;
|
||||||
|
surface->remoteID = mg_win32_surface_remote_id;
|
||||||
|
|
||||||
WNDCLASS layerWindowClass = {.style = CS_HREDRAW | CS_VREDRAW | CS_OWNDC,
|
WNDCLASS layerWindowClass = {.style = CS_HREDRAW | CS_VREDRAW | CS_OWNDC,
|
||||||
.lpfnWndProc = DefWindowProc,
|
.lpfnWndProc = DefWindowProc,
|
||||||
.hInstance = GetModuleHandleW(NULL),
|
.hInstance = GetModuleHandleW(NULL),
|
||||||
|
@ -826,7 +931,7 @@ void mp_layer_init_for_sharing(mp_layer* layer, u32 width, u32 height)
|
||||||
0);
|
0);
|
||||||
|
|
||||||
//NOTE: create the layer window
|
//NOTE: create the layer window
|
||||||
layer->hWnd = CreateWindowEx(WS_EX_NOACTIVATE,
|
surface->layer.hWnd = CreateWindowEx(WS_EX_NOACTIVATE,
|
||||||
"server_layer_window_class", "layer",
|
"server_layer_window_class", "layer",
|
||||||
WS_CHILD,
|
WS_CHILD,
|
||||||
0, 0, width, height,
|
0, 0, width, height,
|
||||||
|
@ -836,69 +941,27 @@ void mp_layer_init_for_sharing(mp_layer* layer, u32 width, u32 height)
|
||||||
0);
|
0);
|
||||||
|
|
||||||
//NOTE: unparent it and destroy tmp parent
|
//NOTE: unparent it and destroy tmp parent
|
||||||
SetParent(layer->hWnd, 0);
|
SetParent(surface->layer.hWnd, 0);
|
||||||
DestroyWindow(tmpParent);
|
DestroyWindow(tmpParent);
|
||||||
}
|
}
|
||||||
|
|
||||||
void mp_layer_cleanup(mp_layer* layer)
|
mg_surface_data* mg_win32_surface_create_host(mp_window window)
|
||||||
{
|
{
|
||||||
DestroyWindow(layer->hWnd);
|
mg_surface_data* surface = 0;
|
||||||
}
|
mp_window_data* windowData = mp_window_ptr_from_handle(window);
|
||||||
|
if(windowData)
|
||||||
|
{
|
||||||
|
surface = malloc_type(mg_surface_data);
|
||||||
|
if(surface)
|
||||||
|
{
|
||||||
|
memset(surface, 0, sizeof(mg_surface_data));
|
||||||
|
mg_surface_init_for_window(surface, windowData);
|
||||||
|
|
||||||
void* mp_layer_native_surface(mp_layer* layer)
|
surface->backend = MG_BACKEND_HOST;
|
||||||
{
|
surface->hostConnect = mg_win32_surface_host_connect;
|
||||||
return((void*)layer->hWnd);
|
}
|
||||||
}
|
}
|
||||||
|
return(surface);
|
||||||
vec2 mp_layer_contents_scaling(mp_layer* layer)
|
|
||||||
{
|
|
||||||
u32 dpi = GetDpiForWindow(layer->hWnd);
|
|
||||||
vec2 contentsScaling = (vec2){(float)dpi/96., (float)dpi/96.};
|
|
||||||
return(contentsScaling);
|
|
||||||
}
|
|
||||||
|
|
||||||
mp_rect mp_layer_get_frame(mp_layer* layer)
|
|
||||||
{
|
|
||||||
RECT rect = {0};
|
|
||||||
GetClientRect(layer->hWnd, &rect);
|
|
||||||
|
|
||||||
vec2 scale = mp_layer_contents_scaling(layer);
|
|
||||||
|
|
||||||
mp_rect res = {rect.left/scale.x,
|
|
||||||
rect.bottom/scale.y,
|
|
||||||
(rect.right - rect.left)/scale.x,
|
|
||||||
(rect.bottom - rect.top)/scale.y};
|
|
||||||
return(res);
|
|
||||||
}
|
|
||||||
|
|
||||||
void mp_layer_set_frame(mp_layer* layer, mp_rect frame)
|
|
||||||
{
|
|
||||||
HWND parent = GetParent(layer->hWnd);
|
|
||||||
RECT parentContentRect;
|
|
||||||
|
|
||||||
GetClientRect(parent, &parentContentRect);
|
|
||||||
int parentHeight = parentContentRect.bottom - parentContentRect.top;
|
|
||||||
|
|
||||||
vec2 scale = mp_layer_contents_scaling(layer);
|
|
||||||
|
|
||||||
SetWindowPos(layer->hWnd,
|
|
||||||
HWND_TOP,
|
|
||||||
frame.x * scale.x,
|
|
||||||
parentHeight - (frame.y + frame.h) * scale.y,
|
|
||||||
frame.w * scale.x,
|
|
||||||
frame.h * scale.y,
|
|
||||||
SWP_NOACTIVATE | SWP_NOZORDER);
|
|
||||||
}
|
|
||||||
|
|
||||||
void mp_layer_set_hidden(mp_layer* layer, bool hidden)
|
|
||||||
{
|
|
||||||
ShowWindow(layer->hWnd, hidden ? SW_HIDE : SW_NORMAL);
|
|
||||||
}
|
|
||||||
|
|
||||||
bool mp_layer_get_hidden(mp_layer* layer)
|
|
||||||
{
|
|
||||||
bool hidden = !IsWindowVisible(layer->hWnd);
|
|
||||||
return(hidden);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/////////////////////////////////////////// WIP ///////////////////////////////////////////////
|
/////////////////////////////////////////// WIP ///////////////////////////////////////////////
|
||||||
|
|
|
@ -1,145 +0,0 @@
|
||||||
/************************************************************//**
|
|
||||||
*
|
|
||||||
* @file: win32_surface_sharing.c
|
|
||||||
* @author: Martin Fouilleul
|
|
||||||
* @date: 02/03/2023
|
|
||||||
* @revision:
|
|
||||||
*
|
|
||||||
*****************************************************************/
|
|
||||||
#include"graphics_internal.h"
|
|
||||||
|
|
||||||
//------------------------------------------------------------------------------------------------
|
|
||||||
// Surface client
|
|
||||||
//------------------------------------------------------------------------------------------------
|
|
||||||
|
|
||||||
typedef struct mg_win32_surface_host
|
|
||||||
{
|
|
||||||
mg_surface_data interface;
|
|
||||||
mp_layer layer;
|
|
||||||
|
|
||||||
} mg_win32_surface_host;
|
|
||||||
|
|
||||||
void mg_win32_surface_host_prepare(mg_surface_data* interface)
|
|
||||||
{}
|
|
||||||
|
|
||||||
void mg_win32_surface_host_present(mg_surface_data* interface)
|
|
||||||
{}
|
|
||||||
|
|
||||||
void mg_win32_surface_host_swap_interval(mg_surface_data* interface, int swap)
|
|
||||||
{
|
|
||||||
//TODO
|
|
||||||
}
|
|
||||||
|
|
||||||
vec2 mg_win32_surface_host_contents_scaling(mg_surface_data* interface)
|
|
||||||
{
|
|
||||||
mg_win32_surface_host* surface = (mg_win32_surface_host*)interface;
|
|
||||||
return(mp_layer_contents_scaling(&surface->layer));
|
|
||||||
}
|
|
||||||
|
|
||||||
mp_rect mg_win32_surface_host_get_frame(mg_surface_data* interface)
|
|
||||||
{
|
|
||||||
mg_win32_surface_host* surface = (mg_win32_surface_host*)interface;
|
|
||||||
return(mp_layer_get_frame(&surface->layer));
|
|
||||||
}
|
|
||||||
|
|
||||||
void mg_win32_surface_host_set_frame(mg_surface_data* interface, mp_rect frame)
|
|
||||||
{
|
|
||||||
mg_win32_surface_host* surface = (mg_win32_surface_host*)interface;
|
|
||||||
mp_layer_set_frame(&surface->layer, frame);
|
|
||||||
}
|
|
||||||
|
|
||||||
void mg_win32_surface_host_set_hidden(mg_surface_data* interface, bool hidden)
|
|
||||||
{
|
|
||||||
mg_win32_surface_host* surface = (mg_win32_surface_host*)interface;
|
|
||||||
mp_layer_set_hidden(&surface->layer, hidden);
|
|
||||||
}
|
|
||||||
|
|
||||||
bool mg_win32_surface_host_get_hidden(mg_surface_data* interface)
|
|
||||||
{
|
|
||||||
mg_win32_surface_host* surface = (mg_win32_surface_host*)interface;
|
|
||||||
return(mp_layer_get_hidden(&surface->layer));
|
|
||||||
}
|
|
||||||
|
|
||||||
void* mg_win32_surface_host_native_layer(mg_surface_data* interface)
|
|
||||||
{
|
|
||||||
mg_win32_surface_host* surface = (mg_win32_surface_host*)interface;
|
|
||||||
return(mp_layer_native_surface(&surface->layer));
|
|
||||||
}
|
|
||||||
|
|
||||||
void mg_win32_surface_host_destroy(mg_surface_data* interface)
|
|
||||||
{
|
|
||||||
mg_win32_surface_host* surface = (mg_win32_surface_host*)interface;
|
|
||||||
|
|
||||||
mp_layer_cleanup(&surface->layer);
|
|
||||||
//TODO...
|
|
||||||
|
|
||||||
free(surface);
|
|
||||||
}
|
|
||||||
|
|
||||||
MP_API void mg_win32_surface_host_connect(mg_surface_data* interface, mg_surface_id ID)
|
|
||||||
{
|
|
||||||
mg_win32_surface_host* surface = (mg_win32_surface_host*)interface;
|
|
||||||
|
|
||||||
//NOTE:Quick test
|
|
||||||
HWND dstWnd = mp_layer_native_surface(&surface->layer);
|
|
||||||
HWND srcWnd = (HWND)ID;
|
|
||||||
|
|
||||||
RECT dstRect;
|
|
||||||
GetClientRect(dstWnd, &dstRect);
|
|
||||||
|
|
||||||
SetParent(srcWnd, dstWnd);
|
|
||||||
ShowWindow(srcWnd, SW_NORMAL);
|
|
||||||
|
|
||||||
SetWindowPos(srcWnd,
|
|
||||||
HWND_TOP,
|
|
||||||
0,
|
|
||||||
0,
|
|
||||||
dstRect.right - dstRect.left,
|
|
||||||
dstRect.bottom - dstRect.top,
|
|
||||||
SWP_NOACTIVATE | SWP_NOZORDER);
|
|
||||||
}
|
|
||||||
|
|
||||||
mg_surface_data* mg_win32_surface_create_host(mp_window window)
|
|
||||||
{
|
|
||||||
mg_win32_surface_host* surface = 0;
|
|
||||||
|
|
||||||
mp_window_data* windowData = mp_window_ptr_from_handle(window);
|
|
||||||
if(windowData)
|
|
||||||
{
|
|
||||||
surface = malloc_type(mg_win32_surface_host);
|
|
||||||
if(surface)
|
|
||||||
{
|
|
||||||
mp_layer_init_for_window(&surface->layer, windowData);
|
|
||||||
|
|
||||||
surface->interface.backend = MG_BACKEND_REMOTE;
|
|
||||||
surface->interface.destroy = mg_win32_surface_host_destroy;
|
|
||||||
surface->interface.prepare = mg_win32_surface_host_prepare;
|
|
||||||
surface->interface.present = mg_win32_surface_host_present;
|
|
||||||
surface->interface.swapInterval = mg_win32_surface_host_swap_interval;
|
|
||||||
surface->interface.contentsScaling = mg_win32_surface_host_contents_scaling;
|
|
||||||
surface->interface.getFrame = mg_win32_surface_host_get_frame;
|
|
||||||
surface->interface.setFrame = mg_win32_surface_host_set_frame;
|
|
||||||
surface->interface.getHidden = mg_win32_surface_host_get_hidden;
|
|
||||||
surface->interface.setHidden = mg_win32_surface_host_set_hidden;
|
|
||||||
surface->interface.nativeLayer = mg_win32_surface_host_native_layer;
|
|
||||||
surface->interface.connect = mg_win32_surface_host_connect;
|
|
||||||
//TODO
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return((mg_surface_data*)surface);
|
|
||||||
}
|
|
||||||
|
|
||||||
mg_surface mg_surface_create_host(mp_window window)
|
|
||||||
{
|
|
||||||
if(!__mgData.init)
|
|
||||||
{
|
|
||||||
mg_init();
|
|
||||||
}
|
|
||||||
mg_surface surfaceHandle = {0};
|
|
||||||
mg_surface_data* surface = mg_win32_surface_create_host(window);
|
|
||||||
if(surface)
|
|
||||||
{
|
|
||||||
surfaceHandle = mg_surface_handle_alloc(surface);
|
|
||||||
}
|
|
||||||
return(surfaceHandle);
|
|
||||||
}
|
|
Loading…
Reference in New Issue