This commit is contained in:
commit
bf9474f4f4
12 changed files with 143 additions and 34 deletions
|
|
@ -2,7 +2,7 @@
|
|||
|
||||
MwWidget window, instructions, text;
|
||||
|
||||
void resize(MwWidget handle, void* user_data, void* call_data) {
|
||||
static void resize(MwWidget handle, void* user_data, void* call_data) {
|
||||
unsigned int w, h;
|
||||
|
||||
(void)user_data;
|
||||
|
|
@ -23,7 +23,7 @@ void resize(MwWidget handle, void* user_data, void* call_data) {
|
|||
MwNheight, h - 125 - 50 * 3,
|
||||
NULL);
|
||||
}
|
||||
void clipboard(MwWidget handle, void* user_data, void* call_data) {
|
||||
static void clipboard(MwWidget handle, void* user_data, void* call_data) {
|
||||
char* clipboard = call_data;
|
||||
|
||||
(void)handle;
|
||||
|
|
@ -36,6 +36,10 @@ void clipboard(MwWidget handle, void* user_data, void* call_data) {
|
|||
MwForceRender(window);
|
||||
}
|
||||
|
||||
static void tick(MwWidget handle, void* user_data, void* call_data) {
|
||||
MwGetClipboard(handle);
|
||||
}
|
||||
|
||||
int main() {
|
||||
MwLibraryInit();
|
||||
|
||||
|
|
@ -53,6 +57,7 @@ int main() {
|
|||
MwAddUserHandler(window, MwNclipboardHandler, clipboard, NULL);
|
||||
MwAddUserHandler(instructions, MwNclipboardHandler, clipboard, NULL);
|
||||
MwAddUserHandler(text, MwNclipboardHandler, clipboard, NULL);
|
||||
MwAddUserHandler(window, MwNtickHandler, tick, NULL);
|
||||
|
||||
resize(window, NULL, NULL);
|
||||
|
||||
|
|
|
|||
|
|
@ -16,8 +16,8 @@ void handler_theme(MwWidget handle, void* user_data, void* call_data) {
|
|||
(void)call_data;
|
||||
|
||||
MwVaApply(window,
|
||||
MwNdarkTheme, MwGetInteger(window, MwNdarkTheme) == 0 ? 1 : 0,
|
||||
NULL);
|
||||
MwNdarkTheme, MwGetInteger(window, MwNdarkTheme) == 0 ? 1 : 0,
|
||||
NULL);
|
||||
}
|
||||
|
||||
void handler_look(MwWidget handle, void* user_data, void* call_data) {
|
||||
|
|
@ -26,8 +26,8 @@ void handler_look(MwWidget handle, void* user_data, void* call_data) {
|
|||
(void)call_data;
|
||||
|
||||
MwVaApply(window,
|
||||
MwNmodernLook, MwGetInteger(window, MwNmodernLook) == 0 ? 1 : 0,
|
||||
NULL);
|
||||
MwNmodernLook, MwGetInteger(window, MwNmodernLook) == 0 ? 1 : 0,
|
||||
NULL);
|
||||
}
|
||||
|
||||
void handler_font(MwWidget handle, void* user_data, void* call_data) {
|
||||
|
|
@ -36,8 +36,8 @@ void handler_font(MwWidget handle, void* user_data, void* call_data) {
|
|||
(void)call_data;
|
||||
|
||||
MwVaApply(window,
|
||||
MwNbitmapFont, MwGetInteger(window, MwNbitmapFont) == 0 ? 1 : 0,
|
||||
NULL);
|
||||
MwNbitmapFont, MwGetInteger(window, MwNbitmapFont) == 0 ? 1 : 0,
|
||||
NULL);
|
||||
}
|
||||
|
||||
void resize(MwWidget handle, void* user_data, void* call_data) {
|
||||
|
|
|
|||
|
|
@ -292,8 +292,8 @@ void vulkan_setup(MwWidget handle) {
|
|||
swapchainCreateInfo.imageExtent = (VkExtent2D){.width = ow, .height = oh},
|
||||
swapchainCreateInfo.imageArrayLayers = 1,
|
||||
swapchainCreateInfo.imageUsage = VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT |
|
||||
VK_IMAGE_USAGE_TRANSFER_DST_BIT |
|
||||
VK_IMAGE_USAGE_SAMPLED_BIT;
|
||||
VK_IMAGE_USAGE_TRANSFER_DST_BIT |
|
||||
VK_IMAGE_USAGE_SAMPLED_BIT;
|
||||
// th is how we specify no transformation.
|
||||
swapchainCreateInfo.preTransform = VK_SURFACE_TRANSFORM_IDENTITY_BIT_KHR;
|
||||
swapchainCreateInfo.compositeAlpha = VK_COMPOSITE_ALPHA_OPAQUE_BIT_KHR;
|
||||
|
|
|
|||
|
|
@ -357,9 +357,16 @@ MWDECL void MwGetScreenSize(MwWidget handle, MwRect* rect);
|
|||
|
||||
/*!
|
||||
* @brief Reports whether a widget reports global or local coordinates upon GetXY/SetXY. Anything with a parent reports local, and most backends report global coordinates being supported for top level windows, but some (Wayland) do not.
|
||||
* @param handle Widget
|
||||
*/
|
||||
MWDECL int MwGetCoordinateType(MwWidget handle);
|
||||
|
||||
/*!
|
||||
* @brief Queue to get clipboard content
|
||||
* @param handle Widget
|
||||
*/
|
||||
MWDECL void MwGetClipboard(MwWidget handle);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
|
|
|||
|
|
@ -30,9 +30,17 @@ struct _MwLLX11 {
|
|||
Colormap colormap;
|
||||
Atom wm_delete;
|
||||
Atom wm_protocols;
|
||||
Atom utf8_string;
|
||||
Atom compound_text;
|
||||
Atom text;
|
||||
Atom clipboard;
|
||||
Atom selection;
|
||||
XIM xim;
|
||||
XIC xic;
|
||||
|
||||
long clipboard_time;
|
||||
int clipboard_pending; /* 1 if UTF8_STRING, 2 if COMPOUNd_TEXT, 3 if TEXT, 4 if STRING, otherwise 0 */
|
||||
|
||||
int top;
|
||||
int toplevel;
|
||||
int grabbed;
|
||||
|
|
|
|||
14
pl/rules.pl
14
pl/rules.pl
|
|
@ -35,13 +35,13 @@ if (grep(/^wayland$/, @backends)) {
|
|||
}
|
||||
|
||||
scan_wayland_protocol_core();
|
||||
scan_wayland_protocol("stable", "xdg-shell", "");
|
||||
scan_wayland_protocol("stable", "viewporter", "");
|
||||
scan_wayland_protocol("stable", "tablet", "-v2");
|
||||
scan_wayland_protocol("staging", "xdg-toplevel-icon", "-v1");
|
||||
scan_wayland_protocol("staging", "cursor-shape", "-v1");
|
||||
scan_wayland_protocol("unstable", "xdg-decoration", "-unstable-v1");
|
||||
scan_wayland_protocol("unstable", "primary-selection", "-unstable-v1");
|
||||
scan_wayland_protocol("stable", "xdg-shell", "");
|
||||
scan_wayland_protocol("stable", "viewporter", "");
|
||||
scan_wayland_protocol("stable", "tablet", "-v2");
|
||||
scan_wayland_protocol("staging", "xdg-toplevel-icon", "-v1");
|
||||
scan_wayland_protocol("staging", "cursor-shape", "-v1");
|
||||
scan_wayland_protocol("unstable", "xdg-decoration", "-unstable-v1");
|
||||
scan_wayland_protocol("unstable", "primary-selection", "-unstable-v1");
|
||||
scan_wayland_protocol("unstable", "pointer-constraints", "-unstable-v1");
|
||||
|
||||
$gl_libs = "-lGL -lGLU";
|
||||
|
|
|
|||
|
|
@ -58,7 +58,6 @@ sub use_backend {
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
sub scan_wayland_protocol_core {
|
||||
my $proto_c = "src/backend/wayland-core-protocol.c";
|
||||
|
||||
|
|
|
|||
|
|
@ -2,6 +2,8 @@
|
|||
|
||||
#include "../../external/stb_ds.h"
|
||||
|
||||
#define ClipboardTimeout 100
|
||||
|
||||
typedef struct mwm_hints {
|
||||
unsigned long flags;
|
||||
unsigned long functions;
|
||||
|
|
@ -215,6 +217,14 @@ static MwLL MwLLCreateImpl(MwLL parent, int x, int y, int width, int height) {
|
|||
r->x11.wm_protocols = XInternAtom(r->x11.display, "WM_PROTOCOLS", False);
|
||||
XSetWMProtocols(r->x11.display, r->x11.window, &r->x11.wm_delete, 1);
|
||||
|
||||
r->x11.utf8_string = XInternAtom(r->x11.display, "UTF8_STRING", False);
|
||||
r->x11.compound_text = XInternAtom(r->x11.display, "COMPOUND_TEXT", False);
|
||||
r->x11.text = XInternAtom(r->x11.display, "TEXT", False);
|
||||
r->x11.clipboard = XInternAtom(r->x11.display, "CLIPBOARD", False);
|
||||
r->x11.selection = XInternAtom(r->x11.display, "_MILSKO_SELECTION_", False);
|
||||
|
||||
r->x11.clipboard_pending = 0;
|
||||
|
||||
r->x11.gc = XCreateGC(r->x11.display, r->x11.window, 0, NULL);
|
||||
|
||||
create_pixmap(r);
|
||||
|
|
@ -414,7 +424,11 @@ static void MwLLFreeColorImpl(MwLLColor color) {
|
|||
static int MwLLPendingImpl(MwLL handle) {
|
||||
XEvent ev;
|
||||
|
||||
if(XCheckTypedWindowEvent(handle->x11.display, handle->x11.window, ClientMessage, &ev) || XCheckWindowEvent(handle->x11.display, handle->x11.window, mask, &ev)) {
|
||||
if(handle->x11.clipboard_pending && (MwTimeGetTick() - handle->x11.clipboard_time) >= ClipboardTimeout) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
if(XCheckTypedWindowEvent(handle->x11.display, handle->x11.window, ClientMessage, &ev) || XCheckTypedWindowEvent(handle->x11.display, handle->x11.window, SelectionNotify, &ev) || XCheckWindowEvent(handle->x11.display, handle->x11.window, mask, &ev)) {
|
||||
XPutBackEvent(handle->x11.display, &ev);
|
||||
return 1;
|
||||
}
|
||||
|
|
@ -424,7 +438,33 @@ static int MwLLPendingImpl(MwLL handle) {
|
|||
static void MwLLNextEventImpl(MwLL handle) {
|
||||
XEvent ev;
|
||||
|
||||
while(XCheckTypedWindowEvent(handle->x11.display, handle->x11.window, ClientMessage, &ev) || XCheckWindowEvent(handle->x11.display, handle->x11.window, mask, &ev)) {
|
||||
if(handle->x11.clipboard_pending && (MwTimeGetTick() - handle->x11.clipboard_time) >= ClipboardTimeout) {
|
||||
Atom a = handle->x11.selection;
|
||||
|
||||
handle->x11.clipboard_pending++;
|
||||
handle->x11.clipboard_time = MwTimeGetTick();
|
||||
|
||||
switch(handle->x11.clipboard_pending) {
|
||||
case 2:
|
||||
a = handle->x11.compound_text;
|
||||
break;
|
||||
case 3:
|
||||
a = handle->x11.text;
|
||||
break;
|
||||
case 4:
|
||||
a = XA_STRING;
|
||||
break;
|
||||
case 5:
|
||||
handle->x11.clipboard_pending = 0;
|
||||
break;
|
||||
}
|
||||
|
||||
if(a != handle->x11.selection) {
|
||||
XConvertSelection(handle->x11.display, handle->x11.clipboard, a, handle->x11.selection, handle->x11.window, CurrentTime);
|
||||
}
|
||||
}
|
||||
|
||||
while(XCheckTypedWindowEvent(handle->x11.display, handle->x11.window, ClientMessage, &ev) || XCheckTypedWindowEvent(handle->x11.display, handle->x11.window, SelectionNotify, &ev) || XCheckWindowEvent(handle->x11.display, handle->x11.window, mask, &ev)) {
|
||||
int render = 0;
|
||||
if(ev.type == Expose) {
|
||||
handle->x11.force_render = 0;
|
||||
|
|
@ -563,6 +603,49 @@ static void MwLLNextEventImpl(MwLL handle) {
|
|||
MwLLDispatch(handle, key_released, &n);
|
||||
}
|
||||
}
|
||||
} else if(ev.type == SelectionNotify) {
|
||||
handle->x11.clipboard_pending = 0;
|
||||
|
||||
if(ev.xselection.property != None) {
|
||||
Atom type;
|
||||
int format;
|
||||
unsigned long nitems, after, size;
|
||||
unsigned char* pdat;
|
||||
int ret = XGetWindowProperty(handle->x11.display, handle->x11.window, handle->x11.selection, 0, 0, False, AnyPropertyType, &type, &format, &nitems, &after, &pdat);
|
||||
|
||||
if(pdat != NULL) XFree(pdat);
|
||||
|
||||
size = after;
|
||||
|
||||
if(ret == Success && type != None && format == 8) {
|
||||
char* buf = malloc(size + 1);
|
||||
int offset;
|
||||
|
||||
for(offset = 0; after > 0; offset += nitems) {
|
||||
ret = XGetWindowProperty(handle->x11.display, handle->x11.window, handle->x11.selection, offset / 4, after / 4 + 1, False, AnyPropertyType, &type, &format, &nitems, &after, &pdat);
|
||||
|
||||
if(ret != Success) {
|
||||
free(buf);
|
||||
buf = NULL;
|
||||
break;
|
||||
}
|
||||
|
||||
memcpy(buf + offset, pdat, nitems);
|
||||
|
||||
XFree(pdat);
|
||||
}
|
||||
|
||||
if(buf != NULL) {
|
||||
buf[size] = 0;
|
||||
|
||||
MwLLDispatch(handle, clipboard, buf);
|
||||
|
||||
free(buf);
|
||||
}
|
||||
}
|
||||
|
||||
XDeleteProperty(handle->x11.display, handle->x11.window, handle->x11.selection);
|
||||
}
|
||||
}
|
||||
if(render) {
|
||||
int x, y;
|
||||
|
|
@ -961,9 +1044,12 @@ static void MwLLSetClipboardImpl(MwLL handle, const char* text) {
|
|||
}
|
||||
|
||||
static void MwLLGetClipboardImpl(MwLL handle) {
|
||||
/* TODO */
|
||||
if(handle->x11.clipboard_pending) return;
|
||||
|
||||
(void)handle;
|
||||
XConvertSelection(handle->x11.display, handle->x11.clipboard, handle->x11.utf8_string, handle->x11.selection, handle->x11.window, CurrentTime);
|
||||
|
||||
handle->x11.clipboard_pending = 1;
|
||||
handle->x11.clipboard_time = MwTimeGetTick();
|
||||
}
|
||||
|
||||
static void MwLLMakeToolWindowImpl(MwLL handle) {
|
||||
|
|
|
|||
16
src/core.c
16
src/core.c
|
|
@ -134,8 +134,8 @@ static void lldarkthemehandler(MwLL handle, void* data) {
|
|||
|
||||
if(IsFirstVisible(h)) {
|
||||
MwVaApply(h,
|
||||
MwNdarkTheme, *ptr,
|
||||
NULL);
|
||||
MwNdarkTheme, *ptr,
|
||||
NULL);
|
||||
|
||||
MwDispatchUserHandler(h, MwNdarkThemeHandler, data);
|
||||
}
|
||||
|
|
@ -449,7 +449,7 @@ void MwSetInteger(MwWidget handle, const char* key, int n) {
|
|||
if(strcmp(key, MwNforceInverted) == 0) {
|
||||
MwForceRender(handle);
|
||||
}
|
||||
if(strcmp(key, MwNmodernLook) == 0 || strcmp(key, MwNdarkTheme) == 0 || strcmp(key, MwNbitmapFont) == 0){
|
||||
if(strcmp(key, MwNmodernLook) == 0 || strcmp(key, MwNdarkTheme) == 0 || strcmp(key, MwNbitmapFont) == 0) {
|
||||
force_render_all(handle);
|
||||
}
|
||||
}
|
||||
|
|
@ -762,8 +762,8 @@ void MwGrabPointer(MwWidget handle, int toggle) {
|
|||
|
||||
void MwSetDarkTheme(MwWidget handle, int toggle) {
|
||||
MwVaApply(handle,
|
||||
MwNdarkTheme, toggle,
|
||||
NULL);
|
||||
MwNdarkTheme, toggle,
|
||||
NULL);
|
||||
}
|
||||
|
||||
MwWidget MwGetParent(MwWidget handle) {
|
||||
|
|
@ -856,4 +856,8 @@ int MwGetCoordinateType(MwWidget handle) {
|
|||
} else {
|
||||
return MwCoordinatesLocal;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
void MwGetClipboard(MwWidget handle) {
|
||||
MwLLGetClipboard(handle->lowlevel);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -283,7 +283,6 @@ static void MwDrawFrameEx_simple(MwWidget handle, MwRect* rect, MwLLColor color,
|
|||
int ColorDiff = get_color_diff(handle);
|
||||
MwLLColor darker = MwLightenColor(handle, color, -ColorDiff * 3 / 2 + diff, -ColorDiff * 3 / 2 + diff, -ColorDiff * 3 / 2 + diff);
|
||||
MwLLColor lighter = same ? MwLightenColor(handle, darker, 0, 0, 0) : MwLightenColor(handle, color, ColorDiff - diff, ColorDiff - diff, ColorDiff - diff);
|
||||
int i;
|
||||
int roundness = MwGetInteger(handle, MwNroundness);
|
||||
|
||||
if(roundness == MwDEFAULT) roundness = DEFAULT_ROUNDNESS;
|
||||
|
|
@ -345,9 +344,11 @@ static void MwDrawFrameEx_simple(MwWidget handle, MwRect* rect, MwLLColor color,
|
|||
static void frame_border_complex(MwWidget handle, MwRect* rect, MwLLColor lighter, MwLLColor darker, int invert, int border, int diff, int same, int rounded) {
|
||||
MwPoint p[7];
|
||||
int roundness = MwGetInteger(handle, MwNroundness);
|
||||
MwRect r = *rect;
|
||||
int i;
|
||||
|
||||
(void)diff;
|
||||
(void)same;
|
||||
|
||||
if(roundness == MwDEFAULT) roundness = DEFAULT_ROUNDNESS;
|
||||
if(roundness >= MAX_ROUNDNESS) roundness = MAX_ROUNDNESS;
|
||||
if(rounded && rect->height >= (roundness * 2) && rect->width >= (roundness * 2) && roundness > 0) {
|
||||
|
|
@ -493,8 +494,7 @@ static void MwDrawFrameEx_complex(MwWidget handle, MwRect* rect, MwLLColor color
|
|||
int ColorDiff = get_color_diff(handle);
|
||||
MwLLColor darker = MwLightenColor(handle, color, -ColorDiff * 3 / 2 + diff, -ColorDiff * 3 / 2 + diff, -ColorDiff * 3 / 2 + diff);
|
||||
MwLLColor lighter = same ? MwLightenColor(handle, darker, 0, 0, 0) : MwLightenColor(handle, color, (ColorDiff / 2) - diff, (ColorDiff / 2) - diff, (ColorDiff / 2) - diff);
|
||||
int i;
|
||||
MwRect r = *rect;
|
||||
MwRect r = *rect;
|
||||
|
||||
frame_border_complex(handle, rect, lighter, darker, invert, border, diff, same, rounded);
|
||||
|
||||
|
|
|
|||
|
|
@ -54,7 +54,7 @@ void (*MwLLGetScreenSize)(MwLL handle, MwRect* rect) = NULL;
|
|||
void MwLLCreateCommon(MwLL handle) {
|
||||
handle->common.handler = malloc(sizeof(*handle->common.handler));
|
||||
memset(handle->common.handler, 0, sizeof(*handle->common.handler));
|
||||
|
||||
|
||||
handle->common.supports_transparency = 0;
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -229,7 +229,7 @@ static MwErrorEnum vulkan_instance_setup(MwWidget handle, vulkan_t* o) {
|
|||
if(handle->lowlevel->common.type == MwLLBackendWayland) {
|
||||
arrput(enabledExtensions, VK_KHR_WAYLAND_SURFACE_EXTENSION_NAME);
|
||||
/* take this opprutunity to set the widget to always render */
|
||||
MwWaylandAlwaysRender = MwTRUE;
|
||||
MwWaylandAlwaysRender = MwTRUE;
|
||||
}
|
||||
#endif
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue