diff --git a/GNUmakefile b/GNUmakefile index f718b73e..17eac077 100644 --- a/GNUmakefile +++ b/GNUmakefile @@ -15,11 +15,14 @@ ifndef OS UNAME = $(shell uname -s) ifeq ($(UNAME),Darwin) OS = darwin + else ifeq ($(UNAME),Haiku) + OS = haiku else OS = unix endif endif +# TODO this is wrong for Haiku ifndef ARCH UNAME = $(shell uname -m) ifeq ($(UNAME),x86_64) diff --git a/haiku/GNUmakeinc.mk b/haiku/GNUmakeinc.mk new file mode 100644 index 00000000..0647c623 --- /dev/null +++ b/haiku/GNUmakeinc.mk @@ -0,0 +1,21 @@ +# 22 april 2015 + +CFILES += \ + +HFILES += \ + haiku/uipriv_haiku.h + +# thanks ebassi in irc.gimp.net/#gtk+ +CFLAGS += \ + -D_UI_EXTERN='__attribute__((visibility("default"))) extern' \ + -fvisibility=hidden \ + -fPIC + +LDFLAGS += \ + -fvisibility=hidden \ + -fPIC \ + -lbe -lm + +# flags for warning on undefined symbols +LDFLAGS += \ + -Wl,--no-undefined -Wl,--no-allow-shlib-undefined diff --git a/haiku/GNUosspecific.mk b/haiku/GNUosspecific.mk new file mode 100644 index 00000000..0e2a497c --- /dev/null +++ b/haiku/GNUosspecific.mk @@ -0,0 +1,4 @@ +# 16 october 2015 + +EXESUFFIX = +LIBSUFFIX = .so diff --git a/ui_haiku.hpp b/ui_haiku.hpp new file mode 100644 index 00000000..08dcbfe6 --- /dev/null +++ b/ui_haiku.hpp @@ -0,0 +1,65 @@ +// 17 november 2015 + +/* +This file assumes that you have included the various Haiku header files and "ui.h" beforehand. It provides API-specific functions for interfacing with foreign controls in Haiku. +*/ + +#ifndef __LIBUI_UI_HAIKU_HPP__ +#define __LIBUI_UI_WAIKU_HPP__ + +#ifndef __cplusplus +#error Sorry; ui_haiku.hpp can currently only be used from C++ code. +#endif + +extern "C" { + +typedef struct uiHaikuControl uiHaikuControl; +struct uiHaikuControl { + uiControl c; +}; +_UI_EXTERN uintmax_t uiHaikuControlType(void); +#define uiHaikuControl(this) ((uiHaikuControl *) uiIsA((this), uiHaikuControlType(), 1)) + +// TODO document +#define uiHaikuDefineControlWithOnDestroy(type, typefn, handlefield, onDestroy) \ + static uintmax_t _ ## type ## Type = 0; \ + uintmax_t typefn(void) \ + { \ + if (_ ## type ## Type == 0) \ + _ ## type ## Type = uiRegisterType(#type, uiDarwinControlType(), sizeof (type)); \ + return _ ## type ## Type; \ + } \ + static void _ ## type ## CommitDestroy(uiControl *c) \ + { \ + type *hthis = type(c); \ + onDestroy; \ + delete hthis->handlefield; \ + } \ + static uintptr_t _ ## type ## Handle(uiControl *c) \ + { \ + return (uintptr_t) (type(c)->handlefield); \ + } \ + static void _ ## type ## ContainerUpdateState(uiControl *c) \ + { \ + /* do nothing */ \ + } + +#define uiHaikuDefineControl(type, typefn, handlefield) \ + uiHaikuDefineControlWithOnDestroy(type, typefn, handlefield, (void) hthis;) + +#define uiHaikuFinishNewControl(variable, type) \ + uiControl(variable)->CommitDestroy = _ ## type ## CommitDestroy; \ + uiControl(variable)->Handle = _ ## type ## Handle; \ + uiControl(variable)->ContainerUpdateState = _ ## type ## ContainerUpdateState; \ + uiHaikuFinishControl(uiControl(variable)); + +// This is a function used to set up a control. +// Don't call it directly; use uiHaikuFinishNewControl() instead. +_UI_EXTERN void uiHaikuFinishControl(uiControl *c); + +// uiHaikuStrdupText() takes the given string and produces a copy of it suitable for being freed by uiFreeText(). +_UI_EXTERN char *uiHaikuStrdupText(const char *); + +} + +#endif diff --git a/ui_unix.h b/ui_unix.h index 070e6a39..f41a1301 100644 --- a/ui_unix.h +++ b/ui_unix.h @@ -56,7 +56,7 @@ _UI_EXTERN uintmax_t uiUnixControlType(void); _UI_EXTERN void uiUnixFinishControl(uiControl *c); // uiUnixStrdupText() takes the given string and produces a copy of it suitable for being freed by uiFreeText(). -extern char *uiUnixStrdupText(const char *); +_UI_EXTERN char *uiUnixStrdupText(const char *); #ifdef __cplusplus }