Added camera mode to c++

This commit is contained in:
2024-08-19 18:30:02 +03:00
parent 72beab0829
commit d1dc024353
7 changed files with 179 additions and 30 deletions

15
.vscode/launch.json vendored
View File

@@ -5,13 +5,22 @@
"version": "0.2.0", "version": "0.2.0",
"configurations": [ "configurations": [
{ {
"name": "Run Gym", "name": "Run Editor",
"type": "cppdbg", "type": "cppdbg",
"request": "launch", "request": "launch",
"program": "${workspaceRoot}/src/godot/bin/godot.x11.opt.tools.64", "program": "${workspaceRoot}/src/godot/bin/godot.x11.opt.tools.64",
"args": ["addons/astream/stream_view.tscn"], "args": ["main/editor.tscn"],
"cwd": "${workspaceRoot}/godot",
"setupCommands": [{"text": "source ${workspaceRoot}/debug.py"}]
},
{
"name": "Run Game",
"type": "cppdbg",
"request": "launch",
"program": "${workspaceRoot}/src/godot/bin/godot.x11.opt.tools.64",
"args": ["main/main.tscn"],
"cwd": "${workspaceRoot}/godot", "cwd": "${workspaceRoot}/godot",
"setupCommands": [{"text": "source ${workspaceRoot}/debug.py"}] "setupCommands": [{"text": "source ${workspaceRoot}/debug.py"}]
} }
] ]
} }

5
debug.py Normal file
View File

@@ -0,0 +1,5 @@
def release_mouse (event):
gdb.write("GDB/godot: Releasing mouse\n")
gdb.execute("call OS::get_singleton()->set_mouse_mode(0)")
gdb.events.stop.connect(release_mouse)
gdb.write("GDB/godot: installed release mouse for godot\n")

View File

