diff --git a/GNUmakefile b/GNUmakefile
index 2b53b91..01ec37b 100644
--- a/GNUmakefile
+++ b/GNUmakefile
@@ -35,6 +35,7 @@ E_LIBS = $(LIBS) -lMw
L_OBJS = src/core.o src/default.o src/draw.o src/lowlevel.o src/font.o src/boldfont.o src/error.o
L_OBJS += src/external/ds.o src/external/image.o
L_OBJS += src/widget/window.o src/widget/button.o src/widget/frame.o src/widget/menu.o src/widget/submenu.o src/widget/image.o src/widget/scrollbar.o
+L_OBJS += src/cursor/default.o
ifeq ($(TARGET),NetBSD)
CFLAGS += -I/usr/X11R7/include -I/usr/pkg/include
@@ -66,7 +67,7 @@ endif
ifeq ($(UNIX),1)
L_CFLAGS += -DUSE_X11
L_OBJS += src/backend/x11.o
-L_LIBS += -lm -lX11 -lXrender -lXext
+L_LIBS += -lm -lX11 -lXrender -lXext -lXcursor
GL = -lGL -lGLU
diff --git a/doc/index.html b/doc/index.html
index f403327..89060cb 100644
--- a/doc/index.html
+++ b/doc/index.html
@@ -92,6 +92,15 @@
MwForceRender
+
+ Mw/Cursor.h
+
+
+ MwCursorDefault
+
+
+ MwCursorDefaultMask
+
Mw/Default.h
@@ -1033,6 +1042,27 @@
+Mw/Cursor.h
+
+-
+ Cursor externs.
+
+
+
+MWDECL MwCursor MwCursorDefault;
+
+-
+ Default cursor.
+
+
+
+MWDECL MwCursor MwCursorDefaultMask;
+
+-
+ Default cursor mask.
+
+
+
Mw/Default.h
-
diff --git a/include/Mw/Cursor.h b/include/Mw/Cursor.h
new file mode 100644
index 0000000..c7f9777
--- /dev/null
+++ b/include/Mw/Cursor.h
@@ -0,0 +1,31 @@
+/* $Id$ */
+/*!
+ * %file Mw/Cursor.h
+ * %brief Cursor externs
+ */
+
+#ifndef __MW_CURSOR_H__
+#define __MW_CURSOR_H__
+
+#include
+#include
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/*!
+ * %brief Default cursor
+ */
+MWDECL MwCursor MwCursorDefault;
+
+/*!
+ * %brief Default cursor mask
+ */
+MWDECL MwCursor MwCursorDefaultMask;
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
diff --git a/include/Mw/LowLevel.h b/include/Mw/LowLevel.h
index db9db85..202482e 100644
--- a/include/Mw/LowLevel.h
+++ b/include/Mw/LowLevel.h
@@ -9,11 +9,11 @@
#include
-typedef struct _MwLLHandler *MwLLHandler, MwLLHandlerRec;
+typedef struct _MwLLHandler* MwLLHandler;
#ifdef _MILSKO
-typedef struct _MwLL * MwLL, MwLLRec;
-typedef struct _MwLLColor * MwLLColor, MwLLColorRec;
-typedef struct _MwLLPixmap *MwLLPixmap, MwLLPixmapRec;
+typedef struct _MwLL* MwLL;
+typedef struct _MwLLColor* MwLLColor;
+typedef struct _MwLLPixmap* MwLLPixmap;
#else
typedef void* MwLL;
typedef void* MwLLColor;
@@ -76,6 +76,8 @@ MWDECL void MwLLSetIcon(MwLL handle, MwLLPixmap pixmap);
MWDECL void MwLLForceRender(MwLL handle);
+MWDECL void MwLLSetCursor(MwLL handle, MwCursor* image, MwCursor* mask);
+
#ifdef __cplusplus
}
#endif
diff --git a/include/Mw/Milsko.h b/include/Mw/Milsko.h
index 546e5e4..2a7eea6 100644
--- a/include/Mw/Milsko.h
+++ b/include/Mw/Milsko.h
@@ -15,6 +15,7 @@
#include
#include
#include
+#include
#include
#include
diff --git a/include/Mw/TypeDefs.h b/include/Mw/TypeDefs.h
index e64fc45..de71a99 100644
--- a/include/Mw/TypeDefs.h
+++ b/include/Mw/TypeDefs.h
@@ -16,12 +16,12 @@ typedef struct _MwTextKeyValue MwTextKeyValue;
typedef struct _MwUserHandlerKeyValue MwUserHandlerKeyValue;
typedef struct _MwVoidKeyValue MwVoidKeyValue;
typedef struct _MwFont MwFont;
+typedef struct _MwMenu* MwMenu;
+typedef struct _MwCursor MwCursor;
#ifdef _MILSKO
-typedef struct _MwWidget *MwWidget, MwWidgetRec;
-typedef struct _MwMenu * MwMenu, MwMenuRec;
+typedef struct _MwWidget* MwWidget;
#else
typedef void* MwWidget;
-typedef void* MwMenu;
#endif
typedef void (*MwHandler)(MwWidget handle);
typedef int (*MwHandler2)(MwWidget handle);
@@ -88,6 +88,7 @@ struct _MwWidget {
MwWidget* destroy_queue;
};
+#endif
struct _MwMenu {
char* name;
@@ -95,7 +96,15 @@ struct _MwMenu {
MwWidget wsub;
MwMenu* sub;
};
-#endif
+
+#define MwCursorDataHeight 16
+struct _MwCursor {
+ int width;
+ int height;
+ int x;
+ int y;
+ unsigned int data[MwCursorDataHeight];
+};
struct _MwClass {
MwHandler2 create;
diff --git a/src/backend/gdi.c b/src/backend/gdi.c
index 25a136e..3363d9a 100644
--- a/src/backend/gdi.c
+++ b/src/backend/gdi.c
@@ -319,3 +319,49 @@ void MwLLSetIcon(MwLL handle, MwLLPixmap pixmap) {
void MwLLForceRender(MwLL handle) {
InvalidateRect(handle->hWnd, NULL, FALSE);
}
+
+void MwLLSetCursor(MwLL handle, MwCursor* image, MwCursor* mask) {
+ HCURSOR cursor;
+ BYTE* dmask = malloc((MwCursorDataHeight / 8) * MwCursorDataHeight);
+ BYTE* dimage = malloc((MwCursorDataHeight / 8) * MwCursorDataHeight);
+ int y, x;
+
+ memset(dmask, 0xff, (MwCursorDataHeight / 8) * MwCursorDataHeight);
+ memset(dimage, 0, (MwCursorDataHeight / 8) * MwCursorDataHeight);
+
+ for(y = 0; y < mask->height; y++) {
+ BYTE* l = &dmask[y * (MwCursorDataHeight / 8)];
+ unsigned int n = mask->data[y];
+ for(x = mask->width - 1; x >= 0; x--) {
+ l[x / 8] = l[x / 8] >> 1;
+ if(!(n & 1)) {
+ l[x / 8] |= 1 << 7;
+ }
+
+ n = n >> 1;
+ }
+ }
+
+ for(y = 0; y < image->height; y++) {
+ BYTE* l = &dimage[(y + (MwCursorDataHeight + mask->y)) * (MwCursorDataHeight / 8)];
+ unsigned int n = image->data[y];
+
+ for(x = image->width - 1; x >= 0; x--) {
+ if(n & 1) {
+ l[(x - mask->x) / 8] |= (1 << (7 - ((x - mask->x) % 8)));
+ }
+
+ n = n >> 1;
+ }
+ }
+
+ cursor = CreateCursor(GetModuleHandle(NULL), -mask->x, MwCursorDataHeight + mask->y, MwCursorDataHeight, MwCursorDataHeight, dmask, dimage);
+
+ SetClassLongPtr(handle->hWnd, GCLP_HCURSOR, (LONG_PTR)cursor);
+ SetCursor(cursor);
+
+ DestroyCursor(cursor);
+
+ free(dimage);
+ free(dmask);
+}
diff --git a/src/backend/x11.c b/src/backend/x11.c
index a6f656e..0c2d782 100644
--- a/src/backend/x11.c
+++ b/src/backend/x11.c
@@ -334,3 +334,39 @@ void MwLLForceRender(MwLL handle) {
ev.xexpose.window = handle->window;
XSendEvent(handle->display, handle->window, False, ExposureMask, &ev);
}
+
+void MwLLSetCursor(MwLL handle, MwCursor* image, MwCursor* mask) {
+ XcursorImage* img = XcursorImageCreate(MwCursorDataHeight, MwCursorDataHeight);
+ Cursor cur;
+ int y, x;
+
+ img->xhot = -mask->x;
+ img->yhot = MwCursorDataHeight + mask->y;
+
+ memset(img->pixels, 0, MwCursorDataHeight * MwCursorDataHeight * sizeof(XcursorPixel));
+ for(y = 0; y < mask->height; y++) {
+ unsigned int l = mask->data[y];
+ for(x = mask->width - 1; x >= 0; x--) {
+ if(l & 1) {
+ img->pixels[y * MwCursorDataHeight + x] = 0xff000000;
+ }
+ l = l >> 1;
+ }
+ }
+ for(y = 0; y < image->height; y++) {
+ unsigned int l = image->data[y];
+ for(x = image->width - 1; x >= 0; x--) {
+ int px = 0;
+ if(l & 1) px = 255;
+ img->pixels[(img->yhot + y) * MwCursorDataHeight + (img->xhot + x)] |= (px << 16) | (px << 8) | (px);
+
+ l = l >> 1;
+ }
+ }
+
+ cur = XcursorImageLoadCursor(handle->display, img);
+ XDefineCursor(handle->display, handle->window, cur);
+ XFreeCursor(handle->display, cur);
+
+ XcursorImageDestroy(img);
+}
diff --git a/src/backend/x11.h b/src/backend/x11.h
index e693da2..d6eba6e 100644
--- a/src/backend/x11.h
+++ b/src/backend/x11.h
@@ -8,6 +8,7 @@
#include
#include
+#include
#include
#include
diff --git a/src/core.c b/src/core.c
index c16c954..6a0eb2d 100644
--- a/src/core.c
+++ b/src/core.c
@@ -299,6 +299,8 @@ void MwVaListApply(MwWidget handle, va_list va) {
}
void MwSetDefault(MwWidget handle) {
+ MwLLSetCursor(handle->lowlevel, &MwCursorDefault, &MwCursorDefaultMask);
+
MwSetText(handle, MwNbackground, MwDefaultBackground);
MwSetText(handle, MwNforeground, MwDefaultForeground);
}
diff --git a/src/cursor/default.c b/src/cursor/default.c
new file mode 100644
index 0000000..a32255e
--- /dev/null
+++ b/src/cursor/default.c
@@ -0,0 +1,44 @@
+/* $Id$ */
+#include
+
+/**
+ * Created by bitmaptobdf
+ *
+ * Copyright notice:
+ * These ""glyphs"" are unencumbered
+ */
+MwCursor MwCursorDefault = {
+ 8, 14, 0, -14, {128, /* #....... */
+ 192, /* ##...... */
+ 224, /* ###..... */
+ 240, /* ####.... */
+ 248, /* #####... */
+ 252, /* ######.. */
+ 254, /* #######. */
+ 255, /* ######## */
+ 248, /* #####... */
+ 216, /* ##.##... */
+ 140, /* #...##.. */
+ 12, /* ....##.. */
+ 6, /* .....##. */
+ 6, /* .....##. */
+ 0, 0}};
+MwCursor MwCursorDefaultMask = {
+ 10, 16, -1, -15, {
+ 768, /* ##........ */
+ 896, /* ###....... */
+ 960, /* ####...... */
+ 992, /* #####..... */
+ 1008, /* ######.... */
+ 1016, /* #######... */
+ 1020, /* ########.. */
+ 1022, /* #########. */
+ 1023, /* ########## */
+ 1023, /* ########## */
+ 1016, /* #######... */
+ 956, /* ###.####.. */
+ 828, /* ##..####.. */
+ 30, /* .....####. */
+ 30, /* .....####. */
+ 12 /* ......##.. */
+ }};
diff --git a/src/widget/menu.c b/src/widget/menu.c
index 8672810..40b24c3 100644
--- a/src/widget/menu.c
+++ b/src/widget/menu.c
@@ -106,9 +106,10 @@ static void draw(MwWidget handle) {
MwDrawRect(handle, &r, base);
BEGIN_MENU_LOOP;
- (void)in_area;
if(m->sub[i]->wsub != NULL) {
MwDrawFrame(handle, &r, base, 0);
+ } else if(in_area && handle->pressed) {
+ MwDrawFrame(handle, &r, base, 0);
}
MwDrawText(handle, &p, m->sub[i]->name + incr, 1, text);
diff --git a/tools/cursor.pl b/tools/cursor.pl
new file mode 100755
index 0000000..a793a0b
--- /dev/null
+++ b/tools/cursor.pl
@@ -0,0 +1,138 @@
+#!/usr/bin/env perl
+# $Id$
+my $font = $ARGV[0];
+my $name = $ARGV[1];
+my $out = $ARGV[2];
+my $char = "";
+my $bmp = 0;
+
+my $w = 0;
+my $h = 0;
+my $ln = 0;
+my $com = 0;
+my $nocom = 0;
+
+my $MAX = 16;
+
+if ($name) {
+ print("/* \$Id\$ */\n");
+ print("#include \n");
+ print("\n");
+}
+
+open(IN, "<", $font) or die;
+while (my $l = ) {
+ $l =~ s/\r?\n$//g;
+ if (!$name && ($l =~ /^STARTCHAR ("?)(.+)\1$/)) {
+ if (!($2 =~ /_mask$/)) {
+ print("$2\n");
+ }
+ }
+ elsif ($name && ($l =~ /^COPYRIGHT ("?)(.+)\1$/)) {
+ if (!$com) {
+ print("/**\n");
+ }
+ else {
+ print(" *\n");
+ }
+ print(" * Copyright notice:\n");
+ print(" * $2\n");
+ if (!$com) {
+ print(" */\n");
+ }
+ }
+ elsif ($name && ($l =~ /^COMMENT ("?)(.+)\1$/)) {
+ if (!$nocom) {
+ if (!$com) {
+ $com = 1;
+ print("/**\n");
+ }
+ print(" * $2\n");
+ }
+ }
+ elsif ($name && ($l =~ /^ENDPROPERTIES$/)) {
+ if ($com) {
+ print(" */\n");
+ $com = 0;
+ $nocom = 1;
+ }
+ }
+ elsif (
+ $name
+ && ( ($l =~ /^STARTCHAR ("?)\Q$name\E\1$/)
+ || ($l =~ /^STARTCHAR ("?)\Q${name}\E_(mask)\1$/))
+ )
+ {
+ my $suffix = "";
+ if ($2) {
+ $suffix = "Mask";
+ }
+ $char = $name;
+ print("MwCursor MwCursor$out$suffix = {\n");
+ }
+ elsif ($name
+ && $char
+ && ($l =~ /^BBX (\-?[0-9]+) (\-?[0-9]+) (\-?[0-9]+) (\-?[0-9]+)$/))
+ {
+ print(" $1, $2, $3, $4,\n");
+
+ $w = $1 + 0;
+ $h = $2 + 0;
+ }
+ elsif ($name && $char && ($l =~ /^BITMAP$/)) {
+ print(" {\n");
+ $bmp = 1;
+ $ln = 0;
+ }
+ elsif ($name && $char && ($l =~ /^ENDCHAR$/)) {
+ $bmp = 0;
+ $char = "";
+ for (my $i = 0 ; $i < ($MAX - $h) ; $i++) {
+ if ($i == ($MAX - $h - 1)) {
+ print(" 0\n");
+ }
+ else {
+ print(" 0,\n");
+ }
+ }
+ print(" }\n");
+ print("};\n");
+ }
+ elsif ($bmp) {
+ my $txt = "";
+
+ my $c = 0;
+ my $n = 0;
+ my $incr = 0;
+
+ my $num = 0;
+
+ while ($c < $w) {
+ if (($c % 8) == 0) {
+ $n = hex("0x" . substr($l, $incr, 2));
+ $incr += 2;
+ }
+
+ $num = $num << 1;
+ if ($n & (1 << 7)) {
+ $num = $num | 1;
+ $txt = $txt . "#";
+ }
+ else {
+ $num = $num | 0;
+ $txt = $txt . ".";
+ }
+
+ $n = $n << 1;
+ $c = $c + 1;
+ }
+ $ln = $ln + 1;
+ if ($ln == $MAX) {
+ print(" $num /* $txt */\n");
+ }
+ else {
+ print(" $num, /* $txt */\n");
+ }
+ }
+}
+close(IN);