### Install PlutoVG using CMake Source: https://github.com/ghsoares/godot-rmlui/blob/main/thirdparty/plutovg/README.md These bash commands guide you through cloning the PlutoVG repository, configuring the build with CMake, compiling the library, and installing it. ```bash git clone https://github.com/sammycage/plutovg.git cd plutovg cmake -B build . cmake --build build cmake --install build ``` -------------------------------- ### Install PlutoVG using Meson Source: https://github.com/ghsoares/godot-rmlui/blob/main/thirdparty/plutovg/README.md Follow these bash commands to clone the PlutoVG repository, set up the build environment with Meson, compile the library, and install it. ```bash git clone https://github.com/sammycage/plutovg.git cd plutovg meson setup build Meson compile -C build Meson install -C build ``` -------------------------------- ### Install RmlUi Core Target Source: https://github.com/ghsoares/godot-rmlui/blob/main/thirdparty/rmlui/Source/Core/CMakeLists.txt Installs the rmlui_core target, including runtime dependencies, to the appropriate directories (bin, lib). It also installs the PDB file for debugging. ```cmake # RMLUI_CMAKE_MINIMUM_VERSION_RAISE_NOTICE: # We use default paths provided from GNUInstallDirs. From CMake 3.14 these paths (CMAKE_INSTALL_...) will be used # automatically and can be removed from the following call. The same applies to many other calls to install(TARGETS...). # Note that GNUInstallDirs should still be included in the project root. install(TARGETS rmlui_core EXPORT RmlUiTargets ${RMLUI_RUNTIME_DEPENDENCY_SET_ARG} RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR} LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} ) install_target_pdb(rmlui_core) ``` -------------------------------- ### Load and Interact with RMLDocument Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Example of using the `RMLDocument` node in Godot. It loads an RML file and demonstrates how to dynamically toggle CSS classes on an element using GDScript for interactive effects. ```gdscript extends RMLDocument func _ready() -> void: load_from_path("res://ui/fancy_card.rml") # Dynamically toggle the blur filter class await get_tree().create_timer(2.0).timeout var card: RMLElement = as_element().query_selector("#info-card") if card.is_valid(): card.toggle_class("blurred") ``` -------------------------------- ### Basic RML Structure Example Source: https://github.com/ghsoares/godot-rmlui/blob/main/README.md An example of a basic RML document structure, including common elements like span, button, svg, and input. This can be loaded using the RMLDocument node. ```xml Hello! ``` -------------------------------- ### Create New RMLDocument Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Use `new_document()` to start with a clean slate when dynamically building the DOM from GDScript. This discards any previously loaded content. ```gdscript extends RMLDocument func build_inventory_ui(items: Array[Dictionary]) -> void: new_document() # start with a clean slate var root: RMLElement = as_element() root.set_inner_rml("") # body is already empty, but explicit for item in items: var div: RMLElement = create_element("div") div.set_attribute("class", "item-card") div.set_text_content(item["name"]) div.set_property("background-color", item.get("color", "#333")) root.append_child(div) # Force layout recalculation so get_rect() is accurate immediately update() print("First card rect: ", root.get_child(0).get_rect()) ``` -------------------------------- ### Manage RML Documents with RMLServer Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Example of managing RML documents using RMLServer. It shows how to create, store, and free RML document RIDs to prevent memory leaks. Ensure `free_rid` is called when documents are no longer needed. ```gdscript extends Node var _docs: Array[RID] = [] func create_popup(rml_path: String) -> RID: var rid: RID = RMLServer.create_document_from_path(rml_path) _docs.append(rid) return rid func destroy_popup(rid: RID) -> void: if rid.is_valid(): RMLServer.free_rid(rid) _docs.erase(rid) func _exit_tree() -> void: # Clean up all open documents on scene exit for rid in _docs: if rid.is_valid(): RMLServer.free_rid(rid) _docs.clear() ``` -------------------------------- ### Get RMLDocument Root Element Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Use `as_element()` to get an `RMLElement` reference to the document's root (``) element. This is the entry point for DOM traversal and mutation. ```gdscript extends RMLDocument func _ready() -> void: load_from_rml_string("

Hello

") var body: RMLElement = as_element() print("Tag: ", body.get_tag_name()) # "body" print("Children: ", body.get_child_count()) # 1 var p_el: RMLElement = body.get_child(0) print("Text: ", p_el.get_text_content()) # ["Hello"] ``` -------------------------------- ### Draw a Smiley Face with PlutoVG Source: https://github.com/ghsoares/godot-rmlui/blob/main/thirdparty/plutovg/README.md This C code demonstrates how to create a smiley face image using PlutoVG. It involves creating a surface, a canvas, drawing arcs for the face, eyes, and mouth, setting colors, line widths, and finally saving the output as a PNG file. Ensure PlutoVG is installed and linked correctly. ```c #include int main(void) { const int width = 150; const int height = 150; const float center_x = width / 2.f; const float center_y = height / 2.f; const float face_radius = 70; const float mouth_radius = 50; const float eye_radius = 10; const float eye_offset_x = 25; const float eye_offset_y = 20; const float eye_x = center_x - eye_offset_x; const float eye_y = center_y - eye_offset_y; plutovg_surface_t* surface = plutovg_surface_create(width, height); plutovg_canvas_t* canvas = plutovg_canvas_create(surface); plutovg_canvas_save(canvas); plutovg_canvas_arc(canvas, center_x, center_y, face_radius, 0, PLUTOVG_TWO_PI, 0); plutovg_canvas_set_rgb(canvas, 1, 1, 0); plutovg_canvas_fill_preserve(canvas); plutovg_canvas_set_rgb(canvas, 0, 0, 0); plutovg_canvas_set_line_width(canvas, 5); plutovg_canvas_stroke(canvas); plutovg_canvas_restore(canvas); plutovg_canvas_save(canvas); plutovg_canvas_arc(canvas, eye_x, eye_y, eye_radius, 0, PLUTOVG_TWO_PI, 0); plutovg_canvas_arc(canvas, center_x + eye_offset_x, eye_y, eye_radius, 0, PLUTOVG_TWO_PI, 0); plutovg_canvas_set_rgb(canvas, 0, 0, 0); plutovg_canvas_fill(canvas); plutovg_canvas_restore(canvas); plutovg_canvas_save(canvas); plutovg_canvas_arc(canvas, center_x, center_y, mouth_radius, 0, PLUTOVG_PI, 0); plutovg_canvas_set_rgb(canvas, 0, 0, 0); plutovg_canvas_set_line_width(canvas, 5); plutovg_canvas_stroke(canvas); plutovg_canvas_restore(canvas); plutovg_surface_write_to_png(surface, "smiley.png"); plutovg_canvas_destroy(canvas); plutovg_surface_destroy(surface); return 0; } ``` -------------------------------- ### Apply and Get Inline Styles with RMLElement Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Use `set_property` to apply inline RCSS styles similar to the HTML `style` attribute. `get_property` retrieves computed styles, falling back to a default if not set. `remove_property` reverts to stylesheet values. ```gdscript extends RMLDocument func highlight_element(selector: String, color: String = "#ffeb3b") -> void: var el: RMLElement = as_element().query_selector(selector) if not el.is_valid(): return # Apply inline styles el.set_property("background-color", color) el.set_property("border", "2px " + color) el.set_property("transition", "background-color 0.3s") # Read back a computed property var bg: String = el.get_property("background-color", "transparent") print("Background is now: ", bg) # Remove an inline override to fall back to stylesheet await get_tree().create_timer(2.0).timeout el.remove_property("background-color") el.remove_property("border") ``` -------------------------------- ### RMLElement DOM Traversal and Manipulation Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Provides methods for traversing and manipulating the Document Object Model (DOM) of RML elements. This includes getting parent and child elements, adding, removing, and clearing children. ```APIDOC ## RMLElement DOM Traversal (`get_parent`, `get_children`, `get_child`, `get_child_count`, `append_child`, `remove_child`, `clear_children`) Provides full parent/child DOM manipulation. Elements are `RefCounted` references; adding/removing them from the tree does not free the underlying data while a reference is held. ```gdscript extends RMLDocument func _ready() -> void: load_from_path("res://ui/inventory.rml") var grid: RMLElement = as_element().query_selector("#item-grid") if not grid.is_valid(): return print("Slot count: ", grid.get_child_count()) # e.g. 16 # Iterate all children for child in grid.get_children(): var slot := child as RMLElement if slot.get_attribute("data-empty", "true") == "true": slot.set_property("opacity", "0.3") # Move first child to end var first: RMLElement = grid.get_child(0) grid.remove_child(first) grid.append_child(first) # Check parent linkage print("Parent tag: ", first.get_parent().get_tag_name()) # "div" (grid) # Remove all slots and rebuild grid.clear_children() for i in range(8): var slot: RMLElement = create_element("div") slot.set_attribute("class", "slot") slot.set_attribute("data-empty", "true") grid.append_child(slot) ``` ``` -------------------------------- ### Project Settings Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Control the default stylesheet loaded at startup using project settings. You can enable the built-in default stylesheet or specify a custom one. ```APIDOC ## Project Settings Two project settings control the default stylesheet loaded at startup. ```gdscript # Project Settings (Project > Project Settings > RmlUi) # "RmlUi/load_user_agent_stylesheet" (bool, default: true) # Loads the built-in default.rcss stylesheet that styles body, headings, # buttons, scrollbars, inputs, tables, etc. # # "RmlUi/custom_user_agent_stylesheet" (String, default: "") # Path to a custom .rcss file that replaces the built-in stylesheet. # Leave empty to use the bundled default. # Override via code (call before the first document is created): ProjectSettings.set_setting("RmlUi/load_user_agent_stylesheet", true) ProjectSettings.set_setting("RmlUi/custom_user_agent_stylesheet", "res://ui/my_theme.rcss") ``` ``` -------------------------------- ### RMLServer Usage Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Headless/offscreen rendering using the RMLServer singleton with raw RIDs. Create documents with create_document_from_path or create_document_from_rml_string, size them with document_set_size, drive input with document_process_event, and render each frame with document_update + document_draw. ```APIDOC ## RMLServer ### Description For advanced integration — such as rendering UI onto a 3D surface, inside a SubViewport, or in a headless simulation — use `RMLServer` directly. Create documents with `create_document_from_path` or `create_document_from_rml_string`, size them with `document_set_size`, drive input with `document_process_event`, and render each frame with `document_update` + `document_draw` passing a canvas item RID. ### GDScript Example Snippet ```gdscript # Assuming 'rml_path' is a valid path to an RML file var rid: RID = RMLServer.create_document_from_path(rml_path) # Set document size RMLServer.document_set_size(rid, Vector2(800, 600)) # Process input events (example) var event = InputEventMouseMotion.new() event.position = Vector2(100, 100) RMLServer.document_process_event(rid, event) # Update and draw the document (requires a CanvasItem RID) # var canvas_item_rid: RID = ... # RMLServer.document_update(rid) # RMLServer.document_draw(rid, canvas_item_rid) ``` ``` -------------------------------- ### Configure RmlUi Project Settings Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Set project settings to control the default stylesheet loaded at startup. This can be done via the Project Settings UI or programmatically before the first document is created. ```gdscript # Project Settings (Project > Project Settings > RmlUi) # "RmlUi/load_user_agent_stylesheet" (bool, default: true) # Loads the built-in default.rcss stylesheet that styles body, headings, # buttons, scrollbars, inputs, tables, etc. # # "RmlUi/custom_user_agent_stylesheet" (String, default: "") # Path to a custom .rcss file that replaces the built-in stylesheet. # Leave empty to use the bundled default. # Override via code (call before the first document is created): ProjectSettings.set_setting("RmlUi/load_user_agent_stylesheet", true) ProjectSettings.set_setting("RmlUi/custom_user_agent_stylesheet", "res://ui/my_theme.rcss") ``` -------------------------------- ### Center RMLElement using get_rect() in GDScript Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Calculates and sets the position of an RMLElement to center it within its parent. Ensure the layout is up-to-date by calling RMLDocument.update() before getting the element's rectangle. ```gdscript extends RMLDocument func center_popup(popup_selector: String) -> void: update() # ensure layout is current var popup: RMLElement = as_element().query_selector(popup_selector) if not popup.is_valid(): return var r: Rect2 = popup.get_rect() var doc_size: Vector2 = size # Control.size — the RMLDocument node size var center_x: float = (doc_size.x - r.size.x) / 2.0 var center_y: float = (doc_size.y - r.size.y) / 2.0 popup.set_property("position", "absolute") popup.set_property("left", "%dpx" % int(center_x)) popup.set_property("top", "%dpx" % int(center_y)) print("Popup rect: ", r) # e.g. Rect2(0, 0, 300, 200) print("Centered at: ", center_x, center_y) ``` -------------------------------- ### Manipulate Server-Managed RML Document Root in GDScript Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Demonstrates how to get the root RMLElement of a server-managed RML document using RMLServer.get_document_root. This allows for DOM manipulation similar to RMLDocument, but on documents managed by RMLServer. ```gdscript func populate_server_document(doc_rid: RID, items: Array[String]) -> void: var root: RMLElement = RMLServer.get_document_root(doc_rid) if not root.is_valid(): return root.clear_children() for item_text in items: var li: RMLElement = RMLServer.create_element(doc_rid, "li") li.set_text_content(item_text) root.append_child(li) ``` -------------------------------- ### Query RMLElements with CSS Selectors Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Use `query_selector()` to find the first matching element or `query_selector_all()` to find all matches using standard CSS selectors. Supports tag, class, id, and combinators. ```gdscript extends RMLDocument func _ready() -> void: load_from_path("res://ui/settings.rml") # Single element by id var volume_slider: RMLElement = as_element().query_selector("#volume-slider") if volume_slider.is_valid(): volume_slider.set_attribute("value", "75") # All elements with a class var tabs: Array = as_element().query_selector_all(".tab-button") for tab in tabs: var t := tab as RMLElement if t.is_valid(): t.add_event_listener("click", func(ev: Dictionary): # Remove active from all, then set on clicked for other in tabs: (other as RMLElement).remove_class("active") (ev["target_element"] as RMLElement).set_class("active") ) ``` -------------------------------- ### Create and Render RML Documents Headlessly in GDScript Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Shows how to create RML documents using the RMLServer for headless rendering, such as to a texture. It covers creating documents from paths or strings, setting their size, updating the layout, and drawing to a canvas item. ```gdscript # Headless document rendering to a custom canvas item extends Node2D var _doc_rid: RID func _ready() -> void: var server: RMLServer = RMLServer # Create from file _doc_rid = server.create_document_from_path("res://ui/minimap.rml") # OR from inline string # _doc_rid = server.create_document_from_rml_string( # "
" # ) if not _doc_rid.is_valid(): push_error("Failed to create document") return server.document_set_size(_doc_rid, Vector2i(256, 256)) func _draw() -> void: if _doc_rid.is_valid(): RMLServer.document_update(_doc_rid) RMLServer.document_draw(_doc_rid, get_canvas_item()) func _exit_tree() -> void: if _doc_rid.is_valid(): RMLServer.free_rid(_doc_rid) _doc_rid = RID() ``` -------------------------------- ### Load RML UI from File with RMLDocument Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Load an RML UI layout from a file using `RMLDocument.load_from_path()`. This method resolves paths through Godot's virtual file system. After loading, elements can be queried and updated. ```gdscript # res://ui/hud.rml # #
Score: 0
extends RMLDocument # node type set to RMLDocument in the scene func _ready() -> void: load_from_path("res://ui/hud.rml") # After loading, query the score element and update its text var score_el: RMLElement = as_element().query_selector("#score") if score_el.is_valid(): score_el.set_text_content("Score: 42") ``` -------------------------------- ### Custom Configuration File and Include Directories Source: https://github.com/ghsoares/godot-rmlui/blob/main/thirdparty/rmlui/Source/Core/CMakeLists.txt Allows specifying a custom configuration file and include directories for RmlUi. This is controlled by `RMLUI_CUSTOM_CONFIGURATION_FILE` and `RMLUI_CUSTOM_INCLUDE_DIRS`. ```cmake if(RMLUI_CUSTOM_CONFIGURATION AND RMLUI_CUSTOM_CONFIGURATION_FILE) target_compile_definitions(rmlui_core PUBLIC "RMLUI_CUSTOM_CONFIGURATION_FILE=\"${RMLUI_CUSTOM_CONFIGURATION_FILE}\"") message(STATUS "Including ${RMLUI_CUSTOM_CONFIGURATION_FILE} instead of ") endif() if(RMLUI_CUSTOM_CONFIGURATION AND RMLUI_CUSTOM_INCLUDE_DIRS) target_include_directories(rmlui_core PUBLIC ${RMLUI_CUSTOM_INCLUDE_DIRS}) endif() if(RMLUI_CUSTOM_CONFIGURATION AND RMLUI_CUSTOM_LINK_LIBRARIES) target_link_libraries(rmlui_core PUBLIC ${RMLUI_CUSTOM_LINK_LIBRARIES}) endif() ``` -------------------------------- ### RMLDocument - new_document() Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Creates a fresh empty document, discarding any previously loaded content. Use this as a reset before dynamically building the DOM entirely from GDScript. ```APIDOC ## RMLDocument - new_document() Creates a fresh empty document, discarding any previously loaded content. Use this as a reset before dynamically building the DOM entirely from GDScript. ```gdscript extends RMLDocument func build_inventory_ui(items: Array[Dictionary]) -> void: new_document() # start with a clean slate var root: RMLElement = as_element() root.set_inner_rml("") # body is already empty, but explicit for item in items: var div: RMLElement = create_element("div") div.set_attribute("class", "item-card") div.set_text_content(item["name"]) div.set_property("background-color", item.get("color", "#333")) root.append_child(div) # Force layout recalculation so get_rect() is accurate immediately update() print("First card rect: ", root.get_child(0).get_rect()) ``` ``` -------------------------------- ### RMLDocument — load_from_path Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Loads an RML document from a file path using Godot's virtual file system. This is suitable for authoring full UI screens. ```APIDOC ## RMLDocument — `load_from_path(path: String)` Replaces the current document with one loaded from an `.rml` file on disk. The file is resolved through Godot's virtual file system so `res://` and `user://` paths both work. This is the simplest way to author a full UI screen. ```gdscript # res://ui/hud.rml # #
Score: 0
extends RMLDocument # node type set to RMLDocument in the scene func _ready() -> void: load_from_path("res://ui/hud.rml") # After loading, query the score element and update its text var score_el: RMLElement = as_element().query_selector("#score") if score_el.is_valid(): score_el.set_text_content("Score: 42") ``` ``` -------------------------------- ### RMLServer Document Creation Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Provides low-level methods for creating RML documents managed by the RMLServer. Documents can be created from a file path, an RML string, or an empty RID. This is useful for managing documents outside the scene tree. ```APIDOC ## RMLServer — `create_document() -> RID` / `create_document_from_path(path) -> RID` / `create_document_from_rml_string(rml) -> RID` Low-level document creation through the singleton server, returning an opaque `RID`. Use this when you need to manage RmlUi documents outside the scene tree (e.g., render to a texture, headless processing). ```gdscript # Headless document rendering to a custom canvas item extends Node2D var _doc_rid: RID func _ready() -> void: var server: RMLServer = RMLServer # Create from file _doc_rid = server.create_document_from_path("res://ui/minimap.rml") # OR from inline string # _doc_rid = server.create_document_from_rml_string( # "
" # ) if not _doc_rid.is_valid(): push_error("Failed to create document") return server.document_set_size(_doc_rid, Vector2i(256, 256)) func _draw() -> void: if _doc_rid.is_valid(): RMLServer.document_update(_doc_rid) RMLServer.document_draw(_doc_rid, get_canvas_item()) func _exit_tree() -> void: if _doc_rid.is_valid(): RMLServer.free_rid(_doc_rid) _doc_rid = RID() ``` ``` -------------------------------- ### Load RML UI from String with RMLDocument Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Load an RML UI layout directly from a string using `RMLDocument.load_from_rml_string()`. This is useful for procedurally generated UIs or small, in-code layouts. Event listeners can be attached after loading. ```gdscript extends RMLDocument func _ready() -> void: var rml := """ " load_from_rml_string(rml) # Attach a click handler after loading var btn: RMLElement = as_element().query_selector("#start-btn") if btn.is_valid(): btn.add_event_listener("click", _on_start_clicked) func _on_start_clicked(event: Dictionary) -> void: # event keys: "type", "target_element", "current_element" print("Start clicked! Event type: ", event["type"]) # Stop the event from bubbling further event["stop_propagation"] = true get_tree().change_scene_to_file("res://game.tscn") ``` -------------------------------- ### RMLElement - query_selector() / query_selector_all() Source: https://context7.com/ghsoares/godot-rmlui/llms.txt CSS-style element selection. query_selector returns the first match; query_selector_all returns all matches as a typed array. Supports standard CSS selectors (tag, class, id, combinators). ```APIDOC ## RMLElement - query_selector(selector: String) -> RMLElement / query_selector_all(selector: String) -> RMLElement[] CSS-style element selection. `query_selector` returns the first match; `query_selector_all` returns all matches as a typed array. Supports standard CSS selectors (tag, class, id, combinators). ```gdscript extends RMLDocument func _ready() -> void: load_from_path("res://ui/settings.rml") # Single element by id var volume_slider: RMLElement = as_element().query_selector("#volume-slider") if volume_slider.is_valid(): volume_slider.set_attribute("value", "75") # All elements with a class var tabs: Array = as_element().query_selector_all(".tab-button") for tab in tabs: var t := tab as RMLElement if t.is_valid(): t.add_event_listener("click", func(ev: Dictionary): # Remove active from all, then set on clicked for other in tabs: (other as RMLElement).remove_class("active") (ev["target_element"] as RMLElement).set_class("active") ) ``` ``` -------------------------------- ### RMLDocument Usage Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Scene-integrated UI using the RMLDocument Control node. Drop an RMLDocument node into any scene, extend it in GDScript, call load_from_path in _ready, and use as_element().query_selector(...) to wire up interactivity. ```APIDOC ## RMLDocument ### Description Scene-integrated UI using the `RMLDocument` Control node. Drop an `RMLDocument` node into any scene, extend it in GDScript, call `load_from_path` in `_ready`, and use `as_element().query_selector(...)` to wire up interactivity — the Control node handles sizing, input forwarding, and rendering automatically. ### GDScript Example ```gdscript extends RMLDocument func _ready() -> void: load_from_path("res://ui/fancy_card.rml") # Dynamically toggle the blur filter class await get_tree().create_timer(2.0).timeout var card: RMLElement = as_element().query_selector("#info-card") if card.is_valid(): card.toggle_class("blurred") ``` ``` -------------------------------- ### Add Lottie Plugin Source Files to rmlui_core Source: https://github.com/ghsoares/godot-rmlui/blob/main/thirdparty/rmlui/Source/Lottie/CMakeLists.txt Specifies the source files for the Lottie plugin to be compiled directly into the rmlui_core library when the plugin is enabled. ```cmake target_sources(rmlui_core PRIVATE "${CMAKE_CURRENT_SOURCE_DIR}/ElementLottie.cpp" "${CMAKE_CURRENT_SOURCE_DIR}/LottiePlugin.cpp" "${CMAKE_CURRENT_SOURCE_DIR}/LottiePlugin.h" "${PROJECT_SOURCE_DIR}/Include/RmlUi/Lottie/ElementLottie.h" ) ``` -------------------------------- ### Link Lottie Plugin Source: https://github.com/ghsoares/godot-rmlui/blob/main/thirdparty/rmlui/Source/Core/CMakeLists.txt Links the rlottie library to the rmlui_core target if the RMLUI_LOTTIE_PLUGIN is enabled. This is for RmlUi's Lottie animation plugin. ```cmake if(RMLUI_LOTTIE_PLUGIN) # RMLUI_CMAKE_MINIMUM_VERSION_RAISE_NOTICE: # From CMake 3.13 we could move this to `Lottie/CMakeLists.txt`, see CMP0079. target_link_libraries(rmlui_core PRIVATE rlottie::rlottie) endif() ``` -------------------------------- ### RMLServer.load_font_face_from_path and RMLServer.load_font_face_from_buffer Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Registers font files or buffers with RmlUi's font engine. Allows adding custom fonts beyond the default. Returns true on success. ```APIDOC ## RMLServer.load_font_face_from_path / RMLServer.load_font_face_from_buffer ### Description Registers a font file with RmlUi's font engine. `fallback_face` marks the font as the fallback for unrecognized glyphs. Returns `true` on success. The built-in Open Sans font is loaded automatically; use these methods to add custom fonts. ### Method Signatures `load_font_face_from_path(path: String, fallback_face: bool = false) -> bool` `load_font_face_from_buffer(buffer: PackedByteArray, family: String, fallback_face: bool = false, is_italic: bool = false) -> bool` ``` -------------------------------- ### Define RMLUI_LOTTIE_PLUGIN Compile Definition Source: https://github.com/ghsoares/godot-rmlui/blob/main/thirdparty/rmlui/Source/Lottie/CMakeLists.txt Adds a compile definition 'RMLUI_LOTTIE_PLUGIN' to the rmlui_core target, enabling Lottie plugin specific code paths. ```cmake target_compile_definitions(rmlui_core PRIVATE "RMLUI_LOTTIE_PLUGIN") ``` -------------------------------- ### RML Document with RCSS Styling Source: https://context7.com/ghsoares/godot-rmlui/llms.txt An RML document demonstrating advanced RCSS styling, including keyframe animations, gradient decorators, box shadows, filters, and backdrop filters. It also shows dynamic class toggling for visual effects. ```xml

Godot RmlUi

HTML/CSS-based UI inside Godot 4.5+

``` -------------------------------- ### Configure Tracy Profiling Source: https://github.com/ghsoares/godot-rmlui/blob/main/thirdparty/rmlui/Source/Core/CMakeLists.txt Configures RmlUi to use Tracy for profiling. It supports conditional linking and compile definitions based on configuration types and memory profiling flags. ```cmake if(RMLUI_TRACY_PROFILING) if(CMAKE_CONFIGURATION_TYPES AND RMLUI_TRACY_CONFIGURATION) target_link_libraries(rmlui_core PUBLIC "$<$:Tracy::TracyClient>") target_compile_definitions(rmlui_core PUBLIC "$<$:RMLUI_TRACY_PROFILING>") if(RMLUI_TRACY_MEMORY_PROFILING) target_compile_definitions(rmlui_core PRIVATE "$<$:RMLUI_TRACY_MEMORY_PROFILING>") endif() message(STATUS "Tracy profiling enabled in configuration `Tracy`.") else() target_link_libraries(rmlui_core PUBLIC Tracy::TracyClient) target_compile_definitions(rmlui_core PUBLIC "RMLUI_TRACY_PROFILING") if(RMLUI_TRACY_MEMORY_PROFILING) target_compile_definitions(rmlui_core PRIVATE "RMLUI_TRACY_MEMORY_PROFILING") endif() message(STATUS "Tracy profiling enabled.") endif() endif() ``` -------------------------------- ### Include RMLUI Core and Optional Plugins Source: https://github.com/ghsoares/godot-rmlui/blob/main/thirdparty/rmlui/Source/CMakeLists.txt This snippet shows how to add RMLUI subdirectories to the CMake build. Optional plugins are included conditionally based on defined variables. ```cmake add_subdirectory("Core") if(RMLUI_LOTTIE_PLUGIN) add_subdirectory("Lottie") endif() if(RMLUI_SVG_PLUGIN) add_subdirectory("SVG") endif() add_subdirectory("Debugger") if(RMLUI_LUA_BINDINGS) add_subdirectory("Lua") endif() ``` -------------------------------- ### Update and Draw Server-Managed Document Source: https://context7.com/ghsoares/godot-rmlui/llms.txt The core rendering loop for server-managed documents. Call `document_update` to recalculate layout, then `document_draw` to issue draw commands. Ensure `queue_redraw` is called to trigger rendering. ```gdscript extends Node2D var _doc_rid: RID func _ready() -> void: _doc_rid = RMLServer.create_document_from_path("res://ui/hud.rml") RMLServer.document_set_size(_doc_rid, Vector2i(get_viewport_rect().size)) func _draw() -> void: if not _doc_rid.is_valid(): return RMLServer.document_update(_doc_rid) RMLServer.document_draw(_doc_rid, get_canvas_item()) func _process(_delta: float) -> void: queue_redraw() # trigger _draw each frame func _exit_tree() -> void: if _doc_rid.is_valid(): RMLServer.free_rid(_doc_rid) ``` -------------------------------- ### Load RML Document from Path in Godot Source: https://github.com/ghsoares/godot-rmlui/blob/main/README.md Use this script to load an RML document from a specified path within your Godot project. Ensure the RML file exists at the given path. ```gdscript extends RMLDocument func _ready() -> void: load_from_path("res://test.rml") ``` -------------------------------- ### Load Custom Fonts Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Registers custom font files with RmlUi. Use `load_font_face_from_path` for project files or `load_font_face_from_buffer` for byte arrays. The `fallback_face` parameter marks a font for unrecognized glyphs. ```gdscript extends Node func _ready() -> void: var server: RMLServer = RMLServer # Load from project file var ok: bool = server.load_font_face_from_path("res://fonts/MyFont-Regular.ttf") print("Font loaded: ", ok) # true # Load italic variant ok = server.load_font_face_from_path("res://fonts/MyFont-Italic.ttf") print("Italic loaded: ", ok) # Load from a FontFile resource buffer (e.g., packed at export time) var font_file: FontFile = load("res://fonts/FallbackFont.ttf") if font_file: var buffer: PackedByteArray = font_file.data ok = server.load_font_face_from_buffer(buffer, "FallbackFont", true, false) print("Fallback font loaded: ", ok) # Now use the custom font in RCSS # body { font-family: 'MyFont'; } ``` -------------------------------- ### RMLDocument - as_element() Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Returns an RMLElement reference to the document's root () element, providing the entry point for all DOM traversal and mutation on the high-level node. ```APIDOC ## RMLDocument - as_element() -> RMLElement Returns an `RMLElement` reference to the document's root (``) element, providing the entry point for all DOM traversal and mutation on the high-level node. ```gdscript extends RMLDocument func _ready() -> void: load_from_rml_string("