@@ -1,6 +1,6 @@
extends Spatial extends Spatial
var camera_mode = -1 #var camera_mode = -1
onready var vmode = { onready var vmode = {
2: $"%v_buildings", 2: $"%v_buildings",
@@ -10,6 +10,10 @@ onready var vmode = {
7: $"%v_npc", 7: $"%v_npc",
} }
func change_building_type(index):
var item = $"%building_type".get_item_text(index)
$WorldEditor.editor_command("change_building_type", [selected_building, item])
func _ready(): func _ready():
for b in [ for b in [
$"%select_buildings", $"%select_buildings",
@@ -24,6 +28,7 @@ func _ready():
for k in vmode.keys(): for k in vmode.keys():
vmode[k].hide() vmode[k].hide()
$building_cursor.hide() $building_cursor.hide()
$"%building_type".connect("item_selected", self, "change_building_type")
func editor_event(evname: String, args: Array): func editor_event(evname: String, args: Array):
print(evname, args) print(evname, args)
@@ -40,6 +45,8 @@ func editor_event(evname: String, args: Array):
vmode[mode_next].show() vmode[mode_next].show()
if mode_next == 2: if mode_next == 2:
$WorldEditor.editor_command("get_building_types", []) $WorldEditor.editor_command("get_building_types", [])
elif mode_next == 6:
$WorldEditor.editor_command("get_lines_list", [])
elif evname == "result:get_closest_building": elif evname == "result:get_closest_building":
print(evname, args) print(evname, args)
select_building(args[0], args[3], args[4]) select_building(args[0], args[3], args[4])
@@ -72,6 +79,14 @@ func _process(delta):
setup_cam2() setup_cam2()
if Input.is_action_just_pressed("editor_cam3"): if Input.is_action_just_pressed("editor_cam3"):
setup_cam3() setup_cam3()
var mode = $"%buildings_edit_mode".selected
if mode == 2:
$building_rot_cursor.global_transform = selected_building_xform
if !$building_rot_cursor.visible:
$building_rot_cursor.show()
else:
if $building_rot_cursor.visible:
$building_rot_cursor.hide()
if dragging: if dragging:
if !Input.is_action_pressed("mouse1"): if !Input.is_action_pressed("mouse1"):
dragging = false dragging = false
@@ -86,7 +101,8 @@ func _process(delta):
var result = space_state.intersect_ray(start, end, [], 1 << 15, false, true) var result = space_state.intersect_ray(start, end, [], 1 << 15, false, true)
if result.has("collider"): if result.has("collider"):
var proj = result.position var proj = result.position
if $"%buildings_edit_mode".selected == 1: if mode == 1:
# move
print(proj) print(proj)
var newpos = proj var newpos = proj
newpos.x = stepify(newpos.x, 2.0) newpos.x = stepify(newpos.x, 2.0)
@@ -97,6 +113,25 @@ func _process(delta):
$WorldEditor.editor_command("update_building_transform", [selected_building, Transform(selected_building_xform.basis, newpos)]) $WorldEditor.editor_command("update_building_transform", [selected_building, Transform(selected_building_xform.basis, newpos)])
selected_building_xform = Transform(selected_building_xform.basis, newpos) selected_building_xform = Transform(selected_building_xform.basis, newpos)
$building_cursor.global_transform.origin = newpos $building_cursor.global_transform.origin = newpos
elif mode == 2:
# rotate
var m = proj
m.y = selected_building_xform.origin.y
var xform = selected_building_xform.looking_at(m, Vector3.UP)
$WorldEditor.editor_command("update_building_transform", [selected_building, xform])
$building_rot_cursor.global_transform = xform
selected_building_xform = xform
# var o = selected_building_xform.origin
# var m = proj
# o.y = 0
# m.y = 0
# var d = m - o
# var rot: float = -0.01 * d.x * delta
# var basis: Basis = selected_building_xform.basis
# var pos: Vector3 = selected_building_xform.origin
# var xform = Transform(basis.rotated(Vector3.UP, rot), pos)
# $WorldEditor.editor_command("update_building_transform", [selected_building, xform])
# selected_building_xform = xform
var motion = Vector2() var motion = Vector2()
var old_mouse_pos = Vector2(-1, -1) var old_mouse_pos = Vector2(-1, -1)
var rotation_y = 0 var rotation_y = 0
@@ -105,6 +140,7 @@ var drag_delay = 0.2
var drag_start = Vector3() var drag_start = Vector3()
func _unhandled_input(event): func _unhandled_input(event):
var editor_mode = $WorldEditor.get_current_mode() var editor_mode = $WorldEditor.get_current_mode()
var camera_mode = $WorldEditor.get_camera_mode()
if camera_mode in [2, 3]: if camera_mode in [2, 3]:
if event is InputEventMouseMotion: if event is InputEventMouseMotion:
motion = event.relative motion = event.relative
@@ -113,6 +149,7 @@ func _unhandled_input(event):
2: 2:
check_edit_building() check_edit_building()
func check_edit_building(): func check_edit_building():
var mode = $"%buildings_edit_mode".selected
if Input.is_action_just_pressed("mouse1"): if Input.is_action_just_pressed("mouse1"):
var position = get_viewport().get_mouse_position() var position = get_viewport().get_mouse_position()
# var proj = get_viewport().get_camera().project_position(position, $cam.global_transform.origin.y + position.y * 0.5) # var proj = get_viewport().get_camera().project_position(position, $cam.global_transform.origin.y + position.y * 0.5)
@@ -130,13 +167,20 @@ func check_edit_building():
var result = space_state.intersect_ray(start, end, [], 1 << 15, false, true) var result = space_state.intersect_ray(start, end, [], 1 << 15, false, true)
if result.has("collider"): if result.has("collider"):
var proj = result.position var proj = result.position
if $"%buildings_edit_mode".selected == 0: if mode == 0:
print("get closest building") print("get closest building")
$WorldEditor.editor_command("get_closest_building", [Transform(Basis(), proj)]) $WorldEditor.editor_command("get_closest_building", [Transform(Basis(), proj)])
elif mode == 2:
var m = proj
m.y = selected_building_xform.origin.y
var xform = selected_building_xform.looking_at(m, Vector3.UP)
$WorldEditor.editor_command("update_building_transform", [selected_building, xform])
$building_rot_cursor.global_transform = xform
selected_building_xform = xform
elif Input.is_action_pressed("mouse1"): elif Input.is_action_pressed("mouse1"):
# Moving buildings # Moving/rotating buildings
if $"%buildings_edit_mode".selected == 1: if mode in [1, 2]:
if drag_delay < 0.0 && !dragging: if ((mode == 1 && drag_delay < 0.0) || mode == 2) && !dragging:
dragging = true dragging = true
var position = get_viewport().get_mouse_position() var position = get_viewport().get_mouse_position()
var camera = get_viewport().get_camera() var camera = get_viewport().get_camera()
@@ -148,7 +192,14 @@ func check_edit_building():
if result.has("collider"): if result.has("collider"):
var proj = result.position var proj = result.position
drag_start = proj drag_start = proj
$WorldEditor.editor_command("buildings_checkpoint", []) if mode == 2:
var m = proj
m.y = selected_building_xform.origin.y
var xform = selected_building_xform.looking_at(m, Vector3.UP)
$WorldEditor.editor_command("update_building_transform", [selected_building, xform])
$building_rot_cursor.global_transform = xform
selected_building_xform = xform
$WorldEditor.editor_command("buildings_checkpoint", [])
else: else:
drag_delay -= get_process_delta_time() drag_delay -= get_process_delta_time()
else: else:
@@ -159,6 +210,7 @@ func check_edit_building():
drag_delay = 0.2 drag_delay = 0.2
func _physics_process(delta): func _physics_process(delta):
var editor_mode = $WorldEditor.get_current_mode() var editor_mode = $WorldEditor.get_current_mode()
var camera_mode = $WorldEditor.get_camera_mode()
if camera_mode == 1: if camera_mode == 1:
var mouse_pos = get_viewport().get_mouse_position() var mouse_pos = get_viewport().get_mouse_position()
if old_mouse_pos.x < 0: if old_mouse_pos.x < 0:
@@ -203,16 +255,17 @@ func _physics_process(delta):
$Area.global_transform.origin.z = $Camera.global_transform.origin.z $Area.global_transform.origin.z = $Camera.global_transform.origin.z
func setup_cam1(): func setup_cam1():
Input.mouse_mode = Input.MOUSE_MODE_CAPTURED Input.mouse_mode = Input.MOUSE_MODE_CAPTURED
camera_mode = 1 var camera_mode = $WorldEditor.get_camera_mode()
if camera_mode == -1: if camera_mode == -1:
$Camera.global_transform.origin.y = 80.0 $Camera.global_transform.origin.y = 80.0
$Camera.global_transform.basis = Basis().rotated(Vector3(1, 0, 0), -PI / 2.0) $Camera.global_transform.basis = Basis().rotated(Vector3(1, 0, 0), -PI / 2.0)
func setup_cam2(): func setup_cam2():
camera_mode = 2 var camera_mode = $WorldEditor.get_camera_mode()
Input.mouse_mode = Input.MOUSE_MODE_CAPTURED Input.mouse_mode = Input.MOUSE_MODE_CAPTURED
if camera_mode == -1: if camera_mode == -1:
$Camera.global_transform.origin.y = 80.0 $Camera.global_transform.origin.y = 80.0
$WorldEditor.set_camera_mode(2)
$Camera.global_transform.basis = Basis().rotated(Vector3(1, 0, 0), -PI / 4.0) $Camera.global_transform.basis = Basis().rotated(Vector3(1, 0, 0), -PI / 4.0)
func setup_cam3(): func setup_cam3():
camera_mode = 3
Input.mouse_mode = Input.MOUSE_MODE_VISIBLE Input.mouse_mode = Input.MOUSE_MODE_VISIBLE
$WorldEditor.set_camera_mode(3)

View File

@@ -1,4 +1,4 @@
[gd_scene load_steps=14 format=2] [gd_scene load_steps=15 format=2]
[ext_resource path="res://main/editor.gd" type="Script" id=1] [ext_resource path="res://main/editor.gd" type="Script" id=1]
[ext_resource path="res://terrain/terrain_draw.png" type="Image" id=2] [ext_resource path="res://terrain/terrain_draw.png" type="Image" id=2]
@@ -41,6 +41,9 @@ emission_on_uv2 = false
[sub_resource type="BoxShape" id=12] [sub_resource type="BoxShape" id=12]
extents = Vector3( 50, 1, 50 ) extents = Vector3( 50, 1, 50 )
[sub_resource type="CubeMesh" id=13]
size = Vector3( 4, 4, 120 )
[node name="editor" type="Spatial"] [node name="editor" type="Spatial"]
script = ExtResource( 1 ) script = ExtResource( 1 )
@@ -110,7 +113,7 @@ text = "NPC Mode"
unique_name_in_owner = true unique_name_in_owner = true
margin_top = 154.0 margin_top = 154.0
margin_right = 160.0 margin_right = 160.0
margin_bottom = 248.0 margin_bottom = 274.0
[node name="HSeparator" type="HSeparator" parent="VBoxContainer/v_buildings"] [node name="HSeparator" type="HSeparator" parent="VBoxContainer/v_buildings"]
margin_right = 160.0 margin_right = 160.0
@@ -131,25 +134,36 @@ text = "Select"
items = [ "Select", null, false, 0, null, "Move", null, false, 1, null, "Rotate", null, false, 2, null ] items = [ "Select", null, false, 0, null, "Move", null, false, 1, null, "Rotate", null, false, 2, null ]
selected = 0 selected = 0
[node name="building_type" type="OptionButton" parent="VBoxContainer/v_buildings"] [node name="Label2" type="Label" parent="VBoxContainer/v_buildings"]
unique_name_in_owner = true
margin_top = 50.0 margin_top = 50.0
margin_right = 160.0 margin_right = 160.0
margin_bottom = 70.0 margin_bottom = 64.0
text = "Building type"
[node name="building_type" type="OptionButton" parent="VBoxContainer/v_buildings"]
unique_name_in_owner = true
margin_top = 68.0
margin_right = 160.0
margin_bottom = 88.0
text = "Building Type" text = "Building Type"
[node name="HSeparator2" type="HSeparator" parent="VBoxContainer/v_buildings"]
margin_top = 92.0
margin_right = 160.0
margin_bottom = 96.0
[node name="buildings_save" type="Button" parent="VBoxContainer/v_buildings"] [node name="buildings_save" type="Button" parent="VBoxContainer/v_buildings"]
unique_name_in_owner = true unique_name_in_owner = true
margin_top = 74.0 margin_top = 100.0
margin_right = 160.0 margin_right = 160.0
margin_bottom = 94.0 margin_bottom = 120.0
text = "Save Buildings" text = "Save Buildings"
[node name="v_navigation" type="VBoxContainer" parent="VBoxContainer"] [node name="v_navigation" type="VBoxContainer" parent="VBoxContainer"]
unique_name_in_owner = true unique_name_in_owner = true
margin_top = 252.0 margin_top = 278.0
margin_right = 160.0 margin_right = 160.0
margin_bottom = 274.0 margin_bottom = 300.0
[node name="HSeparator" type="HSeparator" parent="VBoxContainer/v_navigation"] [node name="HSeparator" type="HSeparator" parent="VBoxContainer/v_navigation"]
margin_right = 160.0 margin_right = 160.0
@@ -163,9 +177,9 @@ text = "Navigation mode"
[node name="v_poi" type="VBoxContainer" parent="VBoxContainer"] [node name="v_poi" type="VBoxContainer" parent="VBoxContainer"]
unique_name_in_owner = true unique_name_in_owner = true
margin_top = 278.0 margin_top = 304.0
margin_right = 160.0 margin_right = 160.0
margin_bottom = 300.0 margin_bottom = 326.0
[node name="HSeparator" type="HSeparator" parent="VBoxContainer/v_poi"] [node name="HSeparator" type="HSeparator" parent="VBoxContainer/v_poi"]
margin_right = 160.0 margin_right = 160.0
@@ -179,9 +193,9 @@ text = "POI mode"
[node name="v_road_lines" type="VBoxContainer" parent="VBoxContainer"] [node name="v_road_lines" type="VBoxContainer" parent="VBoxContainer"]
unique_name_in_owner = true unique_name_in_owner = true
margin_top = 304.0 margin_top = 330.0
margin_right = 160.0 margin_right = 160.0
margin_bottom = 326.0 margin_bottom = 356.0
[node name="HSeparator" type="HSeparator" parent="VBoxContainer/v_road_lines"] [node name="HSeparator" type="HSeparator" parent="VBoxContainer/v_road_lines"]
margin_right = 160.0 margin_right = 160.0
@@ -193,11 +207,17 @@ margin_right = 160.0
margin_bottom = 22.0 margin_bottom = 22.0
text = "Road Lines mode" text = "Road Lines mode"
[node name="lines_list" type="ItemList" parent="VBoxContainer/v_road_lines"]
unique_name_in_owner = true
margin_top = 26.0
margin_right = 160.0
margin_bottom = 26.0
[node name="v_npc" type="VBoxContainer" parent="VBoxContainer"] [node name="v_npc" type="VBoxContainer" parent="VBoxContainer"]
unique_name_in_owner = true unique_name_in_owner = true
margin_top = 330.0 margin_top = 360.0
margin_right = 160.0 margin_right = 160.0
margin_bottom = 352.0 margin_bottom = 382.0
[node name="HSeparator" type="HSeparator" parent="VBoxContainer/v_npc"] [node name="HSeparator" type="HSeparator" parent="VBoxContainer/v_npc"]
margin_right = 160.0 margin_right = 160.0
@@ -249,3 +269,20 @@ monitoring = false
[node name="CollisionShape" type="CollisionShape" parent="building_cursor/Area"] [node name="CollisionShape" type="CollisionShape" parent="building_cursor/Area"]
transform = Transform( 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, -2, 0 ) transform = Transform( 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, -2, 0 )
shape = SubResource( 12 ) shape = SubResource( 12 )
[node name="building_rot_cursor" type="Spatial" parent="."]
[node name="building_rot_cursor" type="MeshInstance" parent="building_rot_cursor"]
transform = Transform( 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, -60 )
mesh = SubResource( 13 )
skeleton = NodePath("../..")
material/0 = SubResource( 11 )
[node name="Area" type="Area" parent="building_rot_cursor/building_rot_cursor"]
collision_layer = 32768
collision_mask = 32768
monitoring = false
[node name="CollisionShape" type="CollisionShape" parent="building_rot_cursor/building_rot_cursor/Area"]
transform = Transform( 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, -2, 0 )
shape = SubResource( 12 )

View File

@@ -436,8 +436,11 @@ void StreamWorld::run_command(const String &command, const Array &args)
return; return;
String key = buildings[id].key; String key = buildings[id].key;
buildings[id].xform == args[1]; buildings[id].xform == args[1];
Spatial *bnode = Object::cast_to<Spatial>(item_nodes[id]); if (item_nodes.has(id)) {
bnode->set_global_transform(args[1]); Spatial *bnode =
Object::cast_to<Spatial>(item_nodes[id]);
bnode->set_global_transform(args[1]);
}
VariantWriter::write_to_string(buildings[id].xform, key); VariantWriter::write_to_string(buildings[id].xform, key);
buildings[id].key = key; buildings[id].key = key;
} else if (command == "buildings_checkpoint") { } else if (command == "buildings_checkpoint") {
@@ -454,6 +457,26 @@ void StreamWorld::run_command(const String &command, const Array &args)
Array ret_data; Array ret_data;
ret_data.push_back(buildings_data); ret_data.push_back(buildings_data);
emit_signal("command_result", command, ret_data); emit_signal("command_result", command, ret_data);
} else if (command == "change_building_type") {
if (args.size() == 0) {
print_error("bad command: not enough args: " + command);
return;
}
int id = args[0];
String new_type = args[1];
Dictionary buildings_data =
config.get_value("buildings", "building_data");
if (!building_data.has(new_type)) {
print_error("unknown building type: " + new_type);
return;
}
String old_type = buildings[id].id;
unload_building(id);
buildings[id].id = new_type;
load_building(id);
update_items();
print_line("changed building: " + itos(id) +
" from: " + old_type + " to: " + new_type);
} else } else
print_error("No command " + command); print_error("No command " + command);
} }

