godot-ui-control
gamedev-skills/awesome-gamedev-agent-skills
Build responsive Godot 4.7 UIs with Control nodes, Containers, Themes, and keyboard/gamepad focus.
What is godot-ui-control?
Lays out responsive user interfaces in Godot 4.7 using Control nodes with anchors, Container nodes for automatic arrangement, Theme resources for consistent styling, and focus navigation for keyboard and gamepad input. Use this when building HUDs, menus, dialogs, or settings screens that adapt to window size.
- Position and size UI with Control anchors and responsive presets (Full Rect, Center, etc.)
- Arrange children automatically using Container nodes (VBoxContainer, HBoxContainer, GridContainer, MarginContainer)
- Apply consistent styling via Theme resources with per-node overrides when needed
- Wire keyboard and gamepad focus navigation between buttons and interactive controls
- Connect UI signals (pressed, toggled, text_submitted, value_changed) to game logic
- Control child sizing with size_flags to make elements expand or shrink to fill space
How to install godot-ui-control
npx skills add https://github.com/gamedev-skills/awesome-gamedev-agent-skills --skill godot-ui-control- Godot 4.7 installed
- Basic familiarity with the Godot editor and scene tree
- Understanding of Control nodes vs Node2D for UI work
How to use godot-ui-control
- 1.Create a Control or Container node as the root of your UI scene
- 2.Use the Layout presets in the editor or set anchors_preset in code to make UI responsive
- 3.Add child Control nodes (Button, Label, Panel, etc.) and place them in Container nodes
- 4.Assign a Theme resource to the root Control to style all children, or use add_theme_* methods for per-node overrides
- 5.Call grab_focus() on an initial button to enable gamepad/keyboard navigation
- 6.Connect button pressed signals and other UI events to your game logic functions
Use cases
- Building a main menu with vertically stacked buttons that respond to gamepad input
- Creating a responsive HUD that scales with window size using anchor presets
- Designing an inventory or settings screen with themed panels and labeled controls
- Laying out a dialog box with title, content, and action buttons using margin containers
- Making a pause menu with focus navigation that works on both keyboard and controller
- Godot game developers building UI systems
- Game designers prototyping menus and HUDs
- Developers migrating from Godot 3.x to 4.x UI patterns
godot-ui-control FAQ
Always use Control-derived nodes for UI. Node2D is for in-world 2D sprites and objects. Control nodes support theming, focus navigation, and responsive layout.
Use anchors instead of manual position. Set anchors via the Layout presets (e.g., Full Rect, Center) or in code with anchors_preset. Anchors are fractions (0–1) of the parent; offsets are pixel adjustments from the anchored point.
Ensure a Control has focus by calling grab_focus() on an initial button, and verify focus_mode is not FOCUS_NONE. If nothing is focused, directional input is ignored.
No. Children inside a Container cannot set their own position or anchors—the container owns layout. To free-place a node, remove it from the container or wrap it in a plain Control.
A Theme resource styles an entire subtree consistently. Theme overrides (add_theme_*) apply to a single node. Use Theme for centralized styling and overrides only when a specific node needs to differ.
Full instructions (SKILL.md)
Source of truth, from gamedev-skills/awesome-gamedev-agent-skills.
name: godot-ui-control description: > Build Godot 4.7 user interfaces with Control nodes: anchors and offsets for responsive layout, Container nodes (VBox/HBox/Grid/Margin) for automatic arrangement, Theme resources for consistent styling, and keyboard/gamepad focus navigation. Use when laying out a HUD, menu, or UI in a Godot project, working with Control/Container nodes, anchors, themes, or focus in a .tscn.
Godot UI / Control nodes (4.x)
Lay out responsive UI with Control anchors and Container nodes, style it with a
Theme, and make it navigable by keyboard and gamepad. Targets Godot 4.7.
When to use
- Use when building HUDs, menus, inventories, dialog boxes, or settings screens with
Control-derived nodes; arranging UI that adapts to window size; theming; or wiring focus navigation for controller/keyboard.
When not to use: in-world 2D nodes (Node2D/sprites) → godot-nodes-scenes;
animating UI transitions → godot-animation (Tween); genre UIs like card hands →
card-game/visual-novel. For full input rebinding → input-systems.
Core workflow
- Use
Controlnodes for UI, notNode2D. Controls have a rect (position + size), anchors, and participate in focus/theming. - Anchor for responsiveness. Anchors are fractions (0–1) of the parent rect that the Control's edges stick to. Use the editor's Layout presets (Top-Left, Full Rect, Center, etc.) instead of hand-placing pixels.
- Let Containers position children. Put children in a
VBoxContainer,HBoxContainer,GridContainer,MarginContainer, etc. — the container sets their position/size; you control flow withsize_flags. Don't set child anchors inside a container (it overrides them). - Style with a
Theme. Assign aThemeresource on a top Control; children inherit it. Override per-node with theme overrides only when necessary. - Wire focus so gamepad/keyboard can move between buttons; set a default focused control and define neighbors or rely on auto-neighbor.
- Connect signals (
pressed,toggled,text_submitted,value_changed).
Patterns
1. Responsive layout with anchors (code form)
extends Control
func _ready() -> void:
# Stretch this panel to fill its parent (equivalent to the "Full Rect" preset).
anchors_preset = Control.PRESET_FULL_RECT
# Or set anchors manually: all four edges at the parent's far corners.
# anchor_left = 0; anchor_top = 0; anchor_right = 1; anchor_bottom = 1
2. A menu built from containers + button signals
extends VBoxContainer # children stack vertically, auto-sized
func _ready() -> void:
for child in get_children():
if child is Button:
child.pressed.connect(_on_button_pressed.bind(child.name))
# Give the first button focus so a gamepad can navigate immediately.
if get_child_count() > 0:
(get_child(0) as Control).grab_focus()
func _on_button_pressed(which: StringName) -> void:
match which:
"PlayButton": get_tree().change_scene_to_file("res://game.tscn")
"QuitButton": get_tree().quit()
3. Size flags: make one child expand to fill leftover space
# In a HBoxContainer: a label on the left, a spacer that eats remaining width.
func _ready() -> void:
$Label.size_flags_horizontal = Control.SIZE_SHRINK_BEGIN
$Spacer.size_flags_horizontal = Control.SIZE_EXPAND_FILL # grows to fill
4. Theme override for one node (without a full Theme resource)
func _ready() -> void:
# Per-node overrides: use add_theme_* (type-specific setters).
$Title.add_theme_font_size_override("font_size", 32)
$Title.add_theme_color_override("font_color", Color.GOLD)
$Panel.add_theme_stylebox_override("panel", preload("res://ui/panel.stylebox.tres"))
Pitfalls
- Mixing manual position with Containers. A child of a
Containercannot set its own position/anchors — the container owns layout. To free-place, take the node out of the container or use a plainControl/PanelContainerwrapper. - Anchors vs offsets. Anchors are fractions of the parent; offsets are pixel deltas from the anchored point. Set anchors via presets, then nudge with offsets. Setting only position while anchors are at 0 makes UI not scale with the window.
Node2Dfor UI. Buttons/labels parented under aNode2Dwon't theme or take focus correctly. Keep UI under aCanvasLayer/Controlsubtree.- Focus lost on gamepad. If nothing is focused, directional input does nothing. Call
grab_focus()on an initial control and ensurefocus_modeis notFOCUS_NONE. - Theme vs theme override. A
Themeresource styles a whole subtree;add_theme_*overrides one node. Overusing per-node overrides defeats centralized theming. rect_*properties are renamed. Godot 3'srect_size/rect_position/rect_min_sizeare nowsize/position/custom_minimum_sizein 4.x.mouse_filteron a full-rect Control can swallow clicks meant for nodes beneath it; setMOUSE_FILTER_IGNOREon purely decorative panels.
References
- For the anchor/offset math, every Container type, building/extending Theme and StyleBox
resources, focus neighbor wiring, and
CanvasLayerfor HUDs, readreferences/layout-and-theming.md.
Related skills
game-ui-ux— cross-engine UI/UX: responsive scaling, safe areas, focus navigation, screen flow.godot-animation— Tween-based UI transitions and juicing.godot-signals-groups— connecting UI events to game logic.input-systems— rebindable input and multi-device focus.card-game/visual-novel— UI-heavy genre templates.
Related skills
More from gamedev-skills/awesome-gamedev-agent-skills and the wider catalog.

input-systems
Design game input as named actions with rebinding, multi-device support, deadzones, and feel features like buffering and coyote time.

itch-publish
Publish and update game builds on itch.io using butler CLI with efficient delta uploads.

level-design
Design playable levels through blockout-to-playable workflow: metrics, pacing, gating, and encounter design.

love2d-core
Set up and debug LÖVE 11.x games: the callback loop, delta-time movement, input, and screen states.

performance-optimization
Measure, find the bottleneck, apply the right fix—CPU pooling/allocation control or GPU batching/draw calls.

phaser-arcade-physics
Add movement and collision to Phaser games with the lightweight Arcade Physics engine.