diff --git a/.zed/debug.json b/.zed/debug.json index 8c4ea156..5ff2f5de 100644 --- a/.zed/debug.json +++ b/.zed/debug.json @@ -1,14 +1,21 @@ [ - { - "label": "Debug RPG++ Editor (Linux)", - "build": { - "command": "xmake", - "args": ["build", "--all"], - "cwd": "${ZED_WORKTREE_ROOT}", - }, - "program": "${ZED_WORKTREE_ROOT}/build/linux/x86_64/debug/editor", - "request": "launch", - "adapter": "CodeLLDB", - "cwd": "${ZED_WORKTREE_ROOT}/build/linux/x86_64/debug", - }, + { + "label": "Debug RPG++ Editor (Linux)", + "build": { + "command": "xmake", + "args": ["build", "--all"], + "cwd": "${ZED_WORKTREE_ROOT}", + }, + "program": "${ZED_WORKTREE_ROOT}/build/linux/x86_64/debug/editor", + "request": "launch", + "adapter": "CodeLLDB", + "cwd": "${ZED_WORKTREE_ROOT}/build/linux/x86_64/debug", + }, + { + "label": "Debug RPG++ Game (Linux)", + "program": "/home/nikodev/Documents/Projects/rpgpp-test-proj/TestProj", + "request": "launch", + "adapter": "CodeLLDB", + "cwd": "/home/nikodev/Documents/Projects/rpgpp-test-proj", + }, ] diff --git a/doc.json b/doc.json deleted file mode 100644 index 1ffb4add..00000000 --- a/doc.json +++ /dev/null @@ -1,808 +0,0 @@ -[ - { - "defines": [ - { - "async": false, - "deprecated": false, - "file": "types.lua", - "finish": [ - 21, - 16 - ], - "start": [ - 21, - 11 - ], - "type": "doc.class", - "view": "Actor", - "visible": "public" - } - ], - "fields": [ - { - "async": false, - "deprecated": false, - "extends": { - "args": [], - "finish": [ - 25, - 32 - ], - "returns": [ - { - "type": "function.return", - "view": "Vector2" - } - ], - "start": [ - 25, - 0 - ], - "type": "function", - "view": "function Actor.GetPosition()\n -> Vector2" - }, - "file": "types.lua", - "finish": [ - 25, - 26 - ], - "name": "GetPosition", - "start": [ - 25, - 9 - ], - "type": "setfield", - "view": "function", - "visible": "public" - } - ], - "name": "Actor", - "type": "type", - "view": "Actor" - }, - { - "defines": [ - { - "async": false, - "deprecated": false, - "desc": " The StateService is responsible for storing gameplay-related variables\n that make up the state of the game.\n\n !doctype module", - "file": "stateService.lua", - "finish": [ - 4, - 20 - ], - "rawdesc": " The StateService is responsible for storing gameplay-related variables\n that make up the state of the game.\n\n !doctype module", - "start": [ - 4, - 11 - ], - "type": "doc.class", - "view": "GameState", - "visible": "public" - } - ], - "desc": " The StateService is responsible for storing gameplay-related variables\n that make up the state of the game.\n\n !doctype module", - "fields": [ - { - "async": false, - "deprecated": false, - "desc": " Get a property", - "extends": { - "args": [ - { - "finish": [ - 10, - 27 - ], - "name": "prop", - "start": [ - 10, - 23 - ], - "type": "local", - "view": "any" - } - ], - "desc": " Get a property", - "finish": [ - 10, - 32 - ], - "rawdesc": " Get a property", - "returns": [ - { - "type": "function.return", - "view": "any" - } - ], - "start": [ - 10, - 0 - ], - "type": "function", - "view": "function GameState.Get(prop: any)\n -> any" - }, - "file": "stateService.lua", - "finish": [ - 10, - 22 - ], - "name": "Get", - "rawdesc": " Get a property", - "start": [ - 10, - 9 - ], - "type": "setfield", - "view": "function", - "visible": "public" - }, - { - "async": false, - "deprecated": false, - "desc": " Set the property with the chosen value.", - "extends": { - "args": [ - { - "finish": [ - 15, - 27 - ], - "name": "prop", - "start": [ - 15, - 23 - ], - "type": "local", - "view": "any" - }, - { - "finish": [ - 15, - 34 - ], - "name": "value", - "start": [ - 15, - 29 - ], - "type": "local", - "view": "any" - } - ], - "desc": " Set the property with the chosen value.", - "finish": [ - 15, - 39 - ], - "rawdesc": " Set the property with the chosen value.", - "start": [ - 15, - 0 - ], - "type": "function", - "view": "function GameState.Set(prop: any, value: any)" - }, - "file": "stateService.lua", - "finish": [ - 15, - 22 - ], - "name": "Set", - "rawdesc": " Set the property with the chosen value.", - "start": [ - 15, - 9 - ], - "type": "setfield", - "view": "function", - "visible": "public" - } - ], - "name": "GameState", - "rawdesc": " The StateService is responsible for storing gameplay-related variables\n that make up the state of the game.\n\n !doctype module", - "type": "type", - "view": "GameState" - }, - { - "defines": [ - { - "async": false, - "deprecated": false, - "desc": " The InterfaceService acts for the User Interface (UI).\n\n !doctype module", - "file": "interfaceService.lua", - "finish": [ - 3, - 20 - ], - "rawdesc": " The InterfaceService acts for the User Interface (UI).\n\n !doctype module", - "start": [ - 3, - 11 - ], - "type": "doc.class", - "view": "Interface", - "visible": "public" - } - ], - "desc": " The InterfaceService acts for the User Interface (UI).\n\n !doctype module", - "fields": [ - { - "async": false, - "deprecated": false, - "desc": " Open a dialogue with a certain title.", - "extends": { - "args": [ - { - "finish": [ - 8, - 40 - ], - "name": "dialogue", - "start": [ - 8, - 32 - ], - "type": "local", - "view": "string" - } - ], - "desc": " Open a dialogue with a certain title.", - "finish": [ - 8, - 45 - ], - "rawdesc": " Open a dialogue with a certain title.", - "start": [ - 8, - 0 - ], - "type": "function", - "view": "function Interface.OpenDialogue(dialogue: string)" - }, - "file": "interfaceService.lua", - "finish": [ - 8, - 31 - ], - "name": "OpenDialogue", - "rawdesc": " Open a dialogue with a certain title.", - "start": [ - 8, - 9 - ], - "type": "setfield", - "view": "function", - "visible": "public" - }, - { - "async": false, - "deprecated": false, - "desc": " hello.", - "extends": { - "args": [], - "desc": " hello.", - "finish": [ - 11, - 29 - ], - "rawdesc": " hello.", - "start": [ - 11, - 0 - ], - "type": "function", - "view": "function Interface.test()" - }, - "file": "interfaceService.lua", - "finish": [ - 11, - 23 - ], - "name": "test", - "rawdesc": " hello.", - "start": [ - 11, - 9 - ], - "type": "setfield", - "view": "function", - "visible": "public" - } - ], - "name": "Interface", - "rawdesc": " The InterfaceService acts for the User Interface (UI).\n\n !doctype module", - "type": "type", - "view": "Interface" - }, - { - "DOC": "/home/nikodev/Документи/Projects/rpgpp/luasrc", - "defines": [], - "fields": [], - "name": "LuaLS", - "type": "luals.config" - }, - { - "defines": [ - { - "async": false, - "deprecated": false, - "desc": " The SoundService is responsible for playing sounds and managing the current background music\n\n !doctype module", - "file": "soundsService.lua", - "finish": [ - 3, - 17 - ], - "rawdesc": " The SoundService is responsible for playing sounds and managing the current background music\n\n !doctype module", - "start": [ - 3, - 11 - ], - "type": "doc.class", - "view": "Sounds", - "visible": "public" - } - ], - "desc": " The SoundService is responsible for playing sounds and managing the current background music\n\n !doctype module", - "fields": [ - { - "async": false, - "deprecated": false, - "desc": " Load the music with the specified id.", - "extends": { - "args": [ - { - "finish": [ - 12, - 31 - ], - "name": "music", - "start": [ - 12, - 26 - ], - "type": "local", - "view": "string" - } - ], - "desc": " Load the music with the specified id.", - "finish": [ - 12, - 36 - ], - "rawdesc": " Load the music with the specified id.", - "start": [ - 12, - 0 - ], - "type": "function", - "view": "function Sounds.LoadMusic(music: string)" - }, - "file": "soundsService.lua", - "finish": [ - 12, - 25 - ], - "name": "LoadMusic", - "rawdesc": " Load the music with the specified id.", - "start": [ - 12, - 9 - ], - "type": "setfield", - "view": "function", - "visible": "public" - }, - { - "async": false, - "deprecated": false, - "desc": " Play the loaded music.", - "extends": { - "args": [], - "desc": " Play the loaded music.", - "finish": [ - 15, - 31 - ], - "rawdesc": " Play the loaded music.", - "start": [ - 15, - 0 - ], - "type": "function", - "view": "function Sounds.PlayMusic()" - }, - "file": "soundsService.lua", - "finish": [ - 15, - 25 - ], - "name": "PlayMusic", - "rawdesc": " Play the loaded music.", - "start": [ - 15, - 9 - ], - "type": "setfield", - "view": "function", - "visible": "public" - }, - { - "async": false, - "deprecated": false, - "desc": " Play the sound with the specified id.", - "extends": { - "args": [ - { - "finish": [ - 8, - 31 - ], - "name": "sound", - "start": [ - 8, - 26 - ], - "type": "local", - "view": "string" - } - ], - "desc": " Play the sound with the specified id.", - "finish": [ - 8, - 36 - ], - "rawdesc": " Play the sound with the specified id.", - "start": [ - 8, - 0 - ], - "type": "function", - "view": "function Sounds.PlaySound(sound: string)" - }, - "file": "soundsService.lua", - "finish": [ - 8, - 25 - ], - "name": "PlaySound", - "rawdesc": " Play the sound with the specified id.", - "start": [ - 8, - 9 - ], - "type": "setfield", - "view": "function", - "visible": "public" - } - ], - "name": "Sounds", - "rawdesc": " The SoundService is responsible for playing sounds and managing the current background music\n\n !doctype module", - "type": "type", - "view": "Sounds" - }, - { - "defines": [ - { - "async": false, - "deprecated": false, - "file": "types.lua", - "finish": [ - 0, - 18 - ], - "start": [ - 0, - 11 - ], - "type": "doc.class", - "view": "Vector2", - "visible": "public" - } - ], - "fields": [ - { - "async": false, - "deprecated": false, - "desc": " Construct a new `Vector2`", - "extends": { - "args": [ - { - "finish": [ - 7, - 22 - ], - "name": "x", - "start": [ - 7, - 21 - ], - "type": "local", - "view": "any" - }, - { - "finish": [ - 7, - 25 - ], - "name": "y", - "start": [ - 7, - 24 - ], - "type": "local", - "view": "any" - } - ], - "desc": " Construct a new `Vector2`", - "finish": [ - 7, - 30 - ], - "rawdesc": " Construct a new `Vector2`", - "start": [ - 7, - 0 - ], - "type": "function", - "view": "function Vector2.new(x: any, y: any)" - }, - "file": "types.lua", - "finish": [ - 7, - 20 - ], - "name": "new", - "rawdesc": " Construct a new `Vector2`", - "start": [ - 7, - 9 - ], - "type": "setfield", - "view": "function", - "visible": "public" - }, - { - "async": false, - "deprecated": false, - "extends": { - "finish": [ - 3, - 13 - ], - "start": [ - 3, - 12 - ], - "type": "integer", - "view": "integer" - }, - "file": "types.lua", - "finish": [ - 3, - 9 - ], - "name": "x", - "start": [ - 3, - 0 - ], - "type": "setfield", - "view": "integer", - "visible": "public" - }, - { - "async": false, - "deprecated": false, - "extends": { - "finish": [ - 4, - 13 - ], - "start": [ - 4, - 12 - ], - "type": "integer", - "view": "integer" - }, - "file": "types.lua", - "finish": [ - 4, - 9 - ], - "name": "y", - "start": [ - 4, - 0 - ], - "type": "setfield", - "view": "integer", - "visible": "public" - } - ], - "name": "Vector2", - "type": "type", - "view": "Vector2" - }, - { - "defines": [ - { - "async": false, - "deprecated": false, - "desc": " The WorldService is responsible for containing and drawing the Room.\n\n !doctype module", - "file": "worldService.lua", - "finish": [ - 3, - 23 - ], - "rawdesc": " The WorldService is responsible for containing and drawing the Room.\n\n !doctype module", - "start": [ - 3, - 11 - ], - "type": "doc.class", - "view": "WorldService", - "visible": "public" - } - ], - "desc": " The WorldService is responsible for containing and drawing the Room.\n\n !doctype module", - "fields": [ - { - "async": false, - "deprecated": false, - "desc": " Get the Player.", - "extends": { - "args": [], - "desc": " Get the Player.", - "finish": [ - 8, - 37 - ], - "rawdesc": " Get the Player.", - "returns": [ - { - "type": "function.return", - "view": "Player" - } - ], - "start": [ - 8, - 0 - ], - "type": "function", - "view": "function WorldService.GetPlayer()\n -> Player" - }, - "file": "worldService.lua", - "finish": [ - 8, - 31 - ], - "name": "GetPlayer", - "rawdesc": " Get the Player.", - "start": [ - 8, - 9 - ], - "type": "setfield", - "view": "function", - "visible": "public" - }, - { - "async": false, - "deprecated": false, - "desc": " Get the current Room", - "extends": { - "args": [], - "desc": " Get the current Room", - "finish": [ - 16, - 35 - ], - "rawdesc": " Get the current Room", - "returns": [ - { - "type": "function.return", - "view": "Room" - } - ], - "start": [ - 16, - 0 - ], - "type": "function", - "view": "function WorldService.GetRoom()\n -> Room" - }, - "file": "worldService.lua", - "finish": [ - 16, - 29 - ], - "name": "GetRoom", - "rawdesc": " Get the current Room", - "start": [ - 16, - 9 - ], - "type": "setfield", - "view": "function", - "visible": "public" - }, - { - "async": false, - "deprecated": false, - "desc": " Set the current room using a room title in the game.", - "extends": { - "args": [ - { - "finish": [ - 12, - 34 - ], - "name": "room", - "start": [ - 12, - 30 - ], - "type": "local", - "view": "string" - } - ], - "desc": " Set the current room using a room title in the game.", - "finish": [ - 12, - 39 - ], - "rawdesc": " Set the current room using a room title in the game.", - "start": [ - 12, - 0 - ], - "type": "function", - "view": "function WorldService.SetRoom(room: string)" - }, - "file": "worldService.lua", - "finish": [ - 12, - 29 - ], - "name": "SetRoom", - "rawdesc": " Set the current room using a room title in the game.", - "start": [ - 12, - 9 - ], - "type": "setfield", - "view": "function", - "visible": "public" - } - ], - "name": "WorldService", - "rawdesc": " The WorldService is responsible for containing and drawing the Room.\n\n !doctype module", - "type": "type", - "view": "WorldService" - }, - { - "defines": [ - { - "desc": "```lua\n{\n DOWN_IDLE: integer = 0,\n DOWN: integer = 1,\n UP_IDLE: integer = 2,\n UP: integer = 3,\n LEFT_IDLE: integer = 4,\n LEFT: integer = 5,\n RIGHT_IDLE: integer = 6,\n RIGHT: integer = 7,\n}\n```", - "file": "types.lua", - "finish": [ - 9, - 13 - ], - "rawdesc": "```lua\n{\n DOWN_IDLE: integer = 0,\n DOWN: integer = 1,\n UP_IDLE: integer = 2,\n UP: integer = 3,\n LEFT_IDLE: integer = 4,\n LEFT: integer = 5,\n RIGHT_IDLE: integer = 6,\n RIGHT: integer = 7,\n}\n```", - "start": [ - 9, - 10 - ], - "type": "doc.enum", - "view": "dir" - } - ], - "fields": [], - "name": "dir", - "type": "type", - "view": "dir" - } -] \ No newline at end of file diff --git a/doc.md b/doc.md deleted file mode 100644 index bee39449..00000000 --- a/doc.md +++ /dev/null @@ -1,177 +0,0 @@ -# Actor - -## GetPosition - - -```lua -function Actor.GetPosition() - -> Vector2 -``` - - ---- - -# GameState - - The StateService is responsible for storing gameplay-related variables - that make up the state of the game. - - !doctype module - -## Get - - -```lua -function GameState.Get(prop: any) - -> any -``` - - Get a property - -## Set - - -```lua -function GameState.Set(prop: any, value: any) -``` - - Set the property with the chosen value. - - ---- - -# Interface - - The InterfaceService acts for the User Interface (UI). - - !doctype module - -## OpenDialogue - - -```lua -function Interface.OpenDialogue(dialogue: string) -``` - - Open a dialogue with a certain title. - -## test - - -```lua -function Interface.test() -``` - - hello. - - ---- - -# LuaLS - - ---- - -# Sounds - - The SoundService is responsible for playing sounds and managing the current background music - - !doctype module - -## LoadMusic - - -```lua -function Sounds.LoadMusic(music: string) -``` - - Load the music with the specified id. - -## PlayMusic - - -```lua -function Sounds.PlayMusic() -``` - - Play the loaded music. - -## PlaySound - - -```lua -function Sounds.PlaySound(sound: string) -``` - - Play the sound with the specified id. - - ---- - -# Vector2 - -## new - - -```lua -function Vector2.new(x: any, y: any) -``` - - Construct a new `Vector2` - -## x - - -```lua -integer -``` - -## y - - -```lua -integer -``` - - ---- - -# WorldService - - The WorldService is responsible for containing and drawing the Room. - - !doctype module - -## GetPlayer - - -```lua -function WorldService.GetPlayer() - -> Player -``` - - Get the Player. - -## GetRoom - - -```lua -function WorldService.GetRoom() - -> Room -``` - - Get the current Room - -## SetRoom - - -```lua -function WorldService.SetRoom(room: string) -``` - - Set the current room using a room title in the game. - - ---- - -# dir \ No newline at end of file diff --git a/docs/guide/resourcetypes/interfaceview.rst b/docs/guide/resourcetypes/interfaceview.rst new file mode 100644 index 00000000..db730aee --- /dev/null +++ b/docs/guide/resourcetypes/interfaceview.rst @@ -0,0 +1,135 @@ +Interface View +============== + +========================== +What is an Interface View? +========================== + +An Interface View represents a group of UI elements/controls that will appear on the screen in-game. It can contain text labels, buttons and etc. + +Interface View files have the ``.rview`` file extension. + +====================================== +Creating and editing an Interface View +====================================== + +You can create an UI View by providing a name for it. + +.. image:: ../../images/rpgpp-createinterfaceview.png + :width: 80% + +.. image:: ../../images/rpgpp-interfaceviewview.png + :width: 80% + +After creation, you can see a preview of the Interface View itself, grid snap setting at the top, elements list and Create element button on the top right and Properties list on the bottom right. + +============= +Elements List +============= + +In the top right corner, you can see a 'Create' button and a list of UI Elements. + +.. image:: ../../images/rpgpp-view-elementslist.png + :width: 40% + +* **Create** + +When you click 'Create', a 'Create Element' form will pop up. First enter the name of the element, then choose its type. RPG++ provides a set of UI Element types. + +.. image:: ../../images/rpgpp-view-createelement.png + :width: 40% + +* **Element list** + +You can see a list of UI Elements in this Interface View. Left-clicking on any of them will highlight them in the UI preview and will show its properties in the Properties List. +Right-clicking will reveal a context menu for this UI element. + + .. image:: ../../images/rpgpp-view-contextmenu.png + :width: 40% + + + * **Rename**: Rename this element. A Rename Element form will pop up, asking you to set a new name. + + * **Move Up**: Move this element one level up. Switches places with the element above it. + + * **Move Down**: Move this element one level down. Switches places with the element under it. + + * **Move to Top**: Move this element to the very top. + + * **Move to Bottom**: Move this element to the bottom of the hierarchy. + + * **Delete**: Delete this UI element. + +=============== +Properties List +=============== + +When viewing an Interface View file, the Properties List has two tabs: 'UI View' and 'Properties' + +* **UI View**: + +In this tab, you can see the properties of the Interface View itself. You can attach a script to it. See `Scripting`_ + +.. image:: ../../images/rpgpp-view-props-ui.png + :width: 40% + +* **Properties**: + +In this tab, you can see the properties of the currently selected UI Element. + +.. image:: ../../images/rpgpp-view-props-element.png + :width: 40% + +=============== +UI View Preview +=============== + +In the preview you can see the Interface View the same way it will appear in-game. + +.. image:: ../../images/rpgpp-view-preview.png + :width: 80% + +The gray borders outline the size of the game window. +Selected UI Element will be shown in red. You can move it around using the left mouse button. Holding it down will move it according to the snap setting. +You can also drag the sides of the element to resize it. + +========= +Scripting +========= + +You can attach scripts to Interface Views. This section will explain which parts are scriptable. Please refer to the Lua API Documentation for more information. + +Your script can include a ``open()`` and/or a ``close()`` function. + +.. code:: lua + + function open() + print("The View was opened!") + end + + function close() + print("The View was closed!") + end + + +It is also possible to access the UI Elements themselves and change them! + +.. code:: lua + + function open() + element = view:GetEntity("title") + element.text = "My game!" + print("The View was opened!") + end + +You can also listen to callbacks from UI Elements who have such properties, such as Buttons. +This example code will print a message when the button has been triggered. Its 'callback_triggered' property is set to the name of the function that will be called. + +.. image:: ../../images/rpgpp-view-prop-callback.png + :width: 40% + +.. code:: lua + + function play() + print("Play button pressed!") + end diff --git a/docs/guide/typesindex.rst b/docs/guide/typesindex.rst index dc658089..9293a282 100644 --- a/docs/guide/typesindex.rst +++ b/docs/guide/typesindex.rst @@ -7,4 +7,5 @@ Resource Types resourcetypes/actor resourcetypes/dialogue resourcetypes/prop - resourcetypes/interactable \ No newline at end of file + resourcetypes/interactable + resourcetypes/interfaceview diff --git a/docs/images/rpgpp-createinterfaceview.png b/docs/images/rpgpp-createinterfaceview.png new file mode 100644 index 00000000..30f342f6 Binary files /dev/null and b/docs/images/rpgpp-createinterfaceview.png differ diff --git a/docs/images/rpgpp-interfaceviewview.png b/docs/images/rpgpp-interfaceviewview.png new file mode 100644 index 00000000..2e0ff0e4 Binary files /dev/null and b/docs/images/rpgpp-interfaceviewview.png differ diff --git a/docs/images/rpgpp-view-contextmenu.png b/docs/images/rpgpp-view-contextmenu.png new file mode 100644 index 00000000..a5fcddd7 Binary files /dev/null and b/docs/images/rpgpp-view-contextmenu.png differ diff --git a/docs/images/rpgpp-view-createelement.png b/docs/images/rpgpp-view-createelement.png new file mode 100644 index 00000000..c3ac675d Binary files /dev/null and b/docs/images/rpgpp-view-createelement.png differ diff --git a/docs/images/rpgpp-view-elementslist.png b/docs/images/rpgpp-view-elementslist.png new file mode 100644 index 00000000..53b5d24c Binary files /dev/null and b/docs/images/rpgpp-view-elementslist.png differ diff --git a/docs/images/rpgpp-view-preview.png b/docs/images/rpgpp-view-preview.png new file mode 100644 index 00000000..10796f9f Binary files /dev/null and b/docs/images/rpgpp-view-preview.png differ diff --git a/docs/images/rpgpp-view-prop-callback.png b/docs/images/rpgpp-view-prop-callback.png new file mode 100644 index 00000000..92cd46c5 Binary files /dev/null and b/docs/images/rpgpp-view-prop-callback.png differ diff --git a/docs/images/rpgpp-view-props-element.png b/docs/images/rpgpp-view-props-element.png new file mode 100644 index 00000000..dcfc2a96 Binary files /dev/null and b/docs/images/rpgpp-view-props-element.png differ diff --git a/docs/images/rpgpp-view-props-ui.png b/docs/images/rpgpp-view-props-ui.png new file mode 100644 index 00000000..5313264d Binary files /dev/null and b/docs/images/rpgpp-view-props-ui.png differ diff --git a/docs/userapi/doc.json b/docs/userapi/doc.json index f8a285e0..1baad2ad 100644 --- a/docs/userapi/doc.json +++ b/docs/userapi/doc.json @@ -970,6 +970,69 @@ "type": "type", "view": "Direction" }, + { + "defines": [ + { + "async": false, + "deprecated": false, + "desc": " The Game namespace is responsible for maanging the state of the program itself\n", + "file": "game.lua", + "finish": [ + 2, + 15 + ], + "rawdesc": " The Game namespace is responsible for maanging the state of the program itself\n", + "start": [ + 2, + 11 + ], + "type": "doc.class", + "view": "Game", + "visible": "public" + } + ], + "desc": " The Game namespace is responsible for maanging the state of the program itself\n", + "fields": [ + { + "async": false, + "deprecated": false, + "desc": " Closes the game.", + "extends": { + "args": [], + "desc": " Closes the game.", + "finish": [ + 6, + 25 + ], + "rawdesc": " Closes the game.", + "start": [ + 6, + 0 + ], + "type": "function", + "view": "function Game.Close()" + }, + "file": "game.lua", + "finish": [ + 6, + 19 + ], + "name": "Close", + "rawdesc": " Closes the game.", + "start": [ + 6, + 9 + ], + "type": "setfield", + "view": "function", + "visible": "public" + } + ], + "name": "Game", + "rawdesc": " The Game namespace is responsible for maanging the state of the program itself\n", + "type": "type", + "view": "Game" + }, { "defines": [ { @@ -1299,7 +1362,7 @@ { "async": false, "deprecated": false, - "desc": " Set whether this interactable will be invoked when player touches it. ", + "desc": " Set whether this interactable will be invoked when player touches it.", "extends": { "args": [ { @@ -1329,12 +1392,12 @@ "view": "boolean" } ], - "desc": " Set whether this interactable will be invoked when player touches it. ", + "desc": " Set whether this interactable will be invoked when player touches it.", "finish": [ 110, 43 ], - "rawdesc": " Set whether this interactable will be invoked when player touches it. ", + "rawdesc": " Set whether this interactable will be invoked when player touches it.", "start": [ 110, 0 @@ -1348,7 +1411,7 @@ 32 ], "name": "SetOnTouch", - "rawdesc": " Set whether this interactable will be invoked when player touches it. ", + "rawdesc": " Set whether this interactable will be invoked when player touches it.", "start": [ 110, 9 @@ -1792,6 +1855,40 @@ ], "desc": " The InterfaceService acts for the User Interface (UI).\n", "fields": [ + { + "async": false, + "deprecated": false, + "desc": " Get a reference to the current UI View.", + "extends": { + "args": [], + "desc": " Get a reference to the current UI View.", + "finish": [ + 15, + 39 + ], + "rawdesc": " Get a reference to the current UI View.", + "start": [ + 15, + 0 + ], + "type": "function", + "view": "function Interface.GetCurrentView()" + }, + "file": "interfaceService.lua", + "finish": [ + 15, + 33 + ], + "name": "GetCurrentView", + "rawdesc": " Get a reference to the current UI View.", + "start": [ + 15, + 9 + ], + "type": "setfield", + "view": "function", + "visible": "public" + }, { "async": false, "deprecated": false, @@ -1800,12 +1897,12 @@ "args": [ { "finish": [ - 7, + 11, 40 ], "name": "dialogue", "start": [ - 7, + 11, 32 ], "type": "local", @@ -1814,12 +1911,12 @@ ], "desc": " Open a dialogue with a certain title.", "finish": [ - 7, + 11, 45 ], "rawdesc": " Open a dialogue with a certain title.", "start": [ - 7, + 11, 0 ], "type": "function", @@ -1827,11 +1924,59 @@ }, "file": "interfaceService.lua", "finish": [ - 7, + 11, 31 ], "name": "OpenDialogue", "rawdesc": " Open a dialogue with a certain title.", + "start": [ + 11, + 9 + ], + "type": "setfield", + "view": "function", + "visible": "public" + }, + { + "async": false, + "deprecated": false, + "desc": " Open the UI View identified by this title.", + "extends": { + "args": [ + { + "finish": [ + 7, + 33 + ], + "name": "title", + "start": [ + 7, + 28 + ], + "type": "local", + "view": "string" + } + ], + "desc": " Open the UI View identified by this title.", + "finish": [ + 7, + 38 + ], + "rawdesc": " Open the UI View identified by this title.", + "start": [ + 7, + 0 + ], + "type": "function", + "view": "function Interface.OpenView(title: string)" + }, + "file": "interfaceService.lua", + "finish": [ + 7, + 27 + ], + "name": "OpenView", + "rawdesc": " Open the UI View identified by this title.", "start": [ 7, 9 @@ -1847,7 +1992,208 @@ "view": "Interface" }, { - "DOC": "/home/nikodev/Документи/Projects/rpgpp/luasrc", + "defines": [ + { + "async": false, + "deprecated": false, + "file": "types.lua", + "finish": [ + 281, + 24 + ], + "start": [ + 281, + 11 + ], + "type": "doc.class", + "view": "InterfaceView", + "visible": "public" + } + ], + "fields": [ + { + "async": false, + "deprecated": false, + "desc": " Change focus to another UI element.", + "extends": { + "args": [ + { + "finish": [ + 291, + 8 + ], + "name": "self", + "start": [ + 291, + 8 + ], + "type": "self", + "view": "InterfaceView" + }, + { + "finish": [ + 291, + 39 + ], + "name": "name", + "start": [ + 291, + 35 + ], + "type": "local", + "view": "string" + } + ], + "desc": " Change focus to another UI element.", + "finish": [ + 291, + 44 + ], + "rawdesc": " Change focus to another UI element.", + "start": [ + 291, + 0 + ], + "type": "function", + "view": "(method) InterfaceView:ChangeFocus(name: string)" + }, + "file": "types.lua", + "finish": [ + 291, + 34 + ], + "name": "ChangeFocus", + "rawdesc": " Change focus to another UI element.", + "start": [ + 291, + 9 + ], + "type": "setmethod", + "view": "function", + "visible": "public" + }, + { + "async": false, + "deprecated": false, + "desc": " Get an element from the UI View.", + "extends": { + "args": [ + { + "finish": [ + 287, + 8 + ], + "name": "self", + "start": [ + 287, + 8 + ], + "type": "self", + "view": "InterfaceView" + }, + { + "finish": [ + 287, + 37 + ], + "name": "name", + "start": [ + 287, + 33 + ], + "type": "local", + "view": "string" + } + ], + "desc": " Get an element from the UI View.", + "finish": [ + 287, + 42 + ], + "rawdesc": " Get an element from the UI View.", + "returns": [ + { + "type": "function.return", + "view": "UIElement" + } + ], + "start": [ + 287, + 0 + ], + "type": "function", + "view": "(method) InterfaceView:GetEntity(name: string)\n -> UIElement" + }, + "file": "types.lua", + "finish": [ + 287, + 32 + ], + "name": "GetEntity", + "rawdesc": " Get an element from the UI View.", + "start": [ + 287, + 9 + ], + "type": "setmethod", + "view": "function", + "visible": "public" + }, + { + "async": false, + "deprecated": false, + "desc": " Reset the elements to their original positions and sizes.", + "extends": { + "args": [ + { + "finish": [ + 294, + 8 + ], + "name": "self", + "start": [ + 294, + 8 + ], + "type": "self", + "view": "InterfaceView" + } + ], + "desc": " Reset the elements to their original positions and sizes.", + "finish": [ + 294, + 34 + ], + "rawdesc": " Reset the elements to their original positions and sizes.", + "start": [ + 294, + 0 + ], + "type": "function", + "view": "(method) InterfaceView:Reset()" + }, + "file": "types.lua", + "finish": [ + 294, + 28 + ], + "name": "Reset", + "rawdesc": " Reset the elements to their original positions and sizes.", + "start": [ + 294, + 9 + ], + "type": "setmethod", + "view": "function", + "visible": "public" + } + ], + "name": "InterfaceView", + "type": "type", + "view": "InterfaceView" + }, + { + "DOC": "/home/nikodev/Documents/Projects/rpgpp/luasrc", "defines": [], "fields": [], "name": "LuaLS", @@ -3574,6 +3920,154 @@ "type": "type", "view": "TileMap" }, + { + "defines": [ + { + "desc": "```lua\n{\n Linear: integer = 0,\n InSine: integer = 1,\n OutSine: integer = 2,\n InOutSine: integer = 3,\n InQuad: integer = 4,\n OutQuad: integer = 5,\n InOutQuad: integer = 6,\n InCubic: integer = 7,\n OutCubic: integer = 8,\n InOutCubic: integer = 9,\n InQuart: integer = 10,\n OutQuart: integer = 11,\n InOutQuart: integer = 12,\n OutQuint: integer = 14,\n InOutQuint: integer = 15,\n InExpo: integer = 16,\n OutExpo: integer = 17,\n InOutExpo: integer = 18,\n InCirc: integer = 19,\n OutCirc: integer = 20,\n InOutCirc: integer = 21,\n InBack: integer = 22,\n OutBack: integer = 23,\n InOutBack: integer = 24,\n InElastic: integer = 25,\n OutElastic: integer = 26,\n InOutElastic: integer = 27,\n InBounce: integer = 28,\n OutBounce: integer = 29,\n InOutBounce: integer = 30,\n}\n```", + "file": "types.lua", + "finish": [ + 246, + 19 + ], + "rawdesc": "```lua\n{\n Linear: integer = 0,\n InSine: integer = 1,\n OutSine: integer = 2,\n InOutSine: integer = 3,\n InQuad: integer = 4,\n OutQuad: integer = 5,\n InOutQuad: integer = 6,\n InCubic: integer = 7,\n OutCubic: integer = 8,\n InOutCubic: integer = 9,\n InQuart: integer = 10,\n OutQuart: integer = 11,\n InOutQuart: integer = 12,\n OutQuint: integer = 14,\n InOutQuint: integer = 15,\n InExpo: integer = 16,\n OutExpo: integer = 17,\n InOutExpo: integer = 18,\n InCirc: integer = 19,\n OutCirc: integer = 20,\n InOutCirc: integer = 21,\n InBack: integer = 22,\n OutBack: integer = 23,\n InOutBack: integer = 24,\n InElastic: integer = 25,\n OutElastic: integer = 26,\n InOutElastic: integer = 27,\n InBounce: integer = 28,\n OutBounce: integer = 29,\n InOutBounce: integer = 30,\n}\n```", + "start": [ + 246, + 10 + ], + "type": "doc.enum", + "view": "TweenType" + } + ], + "fields": [], + "name": "TweenType", + "type": "type", + "view": "TweenType" + }, + { + "defines": [ + { + "async": false, + "deprecated": false, + "file": "types.lua", + "finish": [ + 296, + 20 + ], + "start": [ + 296, + 11 + ], + "type": "doc.class", + "view": "UIElement", + "visible": "public" + } + ], + "fields": [ + { + "async": false, + "deprecated": false, + "desc": " Tween this element.", + "extends": { + "args": [ + { + "finish": [ + 304, + 8 + ], + "name": "self", + "start": [ + 304, + 8 + ], + "type": "self", + "view": "UIElement" + }, + { + "finish": [ + 304, + 33 + ], + "name": "property", + "start": [ + 304, + 25 + ], + "type": "local", + "view": "string" + }, + { + "finish": [ + 304, + 40 + ], + "name": "value", + "start": [ + 304, + 35 + ], + "type": "local", + "view": "any" + }, + { + "finish": [ + 304, + 50 + ], + "name": "duration", + "start": [ + 304, + 42 + ], + "type": "local", + "view": "number" + }, + { + "finish": [ + 304, + 61 + ], + "name": "tweenType", + "start": [ + 304, + 52 + ], + "type": "local", + "view": "TweenType" + } + ], + "desc": " Tween this element.", + "finish": [ + 304, + 66 + ], + "rawdesc": " Tween this element.", + "start": [ + 304, + 0 + ], + "type": "function", + "view": "(method) UIElement:Tween(property: string, value: any, duration: number, tweenType: TweenType)" + }, + "file": "types.lua", + "finish": [ + 304, + 24 + ], + "name": "Tween", + "rawdesc": " Tween this element.", + "start": [ + 304, + 9 + ], + "type": "setmethod", + "view": "function", + "visible": "public" + } + ], + "name": "UIElement", + "type": "type", + "view": "UIElement" + }, { "defines": [ { @@ -3759,7 +4253,7 @@ "file": "worldService.lua", "finish": [ 2, - 23 + 16 ], "rawdesc": " The WorldService is responsible for containing and drawing the Room.\n", "start": [ @@ -3767,7 +4261,7 @@ 11 ], "type": "doc.class", - "view": "WorldService", + "view": "World", "visible": "public" } ], @@ -3782,7 +4276,7 @@ "desc": " Get the Player.", "finish": [ 7, - 37 + 30 ], "rawdesc": " Get the Player.", "returns": [ @@ -3796,12 +4290,12 @@ 0 ], "type": "function", - "view": "function WorldService.GetPlayer()\n -> Player" + "view": "function World.GetPlayer()\n -> Player" }, "file": "worldService.lua", "finish": [ 7, - 31 + 24 ], "name": "GetPlayer", "rawdesc": " Get the Player.", @@ -3822,7 +4316,7 @@ "desc": " Get the current Room", "finish": [ 15, - 35 + 28 ], "rawdesc": " Get the current Room", "returns": [ @@ -3836,12 +4330,12 @@ 0 ], "type": "function", - "view": "function WorldService.GetRoom()\n -> Room" + "view": "function World.GetRoom()\n -> Room" }, "file": "worldService.lua", "finish": [ 15, - 29 + 22 ], "name": "GetRoom", "rawdesc": " Get the current Room", @@ -3862,12 +4356,12 @@ { "finish": [ 11, - 34 + 27 ], "name": "room", "start": [ 11, - 30 + 23 ], "type": "local", "view": "string" @@ -3876,7 +4370,7 @@ "desc": " Set the current room using a room title in the game.", "finish": [ 11, - 39 + 32 ], "rawdesc": " Set the current room using a room title in the game.", "start": [ @@ -3884,12 +4378,12 @@ 0 ], "type": "function", - "view": "function WorldService.SetRoom(room: string)" + "view": "function World.SetRoom(room: string)" }, "file": "worldService.lua", "finish": [ 11, - 29 + 22 ], "name": "SetRoom", "rawdesc": " Set the current room using a room title in the game.", @@ -3902,9 +4396,9 @@ "visible": "public" } ], - "name": "WorldService", + "name": "World", "rawdesc": " The WorldService is responsible for containing and drawing the Room.\n", "type": "type", - "view": "WorldService" + "view": "World" } ] \ No newline at end of file diff --git a/docs/userapi/doc.md b/docs/userapi/doc.md index 234beeeb..5a0a66c9 100644 --- a/docs/userapi/doc.md +++ b/docs/userapi/doc.md @@ -1,8 +1,8 @@ # Lua API Reference -## Actor +# Actor -### ChangeAnimation +## ChangeAnimation ```lua @@ -11,7 +11,7 @@ Change the Actor's current animation and play it. -### GetPosition +## GetPosition ```lua @@ -21,7 +21,7 @@ Get the Actor's position -### GetTilePosition +## GetTilePosition ```lua @@ -30,7 +30,7 @@ Get this Actor's tile position. -### MoveByVelocity +## MoveByVelocity ```lua @@ -39,7 +39,7 @@ Move the Actor using a velocity vector. -### PlayAnimation +## PlayAnimation ```lua @@ -48,7 +48,7 @@ Temporarily play an animation. -### SetPosition +## SetPosition ```lua @@ -57,7 +57,7 @@ Set this Actor's position. -### SetTilePosition +## SetTilePosition ```lua @@ -69,9 +69,9 @@ --- -## ActorContainer +# ActorContainer -### Exists +## Exists ```lua @@ -81,7 +81,7 @@ Whether an Actor with such a name exists in the current room. -### Get +## Get ```lua @@ -91,7 +91,7 @@ Get an Actor by its in-room name. -### Push +## Push ```lua @@ -100,7 +100,7 @@ Add a new Actor at this tile position of this type. It will have this in-room name. -### Remove +## Remove ```lua @@ -112,23 +112,23 @@ --- -## CollisionsContainer +# CollisionsContainer -### Exists +## Exists ```lua (method) CollisionsContainer:Exists(item: Vector2) ``` -### Push +## Push ```lua (method) CollisionsContainer:Push(item: Vector2) ``` -### Remove +## Remove ```lua @@ -138,18 +138,35 @@ --- -## Direction +# Direction --- -## GameState +# Game + + The Game namespace is responsible for maanging the state of the program itself + + +## Close + + +```lua +function Game.Close() +``` + + Closes the game. + + +--- + +# GameState The StateService is responsible for storing gameplay-related variables that make up the state of the game. -### Get +## Get ```lua @@ -159,7 +176,7 @@ function GameState.Get(prop: string) Get a property -### Set +## Set ```lua @@ -171,9 +188,9 @@ function GameState.Set(prop: string, value: any) --- -## Interactable +# Interactable -### GetPosition +## GetPosition ```lua @@ -183,7 +200,7 @@ function GameState.Set(prop: string, value: any) Get the World position of this Interactable -### GetType +## GetType ```lua @@ -193,7 +210,7 @@ function GameState.Set(prop: string, value: any) Get this Interactable's type -### IsOnTouch +## IsOnTouch ```lua @@ -203,16 +220,16 @@ function GameState.Set(prop: string, value: any) Whether this Interactable is set to be interacted with on player collision or not. -### SetOnTouch +## SetOnTouch ```lua (method) Interactable:SetOnTouch(value: boolean) ``` - Set whether this interactable will be invoked when player touches it. + Set whether this interactable will be invoked when player touches it. -### SetProp +## SetProp ```lua @@ -221,7 +238,7 @@ function GameState.Set(prop: string, value: any) Set an Interactable's property -### SetType +## SetType ```lua @@ -233,16 +250,16 @@ function GameState.Set(prop: string, value: any) --- -## InteractablesContainer +# InteractablesContainer -### Exists +## Exists ```lua (method) InteractablesContainer:Exists(pos: Vector2) ``` -### GetAt +## GetAt ```lua @@ -250,14 +267,14 @@ function GameState.Set(prop: string, value: any) -> Interactable ``` -### Push +## Push ```lua (method) InteractablesContainer:Push(pos: Vector2, type: string) ``` -### Remove +## Remove ```lua @@ -267,12 +284,21 @@ function GameState.Set(prop: string, value: any) --- -## Interface +# Interface The InterfaceService acts for the User Interface (UI). -### OpenDialogue +## GetCurrentView + + +```lua +function Interface.GetCurrentView() +``` + + Get a reference to the current UI View. + +## OpenDialogue ```lua @@ -281,12 +307,59 @@ function Interface.OpenDialogue(dialogue: string) Open a dialogue with a certain title. +## OpenView + + +```lua +function Interface.OpenView(title: string) +``` + + Open the UI View identified by this title. + + +--- + +# InterfaceView + +## ChangeFocus + + +```lua +(method) InterfaceView:ChangeFocus(name: string) +``` + + Change focus to another UI element. + +## GetEntity + + +```lua +(method) InterfaceView:GetEntity(name: string) + -> UIElement +``` + + Get an element from the UI View. + +## Reset + + +```lua +(method) InterfaceView:Reset() +``` + + Reset the elements to their original positions and sizes. + + +--- + +# LuaLS + --- -## Player +# Player -### GetActor +## GetActor ```lua @@ -296,7 +369,7 @@ function Interface.OpenDialogue(dialogue: string) Get the player's actor. -### GetPosition +## GetPosition ```lua @@ -306,7 +379,7 @@ function Interface.OpenDialogue(dialogue: string) Get the player's position -### GetTilePosition +## GetTilePosition ```lua @@ -315,7 +388,7 @@ function Interface.OpenDialogue(dialogue: string) Get this player's tile position. -### MoveByVelocity +## MoveByVelocity ```lua @@ -324,7 +397,7 @@ function Interface.OpenDialogue(dialogue: string) Move the Actor using a velocity vector. -### SetPosition +## SetPosition ```lua @@ -333,7 +406,7 @@ function Interface.OpenDialogue(dialogue: string) Set this player's position. -### SetTilePosition +## SetTilePosition ```lua @@ -345,9 +418,9 @@ function Interface.OpenDialogue(dialogue: string) --- -## Prop +# Prop -### GetInteractable +## GetInteractable ```lua @@ -357,7 +430,7 @@ function Interface.OpenDialogue(dialogue: string) Get the Interactable of this Prop. -### GetPosition +## GetPosition ```lua @@ -367,7 +440,7 @@ function Interface.OpenDialogue(dialogue: string) Get the absolute world position of this Prop. -### GetTilePosition +## GetTilePosition ```lua @@ -377,7 +450,7 @@ function Interface.OpenDialogue(dialogue: string) Get the tile position of this Prop. -### SetPosition +## SetPosition ```lua @@ -386,7 +459,7 @@ function Interface.OpenDialogue(dialogue: string) Set the absolute world position of this Prop. -### SetTilePosition +## SetTilePosition ```lua @@ -398,16 +471,16 @@ function Interface.OpenDialogue(dialogue: string) --- -## PropsContainer +# PropsContainer -### Exists +## Exists ```lua (method) PropsContainer:Exists(pos: Vector2) ``` -### GetAt +## GetAt ```lua @@ -415,14 +488,14 @@ function Interface.OpenDialogue(dialogue: string) -> Prop ``` -### Push +## Push ```lua (method) PropsContainer:Push(pos: Vector2, type: string) ``` -### Remove +## Remove ```lua @@ -432,9 +505,9 @@ function Interface.OpenDialogue(dialogue: string) --- -## Room +# Room -### GetActors +## GetActors ```lua @@ -444,7 +517,7 @@ function Interface.OpenDialogue(dialogue: string) Get a refernece to the collection of Actors. -### GetCollisions +## GetCollisions ```lua @@ -454,7 +527,7 @@ function Interface.OpenDialogue(dialogue: string) Get a reference to the CollisionsContainer of this Room. -### GetInteractables +## GetInteractables ```lua @@ -464,7 +537,7 @@ function Interface.OpenDialogue(dialogue: string) Get a reference to the InteractablesContainer of this Room. -### GetPlayer +## GetPlayer ```lua @@ -474,7 +547,7 @@ function Interface.OpenDialogue(dialogue: string) Get a reference to the Player object. -### GetProps +## GetProps ```lua @@ -484,7 +557,7 @@ function Interface.OpenDialogue(dialogue: string) Get a reference to the PropsContainer of this Room. -### GetStartTile +## GetStartTile ```lua @@ -494,7 +567,7 @@ function Interface.OpenDialogue(dialogue: string) Set the start tile position. -### GetTileMap +## GetTileMap ```lua @@ -507,12 +580,12 @@ function Interface.OpenDialogue(dialogue: string) --- -## Sounds +# Sounds The SoundService is responsible for playing sounds and managing the current background music -### LoadMusic +## LoadMusic ```lua @@ -521,7 +594,7 @@ function Sounds.LoadMusic(music: string) Load the music with the specified id. -### PlayMusic +## PlayMusic ```lua @@ -530,7 +603,7 @@ function Sounds.PlayMusic() Play the loaded music. -### PlaySound +## PlaySound ```lua @@ -542,9 +615,9 @@ function Sounds.PlaySound(sound: string) --- -## TileMap +# TileMap -### GetWorldSizeInTiles +## GetWorldSizeInTiles ```lua @@ -554,7 +627,7 @@ function Sounds.PlaySound(sound: string) Get the size of this TileMap in tiles. -### SetEmptyTile +## SetEmptyTile ```lua @@ -563,7 +636,7 @@ function Sounds.PlaySound(sound: string) Set the tile at the specified world position to be empty (not drawn). -### SetTile +## SetTile ```lua @@ -576,9 +649,28 @@ function Sounds.PlaySound(sound: string) --- -## Vector2 +# TweenType + + +--- + +# UIElement + +## Tween + + +```lua +(method) UIElement:Tween(property: string, value: any, duration: number, tweenType: TweenType) +``` + + Tween this element. + + +--- + +# Vector2 -### new +## new ```lua @@ -587,7 +679,7 @@ function Vector2.new(x: number, y: number) Construct a new `Vector2` -### x +## x ```lua @@ -596,7 +688,7 @@ number The x coordinate -### y +## y ```lua @@ -608,36 +700,36 @@ The y coordinate --- -## WorldService +# World The WorldService is responsible for containing and drawing the Room. -### GetPlayer +## GetPlayer ```lua -function WorldService.GetPlayer() +function World.GetPlayer() -> Player ``` Get the Player. -### GetRoom +## GetRoom ```lua -function WorldService.GetRoom() +function World.GetRoom() -> Room ``` Get the current Room -### SetRoom +## SetRoom ```lua -function WorldService.SetRoom(room: string) +function World.SetRoom(room: string) ``` Set the current room using a room title in the game. diff --git a/doxygen.conf b/doxygen.conf index c532f044..283602df 100644 --- a/doxygen.conf +++ b/doxygen.conf @@ -1026,7 +1026,7 @@ WARN_LOGFILE = # spaces. See also FILE_PATTERNS and EXTENSION_MAPPING # Note: If this tag is empty the current directory is searched. -INPUT = "include" +INPUT = include include/ui_elements # This tag can be used to specify the character encoding of the source files # that Doxygen parses. Internally Doxygen uses the UTF-8 encoding. Doxygen uses @@ -1130,7 +1130,7 @@ RECURSIVE = NO # Note that relative paths are relative to the directory from which Doxygen is # run. -EXCLUDE = +EXCLUDE = "ini.h" # The EXCLUDE_SYMLINKS tag can be used to select whether or not files or # directories that are symbolic links (a Unix file system feature) are excluded diff --git a/include/colorRect.hpp b/include/colorRect.hpp deleted file mode 100644 index adab37c2..00000000 --- a/include/colorRect.hpp +++ /dev/null @@ -1,22 +0,0 @@ -#ifndef _RPGPP_COLORRECT_H -#define _RPGPP_COLORRECT_H - -#include - -#include "uiElement.hpp" - -class ColorRect : public UIElement { -private: - Rectangle rect; - Color color; - -public: - ColorRect(); - - explicit ColorRect(Rectangle rect); - void setColor(Color newColor); - void update() override; - void draw() override; -}; - -#endif diff --git a/include/dialogueBalloon.hpp b/include/dialogueBalloon.hpp index 16798715..8c35287c 100644 --- a/include/dialogueBalloon.hpp +++ b/include/dialogueBalloon.hpp @@ -41,46 +41,4 @@ struct DialogueBin { std::vector lines; }; -class DialogueBalloon { -private: - std::string fontName = "LanaPixel"; - Font font; - Rectangle rect; - Rectangle textRect; - Rectangle textPortraitRect; - Rectangle optionsRect; - DialogueBin dialogue; - std::string text; - DialogueTextSection sectionText; - - bool firstCharTyped; - bool finishedTyping = false; - bool active; - int frameCounter; - int charIndex; - int lineIndex; - int sectionIndex; - int lastSectionLen; - - Color textColor; - Vector2 textPos; - bool delay = false; - float delayDuration = 0.0f; - int hoveredOption = 0; - float padding = 0.0f; - float maxLineHeight = 0.0f; - bool appliedTag = false; - - void drawPortrait() const; - -public: - DialogueBalloon(); - DialogueBalloon(Rectangle rect); - void update(); - void draw(); - void showDialogue(const DialogueBin &newDialogue); - void hideDialogue(); - void charP(Vector2 charMeasure, const char *c, DialogueLine &textLine, DialogueTextSection &textSection); -}; - #endif diff --git a/include/dialogueInterfaceView.hpp b/include/dialogueInterfaceView.hpp new file mode 100644 index 00000000..f7aa6d0a --- /dev/null +++ b/include/dialogueInterfaceView.hpp @@ -0,0 +1,32 @@ +#ifndef _RPGPP_DIALOGUEINTERFACEVIEW_H +#define _RPGPP_DIALOGUEINTERFACEVIEW_H + +#include + +#include "dialogue.hpp" +#include "dialogueBalloon.hpp" +#include "gamedata.hpp" +#include "interfaceView.hpp" + +class DialogueInterfaceView : public InterfaceView { +public: + DialogueBin dialogue; + int optionsCount = 0; + bool notifiedEndLine = false; + + DialogueInterfaceView(); + + DialogueInterfaceView(const std::string &filePath); + DialogueInterfaceView(InterfaceViewBin &bin); + + void setDialogue(DialogueBin dialogue); + + void onNotify(Event event); + + void update(); + void draw(); + + void removeOptionButtons(); +}; + +#endif diff --git a/include/drawHelper.hpp b/include/drawHelper.hpp new file mode 100644 index 00000000..7c823da4 --- /dev/null +++ b/include/drawHelper.hpp @@ -0,0 +1,8 @@ +#ifndef _RPGPP_DRAWHELPER_H +#define _RPGPP_DRAWHELPER_H + +#include "raylib.h" + +void DrawRectangleLinesPro(Rectangle rect, Color color); + +#endif \ No newline at end of file diff --git a/include/editor/actions/action.hpp b/include/editor/actions/action.hpp index 22415aea..7dabcfb0 100644 --- a/include/editor/actions/action.hpp +++ b/include/editor/actions/action.hpp @@ -1,12 +1,20 @@ #ifndef _RPGPP_ACTION_H #define _RPGPP_ACTION_H +#include class Action { public: bool executeOnAdd = true; Action() = default; - virtual void execute() {}; - virtual void undo() {}; + virtual void execute() { + onAction(); + }; + virtual void undo() { + onUndo(); + }; + + std::function onAction; + std::function onUndo; }; -#endif \ No newline at end of file +#endif diff --git a/include/editor/childWindows/editListFieldWindow.hpp b/include/editor/childWindows/editListFieldWindow.hpp index 5496ef6f..01b2ae93 100644 --- a/include/editor/childWindows/editListFieldWindow.hpp +++ b/include/editor/childWindows/editListFieldWindow.hpp @@ -80,11 +80,19 @@ inline void EditListFieldWindow::addItem(int index) { auto &newItem = list->emplace_back(); auto newField = TextField::create(); newField->setSize({"100%", 24}); - newField->label->setText(TextFormat("[%i]", list->size() - 1)); + newField->label->setText(TextFormat("[%lu]", list->size() - 1)); newField->value->onTextChange([&newItem, this](const tgui::String &text) { newItem = text.toStdString(); field->value->setText(VecToString(*list)); }); + + newField->enableRemoving(); + newField->remove->onClick([this, &newField, index] { + list->erase(list->begin() + index); + layout->remove(newField); + field->value->setText(VecToString(*list)); + }); + layout->add(newField); } else { auto &newItem = list->at(index); @@ -96,6 +104,14 @@ inline void EditListFieldWindow::addItem(int index) { newItem = text.toStdString(); field->value->setText(VecToString(*list)); }); + + newField->enableRemoving(); + newField->remove->onClick([this, &newField, index] { + list->erase(list->begin() + index); + setup(list); + field->value->setText(VecToString(*list)); + }); + layout->add(newField); } } @@ -148,4 +164,4 @@ inline void EditListFieldWindow::addItem(int index) { } } -#endif \ No newline at end of file +#endif diff --git a/include/editor/childWindows/elementInitWindow.hpp b/include/editor/childWindows/elementInitWindow.hpp new file mode 100644 index 00000000..814905ef --- /dev/null +++ b/include/editor/childWindows/elementInitWindow.hpp @@ -0,0 +1,23 @@ +#ifndef _RPGPP_ELEMENTINITWINDOW_H +#define _RPGPP_ELEMENTINITWINDOW_H + +#include "TGUI/Widgets/EditBox.hpp" +#include "TGUI/Widgets/TreeView.hpp" +#include "childWindows/popupWindow.hpp" +#include "interfaceView.hpp" + +class ElementInitWindow : public PopupWindow { +private: + tgui::EditBox::Ptr input; + tgui::TreeView::Ptr list; + +public: + InterfaceView *view = nullptr; + tgui::TreeView *tree = nullptr; + ElementInitWindow(); + void init(); + + void onAddElement(const std::string& title, const std::string& type); +}; + +#endif diff --git a/include/editor/childWindows/elementRenameWindow.hpp b/include/editor/childWindows/elementRenameWindow.hpp new file mode 100644 index 00000000..eab172aa --- /dev/null +++ b/include/editor/childWindows/elementRenameWindow.hpp @@ -0,0 +1,22 @@ +#ifndef _RPGPP_ELEMENTRENAMEWINDOW_H +#define _RPGPP_ELEMENTRENAMEWINDOW_H + +#include "TGUI/Widgets/EditBox.hpp" +#include "TGUI/Widgets/TreeView.hpp" +#include "childWindows/popupWindow.hpp" +#include "interfaceView.hpp" + +class ElementRenameWindow : public PopupWindow { +private: + tgui::EditBox::Ptr input; +public: + InterfaceView *view = nullptr; + tgui::TreeView *tree = nullptr; + ElementIndex elementIndex = MAX_ELEMENTS; + ElementRenameWindow(); + void init(); + + void onRenameElement(ElementIndex index, const std::string& newName); +}; + +#endif diff --git a/include/editor/childWindows/nPatchInfoWindow.hpp b/include/editor/childWindows/nPatchInfoWindow.hpp new file mode 100644 index 00000000..02dffca5 --- /dev/null +++ b/include/editor/childWindows/nPatchInfoWindow.hpp @@ -0,0 +1,28 @@ +#ifndef _RPGPP_NPATCHINFOWINDOW_H +#define _RPGPP_NPATCHINFOWINDOW_H + +#include "TGUI/Widgets/Panel.hpp" +#include "childWindows/popupWindow.hpp" +#include "raylib.h" +#include "views/nPatchView.hpp" +#include "widgets/propertyFields/intField.hpp" + +class NPatchInfoWindow : public PopupWindow { +private: + const float FIELD_WIDTH = 130.0f; + +public: + NPatchInfoWindow(); + + tgui::Panel::Ptr topPanel; + IntField::Ptr top; + IntField::Ptr left; + IntField::Ptr bottom; + IntField::Ptr right; + + NPatchView::Ptr view; + + void init(NPatchInfo *info, Texture texture); +}; + +#endif \ No newline at end of file diff --git a/include/editor/childWindows/projectSettingsPanel/game.hpp b/include/editor/childWindows/projectSettingsPanel/game.hpp index 1213ff78..a93d8ce4 100644 --- a/include/editor/childWindows/projectSettingsPanel/game.hpp +++ b/include/editor/childWindows/projectSettingsPanel/game.hpp @@ -3,6 +3,7 @@ #include +#include "TGUI/Widgets/Label.hpp" #include "childWindows/editListFieldWindow.hpp" #include "childWindows/settingsPanel/base.hpp" #include "widgets/propertyFields/boolField.hpp" @@ -12,7 +13,7 @@ class ProjectSettingsPanelGame : public SettingsPanelBase { public: - FileField::Ptr defaultRoom; + FileField::Ptr defaultLoading; FileField::Ptr playerActor; IntField::Ptr tileSize; BoolField::Ptr debugDraw; @@ -25,4 +26,4 @@ class ProjectSettingsPanelGame : public SettingsPanelBase { void setup(Project *project); }; -#endif \ No newline at end of file +#endif diff --git a/include/editor/childWindows/uiElementRefWindow.hpp b/include/editor/childWindows/uiElementRefWindow.hpp new file mode 100644 index 00000000..e5015d2e --- /dev/null +++ b/include/editor/childWindows/uiElementRefWindow.hpp @@ -0,0 +1,28 @@ +#ifndef _RPGPP_UIELEMENTREFWINDOW_H +#define _RPGPP_UIELEMENTREFWINDOW_H + +#include + +#include "TGUI/Widgets/GrowVerticalLayout.hpp" +#include "TGUI/Widgets/ScrollablePanel.hpp" +#include "TGUI/Widgets/TreeView.hpp" +#include "childWindows/popupWindow.hpp" +#include "gamedata.hpp" +#include "interfaceView.hpp" +#include "widgets/propertyFields/uiElementRefField.hpp" + +class UIElementRefWindow : public PopupWindow { +private: + tgui::ScrollablePanel::Ptr panel; + tgui::GrowVerticalLayout::Ptr layout; + tgui::TreeView::Ptr list; + +public: + InterfaceView *view = nullptr; + UIElementRef *ref = nullptr; + UIElementRefField *field = nullptr; + UIElementRefWindow(); + void init(); +}; + +#endif \ No newline at end of file diff --git a/include/editor/components/nPatchLines.hpp b/include/editor/components/nPatchLines.hpp new file mode 100644 index 00000000..79925ead --- /dev/null +++ b/include/editor/components/nPatchLines.hpp @@ -0,0 +1,40 @@ +#ifndef _RPGPP_NPATCHLINES_H +#define _RPGPP_NPATCHLINES_H + +#include "components/resizeDirection.hpp" +#include "raylib.h" + +enum BoxCorners { CORNER_NONE, CORNER_TOPLEFT, CORNER_TOPRIGHT, CORNER_BOTTOMLEFT, CORNER_BOTTOMRIGHT }; + +class NPatchLines { +private: + const float HANDLE_RADIUS = 1.0f; + + Vector2 topLeft; + Vector2 topRight; + Vector2 bottomLeft; + Vector2 bottomRight; + + bool isResizing = false; + Vector2 startMousePos = {0, 0}; + BoxCorners corner; + BoxCorners heldCorner; + + bool isInRect(Vector2 mousePos); + void calcCorners(); + void detectCorner(Vector2 mousePos); + +public: + Texture texture; + NPatchInfo *info = nullptr; + int scale = 1; + + NPatchLines(); + void draw(); + + bool leftMousePressed(Vector2 mousePos); + void mouseMoved(Vector2 mousePos, int snapWidth, int snapHeight); + void leftMouseReleased(Vector2 mousePos); +}; + +#endif \ No newline at end of file diff --git a/include/editor/components/resizableCanvasBox.hpp b/include/editor/components/resizableCanvasBox.hpp index 228b05f9..63679bfa 100644 --- a/include/editor/components/resizableCanvasBox.hpp +++ b/include/editor/components/resizableCanvasBox.hpp @@ -2,10 +2,9 @@ #define RPGPP_RESIZABLECANVASBOX_H #include +#include "components/resizeDirection.hpp" #include "raylib.h" -enum ResizeDirection { NONE = 0, MOVE = 1 << 0, TOP = 1 << 1, BOTTOM = 1 << 2, LEFT = 1 << 3, RIGHT = 1 << 4 }; - class ResizableCanvasBox { public: ResizableCanvasBox(std::string id, float x, float y, float width, float height, Color color, @@ -16,6 +15,7 @@ class ResizableCanvasBox { // @returns true if the box was clicked, false otherwise bool leftMousePressed(Vector2 mousePos); void mouseMoved(Vector2 mousePos, int snapWidth = 1, int snapHeight = 1); + bool mouseMovedTrigger(Vector2 mousePos, int snapWidth = 1, int snapHeight = 1); // @returns the new rectangle after the mouse is released Rectangle leftMouseReleased(Vector2 mousePos); @@ -24,8 +24,10 @@ class ResizableCanvasBox { void updatePosition(float x, float y); void updateSize(float width, float height); void updateColor(Color color); - void updateRec(Rectangle rec); + + void setResizeMargin(float newResizeMargin); + bool focused = false; std::string id{}; @@ -33,7 +35,7 @@ class ResizableCanvasBox { float getMinSize() const { return minSize; } private: - const float RESIZE_MARGIN = 1.f; + float resizeMargin = 1.f; float minSize = 2.f; bool isResizable = true; @@ -43,7 +45,10 @@ class ResizableCanvasBox { bool isResizing = false; Vector2 startMousePos{}; float prevX = 0, prevY = 0, prevWidth = 0, prevHeight = 0; - int resizeDirection = NONE; + int activeGrabber = NONE; + int inGrabber(Vector2 pos); + bool cursorModified = false; + void updateCursor(Vector2 absolutePos); }; #endif diff --git a/include/editor/components/resizableContainer.hpp b/include/editor/components/resizableContainer.hpp index b5f92c48..61768f07 100644 --- a/include/editor/components/resizableContainer.hpp +++ b/include/editor/components/resizableContainer.hpp @@ -4,8 +4,7 @@ #include "TGUI/Signal.hpp" #include "TGUI/Vector2.hpp" #include "TGUI/Widgets/Group.hpp" - -enum class ResizeDirection { MOVE = 0, LEFT = 1 << 0, RIGHT = 1 << 1, TOP = 1 << 2, BOTTOM = 1 << 3 }; +#include "resizeDirection.hpp" class ResizableContainer : public tgui::Group { private: @@ -24,6 +23,7 @@ class ResizableContainer : public tgui::Group { bool cursorModified = false; bool inEnabledGrabber(ResizeDirection direction, tgui::Vector2f absolutePos); + void updateCursor(tgui::Vector2f absolutePos); public: ResizableContainer(const tgui::Layout2d &size, const tgui::Layout2d &position); diff --git a/include/editor/components/resizeDirection.hpp b/include/editor/components/resizeDirection.hpp new file mode 100644 index 00000000..94f65ac0 --- /dev/null +++ b/include/editor/components/resizeDirection.hpp @@ -0,0 +1,6 @@ +#ifndef _RPGPP_RESIZEDIRECTION_H +#define _RPGPP_RESIZEDIRECTION_H + +enum ResizeDirection { NONE = 0, MOVE = 1 << 0, TOP = 1 << 1, BOTTOM = 1 << 2, LEFT = 1 << 3, RIGHT = 1 << 4 }; + +#endif diff --git a/include/editor/fileInitVisitor.hpp b/include/editor/fileInitVisitor.hpp index c0cad4e5..8cb2faa0 100644 --- a/include/editor/fileInitVisitor.hpp +++ b/include/editor/fileInitVisitor.hpp @@ -22,6 +22,7 @@ class FileInitVisitor { static void prop(NewFileDialog::Ptr dialog); static void dialogue(NewFileDialog::Ptr dialog); static void interactable(NewFileDialog::Ptr dialog); + static void interface(NewFileDialog::Ptr dialog); }; #endif diff --git a/include/editor/fileViews/actorFileView.hpp b/include/editor/fileViews/actorFileView.hpp index 854649ac..4d0ec334 100644 --- a/include/editor/fileViews/actorFileView.hpp +++ b/include/editor/fileViews/actorFileView.hpp @@ -1,6 +1,7 @@ #ifndef RPGPP_ACTORFILEVIEW_H #define RPGPP_ACTORFILEVIEW_H +#include #include "fileViews/fileView.hpp" #include "views/actorView.hpp" #include "widgets/frameEditor.hpp" diff --git a/include/editor/fileViews/fileView.hpp b/include/editor/fileViews/fileView.hpp index f70001ab..d9afb861 100644 --- a/include/editor/fileViews/fileView.hpp +++ b/include/editor/fileViews/fileView.hpp @@ -13,13 +13,12 @@ class FileView { protected: VariantWrapper *variant; std::vector widgetContainer; - std::vector> actions; - int currentAction = -1; - std::vector>::iterator iter; std::stack> past; std::stack> future; + bool dirty = false; + public: bool fileViewFocused = false; @@ -33,6 +32,9 @@ class FileView { void pushAction(std::unique_ptr action); void undoAction(); void redoAction(); + + void setDirty(bool value = true); + bool getDirty(); }; #endif diff --git a/include/editor/fileViews/interfaceViewFileView.hpp b/include/editor/fileViews/interfaceViewFileView.hpp new file mode 100644 index 00000000..86f50504 --- /dev/null +++ b/include/editor/fileViews/interfaceViewFileView.hpp @@ -0,0 +1,39 @@ +#ifndef _RPGPP_FILEVIEWS_UIFILEVIEW_H +#define _RPGPP_FILEVIEWS_UIFILEVIEW_H + +#include + +#include "TGUI/Widgets/ContextMenu.hpp" +#include "TGUI/Widgets/TreeView.hpp" +#include "fileViews/fileView.hpp" +#include "nlohmann/json_fwd.hpp" +#include "uiElementPropVisitor.hpp" +#include "views/interfaceViewView.hpp" +#include "widgets/propertiesBox.hpp" +#include "widgets/propertyFields/fileField.hpp" + +class InterfaceViewFileView : public FileView { +private: + static const int RIGHT_PANEL_W = 300; + + tgui::TreeView::Ptr treeView; + FileField::Ptr scriptFileField; + PropertiesBox::Ptr propertiesBox; + InterfaceViewView::Ptr view; + + IntField::Ptr snapGridField; + + tgui::ContextMenu::Ptr elementContextMenu; + std::string selectedElement; + + UIElementPropVisitor visitor; + std::unique_ptr> editListFieldWindow; + +public: + InterfaceViewFileView(); + void init(tgui::Group::Ptr layout, VariantWrapper *variant) override; + void visitProps(const std::string &title); + void populateTree(); +}; + +#endif diff --git a/include/editor/projectFile.hpp b/include/editor/projectFile.hpp index 1de8129d..31ab2386 100644 --- a/include/editor/projectFile.hpp +++ b/include/editor/projectFile.hpp @@ -27,6 +27,8 @@ class ProjectFile { void addWidgets(tgui::Group::Ptr layout); void saveFile(const std::string &path); FileView &getView(); + FileView* getViewPtr(); + EngineFileType getFileType(); }; #endif diff --git a/include/editor/projectFileVisitor.hpp b/include/editor/projectFileVisitor.hpp index bace4ade..41a50602 100644 --- a/include/editor/projectFileVisitor.hpp +++ b/include/editor/projectFileVisitor.hpp @@ -28,6 +28,7 @@ class ProjectFileVisitor { static std::unique_ptr soundView(const std::string &path); static std::unique_ptr musicView(const std::string &path); static std::unique_ptr interactableView(const std::string &path); + static std::unique_ptr interfaceView(const std::string &path); }; #endif diff --git a/include/editor/screens/projectScreen.hpp b/include/editor/screens/projectScreen.hpp index d879de47..650f8565 100644 --- a/include/editor/screens/projectScreen.hpp +++ b/include/editor/screens/projectScreen.hpp @@ -13,7 +13,6 @@ #include "projectFile.hpp" #include "projectFileVisitor.hpp" #include "services/fileSystemService.hpp" -#include "services/translationService.hpp" #include "widgets/fileTab.hpp" namespace screens { diff --git a/include/editor/services/childWindowSubService.hpp b/include/editor/services/childWindowSubService.hpp index 81b4cf8c..1df4789b 100644 --- a/include/editor/services/childWindowSubService.hpp +++ b/include/editor/services/childWindowSubService.hpp @@ -7,7 +7,7 @@ class ChildWindowSubService { private: - std::map> childWindows = {}; + std::unordered_map> childWindows = {}; public: ChildWindowSubService(); diff --git a/include/editor/services/editorGuiService.hpp b/include/editor/services/editorGuiService.hpp index 7d67c5fa..807ca62d 100644 --- a/include/editor/services/editorGuiService.hpp +++ b/include/editor/services/editorGuiService.hpp @@ -20,6 +20,8 @@ constexpr int ACTION_BUTTON_SIZE = 16; class EditorGuiService { private: + Font font; + std::vector> updatableWidgets; std::unique_ptr childWindowService; PerformanceOverlay perfOverlay; @@ -35,9 +37,6 @@ class EditorGuiService { EditorGuiService(); ~EditorGuiService() = default; - // I have no fucking clue what this is. - // int setScreen(int _cpp_par_); - std::unique_ptr gui; std::unique_ptr currentScreen; std::deque> screenHistory; @@ -64,6 +63,9 @@ class EditorGuiService { void alert(tgui::String title, tgui::String content); static void createLogoCenter(const tgui::GrowVerticalLayout::Ptr &layout); static void centerWidget(tgui::Widget::Ptr widget); + + Font getFont(); + void unload(); }; #endif diff --git a/include/editor/services/fileSystemService.hpp b/include/editor/services/fileSystemService.hpp index bb98a5fa..95912b8b 100644 --- a/include/editor/services/fileSystemService.hpp +++ b/include/editor/services/fileSystemService.hpp @@ -10,7 +10,7 @@ #include "TGUI/String.hpp" #include "variant.hpp" -#define FILETYPE_MAX 12 +#define FILETYPE_MAX 13 enum class EngineFileType { FILE_TILESET, @@ -24,6 +24,7 @@ enum class EngineFileType { FILE_MUSIC, FILE_PROP, FILE_INTERACTABLE, + FILE_INTERFACEVIEW, FILE_EMPTY, }; diff --git a/include/editor/uiElementPropVisitor.hpp b/include/editor/uiElementPropVisitor.hpp new file mode 100644 index 00000000..c9ba750c --- /dev/null +++ b/include/editor/uiElementPropVisitor.hpp @@ -0,0 +1,36 @@ +#ifndef _RPGPP_UIELEMENTPROPVISITOR_H +#define _RPGPP_UIELEMENTPROPVISITOR_H + +#include "childWindows/editListFieldWindow.hpp" +#include "screens/projectScreen.hpp" +#include "widgets/propertiesBox.hpp" + +struct UIElementPropVisitor { + PropertiesBox *box = nullptr; + InterfaceView *view = nullptr; + UIElement *element = nullptr; + std::string key; + void operator()(int val); + void operator()(bool val); + void operator()(const std::string &val); + void operator()(Rectangle val); + void operator()(Color val); + void operator()(FontRef val); + void operator()(ImageRef val); + void operator()(UIElementRef val); + void operator()(VerticalAlignment val); + void operator()(HorizontalAlignment val); + void operator()(NPatchInfo val); + void operator()(StringVector val); + void operator()(InputC val); + + void uiElementRef(UIElementRef *ref, const std::string &key); + + EditListFieldWindow *editListFieldWindow; + screens::ProjectScreen* screen; + int currentItemId = 0; + + void visitProps(); +}; + +#endif diff --git a/include/editor/views/actorView.hpp b/include/editor/views/actorView.hpp index 19933fe1..4154bcd8 100644 --- a/include/editor/views/actorView.hpp +++ b/include/editor/views/actorView.hpp @@ -3,6 +3,7 @@ #include +#include "TGUI/Signal.hpp" #include "actor.hpp" #include "components/resizableCanvasBox.hpp" #include "raylib.h" @@ -23,6 +24,7 @@ class ActorView : public WorldView { ActorView(ActorFileView *actorFileView); Actor *actor{nullptr}; + tgui::Signal onAttributeChanged = {"OnFrameChanged"}; // Animation Settings bool isPlaying{false}; diff --git a/include/editor/views/interfaceViewView.hpp b/include/editor/views/interfaceViewView.hpp new file mode 100644 index 00000000..aa72c294 --- /dev/null +++ b/include/editor/views/interfaceViewView.hpp @@ -0,0 +1,55 @@ +#ifndef _RPGPP_INTERFACEVIEWVIEW_H +#define _RPGPP_INTERFACEVIEWVIEW_H + +#include +#include + +#include "TGUI/Signal.hpp" +#include "components/resizableCanvasBox.hpp" +#include "interfaceView.hpp" +#include "sol/state.hpp" +#include "uiElementPropVisitor.hpp" +#include "views/worldView.hpp" +#include "widgets/propertiesBox.hpp" + +class InterfaceViewView : public WorldView { +private: + std::unique_ptr canvasBox; + bool hasActiveElement = false; + ElementIndex activeElement = MAX_ELEMENTS; + void setElementAtMouse(); + int activeSnapSize = 1; + +public: + typedef std::shared_ptr Ptr; + + tgui::SignalTyped onActiveElementChanged = {"ActiveElementChanged"}; + tgui::SignalTyped onActiveEntityChanged = {"ActiveEntityChanged"}; + + InterfaceViewView(); + + InterfaceView *ptr{nullptr}; + PropertiesBox *propBox{nullptr}; + UIElementPropVisitor *visitor{nullptr}; + + int gridSnapSize = 4; + + void drawCanvas() override; + void drawOverlay() override; + + static InterfaceViewView::Ptr create(); + + void setInterfaceView(InterfaceView *ptr); + + void update() override; + + bool leftMousePressed(tgui::Vector2f pos) override; + void leftMouseReleased(tgui::Vector2f pos) override; + void mouseMoved(tgui::Vector2f pos) override; + + void selectElement(const std::string &elementName); + + void visitProps(const std::string &title); +}; + +#endif diff --git a/include/editor/views/nPatchView.hpp b/include/editor/views/nPatchView.hpp new file mode 100644 index 00000000..c840a9ac --- /dev/null +++ b/include/editor/views/nPatchView.hpp @@ -0,0 +1,36 @@ +#ifndef _RPGPP_NPATCHVIEW_H +#define _RPGPP_NPATCHVIEW_H + +#include "TGUI/Signal.hpp" +#include "components/nPatchLines.hpp" +#include "gamedata.hpp" +#include "raylib.h" +#include "views/worldView.hpp" + +class NPatchView : public WorldView { +public: + typedef std::shared_ptr Ptr; + + NPatchView(); + + tgui::SignalTyped onInfoChanged = {"InfoChanged"}; + + Texture texture; + NPatchInfo *info; + int scale = 1; + + NPatchLines lines; + + void drawCanvas() override; + void drawOverlay() override; + + static NPatchView::Ptr create(); + + void setup(NPatchInfo *info, Texture texture, int scale); + + bool leftMousePressed(tgui::Vector2f pos) override; + void leftMouseReleased(tgui::Vector2f pos) override; + void mouseMoved(tgui::Vector2f pos) override; +}; + +#endif \ No newline at end of file diff --git a/include/editor/views/roomView.hpp b/include/editor/views/roomView.hpp index 4400d5dd..ed6f8748 100644 --- a/include/editor/views/roomView.hpp +++ b/include/editor/views/roomView.hpp @@ -3,6 +3,7 @@ #include +#include "TGUI/Signal.hpp" #include "TGUI/Vector2.hpp" #include "TGUI/Widgets/ComboBox.hpp" #include "fileViews/fileView.hpp" @@ -42,6 +43,7 @@ class RoomView : public WorldView { FileView *fileView; tgui::ComboBox *interactableChoose; tgui::ComboBox *propChoose; + tgui::Signal onAttributeChanged = {"OnAttributeChanged"}; RoomLayerViewVisitor *layerVisitor; RoomView(); diff --git a/include/editor/views/worldView.hpp b/include/editor/views/worldView.hpp index d4186ee5..69a0d6c7 100644 --- a/include/editor/views/worldView.hpp +++ b/include/editor/views/worldView.hpp @@ -56,7 +56,7 @@ class WorldView : public tgui::CanvasRaylib, public IUpdatable { void drawOrigin(); - void update() override; + virtual void update() override; static std::shared_ptr asUpdatable(const std::shared_ptr &ptr); void setTool(RoomTool newTool); diff --git a/include/editor/widgets/dialogueEditor.hpp b/include/editor/widgets/dialogueEditor.hpp index 05b2ba8b..927ef9f2 100644 --- a/include/editor/widgets/dialogueEditor.hpp +++ b/include/editor/widgets/dialogueEditor.hpp @@ -47,7 +47,7 @@ class DialogueEditor : public tgui::TextArea { * This fixes an interesting case with TGUI .w. */ void fixSelectionRange(); - bool isTextNonEditable(std::string& tagName); + bool isTextNonEditable(std::string &tagName); }; #endif /* _RPGPP_DIALOGUEEDITOR_HPP */ diff --git a/include/editor/widgets/fileTab.hpp b/include/editor/widgets/fileTab.hpp index 6f559474..e6362ae1 100644 --- a/include/editor/widgets/fileTab.hpp +++ b/include/editor/widgets/fileTab.hpp @@ -2,12 +2,14 @@ #define _RPGPP_FILETAB_H #include +#include #include "TGUI/Signal.hpp" #include "TGUI/Widget.hpp" #include "TGUI/Widgets/Tabs.hpp" #include "components/tooltip.hpp" #include "fileTabRenderer.hpp" +#include "fileViews/fileView.hpp" class FileTab : public tgui::Tabs { private: @@ -28,9 +30,10 @@ class FileTab : public tgui::Tabs { bool cursorModified = false; - void renderTab(tgui::BackendRenderTarget &target, tgui::RenderStates &states, int idx, bool roundedCorners, - float borderWidth, float usableHeight, tgui::Sprite &close) const; + void renderTab(tgui::BackendRenderTarget &target, tgui::RenderStates &states, int idx, float borderWidth, + float usableHeight, tgui::Sprite &close) const; void closeAndOpenNextTab(std::size_t idx); + std::map m_fileViews; public: bool useExternalMouseEvent = false; @@ -61,7 +64,10 @@ class FileTab : public tgui::Tabs { bool select(std::size_t i); - size_t addFileTab(const std::string &path, const std::string &fileName); + tgui::TabsBase::Tab *getTabId(const std::string id); + tgui::TabsBase::Tab *getTabName(const std::string fileName); + size_t addFileTab(const std::string &path, const std::string &fileName, FileView *fileView); + void closeTabFilename(std::string fileName); void closeCurrentTab(); protected: diff --git a/include/editor/widgets/frameEditor.hpp b/include/editor/widgets/frameEditor.hpp index 31885fa6..b963c579 100644 --- a/include/editor/widgets/frameEditor.hpp +++ b/include/editor/widgets/frameEditor.hpp @@ -4,12 +4,10 @@ #include #include -#include "TGUI/SubwidgetContainer.hpp" +#include "TGUI/Signal.hpp" #include "TGUI/Widget.hpp" -#include "TGUI/Widgets/Button.hpp" #include "TGUI/Widgets/ComboBox.hpp" #include "TGUI/Widgets/GrowHorizontalLayout.hpp" -#include "TGUI/Widgets/Panel.hpp" #include "TGUI/Widgets/ScrollablePanel.hpp" #include "TGUI/Widgets/ToggleButton.hpp" #include "components/frameButton.hpp" @@ -32,6 +30,7 @@ class FrameEditor : public tgui::ScrollablePanel { typedef std::shared_ptr Ptr; static FrameEditor::Ptr create(ActorFileView *fileView); + tgui::Signal onAttributeChanged = {"OnAttributeChanged"}; void init(); diff --git a/include/editor/widgets/propertiesBox.hpp b/include/editor/widgets/propertiesBox.hpp index f5850dd8..6ea11edc 100644 --- a/include/editor/widgets/propertiesBox.hpp +++ b/include/editor/widgets/propertiesBox.hpp @@ -4,21 +4,27 @@ #include #include +#include "TGUI/Signal.hpp" #include "TGUI/String.hpp" #include "TGUI/Widget.hpp" #include "TGUI/Widgets/Button.hpp" #include "TGUI/Widgets/ChildWindow.hpp" #include "TGUI/Widgets/GrowVerticalLayout.hpp" +#include "TGUI/Widgets/ScrollablePanel.hpp" #include "interactable.hpp" #include "widgets/propertyFields/boolField.hpp" +#include "widgets/propertyFields/colorField.hpp" #include "widgets/propertyFields/fileField.hpp" #include "widgets/propertyFields/intField.hpp" #include "widgets/propertyFields/interPropField.hpp" +#include "widgets/propertyFields/listField.hpp" +#include "widgets/propertyFields/nPatchInfoField.hpp" #include "widgets/propertyFields/rectangleField.hpp" #include "widgets/propertyFields/selectField.hpp" #include "widgets/propertyFields/textField.hpp" +#include "widgets/propertyFields/uiElementRefField.hpp" -class PropertiesBox : public tgui::ChildWindow { +class PropertiesBox : public tgui::ScrollablePanel { protected: static const int GAP = 4; @@ -30,6 +36,8 @@ class PropertiesBox : public tgui::ChildWindow { typedef std::shared_ptr Ptr; typedef std::shared_ptr ConstPtr; + tgui::SignalTyped onJsonChanged = {"JsonChanged"}; + Interactable *interactable = nullptr; PropertiesBox(const char *typeName = "PropertiesBox", bool initRenderer = true); @@ -41,17 +49,32 @@ class PropertiesBox : public tgui::ChildWindow { void addPropsJson(nlohmann::json &j, bool clear = true, bool editable = false); void addIntField(const tgui::String &title, int initialValue, std::function callback); - void addIntField(IntField::Ptr field); - void addFileField(FileField::Ptr field); - void addTextField(TextField::Ptr field); - void addBooleanField(BoolField::Ptr field); - void addRectangleField(RectangleField::Ptr field); - void addSelectField(SelectField::Ptr field); + void addIntField(IntField::Ptr field, const std::string& title = ""); + void addFileField(FileField::Ptr field, const std::string& title = ""); + void addTextField(TextField::Ptr field, const std::string& title = ""); + void addBooleanField(BoolField::Ptr field, const std::string& title = ""); + void addRectangleField(RectangleField::Ptr field, const std::string& title = ""); + void addSelectField(SelectField::Ptr field, const std::string& title = ""); + void addColorField(ColorField::Ptr field, const std::string& title = ""); + void addRefField(UIElementRefField::Ptr field, const std::string& title = ""); + void addNPatchFIeld(NPatchInfoField::Ptr field, const std::string& title = ""); + + template + void addListField(typename ListField::Ptr field) { + field->setSize({"100%", 24}); + layout->add(field); + } + void addButton(const tgui::String &title, std::function callback); void addInterPropField(InterPropField::Ptr field); void addPropertiesBox(PropertiesBox::Ptr box); void addWidget(tgui::Widget::Ptr widget); tgui::Button::Ptr constructButton(const tgui::String &title, std::function callback); + void addSection(const tgui::String &title); + + tgui::Widget* getPropertyField(const std::string& title); + + void clear(); }; #endif diff --git a/include/editor/widgets/propertyFields/colorField.hpp b/include/editor/widgets/propertyFields/colorField.hpp new file mode 100644 index 00000000..38916e79 --- /dev/null +++ b/include/editor/widgets/propertyFields/colorField.hpp @@ -0,0 +1,45 @@ +#ifndef _RPGPP_COLORFIELD_H +#define _RPGPP_COLORFIELD_H + +#include "TGUI/Color.hpp" +#include "TGUI/Signal.hpp" +#include "TGUI/SubwidgetContainer.hpp" +#include "TGUI/Widget.hpp" +#include "TGUI/Widgets/Button.hpp" +#include "TGUI/Widgets/ColorPicker.hpp" +#include "TGUI/Widgets/Group.hpp" +#include "TGUI/Widgets/Label.hpp" +#include "TGUI/Widgets/Panel.hpp" +#include "raylib.h" + +class ColorField : public tgui::Group { +private: + void updateSize(); + tgui::Color color = {255, 0, 0}; + +protected: + tgui::Widget::Ptr clone() const override; + +public: + tgui::Label::Ptr label; + tgui::Button::Ptr value; + tgui::ColorPicker::Ptr panel; + + tgui::SignalTyped onColorChanged = {"ColorChanged"}; + + typedef std::shared_ptr Ptr; + typedef std::shared_ptr ConstPtr; + + ColorField(const char *typeName = "ColorField", bool initRenderer = true); + + static ColorField::Ptr create(); + static ColorField::Ptr create(const tgui::String &label, const tgui::String &value); + static ColorField::Ptr copy(ColorField::ConstPtr widget); + + void setSize(const tgui::Layout2d &size) override; + + void setColor(Color color); + void setColor(tgui::Color color); +}; + +#endif diff --git a/include/editor/widgets/propertyFields/fieldConfig.hpp b/include/editor/widgets/propertyFields/fieldConfig.hpp index fa5ce9d9..34f6a6e7 100644 --- a/include/editor/widgets/propertyFields/fieldConfig.hpp +++ b/include/editor/widgets/propertyFields/fieldConfig.hpp @@ -1 +1,6 @@ +#ifndef _RPGPP_PROPERTYFIELDS_FIELDCONFIG_H +#define _RPGPP_PROPERTYFIELDS_FIELDCONFIG_H + static const int PADDING = 8; + +#endif diff --git a/include/editor/widgets/propertyFields/nPatchInfoField.hpp b/include/editor/widgets/propertyFields/nPatchInfoField.hpp new file mode 100644 index 00000000..8a2bdda0 --- /dev/null +++ b/include/editor/widgets/propertyFields/nPatchInfoField.hpp @@ -0,0 +1,37 @@ +#ifndef _RPGPP_NPATCHINFOFIELD_H +#define _RPGPP_NPATCHINFOFIELD_H + +#include "TGUI/SubwidgetContainer.hpp" +#include "TGUI/Widgets/Button.hpp" +#include "TGUI/Widgets/Label.hpp" +#include "gamedata.hpp" +#include "interfaceView.hpp" +#include "raylib.h" + +class NPatchInfoField : public tgui::SubwidgetContainer { +private: + void updateSize(); + +protected: + tgui::Widget::Ptr clone() const override; + +public: + tgui::Label::Ptr label; + tgui::Button::Ptr value; + + typedef std::shared_ptr Ptr; + typedef std::shared_ptr ConstPtr; + + NPatchInfoField(const char *typeName = "NPatchInfoField", bool initRenderer = true); + + static NPatchInfoField::Ptr create(); + static NPatchInfoField::Ptr create(const tgui::String &label, const tgui::String &value); + static NPatchInfoField::Ptr copy(NPatchInfoField::ConstPtr widget); + + void setSize(const tgui::Layout2d &size) override; + + NPatchInfo *info = nullptr; + ImageRef *imageRef = nullptr; +}; + +#endif diff --git a/include/editor/widgets/propertyFields/textField.hpp b/include/editor/widgets/propertyFields/textField.hpp index d3d68e1d..2a3180f5 100644 --- a/include/editor/widgets/propertyFields/textField.hpp +++ b/include/editor/widgets/propertyFields/textField.hpp @@ -17,6 +17,8 @@ class TextField : public tgui::SubwidgetContainer { public: tgui::Label::Ptr label; tgui::EditBox::Ptr value; + tgui::BitmapButton::Ptr remove; + bool removable = false; typedef std::shared_ptr Ptr; typedef std::shared_ptr ConstPtr; @@ -27,6 +29,8 @@ class TextField : public tgui::SubwidgetContainer { static TextField::Ptr copy(TextField::ConstPtr widget); void setSize(const tgui::Layout2d &size) override; + + void enableRemoving(); }; #endif diff --git a/include/editor/widgets/propertyFields/uiElementRefField.hpp b/include/editor/widgets/propertyFields/uiElementRefField.hpp new file mode 100644 index 00000000..c07ae8b6 --- /dev/null +++ b/include/editor/widgets/propertyFields/uiElementRefField.hpp @@ -0,0 +1,36 @@ +#ifndef _RPGPP_UIELEMENTREFFIELD_H +#define _RPGPP_UIELEMENTREFFIELD_H + +#include "TGUI/SubwidgetContainer.hpp" +#include "TGUI/Widgets/Button.hpp" +#include "TGUI/Widgets/Label.hpp" +#include "gamedata.hpp" +#include "interfaceView.hpp" + +class UIElementRefField : public tgui::SubwidgetContainer { +private: + void updateSize(); + +protected: + tgui::Widget::Ptr clone() const override; + +public: + tgui::Label::Ptr label; + tgui::Button::Ptr value; + + typedef std::shared_ptr Ptr; + typedef std::shared_ptr ConstPtr; + + UIElementRefField(const char *typeName = "UIElementRefField", bool initRenderer = true); + + static UIElementRefField::Ptr create(); + static UIElementRefField::Ptr create(const tgui::String &label, const tgui::String &value); + static UIElementRefField::Ptr copy(UIElementRefField::ConstPtr widget); + + void setSize(const tgui::Layout2d &size) override; + + InterfaceView *view = nullptr; + UIElementRef *ref = nullptr; +}; + +#endif \ No newline at end of file diff --git a/include/game.hpp b/include/game.hpp index 680e86c2..66cbdccf 100644 --- a/include/game.hpp +++ b/include/game.hpp @@ -22,6 +22,7 @@ class Game { static Game *instance_; static std::unique_ptr gameData; static bool usesBin; + static bool willClose; static std::unique_ptr state; static std::unique_ptr world; static std::unique_ptr ui; @@ -32,6 +33,7 @@ class Game { public: Game(); static Game &instance(); + static Game *instancePtr(); static bool isUsingBin(); static void useBin(const std::string &filePath); static GameData &getBin(); @@ -42,13 +44,16 @@ class Game { static SoundService &getSounds(); static ScriptService &getScripts(); - static void init(); + static void init(bool useBin = false); static void update(); static void draw(); static void unload(); static void setLua(sol::state_view lua); + + static void closeGame(); + static bool windowWillClose(); }; #endif diff --git a/include/gamedata.hpp b/include/gamedata.hpp index 8913f704..cdd19922 100644 --- a/include/gamedata.hpp +++ b/include/gamedata.hpp @@ -4,9 +4,15 @@ #include #include +#include +#include +#include +#include #include #include #include +#include +#include #include #include "dialogueBalloon.hpp" @@ -39,6 +45,94 @@ struct IRect { int height; }; +struct UIElementRef { + std::string title = ""; + uint8_t entityId = 255; +}; + +struct FontRef { + std::string path = ""; + Font font; + int fontSize = 13; +}; + +struct ImageRef { + std::string path = ""; + Texture texture; + int scale = 1; + void scaleImage(int newScale) { + this->scale = newScale; + auto loadedImage = LoadImage(TextFormat("images/%s", path.c_str())); + ImageResizeNN(&loadedImage, loadedImage.width * scale, loadedImage.height * scale); + texture = LoadTextureFromImage(loadedImage); + UnloadImage(loadedImage); + } +}; + +const std::string CALLBACK_TRIGGER = "callback_trigger"; +const std::string CALLBACK_FOCUSED = "callback_focused"; +const std::string CALLBACK_UNFOCUSED = "callback_unfocused"; + +#define RPGPP_CALLBACK_MAX (3) + +struct CallbacksArray { + std::unordered_map funcNames = { + {CALLBACK_TRIGGER, ""}, + {CALLBACK_UNFOCUSED, ""}, + {CALLBACK_FOCUSED, ""} + }; +}; + +struct InputC { + UIElementRef upButton; + UIElementRef downButton; + UIElementRef leftButton; + UIElementRef rightButton; + + CallbacksArray funcNames; +}; + +enum TextAlignment { + TEXT_ALIGN_LEFT = 0, + TEXT_ALIGN_TOP = 0, + TEXT_ALIGN_CENTRE = 1, + TEXT_ALIGN_MIDDLE = 1, + TEXT_ALIGN_RIGHT = 2, + TEXT_ALIGN_BOTTOM = 2 +}; + +struct VerticalAlignment { + TextAlignment val = TEXT_ALIGN_TOP; +}; + +struct HorizontalAlignment { + TextAlignment val = TEXT_ALIGN_LEFT; +}; + +enum ElementPropertyType { + UI_PROP_INT, + UI_PROP_BOOL, + UI_PROP_STRING, + UI_PROP_RECT, + UI_PROP_COLOR, + UI_PROP_FONT, + UI_PROP_IMAGE, + UI_PROP_REF, + UI_PROP_NPATCHINFO, + UI_PROP_INPUT +}; + +typedef std::vector StringVector; + +typedef std::variant + ElementProperty; + +struct Event { + KeyboardKey key; + bool hold = false; +}; + struct ActorBin { std::string name; std::string tileSetName; @@ -134,8 +228,15 @@ struct RoomBin { std::string musicSource; }; -struct GameBinSettings { - std::string playerActor; +struct UIElementBin { + std::string type = ""; + std::unordered_map props; +}; + +struct InterfaceViewBin { + std::string scriptSource = ""; + std::unordered_map> entites; + std::unordered_map elements = {}; }; struct ProjectProgramSettings { @@ -149,7 +250,8 @@ struct ProjectProgramSettings { }; struct ProjectGameSettings { - std::string defaultRoomPath; + std::string defaultLoadingPath; + bool isLoadUi; std::string playerActorPath; int tileSize = 16; bool debugDraw = false; @@ -168,6 +270,7 @@ struct GameData { std::vector rooms; std::map actors; std::vector props; + std::map interfaceViews; std::map dialogues; std::map music; std::map scripts; @@ -181,4 +284,64 @@ struct DataSerialization { void serializeDataToFile(std::string fileName, GameData data); GameData deserializeFile(std::string fileName); +template +void serialize(Archive &a, Rectangle &b) { + a(b.x, b.y, b.width, b.height); +} + +template +void serialize(Archive &a, Color &b) { + a(b.a, b.r, b.g, b.b); +} + +template +void serialize(Archive &a, UIElementRef &b) { + a(b.title); +} + +template +void serialize(Archive &a, ImageRef &b) { + a(b.path, b.scale); +} + +template +void serialize(Archive &a, FontRef &b) { + a(b.path, b.fontSize); +} + +template +void serialize(Archive &a, HorizontalAlignment &b) { + a(b.val); +} + +template +void serialize(Archive &a, VerticalAlignment &b) { + a(b.val); +} + +template +void serialize(Archive &a, NPatchInfo &b) { + a(b.top, b.bottom, b.left, b.right, b.layout); +} + +template +void serialize(Archive &a, InputC &b) { + a(b.upButton, b.downButton, b.leftButton, b.rightButton, b.funcNames); +} + +template +void serialize(Archive &a, CallbacksArray &b) { + a(b.funcNames); +} + +template +void serialize(Archive &a, UIElementBin &b) { + a(b.type, b.props); +} + +template +void serialize(Archive &a, InterfaceViewBin &b) { + a(b.scriptSource, b.entites, b.elements); +} + #endif diff --git a/include/imageRect.hpp b/include/imageRect.hpp deleted file mode 100644 index 3acff511..00000000 --- a/include/imageRect.hpp +++ /dev/null @@ -1,25 +0,0 @@ -#ifndef _RPGPP_IMAGERECT_H -#define _RPGPP_IMAGERECT_H - -#include - -#include - -#include "uiElement.hpp" - -class ImageRect : public UIElement { -private: - Rectangle rect; - std::string source; - Texture2D texture; - -public: - ImageRect(); - ImageRect(Rectangle rect); - void setSource(const std::string &source); - void setTexture(Texture2D texture); - void update(); - void draw(); -}; - -#endif diff --git a/include/interfaceService.hpp b/include/interfaceService.hpp index 97de8ba8..65199e0d 100644 --- a/include/interfaceService.hpp +++ b/include/interfaceService.hpp @@ -8,7 +8,9 @@ #include #include "dialogueBalloon.hpp" +#include "gamedata.hpp" #include "interfaceView.hpp" +#include "ui_elements/elementFactory.hpp" /** The InterfaceService acts for the User Interface (UI). */ class InterfaceService { @@ -16,25 +18,56 @@ class InterfaceService { /** The loaded font that will be used for the User Interface. */ Font font; bool fpsVisible; - /** Texture for UI components. */ - Texture uiTexture; - /** Component for in-game dialogue. */ - DialogueBalloon dialogue; + bool notifyLock = false; + /** Helper for instantiating element types. */ + static ElementFactory factory; /** Available UI Views. */ - std::unique_ptr> views; + std::map> views; + /** Current active view. */ + std::string currentViewName; + /** Last KeyboardKey. */ + KeyboardKey lastKey = KEY_NULL; + + /** Frame counter for transition tween */ + int frameCounter; + bool transitionActive; + Color transitionColor; + float alpha; + bool transitionSecondStage; + std::function onTransitionPoint; public: /** Empty constructor. */ InterfaceService(); ~InterfaceService(); + /** Initialize this service with a GameBin. */ + void initBin(GameData &bin); /** Get the font used for the game's UI. */ Font getFont() const; - /** Get the texture, used for UI nine-patch components. */ - Texture getTexture() const; /** Open a dialogue with a certain title. */ - void showDialogue(const std::string &id); + void showDialogue(const std::string &id, bool runScript = true); /** Open the dialogue with a Dialogue structure */ - void showDialogue(const DialogueBin &dialogue); + void showDialogue(const DialogueBin &dialogue, bool runScript = true); + /** Get the current active view. */ + InterfaceView *getCurrentView(); + /** Set this view as the current one and show it. */ + void showInterface(const std::string &title, bool runScript = true); + /** Hide the current view (no current view). */ + void hideInterface(bool runScript = true); + void setNotifyLock(); + bool getNotifyLock(); + /** Get the last pressed key. */ + KeyboardKey getLastKey(); + /** Get a reference to the factory helper. */ + static ElementFactory &getFactory(); + + /** Active a fade transition. */ + void doFadeTransition(); + /** Update transition routine. */ + void updateFade(); + /** Set transition point callback. */ + void setTransitionPointCallback(std::function callback); + /** Update routine. */ void update(); /** Draw routine. */ diff --git a/include/interfaceView.hpp b/include/interfaceView.hpp index ac8c8672..aefefba7 100644 --- a/include/interfaceView.hpp +++ b/include/interfaceView.hpp @@ -3,22 +3,133 @@ #include +#include #include +#include +#include +#include #include -#include "uiElement.hpp" +#include "gamedata.hpp" +#include "lua.hpp" +#include "saveable.hpp" +#include "sol/forward.hpp" +#include "sol/state_view.hpp" +#include "tween.hpp" +#include "tweenContainer.hpp" +#include "ui_elements/uiElement.hpp" -class InterfaceView { +/** An InterfaceView represents a collection of UI elements drawn on the screen to make up a user interface. */ +class InterfaceView : public ISaveable { private: Rectangle rect; - std::vector> elements; + +protected: + /** The structure which was used to construct this InterfaceView. */ + InterfaceViewBin bin; + + /** The title of the currently focused element. */ + std::string focusedElementName = ""; + + /** The source of the Lua script. */ + std::string scriptSource = ""; + /** Whether this view has a script or not. */ + bool scriptFlag = false; + /** A Lua environment for this view. */ + sol::environment env; + + /** The array of UI elements. */ + std::array, MAX_ELEMENTS> elements = {}; + /** The array of the elements' names. */ + std::array elementNames = {}; + + /** Index of the currently focused element. */ + ElementIndex currentElement = MAX_ELEMENTS; + /** Queue of available element indexes. */ + std::queue availableIds = {}; + /** Amount of elements in this View. */ + int size = 0; + + /** List of the tweens currently being ran. */ + std::list tweens = {}; public: + /** Flag whether the script should be ran. */ + bool runScript = true; + + /** Default constructor. */ InterfaceView(); - explicit InterfaceView(Rectangle rect); - void addElement(UIElement *element); - void update() const; - void draw() const; + /** Construct from a UI View file. */ + InterfaceView(const std::string &filePath); + /** Construct from binary data. */ + InterfaceView(InterfaceViewBin &bin); + + /** Dump json data. */ + nlohmann::json dumpJson(); + + /** Get name of an element by index. */ + const std::string &getEntityName(int index); + /** Get the index of an element identified by its name. */ + ElementIndex findByName(const std::string &title); + + /** Whether an element with such a name exists. */ + bool elementExists(const std::string &title); + /** Add an element with a title and a registered type. */ + ElementIndex addElement(const std::string &title, const std::string &type); + /** Remove an element by its title. */ + void removeElement(const std::string &title); + /** Get an element pointer by its title. */ + UIElement *getElement(const std::string &title); + /** Get an element pointer by its index. */ + UIElement *getElement(ElementIndex i); + /** Rename an element. */ + void renameElement(const std::string &title, const std::string &newTitle); + /** Change the focus to an element identified by its index. */ + void changeFocusedElement(const std::string &title); + /** Change the focus to an element identified by an index. */ + void changeFocusedElement(ElementIndex index); + /** Clone an element by giving it a title. It will appear right above the element that was cloned. */ + UIElement *cloneElement(const std::string &title, const std::string &newTitle); + /** Get an array of the elements. */ + const std::array, MAX_ELEMENTS> &getElements(); + /** Swap two elements. */ + void swapElements(ElementIndex a, ElementIndex b); + /** Move an element to another position within the array. */ + void moveToPosition(ElementIndex source, ElementIndex dest); + /** Reset the elements' positions and sizes. */ + void resetElements(); + + /** Get the amount of elements within this View. */ + ElementIndex getSize(); + + /** Notify routine, the View shall react to this event. */ + virtual void onNotify(Event event); + /** Update routine. */ + virtual void update(); + /** Draw routine. Draws all the elements. */ + virtual void draw(); + /** Draw a specific element. */ + virtual void drawEntity(ElementIndex i); + + /** Set the script file for this UI View. */ + void setScriptFile(const std::string &fileName); + /** Get the path to the script file for this UI View. */ + std::string getScriptFile(); + /** Check whether this View has an attached script or not. */ + bool hasScript(); + + /** Get a reference to the Lua environment of this View. */ + sol::environment &getLuaEnvironment(); + + /** Get a reference to the list of running tweens. */ + std::list &getTweens(); + /** Add a tween container to be animated. */ + void addTweenContainer(TweenContainer tweenContainer); + /** Add a singular tween to be animated. */ + void addTween(Tween tween); + + /** Abandon the Lua environment. Should always be done before the end of the program. */ + void abandonLua(); }; #endif diff --git a/include/jsonConversions.hpp b/include/jsonConversions.hpp new file mode 100644 index 00000000..d3e9093a --- /dev/null +++ b/include/jsonConversions.hpp @@ -0,0 +1,38 @@ +#ifndef _RPGPP_JSONCONVERSIONS_H +#define _RPGPP_JSONCONVERSIONS_H + +#include + +#include "gamedata.hpp" +#include "raylib.h" + +class UIElement; + +using json = nlohmann::json; + +// property types +void to_json(json &j, const Rectangle &rect); +void from_json(const json &j, Rectangle &rect); + +void to_json(json &j, const Color &color); +void from_json(const json &j, Color &color); + +void to_json(json &j, const ImageRef &image); +void from_json(const json &j, ImageRef &image); + +void to_json(json &j, const FontRef &font); +void from_json(const json &j, FontRef &font); + +void to_json(json &j, const NPatchInfo &info); +void from_json(const json &j, NPatchInfo &info); + +void to_json(json &j, const CallbacksArray &info); +void from_json(const json &j, CallbacksArray &info); + +void to_json(json &j, const UIElementRef &info); +void from_json(const json &j, UIElementRef &info); + +void to_json(json &j, const InputC &input); +void from_json(const json &j, InputC &input); + +#endif diff --git a/include/lua/apiTypes.hpp b/include/lua/apiTypes.hpp index 9c71e50c..2f938379 100644 --- a/include/lua/apiTypes.hpp +++ b/include/lua/apiTypes.hpp @@ -17,5 +17,6 @@ struct lua_Vector2 { }; void lua_types_set(sol::state_view lua); +void lua_basic_types_set(sol::environment &env); -#endif \ No newline at end of file +#endif diff --git a/include/lua/interfaceApi.hpp b/include/lua/interfaceApi.hpp index 6fe52132..3776f298 100644 --- a/include/lua/interfaceApi.hpp +++ b/include/lua/interfaceApi.hpp @@ -1,9 +1,10 @@ #ifndef _RPGPP_LUA_INTERFACEAPI_H #define _RPGPP_LUA_INTERFACEAPI_H -#include "sol/state_view.hpp" #include +#include "sol/state_view.hpp" + void lua_ui_opendiag(const std::string &id); void lua_ui_set(sol::state_view &lua); diff --git a/include/lua/soundsApi.hpp b/include/lua/soundsApi.hpp index 3127be9f..c2d971a4 100644 --- a/include/lua/soundsApi.hpp +++ b/include/lua/soundsApi.hpp @@ -1,9 +1,10 @@ #ifndef _RPGPP_LUA_SOUNDSAPI_H #define _RPGPP_LUA_SOUNDSAPI_H -#include "sol/state_view.hpp" #include +#include "sol/state_view.hpp" + void lua_sounds_loadMusic(const std::string &id); void lua_sounds_playMusic(); void lua_sounds_playSound(const std::string &id); diff --git a/include/lua/uiTypesApi.hpp b/include/lua/uiTypesApi.hpp new file mode 100644 index 00000000..09d6c001 --- /dev/null +++ b/include/lua/uiTypesApi.hpp @@ -0,0 +1,9 @@ +#ifndef _RPGPP_LUA_UITYPESAPI_H +#define _RPGPP_LUA_UITYPESAPI_H + +#include "sol/forward.hpp" +#include "sol/state_view.hpp" + +void lua_ui_types_set(sol::environment &env); + +#endif diff --git a/include/player.hpp b/include/player.hpp index b4b97d9a..7ad7c68f 100644 --- a/include/player.hpp +++ b/include/player.hpp @@ -61,6 +61,8 @@ class Player { Vector2 getCollisionPos() const; /** Get the center position of the player's collision. */ Vector2 getCollisionCenterPos() const; + /** Set whether the Player should be able to move or not. */ + void setMovementLock(bool value); }; #endif diff --git a/include/resourceService.hpp b/include/resourceService.hpp index 947f3584..11273a40 100644 --- a/include/resourceService.hpp +++ b/include/resourceService.hpp @@ -18,9 +18,11 @@ class ResourceService { void addTextureFromFile(const std::string &filePath); void addTexture(const std::string &id, Texture2D texture); Texture2D getTexture(const std::string &id); + bool textureExists(const std::string &id); void addFont(const std::string &id, Font font); void addFontFromFile(const std::string &filePath, int fontSize); Font getFont(const std::string &id); + bool fontExists(const std::string &id); void unload() const; }; diff --git a/include/scriptService.hpp b/include/scriptService.hpp index 657bacbf..ce9232f6 100644 --- a/include/scriptService.hpp +++ b/include/scriptService.hpp @@ -4,6 +4,7 @@ #include #include +#include "sol/forward.hpp" #include "sol/state.hpp" #include "sol/state_view.hpp" @@ -16,6 +17,7 @@ class ScriptService { sol::state &getState(); void setLua(sol::state_view lua); void addToState(nlohmann::json &j); + sol::environment createEnvironment(); }; #endif \ No newline at end of file diff --git a/include/textArea.hpp b/include/textArea.hpp deleted file mode 100644 index dfce7781..00000000 --- a/include/textArea.hpp +++ /dev/null @@ -1,24 +0,0 @@ -#ifndef _RPGPP_TEXTAREA_H -#define _RPGPP_TEXTAREA_H - -#include - -#include - -#include "uiElement.hpp" - -class TextArea : public UIElement { -private: - Rectangle rect; - std::string content; - void putChar(int i, Vector2 *charPos, Vector2 *charMeasure) const; - -public: - TextArea(); - TextArea(Rectangle rect); - void setText(const std::string &text); - void update(); - void draw(); -}; - -#endif diff --git a/include/tween.hpp b/include/tween.hpp new file mode 100644 index 00000000..59dffb67 --- /dev/null +++ b/include/tween.hpp @@ -0,0 +1,119 @@ +#ifndef _RPGPP_TWEEN_H +#define _RPGPP_TWEEN_H + +#include +#include +#include + +#include "gamedata.hpp" +#include "sol/forward.hpp" +#include "sol/sol.hpp" + +enum class TweenType { + LINEAR, + INSINE, + OUTSINE, + INOUTSINE, + INQUAD, + OUTQUAD, + INOUTQUAD, + INCUBIC, + OUTCUBIC, + INOUTCUBIC, + INQUART, + OUTQUART, + INOUTQUART, + INQUINT, + OUTQUINT, + INOUTQUINT, + INEXPO, + OUTEXPO, + INOUTEXPO, + INCIRC, + OUTCIRC, + INOUTCIRC, + INBACK, + OUTBACK, + INOUTBACK, + INELASTIC, + OUTELASTIC, + INOUTELASTIC, + INBOUNCE, + OUTBOUNCE, + INOUTBOUNCE +}; + +#define TWEEN_TYPE_MAX (31) + +struct Tween { + float a; + float b; + float *ptr = nullptr; + float duration; + TweenType type = TweenType::LINEAR; + float left; +}; + +struct TweenLua { + float a; + float b; + sol::userdata source; + sol::userdata dest; + std::string key; + float duration; + TweenType type = TweenType::LINEAR; + float left; + bool empty = true; +}; + +struct TweenProvider { + static std::array, TWEEN_TYPE_MAX> arr; + static float tweenFunc(TweenType type, float t); + static void setupTweenFuncs(); + static std::list initPropTween(ElementProperty *dest, ElementProperty source, float duration, + TweenType type); +}; + +float linear(float t); + +float inSine(float t); +float outSine(float t); +float inOutSine(float t); + +float inQuad(float t); +float outQuad(float t); +float inOutQuad(float t); + +float inCubic(float t); +float outCubic(float t); +float inOutCubic(float t); + +float inQuart(float t); +float outQuart(float t); +float inOutQuart(float t); + +float inQuint(float t); +float outQuint(float t); +float inOutQuint(float t); + +float inExpo(float t); +float outExpo(float t); +float inOutExpo(float t); + +float inCirc(float t); +float outCirc(float t); +float inOutCirc(float t); + +float inBack(float t); +float outBack(float t); +float inOutBack(float t); + +float inElastic(float t); +float outElastic(float t); +float inOutElastic(float t); + +float inBounce(float t); +float outBounce(float t); +float inOutBounce(float t); + +#endif diff --git a/include/tweenContainer.hpp b/include/tweenContainer.hpp new file mode 100644 index 00000000..32dd42e5 --- /dev/null +++ b/include/tweenContainer.hpp @@ -0,0 +1,25 @@ +#ifndef _RPGPP_TWEENCONTAINER_H +#define _RPGPP_TWEENCONTAINER_H + +#include + +#include "tween.hpp" + +#define MAX_TWEENS (5) + +class TweenContainer { +private: + std::array tweens; + int size = 0; + int sizeLua = 0; + +public: + TweenContainer(); + void addTween(Tween tween); + void removeTween(int index); + + void update(); + int getSize(); +}; + +#endif diff --git a/include/uiElement.hpp b/include/uiElement.hpp deleted file mode 100644 index 4467ce56..00000000 --- a/include/uiElement.hpp +++ /dev/null @@ -1,13 +0,0 @@ -#ifndef _RPGPP_UIELEMENT_H -#define _RPGPP_UIELEMENT_H - -class UIElement { -public: - virtual ~UIElement() = default; - - UIElement(); - virtual void update(); - virtual void draw(); -}; - -#endif diff --git a/include/ui_elements/button.hpp b/include/ui_elements/button.hpp new file mode 100644 index 00000000..d45f8fc1 --- /dev/null +++ b/include/ui_elements/button.hpp @@ -0,0 +1,18 @@ +#ifndef _RPGPP_UI_ELEMENTS_BUTTON_H +#define _RPGPP_UI_ELEMENTS_BUTTON_H + +#include "ui_elements/uiElement.hpp" + +struct Button : public UIElement { + Button(); + void init(); + void update(); + void draw(Rectangle rect); + + Color shownTextColor = BLACK; + + void config(); + void loadFont(const std::string &path); +}; + +#endif diff --git a/include/ui_elements/colorRect.hpp b/include/ui_elements/colorRect.hpp new file mode 100644 index 00000000..768db281 --- /dev/null +++ b/include/ui_elements/colorRect.hpp @@ -0,0 +1,13 @@ +#ifndef _RPGPP_UI_ELEMENTS_COLORRECT_H +#define _RPGPP_UI_ELEMENTS_COLORRECT_H + +#include "ui_elements/uiElement.hpp" + +struct ColorRect : public UIElement { + ColorRect(); + void init(); + void update(); + void draw(Rectangle rect); +}; + +#endif diff --git a/include/ui_elements/comboBox.hpp b/include/ui_elements/comboBox.hpp new file mode 100644 index 00000000..f9101ade --- /dev/null +++ b/include/ui_elements/comboBox.hpp @@ -0,0 +1,19 @@ +#ifndef _RPGPP_UI_ELEMENTS_COMBOBOX_H +#define _RPGPP_UI_ELEMENTS_COMBOBOX_H + +#include "uiElement.hpp" + +struct ComboBox : public UIElement { + ComboBox(); + void init(); + void update(); + void draw(Rectangle rect); + void onNotify(Event event); + void config(); + + void loadFont(const std::string &path); + + Color shownTextColor = RAYWHITE; +}; + +#endif diff --git a/include/ui_elements/dialogueArea.hpp b/include/ui_elements/dialogueArea.hpp new file mode 100644 index 00000000..732fe362 --- /dev/null +++ b/include/ui_elements/dialogueArea.hpp @@ -0,0 +1,43 @@ +#ifndef _RPGPP_UI_ELEMENTS_DIALOGUEAREA_H +#define _RPGPP_UI_ELEMENTS_DIALOGUEAREA_H + +#include "ui_elements/uiElement.hpp" + +struct DialogueArea : public UIElement { + DialogueArea(); + void init(); + void update(); + void draw(Rectangle rect); + // + std::string text = ""; + + DialogueBin dialogue; + DialogueLine *line = nullptr; + DialogueTextSection *section = nullptr; + + int frameCounter = 0; + + Vector2 textPos; + int charIndex = 0; + int lineIndex = 0; + int sectionIndex = 0; + + bool appliedTag = false; + bool finishedTyping = false; + bool firstCharTyped = false; + float maxLineHeight = 0.0f; + bool delay = false; + float delayDuration = 0.0f; + float padding = 0.0f; + + FontRef font; + + bool dialogueFinished = false; + + void setDialogue(const DialogueBin &dialogue); + void putChar(Vector2 charMeasure, const char *c, Rectangle rect); + void chooseSection(int i, Rectangle rect); + void advanceToNextLine(); +}; + +#endif diff --git a/include/ui_elements/elementFactory.hpp b/include/ui_elements/elementFactory.hpp new file mode 100644 index 00000000..317ed54f --- /dev/null +++ b/include/ui_elements/elementFactory.hpp @@ -0,0 +1,17 @@ +#ifndef _RPGPP_UI_ELEMENTS_ELEMENTFACTORY_H +#define _RPGPP_UI_ELEMENTS_ELEMENTFACTORY_H + +#include +#include + +#include "ui_elements/uiElement.hpp" + +struct ElementFactory { + std::unordered_map()>> map = {}; + std::list elementNames = {}; + std::unique_ptr constructElement(const std::string &title); + + ElementFactory(); +}; + +#endif diff --git a/include/ui_elements/imageRect.hpp b/include/ui_elements/imageRect.hpp new file mode 100644 index 00000000..775d7530 --- /dev/null +++ b/include/ui_elements/imageRect.hpp @@ -0,0 +1,17 @@ +#ifndef _RPGPP_UI_ELEMENTS_IMAGERECT_H +#define _RPGPP_UI_ELEMENTS_IMAGERECT_H + +#include "ui_elements/uiElement.hpp" + +struct ImageRect : public UIElement { + ImageRect(); + void init(); + void update(); + void draw(Rectangle rect); + + void config(); + void scaleImage(int scale); + void loadImage(const std::string &path); +}; + +#endif diff --git a/include/ui_elements/label.hpp b/include/ui_elements/label.hpp new file mode 100644 index 00000000..a74d7724 --- /dev/null +++ b/include/ui_elements/label.hpp @@ -0,0 +1,16 @@ +#ifndef _RPGPP_UI_ELEMENTS_LABEL_H +#define _RPGPP_UI_ELEMENTS_LABEL_H + +#include "ui_elements/uiElement.hpp" + +struct Label : public UIElement { + Label(); + void init(); + void update(); + void draw(Rectangle rect); + + void config(); + void loadFont(const std::string &path); +}; + +#endif diff --git a/include/ui_elements/ninePatchImageRect.hpp b/include/ui_elements/ninePatchImageRect.hpp new file mode 100644 index 00000000..1e6e89b2 --- /dev/null +++ b/include/ui_elements/ninePatchImageRect.hpp @@ -0,0 +1,17 @@ +#ifndef _RPGPP_UI_ELEMENTS_NINEPATCHIMAGERECT_H +#define _RPGPP_UI_ELEMENTS_NINEPATCHIMAGERECT_H + +#include "ui_elements/uiElement.hpp" + +struct NinePatchImageRect : public UIElement { + NinePatchImageRect(); + void init(); + void update(); + void draw(Rectangle rect); + + void config(); + void scaleImage(int scale); + void loadImage(const std::string &path); +}; + +#endif diff --git a/include/ui_elements/textBox.hpp b/include/ui_elements/textBox.hpp new file mode 100644 index 00000000..b5d33909 --- /dev/null +++ b/include/ui_elements/textBox.hpp @@ -0,0 +1,22 @@ +#ifndef _RPGPP_UI_ELEMENTS_TEXTBOX_H +#define _RPGPP_UI_ELEMENTS_TEXTBOX_H + +#include "uiElement.hpp" + +struct TextBox : public UIElement { + TextBox(); + void init(); + void update(); + void draw(Rectangle rect); + void onNotify(Event event); + void config(); + + void loadFont(const std::string &path); + + Color shownTextColor = RAYWHITE; + int cursorPosition = 0; + + int debounce = 0; +}; + +#endif diff --git a/include/ui_elements/uiElement.hpp b/include/ui_elements/uiElement.hpp new file mode 100644 index 00000000..507ab388 --- /dev/null +++ b/include/ui_elements/uiElement.hpp @@ -0,0 +1,50 @@ +#ifndef _RPGPP_UI_ELEMENTS_H +#define _RPGPP_UI_ELEMENTS_H + +#include + +#include "gamedata.hpp" + +/** The maximum number of UI elements allowed in an InterfaceView. */ +#define MAX_ELEMENTS (255) + +/** A struct, representing an UI element in a View. */ +struct UIElement { + /** A map of the properties of this element. */ + std::unordered_map props = {}; + + /** A map of the callbacks that this element has. */ + std::unordered_map> callbacks = {}; + + /** Name of the type of this UI element. */ + std::string typeName = ""; + + /** Empty constructor. */ + UIElement(); + + /** Constructor with a name for the element type. Shall be used by derived structs. */ + UIElement(const std::string &typeName); + + /** Virtual destructor. */ + virtual ~UIElement() {}; + + /** Initialize the properties and callbacks. */ + virtual void init(); + + /** Routine to update the element after a property has been changed. */ + virtual void config(); + + /** Update routine. */ + virtual void update() = 0; + + /** Draw routine using a rect. */ + virtual void draw(Rectangle rect) = 0; + + /** Notify routine, element responds to an event. */ + virtual void onNotify(Event event); +}; + +/** 8-bit number representing a number identifier for an UIElement within an InterfaceView. */ +typedef uint8_t ElementIndex; + +#endif diff --git a/include/ui_elements/valueSlider.hpp b/include/ui_elements/valueSlider.hpp new file mode 100644 index 00000000..d28c5ae4 --- /dev/null +++ b/include/ui_elements/valueSlider.hpp @@ -0,0 +1,17 @@ +#ifndef _RPGPP_UI_ELEMENTS_VALUESLIDER_H +#define _RPGPP_UI_ELEMENTS_VALUESLIDER_H + +#include "uiElement.hpp" + +struct ValueSlider : public UIElement { + ValueSlider(); + void init(); + void update(); + void draw(Rectangle rect); + void onNotify(Event event); + void config(); + + Color currentColor = RAYWHITE; +}; + +#endif diff --git a/include/worldService.hpp b/include/worldService.hpp index 4fa9c9b3..793e7efa 100644 --- a/include/worldService.hpp +++ b/include/worldService.hpp @@ -17,17 +17,14 @@ class WorldService { bool lock; /** Id for the next room. */ std::string deferredRoomId; + /** Whether there will be a deferred change of Room event. */ bool deferRoomChange; - /** Frame counter for transition tween */ - int frameCounter; - bool transitionActive; - Color transitionColor; - float alpha; - bool transitionSecondStage; public: /** Empty constructor. */ WorldService(); + /** Check if the room exists. */ + bool getIfRoomExist(); /** Get a reference to the current room. */ Room &getRoom() const; /** Set the current room using path to a .rmap file. */ diff --git a/libs/noop/main.cpp b/libs/noop/main.cpp index 33c14ce1..76e81970 100644 --- a/libs/noop/main.cpp +++ b/libs/noop/main.cpp @@ -1,3 +1 @@ -int main() { - return 0; -} +int main() { return 0; } diff --git a/luasrc/game.lua b/luasrc/game.lua new file mode 100644 index 00000000..deb33103 --- /dev/null +++ b/luasrc/game.lua @@ -0,0 +1,9 @@ +--- The Game namespace is responsible for maanging the state of the program itself +--- +--- @class Game +local Game = {} + +--- Closes the game. +function Game.Close() end + +return Game diff --git a/luasrc/interfaceService.lua b/luasrc/interfaceService.lua index a5119a4f..6248540a 100644 --- a/luasrc/interfaceService.lua +++ b/luasrc/interfaceService.lua @@ -3,8 +3,16 @@ --- @class Interface local Interface = {} +--- Open the UI View identified by this title. +--- @param title string +function Interface.OpenView(title) end + --- Open a dialogue with a certain title. --- @param dialogue string function Interface.OpenDialogue(dialogue) end -return Interface \ No newline at end of file +--- Get a reference to the current UI View. +--- @param title string +function Interface.GetCurrentView() end + +return Interface diff --git a/luasrc/types.lua b/luasrc/types.lua index 08ea95f5..d1672f27 100644 --- a/luasrc/types.lua +++ b/luasrc/types.lua @@ -106,7 +106,7 @@ function Interactable:SetProp(key, value) end --- @return boolean function Interactable:IsOnTouch() end ---- Set whether this interactable will be invoked when player touches it. +--- Set whether this interactable will be invoked when player touches it. --- @param value boolean function Interactable:SetOnTouch(value) end @@ -244,3 +244,62 @@ function Room:GetProps() end --- @return ActorContainer function Room:GetActors() end +--- @enum TweenType +local TweenType = { + Linear = 0, + InSine = 1, + OutSine = 2, + InOutSine = 3, + InQuad = 4, + OutQuad = 5, + InOutQuad = 6, + InCubic = 7, + OutCubic = 8, + InOutCubic = 9, + InQuart = 10, + OutQuart = 11, + InOutQuart = 12, + InQuint = 13. + OutQuint = 14, + InOutQuint = 15, + InExpo = 16, + OutExpo = 17, + InOutExpo = 18, + InCirc = 19, + OutCirc = 20, + InOutCirc = 21, + InBack = 22, + OutBack = 23, + InOutBack = 24, + InElastic = 25, + OutElastic = 26, + InOutElastic = 27, + InBounce = 28, + OutBounce = 29, + InOutBounce = 30 +} + +--- @class InterfaceView +local InterfaceView = {} + +--- Get an element from the UI View. +--- @param name string +--- @return UIElement +function InterfaceView:GetEntity(name) end + +--- Change focus to another UI element. +--- @param name string +function InterfaceView:ChangeFocus(name) end + +--- Reset the elements to their original positions and sizes. +function InterfaceView:Reset() end + +--- @class UIElement +local UIElement = {} + +--- Tween this element. +--- @param property string +--- @param value any +--- @param duration number +--- @param tweenType TweenType +function UIElement:Tween(property, value, duration, tweenType) end diff --git a/luasrc/worldService.lua b/luasrc/worldService.lua index af2ee6a2..3f2f6be5 100644 --- a/luasrc/worldService.lua +++ b/luasrc/worldService.lua @@ -1,18 +1,18 @@ --- The WorldService is responsible for containing and drawing the Room. --- ---- @class WorldService -local WorldService = {} +--- @class World +local World = {} --- Get the Player. --- @return Player -function WorldService.GetPlayer() end +function World.GetPlayer() end --- Set the current room using a room title in the game. --- @param room string -function WorldService.SetRoom(room) end +function World.SetRoom(room) end --- Get the current Room --- @return Room -function WorldService.GetRoom() end +function World.GetRoom() end -return WorldService +return World diff --git a/resources/defaults/dialogues/welcome.rdiag b/resources/defaults/dialogues/welcome.rdiag index 3ccb9beb..072632f1 100644 --- a/resources/defaults/dialogues/welcome.rdiag +++ b/resources/defaults/dialogues/welcome.rdiag @@ -1 +1,11 @@ -{"diag":[["Introductor","Welcome to RPG++!","0",""]]} \ No newline at end of file +{ + "diag": [ + { + "characterName": "Introductor", + "text": "Welcome to RPG++!", + "hasPortrait": false, + "imageId": "", + "options": [] + } + ] +} diff --git a/resources/defaults/images/logo-sq.png b/resources/defaults/images/logo-sq.png new file mode 100644 index 00000000..0aceb15a Binary files /dev/null and b/resources/defaults/images/logo-sq.png differ diff --git a/resources/defaults/maps/map.rmap b/resources/defaults/maps/map.rmap index c2674f64..39020093 100644 --- a/resources/defaults/maps/map.rmap +++ b/resources/defaults/maps/map.rmap @@ -1 +1 @@ -{"actors":{},"collision":[],"height":20,"interactables":{},"map":[[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[0,0],[1,0],[1,0],[1,0],[1,0],[1,0],[1,0],[2,0],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[0,1],[1,1],[1,1],[1,1],[1,1],[1,1],[1,1],[2,1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[0,1],[1,1],[1,1],[1,1],[1,1],[1,1],[1,1],[2,1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[0,2],[1,2],[1,2],[1,2],[1,2],[1,2],[1,2],[2,2],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]]],"music_source":"","props":{"9;0":{"props":{"dialogue":{"propType":"dialogue","value":"welcome"}},"src":"props/prop.rprop"}},"start_pos":[9,2],"tileSize":48,"tileset":"tilesets/tiles.rtiles","width":20} \ No newline at end of file +{"actors":{},"collision":[],"height":20,"interactables":{},"map":[[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[0,0],[1,0],[1,0],[1,0],[1,0],[1,0],[1,0],[2,0],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[0,1],[1,1],[1,1],[1,1],[1,1],[1,1],[1,1],[2,1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[0,1],[1,1],[1,1],[1,1],[1,1],[1,1],[1,1],[2,1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[0,2],[1,2],[1,2],[1,2],[1,2],[1,2],[1,2],[2,2],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]],[[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1],[-1,-1]]],"music_source":"","props":{"9;7":{"props":{"dialogue":{"propType":"dialogue","value":"welcome"}},"src":"props/prop.rprop"}},"start_pos":[9,8],"tileSize":48,"tileset":"tilesets/tiles.rtiles","width":20} \ No newline at end of file diff --git a/resources/defaults/scripts/mainmenu.lua b/resources/defaults/scripts/mainmenu.lua new file mode 100644 index 00000000..41883db6 --- /dev/null +++ b/resources/defaults/scripts/mainmenu.lua @@ -0,0 +1,12 @@ +function open() + view:ChangeFocus("play") +end + +function play() + print("pressed play") + World.SetRoom("map") +end + +function quit() + Game.Close() +end diff --git a/resources/defaults/views/dialogue.rui b/resources/defaults/views/dialogue.rui new file mode 100644 index 00000000..8bdc45fb --- /dev/null +++ b/resources/defaults/views/dialogue.rui @@ -0,0 +1 @@ +{"bin":{"value0":"scr.lua","value1":[],"value2":[{"key":"optionsImage","value":{"value0":"NinePatchImageRect","value1":[{"key":"npatchInfo","value":{"data":{"value0":3,"value1":3,"value2":3,"value3":3,"value4":0},"index":10}},{"key":"image","value":{"data":{"value0":"ui-npatch.png","value1":3},"index":6}},{"key":"visible","value":{"data":false,"index":1}},{"key":"rect","value":{"data":{"value0":239.0,"value1":132.0,"value2":180.0,"value3":180.0},"index":3}}]}},{"key":"optionButton","value":{"value0":"Button","value1":[{"key":"rect","value":{"data":{"value0":247.0,"value1":141.0,"value2":162.0,"value3":51.0},"index":3}},{"key":"visible","value":{"data":false,"index":1}},{"key":"normalTextColor","value":{"data":{"value0":255,"value1":0,"value2":0,"value3":0},"index":4}},{"key":"text","value":{"data":"Option","index":2}},{"key":"focusedTextColor","value":{"data":{"value0":255,"value1":130,"value2":130,"value3":130},"index":4}},{"key":"bgColor","value":{"data":{"value0":0,"value1":245,"value2":245,"value3":245},"index":4}},{"key":"input","value":{"data":{"value0":{"value0":""},"value1":{"value0":""},"value2":{"value0":""},"value3":{"value0":""},"value4":{"value0":[{"key":"callback_trigger","value":""},{"key":"callback_unfocused","value":""},{"key":"callback_focused","value":""}]}},"index":11}},{"key":"horizontalAlignment","value":{"data":{"value0":1},"index":8}},{"key":"verticalAlignment","value":{"data":{"value0":1},"index":7}},{"key":"font","value":{"data":{"value0":"","value1":39},"index":5}}]}},{"key":"diagImage","value":{"value0":"NinePatchImageRect","value1":[{"key":"npatchInfo","value":{"data":{"value0":3,"value1":3,"value2":3,"value3":3,"value4":0},"index":10}},{"key":"image","value":{"data":{"value0":"ui-npatch.png","value1":3},"index":6}},{"key":"visible","value":{"data":true,"index":1}},{"key":"rect","value":{"data":{"value0":10.0,"value1":320.0,"value2":620.0,"value3":140.0},"index":3}}]}},{"key":"dialogueArea","value":{"value0":"DialogueArea","value1":[{"key":"text","value":{"data":"","index":2}},{"key":"visible","value":{"data":true,"index":1}},{"key":"rect","value":{"data":{"value0":19.0,"value1":329.0,"value2":611.0,"value3":131.0},"index":3}}]}},{"key":"portrait","value":{"value0":"ImageRect","value1":[{"key":"image","value":{"data":{"value0":"","value1":1},"index":6}},{"key":"visible","value":{"data":true,"index":1}},{"key":"rect","value":{"data":{"value0":19.0,"value1":329.0,"value2":122.0,"value3":122.0},"index":3}}]}}]}} \ No newline at end of file diff --git a/resources/defaults/views/mainmenu.rui b/resources/defaults/views/mainmenu.rui new file mode 100644 index 00000000..96b91c40 --- /dev/null +++ b/resources/defaults/views/mainmenu.rui @@ -0,0 +1 @@ +{"bin":{"value0":"mainmenu.lua","value1":[],"value2":[{"key":"quit","value":{"value0":"Button","value1":[{"key":"rect","value":{"data":{"value0":8.0,"value1":272.0,"value2":113.0,"value3":52.0},"index":3}},{"key":"visible","value":{"data":true,"index":1}},{"key":"normalTextColor","value":{"data":{"value0":255,"value1":0,"value2":0,"value3":0},"index":4}},{"key":"text","value":{"data":"Quit","index":2}},{"key":"focusedTextColor","value":{"data":{"value0":255,"value1":130,"value2":130,"value3":130},"index":4}},{"key":"bgColor","value":{"data":{"value0":255,"value1":245,"value2":245,"value3":245},"index":4}},{"key":"input","value":{"data":{"value0":{"value0":"play"},"value1":{"value0":""},"value2":{"value0":""},"value3":{"value0":""},"value4":{"value0":[{"key":"callback_trigger","value":"quit"},{"key":"callback_unfocused","value":""},{"key":"callback_focused","value":""}]}},"index":11}},{"key":"horizontalAlignment","value":{"data":{"value0":1},"index":8}},{"key":"verticalAlignment","value":{"data":{"value0":1},"index":7}},{"key":"font","value":{"data":{"value0":"","value1":39},"index":5}}]}},{"key":"title","value":{"value0":"Label","value1":[{"key":"rect","value":{"data":{"value0":8.0,"value1":148.0,"value2":260.0,"value3":60.0},"index":3}},{"key":"visible","value":{"data":true,"index":1}},{"key":"text","value":{"data":"Title","index":2}},{"key":"textColor","value":{"data":{"value0":255,"value1":0,"value2":0,"value3":0},"index":4}},{"key":"horizontalAlignment","value":{"data":{"value0":0},"index":8}},{"key":"verticalAlignment","value":{"data":{"value0":0},"index":7}},{"key":"font","value":{"data":{"value0":"","value1":52},"index":5}}]}},{"key":"play","value":{"value0":"Button","value1":[{"key":"font","value":{"data":{"value0":"","value1":39},"index":5}},{"key":"verticalAlignment","value":{"data":{"value0":1},"index":7}},{"key":"horizontalAlignment","value":{"data":{"value0":1},"index":8}},{"key":"input","value":{"data":{"value0":{"value0":""},"value1":{"value0":"quit"},"value2":{"value0":""},"value3":{"value0":""},"value4":{"value0":[{"key":"callback_focused","value":""},{"key":"callback_unfocused","value":""},{"key":"callback_trigger","value":"play"}]}},"index":11}},{"key":"bgColor","value":{"data":{"value0":255,"value1":245,"value2":245,"value3":245},"index":4}},{"key":"focusedTextColor","value":{"data":{"value0":255,"value1":130,"value2":130,"value3":130},"index":4}},{"key":"text","value":{"data":"Play","index":2}},{"key":"normalTextColor","value":{"data":{"value0":255,"value1":0,"value2":0,"value3":0},"index":4}},{"key":"visible","value":{"data":true,"index":1}},{"key":"rect","value":{"data":{"value0":8.0,"value1":220.0,"value2":113.0,"value3":51.0},"index":3}}]}}]}} \ No newline at end of file diff --git a/resources/translations/bg.json b/resources/translations/bg.json index 4e0eed38..e924a810 100644 --- a/resources/translations/bg.json +++ b/resources/translations/bg.json @@ -55,6 +55,9 @@ }, "project": { "create_new_resource": "Нов ресурс", + "filenotexist": { + "notice": "Този файл вече не съществува!" + }, "emptyview": { "notice": "Няма отворен файл" }, @@ -132,6 +135,9 @@ "script": "Скрипт", "on_touch": "Извикай при допир?" }, + "viewsview": { + "create": "Създай" + }, "toolbar": { "play": "Пусни игра", "build": "Компилирай игра" @@ -170,7 +176,7 @@ }, "game": { "_label": "Игра", - "default_room": "Първоначална стая", + "default_load": "Първоначална стая", "player_actor": "Актьор на играча", "tile_size": "Размер на плочка", "debug_draw": "Дебъгерно рисуване", @@ -222,6 +228,14 @@ "title": "Редактиране на списък..", "add": "Добави..", "close": "Затвори" + }, + "init_element": { + "title": "Създай елемент", + "elm_name": "Име" + }, + "rename_element": { + "title": "Преименувай елемент", + "rename": "Преименувай" } }, "widget": { @@ -240,10 +254,11 @@ "button": { "go_back": "Върни се", "restart": "Рестартирай", - "restart_later": "Рестартирай по-късно" + "restart_later": "Рестартирай по-късно", + "okay": "Ок" }, "context_menu": { "copy_full_path": "Копирай пълен път", "delete": "Изтрий" } -} \ No newline at end of file +} diff --git a/resources/translations/en_us.json b/resources/translations/en_us.json index 0349d00e..2e6dea09 100644 --- a/resources/translations/en_us.json +++ b/resources/translations/en_us.json @@ -55,6 +55,9 @@ }, "project": { "create_new_resource": "New Resource", + "filenotexist": { + "notice": "This file doesn't exist anymore!" + }, "emptyview": { "notice": "No file opened or view not defined yet!" }, @@ -132,6 +135,9 @@ "script": "Script", "on_touch": "On Touch?" }, + "viewsview": { + "create": "Create" + }, "toolbar": { "play": "Play", "build": "Build" @@ -170,7 +176,7 @@ }, "game": { "_label": "Game", - "default_room": "Default Room", + "default_load": "Default Room/UI View", "player_actor": "Player Actor", "tile_size": "Tile Size", "debug_draw": "Debug Draw", @@ -222,6 +228,14 @@ "title": "Edit List..", "add": "Add..", "close": "Close" + }, + "init_element": { + "title": "Create Element", + "elm_name": "Element Name" + }, + "rename_element": { + "title": "Rename Element", + "rename": "Rename" } }, "widget": { @@ -240,10 +254,11 @@ "button": { "go_back": "Go Back", "restart": "Restart", - "restart_later": "Restart Later" + "restart_later": "Restart Later", + "okay": "Okay" }, "context_menu": { "copy_full_path": "Copy full path", "delete": "Delete" } -} \ No newline at end of file +} diff --git a/resources/translations/tr.json b/resources/translations/tr.json index f3982c2b..8e0286ac 100644 --- a/resources/translations/tr.json +++ b/resources/translations/tr.json @@ -55,6 +55,9 @@ }, "project": { "create_new_resource": "Yeni Kaynak", + "filenotexist": { + "notice": "Bu dosya artık yoktur!" + }, "emptyview": { "notice": "Hiç bir dosya ya da görünüş tanımlanmamıştır!" }, @@ -98,6 +101,9 @@ "tile_height": "Kare Yüksekliği", "texture": "Doku" }, + "viewsview": { + "create": "Oluştur" + }, "roomview": { "mapwidth": "Harita Genişliği", "mapheight": "Harita Yüksekliği", @@ -170,7 +176,7 @@ }, "game": { "_label": "Oyun", - "default_room": "Öntanımlı Oda", + "default_load": "Öntanımlı Oda/Ekran", "player_actor": "Oyuncunun Aktörü", "tile_size": "Kare Boyutu", "debug_draw": "Hata Ayıklamayı Çiz", @@ -222,7 +228,16 @@ "title": "Listeyi Düzenleyin...", "add": "Ekle..", "close": "Kapat" + }, + "init_element": { + "title": "Öğe Oluştur", + "elm_name": "Öğe Adı" + }, + "rename_element": { + "title": "Öğeyi Yeniden Adlandır...", + "rename": "Yeniden Adlandır" } + }, "widget": { "filechooser": { @@ -240,10 +255,11 @@ "button": { "go_back": "Geri Git", "restart": "Yeniden Başlat", - "restart_later": "Sonra Yeniden Başlat" + "restart_later": "Sonra Yeniden Başlat", + "okay": "Tamam" }, "context_menu": { "copy_full_path": "Full yolunu kopyala", "delete": "Sil" } -} \ No newline at end of file +} diff --git a/resources/translations/vn.json b/resources/translations/vn.json index 39b5c1bd..fa38f0e9 100644 --- a/resources/translations/vn.json +++ b/resources/translations/vn.json @@ -58,6 +58,9 @@ }, "project": { "create_new_resource": "Tạo tài nguyên", + "filenotexist": { + "notice": "Tệp tin không tồn tại!" + }, "emptyview": { "notice": "Chưa mở tệp tin nào, hoặc tệp tin chưa được hỗ trợ để mở!" }, @@ -138,6 +141,9 @@ "script": "Tệp Script", "on_touch": "Kích hoạt khi chạm?" }, + "viewsview": { + "create": "Tạo" + }, "toolbar": { "play": "Chạy chương trình", "build": "Dịch và tạo chương trình" @@ -178,7 +184,7 @@ }, "game": { "_label": "Trò chơi", - "default_room": "Room mặc định", + "default_load": "Room/UI mặc định", "player_actor": "Actor người chơi", "tile_size": "Kích cỡ Tile", "debug_draw": "Vẽ gỡ lỗi", @@ -230,6 +236,14 @@ "title": "Sửa danh sách", "add": "Thêm", "close": "Thoát" + }, + "init_element": { + "title": "Tạo phần tử UI", + "elm_name": "Tên phân tử" + }, + "rename_element": { + "title": "Đổi tên phần tử UI", + "rename": "Đổi tên" } }, @@ -250,7 +264,8 @@ "button": { "go_back": "Quay lại", "restart": "Khởi động lại", - "restart_later": "Khởi động lại sau" + "restart_later": "Khởi động lại sau", + "okay": "Ok" }, "context_menu": { "copy_full_path": "Sao chép đường dẫn", diff --git a/src/colorRect.cpp b/src/colorRect.cpp deleted file mode 100644 index b6c4c505..00000000 --- a/src/colorRect.cpp +++ /dev/null @@ -1,18 +0,0 @@ -#include "colorRect.hpp" - -#include - -ColorRect::ColorRect() : rect(Rectangle{1, 1, 1, 1}), color() {} - -ColorRect::ColorRect(const Rectangle rect) { - this->rect = rect; - this->color = RAYWHITE; -} - -void ColorRect::setColor(const Color newColor) { this->color = newColor; } - -void ColorRect::update() { - // TODO -} - -void ColorRect::draw() { DrawRectangleRec(rect, color); } diff --git a/src/dialogueBalloon.cpp b/src/dialogueBalloon.cpp deleted file mode 100644 index 34687902..00000000 --- a/src/dialogueBalloon.cpp +++ /dev/null @@ -1,287 +0,0 @@ -#include "dialogueBalloon.hpp" - -#include -#include - -#include - -#include "game.hpp" -#include "interfaceService.hpp" - -DialogueBalloon::DialogueBalloon() = default; - -DialogueBalloon::DialogueBalloon(Rectangle rect) { - this->font = Game::getResources().getFont("LanaPixel"); - this->rect = rect; - this->textRect = Rectangle{rect.x + 9, rect.y + 9, rect.width - (9 * 2), rect.height - (9 * 2)}; - this->textPortraitRect = this->textRect; - this->textPortraitRect.width -= this->textRect.height; - this->textPortraitRect.x += this->textRect.height; - this->optionsRect = {rect.x + (rect.width - 180), rect.y - 8 - 180, 180, 180}; - - this->lineIndex = 0; - this->sectionIndex = 0; - - this->firstCharTyped = false; - this->active = false; - this->frameCounter = 0; - this->charIndex = 0; - - this->textColor = WHITE; - this->text = - "Lorem ipsum dolor sit amet, consectetur adipiscing elit. Donec " - "placerat vel nulla eget ullamcorper. Proin varius erat in " - "tristique dignissim. Aliquam erat volutpat."; - this->sectionText = {"", text}; - this->lastSectionLen = 0; - - this->textPos = Vector2{0, 0}; -} - -void DialogueBalloon::update() { - if (active) { - if (firstCharTyped == false) { - firstCharTyped = true; - auto &soundId = dialogue.lines.at(lineIndex).sections.at(sectionIndex).sound; - Game::getSounds().playSound(soundId); - return; - } - - bool finished = false; - if (charIndex == (text.size() - 1) || charIndex == text.size()) { - finished = true; - } - - this->finishedTyping = finished; - - if (IsKeyPressed(KEY_Z)) { - if (finished) { - if (dialogue.lines.at(lineIndex).hasOptions) { - std::string newDialogue = dialogue.lines.at(lineIndex).options.at(hoveredOption).nextDialogue; - hideDialogue(); - showDialogue(Game::getBin().dialogues[newDialogue]); - return; - } - - if (lineIndex == (dialogue.lines.size() - 1)) { - hideDialogue(); - } else { - lineIndex++; - text = ""; - for (auto k : dialogue.lines.at(lineIndex).sections) { - text = text.append(k.text); - } - - charIndex = 0; - firstCharTyped = false; - sectionIndex = 0; - lastSectionLen = 0; - - textPos = Vector2{0, 0}; - - appliedTag = false; - padding = 0.0f; - maxLineHeight = 0.0f; - } - } else { - charIndex = (text.size() - 1); - } - } - - if (dialogue.lines.at(lineIndex).hasOptions) { - if (IsKeyPressed(KEY_UP) && hoveredOption != 0) { - hoveredOption--; - } - if (IsKeyPressed(KEY_DOWN) && hoveredOption < (dialogue.lines.at(lineIndex).options.size() - 1)) { - hoveredOption++; - } - } - - if (delay) { - delayDuration -= (GetFrameTime() * static_cast(60.0f / 20.0f)); - if (delayDuration <= 0.0f) { - delay = false; - } - } - - frameCounter++; - if (frameCounter > (60 / 20) && !delay) { - frameCounter = 0; - if (charIndex < text.size()) { - charIndex++; - - // play sound - if (charIndex < text.size()) { - if (text.at(charIndex) != ' ') { - auto &soundId = dialogue.lines.at(lineIndex).sections.at(sectionIndex).sound; - Game::getSounds().playSound(soundId); - } - } - } - } - } -} - -void DialogueBalloon::drawPortrait() const { - Texture2D texture = Game::getResources().getTexture(dialogue.lines.at(lineIndex).imageId); - Rectangle source = Rectangle{0.0f, 0.0f, static_cast(texture.width), static_cast(texture.height)}; - Rectangle dest = Rectangle{rect.x + 9, rect.y + 9, rect.height - (9 * 2), rect.height - (9 * 2)}; - DrawTexturePro(texture, source, dest, Vector2{0, 0}, 0.0f, WHITE); -} - -void DialogueBalloon::draw() { - if (active) { - Texture uiTexture = Game::getUi().getTexture(); - - Vector2 origin = {0.0f, 0.0f}; - NPatchInfo info = - NPatchInfo{Rectangle{0, 0, static_cast(uiTexture.width), static_cast(uiTexture.height)}, - 3 * 3, 3 * 3, uiTexture.width - (3 * 3), uiTexture.height - (3 * 3)}; - - DrawTextureNPatch(uiTexture, info, rect, origin, 0.0f, WHITE); - - if (dialogue.lines.at(lineIndex).hasPortrait) { - drawPortrait(); - } - - textPos = Vector2{0, 0}; - sectionIndex = 0; - Vector2 charMeasure = Vector2{0, 0}; - for (int i = 0; i < charIndex; i++) { - int size = 0; - int idx = 0; - for (auto section : dialogue.lines.at(lineIndex).sections) { - if (i < (size + TextLength(section.text.c_str()))) { - if (sectionIndex != idx) { - if (section.paddingMode == PADDING_PX) { - padding = section.padding; - } else { - padding = textRect.width * (section.padding / 100); - } - appliedTag = false; - if (section.newline) { - printf("newline tag.. \n"); - } - } - sectionIndex = idx; - - break; - } else { - size += TextLength(section.text.c_str()); - } - idx++; - } - - if (maxLineHeight < charMeasure.y) { - maxLineHeight = charMeasure.y; - } - - auto &line = dialogue.lines.at(lineIndex); - auto §ion = dialogue.lines.at(lineIndex).sections.at(sectionIndex); - - if (fontName != section.font) { - font = Game::getResources().getFont(section.font); - fontName = section.font; - } - - if (section.key == "delay" || section.delay > 0) { - if (!delay) { - delay = true; - delayDuration = section.delay; - } - } - - if (!appliedTag) { - if (section.padding > 0.0f) { - charMeasure.x += padding; - appliedTag = true; - } - } - - const char *subText = TextSubtext(text.c_str(), i, 1); - charP(charMeasure, subText, line, section); - - Vector2 newMeasure = MeasureTextEx(Game::getResources().getFont(section.font), - TextSubtext(text.c_str(), i, 1), section.textSize * 3, 1.0f); - charMeasure = newMeasure; - } - - if (finishedTyping && dialogue.lines.at(lineIndex).hasOptions) { - auto &line = dialogue.lines.at(lineIndex); - - DrawTextureNPatch(uiTexture, info, optionsRect, origin, 0.0f, WHITE); - - Vector2 optionTextPos = {optionsRect.x + 20, optionsRect.y + 20}; - int i = 0; - - for (auto &option : line.options) { - optionTextPos.y += (13 * 3) * i + (4 * i); - - Color optionTextColor = WHITE; - - if (hoveredOption == i) optionTextColor = YELLOW; - - DrawTextEx(Game::getResources().getFont("LanaPixel"), option.title.c_str(), optionTextPos, 13 * 3, 1.0, - optionTextColor); - - i++; - } - } - } -} - -void DialogueBalloon::charP(Vector2 charMeasure, const char *c, DialogueLine &textLine, - DialogueTextSection &textSection) { - Rectangle resRect = this->textRect; - if (textLine.hasPortrait) { - resRect = textPortraitRect; - } - - Vector2 a = Vector2Add(textPos, Vector2{charMeasure.x + 1, 0.0f}); - Vector2 finalCharPos = Vector2Add(Vector2{resRect.x, resRect.y}, a); - - auto §ion = dialogue.lines.at(lineIndex).sections.at(sectionIndex); - - bool hasNewline = false; - if (!appliedTag && section.newline) { - hasNewline = true; - } - if (TextIsEqual(c, "\n")) { - hasNewline = true; - } - - // Check for text overflow on x axis or for newline. - if ((finalCharPos.x + charMeasure.x) > textRect.width || hasNewline) { - textPos.x = 0; - textPos.y += charMeasure.y; - - a = textPos; - finalCharPos = Vector2Add(Vector2{resRect.x, resRect.y}, a); - } else { - textPos.x += charMeasure.x; - } - - DrawTextEx(Game::getResources().getFont(textSection.font), c, finalCharPos, textSection.textSize * 3, 1, - textSection.textColor); -} - -void DialogueBalloon::showDialogue(const DialogueBin &newDialogue) { - if (active) return; - - this->dialogue = newDialogue; - - this->lineIndex = 0; - - firstCharTyped = false; - active = true; - text = ""; - - for (auto k : dialogue.lines.at(lineIndex).sections) { - text = text.append(k.text); - } - - this->frameCounter = 0; - this->charIndex = 0; -} - -void DialogueBalloon::hideDialogue() { active = false; } diff --git a/src/dialogueInterfaceView.cpp b/src/dialogueInterfaceView.cpp new file mode 100644 index 00000000..3f10df92 --- /dev/null +++ b/src/dialogueInterfaceView.cpp @@ -0,0 +1,163 @@ +#include "dialogueInterfaceView.hpp" + +#include +#include +#include + +#include "dialogueBalloon.hpp" +#include "game.hpp" +#include "gamedata.hpp" +#include "interfaceView.hpp" +#include "raylib.h" +#include "ui_elements/button.hpp" +#include "ui_elements/dialogueArea.hpp" +#include "ui_elements/imageRect.hpp" +#include "ui_elements/ninePatchImageRect.hpp" + +static const Rectangle diagImageRect = Rectangle{10, 320, 620, 140}; +static const Rectangle normalDiagAreaRect = Rectangle{19, 329, 611, 131}; +static const Rectangle portraitDiagAreaRect = + Rectangle{normalDiagAreaRect.x + diagImageRect.height, normalDiagAreaRect.y, + normalDiagAreaRect.width - diagImageRect.height - (9 * 2), normalDiagAreaRect.height}; +static const Rectangle optionsRect = + Rectangle{diagImageRect.x + (diagImageRect.width - 180), diagImageRect.y - 8 - 180, 180, 180}; + +DialogueInterfaceView::DialogueInterfaceView() : InterfaceView() {} + +DialogueInterfaceView::DialogueInterfaceView(const std::string &filePath) : InterfaceView(filePath) {} + +DialogueInterfaceView::DialogueInterfaceView(InterfaceViewBin &bin) : InterfaceView(bin) {} + +void DialogueInterfaceView::setDialogue(DialogueBin dialogue) { + this->dialogue = dialogue; + + DialogueArea *diagArea = static_cast(getElement("dialogueArea")); + if (diagArea != nullptr) { + diagArea->setDialogue(dialogue); + } +} + +void DialogueInterfaceView::removeOptionButtons() { + if (optionsCount > 0) { + for (int i = 0; i < optionsCount; i++) { + std::string elementName = TextFormat("option-%i", i); + removeElement(elementName); + } + } +} + +void DialogueInterfaceView::onNotify(Event event) { + InterfaceView::onNotify(event); + + if (event.hold) return; + if (event.key == KEY_Z) { + DialogueArea *diagArea = static_cast(getElement("dialogueArea")); + + if (diagArea != nullptr) { + if (!Game::getUi().getNotifyLock()) { + diagArea->advanceToNextLine(); + } + + if (diagArea->dialogueFinished) return; + + ImageRect *portrait = static_cast(getElement("portrait")); + if (diagArea->line->hasPortrait) { + portrait->loadImage(diagArea->line->imageId); + portrait->props["visible"] = true; + diagArea->props["rect"] = portraitDiagAreaRect; + } else { + portrait->props["visible"] = false; + diagArea->props["rect"] = normalDiagAreaRect; + } + + Button *optionButton = static_cast