View File

@@ -11,6 +11,7 @@ WorldEditor::WorldEditor()
, stream_world(nullptr) , stream_world(nullptr)
, editor_menu(nullptr) , editor_menu(nullptr)
, current_mode(-1) , current_mode(-1)
, current_camera_mode(-1)
{ {
} }
@@ -18,6 +19,16 @@ WorldEditor::~WorldEditor()
{ {
} }
void WorldEditor::set_camera_mode(int mode)
{
current_camera_mode = mode;
}
int WorldEditor::get_camera_mode() const
{
return current_camera_mode;
}
void WorldEditor::disable_all() void WorldEditor::disable_all()
{ {
} }
@@ -136,6 +147,10 @@ void WorldEditor::editor_command(const String &command, const Array &args)
if (stream_world) { if (stream_world) {
stream_world->run_command(command, args); stream_world->run_command(command, args);
} }
} else if (command == "change_building_type") {
if (stream_world) {
stream_world->run_command(command, args);
}
} }
} }
@@ -198,6 +213,10 @@ void WorldEditor::_bind_methods()
&WorldEditor::world_exited); &WorldEditor::world_exited);
ClassDB::bind_method(D_METHOD("world_command_result", "what", "data"), ClassDB::bind_method(D_METHOD("world_command_result", "what", "data"),
&WorldEditor::world_command_result); &WorldEditor::world_command_result);
ClassDB::bind_method(D_METHOD("set_camera_mode", "mode"),
&WorldEditor::set_camera_mode);
ClassDB::bind_method(D_METHOD("get_camera_mode"),
&WorldEditor::get_camera_mode);
ADD_SIGNAL(MethodInfo("editor_event", ADD_SIGNAL(MethodInfo("editor_event",
PropertyInfo(Variant::STRING, "event_name"), PropertyInfo(Variant::STRING, "event_name"),
PropertyInfo(Variant::ARRAY, "args"))); PropertyInfo(Variant::ARRAY, "args")));

View File

@@ -7,6 +7,8 @@ class WorldEditor : public Spatial {
protected: protected:
StreamWorld *stream_world; StreamWorld *stream_world;
Control *editor_menu; Control *editor_menu;
void set_camera_mode(int mode);
int get_camera_mode() const;
void disable_all(); void disable_all();
void mode_buildings(); void mode_buildings();
void mode_navigation(); void mode_navigation();
@@ -24,6 +26,7 @@ protected:
private: private:
void world_exited(); void world_exited();
int current_mode; int current_mode;
int current_camera_mode;
public: public:
WorldEditor(); WorldEditor();