|
@@ -0,0 +1,146 @@
|
|
|
|
+#include "raylib.h"
|
|
|
|
+
|
|
|
|
+#define RAYGUI_IMPLEMENTATION
|
|
|
|
+#include "../../raygui.h"
|
|
|
|
+
|
|
|
|
+#include "../../styles/dark/style_dark.h"
|
|
|
|
+
|
|
|
|
+static Vector2 window_position = { 10, 10 };
|
|
|
|
+static Vector2 window_size = { 200, 400 };
|
|
|
|
+static bool minimized = false;
|
|
|
|
+static bool moving = false;
|
|
|
|
+static bool resizing = false;
|
|
|
|
+static Vector2 scroll;
|
|
|
|
+
|
|
|
|
+static Vector2 window2_position = { 250, 10 };
|
|
|
|
+static Vector2 window2_size = { 200, 400 };
|
|
|
|
+static bool minimized2 = false;
|
|
|
|
+static bool moving2 = false;
|
|
|
|
+static bool resizing2 = false;
|
|
|
|
+static Vector2 scroll2;
|
|
|
|
+
|
|
|
|
+void GuiWindowFloating(Vector2 *position, Vector2 *size, bool *minimized, bool *moving, bool *resizing, void (*draw_content)(Vector2, Vector2), Vector2 content_size, Vector2 *scroll, const char* title) {
|
|
|
|
+ #if !defined(RAYGUI_WINDOWBOX_STATUSBAR_HEIGHT)
|
|
|
|
+ #define RAYGUI_WINDOWBOX_STATUSBAR_HEIGHT 24
|
|
|
|
+ #endif
|
|
|
|
+
|
|
|
|
+ #if !defined(RAYGUI_WINDOW_CLOSEBUTTON_SIZE)
|
|
|
|
+ #define RAYGUI_WINDOW_CLOSEBUTTON_SIZE 18
|
|
|
|
+ #endif
|
|
|
|
+
|
|
|
|
+ int close_title_size_delta_half = (RAYGUI_WINDOWBOX_STATUSBAR_HEIGHT - RAYGUI_WINDOW_CLOSEBUTTON_SIZE) / 2;
|
|
|
|
+
|
|
|
|
+ // window movement and resize input and collision check
|
|
|
|
+ if(IsMouseButtonPressed(MOUSE_LEFT_BUTTON) && !*moving && !*resizing) {
|
|
|
|
+ Vector2 mouse_position = GetMousePosition();
|
|
|
|
+
|
|
|
|
+ Rectangle title_collision_rect = { position->x, position->y, size->x - (RAYGUI_WINDOW_CLOSEBUTTON_SIZE + close_title_size_delta_half), RAYGUI_WINDOWBOX_STATUSBAR_HEIGHT };
|
|
|
|
+ Rectangle resize_collision_rect = { position->x + size->x - 20, position->y + size->y - 20, 20, 20 };
|
|
|
|
+
|
|
|
|
+ if(CheckCollisionPointRec(mouse_position, title_collision_rect)) {
|
|
|
|
+ *moving = true;
|
|
|
|
+ } else if(!*minimized && CheckCollisionPointRec(mouse_position, resize_collision_rect)) {
|
|
|
|
+ *resizing = true;
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ // window movement and resize update
|
|
|
|
+ if(*moving) {
|
|
|
|
+ Vector2 mouse_delta = GetMouseDelta();
|
|
|
|
+ position->x += mouse_delta.x;
|
|
|
|
+ position->y += mouse_delta.y;
|
|
|
|
+
|
|
|
|
+ if (IsMouseButtonReleased(MOUSE_LEFT_BUTTON)) {
|
|
|
|
+ *moving = false;
|
|
|
|
+
|
|
|
|
+ // clamp window position keep it inside the application area
|
|
|
|
+ if(position->x < 0) position->x = 0;
|
|
|
|
+ else if(position->x > GetScreenWidth() - size->x) position->x = GetScreenWidth() - size->x;
|
|
|
|
+ if(position->y < 0) position->y = 0;
|
|
|
|
+ else if(position->y > GetScreenHeight()) position->y = GetScreenHeight() - RAYGUI_WINDOWBOX_STATUSBAR_HEIGHT;
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ } else if(*resizing) {
|
|
|
|
+ Vector2 mouse_delta = GetMouseDelta();
|
|
|
|
+ size->x += mouse_delta.x;
|
|
|
|
+ size->y += mouse_delta.y;
|
|
|
|
+
|
|
|
|
+ // clamp window size to an arbitrary minimum value and the window size as the maximum
|
|
|
|
+ if(size->x < 100) size->x = 100;
|
|
|
|
+ else if(size->x > GetScreenWidth()) size->x = GetScreenWidth();
|
|
|
|
+ if(size->y < 100) size->y = 100;
|
|
|
|
+ else if(size->y > GetScreenHeight()) size->y = GetScreenHeight();
|
|
|
|
+
|
|
|
|
+ if (IsMouseButtonReleased(MOUSE_LEFT_BUTTON)) {
|
|
|
|
+ *resizing = false;
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ // window and content drawing with scissor and scroll area
|
|
|
|
+ if(*minimized) {
|
|
|
|
+ GuiStatusBar((Rectangle){ position->x, position->y, size->x, RAYGUI_WINDOWBOX_STATUSBAR_HEIGHT }, title);
|
|
|
|
+
|
|
|
|
+ if (GuiButton((Rectangle){ position->x + size->x - RAYGUI_WINDOW_CLOSEBUTTON_SIZE - close_title_size_delta_half,
|
|
|
|
+ position->y + close_title_size_delta_half,
|
|
|
|
+ RAYGUI_WINDOW_CLOSEBUTTON_SIZE,
|
|
|
|
+ RAYGUI_WINDOW_CLOSEBUTTON_SIZE },
|
|
|
|
+ "#120#")) {
|
|
|
|
+ *minimized = false;
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ } else {
|
|
|
|
+ *minimized = GuiWindowBox((Rectangle) { position->x, position->y, size->x, size->y }, title);
|
|
|
|
+
|
|
|
|
+ // scissor and draw content within a scroll panel
|
|
|
|
+ if(draw_content != NULL) {
|
|
|
|
+ Rectangle scissor = { 0 };
|
|
|
|
+ GuiScrollPanel((Rectangle) { position->x, position->y + RAYGUI_WINDOWBOX_STATUSBAR_HEIGHT, size->x, size->y - RAYGUI_WINDOWBOX_STATUSBAR_HEIGHT },
|
|
|
|
+ NULL,
|
|
|
|
+ (Rectangle) { position->x, position->y, content_size.x, content_size.y },
|
|
|
|
+ scroll,
|
|
|
|
+ &scissor);
|
|
|
|
+
|
|
|
|
+ bool require_scissor = size->x < content_size.x || size->y < content_size.y;
|
|
|
|
+
|
|
|
|
+ if(require_scissor) {
|
|
|
|
+ BeginScissorMode(scissor.x, scissor.y, scissor.width, scissor.height);
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ draw_content(*position, *scroll);
|
|
|
|
+
|
|
|
|
+ if(require_scissor) {
|
|
|
|
+ EndScissorMode();
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ // draw the resize button/icon
|
|
|
|
+ GuiDrawIcon(71, position->x + size->x - 20, position->y + size->y - 20, 1, WHITE);
|
|
|
|
+ }
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+static void DrawContent(Vector2 position, Vector2 scroll) {
|
|
|
|
+ GuiButton((Rectangle) { position.x + 20 + scroll.x, position.y + 50 + scroll.y, 100, 25 }, "Button 1");
|
|
|
|
+ GuiButton((Rectangle) { position.x + 20 + scroll.x, position.y + 100 + scroll.y, 100, 25 }, "Button 2");
|
|
|
|
+ GuiButton((Rectangle) { position.x + 20 + scroll.x, position.y + 150 + scroll.y, 100, 25 }, "Button 3");
|
|
|
|
+ GuiLabel((Rectangle) { position.x + 20 + scroll.x, position.y + 200 + scroll.y, 250, 25 }, "A Label");
|
|
|
|
+ GuiLabel((Rectangle) { position.x + 20 + scroll.x, position.y + 250 + scroll.y, 250, 25 }, "Another Label");
|
|
|
|
+ GuiLabel((Rectangle) { position.x + 20 + scroll.x, position.y + 300 + scroll.y, 250, 25 }, "Yet Another Label");
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+int main(void) {
|
|
|
|
+ InitWindow(960, 560, "raygui - floating window example");
|
|
|
|
+ SetTargetFPS(60);
|
|
|
|
+ GuiLoadStyleDark();
|
|
|
|
+
|
|
|
|
+ while(!WindowShouldClose()) {
|
|
|
|
+ BeginDrawing();
|
|
|
|
+ ClearBackground(DARKGREEN);
|
|
|
|
+ GuiWindowFloating(&window_position, &window_size, &minimized, &moving, &resizing, &DrawContent, (Vector2) { 140, 320 }, &scroll, "Movable & Scalable Window");
|
|
|
|
+ GuiWindowFloating(&window2_position, &window2_size, &minimized2, &moving2, &resizing2, &DrawContent, (Vector2) { 140, 320 }, &scroll2, "Another window");
|
|
|
|
+ EndDrawing();
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ CloseWindow();
|
|
|
|
+
|
|
|
|
+ return 0;
|
|
|
|
+}
|