Upgrade to Godot 4.5

Upgraded to version 4.5 of Godot. Also now includes code to load map from resources, plus on-screen controls, zooming and instructions on how to adjust basic functionality
pull/19/head
Kenney 2025-09-16 12:23:04 +07:00
parent 3ced0cf607
commit 1023ab252f
49 changed files with 247 additions and 21 deletions

@ -1,6 +1,6 @@
MIT License
Copyright (c) 2023 Kenney
Copyright (c) 2025 Kenney
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal

@ -2,7 +2,7 @@
# Starter Kit City Builder
This package includes a basic template for a 3D city builder in Godot 4.3 (stable). Includes features like;
This package includes a basic template for a 3D city builder in Godot 4.5 (stable). Includes features like;
- Building and removing structures
- Smooth camera controls
@ -21,6 +21,7 @@ This package includes a basic template for a 3D city builder in Godot 4.3 (stabl
| <kbd>W</kbd> <kbd>A</kbd> <kbd>S</kbd> <kbd>D</kbd> | Move camera |
| <kbd>F</kbd> | Camera to center |
| <kbd>Middle mouse button</kbd> | Hold to rotate camera |
| <kbd>Scroll wheel</kbd> | Zoom |
| <kbd>Left mouse button</kbd> | Place building |
| <kbd>DEL</kbd> | Remove building |
| <kbd>Right mouse button</kbd> | Rotate building |
@ -28,11 +29,34 @@ This package includes a basic template for a 3D city builder in Godot 4.3 (stabl
| <kbd>F1</kbd> | Save |
| <kbd>F2</kbd> | Load |
### Instructions
1. How to add more buildings?
Duplicate one of the existing resources in the 'structures' folder, adjust the properties in the inspector. Select the 'Builder' node in the scene and add your new resources to the 'Structures' array.
2. How to adjust building models?
Select the resource of the building you'd like to change in the 'structures' folder, adjust the model in the inspector.
3. How to save and load cities?
Pressing F1 during gameplay will save the current city to disk, F2 will load it from the same location. The file is saved as 'map.res' in the user folder (see below). You can adjust this in the 'action_save' and 'action_load' functions found in the 'builder.gd' script.
User data folder:
- Windows: `%APPDATA%/Godot/app_userdata/Starter Kit City Builder/`
- Linux: `~/.local/share/godot/app_userdata/Starter Kit City Builder/`
- MacOS: `~/Library/Application Support/Godot/app_userdata/Starter Kit City Builder/`
4. How to include city data in the project and load this?
You'll find a sample map in the 'sample map' folder, to load this during gameplay press F3. You can find the function that handles this as 'action_load_resources' found in the 'builder.gd' script.
### License
MIT License
Copyright (c) 2024 Kenney
Copyright (c) 2025 Kenney
Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:

Binary file not shown.

Before

Width:  |  Height:  |  Size: 9.2 KiB

After

Width:  |  Height:  |  Size: 9.9 KiB

@ -2,23 +2,24 @@
importer="texture"
type="CompressedTexture2D"
uid="uid://bnn1b2yg61elu"
path.s3tc="res://.godot/imported/colormap.png-c1bc3c3aabeec406ff4b53328583776a.s3tc.ctex"
uid="uid://k6f5xxl8mufc"
path="res://.godot/imported/colormap.png-c1bc3c3aabeec406ff4b53328583776a.ctex"
metadata={
"imported_formats": ["s3tc_bptc"],
"vram_texture": true
"vram_texture": false
}
[deps]
source_file="res://models/Textures/colormap.png"
dest_files=["res://.godot/imported/colormap.png-c1bc3c3aabeec406ff4b53328583776a.s3tc.ctex"]
dest_files=["res://.godot/imported/colormap.png-c1bc3c3aabeec406ff4b53328583776a.ctex"]
[params]
compress/mode=2
compress/mode=0
compress/high_quality=false
compress/lossy_quality=0.7
compress/uastc_level=0
compress/rdo_quality_loss=0.0
compress/hdr_compression=1
compress/normal_map=0
compress/channel_pack=0
@ -26,6 +27,10 @@ mipmaps/generate=true
mipmaps/limit=-1
roughness/mode=0
roughness/src_normal=""
process/channel_remap/red=0
process/channel_remap/green=1
process/channel_remap/blue=2
process/channel_remap/alpha=3
process/fix_alpha_border=true
process/premult_alpha=false
process/normal_map_invert_y=false

Binary file not shown.

@ -15,9 +15,12 @@ dest_files=["res://.godot/imported/building-garage.glb-79efa6120b759910e8bd3785c
nodes/root_type="Node3D"
nodes/root_name="Scene Root"
nodes/root_script=null
nodes/apply_root_scale=true
nodes/root_scale=1.0
nodes/import_as_skeleton_bones=false
nodes/use_name_suffixes=true
nodes/use_node_type_suffixes=true
meshes/ensure_tangents=true
meshes/generate_lods=true
meshes/create_shadow_meshes=true
@ -31,6 +34,9 @@ animation/trimming=false
animation/remove_immutable_tracks=true
animation/import_rest_as_RESET=false
import_script/path=""
materials/extract=0
materials/extract_format=0
materials/extract_path=""
_subresources={}
gltf/naming_version=0
gltf/embedded_image_handling=1

Binary file not shown.

@ -15,9 +15,12 @@ dest_files=["res://.godot/imported/building-small-a.glb-ebf8430e523f14eba5266940
nodes/root_type="Node3D"
nodes/root_name="Scene Root"
nodes/root_script=null
nodes/apply_root_scale=true
nodes/root_scale=1.0
nodes/import_as_skeleton_bones=false
nodes/use_name_suffixes=true
nodes/use_node_type_suffixes=true
meshes/ensure_tangents=true
meshes/generate_lods=true
meshes/create_shadow_meshes=true
@ -31,6 +34,9 @@ animation/trimming=false
animation/remove_immutable_tracks=true
animation/import_rest_as_RESET=false
import_script/path=""
materials/extract=0
materials/extract_format=0
materials/extract_path=""
_subresources={}
gltf/naming_version=0
gltf/embedded_image_handling=1

Binary file not shown.

@ -15,9 +15,12 @@ dest_files=["res://.godot/imported/building-small-b.glb-437a13e47ceef14c49e1239f
nodes/root_type="Node3D"
nodes/root_name="Scene Root"
nodes/root_script=null
nodes/apply_root_scale=true
nodes/root_scale=1.0
nodes/import_as_skeleton_bones=false
nodes/use_name_suffixes=true
nodes/use_node_type_suffixes=true
meshes/ensure_tangents=true
meshes/generate_lods=true
meshes/create_shadow_meshes=true
@ -31,6 +34,9 @@ animation/trimming=false
animation/remove_immutable_tracks=true
animation/import_rest_as_RESET=false
import_script/path=""
materials/extract=0
materials/extract_format=0
materials/extract_path=""
_subresources={}
gltf/naming_version=0
gltf/embedded_image_handling=1

Binary file not shown.

@ -15,9 +15,12 @@ dest_files=["res://.godot/imported/building-small-c.glb-73a68022181ffa29853dcbcb
nodes/root_type="Node3D"
nodes/root_name="Scene Root"
nodes/root_script=null
nodes/apply_root_scale=true
nodes/root_scale=1.0
nodes/import_as_skeleton_bones=false
nodes/use_name_suffixes=true
nodes/use_node_type_suffixes=true
meshes/ensure_tangents=true
meshes/generate_lods=true
meshes/create_shadow_meshes=true
@ -31,6 +34,9 @@ animation/trimming=false
animation/remove_immutable_tracks=true
animation/import_rest_as_RESET=false
import_script/path=""
materials/extract=0
materials/extract_format=0
materials/extract_path=""
_subresources={}
gltf/naming_version=0
gltf/embedded_image_handling=1

Binary file not shown.

@ -15,9 +15,12 @@ dest_files=["res://.godot/imported/building-small-d.glb-5e1b608dc43429cd8ce16f12
nodes/root_type="Node3D"
nodes/root_name="Scene Root"
nodes/root_script=null
nodes/apply_root_scale=true
nodes/root_scale=1.0
nodes/import_as_skeleton_bones=false
nodes/use_name_suffixes=true
nodes/use_node_type_suffixes=true
meshes/ensure_tangents=true
meshes/generate_lods=true
meshes/create_shadow_meshes=true
@ -31,6 +34,9 @@ animation/trimming=false
animation/remove_immutable_tracks=true
animation/import_rest_as_RESET=false
import_script/path=""
materials/extract=0
materials/extract_format=0
materials/extract_path=""
_subresources={}
gltf/naming_version=0
gltf/embedded_image_handling=1

Binary file not shown.

@ -15,9 +15,12 @@ dest_files=["res://.godot/imported/grass-trees-tall.glb-7300613123c00a0615ded796
nodes/root_type="Node3D"
nodes/root_name="Scene Root"
nodes/root_script=null
nodes/apply_root_scale=true
nodes/root_scale=1.0
nodes/import_as_skeleton_bones=false
nodes/use_name_suffixes=true
nodes/use_node_type_suffixes=true
meshes/ensure_tangents=true
meshes/generate_lods=true
meshes/create_shadow_meshes=true
@ -31,6 +34,9 @@ animation/trimming=false
animation/remove_immutable_tracks=true
animation/import_rest_as_RESET=false
import_script/path=""
materials/extract=0
materials/extract_format=0
materials/extract_path=""
_subresources={}
gltf/naming_version=0
gltf/embedded_image_handling=1

Binary file not shown.

@ -15,9 +15,12 @@ dest_files=["res://.godot/imported/grass-trees.glb-0492608f30e8f36fd08db19dc56a2
nodes/root_type="Node3D"
nodes/root_name="Scene Root"
nodes/root_script=null
nodes/apply_root_scale=true
nodes/root_scale=1.0
nodes/import_as_skeleton_bones=false
nodes/use_name_suffixes=true
nodes/use_node_type_suffixes=true
meshes/ensure_tangents=true
meshes/generate_lods=true
meshes/create_shadow_meshes=true
@ -31,6 +34,9 @@ animation/trimming=false
animation/remove_immutable_tracks=true
animation/import_rest_as_RESET=false
import_script/path=""
materials/extract=0
materials/extract_format=0
materials/extract_path=""
_subresources={}
gltf/naming_version=0
gltf/embedded_image_handling=1

Binary file not shown.

@ -15,9 +15,12 @@ dest_files=["res://.godot/imported/grass.glb-0ce858eae1c69c894a569863f13e24f1.sc
nodes/root_type="Node3D"
nodes/root_name="Scene Root"
nodes/root_script=null
nodes/apply_root_scale=true
nodes/root_scale=1.0
nodes/import_as_skeleton_bones=false
nodes/use_name_suffixes=true
nodes/use_node_type_suffixes=true
meshes/ensure_tangents=true
meshes/generate_lods=true
meshes/create_shadow_meshes=true
@ -31,6 +34,9 @@ animation/trimming=false
animation/remove_immutable_tracks=true
animation/import_rest_as_RESET=false
import_script/path=""
materials/extract=0
materials/extract_format=0
materials/extract_path=""
_subresources={}
gltf/naming_version=0
gltf/embedded_image_handling=1

Binary file not shown.

@ -15,9 +15,12 @@ dest_files=["res://.godot/imported/pavement-fountain.glb-0424db34de6f91479f6cbd7
nodes/root_type="Node3D"
nodes/root_name="Scene Root"
nodes/root_script=null
nodes/apply_root_scale=true
nodes/root_scale=1.0
nodes/import_as_skeleton_bones=false
nodes/use_name_suffixes=true
nodes/use_node_type_suffixes=true
meshes/ensure_tangents=true
meshes/generate_lods=true
meshes/create_shadow_meshes=true
@ -31,6 +34,9 @@ animation/trimming=false
animation/remove_immutable_tracks=true
animation/import_rest_as_RESET=false
import_script/path=""
materials/extract=0
materials/extract_format=0
materials/extract_path=""
_subresources={}
gltf/naming_version=0
gltf/embedded_image_handling=1

Binary file not shown.

@ -15,9 +15,12 @@ dest_files=["res://.godot/imported/pavement.glb-e677d053825d20c1d08d69229498f8a6
nodes/root_type="Node3D"
nodes/root_name="Scene Root"
nodes/root_script=null
nodes/apply_root_scale=true
nodes/root_scale=1.0
nodes/import_as_skeleton_bones=false
nodes/use_name_suffixes=true
nodes/use_node_type_suffixes=true
meshes/ensure_tangents=true
meshes/generate_lods=true
meshes/create_shadow_meshes=true
@ -31,6 +34,9 @@ animation/trimming=false
animation/remove_immutable_tracks=true
animation/import_rest_as_RESET=false
import_script/path=""
materials/extract=0
materials/extract_format=0
materials/extract_path=""
_subresources={}
gltf/naming_version=0
gltf/embedded_image_handling=1

Binary file not shown.

@ -15,9 +15,12 @@ dest_files=["res://.godot/imported/road-corner.glb-d7ee80907d88726297a071be68be1
nodes/root_type="Node3D"
nodes/root_name="Scene Root"
nodes/root_script=null
nodes/apply_root_scale=true
nodes/root_scale=1.0
nodes/import_as_skeleton_bones=false
nodes/use_name_suffixes=true
nodes/use_node_type_suffixes=true
meshes/ensure_tangents=true
meshes/generate_lods=true
meshes/create_shadow_meshes=true
@ -31,6 +34,9 @@ animation/trimming=false
animation/remove_immutable_tracks=true
animation/import_rest_as_RESET=false
import_script/path=""
materials/extract=0
materials/extract_format=0
materials/extract_path=""
_subresources={}
gltf/naming_version=0
gltf/embedded_image_handling=1

Binary file not shown.

@ -15,9 +15,12 @@ dest_files=["res://.godot/imported/road-intersection.glb-8962e4b1c3c280c3abad7b8
nodes/root_type="Node3D"
nodes/root_name="Scene Root"
nodes/root_script=null
nodes/apply_root_scale=true
nodes/root_scale=1.0
nodes/import_as_skeleton_bones=false
nodes/use_name_suffixes=true
nodes/use_node_type_suffixes=true
meshes/ensure_tangents=true
meshes/generate_lods=true
meshes/create_shadow_meshes=true
@ -31,6 +34,9 @@ animation/trimming=false
animation/remove_immutable_tracks=true
animation/import_rest_as_RESET=false
import_script/path=""
materials/extract=0
materials/extract_format=0
materials/extract_path=""
_subresources={}
gltf/naming_version=0
gltf/embedded_image_handling=1

Binary file not shown.

@ -15,9 +15,12 @@ dest_files=["res://.godot/imported/road-split.glb-84d39fa6e15630686f271db254fa4a
nodes/root_type="Node3D"
nodes/root_name="Scene Root"
nodes/root_script=null
nodes/apply_root_scale=true
nodes/root_scale=1.0
nodes/import_as_skeleton_bones=false
nodes/use_name_suffixes=true
nodes/use_node_type_suffixes=true
meshes/ensure_tangents=true
meshes/generate_lods=true
meshes/create_shadow_meshes=true
@ -31,6 +34,9 @@ animation/trimming=false
animation/remove_immutable_tracks=true
animation/import_rest_as_RESET=false
import_script/path=""
materials/extract=0
materials/extract_format=0
materials/extract_path=""
_subresources={}
gltf/naming_version=0
gltf/embedded_image_handling=1

@ -15,9 +15,12 @@ dest_files=["res://.godot/imported/road-straight-lightposts.glb-dce683910787213a
nodes/root_type="Node3D"
nodes/root_name="Scene Root"
nodes/root_script=null
nodes/apply_root_scale=true
nodes/root_scale=1.0
nodes/import_as_skeleton_bones=false
nodes/use_name_suffixes=true
nodes/use_node_type_suffixes=true
meshes/ensure_tangents=true
meshes/generate_lods=true
meshes/create_shadow_meshes=true
@ -31,6 +34,9 @@ animation/trimming=false
animation/remove_immutable_tracks=true
animation/import_rest_as_RESET=false
import_script/path=""
materials/extract=0
materials/extract_format=0
materials/extract_path=""
_subresources={}
gltf/naming_version=0
gltf/embedded_image_handling=1

Binary file not shown.

@ -15,9 +15,12 @@ dest_files=["res://.godot/imported/road-straight.glb-31d31cca3c90d98620d476ef869
nodes/root_type="Node3D"
nodes/root_name="Scene Root"
nodes/root_script=null
nodes/apply_root_scale=true
nodes/root_scale=1.0
nodes/import_as_skeleton_bones=false
nodes/use_name_suffixes=true
nodes/use_node_type_suffixes=true
meshes/ensure_tangents=true
meshes/generate_lods=true
meshes/create_shadow_meshes=true
@ -31,6 +34,9 @@ animation/trimming=false
animation/remove_immutable_tracks=true
animation/import_rest_as_RESET=false
import_script/path=""
materials/extract=0
materials/extract_format=0
materials/extract_path=""
_subresources={}
gltf/naming_version=0
gltf/embedded_image_handling=1

@ -13,7 +13,7 @@ config_version=5
config/name="Starter Kit City Builder"
config/tags=PackedStringArray("starterkit")
run/main_scene="res://scenes/main.tscn"
config/features=PackedStringArray("4.3", "Forward Plus")
config/features=PackedStringArray("4.5", "Forward Plus")
boot_splash/bg_color=Color(0.92549, 0.92549, 0.960784, 1)
boot_splash/image="res://splash-screen.png"
config/icon="res://icon.png"
@ -84,11 +84,26 @@ load={
"events": [Object(InputEventKey,"resource_local_to_scene":false,"resource_name":"","device":-1,"window_id":0,"alt_pressed":false,"shift_pressed":false,"ctrl_pressed":false,"meta_pressed":false,"pressed":false,"keycode":0,"physical_keycode":4194333,"key_label":0,"unicode":0,"location":0,"echo":false,"script":null)
]
}
load_resources={
"deadzone": 0.2,
"events": [Object(InputEventKey,"resource_local_to_scene":false,"resource_name":"","device":-1,"window_id":0,"alt_pressed":false,"shift_pressed":false,"ctrl_pressed":false,"meta_pressed":false,"pressed":false,"keycode":0,"physical_keycode":4194334,"key_label":0,"unicode":0,"location":0,"echo":false,"script":null)
]
}
camera_center={
"deadzone": 0.5,
"events": [Object(InputEventKey,"resource_local_to_scene":false,"resource_name":"","device":-1,"window_id":0,"alt_pressed":false,"shift_pressed":false,"ctrl_pressed":false,"meta_pressed":false,"pressed":false,"keycode":0,"physical_keycode":70,"key_label":0,"unicode":102,"location":0,"echo":false,"script":null)
]
}
zoom_in={
"deadzone": 0.2,
"events": [Object(InputEventMouseButton,"resource_local_to_scene":false,"resource_name":"","device":-1,"window_id":0,"alt_pressed":false,"shift_pressed":false,"ctrl_pressed":false,"meta_pressed":false,"button_mask":0,"position":Vector2(0, 0),"global_position":Vector2(0, 0),"factor":1.0,"button_index":4,"canceled":false,"pressed":false,"double_click":false,"script":null)
]
}
zoom_out={
"deadzone": 0.2,
"events": [Object(InputEventMouseButton,"resource_local_to_scene":false,"resource_name":"","device":-1,"window_id":0,"alt_pressed":false,"shift_pressed":false,"ctrl_pressed":false,"meta_pressed":false,"button_mask":0,"position":Vector2(0, 0),"global_position":Vector2(0, 0),"factor":1.0,"button_index":5,"canceled":false,"pressed":false,"double_click":false,"script":null)
]
}
[rendering]

@ -23,7 +23,6 @@ ssao_intensity = 0.5
ssao_power = 100.0
ssao_horizon = 0.1
sdfgi_cascades = 1
sdfgi_max_distance = 25.6
sdfgi_energy = 0.5
glow_levels/2 = 0.6
glow_levels/3 = 0.6

@ -1,8 +1,8 @@
[gd_scene load_steps=24 format=3 uid="uid://vgwrcfy1qawf"]
[gd_scene load_steps=25 format=3 uid="uid://vgwrcfy1qawf"]
[ext_resource type="Script" path="res://scripts/builder.gd" id="1_jybm7"]
[ext_resource type="Script" uid="uid://76g8ejmdibal" path="res://scripts/builder.gd" id="1_jybm7"]
[ext_resource type="Environment" uid="uid://jbptgqvstei3" path="res://scenes/main-environment.tres" id="1_yndf3"]
[ext_resource type="Script" path="res://scripts/structure.gd" id="2_54v6r"]
[ext_resource type="Script" uid="uid://b4i7dfy6u3e8w" path="res://scripts/structure.gd" id="2_54v6r"]
[ext_resource type="Resource" uid="uid://dv14kkhb6umkv" path="res://structures/road-straight.tres" id="2_bwyku"]
[ext_resource type="Resource" uid="uid://d2jplegnkl6u2" path="res://structures/road-corner.tres" id="3_6fpyf"]
[ext_resource type="Resource" uid="uid://mxrnqinnsqnt" path="res://structures/road-straight-lightposts.tres" id="3_o6o81"]
@ -13,7 +13,7 @@
[ext_resource type="Resource" uid="uid://cqvwy36htu81" path="res://structures/road-split.tres" id="7_kqu4g"]
[ext_resource type="Resource" uid="uid://dveu4dnue0d54" path="res://structures/road-intersection.tres" id="8_1swhv"]
[ext_resource type="Resource" uid="uid://dqqe3iofnleup" path="res://structures/pavement-fountain.tres" id="8_4il2q"]
[ext_resource type="Script" path="res://scripts/view.gd" id="8_yovpv"]
[ext_resource type="Script" uid="uid://dec71yx4xpg2c" path="res://scripts/view.gd" id="8_yovpv"]
[ext_resource type="Resource" uid="uid://tm532uesguhk" path="res://structures/grass.tres" id="9_ifw7y"]
[ext_resource type="Resource" uid="uid://bh65eqgid4kxy" path="res://structures/building-small-c.tres" id="10_84or2"]
[ext_resource type="Resource" uid="uid://ccb475jeg7ym5" path="res://structures/grass-trees.tres" id="10_vaeah"]
@ -22,6 +22,7 @@
[ext_resource type="Resource" uid="uid://bqb6g3t0tebno" path="res://structures/building-garage.tres" id="13_ut2cy"]
[ext_resource type="FontFile" uid="uid://d0cxd77jybrcn" path="res://fonts/lilita_one_regular.ttf" id="16_vlub6"]
[ext_resource type="Texture2D" uid="uid://bng0d1sou7c8a" path="res://sprites/coin.png" id="17_cjamx"]
[ext_resource type="Texture2D" uid="uid://ciwbdik3tmxtp" path="res://sprites/instructions.png" id="22_pm3ni"]
[sub_resource type="LabelSettings" id="LabelSettings_q176i"]
font = ExtResource("16_vlub6")
@ -37,7 +38,7 @@ selector = NodePath("Selector")
selector_container = NodePath("Selector/Container")
view_camera = NodePath("../View/Camera")
gridmap = NodePath("../GridMap")
cash_display = NodePath("../CanvasLayer/Control/Cash")
cash_display = NodePath("../CanvasLayer/Top/Cash")
[node name="Selector" type="Node3D" parent="Builder"]
@ -69,13 +70,13 @@ shadow_opacity = 0.75
[node name="CanvasLayer" type="CanvasLayer" parent="."]
[node name="Control" type="Control" parent="CanvasLayer"]
[node name="Top" type="Control" parent="CanvasLayer"]
layout_mode = 3
anchors_preset = 0
offset_right = 40.0
offset_bottom = 40.0
[node name="CashIcon" type="TextureRect" parent="CanvasLayer/Control"]
[node name="CashIcon" type="TextureRect" parent="CanvasLayer/Top"]
layout_mode = 0
offset_left = 20.0
offset_top = 24.0
@ -84,7 +85,7 @@ offset_bottom = 152.0
scale = Vector2(0.3, 0.3)
texture = ExtResource("17_cjamx")
[node name="Cash" type="Label" parent="CanvasLayer/Control"]
[node name="Cash" type="Label" parent="CanvasLayer/Top"]
layout_mode = 0
offset_left = 69.0
offset_top = 27.0
@ -92,3 +93,21 @@ offset_right = 270.0
offset_bottom = 101.0
text = "$10,000"
label_settings = SubResource("LabelSettings_q176i")
[node name="Bottom" type="Control" parent="CanvasLayer"]
layout_mode = 3
anchors_preset = 2
anchor_top = 1.0
anchor_bottom = 1.0
offset_top = -648.0
offset_bottom = -648.0
grow_vertical = 0
[node name="Instructions" type="TextureRect" parent="CanvasLayer/Bottom"]
layout_mode = 0
offset_left = 24.0
offset_top = 375.0
offset_right = 344.0
offset_bottom = 887.0
scale = Vector2(0.5, 0.5)
texture = ExtResource("22_pm3ni")

@ -46,6 +46,7 @@ func _process(delta):
action_save() # Saving
action_load() # Loading
action_load_resources() # Loading from resources
# Map position based on mouse
@ -154,3 +155,17 @@ func action_load():
gridmap.set_cell_item(Vector3i(cell.position.x, 0, cell.position.y), cell.structure, cell.orientation)
update_cash()
func action_load_resources():
if Input.is_action_just_pressed("load_resources"):
print("Loading map...")
gridmap.clear()
map = ResourceLoader.load("res://sample map/map.res")
if not map:
map = DataMap.new()
for cell in map.structures:
gridmap.set_cell_item(Vector3i(cell.position.x, 0, cell.position.y), cell.structure, cell.orientation)
update_cash()

@ -0,0 +1 @@
uid://76g8ejmdibal

@ -0,0 +1 @@
uid://dvrs714bu830u

@ -0,0 +1 @@
uid://c77is823atr3

@ -0,0 +1 @@
uid://b4i7dfy6u3e8w

@ -3,6 +3,8 @@ extends Node3D
var camera_position:Vector3
var camera_rotation:Vector3
var zoom:float = 30.0 # 30 = Standard zoom level, in meters
@onready var camera = $Camera
func _ready():
@ -18,6 +20,10 @@ func _process(delta):
position = position.lerp(camera_position, delta * 8)
rotation_degrees = rotation_degrees.lerp(camera_rotation, delta * 6)
# Smoothly update zoom
camera.position = camera.position.lerp(Vector3(0, 0, zoom), delta * 8)
handle_input(delta)
# Handle input
@ -35,6 +41,14 @@ func handle_input(_delta):
camera_position += input / 4
# Zoom in/out
if Input.is_action_just_released("zoom_in"):
zoom = max(15, zoom - 5) # 15 = Minimum zoom level, in meters
if Input.is_action_just_released("zoom_out"):
zoom = min(80, zoom + 5) # 80 = Maximum zoom level, in meters
# Back to center
if Input.is_action_pressed("camera_center"):

@ -0,0 +1 @@
uid://dec71yx4xpg2c

Binary file not shown.

After

Width:  |  Height:  |  Size: 29 KiB

@ -0,0 +1,40 @@
[remap]
importer="texture"
type="CompressedTexture2D"
uid="uid://ciwbdik3tmxtp"
path="res://.godot/imported/instructions.png-9c9313d48cdc2ce76399562162121c3a.ctex"
metadata={
"vram_texture": false
}
[deps]
source_file="res://sprites/instructions.png"
dest_files=["res://.godot/imported/instructions.png-9c9313d48cdc2ce76399562162121c3a.ctex"]
[params]
compress/mode=0
compress/high_quality=false
compress/lossy_quality=0.7
compress/uastc_level=0
compress/rdo_quality_loss=0.0
compress/hdr_compression=1
compress/normal_map=0
compress/channel_pack=0
mipmaps/generate=false
mipmaps/limit=-1
roughness/mode=0
roughness/src_normal=""
process/channel_remap/red=0
process/channel_remap/green=1
process/channel_remap/blue=2
process/channel_remap/alpha=3
process/fix_alpha_border=true
process/premult_alpha=false
process/normal_map_invert_y=false
process/hdr_as_srgb=false
process/hdr_clamp_exposure=false
process/size_limit=0
detect_3d/compress_to=1

@ -1,7 +1,7 @@
[gd_resource type="Resource" script_class="Structure" load_steps=3 format=3 uid="uid://bqb6g3t0tebno"]
[ext_resource type="PackedScene" uid="uid://d0nnrx2y4px2v" path="res://models/building-garage.glb" id="1_gyclk"]
[ext_resource type="Script" path="res://scripts/structure.gd" id="2_jrinw"]
[ext_resource type="Script" uid="uid://b4i7dfy6u3e8w" path="res://scripts/structure.gd" id="2_jrinw"]
[resource]
script = ExtResource("2_jrinw")

@ -1,7 +1,7 @@
[gd_resource type="Resource" script_class="Structure" load_steps=3 format=3 uid="uid://dveu4dnue0d54"]
[ext_resource type="PackedScene" uid="uid://euxdh7lkq0oj" path="res://models/road-intersection.glb" id="1_pnjl2"]
[ext_resource type="Script" path="res://scripts/structure.gd" id="2_3eq5k"]
[ext_resource type="Script" uid="uid://b4i7dfy6u3e8w" path="res://scripts/structure.gd" id="2_3eq5k"]
[resource]
script = ExtResource("2_3eq5k")

Binary file not shown.