401 lines
No EOL
9.3 KiB
HolyC
401 lines
No EOL
9.3 KiB
HolyC
extern class Widget;
|
|
extern class Window;
|
|
|
|
#define WIN_FLAGS_NULL 0x0
|
|
#define WIN_FLAGS_NO_REINDEX 0x1 // Wallpaper, taskbar, etc.
|
|
#define WIN_FLAGS_RESIZABLE 0x2
|
|
#define WIN_FLAGS_MOVABLE 0x4
|
|
#define WIN_FLAGS_ICON 0x8
|
|
#define WIN_FLAGS_TITLE_BAR 0x10
|
|
#define WIN_FLAGS_MIN_BUTTON 0x20
|
|
#define WIN_FLAGS_MAX_BUTTON 0x40
|
|
#define WIN_FLAGS_CLOSE_BUTTON 0x80
|
|
|
|
#define WIN_FLAGS_MINIMIZED 0x100
|
|
#define WIN_FLAGS_MAXIMIZED 0x200
|
|
#define WIN_FLAGS_HIDDEN 0x400
|
|
#define WIN_FLAGS_NOHILIGHT 0x800
|
|
|
|
#define WIN_FLAGS_SKIP 0x1000
|
|
#define WIN_FLAGS_NOFILL 0x2000
|
|
#define WIN_FLAGS_MENU 0x4000
|
|
|
|
#define WIN_FLAGS_MAX 0x10000
|
|
|
|
#define WIN_SIGNATURE 0x1596e3c1c62c34b929d75cded8c0
|
|
|
|
#define WIN_FLAGS_DEFAULT \
|
|
(WIN_FLAGS_RESIZABLE | WIN_FLAGS_MOVABLE | WIN_FLAGS_ICON | WIN_FLAGS_TITLE_BAR | WIN_FLAGS_MIN_BUTTON | WIN_FLAGS_MAX_BUTTON | WIN_FLAGS_CLOSE_BUTTON)
|
|
|
|
class @widget_callbacks
|
|
{
|
|
U0 (*change)(Widget* widget);
|
|
U0 (*clicked)(Widget* widget);
|
|
U0 (*repaint)(Widget* widget);
|
|
};
|
|
|
|
class @widget_origin
|
|
{
|
|
I64 x;
|
|
I64 y;
|
|
I64 width;
|
|
I64 height;
|
|
I64 mouse_x;
|
|
I64 mouse_y;
|
|
};
|
|
|
|
class Widget {
|
|
Bool change;
|
|
Bool disabled;
|
|
I64 id;
|
|
I64 type;
|
|
I64 x;
|
|
I64 y;
|
|
I64 width;
|
|
I64 height;
|
|
I64 opacity;
|
|
U64 flags;
|
|
U64 data;
|
|
U8* tag;
|
|
Widget* echo;
|
|
Window* parent_win;
|
|
Context2D* backing_store;
|
|
Context2D* pointer;
|
|
@widget_callbacks callback;
|
|
@widget_origin origin;
|
|
};
|
|
|
|
class @window_widgets_list
|
|
{
|
|
@window_widgets_list* prev;
|
|
@window_widgets_list* next;
|
|
Widget* widget;
|
|
};
|
|
|
|
class @window_origin
|
|
{
|
|
I64 x;
|
|
I64 y;
|
|
I64 width;
|
|
I64 height;
|
|
I64 mouse_x;
|
|
I64 mouse_y;
|
|
};
|
|
|
|
class @window_position
|
|
{
|
|
I64 x;
|
|
I64 y;
|
|
}
|
|
|
|
class @window_buttons
|
|
{
|
|
Bool minimize;
|
|
Bool maximize;
|
|
Bool close;
|
|
};
|
|
|
|
class @window_callbacks
|
|
{
|
|
U0 (*minimize)(Window* win);
|
|
U0 (*maximize)(Window* win);
|
|
U0 (*mouseat)(Window* win);
|
|
U0 (*keypress)(Window* win, I64 key);
|
|
U0 (*repaint)(Window* win);
|
|
U0 (*close)(Window* win);
|
|
};
|
|
|
|
class @window_mouse
|
|
{
|
|
I64 x;
|
|
I64 y;
|
|
Bool left;
|
|
Bool right;
|
|
};
|
|
|
|
class @window_event
|
|
{ // FIXME: Better name?
|
|
I64 x;
|
|
I64 y;
|
|
Bool left;
|
|
Bool right;
|
|
};
|
|
|
|
class Window {
|
|
U64 signature;
|
|
Bool alpha;
|
|
Bool refresh;
|
|
Bool repainting;
|
|
Bool explicit_repaint;
|
|
CTask* client;
|
|
I64 x;
|
|
I64 y;
|
|
I64 width;
|
|
I64 height;
|
|
I64 opacity;
|
|
U64 flags;
|
|
U8 title[512];
|
|
I64 title_bar_x;
|
|
I64 title_bar_width;
|
|
I64 min_width;
|
|
I64 min_height;
|
|
Context2D* icon;
|
|
Context2D* backing_store;
|
|
Context2D* pointer;
|
|
Context2D* render_ctx;
|
|
Context2D* resize_ctx;
|
|
Widget* mouse_down_widget;
|
|
Widget* focused_widget;
|
|
Widget* hovered_widget;
|
|
@window_buttons button;
|
|
@window_callbacks callback;
|
|
@window_origin origin;
|
|
@window_mouse mouse;
|
|
@window_event left_btn_down; // FIXME: put these in a Window.event.xxx class?
|
|
@window_event left_btn_up;
|
|
@window_event right_btn_down;
|
|
@window_event right_btn_up;
|
|
@window_widgets_list* widget;
|
|
};
|
|
|
|
class @gui_widget
|
|
{
|
|
Bool (*IsHovered)(Window* win, Widget* widget);
|
|
U0 (*SetCallback)(Widget* widget, U8* name, U64 callback);
|
|
U0 (*SetEcho)(Widget* widget, Widget* echo);
|
|
U0 (*SetFont)(Widget* widget, U8* font_name);
|
|
U0 (*SetMousePointer)(Widget* widget, Context2D* pointer);
|
|
U0 (*ClearMousePointer)(Widget* widget);
|
|
U0 (*SetOpacity)(Widget* widget, I64 opacity);
|
|
U0 (*SetText)(Widget* widget, U8* text);
|
|
};
|
|
|
|
class @gui_window
|
|
{
|
|
U0 (*Center)(Window* win, Bool horz = TRUE, Bool vert = TRUE);
|
|
U0 (*DisableAlphaChannel)(Window* win);
|
|
U0 (*EnableAlphaChannel)(Window* win);
|
|
U0 (*Hide)(Window* win);
|
|
Bool (*IsHovered)(Window* win);
|
|
Bool (*IsVisible)(Window* win);
|
|
U0 (*SetCallback)(Window* win, U8* name, U64 callback);
|
|
U0 (*SetFocus)(Window* win);
|
|
U0 (*SetIcon)(Window* win, Context2D* icon);
|
|
U0 (*SetMousePointer)(Window* win, Context2D* pointer);
|
|
U0 (*ClearMousePointer)(Window* win);
|
|
U0 (*SetOpacity)(Window* win, I64 opacity);
|
|
U0 (*SetTitle)(Window* win, U8* text);
|
|
U0 (*SetPosition)(Window* win, I64 x, I64 y);
|
|
U0 (*SetZIndex)(Window* win, I64 index);
|
|
U0 (*Show)(Window* win);
|
|
U0 (*Refresh)(Window* win);
|
|
};
|
|
|
|
class @gui
|
|
{
|
|
@gui_widget Widget;
|
|
@gui_window Window;
|
|
U0 (*App)();
|
|
Widget* (*InitWidget)(Widget* widget, Window* win, I64 type, I64 x, I64 y,
|
|
I64 width, I64 height);
|
|
Widget* (*CreateWidget)(Window* win, I64 type, I64 x, I64 y, I64 width,
|
|
I64 height);
|
|
};
|
|
|
|
@gui Gui;
|
|
|
|
I64 @gui_app_header_size;
|
|
U8* @gui_app_header_data = FileRead("M:/Include/Gui.HC", &@gui_app_header_size);
|
|
|
|
U0 @gui_app()
|
|
{
|
|
CDoc* @gui_app_header_doc = DocNew;
|
|
DocLoad(@gui_app_header_doc, @gui_app_header_data, @gui_app_header_size);
|
|
ExeDoc(@gui_app_header_doc);
|
|
}
|
|
|
|
Bool @gui_window_flag_is_set(Window* win, U64 flag)
|
|
{
|
|
if (!win)
|
|
return FALSE;
|
|
if (win->flags & flag == flag)
|
|
return TRUE;
|
|
return FALSE;
|
|
}
|
|
|
|
Bool @gui_window_is_hovered(Window* win)
|
|
{
|
|
if (Mouse.x > win->x && Mouse.x < win->x + win->width && Mouse.y > win->y && Mouse.y < win->y + win->height)
|
|
return TRUE;
|
|
return FALSE;
|
|
}
|
|
|
|
Bool @gui_window_is_visible(Window* win)
|
|
{
|
|
if (!win)
|
|
return NULL;
|
|
return !@gui_window_flag_is_set(win, WIN_FLAGS_HIDDEN);
|
|
}
|
|
|
|
U0 @gui_widget_destroy(Widget* widget)
|
|
{
|
|
Window* win = widget->parent_win;
|
|
@window_widgets_list* widgets = win->widget;
|
|
@window_widgets_list* prev;
|
|
@window_widgets_list* next;
|
|
while (widgets) {
|
|
if (widgets->widget == widget) {
|
|
prev = widgets->prev;
|
|
next = widgets->next;
|
|
if (prev)
|
|
prev->next = next;
|
|
if (next)
|
|
next->prev = prev;
|
|
// FIXME: Free widget and child data
|
|
widget->type = NULL;
|
|
}
|
|
widgets = widgets->next;
|
|
}
|
|
}
|
|
|
|
U0 @gui_widget_repaint(Window* win, Widget* widget, I64 type) { }
|
|
|
|
U0 @gui_window_repaint(Window* win, I64 type)
|
|
{
|
|
@system_log(Fs, "Repainting window 0x%08x [%s]", win, win->title);
|
|
}
|
|
|
|
U0 @gui_window_center(Window* win, Bool horz = TRUE, Bool vert = TRUE)
|
|
{
|
|
if (!win)
|
|
return;
|
|
I64 x = win->x;
|
|
I64 y = win->y;
|
|
if (horz)
|
|
x = (Display.Width() / 2) - (win->width / 2);
|
|
if (vert)
|
|
y = (Display.Height() / 2) - (win->height / 2);
|
|
win->x = x;
|
|
win->y = y;
|
|
}
|
|
|
|
U0 @gui_window_set_position(Window* win, I64 x, I64 y)
|
|
{
|
|
if (!win)
|
|
return;
|
|
win->x = x;
|
|
win->y = y;
|
|
}
|
|
|
|
U0 @gui_window_set_icon(Window* win, Context2D* icon)
|
|
{
|
|
if (!win || !icon)
|
|
return;
|
|
Bool refresh = FALSE;
|
|
if (win->icon != icon)
|
|
refresh = TRUE;
|
|
win->icon = icon;
|
|
if (refresh)
|
|
Gui.Window.Refresh(win);
|
|
}
|
|
|
|
U0 @gui_window_set_mouse_pointer(Window* win, Context2D* pointer)
|
|
{
|
|
if (!win)
|
|
return;
|
|
win->pointer = pointer;
|
|
}
|
|
|
|
U0 @gui_window_clear_mouse_pointer(Window* win)
|
|
{
|
|
if (!win)
|
|
return;
|
|
win->pointer = NULL;
|
|
}
|
|
|
|
U0 @gui_window_set_opacity(Window* win, I64 opacity)
|
|
{
|
|
if (!win)
|
|
return;
|
|
Bool refresh = FALSE;
|
|
if (win->opacity != opacity)
|
|
refresh = TRUE;
|
|
win->opacity = ClampI64(opacity, 0, 255);
|
|
if (refresh)
|
|
Gui.Window.Refresh(win);
|
|
}
|
|
|
|
U0 @gui_window_set_title(Window* win, U8* text)
|
|
{
|
|
if (!win || !text)
|
|
return;
|
|
if (!StrLen(text))
|
|
return;
|
|
if (StrLen(text) > 511) {
|
|
MemCpy(&win->title, text, 512);
|
|
win->title[511] = NULL;
|
|
return;
|
|
}
|
|
StrCpy(&win->title, text);
|
|
Gui.Window.Refresh(win);
|
|
}
|
|
|
|
U0 @gui_window_callback_close(Window* win) { }
|
|
|
|
U0 @gui_window_callback_maximize(Window* win)
|
|
{
|
|
win->flags |= WIN_FLAGS_MAXIMIZED;
|
|
}
|
|
|
|
U0 @gui_window_callback_minimize(Window* win)
|
|
{
|
|
win->flags |= WIN_FLAGS_MINIMIZED;
|
|
}
|
|
|
|
U0 @gui_window_disable_alpha_channel(Window* win) { win->alpha = FALSE; }
|
|
|
|
U0 @gui_window_enable_alpha_channel(Window* win) { win->alpha = TRUE; }
|
|
|
|
U0 @gui_window_hide(Window* win) { win->flags |= WIN_FLAGS_HIDDEN; }
|
|
|
|
U0 @gui_window_show(Window* win)
|
|
{
|
|
win->flags &= ~WIN_FLAGS_HIDDEN;
|
|
win->flags &= ~WIN_FLAGS_MINIMIZED;
|
|
}
|
|
|
|
U0 @gui_window_set_callback(Window* win, U8* name, U64 callback)
|
|
{
|
|
if (!win || !name || !callback)
|
|
return;
|
|
if (!StrCmp(name, "minimize"))
|
|
win->callback.minimize = callback;
|
|
if (!StrCmp(name, "maximize"))
|
|
win->callback.maximize = callback;
|
|
if (!StrCmp(name, "mouseat"))
|
|
win->callback.mouseat = callback;
|
|
if (!StrCmp(name, "keypress"))
|
|
win->callback.keypress = callback;
|
|
if (!StrCmp(name, "repaint"))
|
|
win->callback.repaint = callback;
|
|
if (!StrCmp(name, "close"))
|
|
win->callback.close = callback;
|
|
}
|
|
|
|
Gui.App = &@gui_app;
|
|
Gui.Window.Center = &@gui_window_center;
|
|
Gui.Window.DisableAlphaChannel = &@gui_window_disable_alpha_channel;
|
|
Gui.Window.EnableAlphaChannel = &@gui_window_enable_alpha_channel;
|
|
Gui.Window.Hide = &@gui_window_hide;
|
|
Gui.Window.IsHovered = &@gui_window_is_hovered;
|
|
Gui.Window.IsVisible = &@gui_window_is_visible;
|
|
Gui.Window.SetCallback = &@gui_window_set_callback;
|
|
Gui.Window.SetIcon = &@gui_window_set_icon;
|
|
Gui.Window.SetMousePointer = &@gui_window_set_mouse_pointer;
|
|
Gui.Window.ClearMousePointer = &@gui_window_clear_mouse_pointer;
|
|
Gui.Window.SetOpacity = &@gui_window_set_opacity;
|
|
Gui.Window.SetTitle = &@gui_window_set_title;
|
|
Gui.Window.SetPosition = &@gui_window_set_position;
|
|
Gui.Window.Show = &@gui_window_show;
|
|
|
|
"gui "; |