diff --git a/.gitignore b/.gitignore index 4709183..22a33c0 100644 --- a/.gitignore +++ b/.gitignore @@ -1,2 +1,3 @@ # Godot 4+ specific ignores .godot/ +recordings/ diff --git a/DebugDraw.gd b/DebugDraw.gd index b586cd3..ec49ec2 100644 --- a/DebugDraw.gd +++ b/DebugDraw.gd @@ -34,7 +34,7 @@ func _process(_delta): func _draw(): for vector in vectors: vector.draw(self, get_viewport().get_camera_3d()) - vectors.clear() + #vectors.clear() func draw_vector(pos: Vector3, dir: Vector3, color: Color): diff --git a/WheelSliders.gd b/WheelSliders.gd new file mode 100644 index 0000000..48e0aad --- /dev/null +++ b/WheelSliders.gd @@ -0,0 +1,11 @@ +extends VBoxContainer + +@export var wheel_slider: PackedScene +@export var wheels: Node + +# Called when the node enters the scene tree for the first time. +func _ready(): + for wheel in wheels.get_children(): + var slider = wheel_slider.instantiate() + slider.init(wheel) + add_child(slider) diff --git a/cube_sat.gd b/cube_sat.gd index 66e647b..2367d58 100644 --- a/cube_sat.gd +++ b/cube_sat.gd @@ -1,11 +1,8 @@ extends Node3D var net_momentum = Vector3(0, 0, 0) - -# Called when the node enters the scene tree for the first time. -func _ready(): - pass # Replace with function body. - +var body_velocity = Vector3.ZERO +const inertia: float = 6.0 func get_wheel_momentum(): @@ -13,11 +10,18 @@ func get_wheel_momentum(): for wheel in get_tree().get_nodes_in_group("wheel"): momentum += wheel.get_momentum() return momentum - + + +var count = 0 # Called every frame. 'delta' is the elapsed time since the previous frame. func _process(delta): var body_momentum = net_momentum - get_wheel_momentum() - if not body_momentum.is_zero_approx(): - rotate(body_momentum.normalized(), delta * body_momentum.length()) + body_velocity = body_momentum / inertia + if not body_velocity.is_zero_approx(): + rotate(body_velocity.normalized(), delta * body_velocity.length()) - DebugDraw.draw_vector(global_position, body_momentum * 0.5, Color.GREEN) + count += delta + if count > 0.1: + DebugDraw.draw_vector(global_position, body_velocity * 0.5, Color.GREEN) + count = 0 + #DebugDraw.draw_vector(global_position, get_wheel_momentum() * 0.5, Color.PINK) diff --git a/cube_sat.tscn b/cube_sat.tscn index 1b5769b..d4e5f13 100644 --- a/cube_sat.tscn +++ b/cube_sat.tscn @@ -12,36 +12,34 @@ script = ExtResource("1_xxq55") [node name="base" parent="." instance=ExtResource("1_jxnbk")] +transform = Transform3D(1, 0, 0, 0, 1, 0, 0, 0, 1, 0, -0.8, 0) [node name="wheel1" type="Node3D" parent="." groups=["wheel"]] -transform = Transform3D(1, 0, 0, 0, 0.848048, -0.529919, 0, 0.529919, 0.848048, -1.2615, 1.4606, 0.319901) +transform = Transform3D(1, 0, 0, 0, 0.848048, -0.529919, 0, 0.529919, 0.848048, -1.2615, 0.6606, 0.319901) rotation_edit_mode = 2 script = ExtResource("3_k8xaf") -rpm = -40.0 +velocity = 100.0 [node name="wheel1_model" parent="wheel1" instance=ExtResource("2_7bbpg")] transform = Transform3D(1, 0, 0, 0, 0.848048, 0.529919, 0, -0.529919, 0.848048, 1.2615, -1.40818, 0.502707) [node name="wheel2" type="Node3D" parent="." groups=["wheel"]] -transform = Transform3D(-4.37114e-08, 0.529919, 0.848048, 0, 0.848048, -0.529919, -1, -2.31635e-08, -3.70694e-08, 0.31072, 1.46108, 1.26162) +transform = Transform3D(-4.37114e-08, 0.529919, 0.848048, 0, 0.848048, -0.529919, -1, -2.31635e-08, -3.70694e-08, 0.31072, 0.66108, 1.26162) script = ExtResource("3_k8xaf") -rpm = 0.0 [node name="wheel2_model" parent="wheel2" instance=ExtResource("3_i4bun")] transform = Transform3D(-4.37114e-08, 0, -1, 0.529919, 0.848048, -2.31635e-08, 0.848048, -0.529919, -3.70694e-08, 1.26162, -1.40373, 0.51075) [node name="wheel3" type="Node3D" parent="." groups=["wheel"]] -transform = Transform3D(-1, 4.6327e-08, 7.41387e-08, 0, 0.848048, -0.529919, -8.74228e-08, -0.529919, -0.848048, 1.2626, 1.45715, -0.320415) +transform = Transform3D(-1, 4.6327e-08, 7.41387e-08, 0, 0.848048, -0.529919, -8.74228e-08, -0.529919, -0.848048, 1.2626, 0.65715, -0.320415) script = ExtResource("3_k8xaf") -rpm = 0.0 [node name="wheel3_model" parent="wheel3" instance=ExtResource("4_fogof")] transform = Transform3D(-1, 0, -8.74228e-08, 4.6327e-08, 0.848048, -0.529919, 7.41387e-08, -0.529919, -0.848048, 1.2626, -1.40553, 0.500446) [node name="wheel4" type="Node3D" parent="." groups=["wheel"]] -transform = Transform3D(-4.37114e-08, -0.529919, -0.848048, 0, 0.848048, -0.529919, 1, -2.31635e-08, -3.70694e-08, -0.324512, 1.4571, -1.25987) +transform = Transform3D(-4.37114e-08, -0.529919, -0.848048, 0, 0.848048, -0.529919, 1, -2.31635e-08, -3.70694e-08, -0.324512, 0.6571, -1.25987) script = ExtResource("3_k8xaf") -rpm = 0.0 [node name="wheel4_model" parent="wheel4" instance=ExtResource("5_s3a6f")] transform = Transform3D(-4.37114e-08, 0, 1, -0.529919, 0.848048, -2.31635e-08, -0.848048, -0.529919, -3.70694e-08, 1.25987, -1.40766, 0.496943) diff --git a/project.godot b/project.godot index e57e8d6..b1e5263 100644 --- a/project.godot +++ b/project.godot @@ -19,6 +19,11 @@ config/icon="res://icon.svg" DebugDraw="*res://DebugDraw.gd" +[editor] + +movie_writer/movie_file="/storage/Documents/Godot/ReactionWheels/out.avi" +movie_writer/fps=30 + [input] "Left Click"={ diff --git a/wheel.gd b/wheel.gd index 1a88b0c..29e0b53 100644 --- a/wheel.gd +++ b/wheel.gd @@ -1,23 +1,27 @@ extends Node3D -@export var rpm: float = 4.0 -const inertia: float = 1.0 +const inertia: float = 1.0 # kg * m^2 +const max_velocity: float = 40.0 # rad/s -# Called when the node enters the scene tree for the first time. -func _ready(): - pass # Replace with function body. +@export var velocity: float = 0.0 # rad / s +@export var acceleration: float = 0.0 # rad / s^2 # Called every frame. 'delta' is the elapsed time since the previous frame. func _process(delta): + velocity += acceleration; + if abs(velocity) > max_velocity: + velocity = clamp(velocity, -max_velocity, max_velocity) + acceleration = 0 animate(delta) func animate(delta): - rotate_object_local(Vector3(0, 0, 1), rads_per_sec() * delta) + rotate_object_local(Vector3(0, 0, 1), velocity * delta) func get_momentum() -> Vector3: - return rads_per_sec() * inertia * get_global_transform().basis.z; + return velocity * inertia * get_global_transform().basis.z; -func rads_per_sec() -> float: - return 0.1047198 * rpm + +func rpm() -> float: + return 9.5492968 * velocity diff --git a/wheel_slider.gd b/wheel_slider.gd new file mode 100644 index 0000000..beb0a53 --- /dev/null +++ b/wheel_slider.gd @@ -0,0 +1,34 @@ +extends HBoxContainer + +var wheel: Node + +func init(_wheel: Node): + wheel = _wheel + $ID.text = wheel.name + $Indicator.min_value = -wheel.max_velocity + $Indicator.max_value = wheel.max_velocity + + +func _process(delta): + if wheel.velocity != $Indicator.value: + display_velocity() + +func _gui_input(event): + wheel.velocity = $Indicator.value + +func display_velocity(): + $Indicator.value = wheel.velocity + $RPM.text = "RPM: %.1f" % (9.5492968 * wheel.velocity) + + +func _on_plus_button_down(): + wheel.acceleration = 0.1 # Replace with function body. + +func _on_minus_button_down(): + wheel.acceleration = -0.1 + +func _on_minus_button_up(): + wheel.acceleration = 0 # Replace with function body. + +func _on_plus_button_up(): + wheel.acceleration = 0 # Replace with function body. diff --git a/wheel_slider.tscn b/wheel_slider.tscn new file mode 100644 index 0000000..5852a8c --- /dev/null +++ b/wheel_slider.tscn @@ -0,0 +1,35 @@ +[gd_scene load_steps=2 format=3 uid="uid://c67ruvyiuhsk2"] + +[ext_resource type="Script" path="res://wheel_slider.gd" id="1_jd0x8"] + +[node name="WheelSlider" type="HBoxContainer"] +offset_right = 40.0 +offset_bottom = 40.0 +script = ExtResource("1_jd0x8") + +[node name="ID" type="Label" parent="."] +layout_mode = 2 + +[node name="Indicator" type="ProgressBar" parent="."] +custom_minimum_size = Vector2(100, 0) +layout_mode = 2 +size_flags_horizontal = 3 +size_flags_vertical = 1 +show_percentage = false + +[node name="Minus" type="Button" parent="."] +layout_mode = 2 +text = "<-" + +[node name="Plus" type="Button" parent="."] +layout_mode = 2 +text = "->" + +[node name="RPM" type="Label" parent="."] +layout_mode = 2 +text = "RPM: " + +[connection signal="button_down" from="Minus" to="." method="_on_minus_button_down"] +[connection signal="button_up" from="Minus" to="." method="_on_minus_button_up"] +[connection signal="button_down" from="Plus" to="." method="_on_plus_button_down"] +[connection signal="button_up" from="Plus" to="." method="_on_plus_button_up"] diff --git a/world.gd b/world.gd new file mode 100644 index 0000000..4057e77 --- /dev/null +++ b/world.gd @@ -0,0 +1,10 @@ +extends WorldEnvironment + + +func _input(event): + + # Camera Control + if event is InputEventMouseMotion and Input.is_action_pressed("Right Click"): + $CameraPivot.rotation.y -= event.relative.x*0.01 + $CameraPivot.rotation.x -= event.relative.y*0.01 + $CameraPivot.rotation.x = clamp($CameraPivot.rotation.x, -PI/2, PI/2) diff --git a/world.tscn b/world.tscn index b264684..111c2c1 100644 --- a/world.tscn +++ b/world.tscn @@ -1,8 +1,16 @@ -[gd_scene load_steps=7 format=3 uid="uid://dfyqnvtu6mank"] +[gd_scene load_steps=15 format=3 uid="uid://dfyqnvtu6mank"] [ext_resource type="Texture2D" uid="uid://bticauqhtnqoi" path="res://models/starmap_8k.jpg" id="1_wj1c1"] [ext_resource type="Script" path="res://world.gd" id="2_84njd"] -[ext_resource type="PackedScene" uid="uid://b7cygqcjty0y4" path="res://cube_sat.tscn" id="2_w2af2"] +[ext_resource type="Script" path="res://cube_sat.gd" id="3_u3n3o"] +[ext_resource type="PackedScene" uid="uid://dxic8waqchc3t" path="res://models/base.glb" id="4_ebyt2"] +[ext_resource type="Script" path="res://WheelSliders.gd" id="4_hgbox"] +[ext_resource type="Script" path="res://wheel.gd" id="5_dcxpo"] +[ext_resource type="PackedScene" uid="uid://dkc3ycisdan1s" path="res://models/wheel1.glb" id="6_fbovo"] +[ext_resource type="PackedScene" uid="uid://c67ruvyiuhsk2" path="res://wheel_slider.tscn" id="6_ixj40"] +[ext_resource type="PackedScene" uid="uid://wyem8uhw5svt" path="res://models/wheel2.glb" id="7_d23cs"] +[ext_resource type="PackedScene" uid="uid://bt08pw46fj85o" path="res://models/wheel3.glb" id="8_jnql3"] +[ext_resource type="PackedScene" uid="uid://4d82d6kch12" path="res://models/wheel4.glb" id="9_1451l"] [sub_resource type="PanoramaSkyMaterial" id="PanoramaSkyMaterial_tvcqa"] panorama = ExtResource("1_wj1c1") @@ -19,8 +27,43 @@ sky = SubResource("Sky_cwi6a") environment = SubResource("Environment_crkvp") script = ExtResource("2_84njd") -[node name="CubeSat" parent="." instance=ExtResource("2_w2af2")] +[node name="CubeSat" type="Node3D" parent="."] transform = Transform3D(1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, -0.0125639) +script = ExtResource("3_u3n3o") + +[node name="base" parent="CubeSat" instance=ExtResource("4_ebyt2")] +transform = Transform3D(1, 0, 0, 0, 1, 0, 0, 0, 1, 0, -0.8, 0) + +[node name="wheels" type="Node3D" parent="CubeSat"] + +[node name="wheel1" type="Node3D" parent="CubeSat/wheels" groups=["wheel"]] +transform = Transform3D(1, 0, 0, 0, 0.848048, -0.529919, 0, 0.529919, 0.848048, -1.2615, 0.6606, 0.319901) +rotation_edit_mode = 2 +script = ExtResource("5_dcxpo") + +[node name="wheel1_model" parent="CubeSat/wheels/wheel1" instance=ExtResource("6_fbovo")] +transform = Transform3D(1, 0, 0, 0, 0.848048, 0.529919, 0, -0.529919, 0.848048, 1.2615, -1.40818, 0.502707) + +[node name="wheel2" type="Node3D" parent="CubeSat/wheels" groups=["wheel"]] +transform = Transform3D(-4.37114e-08, 0.529919, 0.848048, 0, 0.848048, -0.529919, -1, -2.31635e-08, -3.70694e-08, 0.31072, 0.66108, 1.26162) +script = ExtResource("5_dcxpo") + +[node name="wheel2_model" parent="CubeSat/wheels/wheel2" instance=ExtResource("7_d23cs")] +transform = Transform3D(-4.37114e-08, 0, -1, 0.529919, 0.848048, -2.31635e-08, 0.848048, -0.529919, -3.70694e-08, 1.26162, -1.40373, 0.51075) + +[node name="wheel3" type="Node3D" parent="CubeSat/wheels" groups=["wheel"]] +transform = Transform3D(-1, 4.6327e-08, 7.41387e-08, 0, 0.848048, -0.529919, -8.74228e-08, -0.529919, -0.848048, 1.2626, 0.65715, -0.320415) +script = ExtResource("5_dcxpo") + +[node name="wheel3_model" parent="CubeSat/wheels/wheel3" instance=ExtResource("8_jnql3")] +transform = Transform3D(-1, 0, -8.74228e-08, 4.6327e-08, 0.848048, -0.529919, 7.41387e-08, -0.529919, -0.848048, 1.2626, -1.40553, 0.500446) + +[node name="wheel4" type="Node3D" parent="CubeSat/wheels" groups=["wheel"]] +transform = Transform3D(-4.37114e-08, -0.529919, -0.848048, 0, 0.848048, -0.529919, 1, -2.31635e-08, -3.70694e-08, -0.324512, 0.6571, -1.25987) +script = ExtResource("5_dcxpo") + +[node name="wheel4_model" parent="CubeSat/wheels/wheel4" instance=ExtResource("9_1451l")] +transform = Transform3D(-4.37114e-08, 0, 1, -0.529919, 0.848048, -2.31635e-08, -0.848048, -0.529919, -3.70694e-08, 1.25987, -1.40766, 0.496943) [node name="CameraPivot" type="Node3D" parent="."] transform = Transform3D(1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0) @@ -30,4 +73,16 @@ transform = Transform3D(1, 0, 0, 0, 1, 0, 0, 0, 1, 0.235759, -0.282455, 7.13333) current = true [node name="DirectionalLight3D" type="DirectionalLight3D" parent="CameraPivot/Camera"] -transform = Transform3D(1, 0, 0, 0, 0.997819, -0.0660129, 0, 0.0660129, 0.997819, 0, -0.0163116, 0.120244) +transform = Transform3D(1, 0, 0, 0, 0.997819, -0.0660129, 0, 0.0660129, 0.997819, 0, -0.0163116, 0.688179) + +[node name="Control" type="Panel" parent="."] +offset_right = 40.0 +offset_bottom = 40.0 + +[node name="WheelSliders" type="VBoxContainer" parent="Control" node_paths=PackedStringArray("wheels")] +layout_mode = 0 +offset_right = 40.0 +offset_bottom = 40.0 +script = ExtResource("4_hgbox") +wheel_slider = ExtResource("6_ixj40") +wheels = NodePath("../../CubeSat/wheels")