class_name CockpitAnalogGauges extends Node3D const CockpitMaterialPalette = preload("res://game/presentation/cockpit/cockpit_material_palette.gd") const CockpitMeshFactory = preload("res://game/presentation/cockpit/cockpit_mesh_factory.gd") var _materials: CockpitMaterialPalette var _battery_needle: Node3D var _pressure_needle: Node3D func _init(materials: CockpitMaterialPalette) -> void: _materials = materials name = "AnalogGauges" _build_binnacle() _battery_needle = _add_gauge( "BatteryGauge", Vector3(-0.095, 0.315, 0.145), "%" ) _pressure_needle = _add_gauge( "PressureGauge", Vector3(0.095, 0.315, 0.145), "BAR" ) _add_binnacle_label("CHARGE BAT.", Vector3(-0.095, 0.235, 0.160)) _add_binnacle_label("PRESSION COQUE", Vector3(0.095, 0.235, 0.160)) func present(battery_ratio: float, pressure_ratio: float) -> void: _set_needle_ratio(_battery_needle, battery_ratio) _set_needle_ratio(_pressure_needle, pressure_ratio) func battery_needle_degrees() -> float: return 0.0 if _battery_needle == null else _battery_needle.rotation_degrees.z func _build_binnacle() -> void: CockpitMeshFactory.add_box( "BinnacleHousing", self, Vector3(0.0, 0.290, 0.095), Vector3(0.40, 0.180, 0.105), _materials.overhead_steel ) CockpitMeshFactory.add_box( "BinnacleFoot", self, Vector3(0.0, 0.205, 0.075), Vector3(0.47, 0.040, 0.14), _materials.dark_steel ) func _add_binnacle_label(caption: String, position: Vector3) -> void: var label := Label3D.new() label.name = "%sLabel" % caption.to_pascal_case().replace(" ", "") label.text = caption label.font_size = 12 label.pixel_size = 0.00055 label.modulate = Color(0.76, 0.72, 0.60) label.position = position add_child(label) func _add_gauge(gauge_name: String, position: Vector3, caption: String) -> Node3D: var gauge := Node3D.new() gauge.name = gauge_name gauge.position = position gauge.scale = Vector3(0.62, 0.62, 0.62) add_child(gauge) CockpitMeshFactory.add_box( "MountingPlate", gauge, Vector3(0.0, 0.0, -0.025), Vector3(0.225, 0.225, 0.055), _materials.dark_steel ) for screw_position: Vector2 in [ Vector2(-0.086, -0.086), Vector2(0.086, -0.086), Vector2(-0.086, 0.086), Vector2(0.086, 0.086), ]: CockpitMeshFactory.add_cylinder( "MountingScrew", gauge, Vector3(screw_position.x, screw_position.y, 0.008), 0.009, 0.012, _materials.brass, Vector3(90.0, 0.0, 0.0) ) var bezel := MeshInstance3D.new() var bezel_mesh := CylinderMesh.new() bezel_mesh.top_radius = 0.095 bezel_mesh.bottom_radius = 0.095 bezel_mesh.height = 0.035 bezel_mesh.radial_segments = 32 bezel.mesh = bezel_mesh bezel.material_override = _materials.brass bezel.rotation_degrees.x = 90.0 gauge.add_child(bezel) var face := MeshInstance3D.new() var face_mesh := CylinderMesh.new() face_mesh.top_radius = 0.078 face_mesh.bottom_radius = 0.078 face_mesh.height = 0.039 face_mesh.radial_segments = 32 face.mesh = face_mesh face.material_override = _materials.gauge_face face.rotation_degrees.x = 90.0 face.position.z = 0.003 gauge.add_child(face) _add_scale_label(gauge, "0", Vector3(-0.052, -0.018, 0.028)) _add_scale_label(gauge, "50", Vector3(0.0, 0.052, 0.028)) _add_scale_label(gauge, "100", Vector3(0.052, -0.018, 0.028)) var needle_root := Node3D.new() needle_root.name = "Needle" needle_root.position.z = 0.027 gauge.add_child(needle_root) CockpitMeshFactory.add_box( "NeedleBlade", needle_root, Vector3(0.0, 0.034, 0.0), Vector3(0.008, 0.068, 0.006), _materials.needle_paint ) CockpitMeshFactory.add_cylinder( "NeedleHub", needle_root, Vector3.ZERO, 0.018, 0.012, _materials.dark_steel, Vector3(90.0, 0.0, 0.0) ) var label := Label3D.new() label.name = "Caption" label.text = caption label.font_size = 12 label.pixel_size = 0.0007 label.modulate = Color(0.11, 0.12, 0.10) label.position = Vector3(0.0, -0.044, 0.032) gauge.add_child(label) var glass := MeshInstance3D.new() glass.name = "GaugeGlass" var glass_mesh := CylinderMesh.new() glass_mesh.top_radius = 0.081 glass_mesh.bottom_radius = 0.081 glass_mesh.height = 0.004 glass_mesh.radial_segments = 40 glass.mesh = glass_mesh glass.material_override = _materials.gauge_glass glass.rotation_degrees.x = 90.0 glass.position.z = 0.036 glass.cast_shadow = GeometryInstance3D.SHADOW_CASTING_SETTING_OFF gauge.add_child(glass) return needle_root func _add_scale_label(gauge: Node3D, text: String, position: Vector3) -> void: var label := Label3D.new() label.name = "Scale%s" % text label.text = text label.font_size = 9 label.pixel_size = 0.00048 label.modulate = Color(0.09, 0.085, 0.065) label.position = position gauge.add_child(label) func _set_needle_ratio(needle: Node3D, ratio: float) -> void: if needle != null: needle.rotation_degrees.z = lerpf(125.0, -125.0, clampf(ratio, 0.0, 1.0))