mirror of
https://github.com/godotengine/godot-demo-projects.git
synced 2026-01-06 14:10:55 +03:00
Add Physics Tests project
This commit is contained in:
35
3d/physics_tests/utils/camera_orbit.gd
Normal file
35
3d/physics_tests/utils/camera_orbit.gd
Normal file
@@ -0,0 +1,35 @@
|
||||
extends Camera
|
||||
|
||||
|
||||
const ROTATION_COEFF = 0.02
|
||||
|
||||
var _rotation_enabled = false
|
||||
var _rotation_pivot
|
||||
|
||||
|
||||
func _ready():
|
||||
call_deferred("_initialize_pivot")
|
||||
|
||||
|
||||
func _unhandled_input(event):
|
||||
var mouse_button_event = event as InputEventMouseButton
|
||||
if mouse_button_event:
|
||||
if mouse_button_event.button_index == BUTTON_LEFT:
|
||||
_rotation_enabled = mouse_button_event.pressed
|
||||
return
|
||||
|
||||
if not _rotation_enabled:
|
||||
return
|
||||
|
||||
var mouse_motion_event = event as InputEventMouseMotion
|
||||
if mouse_motion_event:
|
||||
var rotation_delta = mouse_motion_event.relative.x
|
||||
_rotation_pivot.rotate(Vector3.UP, -rotation_delta * ROTATION_COEFF)
|
||||
|
||||
|
||||
func _initialize_pivot():
|
||||
_rotation_pivot = Spatial.new()
|
||||
var camera_parent = get_parent()
|
||||
camera_parent.add_child(_rotation_pivot)
|
||||
camera_parent.remove_child(self)
|
||||
_rotation_pivot.add_child(self)
|
||||
37
3d/physics_tests/utils/container_log.gd
Normal file
37
3d/physics_tests/utils/container_log.gd
Normal file
@@ -0,0 +1,37 @@
|
||||
extends Control
|
||||
|
||||
|
||||
const MAX_ENTRIES = 100
|
||||
|
||||
var _entry_template
|
||||
|
||||
|
||||
func _enter_tree():
|
||||
Log.connect("entry_logged", self, "_on_log_entry")
|
||||
|
||||
_entry_template = get_child(0) as Label
|
||||
remove_child(_entry_template)
|
||||
|
||||
|
||||
func clear():
|
||||
while get_child_count():
|
||||
var entry = get_child(get_child_count() - 1)
|
||||
remove_child(entry)
|
||||
entry.queue_free()
|
||||
|
||||
|
||||
func _on_log_entry(message, type):
|
||||
var new_entry = _entry_template.duplicate() as Label
|
||||
|
||||
new_entry.set_text(message)
|
||||
if type == Log.LogType.ERROR:
|
||||
new_entry.modulate = Color.red
|
||||
else:
|
||||
new_entry.modulate = Color.white
|
||||
|
||||
if get_child_count() >= MAX_ENTRIES:
|
||||
var first_entry = get_child(0) as Label
|
||||
remove_child(first_entry)
|
||||
first_entry.queue_free()
|
||||
|
||||
add_child(new_entry)
|
||||
30
3d/physics_tests/utils/control3d.gd
Normal file
30
3d/physics_tests/utils/control3d.gd
Normal file
@@ -0,0 +1,30 @@
|
||||
extends Control
|
||||
|
||||
|
||||
export(Vector3) var world_offset
|
||||
|
||||
var _pos_offset
|
||||
var _attachment
|
||||
|
||||
|
||||
func _ready():
|
||||
_pos_offset = rect_position
|
||||
_attachment = get_parent() as Spatial
|
||||
|
||||
|
||||
func _process(_delta):
|
||||
if _attachment == null:
|
||||
return
|
||||
|
||||
var viewport = get_viewport()
|
||||
if viewport == null:
|
||||
return
|
||||
|
||||
var camera = viewport.get_camera()
|
||||
if camera == null:
|
||||
return
|
||||
|
||||
var world_pos = world_offset + _attachment.global_transform.origin
|
||||
var screen_pos = camera.unproject_position(world_pos)
|
||||
|
||||
rect_position = _pos_offset + screen_pos - 0.5 * rect_size
|
||||
8
3d/physics_tests/utils/exception_cylinder.gd
Normal file
8
3d/physics_tests/utils/exception_cylinder.gd
Normal file
@@ -0,0 +1,8 @@
|
||||
extends Node
|
||||
|
||||
|
||||
func _enter_tree():
|
||||
if System.get_physics_engine() == System.PhysicsEngine.GODOT_PHYSICS:
|
||||
Log.print_error("Cylinder shapes not supported, removing '%s'." % name)
|
||||
get_parent().remove_child(self)
|
||||
queue_free()
|
||||
14
3d/physics_tests/utils/label_engine.gd
Normal file
14
3d/physics_tests/utils/label_engine.gd
Normal file
@@ -0,0 +1,14 @@
|
||||
extends Label
|
||||
|
||||
|
||||
func _process(_delta):
|
||||
var engine_name = ""
|
||||
match System.get_physics_engine():
|
||||
System.PhysicsEngine.BULLET:
|
||||
engine_name = "Bullet"
|
||||
System.PhysicsEngine.GODOT_PHYSICS:
|
||||
engine_name = "Godot Physics"
|
||||
System.PhysicsEngine.OTHER:
|
||||
var engine_setting = ProjectSettings.get_setting("physics/3d/physics_engine")
|
||||
engine_name = "Other (%s)" % engine_setting
|
||||
set_text("Physics engine: %s" % engine_name)
|
||||
5
3d/physics_tests/utils/label_fps.gd
Normal file
5
3d/physics_tests/utils/label_fps.gd
Normal file
@@ -0,0 +1,5 @@
|
||||
extends Label
|
||||
|
||||
|
||||
func _process(_delta):
|
||||
set_text("FPS: %d" % Engine.get_frames_per_second())
|
||||
13
3d/physics_tests/utils/label_test.gd
Normal file
13
3d/physics_tests/utils/label_test.gd
Normal file
@@ -0,0 +1,13 @@
|
||||
extends Label
|
||||
|
||||
|
||||
var test_name setget _set_test_name
|
||||
|
||||
|
||||
func _ready():
|
||||
set_text("Select a test from the menu to start it")
|
||||
|
||||
|
||||
func _set_test_name(value):
|
||||
test_name = value
|
||||
set_text("Test: %s" % test_name)
|
||||
5
3d/physics_tests/utils/label_version.gd
Normal file
5
3d/physics_tests/utils/label_version.gd
Normal file
@@ -0,0 +1,5 @@
|
||||
extends Label
|
||||
|
||||
|
||||
func _process(_delta):
|
||||
set_text("Godot Version: %s" % Engine.get_version_info().string)
|
||||
47
3d/physics_tests/utils/option_menu.gd
Normal file
47
3d/physics_tests/utils/option_menu.gd
Normal file
@@ -0,0 +1,47 @@
|
||||
class_name OptionMenu
|
||||
extends MenuButton
|
||||
|
||||
|
||||
signal option_selected(item_path)
|
||||
|
||||
|
||||
func add_menu_item(item_path):
|
||||
var path_elements = item_path.split("/", false)
|
||||
var path_element_count = path_elements.size()
|
||||
assert(path_element_count > 0)
|
||||
|
||||
var path = ""
|
||||
var popup = get_popup()
|
||||
for element_index in path_element_count - 1:
|
||||
var popup_label = path_elements[element_index]
|
||||
path += popup_label + "/"
|
||||
popup = _add_popup(popup, path, popup_label)
|
||||
|
||||
_add_item(popup, path_elements[path_element_count - 1])
|
||||
|
||||
|
||||
func _add_item(parent_popup, label):
|
||||
parent_popup.add_item(label)
|
||||
|
||||
|
||||
func _add_popup(parent_popup, path, label):
|
||||
if parent_popup.has_node(label):
|
||||
var popup_node = parent_popup.get_node(label)
|
||||
var popup_menu = popup_node as PopupMenu
|
||||
assert(popup_menu)
|
||||
return popup_menu
|
||||
|
||||
var popup_menu = PopupMenu.new()
|
||||
popup_menu.name = label
|
||||
|
||||
parent_popup.add_child(popup_menu)
|
||||
parent_popup.add_submenu_item(label, label)
|
||||
|
||||
popup_menu.connect("index_pressed", self, "_on_item_pressed", [popup_menu, path])
|
||||
|
||||
return popup_menu
|
||||
|
||||
|
||||
func _on_item_pressed(item_index, popup_menu, path):
|
||||
var item_path = path + popup_menu.get_item_text(item_index)
|
||||
emit_signal("option_selected", item_path)
|
||||
14
3d/physics_tests/utils/scroll_log.gd
Normal file
14
3d/physics_tests/utils/scroll_log.gd
Normal file
@@ -0,0 +1,14 @@
|
||||
extends ScrollContainer
|
||||
|
||||
|
||||
export(bool) var auto_scroll = false setget set_auto_scroll
|
||||
|
||||
|
||||
func _process(_delta):
|
||||
if auto_scroll:
|
||||
var scrollbar = get_v_scrollbar()
|
||||
scrollbar.value = scrollbar.max_value
|
||||
|
||||
|
||||
func set_auto_scroll(value):
|
||||
auto_scroll = value
|
||||
53
3d/physics_tests/utils/system.gd
Normal file
53
3d/physics_tests/utils/system.gd
Normal file
@@ -0,0 +1,53 @@
|
||||
extends Node
|
||||
|
||||
|
||||
enum PhysicsEngine {
|
||||
BULLET,
|
||||
GODOT_PHYSICS,
|
||||
OTHER,
|
||||
}
|
||||
|
||||
var _engine = PhysicsEngine.OTHER
|
||||
|
||||
|
||||
func _enter_tree():
|
||||
get_tree().debug_collisions_hint = true
|
||||
|
||||
var engine_string = ProjectSettings.get_setting("physics/3d/physics_engine")
|
||||
match engine_string:
|
||||
"DEFAULT":
|
||||
_engine = PhysicsEngine.BULLET
|
||||
"Bullet":
|
||||
_engine = PhysicsEngine.BULLET
|
||||
"GodotPhysics":
|
||||
_engine = PhysicsEngine.GODOT_PHYSICS
|
||||
_:
|
||||
_engine = PhysicsEngine.OTHER
|
||||
|
||||
|
||||
func _process(_delta):
|
||||
if Input.is_action_just_pressed("toggle_full_screen"):
|
||||
OS.window_fullscreen = not OS.window_fullscreen
|
||||
|
||||
if Input.is_action_just_pressed("toggle_debug_collision"):
|
||||
var debug_collision_enabled = not _is_debug_collision_enabled()
|
||||
_set_debug_collision_enabled(debug_collision_enabled)
|
||||
if debug_collision_enabled:
|
||||
Log.print_log("Debug Collision ON")
|
||||
else:
|
||||
Log.print_log("Debug Collision OFF")
|
||||
|
||||
if Input.is_action_just_pressed("exit"):
|
||||
get_tree().quit()
|
||||
|
||||
|
||||
func get_physics_engine():
|
||||
return _engine
|
||||
|
||||
|
||||
func _set_debug_collision_enabled(enabled):
|
||||
get_tree().debug_collisions_hint = enabled
|
||||
|
||||
|
||||
func _is_debug_collision_enabled():
|
||||
return get_tree().debug_collisions_hint
|
||||
20
3d/physics_tests/utils/system_log.gd
Normal file
20
3d/physics_tests/utils/system_log.gd
Normal file
@@ -0,0 +1,20 @@
|
||||
extends Node
|
||||
|
||||
|
||||
enum LogType {
|
||||
LOG,
|
||||
ERROR,
|
||||
}
|
||||
|
||||
signal entry_logged(message, type)
|
||||
|
||||
|
||||
func print_log(message):
|
||||
print(message)
|
||||
emit_signal("entry_logged", message, LogType.LOG)
|
||||
|
||||
|
||||
func print_error(message):
|
||||
push_error(message)
|
||||
printerr(message)
|
||||
emit_signal("entry_logged", message, LogType.ERROR)
|
||||
Reference in New Issue
Block a user