From 01835cbe81adff60fae1da3023340ee168b722e7 Mon Sep 17 00:00:00 2001 From: Ray San Date: Wed, 4 Apr 2018 14:15:21 +0200 Subject: [PATCH] Multiple tool improvements - Support loading tracemap images for reference (and corresponding controls) - Support linked anchors movement (and relink) - Hide/Unhide selected anchor-controls - New fancy help menu --- tools/rGuiLayout/{ => external}/easings.h | 0 tools/rGuiLayout/rguilayout.c | 339 ++++++++++++++++------ tools/rGuiLayout/test_layout.c | 96 ------ tools/rGuiLayout/test_layout.png | Bin 21602 -> 0 bytes tools/rGuiLayout/test_layout.rgl | Bin 572 -> 0 bytes tools/rGuiLayout/test_layout.rlyt | 38 --- tools/rGuiLayout/tracemap_menus.png | Bin 0 -> 6372 bytes tools/rGuiLayout/tracemap_rfxgen.png | Bin 0 -> 21233 bytes 8 files changed, 252 insertions(+), 221 deletions(-) rename tools/rGuiLayout/{ => external}/easings.h (100%) delete mode 100644 tools/rGuiLayout/test_layout.c delete mode 100644 tools/rGuiLayout/test_layout.png delete mode 100644 tools/rGuiLayout/test_layout.rgl delete mode 100644 tools/rGuiLayout/test_layout.rlyt create mode 100644 tools/rGuiLayout/tracemap_menus.png create mode 100644 tools/rGuiLayout/tracemap_rfxgen.png diff --git a/tools/rGuiLayout/easings.h b/tools/rGuiLayout/external/easings.h similarity index 100% rename from tools/rGuiLayout/easings.h rename to tools/rGuiLayout/external/easings.h diff --git a/tools/rGuiLayout/rguilayout.c b/tools/rGuiLayout/rguilayout.c index 06c8ce6..6747119 100644 --- a/tools/rGuiLayout/rguilayout.c +++ b/tools/rGuiLayout/rguilayout.c @@ -15,7 +15,7 @@ #define RAYGUI_STYLE_SAVE_LOAD #include "raygui.h" -#include "easings.h" +#include "external/easings.h" #include "external/tinyfiledialogs.h" // Open/Save file dialogs #include @@ -61,6 +61,7 @@ typedef struct { int x; int y; bool enabled; + bool hidding; } AnchorPoint; // Gui control type @@ -123,9 +124,16 @@ int main() bool anchorLinkMode = false; int selectedAnchor = -1; int linkedAnchor = -1; + + AnchorPoint auxAnchor = { 9, 0, 0, 0}; + bool anchorNewPos = false; bool lockMode = false; - bool helpMode = false; + + int helpPosX = -300; + int helpCounter = 0; + int startPosXHelp = -300; + int deltaPosXHelp = 0; int fileCount = 0; char **droppedFiles = { 0 }; @@ -154,15 +162,15 @@ int main() // List view required variables Rectangle listViewControls = { -200, 0, 140, 500 }; - int counterListViewControls = 0; - int startPosXListViewControls = -200; - int deltaPosXListViewControls = 0; + Rectangle listViewControlsCounter = { GetScreenWidth() + 140, 0, 140, 500 }; int counterListViewControlsCounter = 0; int startPosXListViewControlsCounter = GetScreenWidth() + 140; int deltaPosXListViewControlsCounter = 0; + // ToggleGroup, ComboBox, DropdownBox use this data const char *list[3] = { "ONE", "TWO", "THREE" }; + const char *guiControls[18] = { "LABEL", @@ -205,7 +213,12 @@ int main() }; Texture2D texture = LoadTexture("icons.png"); - Texture2D rfxgenLayout = LoadTexture("screenshot001.png"); + Texture2D tracemap = { 0 }; + Rectangle tracemapRec = { 0 }; + bool tracemapEditMode = false; + float tracemapFade = 0.5f; + Vector2 panOffset = { 0 }; + Vector2 prevPosition = { tracemapRec.x, tracemapRec.y }; // Initialize anchor points to default values for (int i = 0; i < MAX_ANCHOR_POINTS; i++) @@ -214,6 +227,7 @@ int main() anchors[i].x = 0; anchors[i].y = 0; anchors[i].enabled = false; + anchors[i].hidding = false; } anchors[0].enabled = true; // Enable anchors parent (0, 0) @@ -247,34 +261,35 @@ int main() if (CheckCollisionPointRec(GetMousePosition(), listViewControls)) controlCollision = true; else if (CheckCollisionPointRec(GetMousePosition(), listViewControlsCounter)) controlCollision = true; - /* + // Toggle on the controlListView if (IsKeyPressed(KEY_TAB)) { - startPosXListViewControls = listViewControls.x; - deltaPosXListViewControls = 0 - startPosXListViewControls; - counterListViewControls = 0; + startPosXHelp = helpPosX; + deltaPosXHelp = 0 - startPosXHelp; + helpCounter = 0; } if (IsKeyDown(KEY_TAB)) { - counterListViewControls++; - if (counterListViewControls >= 60) counterListViewControls = 60; - listViewControls.x = (int)EaseCubicInOut(counterListViewControls, startPosXListViewControls, deltaPosXListViewControls, 60); + helpCounter++; + if (helpCounter >= 60) helpCounter = 60; + helpPosX = (int)EaseCubicInOut(helpCounter, startPosXHelp, deltaPosXHelp, 60); } else if (IsKeyReleased(KEY_TAB)) { - startPosXListViewControls = listViewControls.x; - deltaPosXListViewControls = -200 - startPosXListViewControls; - counterListViewControls = 0; + startPosXHelp = helpPosX; + deltaPosXHelp = -300 - startPosXHelp; + helpCounter = 0; } else { - counterListViewControls++; - if (counterListViewControls >= 60) counterListViewControls = 60; - listViewControls.x = (int)EaseCubicInOut(counterListViewControls, startPosXListViewControls, deltaPosXListViewControls, 60); + helpCounter++; + if (helpCounter >= 60) helpCounter = 60; + helpPosX = (int)EaseCubicInOut(helpCounter, startPosXHelp, deltaPosXHelp, 60); } + /* // Toggle on the controlListViewCounter if (IsKeyPressed(KEY_W)) { @@ -303,7 +318,7 @@ int main() } */ - if (IsMouseButtonPressed(MOUSE_LEFT_BUTTON) && (selectedControl == -1) && !controlCollision && !anchorMode) + if (IsMouseButtonPressed(MOUSE_LEFT_BUTTON) && (selectedControl == -1) && !controlCollision && !anchorMode && !tracemapEditMode) { // Add new control (button) layout[controlsCounter].id = controlsCounter; @@ -339,13 +354,13 @@ int main() // Check selected control (on mouse hover) for (int i = 0; i < controlsCounter; i++) { - if (controlDrag || lockMode) break; - if ((layout[i].type == WINDOWBOX) && (CheckCollisionPointRec(GetMousePosition(), (Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, 24 }))) + if (controlDrag || lockMode || tracemapEditMode) break; + if ((layout[i].type == WINDOWBOX) && (!layout[i].ap->hidding) && (CheckCollisionPointRec(GetMousePosition(), (Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, 24 }))) { selectedControl = i; break; } - else if (CheckCollisionPointRec(GetMousePosition(), (Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }) && layout[i].type != WINDOWBOX) + else if ((!layout[i].ap->hidding) && (CheckCollisionPointRec(GetMousePosition(), (Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }) && layout[i].type != WINDOWBOX)) { selectedControl = i; break; @@ -585,15 +600,10 @@ int main() textEditMode = true; saveControlSelected = selectedControl; } - - if (IsKeyPressed(KEY_H) && !textEditMode) helpMode = !helpMode; - + // Selected control lock logic - if (lockMode) - { - selectedControl = saveControlSelected; - } - + if (lockMode) selectedControl = saveControlSelected; + if (IsKeyPressed(KEY_SPACE) && !textEditMode && (selectedControl != -1) && !lockMode && !anchorMode) { lockMode = true; @@ -658,17 +668,50 @@ int main() anchors[selectedAnchor].x = 0; anchors[selectedAnchor].y = 0; anchors[selectedAnchor].enabled = false; + anchors[selectedAnchor].hidding = false; anchorMode = false; } // Allows to drag an anchor without losing collision - if (IsMouseButtonPressed(MOUSE_LEFT_BUTTON)) controlDrag = true; + if (IsMouseButtonPressed(MOUSE_LEFT_BUTTON) && IsKeyDown(KEY_A)) + { + controlDrag = true; + anchorNewPos = true; + + for (int i = 0; i < controlsCounter; i++) + { + if (layout[i].ap->id == selectedAnchor) + { + layout[i].rec.x += layout[i].ap->x; + layout[i].rec.y += layout[i].ap->y; + layout[i].ap = &auxAnchor; + } + } + } + else if (IsMouseButtonPressed(MOUSE_LEFT_BUTTON)) controlDrag = true; if (IsMouseButtonReleased(MOUSE_LEFT_BUTTON)) - { + { + if (anchorNewPos) + { + for (int i = 0; i < controlsCounter; i++) + { + if (layout[i].ap->id == 9) + { + layout[i].rec.x += layout[i].ap->x; + layout[i].rec.y += layout[i].ap->y; + layout[i].ap = &anchors[selectedAnchor]; + layout[i].rec.x -= anchors[selectedAnchor].x; + layout[i].rec.y -= anchors[selectedAnchor].y; + } + } + + anchorNewPos = false; + } controlDrag = false; selectedAnchor = -1; anchorMode = false; + } // Moves the anchor to the mouse position @@ -700,6 +743,11 @@ int main() anchorLinkMode = false; anchorMode = false; } + + if (IsKeyPressed(KEY_H)) + { + anchors[selectedAnchor].hidding = !anchors[selectedAnchor].hidding; + } } } @@ -758,6 +806,16 @@ int main() if (IsFileExtension(name, ".rgl")) LoadLayoutRGL(name); else if (IsFileExtension(name, ".rgs")) GuiLoadStyle(name); + else if (IsFileExtension(name, ".png")) + { + if (tracemap.id > 0) UnloadTexture(tracemap); + tracemap = LoadTexture(name); + + SetTextureFilter(tracemap, FILTER_BILINEAR); + + tracemapRec.width = tracemap.width; + tracemapRec.height = tracemap.height; + } ClearDroppedFiles(); } @@ -802,6 +860,72 @@ int main() } if (IsKeyDown(KEY_LEFT_CONTROL) && IsKeyPressed(KEY_ENTER)) GenerateLayoutCode("test_layout.c"); + + // Tracemap texture control logic + if (tracemap.id > 0) + { + // Toggles Texture editting mode between true or false + if (IsKeyDown(KEY_LEFT_CONTROL) && IsKeyPressed(KEY_T)) tracemapEditMode = !tracemapEditMode; + + if (tracemapEditMode) + { + int offsetX = mouseX%GRID_LINE_SPACING; + int offsetY = mouseY%GRID_LINE_SPACING; + + // Moves the texture with the mouse + if (IsMouseButtonPressed(MOUSE_LEFT_BUTTON)) panOffset = (Vector2){ mouseX, mouseY }; + + if (IsMouseButtonDown(MOUSE_LEFT_BUTTON)) + { + if (snapMode) + { + if (offsetX >= GRID_LINE_SPACING/2) mouseX += (GRID_LINE_SPACING - offsetX); + else mouseX -= offsetX; + + if (offsetY >= GRID_LINE_SPACING/2) mouseY += (GRID_LINE_SPACING - offsetY); + else mouseY -= offsetY; + } + + tracemapRec.x = prevPosition.x + (mouseX - panOffset.x); + tracemapRec.y = prevPosition.y + (mouseY - panOffset.y); + } + + if (IsMouseButtonReleased(MOUSE_LEFT_BUTTON)) prevPosition = (Vector2){ tracemapRec.x, tracemapRec.y }; + + // Moves and scales the texture with snap. + if (IsKeyDown(KEY_LEFT_CONTROL)) + { + tracemapRec.height -= GetMouseWheelMove(); + tracemapRec.width -= GetMouseWheelMove(); + } + else + { + tracemapRec.height -= 10*GetMouseWheelMove(); + tracemapRec.width -= 10*GetMouseWheelMove(); + + } + + tracemap.height = tracemapRec.height; + tracemap.width = tracemapRec.width; + + // Change texture fade + if (IsKeyDown(KEY_LEFT)) tracemapFade-= 0.01f; + else if (IsKeyDown(KEY_RIGHT)) tracemapFade+=0.01f; + + if (tracemapFade < 0) tracemapFade = 0; + else if (tracemapFade > 1) tracemapFade = 1; + + // Deletes the texture and resets it + if (IsKeyPressed(KEY_DELETE)) + { + UnloadTexture(tracemap); + tracemap.id = 0; + tracemapEditMode = false; + tracemapRec.x = 0; + tracemapRec.y = 0; + } + } + } //---------------------------------------------------------------------------------- // Draw @@ -812,41 +936,45 @@ int main() if (showGrid) DrawGrid2D(GetScreenWidth()/13, GetScreenHeight()/13); - DrawTexture(rfxgenLayout, 100, 50, Fade(WHITE, 0.6f)); + if (tracemap.id > 0) DrawTexture(tracemap, tracemapRec.x, tracemapRec.y, Fade(WHITE, tracemapFade)); for (int i = 0; i < controlsCounter; i++) { // Draws the Controls when placed on the grid. - switch (layout[i].type) + if (!layout[i].ap->hidding) { - case LABEL: GuiLabel((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, layout[i].text); break; - case BUTTON: GuiButton((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, layout[i].text); break; - case IMAGEBUTTON: GuiImageButtonEx((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, texture, (Rectangle){ 0, 0, texture.width/3, texture.height/6 }, layout[i].text); break; - case TOGGLE: GuiToggleButton((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, layout[i].text, false); break; - case TOGGLEGROUP: GuiToggleGroup((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, list, 3, 1); break; - case SLIDER: GuiSlider((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, 40, 0, 100); break; - case SLIDERBAR: GuiSliderBar((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, 40, 0, 100); break; - case PROGRESSBAR: GuiProgressBar((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, 40, 0, 100); break; - case SPINNER: GuiSpinner((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, 40, 0, 100); break; - case COMBOBOX: GuiComboBox((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, list, 3, 1); break; - case CHECKBOX: GuiCheckBox((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, false); break; - case TEXTBOX: GuiTextBox((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, layout[i].text, 32); break; - case GROUPBOX: GuiGroupBox((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, layout[i].text); break; - case WINDOWBOX: GuiWindowBox((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, layout[i].text); break; - case DUMMYREC: GuiDummyRec((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, layout[i].text); break; - case STATUSBAR: GuiStatusBar((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, layout[i].text, 15); break; - case LISTVIEW: GuiListView((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, guiControls, 14, 1); break; - case COLORPICKER: GuiColorPicker((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, RED); break; - default: break; + switch (layout[i].type) + { + case LABEL: GuiLabel((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, layout[i].text); break; + case BUTTON: GuiButton((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, layout[i].text); break; + case IMAGEBUTTON: GuiImageButtonEx((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, texture, (Rectangle){ 0, 0, texture.width/3, texture.height/6 }, layout[i].text); break; + case TOGGLE: GuiToggleButton((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, layout[i].text, false); break; + case TOGGLEGROUP: GuiToggleGroup((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, list, 3, 1); break; + case SLIDER: GuiSlider((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, 40, 0, 100); break; + case SLIDERBAR: GuiSliderBar((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, 40, 0, 100); break; + case PROGRESSBAR: GuiProgressBar((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, 40, 0, 100); break; + case SPINNER: GuiSpinner((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, 40, 0, 100); break; + case COMBOBOX: GuiComboBox((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, list, 3, 1); break; + case CHECKBOX: GuiCheckBox((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, false); break; + case TEXTBOX: GuiTextBox((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, layout[i].text, 32); break; + case GROUPBOX: GuiGroupBox((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, layout[i].text); break; + case WINDOWBOX: GuiWindowBox((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, layout[i].text); break; + case DUMMYREC: GuiDummyRec((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, layout[i].text); break; + case STATUSBAR: GuiStatusBar((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, layout[i].text, 15); break; + case LISTVIEW: GuiListView((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, guiControls, 14, 1); break; + case COLORPICKER: GuiColorPicker((Rectangle){ layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, layout[i].rec.width, layout[i].rec.height }, RED); break; + default: break; + } + + if ((layout[i].ap->id == selectedAnchor) && (layout[i].ap->id > 0)) DrawLine(layout[i].ap->x, layout[i].ap->y, layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, RED); } - - if ((layout[i].ap->id == selectedAnchor) && (layout[i].ap->id > 0)) DrawLine(layout[i].ap->x, layout[i].ap->y, layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, RED); + else if ((layout[i].ap->id == selectedAnchor) && (layout[i].ap->id > 0)) DrawLine(layout[i].ap->x, layout[i].ap->y, layout[i].ap->x + layout[i].rec.x, layout[i].ap->y + layout[i].rec.y, BLUE); // Draw Control anchor information // DrawText(FormatText("Id: %i | X: %i | Y: %i | Enabled: %i", layout[0].ap->id, layout[0].ap->x, layout[0].ap->y, layout[0].ap->enabled), 100, 100, style[DEFAULT_TEXT_SIZE], RED); } // Draws the defaultRec[selectedType] of the control selected - if (selectedControl == -1 && !anchorMode) + if (selectedControl == -1 && !anchorMode && !tracemapEditMode) { switch (selectedTypeDraw) { @@ -871,6 +999,12 @@ int main() default: break; } } + + // Draw the tracemap controler + if (tracemapEditMode) + { + DrawRectangleLines(tracemapRec.x, tracemapRec.y, tracemapRec.width, tracemapRec.height, RED); + } /* // Draw the list of controls @@ -885,16 +1019,48 @@ int main() // Draw the anchorPoints for (int i = 1; i < MAX_ANCHOR_POINTS; i++) { - if (anchors[i].id == selectedAnchor) DrawCircle(anchors[i].x, anchors[i].y, ANCHOR_RADIUS, Fade(RED, 0.5f)); - else DrawCircleLines(anchors[i].x, anchors[i].y, ANCHOR_RADIUS, Fade(RED, 0.5f)); - DrawRectangle(anchors[i].x - ANCHOR_RADIUS - 5, anchors[i].y, ANCHOR_RADIUS*2 + 10, 1, RED); - DrawRectangle(anchors[i].x, anchors[i].y - ANCHOR_RADIUS - 5, 1, ANCHOR_RADIUS*2 + 10, RED); + if (anchors[i].id == selectedAnchor && anchorNewPos) + { + // Draw the anchor that is currently moving + DrawCircle(anchors[i].x, anchors[i].y, ANCHOR_RADIUS, Fade(ORANGE, 0.5f)); + DrawRectangle(anchors[i].x - ANCHOR_RADIUS - 5, anchors[i].y, ANCHOR_RADIUS*2 + 10, 1, ORANGE); + DrawRectangle(anchors[i].x, anchors[i].y - ANCHOR_RADIUS - 5, 1, ANCHOR_RADIUS*2 + 10, ORANGE); + } + else if (anchors[i].hidding && anchors[i].id == selectedAnchor) + { + // Draw idle anchor + DrawCircle(anchors[i].x, anchors[i].y, ANCHOR_RADIUS, Fade(BLUE, 0.5f)); + DrawRectangle(anchors[i].x - ANCHOR_RADIUS - 5, anchors[i].y, ANCHOR_RADIUS*2 + 10, 1, BLUE); + DrawRectangle(anchors[i].x, anchors[i].y - ANCHOR_RADIUS - 5, 1, ANCHOR_RADIUS*2 + 10, BLUE); + } + else if (anchors[i].id == selectedAnchor) + { + // Draw the selected anchor + DrawCircle(anchors[i].x, anchors[i].y, ANCHOR_RADIUS, Fade(RED, 0.5f)); + DrawRectangle(anchors[i].x - ANCHOR_RADIUS - 5, anchors[i].y, ANCHOR_RADIUS*2 + 10, 1, RED); + DrawRectangle(anchors[i].x, anchors[i].y - ANCHOR_RADIUS - 5, 1, ANCHOR_RADIUS*2 + 10, RED); + } + else if (anchors[i].hidding) + { + // Draw idle anchor + DrawCircleLines(anchors[i].x, anchors[i].y, ANCHOR_RADIUS, Fade(BLUE, 0.5f)); + DrawRectangle(anchors[i].x - ANCHOR_RADIUS - 5, anchors[i].y, ANCHOR_RADIUS*2 + 10, 1, BLUE); + DrawRectangle(anchors[i].x, anchors[i].y - ANCHOR_RADIUS - 5, 1, ANCHOR_RADIUS*2 + 10, BLUE); + } + else + { + // Draw idle anchor + DrawCircleLines(anchors[i].x, anchors[i].y, ANCHOR_RADIUS, Fade(RED, 0.5f)); + DrawRectangle(anchors[i].x - ANCHOR_RADIUS - 5, anchors[i].y, ANCHOR_RADIUS*2 + 10, 1, RED); + DrawRectangle(anchors[i].x, anchors[i].y - ANCHOR_RADIUS - 5, 1, ANCHOR_RADIUS*2 + 10, RED); + } } if ((selectedControl != -1) && (selectedControl < controlsCounter)) { DrawRectangleRec((Rectangle){ layout[selectedControl].ap->x + layout[selectedControl].rec.x, layout[selectedControl].ap->y + layout[selectedControl].rec.y, layout[selectedControl].rec.width, layout[selectedControl].rec.height }, Fade(RED, 0.5f)); - if (layout[selectedControl].ap->id > 0) DrawLine(layout[selectedControl].ap->x, layout[selectedControl].ap->y, layout[selectedControl].ap->x + layout[selectedControl].rec.x, layout[selectedControl].ap->y + layout[selectedControl].rec.y, RED); + if (layout[selectedControl].ap->id > 0 && !layout[selectedControl].ap->hidding) DrawLine(layout[selectedControl].ap->x, layout[selectedControl].ap->y, layout[selectedControl].ap->x + layout[selectedControl].rec.x, layout[selectedControl].ap->y + layout[selectedControl].rec.y, RED); + else if (layout[selectedControl].ap->id > 0 && layout[selectedControl].ap->hidding) DrawLine(layout[selectedControl].ap->x, layout[selectedControl].ap->y, layout[selectedControl].ap->x + layout[selectedControl].rec.x, layout[selectedControl].ap->y + layout[selectedControl].rec.y, BLUE); } if ((selectedControl == -1) && (selectedAnchor == -1)) @@ -927,35 +1093,34 @@ int main() } if (anchorLinkMode) DrawLine(anchors[linkedAnchor].x, anchors[linkedAnchor].y, mouseX, mouseY, BLACK); - - if (helpMode) - { - DrawRectangleRec((Rectangle){ 20, 20, 260, 330 }, GetColor(style[DEFAULT_BACKGROUND_COLOR])); - GuiGroupBox((Rectangle){ 20, 20, 260, 330 }, "Shortcuts"); - GuiLabel((Rectangle){ 30, 30, 0, 0 }, "G - Show/hide grid"); - GuiLabel((Rectangle){ 30, 50, 0, 0 }, "S - Toggle snap"); - GuiLabel((Rectangle){ 30, 70, 0, 0 }, "R - Resize to grid"); - GuiLabel((Rectangle){ 30, 90, 0, 0 }, "A - Anchor mode"); - GuiLabel((Rectangle){ 30, 110, 0, 0 }, "U - Unlink anchor"); - GuiLabel((Rectangle){ 30, 130, 0, 0 }, "Space - Lock/unlock control"); - GuiLabel((Rectangle){ 30, 150, 0, 0 }, "T - Enter text mode(if possible)"); - GuiLabel((Rectangle){ 30, 170, 0, 0 }, "Enter - Exit text mode"); - GuiLabel((Rectangle){ 30, 190, 0, 0 }, "Delete - Delete a control"); - GuiLabel((Rectangle){ 30, 210, 0, 0 }, "Arrows - Modify width/height"); - GuiLabel((Rectangle){ 30, 230, 0, 0 }, "L. Ctrl + Arrows - Modify width/height(smooth)"); - GuiLabel((Rectangle){ 30, 250, 0, 0 }, "L. Alt + Arrows - Modify position"); - GuiLabel((Rectangle){ 30, 270, 0, 0 }, "L. Ctrl + Enter - Export layout to code"); - GuiLabel((Rectangle){ 30, 290, 0, 0 }, "L. Ctrl + S - Save layout(.rgl)"); - GuiLabel((Rectangle){ 30, 310, 0, 0 }, "L. Ctrl + O - Open layout(.rgl)"); - GuiLabel((Rectangle){ 30, 330, 0, 0 }, "L. Ctrl + D - Duplicate selected control"); - } - + + // Draw the help list + DrawRectangleRec((Rectangle){ helpPosX + 20, 20, 260, 350 }, GetColor(style[DEFAULT_BACKGROUND_COLOR])); + GuiGroupBox((Rectangle){ helpPosX + 20, 20, 260, 350 }, "Shortcuts"); + GuiLabel((Rectangle){ helpPosX + 30, 30, 0, 0 }, "G - Show/hide grid"); + GuiLabel((Rectangle){ helpPosX + 30, 50, 0, 0 }, "S - Toggle snap"); + GuiLabel((Rectangle){ helpPosX + 30, 70, 0, 0 }, "R - Resize to grid"); + GuiLabel((Rectangle){ helpPosX + 30, 90, 0, 0 }, "A - Anchor mode"); + GuiLabel((Rectangle){ helpPosX + 30, 110, 0, 0 }, "H - Hide controls of selected anchor"); + GuiLabel((Rectangle){ helpPosX + 30, 130, 0, 0 }, "U - Unlink anchor"); + GuiLabel((Rectangle){ helpPosX + 30, 150, 0, 0 }, "Space - Lock/unlock control"); + GuiLabel((Rectangle){ helpPosX + 30, 170, 0, 0 }, "T - Enter text mode(if possible)"); + GuiLabel((Rectangle){ helpPosX + 30, 190, 0, 0 }, "Enter - Exit text mode"); + GuiLabel((Rectangle){ helpPosX + 30, 210, 0, 0 }, "Delete - Delete a control"); + GuiLabel((Rectangle){ helpPosX + 30, 230, 0, 0 }, "Arrows - Modify width/height"); + GuiLabel((Rectangle){ helpPosX + 30, 250, 0, 0 }, "L. Ctrl + Arrows - Modify width/height(smooth)"); + GuiLabel((Rectangle){ helpPosX + 30, 270, 0, 0 }, "L. Alt + Arrows - Modify position"); + GuiLabel((Rectangle){ helpPosX + 30, 290, 0, 0 }, "L. Ctrl + Enter - Export layout to code"); + GuiLabel((Rectangle){ helpPosX + 30, 310, 0, 0 }, "L. Ctrl + S - Save layout(.rgl)"); + GuiLabel((Rectangle){ helpPosX + 30, 330, 0, 0 }, "L. Ctrl + O - Open layout(.rgl)"); + GuiLabel((Rectangle){ helpPosX + 30, 350, 0, 0 }, "L. Ctrl + D - Duplicate selected control"); + // Draw status bar bottom with debug information GuiStatusBar((Rectangle){ 0, GetScreenHeight() - 24, 125, 24}, FormatText("Controls count: %i", controlsCounter), 20); GuiStatusBar((Rectangle){ 124, GetScreenHeight() - 24, 126, 24}, FormatText("Mouse: (%i, %i)", mouseX, mouseY), 15); if (snapMode) GuiStatusBar((Rectangle){ 249, GetScreenHeight() - 24, 81, 24}, "SNAP ON", 10); else GuiStatusBar((Rectangle){ 249, GetScreenHeight() - 24, 81, 24}, "SNAP OFF", 10); - GuiStatusBar((Rectangle){ 329, GetScreenHeight() - 24, 80, 24}, "H - Help", 10); + GuiStatusBar((Rectangle){ 329, GetScreenHeight() - 24, 80, 24}, "Tab - Help", 10); GuiStatusBar((Rectangle){ 400, GetScreenHeight() - 24, GetScreenWidth() - 400, 24}, FormatText("Selected Control: %s (%i, %i, %i, %i)", controlTypeName[selectedType], layout[selectedControl].rec.x, layout[selectedControl].rec.y, layout[selectedControl].rec.width, layout[selectedControl].rec.height), 15); EndDrawing(); @@ -965,7 +1130,7 @@ int main() // De-Initialization //-------------------------------------------------------------------------------------- UnloadTexture(texture); - UnloadTexture(rfxgenLayout); + UnloadTexture(tracemap); CloseWindow(); // Close window and OpenGL context //-------------------------------------------------------------------------------------- diff --git a/tools/rGuiLayout/test_layout.c b/tools/rGuiLayout/test_layout.c deleted file mode 100644 index bbb244a..0000000 --- a/tools/rGuiLayout/test_layout.c +++ /dev/null @@ -1,96 +0,0 @@ -/******************************************************************************************* -* -* $(tool_name) - $(tool_description) -* -* LICENSE: zlib/libpng -* -* Copyright (c) $(year) $(author) -* -**********************************************************************************************/ - -#include "raylib.h" - -#define RAYGUI_IMPLEMENTATION -#include "raygui.h" - -//---------------------------------------------------------------------------------- -// Controls Functions Declaration -//---------------------------------------------------------------------------------- -static void Button000(); -static void Button001(); - -//------------------------------------------------------------------------------------ -// Program main entry point -//------------------------------------------------------------------------------------ -int main() -{ - // Initialization - //--------------------------------------------------------------------------------------- - int screenWidth = 800; - int screenHeight = 450; - - InitWindow(screenWidth, screenHeight, "rFXGen"); - - Rectangle layoutRecs[12] = { - (Rectangle){ 100, 50, 100, 30 }, // BUTTON 000 - (Rectangle){ 100, 100, 150, 30 }, // BUTTON 001 - (Rectangle){ 100, 150, 100, 30 }, // LABEL 002 - (Rectangle){ 100, 190, 100, 30 }, // TOGGLE 003 - (Rectangle){ 100, 240, 90, 30 }, // TOGGLEGROUP 004 - (Rectangle){ 100, 290, 300, 20 }, // SLIDER 005 - (Rectangle){ 100, 330, 250, 20 }, // PROGRESSBAR 006 - (Rectangle){ 350, 50, 150, 30 }, // SPINNER 007 - (Rectangle){ 350, 100, 120, 30 }, // COMBOBOX 008 - (Rectangle){ 420, 160, 20, 20 }, // CHECKBOX 009 - (Rectangle){ 420, 210, 20, 20 }, // CHECKBOX 010 - (Rectangle){ 450, 250, 150, 30 } // TEXTBOX 011 - }; - - SetTargetFPS(60); - //-------------------------------------------------------------------------------------- - - // Main game loop - while (!WindowShouldClose()) // Detect window close button or ESC key - { - // Update - //---------------------------------------------------------------------------------- - // TODO: Implement required update logic - //---------------------------------------------------------------------------------- - - // Draw - //---------------------------------------------------------------------------------- - BeginDrawing(); - - ClearBackground(GuiBackground()); - - if (GuiButton(layoutRecs[0], "BUTTON")) Button000(); - - if (GuiButton(layoutRecs[1], "BUTTON")) Button001(); - - GuiLabel(layoutRecs[2], "TEXT SAMPLE"); - - EndDrawing(); - //---------------------------------------------------------------------------------- - } - - // De-Initialization - //-------------------------------------------------------------------------------------- - CloseWindow(); // Close window and OpenGL context - //-------------------------------------------------------------------------------------- - - return 0; -} - -//------------------------------------------------------------------------------------ -// Controls Functions Definitions (local) -//------------------------------------------------------------------------------------ -static void Button000() -{ - // TODO: Implement control logic -} - -static void Button001() -{ - // TODO: Implement control logic -} - diff --git a/tools/rGuiLayout/test_layout.png b/tools/rGuiLayout/test_layout.png deleted file mode 100644 index 90bd03b6304db5a0ecb3093713984e5e635ad6ae..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 21602 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 E0S~y?3jhEB diff --git a/tools/rGuiLayout/test_layout.rgl b/tools/rGuiLayout/test_layout.rgl deleted file mode 100644 index a7677e7e8125d8db7775e28c25d24905feba464e..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 572 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 Ov9WU4QEllN{r>=dB?@)` literal 0 HcmV?d00001