xiandie/manager/config_manager/global_config_manager.gd

198 lines
5.4 KiB
GDScript
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

@tool
extends Node
# Constants
const TIMER_INTERVAL := 5.0
const TIMER_LOG_INTERVAL := 6 # 30秒打印一次 (6 * 5秒)
const TIMER_EDITOR_LOG_INTERVAL := 120 # 编辑器中600秒打印一次
# Static config
var config: GlobalConfig:
set = _set_config
# Timer for tracking game time
var timer := Timer.new()
var _timer_tick_counter := 0
func _ready() -> void:
_setup_timer()
func _setup_timer() -> void:
timer.wait_time = TIMER_INTERVAL
timer.one_shot = false
timer.timeout.connect(_on_timer_timeout)
add_child(timer)
timer.start()
func _set_config(val: GlobalConfig) -> void:
config = val
if not config or Engine.is_editor_hint():
return
_apply_compatibility()
_apply_debug_mode()
_apply_window_settings()
_apply_audio_settings()
_apply_locale_settings()
func _apply_compatibility() -> void:
# ("unspecified", "checking", "opengl3", "non-opengl3")
if config.compatibility_mode == 0:
config.compatibility_mode = 1
ResourceSaver.save(config)
elif config.compatibility_mode == 1:
config.compatibility_mode = 2
print("[Compatibility] Compatibility mode set to 'opengl3' for checking launch.")
if config.compatibility_mode == 2:
# 检测是否已经启用 opengl3
if RenderingServer.get_current_rendering_driver_name().begins_with("opengl3"):
print("[Compatibility] Compatibility mode is already 'opengl3'. No action needed.")
return
print("[Compatibility] Switching to 'opengl3' rendering driver.")
# 重启游戏以应用新渲染器
var args = ["--rendering-driver", "opengl3"]
var executable_path = OS.get_executable_path()
OS.create_process(executable_path, args)
if OS.get_name() == "Windows":
# 使用线程来延迟退出
var thread = Thread.new()
thread.start(_delayed_quit)
else:
get_tree().quit()
elif config.compatibility_mode == 3:
print("[Compatibility] Running on 'non-opengl3' rendering driver.")
func _delayed_quit() -> void:
OS.delay_msec(100) # 等待 100 毫秒
OS.kill(OS.get_process_id())
get_tree().quit()
func _apply_debug_mode() -> void:
if config.debug_mode:
GlobalConfig.DEBUG = true
print_rich("[color=orange]Debug mode enabled[/color]")
func _apply_window_settings() -> void:
var window = Engine.get_main_loop().root.get_window()
if config.window_fullscreen:
window.mode = Window.MODE_EXCLUSIVE_FULLSCREEN
else:
window.mode = Window.MODE_WINDOWED
window.always_on_top = config.window_top
func _apply_audio_settings() -> void:
AudioServer.set_bus_volume_db(
AudioServer.get_bus_index(GlobalConfig.BUS_MASTER), config.db_master
)
AudioServer.set_bus_volume_db(
AudioServer.get_bus_index(GlobalConfig.BUS_GAME_SFX), config.db_game_sfx
)
AudioServer.set_bus_volume_db(
AudioServer.get_bus_index(GlobalConfig.BUS_DIALOG), config.db_dialog
)
prints(
"config load volume_db settings (master, sfx, dialog): ",
config.db_master,
config.db_game_sfx,
config.db_dialog
)
func _apply_locale_settings() -> void:
var locale = config.get_locale()
print("set language to: ", locale)
TranslationServer.set_locale(locale)
# -1 null; 0 zh; 1 en
func update_locale(lang_id: int, caption_id: int) -> void:
config.language = wrapi(lang_id, 0, GlobalConfig.LANGUAGE_OPTIONS.size())
var caption_options = GlobalConfig.CAPTION_OPTIONS_DICT.get(config.language, [""])
config.caption = wrapi(caption_id, 0, caption_options.size())
_apply_locale_settings()
func get_locale_language_name() -> String:
if config:
return config.get_locale_language_name()
return ""
func get_locale_caption_name() -> String:
if config:
return config.get_locale_caption_name()
return ""
func _on_timer_timeout() -> void:
var archive := ArchiveManager.archive
if not archive or not config:
return
# Update game time
archive.game_seconds += int(TIMER_INTERVAL)
config.game_total_seconds += int(TIMER_INTERVAL)
_timer_tick_counter += 1
# Check if should log
if _should_log_game_info():
print_global_info()
func _should_log_game_info() -> bool:
# 30s 打印一次,无需首次打印
if _timer_tick_counter % TIMER_LOG_INTERVAL != 0:
return false
# editor 中 600s 打印一次
if Engine.is_editor_hint() and _timer_tick_counter % TIMER_EDITOR_LOG_INTERVAL != 0:
return false
return true
func print_global_info() -> void:
var archive := ArchiveManager.archive
if not archive or not config:
return
var game_time_str = _format_game_time(archive.game_seconds)
var tick_time_str = _format_tick_time()
var round_info = _get_round_info()
var scene_info = archive.current_scene
prints(
"[timemark]",
Time.get_datetime_string_from_system(),
round_info,
scene_info,
game_time_str + " " + tick_time_str
)
func _format_game_time(total_seconds: int) -> String:
@warning_ignore("integer_division")
var hours := total_seconds / 3600
@warning_ignore("integer_division")
var minutes := (total_seconds % 3600) / 60
var seconds := total_seconds % 60
return "game:%d:%02d:%02d" % [hours, minutes, seconds]
func _get_round_info() -> String:
# 0:未开始游戏1:序章2-5:一四章6:结尾
var chapter := EventManager.get_chapter_stage()
return "r%d_c%d" % [config.game_rounds, chapter]
@warning_ignore_start("integer_division")
func _format_tick_time() -> String:
var ticks = Time.get_ticks_msec()
var hours := ticks / 3600000 as int
var minutes := (ticks % 3600000) / 60000 as int
var seconds := (ticks % 60000) / 1000 as int
var msec := ticks % 1000 as int
return "tick:%d:%02d:%02d.%03d" % [hours, minutes, seconds, msec]