Hello

") var body: RMLElement = as_element() print("Tag: ", body.get_tag_name()) # "body" print("Children: ", body.get_child_count()) # 1 var p_el: RMLElement = body.get_child(0) print("Text: ", p_el.get_text_content()) # ["Hello"] ``` ``` -------------------------------- ### RMLDocument - update() Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Forces an immediate layout pass. Call this after bulk DOM mutations if you need to read back layout geometry (e.g., RMLElement.get_rect()) in the same frame without waiting for the next render tick. ```APIDOC ## RMLDocument - update() Forces an immediate layout pass. Call this after bulk DOM mutations if you need to read back layout geometry (e.g., `RMLElement.get_rect()`) in the same frame without waiting for the next render tick. ```gdscript extends RMLDocument func _ready() -> void: load_from_path("res://ui/tooltip.rml") var tooltip: RMLElement = as_element().query_selector("#tooltip") tooltip.set_text_content("This is a very long tooltip message that wraps.") update() # layout is now current var r: Rect2 = tooltip.get_rect() print("Tooltip size after text update: ", r.size) # e.g. (320.0, 48.0) ``` ``` -------------------------------- ### RMLServer.free_rid Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Releases all resources associated with a server-managed document, including its RmlUi context and render context. Must be called when the document is no longer needed to prevent memory leaks. ```APIDOC ## RMLServer.free_rid ### Description Releases all resources associated with a server-managed document, including its RmlUi context and render context. Must be called when the document is no longer needed to prevent memory leaks. ### Method Signature `free_rid(rid: RID)` ### Parameters * **rid** (RID) - The resource identifier of the document to be freed. ``` -------------------------------- ### Manage RMLElement Attributes Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Use `set_attribute()`, `get_attribute()`, and `remove_attribute()` to read, write, and remove arbitrary HTML-style attributes. Values can be strings, integers, or floats. ```gdscript extends RMLDocument func _ready() -> void: load_from_rml_string("") var hp_bar: RMLElement = as_element().query_selector("#hp") if hp_bar.is_valid(): # Read current value (returns Variant; default_value used if absent) var current = hp_bar.get_attribute("value", 100) print("Current HP: ", current) # 100 # Update value hp_bar.set_attribute("value", 65) # Disable the input hp_bar.set_attribute("disabled", true) # Remove the disabled state hp_bar.remove_attribute("disabled") ``` -------------------------------- ### Enable Precompiled Headers Source: https://github.com/ghsoares/godot-rmlui/blob/main/thirdparty/rmlui/Source/Core/CMakeLists.txt Enables precompiled headers for the rmlui_core target if `RMLUI_PRECOMPILED_HEADERS` is set and the CMake version is 3.16 or greater. Otherwise, it prints a status message indicating the requirement. ```cmake # RMLUI_CMAKE_MINIMUM_VERSION_RAISE_NOTICE: # From CMake 3.16 we can skip the version check. if(RMLUI_PRECOMPILED_HEADERS AND CMAKE_VERSION VERSION_GREATER_EQUAL "3.16") target_precompile_headers(rmlui_core PRIVATE "${PROJECT_SOURCE_DIR}/Source/Core/precompiled.h") elseif(RMLUI_PRECOMPILED_HEADERS) message(STATUS "Could not enable precompiled headers, requires CMake version 3.16 or greater.") endif() ``` -------------------------------- ### Create and Append Table Element Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Creates a 'table' element and its child 'tr' and 'td' elements, setting text content for cells. The element must be appended to the DOM to render. ```gdscript func build_table(doc_rid: RID, data: Array[Array]) -> void: var root: RMLElement = RMLServer.get_document_root(doc_rid) var table: RMLElement = RMLServer.create_element(doc_rid, "table") for row_data in data: var tr: RMLElement = RMLServer.create_element(doc_rid, "tr") for cell_text in row_data: var td: RMLElement = RMLServer.create_element(doc_rid, "td") td.set_text_content(str(cell_text)) tr.append_child(td) table.append_child(tr) root.append_child(table) ``` -------------------------------- ### RMLServer.document_process_event Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Forwards a Godot InputEvent to a server-managed document's RmlUi context, handling various input types. Returns true if the event was consumed by the document. ```APIDOC ## RMLServer.document_process_event ### Description Forwards a Godot `InputEvent` to a server-managed document's RmlUi context. Handles mouse buttons, mouse motion, scroll wheel, keyboard, and touch input. Returns `true` if the document consumed the event. ### Method Signature `document_process_event(document: RID, event: InputEvent) -> bool` ``` -------------------------------- ### RMLServer `get_document_root()` Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Retrieves an `RMLElement` reference to the root element of a server-managed document. This allows for DOM manipulation using the same API as the high-level `RMLDocument.as_element()`. ```APIDOC ## RMLServer — `get_document_root(document: RID) -> RMLElement` Retrieves an `RMLElement` reference to the root element of a server-managed document, enabling the same DOM manipulation API as the high-level `RMLDocument.as_element()`. ```gdscript func populate_server_document(doc_rid: RID, items: Array[String]) -> void: var root: RMLElement = RMLServer.get_document_root(doc_rid) if not root.is_valid(): return root.clear_children() for item_text in items: var li: RMLElement = RMLServer.create_element(doc_rid, "li") li.set_text_content(item_text) root.append_child(li) ``` ``` -------------------------------- ### Manipulate RMLElement DOM Tree in GDScript Source: https://context7.com/ghsoares/godot-rmlui/llms.txt Demonstrates DOM traversal and manipulation using methods like get_child_count, get_children, get_child, remove_child, append_child, and clear_children. Use this to dynamically modify the structure of RML elements. ```gdscript extends RMLDocument func _ready() -> void: load_from_path("res://ui/inventory.rml") var grid: RMLElement = as_element().query_selector("#item-grid") if not grid.is_valid(): return print("Slot count: ", grid.get_child_count()) # e.g. 16 # Iterate all children for child in grid.get_children(): var slot := child as RMLElement if slot.get_attribute("data-empty", "true") == "true": slot.set_property("opacity", "0.3") # Move first child to end var first: RMLElement = grid.get_child(0) grid.remove_child(first) grid.append_child(first) # Check parent linkage print("Parent tag: ", first.get_parent().get_tag_name()) # "div" (grid) # Remove all slots and rebuild grid.clear_children() for i in range(8): var slot: RMLElement = create_element("div") slot.set_attribute("class", "slot") slot.set_attribute("data-empty", "true") grid.append_child(slot) ``` -------------------------------- ### Add RMLUI Lua Element Source Files Source: https://github.com/ghsoares/godot-rmlui/blob/main/thirdparty/rmlui/Source/Lua/Elements/CMakeLists.txt Configures the CMake build system to include specific source files for the RMLUI Lua elements. Uses absolute paths for robustness with different CMake versions. ```cmake target_sources(rmlui_lua PRIVATE "${CMAKE_CURRENT_SOURCE_DIR}/As.h" "${CMAKE_CURRENT_SOURCE_DIR}/ElementForm.cpp" "${CMAKE_CURRENT_SOURCE_DIR}/ElementForm.h" "${CMAKE_CURRENT_SOURCE_DIR}/ElementFormControl.cpp" "${CMAKE_CURRENT_SOURCE_DIR}/ElementFormControl.h" "${CMAKE_CURRENT_SOURCE_DIR}/ElementFormControlInput.cpp" "${CMAKE_CURRENT_SOURCE_DIR}/ElementFormControlInput.h" "${CMAKE_CURRENT_SOURCE_DIR}/ElementFormControlSelect.cpp" "${CMAKE_CURRENT_SOURCE_DIR}/ElementFormControlSelect.h" "${CMAKE_CURRENT_SOURCE_DIR}/ElementFormControlTextArea.cpp" "${CMAKE_CURRENT_SOURCE_DIR}/ElementFormControlTextArea.h" "${CMAKE_CURRENT_SOURCE_DIR}/ElementTabSet.cpp" "${CMAKE_CURRENT_SOURCE_DIR}/ElementTabSet.h" "${CMAKE_CURRENT_SOURCE_DIR}/SelectOptionsProxy.cpp" "${CMAKE_CURRENT_SOURCE_DIR}/SelectOptionsProxy.h" ) ```