From 9657f330fc85271699e86e75a9c8cf2d781143e4 Mon Sep 17 00:00:00 2001 From: Florian Date: Mon, 15 Sep 2025 19:03:18 +0200 Subject: [PATCH 1/4] Added A Grid --- earth.tscn | 10 +++++++++- grid.gd | 23 +++++++++++++++++++++++ grid.gd.uid | 1 + 3 files changed, 33 insertions(+), 1 deletion(-) create mode 100644 grid.gd create mode 100644 grid.gd.uid diff --git a/earth.tscn b/earth.tscn index 20f0afd..bc1e011 100644 --- a/earth.tscn +++ b/earth.tscn @@ -1,7 +1,8 @@ -[gd_scene load_steps=4 format=3 uid="uid://33k5v6skcbsm"] +[gd_scene load_steps=5 format=3 uid="uid://33k5v6skcbsm"] [ext_resource type="Texture2D" uid="uid://cy70quh6k3s1j" path="res://icon.svg" id="1_qbwya"] [ext_resource type="Script" uid="uid://b5fhsy1xlreco" path="res://draw_circle.gd" id="2_2bhor"] +[ext_resource type="Script" uid="uid://m3vyyfk8gnma" path="res://grid.gd" id="3_2bhor"] [sub_resource type="CircleShape2D" id="CircleShape2D_5i67w"] radius = 3000.0 @@ -20,3 +21,10 @@ radius = 3000.0 [node name="Camera2D" type="Camera2D" parent="."] position = Vector2(47, -3283) + +[node name="Node2D" type="Node2D" parent="."] +script = ExtResource("3_2bhor") +ground_radius = 3000.0 +cell_height = 300.0 +num_collumns = 36 +debug = true diff --git a/grid.gd b/grid.gd new file mode 100644 index 0000000..0c7c74e --- /dev/null +++ b/grid.gd @@ -0,0 +1,23 @@ +class_name Grid extends Node2D + +@export var ground_radius : float +@export var cell_height : float +@export var num_collumns : int +@export var debug : bool + +func _draw() -> void: + if !debug: + return + + for i in range(10): + draw_arc(Vector2.ZERO, ground_radius + i * cell_height, 0, TAU, 250, Color.SKY_BLUE, 1.0, true); + + for i in range(num_collumns): + var angle = i * TAU / num_collumns; + draw_line(Vector2.ZERO, 10000 * Vector2.from_angle(angle), Color.SKY_BLUE); + +#func cart_to_sphere(cart : Vector2): + #var x = cart.x; var y = cart.y; + #var radius = sqrt(x*x + y*y); + #var angle = tan(y/x) + ## TODO diff --git a/grid.gd.uid b/grid.gd.uid new file mode 100644 index 0000000..5298a7a --- /dev/null +++ b/grid.gd.uid @@ -0,0 +1 @@ +uid://m3vyyfk8gnma From 774a74da04afc3609536f0e17a3f991005935c39 Mon Sep 17 00:00:00 2001 From: Florian Date: Mon, 15 Sep 2025 19:07:52 +0200 Subject: [PATCH 2/4] Named the Grid "Grid". --- earth.tscn | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/earth.tscn b/earth.tscn index bc1e011..a2b03e5 100644 --- a/earth.tscn +++ b/earth.tscn @@ -22,9 +22,10 @@ radius = 3000.0 [node name="Camera2D" type="Camera2D" parent="."] position = Vector2(47, -3283) -[node name="Node2D" type="Node2D" parent="."] +[node name="Grid" type="Node2D" parent="."] script = ExtResource("3_2bhor") ground_radius = 3000.0 cell_height = 300.0 -num_collumns = 36 +num_collumns = 60 debug = true +metadata/_custom_type_script = "uid://m3vyyfk8gnma" From 2274eab9e157a9b328496b11dcc43d188a058d80 Mon Sep 17 00:00:00 2001 From: Florian Date: Tue, 16 Sep 2025 00:19:40 +0200 Subject: [PATCH 3/4] Wrote a shader --- building.gd | 27 +++++++++++++++++++++++++++ building.gd.uid | 1 + building.gdshader | 34 ++++++++++++++++++++++++++++++++++ building.gdshader.uid | 1 + building.tscn | 22 ++++++++++++++++++++++ draw_circle.gd | 2 +- earth.tscn | 11 ++++++++--- grid.gd | 24 +++++++++++++++++++----- 8 files changed, 113 insertions(+), 9 deletions(-) create mode 100644 building.gd create mode 100644 building.gd.uid create mode 100644 building.gdshader create mode 100644 building.gdshader.uid create mode 100644 building.tscn diff --git a/building.gd b/building.gd new file mode 100644 index 0000000..e252fdd --- /dev/null +++ b/building.gd @@ -0,0 +1,27 @@ +class_name Building extends Node2D + +var location : Vector2i # x is the angle, y is the height in the grid +var dimension : Vector2i = Vector2.ONE # same as above +@onready var grid : Grid = get_parent() + +# make sure location is set before adding a building to the scene tree +# also make sure that the buildings are instantiated as children of the grid +func _ready() -> void: + var angle = location.x * TAU / grid.num_collumns; # currently assumes anchor is bottom left + var height = grid.ground_radius + location.y * grid.cell_height; + position = height * Vector2.from_angle(angle) + print(angle, " ", height, " ", position) + +func overlaps(other : Building): + # heights don't overlap + if location.y >= other.location.y + other.dimension.y: return false # other is below + if location.y + dimension.y <= other.location.y: return false # other is above + + # angles overlap. We can now assume heights overlap + var relative_other_loc = (other.location.x - location.x + grid.num_collumns) % grid.num_collumns + if dimension.x > relative_other_loc: return true + if relative_other_loc + other.dimension > grid.num_collumns: return true + + # If we get here, angles do not overlap + return false + diff --git a/building.gd.uid b/building.gd.uid new file mode 100644 index 0000000..9a1e17b --- /dev/null +++ b/building.gd.uid @@ -0,0 +1 @@ +uid://b2ji03ekijjnn diff --git a/building.gdshader b/building.gdshader new file mode 100644 index 0000000..ff2b604 --- /dev/null +++ b/building.gdshader @@ -0,0 +1,34 @@ +shader_type canvas_item; + +uniform ivec2 location; +uniform ivec2 dimension = ivec2(1,1); + +uniform float ground_height = 3000.; +uniform float cell_height = 300.; +uniform int num_cells = 60; + +varying vec2 world_position; + +void vertex() +{ + world_position = (MODEL_MATRIX * vec4(VERTEX, 0.0, 1.0)).xy; +} + +void fragment() { + float radius = sqrt(world_position.x * world_position.x + world_position.y * world_position.y); + float angle = atan(world_position.y, world_position.x); + + float sample_y = 1. - ((radius - ground_height) / cell_height - float( location.y)) / float(dimension.y); + float sample_x = mod(fract(angle / TAU + 1.) * float(num_cells) - float(location.x) + float(num_cells), float(num_cells)) / float(dimension.x); + + if(sample_y > 1. || sample_y < 0. || sample_x > 1. || sample_x < 0.) { + discard; + } + COLOR = texture(TEXTURE, vec2(sample_x, sample_y)); + +} + +//void light() { +// // Called for every pixel for every light affecting the CanvasItem. +// // Uncomment to replace the default light processing function with this one. +//} diff --git a/building.gdshader.uid b/building.gdshader.uid new file mode 100644 index 0000000..984dac8 --- /dev/null +++ b/building.gdshader.uid @@ -0,0 +1 @@ +uid://c7gb1nqwvkr37 diff --git a/building.tscn b/building.tscn new file mode 100644 index 0000000..16ffed3 --- /dev/null +++ b/building.tscn @@ -0,0 +1,22 @@ +[gd_scene load_steps=5 format=3 uid="uid://djawvtdwp423v"] + +[ext_resource type="Script" uid="uid://b2ji03ekijjnn" path="res://building.gd" id="1_5j34s"] +[ext_resource type="Texture2D" uid="uid://cy70quh6k3s1j" path="res://icon.svg" id="2_2yopf"] +[ext_resource type="Shader" uid="uid://c7gb1nqwvkr37" path="res://building.gdshader" id="2_f1gjg"] + +[sub_resource type="ShaderMaterial" id="ShaderMaterial_qnfc1"] +resource_local_to_scene = true +shader = ExtResource("2_f1gjg") +shader_parameter/location = Vector2i(45, 0) +shader_parameter/dimension = Vector2i(1, 1) +shader_parameter/ground_height = 3000.0 +shader_parameter/cell_height = 300.0 +shader_parameter/num_cells = 60 + +[node name="Building" type="Node2D"] +script = ExtResource("1_5j34s") + +[node name="Sprite2D" type="Sprite2D" parent="."] +material = SubResource("ShaderMaterial_qnfc1") +scale = Vector2(7, 7) +texture = ExtResource("2_2yopf") diff --git a/draw_circle.gd b/draw_circle.gd index 2d87a9c..d9ac2d5 100644 --- a/draw_circle.gd +++ b/draw_circle.gd @@ -1,4 +1,4 @@ -extends Sprite2D +extends Node2D @export var radius : float; func _draw(): diff --git a/earth.tscn b/earth.tscn index a2b03e5..8b3dd35 100644 --- a/earth.tscn +++ b/earth.tscn @@ -1,8 +1,8 @@ [gd_scene load_steps=5 format=3 uid="uid://33k5v6skcbsm"] -[ext_resource type="Texture2D" uid="uid://cy70quh6k3s1j" path="res://icon.svg" id="1_qbwya"] [ext_resource type="Script" uid="uid://b5fhsy1xlreco" path="res://draw_circle.gd" id="2_2bhor"] [ext_resource type="Script" uid="uid://m3vyyfk8gnma" path="res://grid.gd" id="3_2bhor"] +[ext_resource type="PackedScene" uid="uid://djawvtdwp423v" path="res://building.tscn" id="3_5i67w"] [sub_resource type="CircleShape2D" id="CircleShape2D_5i67w"] radius = 3000.0 @@ -14,8 +14,7 @@ radius = 3000.0 [node name="CollisionShape2D" type="CollisionShape2D" parent="Ground"] shape = SubResource("CircleShape2D_5i67w") -[node name="Sprite2D" type="Sprite2D" parent="Ground"] -texture = ExtResource("1_qbwya") +[node name="GroundVisual" type="Node2D" parent="Ground"] script = ExtResource("2_2bhor") radius = 3000.0 @@ -29,3 +28,9 @@ cell_height = 300.0 num_collumns = 60 debug = true metadata/_custom_type_script = "uid://m3vyyfk8gnma" + +[node name="Building" parent="." instance=ExtResource("3_5i67w")] +position = Vector2(-5212, -1497) + +[node name="Building2" parent="." instance=ExtResource("3_5i67w")] +position = Vector2(49, 25) diff --git a/grid.gd b/grid.gd index 0c7c74e..1f56b8a 100644 --- a/grid.gd +++ b/grid.gd @@ -5,6 +5,8 @@ class_name Grid extends Node2D @export var num_collumns : int @export var debug : bool +var buildings : Array[Building] = [] + func _draw() -> void: if !debug: return @@ -16,8 +18,20 @@ func _draw() -> void: var angle = i * TAU / num_collumns; draw_line(Vector2.ZERO, 10000 * Vector2.from_angle(angle), Color.SKY_BLUE); -#func cart_to_sphere(cart : Vector2): - #var x = cart.x; var y = cart.y; - #var radius = sqrt(x*x + y*y); - #var angle = tan(y/x) - ## TODO +func add_building_to_collumn(building : Building, collumn : int): + # find the height of the top building in the buildings list: + building.location = Vector2(collumn, 0) + var height = 0 + + # TODO: support other dimensions for buildings + + # add the new building one higher than the previous + height += 1 + building.location = Vector2i(collumn, height); + +# for testing +func _ready() -> void: + var packed : PackedScene = preload("res://building.tscn") + var test_building = packed.instantiate() + test_building.location = Vector2(45, 1) + add_child(test_building) From b7ae0e33acc1412837d5496b200bb3b644a1643f Mon Sep 17 00:00:00 2001 From: Florian Date: Tue, 16 Sep 2025 10:22:24 +0200 Subject: [PATCH 4/4] Made building warping possible with multiple buildings --- building.gdshader | 9 +++++++-- building.tscn | 7 ++++--- building_mesh.gd | 7 +++++++ building_mesh.gd.uid | 1 + earth.tscn | 9 +-------- grid.gd | 9 +++++++++ project.godot | 2 +- 7 files changed, 30 insertions(+), 14 deletions(-) create mode 100644 building_mesh.gd create mode 100644 building_mesh.gd.uid diff --git a/building.gdshader b/building.gdshader index ff2b604..2c950f1 100644 --- a/building.gdshader +++ b/building.gdshader @@ -1,7 +1,7 @@ shader_type canvas_item; -uniform ivec2 location; -uniform ivec2 dimension = ivec2(1,1); +varying flat ivec2 location; +varying flat ivec2 dimension; uniform float ground_height = 3000.; uniform float cell_height = 300.; @@ -12,6 +12,10 @@ varying vec2 world_position; void vertex() { world_position = (MODEL_MATRIX * vec4(VERTEX, 0.0, 1.0)).xy; + location = ivec2(256. * COLOR.xy); + dimension = ivec2(256. * COLOR.zw); + //location = ivec2(45, 1); + //dimension = ivec2(1, 1); } void fragment() { @@ -25,6 +29,7 @@ void fragment() { discard; } COLOR = texture(TEXTURE, vec2(sample_x, sample_y)); + //COLOR = vec4(ivec4(location, dimension)); } diff --git a/building.tscn b/building.tscn index 16ffed3..7ccd539 100644 --- a/building.tscn +++ b/building.tscn @@ -1,14 +1,13 @@ -[gd_scene load_steps=5 format=3 uid="uid://djawvtdwp423v"] +[gd_scene load_steps=6 format=3 uid="uid://djawvtdwp423v"] [ext_resource type="Script" uid="uid://b2ji03ekijjnn" path="res://building.gd" id="1_5j34s"] [ext_resource type="Texture2D" uid="uid://cy70quh6k3s1j" path="res://icon.svg" id="2_2yopf"] [ext_resource type="Shader" uid="uid://c7gb1nqwvkr37" path="res://building.gdshader" id="2_f1gjg"] +[ext_resource type="Script" uid="uid://dj7d4d2xs3nci" path="res://building_mesh.gd" id="4_qnfc1"] [sub_resource type="ShaderMaterial" id="ShaderMaterial_qnfc1"] resource_local_to_scene = true shader = ExtResource("2_f1gjg") -shader_parameter/location = Vector2i(45, 0) -shader_parameter/dimension = Vector2i(1, 1) shader_parameter/ground_height = 3000.0 shader_parameter/cell_height = 300.0 shader_parameter/num_cells = 60 @@ -17,6 +16,8 @@ shader_parameter/num_cells = 60 script = ExtResource("1_5j34s") [node name="Sprite2D" type="Sprite2D" parent="."] +self_modulate = Color(0.1764706, 0, 0.003921569, 0.003921569) material = SubResource("ShaderMaterial_qnfc1") scale = Vector2(7, 7) texture = ExtResource("2_2yopf") +script = ExtResource("4_qnfc1") diff --git a/building_mesh.gd b/building_mesh.gd new file mode 100644 index 0000000..7a381f4 --- /dev/null +++ b/building_mesh.gd @@ -0,0 +1,7 @@ +extends Sprite2D + +func _ready() -> void: + var location = Vector2i(get_parent().location) + var dimension = Vector2i(get_parent().dimension) + print(location, dimension) + self_modulate = Color8(location.x, location.y, dimension.x, dimension.y) diff --git a/building_mesh.gd.uid b/building_mesh.gd.uid new file mode 100644 index 0000000..fc7bbb1 --- /dev/null +++ b/building_mesh.gd.uid @@ -0,0 +1 @@ +uid://dj7d4d2xs3nci diff --git a/earth.tscn b/earth.tscn index 8b3dd35..8785027 100644 --- a/earth.tscn +++ b/earth.tscn @@ -1,8 +1,7 @@ -[gd_scene load_steps=5 format=3 uid="uid://33k5v6skcbsm"] +[gd_scene load_steps=4 format=3 uid="uid://33k5v6skcbsm"] [ext_resource type="Script" uid="uid://b5fhsy1xlreco" path="res://draw_circle.gd" id="2_2bhor"] [ext_resource type="Script" uid="uid://m3vyyfk8gnma" path="res://grid.gd" id="3_2bhor"] -[ext_resource type="PackedScene" uid="uid://djawvtdwp423v" path="res://building.tscn" id="3_5i67w"] [sub_resource type="CircleShape2D" id="CircleShape2D_5i67w"] radius = 3000.0 @@ -28,9 +27,3 @@ cell_height = 300.0 num_collumns = 60 debug = true metadata/_custom_type_script = "uid://m3vyyfk8gnma" - -[node name="Building" parent="." instance=ExtResource("3_5i67w")] -position = Vector2(-5212, -1497) - -[node name="Building2" parent="." instance=ExtResource("3_5i67w")] -position = Vector2(49, 25) diff --git a/grid.gd b/grid.gd index 1f56b8a..44510ef 100644 --- a/grid.gd +++ b/grid.gd @@ -32,6 +32,15 @@ func add_building_to_collumn(building : Building, collumn : int): # for testing func _ready() -> void: var packed : PackedScene = preload("res://building.tscn") + var test_building = packed.instantiate() + test_building.location = Vector2(45, 0) + add_child(test_building) + + test_building = packed.instantiate() + test_building.location = Vector2(44, 0) + add_child(test_building) + + test_building = packed.instantiate() test_building.location = Vector2(45, 1) add_child(test_building) diff --git a/project.godot b/project.godot index ea99ec8..4ff6475 100644 --- a/project.godot +++ b/project.godot @@ -12,7 +12,7 @@ config_version=5 config/name="The Dark Side of Earth" run/main_scene="res://earth.tscn" -config/features=PackedStringArray("4.4", "Forward Plus") +config/features=PackedStringArray("4.5", "Forward Plus") config/icon="res://icon.svg" [display]