mirror of
https://codeberg.org/sunder/sunder.git
synced 2026-07-15 22:14:33 +00:00
upgrade gut
This commit is contained in:
parent
6e724f67fe
commit
82aeebfd35
201 changed files with 8547 additions and 3871 deletions
|
|
@ -1,139 +0,0 @@
|
|||
@tool
|
||||
extends Window
|
||||
|
||||
var GutEditorGlobals = load('res://addons/gut/gui/editor_globals.gd')
|
||||
var default_path = GutEditorGlobals.editor_shortcuts_path
|
||||
|
||||
@onready var _ctrls = {
|
||||
run_all = $Layout/CRunAll/ShortcutButton,
|
||||
run_current_script = $Layout/CRunCurrentScript/ShortcutButton,
|
||||
run_current_inner = $Layout/CRunCurrentInner/ShortcutButton,
|
||||
run_current_test = $Layout/CRunCurrentTest/ShortcutButton,
|
||||
panel_button = $Layout/CPanelButton/ShortcutButton,
|
||||
}
|
||||
|
||||
var _user_prefs = GutEditorGlobals.user_prefs
|
||||
|
||||
func _ready():
|
||||
for key in _ctrls:
|
||||
var sc_button = _ctrls[key]
|
||||
sc_button.connect('start_edit', _on_edit_start.bind(sc_button))
|
||||
sc_button.connect('end_edit', _on_edit_end)
|
||||
|
||||
# show dialog when running scene from editor.
|
||||
if(get_parent() == get_tree().root):
|
||||
popup_centered()
|
||||
|
||||
|
||||
func _cancel_all():
|
||||
_ctrls.run_all.cancel()
|
||||
_ctrls.run_current_script.cancel()
|
||||
_ctrls.run_current_inner.cancel()
|
||||
_ctrls.run_current_test.cancel()
|
||||
_ctrls.panel_button.cancel()
|
||||
|
||||
# ------------
|
||||
# Events
|
||||
# ------------
|
||||
func _on_Hide_pressed():
|
||||
hide()
|
||||
|
||||
|
||||
func _on_edit_start(which):
|
||||
for key in _ctrls:
|
||||
var sc_button = _ctrls[key]
|
||||
if(sc_button != which):
|
||||
sc_button.disable_set(true)
|
||||
sc_button.disable_clear(true)
|
||||
|
||||
|
||||
func _on_edit_end():
|
||||
for key in _ctrls:
|
||||
var sc_button = _ctrls[key]
|
||||
sc_button.disable_set(false)
|
||||
sc_button.disable_clear(false)
|
||||
|
||||
|
||||
func _on_popup_hide():
|
||||
_cancel_all()
|
||||
|
||||
# ------------
|
||||
# Public
|
||||
# ------------
|
||||
func get_run_all():
|
||||
return _ctrls.run_all.get_shortcut()
|
||||
|
||||
func get_run_current_script():
|
||||
return _ctrls.run_current_script.get_shortcut()
|
||||
|
||||
func get_run_current_inner():
|
||||
return _ctrls.run_current_inner.get_shortcut()
|
||||
|
||||
func get_run_current_test():
|
||||
return _ctrls.run_current_test.get_shortcut()
|
||||
|
||||
func get_panel_button():
|
||||
return _ctrls.panel_button.get_shortcut()
|
||||
|
||||
func _set_pref_value(pref, button):
|
||||
pref.value = {shortcut = button.get_shortcut().events}
|
||||
|
||||
|
||||
func save_shortcuts():
|
||||
save_shortcuts_to_file(default_path)
|
||||
|
||||
|
||||
func save_shortcuts_to_editor_settings():
|
||||
_set_pref_value(_user_prefs.shortcut_run_all, _ctrls.run_all)
|
||||
_set_pref_value(_user_prefs.shortcut_run_current_script, _ctrls.run_current_script)
|
||||
_set_pref_value(_user_prefs.shortcut_run_current_inner, _ctrls.run_current_inner)
|
||||
_set_pref_value(_user_prefs.shortcut_run_current_test, _ctrls.run_current_test)
|
||||
_set_pref_value(_user_prefs.shortcut_panel_button, _ctrls.panel_button)
|
||||
|
||||
_user_prefs.save_it()
|
||||
|
||||
|
||||
func save_shortcuts_to_file(path):
|
||||
var f = ConfigFile.new()
|
||||
f.set_value('main', 'run_all', _ctrls.run_all.get_shortcut())
|
||||
f.set_value('main', 'run_current_script', _ctrls.run_current_script.get_shortcut())
|
||||
f.set_value('main', 'run_current_inner', _ctrls.run_current_inner.get_shortcut())
|
||||
f.set_value('main', 'run_current_test', _ctrls.run_current_test.get_shortcut())
|
||||
f.set_value('main', 'panel_button', _ctrls.panel_button.get_shortcut())
|
||||
f.save(path)
|
||||
|
||||
|
||||
func _load_shortcut_from_pref(user_pref):
|
||||
var to_return = Shortcut.new()
|
||||
# value with be _user_prefs.EMPTY which is a string when the value
|
||||
# has not been set.
|
||||
if(typeof(user_pref.value) == TYPE_DICTIONARY):
|
||||
to_return.events.append(user_pref.value.shortcut[0])
|
||||
# to_return = user_pref.value
|
||||
return to_return
|
||||
|
||||
|
||||
func load_shortcuts():
|
||||
load_shortcuts_from_file(default_path)
|
||||
|
||||
|
||||
func load_shortcuts_from_editor_settings():
|
||||
var empty = Shortcut.new()
|
||||
|
||||
_ctrls.run_all.set_shortcut(_load_shortcut_from_pref(_user_prefs.shortcut_run_all))
|
||||
_ctrls.run_current_script.set_shortcut(_load_shortcut_from_pref(_user_prefs.shortcut_run_current_script))
|
||||
_ctrls.run_current_inner.set_shortcut(_load_shortcut_from_pref(_user_prefs.shortcut_run_current_inner))
|
||||
_ctrls.run_current_test.set_shortcut(_load_shortcut_from_pref(_user_prefs.shortcut_run_current_test))
|
||||
_ctrls.panel_button.set_shortcut(_load_shortcut_from_pref(_user_prefs.shortcut_panel_button))
|
||||
|
||||
|
||||
func load_shortcuts_from_file(path):
|
||||
var f = ConfigFile.new()
|
||||
var empty = Shortcut.new()
|
||||
|
||||
f.load(path)
|
||||
_ctrls.run_all.set_shortcut(f.get_value('main', 'run_all', empty))
|
||||
_ctrls.run_current_script.set_shortcut(f.get_value('main', 'run_current_script', empty))
|
||||
_ctrls.run_current_inner.set_shortcut(f.get_value('main', 'run_current_inner', empty))
|
||||
_ctrls.run_current_test.set_shortcut(f.get_value('main', 'run_current_test', empty))
|
||||
_ctrls.panel_button.set_shortcut(f.get_value('main', 'panel_button', empty))
|
||||
|
|
@ -1 +0,0 @@
|
|||
uid://dsmt384dwo7em
|
||||
|
|
@ -1,153 +0,0 @@
|
|||
[gd_scene load_steps=3 format=3 uid="uid://bsk32dh41b4gs"]
|
||||
|
||||
[ext_resource type="PackedScene" uid="uid://sfb1fw8j6ufu" path="res://addons/gut/gui/ShortcutButton.tscn" id="1"]
|
||||
[ext_resource type="Script" path="res://addons/gut/gui/BottomPanelShortcuts.gd" id="2"]
|
||||
|
||||
[node name="BottomPanelShortcuts" type="Popup"]
|
||||
title = "Shortcuts"
|
||||
size = Vector2i(500, 350)
|
||||
visible = true
|
||||
exclusive = true
|
||||
unresizable = false
|
||||
borderless = false
|
||||
script = ExtResource("2")
|
||||
|
||||
[node name="Layout" type="VBoxContainer" parent="."]
|
||||
anchors_preset = 15
|
||||
anchor_right = 1.0
|
||||
anchor_bottom = 1.0
|
||||
offset_left = 5.0
|
||||
offset_right = -5.0
|
||||
offset_bottom = 2.0
|
||||
|
||||
[node name="TopPad" type="CenterContainer" parent="Layout"]
|
||||
custom_minimum_size = Vector2(0, 5)
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label2" type="Label" parent="Layout"]
|
||||
custom_minimum_size = Vector2(0, 20)
|
||||
layout_mode = 2
|
||||
text = "Always Active"
|
||||
|
||||
[node name="ColorRect" type="ColorRect" parent="Layout/Label2"]
|
||||
show_behind_parent = true
|
||||
layout_mode = 0
|
||||
anchor_right = 1.0
|
||||
anchor_bottom = 1.0
|
||||
color = Color(0, 0, 0, 0.196078)
|
||||
|
||||
[node name="CPanelButton" type="HBoxContainer" parent="Layout"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label" type="Label" parent="Layout/CPanelButton"]
|
||||
custom_minimum_size = Vector2(50, 0)
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 7
|
||||
text = "Show/Hide GUT Panel"
|
||||
|
||||
[node name="ShortcutButton" parent="Layout/CPanelButton" instance=ExtResource("1")]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
|
||||
[node name="GutPanelPad" type="CenterContainer" parent="Layout"]
|
||||
custom_minimum_size = Vector2(0, 5)
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label" type="Label" parent="Layout"]
|
||||
custom_minimum_size = Vector2(0, 20)
|
||||
layout_mode = 2
|
||||
text = "Only Active When GUT Panel Shown"
|
||||
|
||||
[node name="ColorRect2" type="ColorRect" parent="Layout/Label"]
|
||||
show_behind_parent = true
|
||||
layout_mode = 0
|
||||
anchor_right = 1.0
|
||||
anchor_bottom = 1.0
|
||||
color = Color(0, 0, 0, 0.196078)
|
||||
|
||||
[node name="TopPad2" type="CenterContainer" parent="Layout"]
|
||||
custom_minimum_size = Vector2(0, 5)
|
||||
layout_mode = 2
|
||||
|
||||
[node name="CRunAll" type="HBoxContainer" parent="Layout"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label" type="Label" parent="Layout/CRunAll"]
|
||||
custom_minimum_size = Vector2(50, 0)
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 7
|
||||
text = "Run All"
|
||||
|
||||
[node name="ShortcutButton" parent="Layout/CRunAll" instance=ExtResource("1")]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
|
||||
[node name="CRunCurrentScript" type="HBoxContainer" parent="Layout"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label" type="Label" parent="Layout/CRunCurrentScript"]
|
||||
custom_minimum_size = Vector2(50, 0)
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 7
|
||||
text = "Run Current Script"
|
||||
|
||||
[node name="ShortcutButton" parent="Layout/CRunCurrentScript" instance=ExtResource("1")]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
|
||||
[node name="CRunCurrentInner" type="HBoxContainer" parent="Layout"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label" type="Label" parent="Layout/CRunCurrentInner"]
|
||||
custom_minimum_size = Vector2(50, 0)
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 7
|
||||
text = "Run Current Inner Class"
|
||||
|
||||
[node name="ShortcutButton" parent="Layout/CRunCurrentInner" instance=ExtResource("1")]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
|
||||
[node name="CRunCurrentTest" type="HBoxContainer" parent="Layout"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label" type="Label" parent="Layout/CRunCurrentTest"]
|
||||
custom_minimum_size = Vector2(50, 0)
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 7
|
||||
text = "Run Current Test"
|
||||
|
||||
[node name="ShortcutButton" parent="Layout/CRunCurrentTest" instance=ExtResource("1")]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
|
||||
[node name="CenterContainer2" type="CenterContainer" parent="Layout"]
|
||||
custom_minimum_size = Vector2(0, 5)
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
size_flags_vertical = 3
|
||||
|
||||
[node name="ShiftDisclaimer" type="Label" parent="Layout"]
|
||||
layout_mode = 2
|
||||
text = "\"Shift\" cannot be the only modifier for a shortcut."
|
||||
|
||||
[node name="HBoxContainer" type="HBoxContainer" parent="Layout"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="CenterContainer" type="CenterContainer" parent="Layout/HBoxContainer"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
size_flags_vertical = 3
|
||||
|
||||
[node name="Hide" type="Button" parent="Layout/HBoxContainer"]
|
||||
custom_minimum_size = Vector2(60, 30)
|
||||
layout_mode = 2
|
||||
text = "Close"
|
||||
|
||||
[node name="BottomPad" type="CenterContainer" parent="Layout"]
|
||||
custom_minimum_size = Vector2(0, 10)
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
|
||||
[connection signal="popup_hide" from="." to="." method="_on_popup_hide"]
|
||||
[connection signal="pressed" from="Layout/HBoxContainer/Hide" to="." method="_on_Hide_pressed"]
|
||||
13
addons/gut/gui/EditorRadioButton.tres
Normal file
13
addons/gut/gui/EditorRadioButton.tres
Normal file
|
|
@ -0,0 +1,13 @@
|
|||
[gd_resource type="Theme" format=3 uid="uid://dssgvu257o1si"]
|
||||
|
||||
[sub_resource type="StyleBoxFlat" id="StyleBoxFlat_u716c"]
|
||||
bg_color = Color(0.43137255, 0.8784314, 0.6156863, 0.5254902)
|
||||
|
||||
[sub_resource type="StyleBoxFlat" id="StyleBoxFlat_ht2pf"]
|
||||
bg_color = Color(0, 0.44705883, 0.23921569, 1)
|
||||
|
||||
[resource]
|
||||
Button/colors/font_hover_pressed_color = Color(1, 1, 1, 1)
|
||||
Button/colors/font_pressed_color = Color(1, 1, 1, 1)
|
||||
Button/styles/hover = SubResource("StyleBoxFlat_u716c")
|
||||
Button/styles/pressed = SubResource("StyleBoxFlat_ht2pf")
|
||||
|
|
@ -2,53 +2,75 @@
|
|||
extends Control
|
||||
|
||||
var GutEditorGlobals = load('res://addons/gut/gui/editor_globals.gd')
|
||||
var TestScript = load('res://addons/gut/test.gd')
|
||||
var GutConfigGui = load('res://addons/gut/gui/gut_config_gui.gd')
|
||||
var ScriptTextEditors = load('res://addons/gut/gui/script_text_editor_controls.gd')
|
||||
|
||||
var AboutWindow = load("res://addons/gut/gui/about.tscn")
|
||||
|
||||
var _interface = null;
|
||||
var _is_running = false;
|
||||
var _is_running = false :
|
||||
set(val):
|
||||
_is_running = val
|
||||
_disable_run_buttons(_is_running)
|
||||
|
||||
var _gut_config = load('res://addons/gut/gut_config.gd').new()
|
||||
var _gut_config_gui = null
|
||||
var _gut_plugin = null
|
||||
var _light_color = Color(0, 0, 0, .5)
|
||||
var _light_color = Color(0, 0, 0, .5) :
|
||||
set(val):
|
||||
_light_color = val
|
||||
if(is_inside_tree()):
|
||||
_ctrls.light.queue_redraw()
|
||||
var _panel_button = null
|
||||
var _last_selected_path = null
|
||||
var _user_prefs = null
|
||||
var _shell_out_panel = null
|
||||
|
||||
|
||||
var menu_manager = null :
|
||||
set(val):
|
||||
menu_manager = val
|
||||
if(val != null):
|
||||
_apply_shortcuts()
|
||||
menu_manager.toggle_windowed.connect(_on_toggle_windowed)
|
||||
menu_manager.about.connect(show_about)
|
||||
menu_manager.run_all.connect(_run_all)
|
||||
menu_manager.show_gut.connect(_on_show_gut)
|
||||
|
||||
|
||||
@onready var _ctrls = {
|
||||
output = $layout/RSplit/CResults/TabBar/OutputText.get_rich_text_edit(),
|
||||
output_ctrl = $layout/RSplit/CResults/TabBar/OutputText,
|
||||
about = %ExtraButtons/About,
|
||||
light = %StatusIndicator,
|
||||
output_button = %ExtraButtons/OutputBtn,
|
||||
run_button = $layout/ControlBar/RunAll,
|
||||
shortcuts_button = $layout/ControlBar/Shortcuts,
|
||||
|
||||
settings_button = $layout/ControlBar/Settings,
|
||||
run_results_button = $layout/ControlBar/RunResultsBtn,
|
||||
output_button = $layout/ControlBar/OutputBtn,
|
||||
|
||||
settings = $layout/RSplit/sc/Settings,
|
||||
shortcut_dialog = $BottomPanelShortcuts,
|
||||
light = $layout/RSplit/CResults/ControlBar/Light3D,
|
||||
results = {
|
||||
bar = $layout/RSplit/CResults/ControlBar,
|
||||
passing = $layout/RSplit/CResults/ControlBar/Passing/value,
|
||||
failing = $layout/RSplit/CResults/ControlBar/Failing/value,
|
||||
pending = $layout/RSplit/CResults/ControlBar/Pending/value,
|
||||
errors = $layout/RSplit/CResults/ControlBar/Errors/value,
|
||||
warnings = $layout/RSplit/CResults/ControlBar/Warnings/value,
|
||||
orphans = $layout/RSplit/CResults/ControlBar/Orphans/value
|
||||
},
|
||||
run_externally_dialog = $ShellOutOptions,
|
||||
run_mode = %ExtraButtons/RunMode,
|
||||
run_at_cursor = $layout/ControlBar/RunAtCursor,
|
||||
run_results = $layout/RSplit/CResults/TabBar/RunResults
|
||||
run_results_button = %ExtraButtons/RunResultsBtn,
|
||||
settings = $layout/RSplit/sc/Settings,
|
||||
settings_button = %ExtraButtons/Settings,
|
||||
shortcut_dialog = $ShortcutDialog,
|
||||
shortcuts_button = %ExtraButtons/Shortcuts,
|
||||
|
||||
results = {
|
||||
bar = $layout/ControlBar2,
|
||||
errors = %errors_value,
|
||||
failing = %failing_value,
|
||||
orphans = %orphans_value,
|
||||
passing = %passing_value,
|
||||
pending = %pending_value,
|
||||
warnings = %warnings_value,
|
||||
},
|
||||
}
|
||||
|
||||
func _init():
|
||||
pass
|
||||
@onready var results_v_split = %VSplitResults
|
||||
@onready var results_h_split = %HSplitResults
|
||||
@onready var results_tree = %RunResults
|
||||
@onready var results_text = %OutputText
|
||||
@onready var make_floating_btn = %MakeFloating
|
||||
|
||||
|
||||
func _ready():
|
||||
if(get_parent() is SubViewport):
|
||||
return
|
||||
|
||||
GutEditorGlobals.create_temp_directory()
|
||||
|
||||
_user_prefs = GutEditorGlobals.user_prefs
|
||||
|
|
@ -59,45 +81,75 @@ func _ready():
|
|||
|
||||
_gut_config.load_options(GutEditorGlobals.editor_run_gut_config_path)
|
||||
_gut_config_gui.set_options(_gut_config.options)
|
||||
_apply_options_to_controls()
|
||||
|
||||
_ctrls.shortcuts_button.icon = get_theme_icon('Shortcut', 'EditorIcons')
|
||||
_ctrls.settings_button.icon = get_theme_icon('Tools', 'EditorIcons')
|
||||
_ctrls.run_results_button.icon = get_theme_icon('AnimationTrackGroup', 'EditorIcons') # Tree
|
||||
_ctrls.output_button.icon = get_theme_icon('Font', 'EditorIcons')
|
||||
make_floating_btn.icon = get_theme_icon("MakeFloating", 'EditorIcons')
|
||||
make_floating_btn.text = ''
|
||||
_ctrls.about.icon = get_theme_icon('Info', 'EditorIcons')
|
||||
_ctrls.about.text = ''
|
||||
_ctrls.run_mode.icon = get_theme_icon("ViewportSpeed", 'EditorIcons')
|
||||
|
||||
_ctrls.run_results.set_output_control(_ctrls.output_ctrl)
|
||||
results_tree.set_output_control(results_text)
|
||||
|
||||
var check_import = load('res://addons/gut/images/red.png')
|
||||
var check_import = load('res://addons/gut/images/HSplitContainer.svg')
|
||||
if(check_import == null):
|
||||
_ctrls.run_results.add_centered_text("GUT got some new images that are not imported yet. Please restart Godot.")
|
||||
results_tree.add_centered_text("GUT got some new images that are not imported yet. Please restart Godot.")
|
||||
print('GUT got some new images that are not imported yet. Please restart Godot.')
|
||||
else:
|
||||
_ctrls.run_results.add_centered_text("Let's run some tests!")
|
||||
results_tree.add_centered_text("Let's run some tests!")
|
||||
|
||||
_ctrls.run_externally_dialog.load_from_file()
|
||||
_apply_options_to_controls()
|
||||
|
||||
results_vert_layout()
|
||||
|
||||
|
||||
func _apply_options_to_controls():
|
||||
hide_settings(_user_prefs.hide_settings.value)
|
||||
hide_result_tree(_user_prefs.hide_result_tree.value)
|
||||
hide_output_text(_user_prefs.hide_output_text.value)
|
||||
_ctrls.run_results.set_show_orphans(!_gut_config.options.hide_orphans)
|
||||
|
||||
|
||||
func _process(delta):
|
||||
func _process(_delta):
|
||||
if(_is_running):
|
||||
if(!_interface.is_playing_scene()):
|
||||
if(_ctrls.run_externally_dialog.should_run_externally()):
|
||||
if(!is_instance_valid(_shell_out_panel)):
|
||||
_is_running = false
|
||||
show_me()
|
||||
elif(!_interface.is_playing_scene()):
|
||||
_is_running = false
|
||||
_ctrls.output_ctrl.add_text("\ndone")
|
||||
results_text.add_text("\ndone")
|
||||
load_result_output()
|
||||
_gut_plugin.make_bottom_panel_item_visible(self)
|
||||
show_me()
|
||||
|
||||
|
||||
# ---------------
|
||||
# Private
|
||||
# ---------------
|
||||
func _apply_options_to_controls():
|
||||
hide_settings(_user_prefs.hide_settings.value)
|
||||
hide_result_tree(_user_prefs.hide_result_tree.value)
|
||||
hide_output_text(_user_prefs.hide_output_text.value)
|
||||
results_tree.set_show_orphans(!_gut_config.options.hide_orphans)
|
||||
var shell_dialog_size = _user_prefs.run_externally_options_dialog_size.value
|
||||
|
||||
func load_shortcuts():
|
||||
_ctrls.shortcut_dialog.load_shortcuts()
|
||||
_apply_shortcuts()
|
||||
if(shell_dialog_size != Vector2i(-1, -1)):
|
||||
_ctrls.run_externally_dialog.size = Vector2i(shell_dialog_size)
|
||||
|
||||
if(_user_prefs.shortcuts_dialog_size.value != Vector2i(-1, -1)):
|
||||
_ctrls.shortcut_dialog.size = _user_prefs.shortcuts_dialog_size.value
|
||||
|
||||
var mode_ind = 'Ed'
|
||||
if(_ctrls.run_externally_dialog.run_mode == _ctrls.run_externally_dialog.RUN_MODE_BLOCKING):
|
||||
mode_ind = 'ExB'
|
||||
elif(_ctrls.run_externally_dialog.run_mode == _ctrls.run_externally_dialog.RUN_MODE_NON_BLOCKING):
|
||||
mode_ind = 'ExN'
|
||||
_ctrls.run_mode.text = mode_ind
|
||||
|
||||
_ctrls.run_at_cursor.apply_gut_config(_gut_config)
|
||||
|
||||
|
||||
|
||||
func _disable_run_buttons(should):
|
||||
_ctrls.run_button.disabled = should
|
||||
_ctrls.run_at_cursor.disabled = should
|
||||
|
||||
|
||||
func _is_test_script(script):
|
||||
|
|
@ -109,22 +161,31 @@ func _is_test_script(script):
|
|||
|
||||
|
||||
func _show_errors(errs):
|
||||
_ctrls.output_ctrl.clear()
|
||||
results_text.clear()
|
||||
var text = "Cannot run tests, you have a configuration error:\n"
|
||||
for e in errs:
|
||||
text += str('* ', e, "\n")
|
||||
text += "Check your settings ----->"
|
||||
_ctrls.output_ctrl.add_text(text)
|
||||
results_text.add_text(text)
|
||||
hide_output_text(false)
|
||||
hide_settings(false)
|
||||
|
||||
|
||||
func _save_config():
|
||||
func _save_user_prefs():
|
||||
_user_prefs.hide_settings.value = !_ctrls.settings_button.button_pressed
|
||||
_user_prefs.hide_result_tree.value = !_ctrls.run_results_button.button_pressed
|
||||
_user_prefs.hide_output_text.value = !_ctrls.output_button.button_pressed
|
||||
_user_prefs.shortcuts_dialog_size.value = _ctrls.shortcut_dialog.size
|
||||
|
||||
_user_prefs.run_externally.value = _ctrls.run_externally_dialog.run_mode != _ctrls.run_externally_dialog.RUN_MODE_EDITOR
|
||||
_user_prefs.run_externally_options_dialog_size.value = _ctrls.run_externally_dialog.size
|
||||
|
||||
_user_prefs.save_it()
|
||||
|
||||
|
||||
func _save_config():
|
||||
_save_user_prefs()
|
||||
|
||||
_gut_config.options = _gut_config_gui.get_options(_gut_config.options)
|
||||
var w_result = _gut_config.write_options(GutEditorGlobals.editor_run_gut_config_path)
|
||||
if(w_result != OK):
|
||||
|
|
@ -133,8 +194,25 @@ func _save_config():
|
|||
_gut_config_gui.mark_saved()
|
||||
|
||||
|
||||
func _run_externally():
|
||||
_shell_out_panel = GutUtils.RunExternallyScene.instantiate()
|
||||
_shell_out_panel.bottom_panel = self
|
||||
_shell_out_panel.blocking_mode = _ctrls.run_externally_dialog.run_mode
|
||||
_shell_out_panel.additional_arguments = _ctrls.run_externally_dialog.get_additional_arguments_array()
|
||||
|
||||
add_child(_shell_out_panel)
|
||||
_shell_out_panel.run_tests()
|
||||
|
||||
|
||||
func _run_tests():
|
||||
show_me()
|
||||
if(_is_running):
|
||||
push_error("GUT: Cannot run tests, tests are already running.")
|
||||
return
|
||||
|
||||
clear_results()
|
||||
GutEditorGlobals.create_temp_directory()
|
||||
_light_color = Color.BLUE
|
||||
|
||||
var issues = _gut_config_gui.get_config_issues()
|
||||
if(issues.size() > 0):
|
||||
|
|
@ -142,29 +220,43 @@ func _run_tests():
|
|||
return
|
||||
|
||||
write_file(GutEditorGlobals.editor_run_bbcode_results_path, 'Run in progress')
|
||||
write_file(GutEditorGlobals.editor_run_json_results_path, '')
|
||||
_save_config()
|
||||
_apply_options_to_controls()
|
||||
|
||||
_ctrls.output_ctrl.clear()
|
||||
_ctrls.run_results.clear()
|
||||
_ctrls.run_results.add_centered_text('Running...')
|
||||
results_text.clear()
|
||||
results_tree.clear()
|
||||
results_tree.add_centered_text('Running...')
|
||||
|
||||
_interface.play_custom_scene('res://addons/gut/gui/run_from_editor.tscn')
|
||||
_is_running = true
|
||||
_ctrls.output_ctrl.add_text('Running...')
|
||||
results_text.add_text('Running...')
|
||||
|
||||
if(_ctrls.run_externally_dialog.should_run_externally()):
|
||||
_gut_plugin.make_bottom_panel_item_visible(self)
|
||||
_run_externally()
|
||||
else:
|
||||
_interface.play_custom_scene('res://addons/gut/gui/run_from_editor.tscn')
|
||||
|
||||
|
||||
func _apply_shortcuts():
|
||||
_ctrls.run_button.shortcut = _ctrls.shortcut_dialog.get_run_all()
|
||||
if(menu_manager != null):
|
||||
menu_manager.apply_gut_shortcuts(_ctrls.shortcut_dialog)
|
||||
|
||||
_ctrls.run_button.shortcut = \
|
||||
_ctrls.shortcut_dialog.scbtn_run_all.get_shortcut()
|
||||
_ctrls.run_at_cursor.get_script_button().shortcut = \
|
||||
_ctrls.shortcut_dialog.get_run_current_script()
|
||||
_ctrls.shortcut_dialog.scbtn_run_current_script.get_shortcut()
|
||||
_ctrls.run_at_cursor.get_inner_button().shortcut = \
|
||||
_ctrls.shortcut_dialog.get_run_current_inner()
|
||||
_ctrls.shortcut_dialog.scbtn_run_current_inner.get_shortcut()
|
||||
_ctrls.run_at_cursor.get_test_button().shortcut = \
|
||||
_ctrls.shortcut_dialog.get_run_current_test()
|
||||
|
||||
_panel_button.shortcut = _ctrls.shortcut_dialog.get_panel_button()
|
||||
_ctrls.shortcut_dialog.scbtn_run_current_test.get_shortcut()
|
||||
# Took this out because it seems to break using the shortcut when docked.
|
||||
# Though it does allow the shortcut to work when windowed. Shortcuts
|
||||
# are weird.
|
||||
# make_floating_btn.shortcut = \
|
||||
# _ctrls.shortcut_dialog.scbtn_windowed.get_shortcut()
|
||||
if(get_parent() is EditorDock):
|
||||
get_parent().dock_shortcut = _ctrls.shortcut_dialog.scbtn_panel.get_shortcut()
|
||||
|
||||
|
||||
func _run_all():
|
||||
|
|
@ -187,11 +279,6 @@ func _on_Light_draw():
|
|||
l.draw_circle(Vector2(l.size.x / 2, l.size.y / 2), l.size.x / 2, _light_color)
|
||||
|
||||
|
||||
func _on_editor_script_changed(script):
|
||||
if(script):
|
||||
set_current_script(script)
|
||||
|
||||
|
||||
func _on_RunAll_pressed():
|
||||
_run_all()
|
||||
|
||||
|
|
@ -199,14 +286,17 @@ func _on_RunAll_pressed():
|
|||
func _on_Shortcuts_pressed():
|
||||
_ctrls.shortcut_dialog.popup_centered()
|
||||
|
||||
func _on_bottom_panel_shortcuts_visibility_changed():
|
||||
|
||||
func _on_sortcut_dialog_confirmed() -> void:
|
||||
_apply_shortcuts()
|
||||
_ctrls.shortcut_dialog.save_shortcuts()
|
||||
_save_user_prefs()
|
||||
|
||||
|
||||
func _on_RunAtCursor_run_tests(what):
|
||||
_gut_config.options.selected = what.script
|
||||
_gut_config.options.inner_class = what.inner_class
|
||||
_gut_config.options.unit_test_name = what.test_method
|
||||
_gut_config.options.unit_test_name = what.method
|
||||
|
||||
_run_tests()
|
||||
|
||||
|
|
@ -231,11 +321,51 @@ func _on_RunResultsBtn_pressed():
|
|||
func _on_UseColors_pressed():
|
||||
pass
|
||||
|
||||
|
||||
func _on_shell_out_options_confirmed() -> void:
|
||||
_ctrls.run_externally_dialog.save_to_file()
|
||||
_save_user_prefs()
|
||||
_apply_options_to_controls()
|
||||
|
||||
|
||||
func _on_run_mode_pressed() -> void:
|
||||
_ctrls.run_externally_dialog.popup_centered()
|
||||
|
||||
|
||||
func _on_toggle_windowed():
|
||||
_gut_plugin.toggle_windowed()
|
||||
|
||||
|
||||
func _on_to_window_pressed() -> void:
|
||||
_gut_plugin.toggle_windowed()
|
||||
|
||||
|
||||
func _on_show_gut() -> void:
|
||||
show_hide()
|
||||
|
||||
|
||||
func _on_about_pressed() -> void:
|
||||
show_about()
|
||||
|
||||
|
||||
func _on_horiz_layout_pressed() -> void:
|
||||
results_horiz_layout()
|
||||
|
||||
|
||||
func _on_vert_layout_pressed() -> void:
|
||||
results_vert_layout()
|
||||
|
||||
|
||||
# ---------------
|
||||
# Public
|
||||
# ---------------
|
||||
func load_shortcuts():
|
||||
_ctrls.shortcut_dialog.load_shortcuts()
|
||||
_apply_shortcuts()
|
||||
|
||||
|
||||
func hide_result_tree(should):
|
||||
_ctrls.run_results.visible = !should
|
||||
results_tree.visible = !should
|
||||
_ctrls.run_results_button.button_pressed = !should
|
||||
|
||||
|
||||
|
|
@ -255,69 +385,84 @@ func hide_settings(should):
|
|||
|
||||
|
||||
func hide_output_text(should):
|
||||
$layout/RSplit/CResults/TabBar/OutputText.visible = !should
|
||||
results_text.visible = !should
|
||||
_ctrls.output_button.button_pressed = !should
|
||||
|
||||
|
||||
func load_result_output():
|
||||
_ctrls.output_ctrl.load_file(GutEditorGlobals.editor_run_bbcode_results_path)
|
||||
func clear_results():
|
||||
_light_color = Color(0, 0, 0, .5)
|
||||
|
||||
_ctrls.results.passing.text = "0"
|
||||
_ctrls.results.passing.get_parent().visible = false
|
||||
|
||||
_ctrls.results.failing.text = "0"
|
||||
_ctrls.results.failing.get_parent().visible = false
|
||||
|
||||
_ctrls.results.pending.text = "0"
|
||||
_ctrls.results.pending.get_parent().visible = false
|
||||
|
||||
_ctrls.results.errors.text = "0"
|
||||
_ctrls.results.errors.get_parent().visible = false
|
||||
|
||||
_ctrls.results.warnings.text = "0"
|
||||
_ctrls.results.warnings.get_parent().visible = false
|
||||
|
||||
_ctrls.results.orphans.text = "0"
|
||||
_ctrls.results.orphans.get_parent().visible = false
|
||||
|
||||
|
||||
func load_result_json():
|
||||
var summary = get_file_as_text(GutEditorGlobals.editor_run_json_results_path)
|
||||
var test_json_conv = JSON.new()
|
||||
if (test_json_conv.parse(summary) != OK):
|
||||
return
|
||||
var results = test_json_conv.get_data()
|
||||
|
||||
_ctrls.run_results.load_json_results(results)
|
||||
results_tree.load_json_results(results)
|
||||
|
||||
var summary_json = results['test_scripts']['props']
|
||||
_ctrls.results.passing.text = str(summary_json.passing)
|
||||
_ctrls.results.passing.text = str(int(summary_json.passing))
|
||||
_ctrls.results.passing.get_parent().visible = true
|
||||
|
||||
_ctrls.results.failing.text = str(summary_json.failures)
|
||||
_ctrls.results.failing.text = str(int(summary_json.failures))
|
||||
_ctrls.results.failing.get_parent().visible = true
|
||||
|
||||
_ctrls.results.pending.text = str(summary_json.pending)
|
||||
_ctrls.results.pending.text = str(int(summary_json.pending) + int(summary_json.risky))
|
||||
_ctrls.results.pending.get_parent().visible = _ctrls.results.pending.text != '0'
|
||||
|
||||
_ctrls.results.errors.text = str(summary_json.errors)
|
||||
_ctrls.results.errors.text = str(int(summary_json.errors))
|
||||
_ctrls.results.errors.get_parent().visible = _ctrls.results.errors.text != '0'
|
||||
|
||||
_ctrls.results.warnings.text = str(summary_json.warnings)
|
||||
_ctrls.results.warnings.text = str(int(summary_json.warnings))
|
||||
_ctrls.results.warnings.get_parent().visible = _ctrls.results.warnings.text != '0'
|
||||
|
||||
_ctrls.results.orphans.text = str(summary_json.orphans)
|
||||
_ctrls.results.orphans.text = str(int(summary_json.orphans))
|
||||
_ctrls.results.orphans.get_parent().visible = _ctrls.results.orphans.text != '0' and !_gut_config.options.hide_orphans
|
||||
|
||||
if(summary_json.tests == 0):
|
||||
_light_color = Color(1, 0, 0, .75)
|
||||
elif(summary_json.failures != 0):
|
||||
_light_color = Color(1, 0, 0, .75)
|
||||
elif(summary_json.pending != 0):
|
||||
elif(summary_json.pending != 0 or summary_json.risky != 0):
|
||||
_light_color = Color(1, 1, 0, .75)
|
||||
else:
|
||||
_light_color = Color(0, 1, 0, .75)
|
||||
|
||||
_ctrls.light.visible = true
|
||||
_ctrls.light.queue_redraw()
|
||||
|
||||
|
||||
func set_current_script(script):
|
||||
if(script):
|
||||
if(_is_test_script(script)):
|
||||
var file = script.resource_path.get_file()
|
||||
_last_selected_path = script.resource_path.get_file()
|
||||
_ctrls.run_at_cursor.activate_for_script(script.resource_path)
|
||||
func load_result_text():
|
||||
results_text.load_file(GutEditorGlobals.editor_run_bbcode_results_path)
|
||||
|
||||
|
||||
func load_result_output():
|
||||
load_result_text()
|
||||
load_result_json()
|
||||
|
||||
|
||||
func set_interface(value):
|
||||
_interface = value
|
||||
_interface.get_script_editor().connect("editor_script_changed",Callable(self,'_on_editor_script_changed'))
|
||||
|
||||
var ste = ScriptTextEditors.new(_interface.get_script_editor())
|
||||
_ctrls.run_results.set_interface(_interface)
|
||||
_ctrls.run_results.set_script_text_editors(ste)
|
||||
_ctrls.run_at_cursor.set_script_text_editors(ste)
|
||||
set_current_script(_interface.get_script_editor().get_current_script())
|
||||
results_tree.set_interface(_interface)
|
||||
|
||||
|
||||
func set_plugin(value):
|
||||
|
|
@ -327,9 +472,7 @@ func set_plugin(value):
|
|||
func set_panel_button(value):
|
||||
_panel_button = value
|
||||
|
||||
# ------------------------------------------------------------------------------
|
||||
# Write a file.
|
||||
# ------------------------------------------------------------------------------
|
||||
|
||||
func write_file(path, content):
|
||||
var f = FileAccess.open(path, FileAccess.WRITE)
|
||||
if(f != null):
|
||||
|
|
@ -339,9 +482,6 @@ func write_file(path, content):
|
|||
return FileAccess.get_open_error()
|
||||
|
||||
|
||||
# ------------------------------------------------------------------------------
|
||||
# Returns the text of a file or an empty string if the file could not be opened.
|
||||
# ------------------------------------------------------------------------------
|
||||
func get_file_as_text(path):
|
||||
var to_return = ''
|
||||
var f = FileAccess.open(path, FileAccess.READ)
|
||||
|
|
@ -351,11 +491,66 @@ func get_file_as_text(path):
|
|||
return to_return
|
||||
|
||||
|
||||
# ------------------------------------------------------------------------------
|
||||
# return if_null if value is null otherwise return value
|
||||
# ------------------------------------------------------------------------------
|
||||
func nvl(value, if_null):
|
||||
if(value == null):
|
||||
return if_null
|
||||
func get_text_output_control():
|
||||
return results_text
|
||||
|
||||
|
||||
func add_output_text(text):
|
||||
results_text.add_text(text)
|
||||
|
||||
|
||||
func show_about():
|
||||
var about = AboutWindow.instantiate()
|
||||
add_child(about)
|
||||
about.popup_centered()
|
||||
about.confirmed.connect(about.queue_free)
|
||||
|
||||
|
||||
func show_me():
|
||||
get_parent().make_visible()
|
||||
|
||||
|
||||
func show_hide():
|
||||
if(owner is Window):
|
||||
if(owner.has_focus()):
|
||||
var win_to_focus_on = EditorInterface.get_editor_main_screen().get_parent()
|
||||
while(win_to_focus_on != null and win_to_focus_on is not Window):
|
||||
win_to_focus_on = win_to_focus_on.get_parent()
|
||||
if(win_to_focus_on != null):
|
||||
win_to_focus_on.grab_focus()
|
||||
else:
|
||||
owner.grab_focus()
|
||||
else:
|
||||
return value
|
||||
pass
|
||||
# We don't have to do anything when we are docked because the GUT
|
||||
# bottom panel has the shortcut and it does the toggling all on its
|
||||
# own.
|
||||
|
||||
|
||||
func get_shortcut_dialog():
|
||||
return _ctrls.shortcut_dialog
|
||||
|
||||
|
||||
func results_vert_layout():
|
||||
if(results_tree.get_parent() != results_v_split):
|
||||
results_tree.reparent(results_v_split)
|
||||
results_text.reparent(results_v_split)
|
||||
results_v_split.visible = true
|
||||
results_h_split.visible = false
|
||||
|
||||
|
||||
func results_horiz_layout():
|
||||
if(results_tree.get_parent() != results_h_split):
|
||||
results_tree.reparent(results_h_split)
|
||||
results_text.reparent(results_h_split)
|
||||
results_v_split.visible = false
|
||||
results_h_split.visible = true
|
||||
|
||||
|
||||
func show_layout_buttons(should):
|
||||
%HorizLayout.visible = should
|
||||
%VertLayout.visible = should
|
||||
|
||||
|
||||
func get_panel_shortcut():
|
||||
_ctrls.shortcut_dialog.scbtn_panel.get_shortcut()
|
||||
|
|
|
|||
|
|
@ -1 +1 @@
|
|||
uid://b84o6yt8c0i3p
|
||||
uid://dtvnb0xatk0my
|
||||
|
|
|
|||
|
|
@ -1,27 +1,21 @@
|
|||
[gd_scene load_steps=10 format=3 uid="uid://b3bostcslstem"]
|
||||
[gd_scene format=3 uid="uid://b3bostcslstem"]
|
||||
|
||||
[ext_resource type="Script" path="res://addons/gut/gui/GutBottomPanel.gd" id="1"]
|
||||
[ext_resource type="PackedScene" uid="uid://bsk32dh41b4gs" path="res://addons/gut/gui/BottomPanelShortcuts.tscn" id="2"]
|
||||
[ext_resource type="Script" uid="uid://dtvnb0xatk0my" path="res://addons/gut/gui/GutBottomPanel.gd" id="1"]
|
||||
[ext_resource type="PackedScene" uid="uid://0yunjxtaa8iw" path="res://addons/gut/gui/RunAtCursor.tscn" id="3"]
|
||||
[ext_resource type="Texture2D" uid="uid://cr6tvdv0ve6cv" path="res://addons/gut/gui/play.png" id="4"]
|
||||
[ext_resource type="Texture2D" uid="uid://bvo0uao7deu0q" path="res://addons/gut/icon.png" id="4_xv2r3"]
|
||||
[ext_resource type="PackedScene" uid="uid://4gyyn12um08h" path="res://addons/gut/gui/RunResults.tscn" id="5"]
|
||||
[ext_resource type="Texture2D" uid="uid://ljc2viafngwd" path="res://addons/gut/images/HSplitContainer.svg" id="5_qdqpf"]
|
||||
[ext_resource type="PackedScene" uid="uid://bqmo4dj64c7yl" path="res://addons/gut/gui/OutputText.tscn" id="6"]
|
||||
[ext_resource type="Texture2D" uid="uid://bhew20crsywxr" path="res://addons/gut/images/VSplitContainer.svg" id="6_ot46d"]
|
||||
[ext_resource type="PackedScene" uid="uid://dj5ve0bq7xa5j" path="res://addons/gut/gui/ShortcutDialog.tscn" id="7_srqj5"]
|
||||
[ext_resource type="PackedScene" uid="uid://ckv5eh8xyrwbk" path="res://addons/gut/gui/ShellOutOptions.tscn" id="7_xv2r3"]
|
||||
|
||||
[sub_resource type="Shortcut" id="9"]
|
||||
|
||||
[sub_resource type="Image" id="Image_4maas"]
|
||||
data = {
|
||||
"data": PackedByteArray(255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 255, 255, 0, 255, 94, 94, 127, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 255, 255, 0, 255, 93, 93, 255, 255, 94, 94, 127, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 255, 255, 0, 255, 93, 93, 255, 255, 93, 93, 255, 255, 94, 94, 127, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 255, 255, 0, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 94, 94, 127, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 93, 93, 231, 255, 94, 94, 54, 255, 94, 94, 57, 255, 93, 93, 233, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 231, 255, 94, 94, 54, 255, 94, 94, 57, 255, 93, 93, 233, 255, 93, 93, 255, 255, 93, 93, 255, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 97, 97, 42, 255, 255, 255, 0, 255, 255, 255, 0, 255, 97, 97, 42, 255, 93, 93, 233, 255, 93, 93, 232, 255, 93, 93, 41, 255, 255, 255, 0, 255, 255, 255, 0, 255, 97, 97, 42, 255, 93, 93, 233, 255, 93, 93, 232, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 96, 96, 45, 255, 93, 93, 44, 255, 255, 255, 0, 255, 97, 97, 42, 255, 97, 97, 42, 255, 255, 255, 0, 255, 96, 96, 45, 255, 93, 93, 44, 255, 255, 255, 0, 255, 97, 97, 42, 255, 97, 97, 42, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 96, 96, 45, 255, 93, 93, 235, 255, 94, 94, 234, 255, 95, 95, 43, 255, 255, 255, 0, 255, 255, 255, 0, 255, 96, 96, 45, 255, 93, 93, 235, 255, 94, 94, 234, 255, 95, 95, 43, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 93, 93, 235, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 233, 255, 95, 95, 59, 255, 96, 96, 61, 255, 93, 93, 235, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 233, 255, 95, 95, 59, 255, 96, 96, 61, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0),
|
||||
"format": "RGBA8",
|
||||
"height": 16,
|
||||
"mipmaps": false,
|
||||
"width": 16
|
||||
}
|
||||
[sub_resource type="ButtonGroup" id="ButtonGroup_bskl7"]
|
||||
|
||||
[sub_resource type="ImageTexture" id="ImageTexture_umaha"]
|
||||
image = SubResource("Image_4maas")
|
||||
|
||||
[node name="GutBottomPanel" type="Control"]
|
||||
[node name="GutBottomPanel" type="Control" unique_id=1136630421]
|
||||
custom_minimum_size = Vector2(250, 250)
|
||||
layout_mode = 3
|
||||
anchor_left = -0.0025866
|
||||
|
|
@ -34,217 +28,292 @@ offset_right = 2.64862
|
|||
offset_bottom = 1.05945
|
||||
script = ExtResource("1")
|
||||
|
||||
[node name="layout" type="VBoxContainer" parent="."]
|
||||
[node name="layout" type="VBoxContainer" parent="." unique_id=790416054]
|
||||
layout_mode = 0
|
||||
anchor_right = 1.0
|
||||
anchor_bottom = 1.0
|
||||
|
||||
[node name="ControlBar" type="HBoxContainer" parent="layout"]
|
||||
[node name="ControlBar" type="HBoxContainer" parent="layout" unique_id=672788595]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="RunAll" type="Button" parent="layout/ControlBar"]
|
||||
[node name="RunAll" type="Button" parent="layout/ControlBar" unique_id=678231332]
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 11
|
||||
shortcut = SubResource("9")
|
||||
text = "Run All"
|
||||
icon = ExtResource("4")
|
||||
|
||||
[node name="Label" type="Label" parent="layout/ControlBar"]
|
||||
layout_mode = 2
|
||||
mouse_filter = 1
|
||||
text = "Current: "
|
||||
|
||||
[node name="RunAtCursor" parent="layout/ControlBar" instance=ExtResource("3")]
|
||||
[node name="Sep3" type="ColorRect" parent="layout/ControlBar" unique_id=1600176902]
|
||||
custom_minimum_size = Vector2(1, 2.08165e-12)
|
||||
layout_mode = 2
|
||||
|
||||
[node name="CenterContainer2" type="CenterContainer" parent="layout/ControlBar"]
|
||||
[node name="RunAtCursor" parent="layout/ControlBar" unique_id=1603612118 instance=ExtResource("3")]
|
||||
custom_minimum_size = Vector2(237, 0)
|
||||
layout_mode = 2
|
||||
|
||||
[node name="CenterContainer2" type="CenterContainer" parent="layout/ControlBar" unique_id=269691286]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
|
||||
[node name="Sep1" type="ColorRect" parent="layout/ControlBar"]
|
||||
[node name="MakeFloating" type="Button" parent="layout/ControlBar" unique_id=1273743620]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
tooltip_text = "Move the GUT panel to a window."
|
||||
icon = ExtResource("4_xv2r3")
|
||||
flat = true
|
||||
|
||||
[node name="HorizLayout" type="Button" parent="layout/ControlBar" unique_id=679134345]
|
||||
unique_name_in_owner = true
|
||||
texture_filter = 1
|
||||
layout_mode = 2
|
||||
toggle_mode = true
|
||||
button_pressed = true
|
||||
button_group = SubResource("ButtonGroup_bskl7")
|
||||
icon = ExtResource("5_qdqpf")
|
||||
icon_alignment = 1
|
||||
|
||||
[node name="VertLayout" type="Button" parent="layout/ControlBar" unique_id=1762257478]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
toggle_mode = true
|
||||
button_group = SubResource("ButtonGroup_bskl7")
|
||||
icon = ExtResource("6_ot46d")
|
||||
|
||||
[node name="ControlBar2" type="HBoxContainer" parent="layout" unique_id=920578685]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Sep2" type="ColorRect" parent="layout/ControlBar2" unique_id=781273927]
|
||||
custom_minimum_size = Vector2(1, 2.08165e-12)
|
||||
layout_mode = 2
|
||||
color = Color(1, 1, 1, 0)
|
||||
|
||||
[node name="StatusIndicator" type="Control" parent="layout/ControlBar2" unique_id=173224142]
|
||||
unique_name_in_owner = true
|
||||
custom_minimum_size = Vector2(30, 30)
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Passing" type="HBoxContainer" parent="layout/ControlBar2" unique_id=2110519605]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Sep" type="ColorRect" parent="layout/ControlBar2/Passing" unique_id=164849935]
|
||||
custom_minimum_size = Vector2(1, 2.08165e-12)
|
||||
layout_mode = 2
|
||||
|
||||
[node name="RunResultsBtn" type="Button" parent="layout/ControlBar"]
|
||||
[node name="label" type="Label" parent="layout/ControlBar2/Passing" unique_id=1437040616]
|
||||
layout_mode = 2
|
||||
toggle_mode = true
|
||||
icon = SubResource("ImageTexture_umaha")
|
||||
text = "Pass"
|
||||
|
||||
[node name="OutputBtn" type="Button" parent="layout/ControlBar"]
|
||||
[node name="passing_value" type="Label" parent="layout/ControlBar2/Passing" unique_id=551548364]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
toggle_mode = true
|
||||
icon = SubResource("ImageTexture_umaha")
|
||||
text = "---"
|
||||
|
||||
[node name="Settings" type="Button" parent="layout/ControlBar"]
|
||||
[node name="Failing" type="HBoxContainer" parent="layout/ControlBar2" unique_id=1824266070]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
toggle_mode = true
|
||||
icon = SubResource("ImageTexture_umaha")
|
||||
|
||||
[node name="Sep2" type="ColorRect" parent="layout/ControlBar"]
|
||||
[node name="Sep" type="ColorRect" parent="layout/ControlBar2/Failing" unique_id=1239759559]
|
||||
custom_minimum_size = Vector2(1, 2.08165e-12)
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Shortcuts" type="Button" parent="layout/ControlBar"]
|
||||
[node name="label" type="Label" parent="layout/ControlBar2/Failing" unique_id=1956836855]
|
||||
layout_mode = 2
|
||||
text = "Fail"
|
||||
|
||||
[node name="failing_value" type="Label" parent="layout/ControlBar2/Failing" unique_id=636519064]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
text = "---"
|
||||
|
||||
[node name="Pending" type="HBoxContainer" parent="layout/ControlBar2" unique_id=1121510368]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Sep" type="ColorRect" parent="layout/ControlBar2/Pending" unique_id=896038473]
|
||||
custom_minimum_size = Vector2(1, 2.08165e-12)
|
||||
layout_mode = 2
|
||||
|
||||
[node name="label" type="Label" parent="layout/ControlBar2/Pending" unique_id=1642849369]
|
||||
layout_mode = 2
|
||||
text = "Risky"
|
||||
|
||||
[node name="pending_value" type="Label" parent="layout/ControlBar2/Pending" unique_id=162567404]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
text = "---"
|
||||
|
||||
[node name="Orphans" type="HBoxContainer" parent="layout/ControlBar2" unique_id=2040966734]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Sep" type="ColorRect" parent="layout/ControlBar2/Orphans" unique_id=153606264]
|
||||
custom_minimum_size = Vector2(1, 2.08165e-12)
|
||||
layout_mode = 2
|
||||
|
||||
[node name="label" type="Label" parent="layout/ControlBar2/Orphans" unique_id=1507291727]
|
||||
layout_mode = 2
|
||||
text = "Orphans"
|
||||
|
||||
[node name="orphans_value" type="Label" parent="layout/ControlBar2/Orphans" unique_id=235887326]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
text = "---"
|
||||
|
||||
[node name="Errors" type="HBoxContainer" parent="layout/ControlBar2" unique_id=1697483051]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Sep" type="ColorRect" parent="layout/ControlBar2/Errors" unique_id=411797244]
|
||||
custom_minimum_size = Vector2(1, 2.08165e-12)
|
||||
layout_mode = 2
|
||||
|
||||
[node name="label" type="Label" parent="layout/ControlBar2/Errors" unique_id=299959536]
|
||||
layout_mode = 2
|
||||
text = "Errors"
|
||||
|
||||
[node name="errors_value" type="Label" parent="layout/ControlBar2/Errors" unique_id=1340004517]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
text = "---"
|
||||
|
||||
[node name="Warnings" type="HBoxContainer" parent="layout/ControlBar2" unique_id=1097631959]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Sep" type="ColorRect" parent="layout/ControlBar2/Warnings" unique_id=763793318]
|
||||
custom_minimum_size = Vector2(1, 2.08165e-12)
|
||||
layout_mode = 2
|
||||
|
||||
[node name="label" type="Label" parent="layout/ControlBar2/Warnings" unique_id=272711725]
|
||||
layout_mode = 2
|
||||
text = "Warnings"
|
||||
|
||||
[node name="warnings_value" type="Label" parent="layout/ControlBar2/Warnings" unique_id=868414665]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
text = "---"
|
||||
|
||||
[node name="CenterContainer" type="CenterContainer" parent="layout/ControlBar2" unique_id=1705687195]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
|
||||
[node name="ExtraButtons" type="HBoxContainer" parent="layout/ControlBar2" unique_id=1132817721]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Sep1" type="ColorRect" parent="layout/ControlBar2/ExtraButtons" unique_id=601143834]
|
||||
custom_minimum_size = Vector2(1, 2.08165e-12)
|
||||
layout_mode = 2
|
||||
|
||||
[node name="RunMode" type="Button" parent="layout/ControlBar2/ExtraButtons" unique_id=1469737845]
|
||||
layout_mode = 2
|
||||
tooltip_text = "Run Mode. Run tests through the editor or externally in a different process."
|
||||
text = "ExN"
|
||||
icon = ExtResource("4_xv2r3")
|
||||
|
||||
[node name="Sep2" type="ColorRect" parent="layout/ControlBar2/ExtraButtons" unique_id=710471274]
|
||||
custom_minimum_size = Vector2(1, 2.08165e-12)
|
||||
layout_mode = 2
|
||||
|
||||
[node name="RunResultsBtn" type="Button" parent="layout/ControlBar2/ExtraButtons" unique_id=385339391]
|
||||
layout_mode = 2
|
||||
tooltip_text = "Show/Hide Result Tree"
|
||||
toggle_mode = true
|
||||
button_pressed = true
|
||||
icon = ExtResource("4_xv2r3")
|
||||
|
||||
[node name="OutputBtn" type="Button" parent="layout/ControlBar2/ExtraButtons" unique_id=1461861149]
|
||||
layout_mode = 2
|
||||
tooltip_text = "Show/Hide Text Output"
|
||||
toggle_mode = true
|
||||
button_pressed = true
|
||||
icon = ExtResource("4_xv2r3")
|
||||
|
||||
[node name="Settings" type="Button" parent="layout/ControlBar2/ExtraButtons" unique_id=1063789901]
|
||||
layout_mode = 2
|
||||
tooltip_text = "GUT Settings"
|
||||
toggle_mode = true
|
||||
button_pressed = true
|
||||
icon = ExtResource("4_xv2r3")
|
||||
|
||||
[node name="Sep3" type="ColorRect" parent="layout/ControlBar2/ExtraButtons" unique_id=650070116]
|
||||
custom_minimum_size = Vector2(1, 2.08165e-12)
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Shortcuts" type="Button" parent="layout/ControlBar2/ExtraButtons" unique_id=545241830]
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 11
|
||||
icon = SubResource("ImageTexture_umaha")
|
||||
tooltip_text = "GUT Shortcuts"
|
||||
icon = ExtResource("4_xv2r3")
|
||||
|
||||
[node name="RSplit" type="HSplitContainer" parent="layout"]
|
||||
[node name="About" type="Button" parent="layout/ControlBar2/ExtraButtons" unique_id=1763800911]
|
||||
layout_mode = 2
|
||||
tooltip_text = "About"
|
||||
text = "A"
|
||||
|
||||
[node name="RSplit" type="HSplitContainer" parent="layout" unique_id=153697410]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
size_flags_vertical = 3
|
||||
collapsed = true
|
||||
|
||||
[node name="sc" type="ScrollContainer" parent="layout/RSplit"]
|
||||
[node name="CResults" type="VBoxContainer" parent="layout/RSplit" unique_id=124140650]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
size_flags_vertical = 3
|
||||
|
||||
[node name="HSplitResults" type="HSplitContainer" parent="layout/RSplit/CResults" unique_id=241208440]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
size_flags_vertical = 3
|
||||
|
||||
[node name="RunResults" parent="layout/RSplit/CResults/HSplitResults" unique_id=1277406275 instance=ExtResource("5")]
|
||||
unique_name_in_owner = true
|
||||
custom_minimum_size = Vector2(255, 255)
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
size_flags_vertical = 3
|
||||
|
||||
[node name="OutputText" parent="layout/RSplit/CResults/HSplitResults" unique_id=1658148044 instance=ExtResource("6")]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
|
||||
[node name="VSplitResults" type="VSplitContainer" parent="layout/RSplit/CResults" unique_id=394710781]
|
||||
unique_name_in_owner = true
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 3
|
||||
|
||||
[node name="sc" type="ScrollContainer" parent="layout/RSplit" unique_id=978940325]
|
||||
custom_minimum_size = Vector2(500, 2.08165e-12)
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 3
|
||||
|
||||
[node name="Settings" type="VBoxContainer" parent="layout/RSplit/sc"]
|
||||
[node name="Settings" type="VBoxContainer" parent="layout/RSplit/sc" unique_id=1724913756]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
size_flags_vertical = 3
|
||||
|
||||
[node name="CResults" type="VBoxContainer" parent="layout/RSplit"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
size_flags_vertical = 3
|
||||
|
||||
[node name="ControlBar" type="HBoxContainer" parent="layout/RSplit/CResults"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Sep2" type="ColorRect" parent="layout/RSplit/CResults/ControlBar"]
|
||||
custom_minimum_size = Vector2(1, 2.08165e-12)
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Light3D" type="Control" parent="layout/RSplit/CResults/ControlBar"]
|
||||
custom_minimum_size = Vector2(30, 30)
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Passing" type="HBoxContainer" parent="layout/RSplit/CResults/ControlBar"]
|
||||
[node name="ShortcutDialog" parent="." unique_id=1224532527 instance=ExtResource("7_srqj5")]
|
||||
size = Vector2i(1512, 1571)
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Sep" type="ColorRect" parent="layout/RSplit/CResults/ControlBar/Passing"]
|
||||
custom_minimum_size = Vector2(1, 2.08165e-12)
|
||||
layout_mode = 2
|
||||
|
||||
[node name="label" type="Label" parent="layout/RSplit/CResults/ControlBar/Passing"]
|
||||
layout_mode = 2
|
||||
text = "Passing"
|
||||
|
||||
[node name="value" type="Label" parent="layout/RSplit/CResults/ControlBar/Passing"]
|
||||
layout_mode = 2
|
||||
text = "---"
|
||||
|
||||
[node name="Failing" type="HBoxContainer" parent="layout/RSplit/CResults/ControlBar"]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Sep" type="ColorRect" parent="layout/RSplit/CResults/ControlBar/Failing"]
|
||||
custom_minimum_size = Vector2(1, 2.08165e-12)
|
||||
layout_mode = 2
|
||||
|
||||
[node name="label" type="Label" parent="layout/RSplit/CResults/ControlBar/Failing"]
|
||||
layout_mode = 2
|
||||
text = "Failing"
|
||||
|
||||
[node name="value" type="Label" parent="layout/RSplit/CResults/ControlBar/Failing"]
|
||||
layout_mode = 2
|
||||
text = "---"
|
||||
|
||||
[node name="Pending" type="HBoxContainer" parent="layout/RSplit/CResults/ControlBar"]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Sep" type="ColorRect" parent="layout/RSplit/CResults/ControlBar/Pending"]
|
||||
custom_minimum_size = Vector2(1, 2.08165e-12)
|
||||
layout_mode = 2
|
||||
|
||||
[node name="label" type="Label" parent="layout/RSplit/CResults/ControlBar/Pending"]
|
||||
layout_mode = 2
|
||||
text = "Pending"
|
||||
|
||||
[node name="value" type="Label" parent="layout/RSplit/CResults/ControlBar/Pending"]
|
||||
layout_mode = 2
|
||||
text = "---"
|
||||
|
||||
[node name="Orphans" type="HBoxContainer" parent="layout/RSplit/CResults/ControlBar"]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Sep" type="ColorRect" parent="layout/RSplit/CResults/ControlBar/Orphans"]
|
||||
custom_minimum_size = Vector2(1, 2.08165e-12)
|
||||
layout_mode = 2
|
||||
|
||||
[node name="label" type="Label" parent="layout/RSplit/CResults/ControlBar/Orphans"]
|
||||
layout_mode = 2
|
||||
text = "Orphans"
|
||||
|
||||
[node name="value" type="Label" parent="layout/RSplit/CResults/ControlBar/Orphans"]
|
||||
layout_mode = 2
|
||||
text = "---"
|
||||
|
||||
[node name="Errors" type="HBoxContainer" parent="layout/RSplit/CResults/ControlBar"]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Sep" type="ColorRect" parent="layout/RSplit/CResults/ControlBar/Errors"]
|
||||
custom_minimum_size = Vector2(1, 2.08165e-12)
|
||||
layout_mode = 2
|
||||
|
||||
[node name="label" type="Label" parent="layout/RSplit/CResults/ControlBar/Errors"]
|
||||
layout_mode = 2
|
||||
text = "Errors"
|
||||
|
||||
[node name="value" type="Label" parent="layout/RSplit/CResults/ControlBar/Errors"]
|
||||
layout_mode = 2
|
||||
text = "---"
|
||||
|
||||
[node name="Warnings" type="HBoxContainer" parent="layout/RSplit/CResults/ControlBar"]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Sep" type="ColorRect" parent="layout/RSplit/CResults/ControlBar/Warnings"]
|
||||
custom_minimum_size = Vector2(1, 2.08165e-12)
|
||||
layout_mode = 2
|
||||
|
||||
[node name="label" type="Label" parent="layout/RSplit/CResults/ControlBar/Warnings"]
|
||||
layout_mode = 2
|
||||
text = "Warnings"
|
||||
|
||||
[node name="value" type="Label" parent="layout/RSplit/CResults/ControlBar/Warnings"]
|
||||
layout_mode = 2
|
||||
text = "---"
|
||||
|
||||
[node name="CenterContainer" type="CenterContainer" parent="layout/RSplit/CResults/ControlBar"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
|
||||
[node name="TabBar" type="HSplitContainer" parent="layout/RSplit/CResults"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
size_flags_vertical = 3
|
||||
|
||||
[node name="RunResults" parent="layout/RSplit/CResults/TabBar" instance=ExtResource("5")]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
size_flags_vertical = 3
|
||||
|
||||
[node name="OutputText" parent="layout/RSplit/CResults/TabBar" instance=ExtResource("6")]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
|
||||
[node name="BottomPanelShortcuts" parent="." instance=ExtResource("2")]
|
||||
[node name="ShellOutOptions" parent="." unique_id=1974075127 instance=ExtResource("7_xv2r3")]
|
||||
size = Vector2i(1300, 1336)
|
||||
visible = false
|
||||
|
||||
[connection signal="pressed" from="layout/ControlBar/RunAll" to="." method="_on_RunAll_pressed"]
|
||||
[connection signal="run_tests" from="layout/ControlBar/RunAtCursor" to="." method="_on_RunAtCursor_run_tests"]
|
||||
[connection signal="pressed" from="layout/ControlBar/RunResultsBtn" to="." method="_on_RunResultsBtn_pressed"]
|
||||
[connection signal="pressed" from="layout/ControlBar/OutputBtn" to="." method="_on_OutputBtn_pressed"]
|
||||
[connection signal="pressed" from="layout/ControlBar/Settings" to="." method="_on_Settings_pressed"]
|
||||
[connection signal="pressed" from="layout/ControlBar/Shortcuts" to="." method="_on_Shortcuts_pressed"]
|
||||
[connection signal="draw" from="layout/RSplit/CResults/ControlBar/Light3D" to="." method="_on_Light_draw"]
|
||||
[connection signal="visibility_changed" from="BottomPanelShortcuts" to="." method="_on_bottom_panel_shortcuts_visibility_changed"]
|
||||
[connection signal="pressed" from="layout/ControlBar/MakeFloating" to="." method="_on_to_window_pressed"]
|
||||
[connection signal="pressed" from="layout/ControlBar/HorizLayout" to="." method="_on_horiz_layout_pressed"]
|
||||
[connection signal="pressed" from="layout/ControlBar/VertLayout" to="." method="_on_vert_layout_pressed"]
|
||||
[connection signal="draw" from="layout/ControlBar2/StatusIndicator" to="." method="_on_Light_draw"]
|
||||
[connection signal="pressed" from="layout/ControlBar2/ExtraButtons/RunMode" to="." method="_on_run_mode_pressed"]
|
||||
[connection signal="pressed" from="layout/ControlBar2/ExtraButtons/RunResultsBtn" to="." method="_on_RunResultsBtn_pressed"]
|
||||
[connection signal="pressed" from="layout/ControlBar2/ExtraButtons/OutputBtn" to="." method="_on_OutputBtn_pressed"]
|
||||
[connection signal="pressed" from="layout/ControlBar2/ExtraButtons/Settings" to="." method="_on_Settings_pressed"]
|
||||
[connection signal="pressed" from="layout/ControlBar2/ExtraButtons/Shortcuts" to="." method="_on_Shortcuts_pressed"]
|
||||
[connection signal="pressed" from="layout/ControlBar2/ExtraButtons/About" to="." method="_on_about_pressed"]
|
||||
[connection signal="confirmed" from="ShortcutDialog" to="." method="_on_sortcut_dialog_confirmed"]
|
||||
[connection signal="confirmed" from="ShellOutOptions" to="." method="_on_shell_out_options_confirmed"]
|
||||
|
|
|
|||
|
|
@ -9,8 +9,7 @@ var GutConfigGui = load('res://addons/gut/gui/gut_config_gui.gd')
|
|||
|
||||
var _config = GutConfig.new()
|
||||
var _config_gui = null
|
||||
var _gut_runner = GutRunnerScene.instantiate()
|
||||
var _has_connected = false
|
||||
var _gut_runner = null
|
||||
var _tree_root : TreeItem = null
|
||||
|
||||
var _script_icon = load('res://addons/gut/images/Script.svg')
|
||||
|
|
@ -43,6 +42,7 @@ func _ready():
|
|||
if Engine.is_editor_hint():
|
||||
return
|
||||
|
||||
_gut_runner = GutRunnerScene.instantiate()
|
||||
$Bg.color = bg_color
|
||||
_ctrls.tabs.set_tab_title(0, 'Tests')
|
||||
_ctrls.tabs.set_tab_title(1, 'Settings')
|
||||
|
|
@ -260,6 +260,10 @@ func run_tests(options = null):
|
|||
_config.options = _config_gui.get_options(_config.options)
|
||||
else:
|
||||
_config.options = options
|
||||
|
||||
# We ar running from within the game, so we should not exit, ever.
|
||||
_config.options.should_exit_on_success = false
|
||||
_config.options.should_exit = false
|
||||
|
||||
_gut_runner.get_gut().get_test_collector().clear()
|
||||
_gut_runner.set_gut_config(_config)
|
||||
|
|
|
|||
|
|
@ -1 +1 @@
|
|||
uid://dxbu5m7ovktb8
|
||||
uid://cqlvpwidawld6
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
[gd_scene load_steps=2 format=3 uid="uid://4jb53yqktyfg"]
|
||||
|
||||
[ext_resource type="Script" path="res://addons/gut/gui/GutControl.gd" id="1_eprql"]
|
||||
[ext_resource type="Script" uid="uid://cqlvpwidawld6" path="res://addons/gut/gui/GutControl.gd" id="1_eprql"]
|
||||
|
||||
[node name="GutControl" type="Control"]
|
||||
layout_mode = 3
|
||||
|
|
|
|||
36
addons/gut/gui/GutLogo.tscn
Normal file
36
addons/gut/gui/GutLogo.tscn
Normal file
|
|
@ -0,0 +1,36 @@
|
|||
[gd_scene load_steps=4 format=3 uid="uid://bjkn8mhx2fmt1"]
|
||||
|
||||
[ext_resource type="Script" uid="uid://b8lvgepb64m8t" path="res://addons/gut/gui/gut_logo.gd" id="1_ba6lh"]
|
||||
[ext_resource type="Texture2D" uid="uid://dyxbmyvpkkcvs" path="res://addons/gut/images/GutIconV2_base.png" id="2_ba6lh"]
|
||||
[ext_resource type="Texture2D" uid="uid://dx0yxxn5q7doc" path="res://addons/gut/images/eyey.png" id="3_rc8fb"]
|
||||
|
||||
[node name="Logo" type="Node2D"]
|
||||
script = ExtResource("1_ba6lh")
|
||||
|
||||
[node name="BaseLogo" type="Sprite2D" parent="."]
|
||||
scale = Vector2(0.5, 0.5)
|
||||
texture = ExtResource("2_ba6lh")
|
||||
|
||||
[node name="LeftEye" type="Sprite2D" parent="BaseLogo"]
|
||||
visible = false
|
||||
position = Vector2(-238, 16)
|
||||
texture = ExtResource("3_rc8fb")
|
||||
|
||||
[node name="RightEye" type="Sprite2D" parent="BaseLogo"]
|
||||
visible = false
|
||||
position = Vector2(239, 16)
|
||||
texture = ExtResource("3_rc8fb")
|
||||
|
||||
[node name="ResetTimer" type="Timer" parent="."]
|
||||
wait_time = 5.0
|
||||
one_shot = true
|
||||
|
||||
[node name="FaceButton" type="Button" parent="."]
|
||||
modulate = Color(1, 1, 1, 0)
|
||||
offset_left = -141.0
|
||||
offset_top = -113.0
|
||||
offset_right = 140.0
|
||||
offset_bottom = 175.0
|
||||
|
||||
[connection signal="timeout" from="ResetTimer" to="." method="_on_reset_timer_timeout"]
|
||||
[connection signal="pressed" from="FaceButton" to="." method="_on_face_button_pressed"]
|
||||
|
|
@ -28,12 +28,15 @@ var result_json_path = null
|
|||
var lgr = GutUtils.get_logger()
|
||||
var gut_config = null
|
||||
|
||||
var error_tracker = GutUtils.get_error_tracker()
|
||||
|
||||
var _hid_gut = null;
|
||||
# Lazy loaded gut instance. Settable for testing purposes.
|
||||
var gut = _hid_gut :
|
||||
get:
|
||||
if(_hid_gut == null):
|
||||
_hid_gut = Gut.new()
|
||||
_hid_gut = Gut.new(lgr)
|
||||
_hid_gut.error_tracker = error_tracker
|
||||
return _hid_gut
|
||||
set(val):
|
||||
_hid_gut = val
|
||||
|
|
@ -94,7 +97,8 @@ func _write_results_for_gut_panel():
|
|||
|
||||
func _handle_quit(should_exit, should_exit_on_success, override_exit_code=EXIT_OK):
|
||||
var quitting_time = should_exit or \
|
||||
(should_exit_on_success and gut.get_fail_count() == 0)
|
||||
(should_exit_on_success and gut.get_fail_count() == 0) or \
|
||||
GutUtils.is_headless()
|
||||
|
||||
if(!quitting_time):
|
||||
if(should_exit_on_success):
|
||||
|
|
@ -122,6 +126,8 @@ func _end_run(override_exit_code=EXIT_OK):
|
|||
if(_ran_from_editor):
|
||||
_write_results_for_gut_panel()
|
||||
|
||||
GutErrorTracker.deregister_logger(error_tracker)
|
||||
|
||||
_handle_quit(gut_config.options.should_exit,
|
||||
gut_config.options.should_exit_on_success,
|
||||
override_exit_code)
|
||||
|
|
@ -157,7 +163,9 @@ func run_tests(show_gui=true):
|
|||
_setup_gui(show_gui)
|
||||
|
||||
if(gut_config.options.dirs.size() + gut_config.options.tests.size() == 0):
|
||||
var err_text = "You do not have any directories configured, so GUT doesn't know where to find the tests. Tell GUT where to find the tests and GUT shall run the tests."
|
||||
var err_text = "You do not have any directories configured, so GUT " + \
|
||||
"doesn't know where to find the tests. Tell GUT where to find the " + \
|
||||
"tests and GUT shall run the tests."
|
||||
lgr.error(err_text)
|
||||
push_error(err_text)
|
||||
_end_run(EXIT_ERROR)
|
||||
|
|
@ -178,11 +186,15 @@ func run_tests(show_gui=true):
|
|||
else:
|
||||
add_child(gut)
|
||||
|
||||
gut.end_run.connect(_on_tests_finished)
|
||||
if(!gut.end_run.is_connected(_on_tests_finished)):
|
||||
gut.end_run.connect(_on_tests_finished)
|
||||
|
||||
gut_config.apply_options(gut)
|
||||
var run_rest_of_scripts = gut_config.options.unit_test_name == ''
|
||||
if GutUtils.is_headless():
|
||||
gut._ignore_pause_before_teardown = true
|
||||
|
||||
var run_rest_of_scripts = gut_config.options.unit_test_name == ''
|
||||
GutErrorTracker.register_logger(error_tracker)
|
||||
gut.test_scripts(run_rest_of_scripts)
|
||||
|
||||
|
||||
|
|
@ -199,6 +211,7 @@ func quit(exit_code):
|
|||
# Sometimes quitting takes a few seconds. This gives some indicator
|
||||
# of what is going on.
|
||||
_gui.set_title("Exiting")
|
||||
|
||||
await get_tree().process_frame
|
||||
|
||||
lgr.info(str('Exiting with code ', exit_code))
|
||||
|
|
|
|||
|
|
@ -1 +1 @@
|
|||
uid://bayjc3x1exeie
|
||||
uid://eg8k46gd42a4
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
[gd_scene load_steps=3 format=3 uid="uid://bqy3ikt6vu4b5"]
|
||||
|
||||
[ext_resource type="Script" path="res://addons/gut/gui/GutRunner.gd" id="1"]
|
||||
[ext_resource type="Script" uid="uid://eg8k46gd42a4" path="res://addons/gut/gui/GutRunner.gd" id="1"]
|
||||
[ext_resource type="PackedScene" uid="uid://m28heqtswbuq" path="res://addons/gut/GutScene.tscn" id="2_6ruxb"]
|
||||
|
||||
[node name="GutRunner" type="Node2D"]
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
|
||||
[ext_resource type="Theme" uid="uid://cstkhwkpajvqu" path="res://addons/gut/gui/GutSceneTheme.tres" id="1_farmq"]
|
||||
[ext_resource type="FontFile" uid="uid://bnh0lslf4yh87" path="res://addons/gut/fonts/CourierPrime-Regular.ttf" id="2_a2e2l"]
|
||||
[ext_resource type="Script" path="res://addons/gut/gui/gut_gui.gd" id="2_eokrf"]
|
||||
[ext_resource type="Script" uid="uid://blvhsbnsvfyow" path="res://addons/gut/gui/gut_gui.gd" id="2_eokrf"]
|
||||
[ext_resource type="PackedScene" uid="uid://bvrqqgjpyouse" path="res://addons/gut/gui/ResizeHandle.tscn" id="4_xrhva"]
|
||||
|
||||
[node name="Min" type="Panel"]
|
||||
|
|
|
|||
|
|
@ -1,7 +1,7 @@
|
|||
[gd_scene load_steps=5 format=3 uid="uid://duxblir3vu8x7"]
|
||||
|
||||
[ext_resource type="Theme" uid="uid://cstkhwkpajvqu" path="res://addons/gut/gui/GutSceneTheme.tres" id="1_5hlsm"]
|
||||
[ext_resource type="Script" path="res://addons/gut/gui/gut_gui.gd" id="2_fue6q"]
|
||||
[ext_resource type="Script" uid="uid://blvhsbnsvfyow" path="res://addons/gut/gui/gut_gui.gd" id="2_fue6q"]
|
||||
[ext_resource type="FontFile" uid="uid://bnh0lslf4yh87" path="res://addons/gut/fonts/CourierPrime-Regular.ttf" id="2_u5uc1"]
|
||||
[ext_resource type="PackedScene" uid="uid://bvrqqgjpyouse" path="res://addons/gut/gui/ResizeHandle.tscn" id="4_2r8a8"]
|
||||
|
||||
|
|
@ -158,17 +158,19 @@ theme_override_font_sizes/font_size = 14
|
|||
text = "test_this_thing.gd"
|
||||
text_overrun_behavior = 3
|
||||
|
||||
[node name="Spacer1" type="CenterContainer" parent="MainBox/HBoxContainer/VBoxContainer/ControlBox"]
|
||||
visible = false
|
||||
[node name="Buttons" type="VBoxContainer" parent="MainBox/HBoxContainer/VBoxContainer/ControlBox"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 10
|
||||
|
||||
[node name="Continue" type="Button" parent="MainBox/HBoxContainer/VBoxContainer/ControlBox"]
|
||||
[node name="Continue" type="Button" parent="MainBox/HBoxContainer/VBoxContainer/ControlBox/Buttons"]
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 4
|
||||
text = "Continue
|
||||
"
|
||||
|
||||
[node name="WordWrap" type="CheckButton" parent="MainBox/HBoxContainer/VBoxContainer/ControlBox/Buttons"]
|
||||
layout_mode = 2
|
||||
text = "Word Wrap"
|
||||
|
||||
[node name="S3" type="CenterContainer" parent="MainBox/HBoxContainer/VBoxContainer/ControlBox"]
|
||||
custom_minimum_size = Vector2(5, 0)
|
||||
layout_mode = 2
|
||||
|
|
|
|||
|
|
@ -89,6 +89,18 @@ var _user_prefs = GutEditorGlobals.user_prefs
|
|||
var _font_name_pctrl = null
|
||||
var _font_size_pctrl = null
|
||||
|
||||
var keywords = [
|
||||
['Failed', Color.RED],
|
||||
['Passed', Color.GREEN],
|
||||
['Pending', Color.YELLOW],
|
||||
['Risky', Color.YELLOW],
|
||||
['Orphans', Color.YELLOW],
|
||||
['WARNING', Color.YELLOW],
|
||||
['ERROR', Color.RED],
|
||||
['ExpectedError', Color.LIGHT_BLUE],
|
||||
]
|
||||
|
||||
|
||||
# Automatically used when running the OutputText scene from the editor. Changes
|
||||
# to this method only affect test-running the control through the editor.
|
||||
func _test_running_setup():
|
||||
|
|
@ -110,6 +122,9 @@ func _test_running_setup():
|
|||
|
||||
|
||||
func _ready():
|
||||
if(get_parent() is SubViewport):
|
||||
return
|
||||
|
||||
_sr.set_text_edit(_ctrls.output)
|
||||
_ctrls.use_colors.icon = get_theme_icon('RichTextEffect', 'EditorIcons')
|
||||
_ctrls.show_search.icon = get_theme_icon('Search', 'EditorIcons')
|
||||
|
|
@ -127,7 +142,7 @@ func _ready():
|
|||
|
||||
|
||||
func _add_other_ctrls():
|
||||
var fname = 'CourierNew'
|
||||
var fname = GutUtils.gut_fonts.DEFAULT_CUSTOM_FONT_NAME
|
||||
if(_user_prefs != null):
|
||||
fname = _user_prefs.output_font_name.value
|
||||
_font_name_pctrl = PanelControls.SelectControl.new('Font', fname, GutUtils.avail_fonts,
|
||||
|
|
@ -170,15 +185,6 @@ func _create_highlighter(default_color=Color(1, 1, 1, 1)):
|
|||
to_return.symbol_color = default_color
|
||||
to_return.member_variable_color = default_color
|
||||
|
||||
var keywords = [
|
||||
['Failed', Color.RED],
|
||||
['Passed', Color.GREEN],
|
||||
['Pending', Color.YELLOW],
|
||||
['Orphans', Color.YELLOW],
|
||||
['WARNING', Color.YELLOW],
|
||||
['ERROR', Color.RED]
|
||||
]
|
||||
|
||||
for keyword in keywords:
|
||||
to_return.add_keyword_color(keyword[0], keyword[1])
|
||||
|
||||
|
|
@ -187,13 +193,6 @@ func _create_highlighter(default_color=Color(1, 1, 1, 1)):
|
|||
|
||||
func _setup_colors():
|
||||
_ctrls.output.clear()
|
||||
|
||||
var f_color = null
|
||||
if (_ctrls.output.theme == null) :
|
||||
f_color = get_theme_color("font_color")
|
||||
else :
|
||||
f_color = _ctrls.output.theme.font_color
|
||||
|
||||
_highlighter = _create_highlighter()
|
||||
_ctrls.output.queue_redraw()
|
||||
|
||||
|
|
@ -300,31 +299,19 @@ func clear():
|
|||
_ctrls.output.text = ''
|
||||
|
||||
|
||||
func _set_font(font_name, custom_name):
|
||||
var rtl = _ctrls.output
|
||||
if(font_name == null):
|
||||
rtl.remove_theme_font_override(custom_name)
|
||||
else:
|
||||
var dyn_font = FontFile.new()
|
||||
dyn_font.load_dynamic_font('res://addons/gut/fonts/' + font_name + '.ttf')
|
||||
rtl.add_theme_font_override(custom_name, dyn_font)
|
||||
func _set_font(custom_name, theme_font_name):
|
||||
var font = GutUtils.gut_fonts.get_font_for_theme_font_name(theme_font_name, custom_name)
|
||||
_ctrls.output.add_theme_font_override(theme_font_name, font)
|
||||
|
||||
|
||||
func set_all_fonts(base_name):
|
||||
_font_name = GutUtils.nvl(base_name, 'Default')
|
||||
|
||||
if(base_name == 'Default'):
|
||||
_set_font(null, 'font')
|
||||
_set_font(null, 'normal_font')
|
||||
_set_font(null, 'bold_font')
|
||||
_set_font(null, 'italics_font')
|
||||
_set_font(null, 'bold_italics_font')
|
||||
else:
|
||||
_set_font(base_name + '-Regular', 'font')
|
||||
_set_font(base_name + '-Regular', 'normal_font')
|
||||
_set_font(base_name + '-Bold', 'bold_font')
|
||||
_set_font(base_name + '-Italic', 'italics_font')
|
||||
_set_font(base_name + '-BoldItalic', 'bold_italics_font')
|
||||
_set_font(base_name, 'font')
|
||||
_set_font(base_name, 'normal_font')
|
||||
_set_font(base_name, 'bold_font')
|
||||
_set_font(base_name, 'italics_font')
|
||||
_set_font(base_name, 'bold_italics_font')
|
||||
|
||||
|
||||
func set_font_size(new_size):
|
||||
|
|
|
|||
|
|
@ -1 +1 @@
|
|||
uid://ccdonk2lpn1d1
|
||||
uid://cax5phqs8acmu
|
||||
|
|
|
|||
File diff suppressed because one or more lines are too long
|
|
@ -1 +1 @@
|
|||
uid://dp618d4ofjpv1
|
||||
uid://duf6rfdqr6yoc
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
[gd_scene load_steps=2 format=3 uid="uid://bvrqqgjpyouse"]
|
||||
|
||||
[ext_resource type="Script" path="res://addons/gut/gui/ResizeHandle.gd" id="1_oi5ed"]
|
||||
[ext_resource type="Script" uid="uid://duf6rfdqr6yoc" path="res://addons/gut/gui/ResizeHandle.gd" id="1_oi5ed"]
|
||||
|
||||
[node name="ResizeHandle" type="ColorRect"]
|
||||
custom_minimum_size = Vector2(20, 20)
|
||||
|
|
|
|||
|
|
@ -1,5 +1,5 @@
|
|||
@tool
|
||||
extends Control
|
||||
extends Tree
|
||||
|
||||
var _show_orphans = true
|
||||
var show_orphans = true :
|
||||
|
|
@ -18,83 +18,55 @@ var _icons = {
|
|||
green = load('res://addons/gut/images/green.png'),
|
||||
yellow = load('res://addons/gut/images/yellow.png'),
|
||||
}
|
||||
const _col_1_bg_color = Color(0, 0, 0, .1)
|
||||
|
||||
@export var script_entry_color : Color = Color(0, 0, 0, .2) :
|
||||
set(val):
|
||||
if(val != null):
|
||||
script_entry_color = val
|
||||
@export var column_0_color : Color = Color(1, 1, 1, 0) :
|
||||
set(val):
|
||||
if(val != null):
|
||||
column_0_color = val
|
||||
@export var column_1_color : Color = Color(0, 0, 0, .2):
|
||||
set(val):
|
||||
if(val != null):
|
||||
column_1_color = val
|
||||
|
||||
|
||||
|
||||
var _max_icon_width = 10
|
||||
var _root : TreeItem
|
||||
|
||||
@onready var _ctrls = {
|
||||
tree = $Tree,
|
||||
lbl_overlay = $Tree/TextOverlay
|
||||
}
|
||||
|
||||
@onready var lbl_overlay = $TextOverlay
|
||||
|
||||
|
||||
signal selected(script_path, inner_class, test_name, line_number)
|
||||
|
||||
func _debug_ready():
|
||||
hide_passing = false
|
||||
load_json_file('user://gut_temp_directory/gut_editor.json')
|
||||
|
||||
|
||||
func _ready():
|
||||
_root = create_item()
|
||||
set_hide_root(true)
|
||||
columns = 2
|
||||
set_column_expand(0, true)
|
||||
set_column_expand_ratio(0, 5)
|
||||
|
||||
set_column_expand_ratio(1, 1)
|
||||
set_column_expand(1, true)
|
||||
|
||||
item_selected.connect(_on_tree_item_selected)
|
||||
|
||||
if(get_parent() == get_tree().root):
|
||||
_debug_ready()
|
||||
|
||||
|
||||
signal item_selected(script_path, inner_class, test_name, line_number)
|
||||
# -------------------
|
||||
# Private
|
||||
# -------------------
|
||||
func _ready():
|
||||
_root = _ctrls.tree.create_item()
|
||||
_root = _ctrls.tree.create_item()
|
||||
_ctrls.tree.set_hide_root(true)
|
||||
_ctrls.tree.columns = 2
|
||||
_ctrls.tree.set_column_expand(0, true)
|
||||
_ctrls.tree.set_column_expand(1, false)
|
||||
_ctrls.tree.set_column_clip_content(0, true)
|
||||
|
||||
$Tree.item_selected.connect(_on_tree_item_selected)
|
||||
|
||||
if(get_parent() == get_tree().root):
|
||||
_test_running_setup()
|
||||
|
||||
func _test_running_setup():
|
||||
load_json_file('user://.gut_editor.json')
|
||||
|
||||
|
||||
func _on_tree_item_selected():
|
||||
var item = _ctrls.tree.get_selected()
|
||||
var item_meta = item.get_metadata(0)
|
||||
var item_type = null
|
||||
|
||||
# Only select the left side of the tree item, cause I like that better.
|
||||
# you can still click the right, but only the left gets highlighted.
|
||||
if(item.is_selected(1)):
|
||||
item.deselect(1)
|
||||
item.select(0)
|
||||
|
||||
if(item_meta == null):
|
||||
return
|
||||
else:
|
||||
item_type = item_meta.type
|
||||
|
||||
var script_path = '';
|
||||
var line = -1;
|
||||
var test_name = ''
|
||||
var inner_class = ''
|
||||
|
||||
if(item_type == 'test'):
|
||||
var s_item = item.get_parent()
|
||||
script_path = s_item.get_metadata(0)['path']
|
||||
inner_class = s_item.get_metadata(0)['inner_class']
|
||||
line = -1
|
||||
test_name = item.get_text(0)
|
||||
elif(item_type == 'assert'):
|
||||
var s_item = item.get_parent().get_parent()
|
||||
script_path = s_item.get_metadata(0)['path']
|
||||
inner_class = s_item.get_metadata(0)['inner_class']
|
||||
line = _get_line_number_from_assert_msg(item.get_text(0))
|
||||
test_name = item.get_parent().get_text(0)
|
||||
elif(item_type == 'script'):
|
||||
script_path = item.get_metadata(0)['path']
|
||||
if(item.get_parent() != _root):
|
||||
inner_class = item.get_text(0)
|
||||
line = -1
|
||||
test_name = ''
|
||||
else:
|
||||
return
|
||||
|
||||
item_selected.emit(script_path, inner_class, test_name, line)
|
||||
|
||||
|
||||
func _get_line_number_from_assert_msg(msg):
|
||||
var line = -1
|
||||
if(msg.find('at line') > 0):
|
||||
|
|
@ -142,17 +114,7 @@ func _add_script_tree_item(script_path, script_json):
|
|||
if(parent == null):
|
||||
parent = _add_script_tree_item(path_info.path, {})
|
||||
|
||||
parent.get_metadata(0).inner_tests += script_json['props']['tests']
|
||||
parent.get_metadata(0).inner_passing += script_json['props']['tests']
|
||||
parent.get_metadata(0).inner_passing -= script_json['props']['failures']
|
||||
parent.get_metadata(0).inner_passing -= script_json['props']['pending']
|
||||
|
||||
var total_text = str("All ", parent.get_metadata(0).inner_tests, " passed")
|
||||
if(parent.get_metadata(0).inner_passing != parent.get_metadata(0).inner_tests):
|
||||
total_text = str(parent.get_metadata(0).inner_passing, '/', parent.get_metadata(0).inner_tests, ' passed.')
|
||||
parent.set_text(1, total_text)
|
||||
|
||||
var item = _ctrls.tree.create_item(parent)
|
||||
var item = create_item(parent)
|
||||
item.set_text(0, item_text)
|
||||
var meta = {
|
||||
"type":"script",
|
||||
|
|
@ -163,51 +125,46 @@ func _add_script_tree_item(script_path, script_json):
|
|||
"inner_tests":0
|
||||
}
|
||||
item.set_metadata(0, meta)
|
||||
item.set_custom_bg_color(1, _col_1_bg_color)
|
||||
item.set_custom_bg_color(0, script_entry_color)
|
||||
item.set_custom_bg_color(1, script_entry_color)
|
||||
|
||||
return item
|
||||
|
||||
|
||||
func _add_assert_item(text, icon, parent_item):
|
||||
# print(' * adding assert')
|
||||
var assert_item = _ctrls.tree.create_item(parent_item)
|
||||
var assert_item = create_item(parent_item)
|
||||
assert_item.set_icon_max_width(0, _max_icon_width)
|
||||
assert_item.set_text(0, text)
|
||||
assert_item.set_metadata(0, {"type":"assert"})
|
||||
assert_item.set_icon(0, icon)
|
||||
assert_item.set_custom_bg_color(1, _col_1_bg_color)
|
||||
assert_item.set_custom_bg_color(0, column_0_color)
|
||||
assert_item.set_custom_bg_color(1, column_1_color)
|
||||
|
||||
return assert_item
|
||||
|
||||
|
||||
func _add_test_tree_item(test_name, test_json, script_item):
|
||||
# print(' * adding test ', test_name)
|
||||
var no_orphans_to_show = !_show_orphans or (_show_orphans and test_json.orphans == 0)
|
||||
var no_orphans_to_show = !_show_orphans or (_show_orphans and test_json.orphan_count == 0)
|
||||
if(_hide_passing and test_json['status'] == 'pass' and no_orphans_to_show):
|
||||
return
|
||||
|
||||
var item = _ctrls.tree.create_item(script_item)
|
||||
var item = create_item(script_item)
|
||||
var status = test_json['status']
|
||||
var meta = {"type":"test", "json":test_json}
|
||||
|
||||
item.set_text(0, test_name)
|
||||
item.set_text(1, status)
|
||||
item.set_text_alignment(1, HORIZONTAL_ALIGNMENT_RIGHT)
|
||||
item.set_custom_bg_color(1, _col_1_bg_color)
|
||||
item.set_custom_bg_color(1, column_1_color)
|
||||
|
||||
item.set_metadata(0, meta)
|
||||
item.set_icon_max_width(0, _max_icon_width)
|
||||
|
||||
var orphan_text = 'orphans'
|
||||
if(test_json.orphans == 1):
|
||||
orphan_text = 'orphan'
|
||||
orphan_text = str(test_json.orphans, ' ', orphan_text)
|
||||
item.set_custom_bg_color(0, column_0_color)
|
||||
|
||||
if(status == 'pass' and no_orphans_to_show):
|
||||
item.set_icon(0, _icons.green)
|
||||
elif(status == 'pass' and !no_orphans_to_show):
|
||||
item.set_icon(0, _icons.yellow)
|
||||
item.set_text(1, orphan_text)
|
||||
elif(status == 'fail'):
|
||||
item.set_icon(0, _icons.red)
|
||||
else:
|
||||
|
|
@ -223,8 +180,18 @@ func _add_test_tree_item(test_name, test_json, script_item):
|
|||
for pending in test_json.pending:
|
||||
_add_assert_item("pending: " + pending.replace("\n", ''), _icons.yellow, item)
|
||||
|
||||
if(status != 'pass' and !no_orphans_to_show):
|
||||
_add_assert_item(orphan_text, _icons.yellow, item)
|
||||
var orphan_text = 'orphans'
|
||||
if(test_json.orphan_count == 1):
|
||||
orphan_text = 'orphan'
|
||||
orphan_text = str(int(test_json.orphan_count), ' ', orphan_text)
|
||||
|
||||
if(!no_orphans_to_show):
|
||||
var orphan_item = _add_assert_item(orphan_text, _icons.yellow, item)
|
||||
for o in test_json.orphans:
|
||||
var orphan_entry = create_item(orphan_item)
|
||||
orphan_entry.set_text(0, o)
|
||||
orphan_entry.set_custom_bg_color(0, column_0_color)
|
||||
orphan_entry.set_custom_bg_color(1, column_1_color)
|
||||
|
||||
return item
|
||||
|
||||
|
|
@ -243,13 +210,17 @@ func _add_script_to_tree(key, script_json):
|
|||
t_item.collapsed = true
|
||||
|
||||
if(s_item.get_children().size() == 0):
|
||||
s_item.free()
|
||||
if(script_json.props.skipped):
|
||||
_add_assert_item("Skipped", _icons.yellow, s_item)
|
||||
s_item.set_text(1, "Skipped")
|
||||
else:
|
||||
s_item.free()
|
||||
else:
|
||||
var total_text = str('All ', test_keys.size(), ' passed')
|
||||
if(bad_count == 0):
|
||||
s_item.collapsed = true
|
||||
else:
|
||||
total_text = str(test_keys.size() - bad_count, '/', test_keys.size(), ' passed')
|
||||
total_text = str(int(test_keys.size() - bad_count), '/', int(test_keys.size()), ' passed')
|
||||
s_item.set_text(1, total_text)
|
||||
|
||||
|
||||
|
|
@ -276,15 +247,60 @@ func _load_result_tree(j):
|
|||
|
||||
var add_count = 0
|
||||
for key in script_keys:
|
||||
if(scripts[key]['props']['tests'] > 0):
|
||||
add_count += 1
|
||||
_add_script_to_tree(key, scripts[key])
|
||||
add_count += 1
|
||||
_add_script_to_tree(key, scripts[key])
|
||||
|
||||
_free_childless_scripts()
|
||||
if(add_count == 0):
|
||||
add_centered_text('Nothing was run')
|
||||
else:
|
||||
_show_all_passed()
|
||||
# -------------------
|
||||
# Events
|
||||
# -------------------
|
||||
func _on_tree_item_selected():
|
||||
var item = get_selected()
|
||||
var item_meta = item.get_metadata(0)
|
||||
var item_type = null
|
||||
|
||||
# Only select the left side of the tree item, cause I like that better.
|
||||
# you can still click the right, but only the left gets highlighted.
|
||||
if(item.is_selected(1)):
|
||||
item.deselect(1)
|
||||
item.select(0)
|
||||
|
||||
if(item_meta == null):
|
||||
return
|
||||
else:
|
||||
item_type = item_meta.type
|
||||
|
||||
var script_path = '';
|
||||
var line = -1;
|
||||
var test_name = ''
|
||||
var inner_class = ''
|
||||
|
||||
if(item_type == 'test'):
|
||||
var s_item = item.get_parent()
|
||||
script_path = s_item.get_metadata(0)['path']
|
||||
inner_class = s_item.get_metadata(0)['inner_class']
|
||||
line = -1
|
||||
test_name = item.get_text(0)
|
||||
elif(item_type == 'assert'):
|
||||
var s_item = item.get_parent().get_parent()
|
||||
script_path = s_item.get_metadata(0)['path']
|
||||
inner_class = s_item.get_metadata(0)['inner_class']
|
||||
line = _get_line_number_from_assert_msg(item.get_text(0))
|
||||
test_name = item.get_parent().get_text(0)
|
||||
elif(item_type == 'script'):
|
||||
script_path = item.get_metadata(0)['path']
|
||||
if(item.get_parent() != _root):
|
||||
inner_class = item.get_text(0)
|
||||
line = -1
|
||||
test_name = ''
|
||||
else:
|
||||
return
|
||||
|
||||
selected.emit(script_path, inner_class, test_name, line)
|
||||
|
||||
|
||||
# -------------------
|
||||
|
|
@ -313,26 +329,29 @@ func load_json_file(path):
|
|||
|
||||
func load_json_results(j):
|
||||
clear()
|
||||
if(_root == null):
|
||||
_root = create_item()
|
||||
|
||||
_load_result_tree(j)
|
||||
|
||||
|
||||
func clear():
|
||||
_ctrls.tree.clear()
|
||||
_root = _ctrls.tree.create_item()
|
||||
#func clear():
|
||||
#clear()
|
||||
#_root = create_item()
|
||||
|
||||
|
||||
func set_summary_min_width(width):
|
||||
_ctrls.tree.set_column_custom_minimum_width(1, width)
|
||||
set_column_custom_minimum_width(1, width)
|
||||
|
||||
|
||||
func add_centered_text(t):
|
||||
_ctrls.lbl_overlay.visible = true
|
||||
_ctrls.lbl_overlay.text = t
|
||||
lbl_overlay.visible = true
|
||||
lbl_overlay.text = t
|
||||
|
||||
|
||||
func clear_centered_text():
|
||||
_ctrls.lbl_overlay.visible = false
|
||||
_ctrls.lbl_overlay.text = ''
|
||||
lbl_overlay.visible = false
|
||||
lbl_overlay.text = ''
|
||||
|
||||
|
||||
func collapse_all():
|
||||
|
|
@ -347,7 +366,3 @@ func set_collapsed_on_all(item, value):
|
|||
item.set_collapsed_recursive(value)
|
||||
if(item == _root and value):
|
||||
item.set_collapsed(false)
|
||||
|
||||
|
||||
func get_selected():
|
||||
return _ctrls.tree.get_selected()
|
||||
|
|
|
|||
|
|
@ -1 +1 @@
|
|||
uid://dmfojusal8t8m
|
||||
uid://dehdhn78qv5tr
|
||||
|
|
|
|||
|
|
@ -1,9 +1,28 @@
|
|||
[gd_scene load_steps=2 format=3 uid="uid://dls5r5f6157nq"]
|
||||
|
||||
[ext_resource type="Script" path="res://addons/gut/gui/ResultsTree.gd" id="1_b4uub"]
|
||||
[ext_resource type="Script" uid="uid://dehdhn78qv5tr" path="res://addons/gut/gui/ResultsTree.gd" id="1_b4uub"]
|
||||
|
||||
[node name="ResultsTree" type="VBoxContainer"]
|
||||
[node name="ResultsTree" type="Tree"]
|
||||
offset_right = 1082.0
|
||||
offset_bottom = 544.0
|
||||
size_flags_horizontal = 3
|
||||
size_flags_vertical = 3
|
||||
columns = 2
|
||||
hide_root = true
|
||||
script = ExtResource("1_b4uub")
|
||||
|
||||
[node name="TextOverlay" type="Label" parent="."]
|
||||
visible = false
|
||||
layout_mode = 1
|
||||
anchors_preset = 15
|
||||
anchor_right = 1.0
|
||||
anchor_bottom = 1.0
|
||||
grow_horizontal = 2
|
||||
grow_vertical = 2
|
||||
|
||||
[node name="ResultsTree" type="VBoxContainer" parent="."]
|
||||
custom_minimum_size = Vector2(10, 10)
|
||||
layout_mode = 1
|
||||
anchors_preset = 15
|
||||
anchor_right = 1.0
|
||||
anchor_bottom = 1.0
|
||||
|
|
@ -13,20 +32,3 @@ grow_horizontal = 2
|
|||
grow_vertical = 2
|
||||
size_flags_horizontal = 3
|
||||
size_flags_vertical = 3
|
||||
script = ExtResource("1_b4uub")
|
||||
|
||||
[node name="Tree" type="Tree" parent="."]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
size_flags_vertical = 3
|
||||
columns = 2
|
||||
hide_root = true
|
||||
|
||||
[node name="TextOverlay" type="Label" parent="Tree"]
|
||||
visible = false
|
||||
layout_mode = 1
|
||||
anchors_preset = 15
|
||||
anchor_right = 1.0
|
||||
anchor_bottom = 1.0
|
||||
grow_horizontal = 2
|
||||
grow_vertical = 2
|
||||
|
|
|
|||
|
|
@ -1,8 +1,7 @@
|
|||
@tool
|
||||
extends Control
|
||||
|
||||
|
||||
var ScriptTextEditors = load('res://addons/gut/gui/script_text_editor_controls.gd')
|
||||
var EditorCaretContextNotifier = load('res://addons/gut/editor_caret_context_notifier.gd')
|
||||
|
||||
@onready var _ctrls = {
|
||||
btn_script = $HBox/BtnRunScript,
|
||||
|
|
@ -13,16 +12,33 @@ var ScriptTextEditors = load('res://addons/gut/gui/script_text_editor_controls.g
|
|||
arrow_2 = $HBox/Arrow2
|
||||
}
|
||||
|
||||
var _editors = null
|
||||
var _cur_editor = null
|
||||
var _last_line = -1
|
||||
var _cur_script_path = null
|
||||
var _caret_notifier = null
|
||||
|
||||
var _last_info = {
|
||||
script = null,
|
||||
inner_class = null,
|
||||
test_method = null
|
||||
method = null
|
||||
}
|
||||
|
||||
var disabled = false :
|
||||
set(val):
|
||||
disabled = val
|
||||
if(is_inside_tree()):
|
||||
_ctrls.btn_script.disabled = val
|
||||
_ctrls.btn_inner.disabled = val
|
||||
_ctrls.btn_method.disabled = val
|
||||
var method_prefix = 'test_'
|
||||
var inner_class_prefix = 'Test'
|
||||
var menu_manager = null :
|
||||
set(val):
|
||||
menu_manager = val
|
||||
menu_manager.run_script.connect(_on_BtnRunScript_pressed)
|
||||
menu_manager.run_at_cursor.connect(run_at_cursor)
|
||||
menu_manager.rerun.connect(rerun)
|
||||
menu_manager.run_inner_class.connect(_on_BtnRunInnerClass_pressed)
|
||||
menu_manager.run_test.connect(_on_BtnRunMethod_pressed)
|
||||
_update_buttons(_last_info)
|
||||
|
||||
|
||||
signal run_tests(what)
|
||||
|
||||
|
|
@ -35,95 +51,103 @@ func _ready():
|
|||
_ctrls.arrow_1.visible = false
|
||||
_ctrls.arrow_2.visible = false
|
||||
|
||||
# ----------------
|
||||
# Private
|
||||
# ----------------
|
||||
func _set_editor(which):
|
||||
_last_line = -1
|
||||
if(_cur_editor != null and _cur_editor.get_ref()):
|
||||
# _cur_editor.get_ref().disconnect('cursor_changed',Callable(self,'_on_cursor_changed'))
|
||||
_cur_editor.get_ref().caret_changed.disconnect(_on_cursor_changed)
|
||||
_caret_notifier = EditorCaretContextNotifier.new()
|
||||
add_child(_caret_notifier)
|
||||
_caret_notifier.it_changed.connect(_on_caret_notifer_changed)
|
||||
|
||||
if(which != null):
|
||||
_cur_editor = weakref(which)
|
||||
which.caret_changed.connect(_on_cursor_changed.bind(which))
|
||||
# which.connect('cursor_changed',Callable(self,'_on_cursor_changed'),[which])
|
||||
disabled = disabled
|
||||
|
||||
_last_line = which.get_caret_line()
|
||||
_last_info = _editors.get_line_info()
|
||||
|
||||
func _on_caret_notifer_changed(data):
|
||||
if(data.is_test_script):
|
||||
_last_info = data
|
||||
_update_buttons(_last_info)
|
||||
|
||||
|
||||
# ----------------
|
||||
# Private
|
||||
# ----------------
|
||||
|
||||
func _update_buttons(info):
|
||||
_ctrls.lbl_none.visible = _cur_script_path == null
|
||||
_ctrls.btn_script.visible = _cur_script_path != null
|
||||
_ctrls.lbl_none.visible = false
|
||||
_ctrls.btn_script.visible = info.script != null
|
||||
|
||||
if(info.script != null and info.is_test_script):
|
||||
_ctrls.btn_script.text = info.script.resource_path.get_file()
|
||||
|
||||
_ctrls.btn_inner.visible = info.inner_class != null
|
||||
_ctrls.arrow_1.visible = info.inner_class != null
|
||||
_ctrls.btn_inner.text = str(info.inner_class)
|
||||
_ctrls.btn_inner.tooltip_text = str("Run all tests in Inner-Test-Class ", info.inner_class)
|
||||
|
||||
_ctrls.btn_method.visible = info.test_method != null
|
||||
_ctrls.arrow_2.visible = info.test_method != null
|
||||
_ctrls.btn_method.text = str(info.test_method)
|
||||
_ctrls.btn_method.tooltip_text = str("Run test ", info.test_method)
|
||||
var is_test_method = info.method != null and info.method.begins_with(method_prefix)
|
||||
_ctrls.btn_method.visible = is_test_method
|
||||
_ctrls.arrow_2.visible = is_test_method
|
||||
if(is_test_method):
|
||||
_ctrls.btn_method.text = str(info.method)
|
||||
_ctrls.btn_method.tooltip_text = str("Run test ", info.method)
|
||||
|
||||
if(menu_manager != null):
|
||||
menu_manager.disable_menu("run_script", info.script == null)
|
||||
menu_manager.disable_menu("run_inner_class", info.inner_class == null)
|
||||
menu_manager.disable_menu("run_at_cursor", info.script == null)
|
||||
menu_manager.disable_menu("run_test", is_test_method)
|
||||
menu_manager.disable_menu("rerun", _last_run_info == {})
|
||||
# The button's new size won't take effect until the next frame.
|
||||
# This appears to be what was causing the button to not be clickable the
|
||||
# first time.
|
||||
call_deferred("_update_size")
|
||||
_update_size.call_deferred()
|
||||
|
||||
|
||||
func _update_size():
|
||||
custom_minimum_size.x = _ctrls.btn_method.size.x + _ctrls.btn_method.position.x
|
||||
|
||||
var _last_run_info = {}
|
||||
func _emit_run_tests(info):
|
||||
_last_run_info = info.duplicate()
|
||||
run_tests.emit(info)
|
||||
|
||||
# ----------------
|
||||
# Events
|
||||
# ----------------
|
||||
func _on_cursor_changed(which):
|
||||
if(which.get_caret_line() != _last_line):
|
||||
_last_line = which.get_caret_line()
|
||||
_last_info = _editors.get_line_info()
|
||||
_update_buttons(_last_info)
|
||||
|
||||
|
||||
func _on_BtnRunScript_pressed():
|
||||
var info = _last_info.duplicate()
|
||||
info.script = _cur_script_path.get_file()
|
||||
info.script = info.script.resource_path.get_file()
|
||||
info.inner_class = null
|
||||
info.test_method = null
|
||||
emit_signal("run_tests", info)
|
||||
info.method = null
|
||||
_emit_run_tests(info)
|
||||
|
||||
|
||||
func _on_BtnRunInnerClass_pressed():
|
||||
var info = _last_info.duplicate()
|
||||
info.script = _cur_script_path.get_file()
|
||||
info.test_method = null
|
||||
emit_signal("run_tests", info)
|
||||
info.script = info.script.resource_path.get_file()
|
||||
info.method = null
|
||||
_emit_run_tests(info)
|
||||
|
||||
|
||||
func _on_BtnRunMethod_pressed():
|
||||
var info = _last_info.duplicate()
|
||||
info.script = _cur_script_path.get_file()
|
||||
emit_signal("run_tests", info)
|
||||
info.script = info.script.resource_path.get_file()
|
||||
_emit_run_tests(info)
|
||||
|
||||
|
||||
# ----------------
|
||||
# Public
|
||||
# ----------------
|
||||
func set_script_text_editors(value):
|
||||
_editors = value
|
||||
func rerun():
|
||||
if(_last_run_info != {}):
|
||||
_emit_run_tests(_last_run_info)
|
||||
|
||||
|
||||
func activate_for_script(path):
|
||||
_ctrls.btn_script.visible = true
|
||||
_ctrls.btn_script.text = path.get_file()
|
||||
_ctrls.btn_script.tooltip_text = str("Run all tests in script ", path)
|
||||
_cur_script_path = path
|
||||
_editors.refresh()
|
||||
# We have to wait a beat for the visibility to change on
|
||||
# the editors, otherwise we always get the first one.
|
||||
await get_tree().process_frame
|
||||
_set_editor(_editors.get_current_text_edit())
|
||||
func run_at_cursor():
|
||||
if(_ctrls.btn_method.visible):
|
||||
_on_BtnRunMethod_pressed()
|
||||
elif(_ctrls.btn_inner.visible):
|
||||
_on_BtnRunInnerClass_pressed()
|
||||
elif(_ctrls.btn_script.visible):
|
||||
_on_BtnRunScript_pressed()
|
||||
else:
|
||||
print("nothing selected")
|
||||
|
||||
|
||||
func get_script_button():
|
||||
|
|
@ -138,21 +162,10 @@ func get_test_button():
|
|||
return _ctrls.btn_method
|
||||
|
||||
|
||||
# not used, thought was configurable but it's just the script prefix
|
||||
func set_method_prefix(value):
|
||||
_editors.set_method_prefix(value)
|
||||
|
||||
|
||||
# not used, thought was configurable but it's just the script prefix
|
||||
func set_inner_class_prefix(value):
|
||||
_editors.set_inner_class_prefix(value)
|
||||
_caret_notifier.inner_class_prefix = value
|
||||
|
||||
|
||||
# Mashed this function in here b/c it has _editors. Probably should be
|
||||
# somewhere else (possibly in script_text_editor_controls).
|
||||
func search_current_editor_for_text(txt):
|
||||
var te = _editors.get_current_text_edit()
|
||||
var result = te.search(txt, 0, 0, 0)
|
||||
var to_return = -1
|
||||
|
||||
return to_return
|
||||
func apply_gut_config(gut_config):
|
||||
_caret_notifier.script_prefix = gut_config.options.prefix
|
||||
_caret_notifier.script_suffix = gut_config.options.suffix
|
||||
|
|
|
|||
|
|
@ -1 +1 @@
|
|||
uid://417tmtcbran2
|
||||
uid://c4gmgdl1xwflw
|
||||
|
|
|
|||
|
|
@ -1,10 +1,10 @@
|
|||
[gd_scene load_steps=4 format=3 uid="uid://0yunjxtaa8iw"]
|
||||
[gd_scene load_steps=3 format=3 uid="uid://0yunjxtaa8iw"]
|
||||
|
||||
[ext_resource type="Script" path="res://addons/gut/gui/RunAtCursor.gd" id="1"]
|
||||
[ext_resource type="Texture2D" uid="uid://cr6tvdv0ve6cv" path="res://addons/gut/gui/play.png" id="2"]
|
||||
[ext_resource type="Script" uid="uid://c4gmgdl1xwflw" path="res://addons/gut/gui/RunAtCursor.gd" id="1"]
|
||||
[ext_resource type="Texture2D" uid="uid://6wra5rxmfsrl" path="res://addons/gut/gui/arrow.png" id="3"]
|
||||
|
||||
[node name="RunAtCursor" type="Control"]
|
||||
custom_minimum_size = Vector2(510, 0)
|
||||
layout_mode = 3
|
||||
anchors_preset = 15
|
||||
anchor_right = 1.0
|
||||
|
|
@ -25,40 +25,35 @@ size_flags_horizontal = 3
|
|||
size_flags_vertical = 3
|
||||
|
||||
[node name="LblNoneSelected" type="Label" parent="HBox"]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
text = "<None>"
|
||||
|
||||
[node name="BtnRunScript" type="Button" parent="HBox"]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
text = "<script>"
|
||||
icon = ExtResource("2")
|
||||
text = "test_test.gd"
|
||||
|
||||
[node name="Arrow1" type="TextureButton" parent="HBox"]
|
||||
visible = false
|
||||
custom_minimum_size = Vector2(24, 0)
|
||||
layout_mode = 2
|
||||
texture_normal = ExtResource("3")
|
||||
stretch_mode = 3
|
||||
|
||||
[node name="BtnRunInnerClass" type="Button" parent="HBox"]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
text = "<inner class>"
|
||||
icon = ExtResource("2")
|
||||
tooltip_text = "Run all tests in Inner-Test-Class TestAssertNe"
|
||||
text = "TestAssertNe"
|
||||
|
||||
[node name="Arrow2" type="TextureButton" parent="HBox"]
|
||||
visible = false
|
||||
custom_minimum_size = Vector2(24, 0)
|
||||
layout_mode = 2
|
||||
texture_normal = ExtResource("3")
|
||||
stretch_mode = 3
|
||||
|
||||
[node name="BtnRunMethod" type="Button" parent="HBox"]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
text = "<method>"
|
||||
icon = ExtResource("2")
|
||||
tooltip_text = "Run test test_fails_with_integers_equal"
|
||||
text = "test_fails_with_integers_equal"
|
||||
|
||||
[connection signal="pressed" from="HBox/BtnRunScript" to="." method="_on_BtnRunScript_pressed"]
|
||||
[connection signal="pressed" from="HBox/BtnRunInnerClass" to="." method="_on_BtnRunInnerClass_pressed"]
|
||||
|
|
|
|||
216
addons/gut/gui/RunExternally.gd
Normal file
216
addons/gut/gui/RunExternally.gd
Normal file
|
|
@ -0,0 +1,216 @@
|
|||
@tool
|
||||
extends Control
|
||||
|
||||
# I'm probably going to put this back in later and I don't want to create it
|
||||
# again. Yeah, yeah, yeah.
|
||||
# class DotsAnimator:
|
||||
# var text = ''
|
||||
# var dot = '.'
|
||||
# var max_dots = 3
|
||||
# var dot_delay = .5
|
||||
|
||||
# var _anim_text = ''
|
||||
# var _elapsed_time = 0.0
|
||||
# var _cur_dots = 0
|
||||
|
||||
# func get_animated_text():
|
||||
# return _anim_text
|
||||
|
||||
# func add_time(delta):
|
||||
# _elapsed_time += delta
|
||||
# if(_elapsed_time > dot_delay):
|
||||
# _elapsed_time = 0
|
||||
# _cur_dots += 1
|
||||
# if(_cur_dots > max_dots):
|
||||
# _cur_dots = 0
|
||||
|
||||
# _anim_text = text.rpad(text.length() + _cur_dots, dot)
|
||||
|
||||
|
||||
var GutEditorGlobals = load('res://addons/gut/gui/editor_globals.gd')
|
||||
|
||||
@onready var btn_kill_it = $BgControl/VBox/Kill
|
||||
@onready var bg_control = $BgControl
|
||||
|
||||
var _pipe_results = {}
|
||||
var _debug_mode = false
|
||||
var _std_thread : Thread
|
||||
var _escape_regex : RegEx = RegEx.new()
|
||||
var _text_buffer = ''
|
||||
|
||||
var bottom_panel = null :
|
||||
set(val):
|
||||
bottom_panel = val
|
||||
bottom_panel.resized.connect(_on_bottom_panel_resized)
|
||||
var blocking_mode = "Blocking"
|
||||
var additional_arguments = []
|
||||
var remove_escape_characters = true
|
||||
@export var bg_color = Color.WHITE:
|
||||
set(val):
|
||||
bg_color = val
|
||||
if(is_inside_tree()):
|
||||
bg_control.get("theme_override_styles/panel").bg_color = bg_color
|
||||
|
||||
|
||||
func _debug_ready():
|
||||
_debug_mode = true
|
||||
additional_arguments = ['-gselect', 'test_awaiter.gd', '-gconfig', 'res://.gutconfig.json'] # '-gunit_test_name', 'test_can_clear_spies'
|
||||
blocking_mode = "NonBlocking"
|
||||
run_tests()
|
||||
|
||||
|
||||
func _ready():
|
||||
_escape_regex.compile("\\x1b\\[[0-9;]*m")
|
||||
btn_kill_it.visible = false
|
||||
|
||||
if(get_parent() == get_tree().root):
|
||||
_debug_ready.call_deferred()
|
||||
bg_color = bg_color
|
||||
|
||||
|
||||
func _process(_delta: float) -> void:
|
||||
if(_pipe_results != {}):
|
||||
if(!OS.is_process_running(_pipe_results.pid)):
|
||||
_end_non_blocking()
|
||||
|
||||
|
||||
# ----------
|
||||
# Private
|
||||
# ----------
|
||||
func _center_me():
|
||||
position = get_parent().size / 2.0 - size / 2.0
|
||||
|
||||
|
||||
func _output_text(text, should_scroll = true):
|
||||
if(_debug_mode):
|
||||
print(text)
|
||||
else:
|
||||
if(remove_escape_characters):
|
||||
text = _escape_regex.sub(text, '', true)
|
||||
|
||||
if(bottom_panel != null):
|
||||
bottom_panel.add_output_text(text)
|
||||
if(should_scroll):
|
||||
_scroll_output_pane(-1)
|
||||
else:
|
||||
_text_buffer += text
|
||||
|
||||
|
||||
func _scroll_output_pane(line):
|
||||
if(!_debug_mode and bottom_panel != null):
|
||||
var txt_ctrl = bottom_panel.get_text_output_control().get_rich_text_edit()
|
||||
if(line == -1):
|
||||
line = txt_ctrl.get_line_count()
|
||||
txt_ctrl.scroll_vertical = line
|
||||
|
||||
|
||||
func _add_arguments_to_output():
|
||||
if(additional_arguments.size() != 0):
|
||||
_output_text(
|
||||
str("Run Mode arguments: ", ' '.join(additional_arguments), "\n\n")
|
||||
)
|
||||
|
||||
|
||||
func _load_json():
|
||||
if(_debug_mode):
|
||||
pass # could load file and print it if we want.
|
||||
elif(bottom_panel != null):
|
||||
bottom_panel.load_result_json()
|
||||
|
||||
|
||||
func _run_blocking(options):
|
||||
btn_kill_it.visible = false
|
||||
var output = []
|
||||
await get_tree().create_timer(.1).timeout
|
||||
|
||||
OS.execute(OS.get_executable_path(), options, output, true)
|
||||
|
||||
_output_text(output[0])
|
||||
_add_arguments_to_output()
|
||||
_scroll_output_pane(-1)
|
||||
|
||||
_load_json()
|
||||
queue_free()
|
||||
|
||||
|
||||
func _read_non_blocking_stdio():
|
||||
while(OS.is_process_running(_pipe_results.pid)):
|
||||
while(_pipe_results.stderr.get_length() > 0):
|
||||
_output_text(_pipe_results.stderr.get_line() + "\n")
|
||||
|
||||
while(_pipe_results.stdio.get_length() > 0):
|
||||
_output_text(_pipe_results.stdio.get_line() + "\n")
|
||||
|
||||
# without this, things start to lock up.
|
||||
await get_tree().process_frame
|
||||
|
||||
|
||||
func _run_non_blocking(options):
|
||||
_pipe_results = OS.execute_with_pipe(OS.get_executable_path(), options, false)
|
||||
_std_thread = Thread.new()
|
||||
_std_thread.start(_read_non_blocking_stdio)
|
||||
btn_kill_it.visible = true
|
||||
|
||||
|
||||
func _end_non_blocking():
|
||||
_add_arguments_to_output()
|
||||
_scroll_output_pane(-1)
|
||||
|
||||
_load_json()
|
||||
|
||||
_pipe_results = {}
|
||||
_std_thread.wait_to_finish()
|
||||
_std_thread = null
|
||||
queue_free()
|
||||
if(_debug_mode):
|
||||
get_tree().quit()
|
||||
|
||||
|
||||
|
||||
# ----------------
|
||||
# Events
|
||||
# ----------------
|
||||
func _on_kill_pressed() -> void:
|
||||
if(_pipe_results != {} and OS.is_process_running(_pipe_results.pid)):
|
||||
OS.kill(_pipe_results.pid)
|
||||
btn_kill_it.visible = false
|
||||
|
||||
|
||||
func _on_color_rect_gui_input(event: InputEvent) -> void:
|
||||
if(event is InputEventMouseMotion):
|
||||
if(event.button_mask == MOUSE_BUTTON_MASK_LEFT):
|
||||
position += event.relative
|
||||
|
||||
|
||||
func _on_bottom_panel_resized():
|
||||
_center_me()
|
||||
|
||||
|
||||
# ----------------
|
||||
# Public
|
||||
# ----------------
|
||||
func run_tests():
|
||||
_center_me()
|
||||
|
||||
var options = ["-s", "res://addons/gut/gut_cmdln.gd", "-graie", "-gdisable_colors",
|
||||
"-gconfig", GutEditorGlobals.editor_run_gut_config_path]
|
||||
options.append_array(additional_arguments)
|
||||
|
||||
if(blocking_mode == 'Blocking'):
|
||||
_run_blocking(options)
|
||||
else:
|
||||
_run_non_blocking(options)
|
||||
|
||||
|
||||
func get_godot_help():
|
||||
_text_buffer = ''
|
||||
var options = ["--help", "--headless"]
|
||||
await _run_blocking(options)
|
||||
return _text_buffer
|
||||
|
||||
|
||||
func get_gut_help():
|
||||
_text_buffer = ''
|
||||
var options = ["-s", "res://addons/gut/gut_cmdln.gd", "-gh", "--headless"]
|
||||
await _run_blocking(options)
|
||||
return _text_buffer
|
||||
1
addons/gut/gui/RunExternally.gd.uid
Normal file
1
addons/gut/gui/RunExternally.gd.uid
Normal file
|
|
@ -0,0 +1 @@
|
|||
uid://bi8pg352un4om
|
||||
65
addons/gut/gui/RunExternally.tscn
Normal file
65
addons/gut/gui/RunExternally.tscn
Normal file
|
|
@ -0,0 +1,65 @@
|
|||
[gd_scene load_steps=3 format=3 uid="uid://cftcb0e6g7tu1"]
|
||||
|
||||
[ext_resource type="Script" uid="uid://bi8pg352un4om" path="res://addons/gut/gui/RunExternally.gd" id="1_lrqqi"]
|
||||
|
||||
[sub_resource type="StyleBoxFlat" id="StyleBoxFlat_haowt"]
|
||||
bg_color = Color(0.025935074, 0.17817128, 0.30283752, 1)
|
||||
corner_radius_top_left = 20
|
||||
corner_radius_top_right = 20
|
||||
corner_radius_bottom_right = 20
|
||||
corner_radius_bottom_left = 20
|
||||
shadow_size = 5
|
||||
shadow_offset = Vector2(7, 7)
|
||||
|
||||
[node name="DoShellOut" type="Control"]
|
||||
layout_mode = 3
|
||||
anchors_preset = 0
|
||||
offset_right = 774.0
|
||||
offset_bottom = 260.0
|
||||
script = ExtResource("1_lrqqi")
|
||||
bg_color = Color(0.025935074, 0.17817128, 0.30283752, 1)
|
||||
|
||||
[node name="BgControl" type="Panel" parent="."]
|
||||
layout_mode = 1
|
||||
anchors_preset = 15
|
||||
anchor_right = 1.0
|
||||
anchor_bottom = 1.0
|
||||
grow_horizontal = 2
|
||||
grow_vertical = 2
|
||||
theme_override_styles/panel = SubResource("StyleBoxFlat_haowt")
|
||||
|
||||
[node name="VBox" type="VBoxContainer" parent="BgControl"]
|
||||
layout_mode = 1
|
||||
anchors_preset = 15
|
||||
anchor_right = 1.0
|
||||
anchor_bottom = 1.0
|
||||
grow_horizontal = 2
|
||||
grow_vertical = 2
|
||||
|
||||
[node name="Spacer" type="CenterContainer" parent="BgControl/VBox"]
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 3
|
||||
|
||||
[node name="Title" type="Label" parent="BgControl/VBox"]
|
||||
layout_mode = 2
|
||||
text = "Running Tests"
|
||||
horizontal_alignment = 1
|
||||
|
||||
[node name="Spacer2" type="CenterContainer" parent="BgControl/VBox"]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 3
|
||||
|
||||
[node name="Kill" type="Button" parent="BgControl/VBox"]
|
||||
visible = false
|
||||
custom_minimum_size = Vector2(200, 50)
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 4
|
||||
text = "Stop"
|
||||
|
||||
[node name="Spacer3" type="CenterContainer" parent="BgControl/VBox"]
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 3
|
||||
|
||||
[connection signal="gui_input" from="BgControl" to="." method="_on_color_rect_gui_input"]
|
||||
[connection signal="pressed" from="BgControl/VBox/Kill" to="." method="_on_kill_pressed"]
|
||||
|
|
@ -4,9 +4,6 @@ extends Control
|
|||
var GutEditorGlobals = load('res://addons/gut/gui/editor_globals.gd')
|
||||
|
||||
var _interface = null
|
||||
var _font = null
|
||||
var _font_size = null
|
||||
var _editors = null # script_text_editor_controls.gd
|
||||
var _output_control = null
|
||||
|
||||
@onready var _ctrls = {
|
||||
|
|
@ -24,6 +21,9 @@ var _output_control = null
|
|||
}
|
||||
|
||||
func _ready():
|
||||
if(get_parent() is SubViewport):
|
||||
return
|
||||
|
||||
var f = null
|
||||
if ($FontSampler.get_label_settings() == null) :
|
||||
f = get_theme_default_font()
|
||||
|
|
@ -42,7 +42,7 @@ func _ready():
|
|||
_ctrls.tree.hide_passing = true
|
||||
_ctrls.toolbar.hide_passing.button_pressed = false
|
||||
_ctrls.tree.show_orphans = true
|
||||
_ctrls.tree.item_selected.connect(_on_item_selected)
|
||||
_ctrls.tree.selected.connect(_on_item_selected)
|
||||
|
||||
if(get_parent() == get_tree().root):
|
||||
_test_running_setup()
|
||||
|
|
@ -127,7 +127,8 @@ func _goto_code(path, line, method_name='', inner_class =''):
|
|||
search_strings.append(method_name)
|
||||
|
||||
await get_tree().process_frame
|
||||
line = _get_line_number_for_seq_search(search_strings, _editors.get_current_text_edit())
|
||||
line = _get_line_number_for_seq_search(search_strings,
|
||||
_interface.get_script_editor().get_current_editor().get_base_editor())
|
||||
if(line != null and line != -1):
|
||||
_interface.get_script_editor().goto_line(line)
|
||||
|
||||
|
|
@ -204,10 +205,6 @@ func set_interface(which):
|
|||
_interface = which
|
||||
|
||||
|
||||
func set_script_text_editors(value):
|
||||
_editors = value
|
||||
|
||||
|
||||
func collapse_all():
|
||||
_ctrls.tree.collapse_all()
|
||||
|
||||
|
|
|
|||
|
|
@ -1 +1 @@
|
|||
uid://d1ntrij87eoco
|
||||
uid://chnko3073tkcv
|
||||
|
|
|
|||
|
|
@ -1,20 +1,9 @@
|
|||
[gd_scene load_steps=5 format=3 uid="uid://4gyyn12um08h"]
|
||||
[gd_scene load_steps=4 format=3 uid="uid://4gyyn12um08h"]
|
||||
|
||||
[ext_resource type="Script" path="res://addons/gut/gui/RunResults.gd" id="1"]
|
||||
[ext_resource type="Script" uid="uid://chnko3073tkcv" path="res://addons/gut/gui/RunResults.gd" id="1"]
|
||||
[ext_resource type="Texture2D" uid="uid://bvo0uao7deu0q" path="res://addons/gut/icon.png" id="2_1k8e0"]
|
||||
[ext_resource type="PackedScene" uid="uid://dls5r5f6157nq" path="res://addons/gut/gui/ResultsTree.tscn" id="2_o808v"]
|
||||
|
||||
[sub_resource type="Image" id="Image_abbh7"]
|
||||
data = {
|
||||
"data": PackedByteArray(255, 255, 255, 0, 255, 255, 255, 0, 255, 128, 128, 4, 255, 128, 128, 4, 255, 128, 128, 4, 255, 128, 128, 4, 255, 128, 128, 4, 255, 128, 128, 4, 255, 128, 128, 4, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 255, 255, 0, 255, 93, 93, 131, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 255, 255, 0, 255, 93, 93, 255, 255, 93, 93, 131, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 255, 255, 0, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 131, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 255, 255, 0, 255, 93, 93, 252, 255, 93, 93, 252, 255, 93, 93, 252, 255, 94, 94, 127, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 128, 128, 4, 255, 128, 128, 4, 255, 128, 128, 4, 255, 128, 128, 4, 255, 128, 128, 4, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 93, 93, 231, 255, 93, 93, 55, 255, 97, 97, 58, 255, 93, 93, 233, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 231, 255, 94, 94, 54, 255, 94, 94, 57, 255, 93, 93, 233, 255, 93, 93, 255, 255, 93, 93, 255, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 97, 97, 42, 255, 255, 255, 0, 255, 255, 255, 0, 255, 97, 97, 42, 255, 93, 93, 233, 255, 93, 93, 232, 255, 93, 93, 41, 255, 255, 255, 0, 255, 255, 255, 0, 255, 97, 97, 42, 255, 93, 93, 233, 255, 93, 93, 232, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 96, 96, 45, 255, 97, 97, 42, 255, 255, 255, 0, 255, 97, 97, 42, 255, 97, 97, 42, 255, 255, 255, 0, 255, 98, 98, 47, 255, 97, 97, 42, 255, 255, 255, 0, 255, 97, 97, 42, 255, 97, 97, 42, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 96, 96, 45, 255, 93, 93, 235, 255, 93, 93, 233, 255, 97, 97, 42, 255, 255, 255, 0, 255, 255, 255, 0, 255, 94, 94, 46, 255, 93, 93, 236, 255, 93, 93, 233, 255, 97, 97, 42, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 93, 93, 235, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 233, 255, 95, 95, 59, 255, 96, 96, 61, 255, 93, 93, 235, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 233, 255, 95, 95, 59, 255, 96, 96, 61, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 93, 93, 255, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 93, 93, 252, 255, 93, 93, 252, 255, 93, 93, 252, 255, 93, 93, 252, 255, 93, 93, 252, 255, 93, 93, 252, 255, 93, 93, 252, 255, 93, 93, 252, 255, 93, 93, 252, 255, 93, 93, 252, 255, 93, 93, 252, 255, 93, 93, 252, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0, 255, 255, 255, 0),
|
||||
"format": "RGBA8",
|
||||
"height": 16,
|
||||
"mipmaps": false,
|
||||
"width": 16
|
||||
}
|
||||
|
||||
[sub_resource type="ImageTexture" id="ImageTexture_x655i"]
|
||||
image = SubResource("Image_abbh7")
|
||||
|
||||
[node name="RunResults" type="Control"]
|
||||
custom_minimum_size = Vector2(345, 0)
|
||||
layout_mode = 3
|
||||
|
|
@ -33,28 +22,32 @@ layout_mode = 2
|
|||
size_flags_horizontal = 0
|
||||
|
||||
[node name="Expand" type="Button" parent="VBox/Toolbar"]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
icon = SubResource("ImageTexture_x655i")
|
||||
icon = ExtResource("2_1k8e0")
|
||||
|
||||
[node name="Collapse" type="Button" parent="VBox/Toolbar"]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
icon = SubResource("ImageTexture_x655i")
|
||||
icon = ExtResource("2_1k8e0")
|
||||
|
||||
[node name="Sep" type="ColorRect" parent="VBox/Toolbar"]
|
||||
visible = false
|
||||
custom_minimum_size = Vector2(2, 0)
|
||||
layout_mode = 2
|
||||
|
||||
[node name="LblAll" type="Label" parent="VBox/Toolbar"]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
text = "All:"
|
||||
|
||||
[node name="ExpandAll" type="Button" parent="VBox/Toolbar"]
|
||||
layout_mode = 2
|
||||
icon = SubResource("ImageTexture_x655i")
|
||||
icon = ExtResource("2_1k8e0")
|
||||
|
||||
[node name="CollapseAll" type="Button" parent="VBox/Toolbar"]
|
||||
layout_mode = 2
|
||||
icon = SubResource("ImageTexture_x655i")
|
||||
icon = ExtResource("2_1k8e0")
|
||||
|
||||
[node name="Sep2" type="ColorRect" parent="VBox/Toolbar"]
|
||||
custom_minimum_size = Vector2(2, 0)
|
||||
|
|
@ -77,13 +70,13 @@ text = "Sync:"
|
|||
layout_mode = 2
|
||||
toggle_mode = true
|
||||
button_pressed = true
|
||||
icon = SubResource("ImageTexture_x655i")
|
||||
icon = ExtResource("2_1k8e0")
|
||||
|
||||
[node name="ScrollOutput" type="Button" parent="VBox/Toolbar"]
|
||||
layout_mode = 2
|
||||
toggle_mode = true
|
||||
button_pressed = true
|
||||
icon = SubResource("ImageTexture_x655i")
|
||||
icon = ExtResource("2_1k8e0")
|
||||
|
||||
[node name="Output" type="Panel" parent="VBox"]
|
||||
self_modulate = Color(1, 1, 1, 0.541176)
|
||||
|
|
|
|||
321
addons/gut/gui/ShellOutOptions.gd
Normal file
321
addons/gut/gui/ShellOutOptions.gd
Normal file
|
|
@ -0,0 +1,321 @@
|
|||
@tool
|
||||
extends ConfirmationDialog
|
||||
|
||||
const RUN_MODE_EDITOR = 'Editor'
|
||||
const RUN_MODE_BLOCKING = 'Blocking'
|
||||
const RUN_MODE_NON_BLOCKING = 'NonBlocking'
|
||||
|
||||
var GutEditorGlobals = load('res://addons/gut/gui/editor_globals.gd')
|
||||
|
||||
@onready var _bad_arg_dialog = $AcceptDialog
|
||||
@onready var _main_container = $ScrollContainer/VBoxContainer
|
||||
|
||||
var _blurb_style_box = StyleBoxEmpty.new()
|
||||
var _opt_maker_setup = false
|
||||
var _arg_vbox : VBoxContainer = null
|
||||
var _my_ok_button : Button = null
|
||||
|
||||
# Run mode button stuff
|
||||
var _run_mode_theme = load('res://addons/gut/gui/EditorRadioButton.tres')
|
||||
var _button_group = ButtonGroup.new()
|
||||
var _btn_in_editor : Button = null
|
||||
var _btn_blocking : Button = null
|
||||
var _btn_non_blocking : Button = null
|
||||
var _txt_additional_arguments = null
|
||||
var _btn_godot_help = null
|
||||
var _btn_gut_help = null
|
||||
|
||||
|
||||
var opt_maker = null
|
||||
var default_path = GutEditorGlobals.run_externally_options_path
|
||||
# I like this. It holds values loaded/saved which makes for an easy
|
||||
# reset mechanism. Hit OK; values get written to this object (not the file
|
||||
# system). Hit Cancel; values are reloaded from this object. Call the
|
||||
# save/load methods to interact with the file system.
|
||||
#
|
||||
# Downside: If the keys/sections in the config file change, this ends up
|
||||
# preserving old data. So you gotta find a way to clean it out
|
||||
# somehow.
|
||||
# Downside solved: Clear the config file at the start of the save method.
|
||||
var _config_file = ConfigFile.new()
|
||||
|
||||
var _run_mode = RUN_MODE_EDITOR
|
||||
var run_mode = _run_mode:
|
||||
set(val):
|
||||
_run_mode = val
|
||||
if(is_inside_tree()):
|
||||
_btn_in_editor.button_pressed = _run_mode == RUN_MODE_EDITOR
|
||||
if(_btn_in_editor.button_pressed):
|
||||
_btn_in_editor.pressed.emit()
|
||||
_btn_blocking.button_pressed = _run_mode == RUN_MODE_BLOCKING
|
||||
if(_btn_blocking.button_pressed):
|
||||
_btn_blocking.pressed.emit()
|
||||
_btn_non_blocking.button_pressed = _run_mode == RUN_MODE_NON_BLOCKING
|
||||
if(_btn_non_blocking.button_pressed):
|
||||
_btn_non_blocking.pressed.emit()
|
||||
get():
|
||||
return _run_mode
|
||||
|
||||
|
||||
var additional_arguments = '' :
|
||||
get():
|
||||
if(_opt_maker_setup):
|
||||
return opt_maker.controls.additional_arguments.value
|
||||
else:
|
||||
return additional_arguments
|
||||
|
||||
|
||||
func _debug_ready():
|
||||
popup_centered()
|
||||
default_path = GutEditorGlobals.temp_directory.path_join('test_external_run_options.cfg')
|
||||
exclusive = false
|
||||
|
||||
var save_btn = Button.new()
|
||||
save_btn.text = 'save'
|
||||
save_btn.pressed.connect(func():
|
||||
save_to_file()
|
||||
print(_config_file.encode_to_text()))
|
||||
save_btn.position = Vector2(100, 20)
|
||||
save_btn.size = Vector2(100, 100)
|
||||
get_tree().root.add_child(save_btn)
|
||||
|
||||
var load_btn = Button.new()
|
||||
load_btn.text = 'load'
|
||||
load_btn.pressed.connect(func():
|
||||
load_from_file()
|
||||
print(_config_file.encode_to_text()))
|
||||
load_btn.position = Vector2(100, 130)
|
||||
load_btn.size = Vector2(100, 100)
|
||||
get_tree().root.add_child(load_btn)
|
||||
|
||||
var show_btn = Button.new()
|
||||
show_btn.text = 'Show'
|
||||
show_btn.pressed.connect(popup_centered)
|
||||
show_btn.position = Vector2(100, 250)
|
||||
show_btn.size = Vector2(100, 100)
|
||||
get_tree().root.add_child(show_btn)
|
||||
|
||||
|
||||
func _ready():
|
||||
opt_maker = GutUtils.OptionMaker.new(_main_container)
|
||||
_add_controls()
|
||||
|
||||
if(get_parent() == get_tree().root):
|
||||
_debug_ready.call_deferred()
|
||||
|
||||
_my_ok_button = Button.new()
|
||||
_my_ok_button.text = 'OK'
|
||||
_my_ok_button.pressed.connect(_validate_and_confirm)
|
||||
get_ok_button().add_sibling(_my_ok_button)
|
||||
get_ok_button().modulate.a = 0.0
|
||||
get_ok_button().text = ''
|
||||
get_ok_button().disabled = true
|
||||
|
||||
canceled.connect(reset)
|
||||
_button_group.pressed.connect(_on_mode_button_pressed)
|
||||
run_mode = run_mode
|
||||
|
||||
|
||||
func _validate_and_confirm():
|
||||
if(validate_arguments()):
|
||||
_save_to_config_file(_config_file)
|
||||
confirmed.emit()
|
||||
hide()
|
||||
else:
|
||||
var dlg_text = str("Invalid arguments. The following cannot be used:\n",
|
||||
' '.join(_invalid_args))
|
||||
|
||||
if(run_mode == RUN_MODE_BLOCKING):
|
||||
dlg_text += str("\nThese cannot be used with blocking mode:\n",
|
||||
' '.join(_invalid_blocking_args))
|
||||
|
||||
_bad_arg_dialog.dialog_text = dlg_text
|
||||
_bad_arg_dialog.popup_centered()
|
||||
|
||||
|
||||
func _on_mode_button_pressed(which):
|
||||
if(which == _btn_in_editor):
|
||||
_arg_vbox.modulate.a = .3
|
||||
else:
|
||||
_arg_vbox.modulate.a = 1.0
|
||||
|
||||
_txt_additional_arguments.value_ctrl.editable = which != _btn_in_editor
|
||||
if(which == _btn_in_editor):
|
||||
_run_mode = RUN_MODE_EDITOR
|
||||
elif(which == _btn_blocking):
|
||||
_run_mode = RUN_MODE_BLOCKING
|
||||
elif(which == _btn_non_blocking):
|
||||
_run_mode = RUN_MODE_NON_BLOCKING
|
||||
|
||||
|
||||
func _add_run_mode_button(text, desc_label, description):
|
||||
var btn = Button.new()
|
||||
btn.size_flags_horizontal = Control.SIZE_EXPAND_FILL
|
||||
btn.toggle_mode = true
|
||||
btn.text = text
|
||||
btn.button_group = _button_group
|
||||
btn.theme = _run_mode_theme
|
||||
btn.pressed.connect(func(): desc_label.text = str('[b]', text, "[/b]\n", description))
|
||||
|
||||
return btn
|
||||
|
||||
|
||||
func _add_blurb(text):
|
||||
var ctrl = opt_maker.add_blurb(text)
|
||||
ctrl.set("theme_override_styles/normal", _blurb_style_box)
|
||||
return ctrl
|
||||
|
||||
|
||||
func _add_title(text):
|
||||
var ctrl = opt_maker.add_title(text)
|
||||
ctrl.get_child(0).horizontal_alignment = HORIZONTAL_ALIGNMENT_CENTER
|
||||
return ctrl
|
||||
|
||||
|
||||
func _add_controls():
|
||||
_add_title("Run Modes")
|
||||
_add_blurb(
|
||||
"Choose how GUT will launch tests. Normally you just run them through the editor, but now " +
|
||||
"you can run them externally. This is an experimental feature. It has been tested on Mac " +
|
||||
"and Windows. Your results may vary. Feedback welcome at [url]https://github.com/bitwes/Gut/issues[/url].\n ")
|
||||
|
||||
var button_desc_box = HBoxContainer.new()
|
||||
var button_box = VBoxContainer.new()
|
||||
var button_desc = RichTextLabel.new()
|
||||
button_desc.fit_content = true
|
||||
button_desc.bbcode_enabled = true
|
||||
button_desc.size_flags_horizontal = Control.SIZE_EXPAND_FILL
|
||||
button_desc.autowrap_mode = TextServer.AUTOWRAP_WORD_SMART
|
||||
_main_container.add_child(button_desc_box)
|
||||
button_desc_box.add_child(button_box)
|
||||
button_desc_box.add_child(button_desc)
|
||||
|
||||
_btn_in_editor = _add_run_mode_button("In Editor (default)", button_desc,
|
||||
"This is the default. Runs through the editor. When an error occurs " +
|
||||
"the debugger is invoked. [b]print[/b] output " +
|
||||
"appears in the Output panel and errors show up in the Debugger panel.")
|
||||
button_box.add_child(_btn_in_editor)
|
||||
_btn_blocking = _add_run_mode_button("Externally - Blocking", button_desc,
|
||||
"Debugger is not enabled, and cannot be enabled. All output (print, errors, warnings, etc) " +
|
||||
"appears in the GUT panel, and [b]not[/b] the Output or Debugger panels. \n" +
|
||||
"The Editor cannot be used while tests are running. If you are trying to test for errors, this " +
|
||||
"mode provides the best output.")
|
||||
button_box.add_child(_btn_blocking)
|
||||
_btn_non_blocking = _add_run_mode_button("Externally - NonBlocking", button_desc,
|
||||
"Debugger is not enabled, and cannot be enabled. All output (print, errors, warnings, etc) " +
|
||||
"appears in the GUT panel, and [b]not[/b] the Output or Debugger panels. \n" +
|
||||
"Test output is streamed to the GUT panel. The editor is not blocked, but can be less " +
|
||||
"responsive when there is a lot of output. This is the only mode that supports the --headless argument." )
|
||||
button_box.add_child(_btn_non_blocking)
|
||||
|
||||
_add_title("Command Line Arguments")
|
||||
_arg_vbox = VBoxContainer.new()
|
||||
_main_container.add_child(_arg_vbox)
|
||||
opt_maker.base_container = _arg_vbox
|
||||
_txt_additional_arguments = opt_maker.add_value("additional_arguments", additional_arguments, '', '')
|
||||
_txt_additional_arguments.value_ctrl.placeholder_text = "Put your arguments here. Ex: --verbose -glog 0"
|
||||
_txt_additional_arguments.value_ctrl.select_all_on_focus = false
|
||||
_add_blurb(
|
||||
"Supply any command line options for GUT and/or Godot when running externally. You cannot use " +
|
||||
"spaces in values. See the Godot and GUT documentation for valid arguments. GUT arguments " +
|
||||
"specified here take precedence over your config.")
|
||||
_add_blurb("[b]Be Careful[/b] There are plenty of argument combinations that may make this " +
|
||||
"act wrong/odd/bad/horrible. Some arguments you might [i]want[/i] " +
|
||||
"to use but [b]shouldn't[/b] are checked for, but not that many. Choose your arguments carefully (generally good advice).")
|
||||
|
||||
opt_maker.base_container = _main_container
|
||||
_add_title("Display CLI Help")
|
||||
_add_blurb("You can use these buttons to get a list of valid GUT and Godot options. They print the CLI help text for each to the [b]Output Panel[/b].")
|
||||
_btn_godot_help = Button.new()
|
||||
_btn_godot_help.text = "Print Godot CLI Help"
|
||||
_main_container.add_child(_btn_godot_help)
|
||||
_btn_godot_help.pressed.connect(func():
|
||||
await _show_help("get_godot_help"))
|
||||
|
||||
_btn_gut_help = Button.new()
|
||||
_btn_gut_help.text = "Print GUT CLI Help"
|
||||
_main_container.add_child(_btn_gut_help)
|
||||
_btn_gut_help.pressed.connect(func():
|
||||
await _show_help("get_gut_help"))
|
||||
|
||||
_opt_maker_setup = true
|
||||
|
||||
|
||||
func _show_help(help_method_name):
|
||||
_btn_godot_help.disabled = true
|
||||
_btn_gut_help.disabled = true
|
||||
var re = GutUtils.RunExternallyScene.instantiate()
|
||||
add_child(re)
|
||||
re.visible = false
|
||||
var text = await re.call(help_method_name)
|
||||
print(text)
|
||||
re.queue_free()
|
||||
_btn_godot_help.disabled = false
|
||||
_btn_gut_help.disabled = false
|
||||
if(GutEditorGlobals.gut_plugin != null):
|
||||
GutEditorGlobals.gut_plugin.show_output_panel()
|
||||
|
||||
|
||||
func _save_to_config_file(f : ConfigFile):
|
||||
f.clear()
|
||||
f.set_value('main', 'run_mode', run_mode)
|
||||
f.set_value('main', 'additional_arguments', opt_maker.controls.additional_arguments.value)
|
||||
|
||||
|
||||
func save_to_file(path = default_path):
|
||||
_save_to_config_file(_config_file)
|
||||
_config_file.save(path)
|
||||
|
||||
|
||||
func _load_from_config_file(f):
|
||||
run_mode = f.get_value('main', 'run_mode', RUN_MODE_EDITOR)
|
||||
opt_maker.controls.additional_arguments.value = \
|
||||
f.get_value('main', 'additional_arguments', '')
|
||||
|
||||
|
||||
func load_from_file(path = default_path):
|
||||
_config_file.load(path)
|
||||
_load_from_config_file(_config_file)
|
||||
|
||||
|
||||
func reset():
|
||||
_load_from_config_file(_config_file)
|
||||
|
||||
|
||||
func get_additional_arguments_array():
|
||||
return additional_arguments.split(" ", false)
|
||||
|
||||
|
||||
func should_run_externally():
|
||||
return run_mode != RUN_MODE_EDITOR
|
||||
|
||||
|
||||
var _invalid_args = [
|
||||
'-d', '--debug',
|
||||
'-s', '--script',
|
||||
'-e', '--editor'
|
||||
]
|
||||
var _invalid_blocking_args = [
|
||||
'--headless'
|
||||
]
|
||||
func validate_arguments():
|
||||
var arg_array = get_additional_arguments_array()
|
||||
var i = 0
|
||||
var invalid_found = false
|
||||
while i < _invalid_args.size() and !invalid_found:
|
||||
if(arg_array.has(_invalid_args[i])):
|
||||
invalid_found = true
|
||||
i += 1
|
||||
|
||||
if(run_mode == RUN_MODE_BLOCKING):
|
||||
i = 0
|
||||
while i < _invalid_blocking_args.size() and !invalid_found:
|
||||
if(arg_array.has(_invalid_blocking_args[i])):
|
||||
invalid_found = true
|
||||
i += 1
|
||||
|
||||
return !invalid_found
|
||||
|
||||
|
||||
func get_godot_help():
|
||||
return ''
|
||||
1
addons/gut/gui/ShellOutOptions.gd.uid
Normal file
1
addons/gut/gui/ShellOutOptions.gd.uid
Normal file
|
|
@ -0,0 +1 @@
|
|||
uid://c64u22kybimgi
|
||||
34
addons/gut/gui/ShellOutOptions.tscn
Normal file
34
addons/gut/gui/ShellOutOptions.tscn
Normal file
|
|
@ -0,0 +1,34 @@
|
|||
[gd_scene load_steps=2 format=3 uid="uid://ckv5eh8xyrwbk"]
|
||||
|
||||
[ext_resource type="Script" uid="uid://c64u22kybimgi" path="res://addons/gut/gui/ShellOutOptions.gd" id="1_ht2pf"]
|
||||
|
||||
[node name="ShellOutOptions" type="ConfirmationDialog"]
|
||||
oversampling_override = 1.0
|
||||
title = "GUT Run Mode (Experimental)"
|
||||
position = Vector2i(0, 36)
|
||||
size = Vector2i(516, 557)
|
||||
visible = true
|
||||
script = ExtResource("1_ht2pf")
|
||||
|
||||
[node name="ScrollContainer" type="ScrollContainer" parent="."]
|
||||
custom_minimum_size = Vector2(500, 500)
|
||||
anchors_preset = 15
|
||||
anchor_right = 1.0
|
||||
anchor_bottom = 1.0
|
||||
offset_left = 8.0
|
||||
offset_top = 8.0
|
||||
offset_right = -8.0
|
||||
offset_bottom = -49.0
|
||||
grow_horizontal = 2
|
||||
grow_vertical = 2
|
||||
|
||||
[node name="VBoxContainer" type="VBoxContainer" parent="ScrollContainer"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
size_flags_vertical = 3
|
||||
|
||||
[node name="AcceptDialog" type="AcceptDialog" parent="."]
|
||||
oversampling_override = 1.0
|
||||
size = Vector2i(399, 106)
|
||||
dialog_text = "Invalid arguments. The following cannot be used:
|
||||
-d --debug -s --script"
|
||||
|
|
@ -120,6 +120,8 @@ func get_shortcut():
|
|||
to_return.events.append(_source_event)
|
||||
return to_return
|
||||
|
||||
func get_input_event():
|
||||
return _source_event
|
||||
|
||||
func set_shortcut(sc):
|
||||
if(sc == null or sc.events == null || sc.events.size() <= 0):
|
||||
|
|
|
|||
|
|
@ -1 +1 @@
|
|||
uid://byhinwdh4mxic
|
||||
uid://k6hvvpekp0xw
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
[gd_scene load_steps=2 format=3 uid="uid://sfb1fw8j6ufu"]
|
||||
|
||||
[ext_resource type="Script" path="res://addons/gut/gui/ShortcutButton.gd" id="1"]
|
||||
[ext_resource type="Script" uid="uid://k6hvvpekp0xw" path="res://addons/gut/gui/ShortcutButton.gd" id="1"]
|
||||
|
||||
[node name="ShortcutButton" type="Control"]
|
||||
custom_minimum_size = Vector2(210, 30)
|
||||
|
|
|
|||
120
addons/gut/gui/ShortcutDialog.gd
Normal file
120
addons/gut/gui/ShortcutDialog.gd
Normal file
|
|
@ -0,0 +1,120 @@
|
|||
@tool
|
||||
extends ConfirmationDialog
|
||||
|
||||
var GutEditorGlobals = load('res://addons/gut/gui/editor_globals.gd')
|
||||
var default_path = GutEditorGlobals.editor_shortcuts_path
|
||||
|
||||
|
||||
@onready var scbtn_run_all = $Scroll/Layout/CRunAll/ShortcutButton
|
||||
@onready var scbtn_run_current_script = $Scroll/Layout/CRunCurrentScript/ShortcutButton
|
||||
@onready var scbtn_run_current_inner = $Scroll/Layout/CRunCurrentInner/ShortcutButton
|
||||
@onready var scbtn_run_current_test = $Scroll/Layout/CRunCurrentTest/ShortcutButton
|
||||
@onready var scbtn_run_at_cursor = $Scroll/Layout/CRunAtCursor/ShortcutButton
|
||||
@onready var scbtn_rerun = $Scroll/Layout/CRerun/ShortcutButton
|
||||
@onready var scbtn_panel = $Scroll/Layout/CPanelButton/ShortcutButton
|
||||
@onready var scbtn_windowed = $Scroll/Layout/CToggleWindowed/ShortcutButton
|
||||
|
||||
|
||||
@onready var all_buttons = [
|
||||
scbtn_run_all, scbtn_run_current_script, scbtn_run_current_inner,
|
||||
scbtn_run_current_test, scbtn_run_at_cursor, scbtn_rerun,
|
||||
scbtn_panel, scbtn_windowed
|
||||
]
|
||||
|
||||
|
||||
func _debug_ready():
|
||||
popup_centered()
|
||||
|
||||
var btn = Button.new()
|
||||
btn.text = "show"
|
||||
get_tree().root.add_child(btn)
|
||||
btn.pressed.connect(popup)
|
||||
btn.position = Vector2(100, 100)
|
||||
btn.size = Vector2(100, 100)
|
||||
|
||||
size_changed.connect(func(): title = str(size))
|
||||
|
||||
|
||||
func _ready():
|
||||
for scbtn in all_buttons:
|
||||
scbtn.connect('start_edit', _on_edit_start.bind(scbtn))
|
||||
scbtn.connect('end_edit', _on_edit_end)
|
||||
|
||||
canceled.connect(_on_cancel)
|
||||
|
||||
# Sizing this window on different monitors, especially compared to what it
|
||||
# looks like if you just run this project is annoying. This is what I came
|
||||
# up with after getting annoyed. You probably won't be looking at this
|
||||
# very often so it's fine...until it isn't.
|
||||
size = Vector2(DisplayServer.screen_get_size()) * Vector2(.5, .8)
|
||||
|
||||
if(get_parent() == get_tree().root):
|
||||
_debug_ready.call_deferred()
|
||||
|
||||
|
||||
|
||||
func _cancel_all():
|
||||
for scbtn in all_buttons:
|
||||
scbtn.cancel()
|
||||
|
||||
|
||||
# ------------
|
||||
# Events
|
||||
# ------------
|
||||
func _on_cancel():
|
||||
_cancel_all()
|
||||
load_shortcuts()
|
||||
|
||||
|
||||
func _on_edit_start(which):
|
||||
for scbtn in all_buttons:
|
||||
if(scbtn != which):
|
||||
scbtn.disable_set(true)
|
||||
scbtn.disable_clear(true)
|
||||
|
||||
|
||||
func _on_edit_end():
|
||||
for scbtn in all_buttons:
|
||||
scbtn.disable_set(false)
|
||||
scbtn.disable_clear(false)
|
||||
|
||||
|
||||
# ------------
|
||||
# Public
|
||||
# ------------
|
||||
func save_shortcuts():
|
||||
save_shortcuts_to_file(default_path)
|
||||
|
||||
|
||||
func save_shortcuts_to_file(path):
|
||||
var f = ConfigFile.new()
|
||||
f.set_value('main', 'panel_button', scbtn_panel.get_shortcut())
|
||||
f.set_value('main', 'rerun', scbtn_rerun.get_shortcut())
|
||||
f.set_value('main', 'run_all', scbtn_run_all.get_shortcut())
|
||||
f.set_value('main', 'run_at_cursor', scbtn_run_at_cursor.get_shortcut())
|
||||
f.set_value('main', 'run_current_inner', scbtn_run_current_inner.get_shortcut())
|
||||
f.set_value('main', 'run_current_script', scbtn_run_current_script.get_shortcut())
|
||||
f.set_value('main', 'run_current_test', scbtn_run_current_test.get_shortcut())
|
||||
# f.set_value('main', 'toggle_windowed', scbtn_windowed.get_shortcut())
|
||||
f.save(path)
|
||||
|
||||
|
||||
func load_shortcuts():
|
||||
load_shortcuts_from_file(default_path)
|
||||
|
||||
|
||||
func load_shortcuts_from_file(path):
|
||||
var f = ConfigFile.new()
|
||||
# as long as this shortcut is never modified, this is fine, otherwise
|
||||
# each thing should get its own default instead.
|
||||
var empty = Shortcut.new()
|
||||
|
||||
f.load(path)
|
||||
scbtn_panel.set_shortcut(f.get_value('main', 'panel_button', empty))
|
||||
scbtn_rerun.set_shortcut(f.get_value('main', 'rerun', empty))
|
||||
scbtn_run_all.set_shortcut(f.get_value('main', 'run_all', empty))
|
||||
scbtn_run_at_cursor.set_shortcut(f.get_value('main', 'run_at_cursor', empty))
|
||||
scbtn_run_current_inner.set_shortcut(f.get_value('main', 'run_current_inner', empty))
|
||||
scbtn_run_current_script.set_shortcut(f.get_value('main', 'run_current_script', empty))
|
||||
scbtn_run_current_test.set_shortcut(f.get_value('main', 'run_current_test', empty))
|
||||
# scbtn_windowed.set_shortcut(f.get_value('main', 'toggle_windowed', empty))
|
||||
1
addons/gut/gui/ShortcutDialog.gd.uid
Normal file
1
addons/gut/gui/ShortcutDialog.gd.uid
Normal file
|
|
@ -0,0 +1 @@
|
|||
uid://dc5jgemxslgvl
|
||||
209
addons/gut/gui/ShortcutDialog.tscn
Normal file
209
addons/gut/gui/ShortcutDialog.tscn
Normal file
|
|
@ -0,0 +1,209 @@
|
|||
[gd_scene format=3 uid="uid://dj5ve0bq7xa5j"]
|
||||
|
||||
[ext_resource type="Script" uid="uid://dc5jgemxslgvl" path="res://addons/gut/gui/ShortcutDialog.gd" id="1_qq8qn"]
|
||||
[ext_resource type="PackedScene" uid="uid://sfb1fw8j6ufu" path="res://addons/gut/gui/ShortcutButton.tscn" id="2_i3wie"]
|
||||
|
||||
[node name="ShortcutDialog" type="ConfirmationDialog" unique_id=1776753623]
|
||||
oversampling_override = 1.0
|
||||
title = "GUT Shortcuts"
|
||||
position = Vector2i(0, 36)
|
||||
size = Vector2i(1920, 1728)
|
||||
visible = true
|
||||
script = ExtResource("1_qq8qn")
|
||||
|
||||
[node name="Scroll" type="ScrollContainer" parent="." unique_id=1914806303]
|
||||
offset_left = 8.0
|
||||
offset_top = 8.0
|
||||
offset_right = 1912.0
|
||||
offset_bottom = 1679.0
|
||||
|
||||
[node name="Layout" type="VBoxContainer" parent="Scroll" unique_id=501181924]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
size_flags_vertical = 3
|
||||
|
||||
[node name="ShortcutDescription" type="RichTextLabel" parent="Scroll/Layout" unique_id=945401700]
|
||||
custom_minimum_size = Vector2(0, 20)
|
||||
layout_mode = 2
|
||||
bbcode_enabled = true
|
||||
text = "Shortcuts for:
|
||||
- Buttons in Panel
|
||||
- Project->Tools->GUT menu items
|
||||
Shortcuts that only apply to menus are labeled."
|
||||
fit_content = true
|
||||
scroll_active = false
|
||||
|
||||
[node name="TopPad" type="CenterContainer" parent="Scroll/Layout" unique_id=1405248155]
|
||||
custom_minimum_size = Vector2(0, 5)
|
||||
layout_mode = 2
|
||||
|
||||
[node name="CPanelButton" type="HBoxContainer" parent="Scroll/Layout" unique_id=1970478925]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label" type="Label" parent="Scroll/Layout/CPanelButton" unique_id=1534644867]
|
||||
custom_minimum_size = Vector2(50, 0)
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 7
|
||||
text = "Show/Hide GUT"
|
||||
|
||||
[node name="ShortcutButton" parent="Scroll/Layout/CPanelButton" unique_id=2131329924 instance=ExtResource("2_i3wie")]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
|
||||
[node name="ShortcutDescription2" type="RichTextLabel" parent="Scroll/Layout" unique_id=2145896902]
|
||||
custom_minimum_size = Vector2(0, 20)
|
||||
layout_mode = 2
|
||||
bbcode_enabled = true
|
||||
text = "[i]Show/hide the gut panel or move focus to/away from the GUT window.
|
||||
[/i]"
|
||||
fit_content = true
|
||||
scroll_active = false
|
||||
|
||||
[node name="CRunAll" type="HBoxContainer" parent="Scroll/Layout" unique_id=1158078093]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label" type="Label" parent="Scroll/Layout/CRunAll" unique_id=1066237403]
|
||||
custom_minimum_size = Vector2(50, 0)
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 7
|
||||
text = "Run All"
|
||||
|
||||
[node name="ShortcutButton" parent="Scroll/Layout/CRunAll" unique_id=738525032 instance=ExtResource("2_i3wie")]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
|
||||
[node name="ShortcutDescription3" type="RichTextLabel" parent="Scroll/Layout" unique_id=140757094]
|
||||
custom_minimum_size = Vector2(0, 20)
|
||||
layout_mode = 2
|
||||
bbcode_enabled = true
|
||||
text = "[i]Run the entire test suite.[/i]"
|
||||
fit_content = true
|
||||
scroll_active = false
|
||||
|
||||
[node name="CRunCurrentScript" type="HBoxContainer" parent="Scroll/Layout" unique_id=736016343]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label" type="Label" parent="Scroll/Layout/CRunCurrentScript" unique_id=950095716]
|
||||
custom_minimum_size = Vector2(50, 0)
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 7
|
||||
text = "Run Current Script"
|
||||
|
||||
[node name="ShortcutButton" parent="Scroll/Layout/CRunCurrentScript" unique_id=983079158 instance=ExtResource("2_i3wie")]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
|
||||
[node name="ShortcutDescription4" type="RichTextLabel" parent="Scroll/Layout" unique_id=1806489359]
|
||||
custom_minimum_size = Vector2(0, 20)
|
||||
layout_mode = 2
|
||||
bbcode_enabled = true
|
||||
text = "[i]Run all tests in the currently selected script.[/i]"
|
||||
fit_content = true
|
||||
scroll_active = false
|
||||
|
||||
[node name="CRunCurrentInner" type="HBoxContainer" parent="Scroll/Layout" unique_id=2095658353]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label" type="Label" parent="Scroll/Layout/CRunCurrentInner" unique_id=1492835813]
|
||||
custom_minimum_size = Vector2(50, 0)
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 7
|
||||
text = "Run Current Inner Class"
|
||||
|
||||
[node name="ShortcutButton" parent="Scroll/Layout/CRunCurrentInner" unique_id=1400542413 instance=ExtResource("2_i3wie")]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
|
||||
[node name="ShortcutDescription5" type="RichTextLabel" parent="Scroll/Layout" unique_id=1669546632]
|
||||
custom_minimum_size = Vector2(0, 20)
|
||||
layout_mode = 2
|
||||
bbcode_enabled = true
|
||||
text = "[i]Run only the currently selected inner test class if one is selected.[/i]"
|
||||
fit_content = true
|
||||
scroll_active = false
|
||||
|
||||
[node name="CRunCurrentTest" type="HBoxContainer" parent="Scroll/Layout" unique_id=641427686]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label" type="Label" parent="Scroll/Layout/CRunCurrentTest" unique_id=879088006]
|
||||
custom_minimum_size = Vector2(50, 0)
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 7
|
||||
text = "Run Current Test"
|
||||
|
||||
[node name="ShortcutButton" parent="Scroll/Layout/CRunCurrentTest" unique_id=1073304800 instance=ExtResource("2_i3wie")]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
|
||||
[node name="ShortcutDescription6" type="RichTextLabel" parent="Scroll/Layout" unique_id=164300543]
|
||||
custom_minimum_size = Vector2(0, 20)
|
||||
layout_mode = 2
|
||||
bbcode_enabled = true
|
||||
text = "[i]Run only the currently selected test, if one is selected[/i]"
|
||||
fit_content = true
|
||||
scroll_active = false
|
||||
|
||||
[node name="CRunAtCursor" type="HBoxContainer" parent="Scroll/Layout" unique_id=1201163993]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label" type="Label" parent="Scroll/Layout/CRunAtCursor" unique_id=1748949401]
|
||||
custom_minimum_size = Vector2(50, 0)
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 7
|
||||
text = "Run At Cursor (menu only)"
|
||||
|
||||
[node name="ShortcutButton" parent="Scroll/Layout/CRunAtCursor" unique_id=282512521 instance=ExtResource("2_i3wie")]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
|
||||
[node name="ShortcutDescription7" type="RichTextLabel" parent="Scroll/Layout" unique_id=1040671512]
|
||||
custom_minimum_size = Vector2(0, 20)
|
||||
layout_mode = 2
|
||||
bbcode_enabled = true
|
||||
text = "[i]Run the most specific test/inner class/script based on where the cursor is.[/i]"
|
||||
fit_content = true
|
||||
scroll_active = false
|
||||
|
||||
[node name="CRerun" type="HBoxContainer" parent="Scroll/Layout" unique_id=1620841467]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label" type="Label" parent="Scroll/Layout/CRerun" unique_id=1644131487]
|
||||
custom_minimum_size = Vector2(50, 0)
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 7
|
||||
text = "Rerun (menu only)"
|
||||
|
||||
[node name="ShortcutButton" parent="Scroll/Layout/CRerun" unique_id=782836241 instance=ExtResource("2_i3wie")]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
|
||||
[node name="ShortcutDescription8" type="RichTextLabel" parent="Scroll/Layout" unique_id=520952349]
|
||||
custom_minimum_size = Vector2(0, 20)
|
||||
layout_mode = 2
|
||||
bbcode_enabled = true
|
||||
text = "[i]Rerun the test(s) that were last run."
|
||||
fit_content = true
|
||||
scroll_active = false
|
||||
|
||||
[node name="CToggleWindowed" type="HBoxContainer" parent="Scroll/Layout" unique_id=1521839247]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Label" type="Label" parent="Scroll/Layout/CToggleWindowed" unique_id=728639840]
|
||||
custom_minimum_size = Vector2(50, 0)
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 7
|
||||
text = "Toggle Windowed"
|
||||
|
||||
[node name="ShortcutButton" parent="Scroll/Layout/CToggleWindowed" unique_id=603114021 instance=ExtResource("2_i3wie")]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
|
||||
[node name="ShortcutDescription9" type="RichTextLabel" parent="Scroll/Layout" unique_id=747035069]
|
||||
visible = false
|
||||
custom_minimum_size = Vector2(0, 20)
|
||||
layout_mode = 2
|
||||
bbcode_enabled = true
|
||||
text = "[i]Toggle GUT in the bottom panel or a separate window.[/i]"
|
||||
fit_content = true
|
||||
scroll_active = false
|
||||
125
addons/gut/gui/about.gd
Normal file
125
addons/gut/gui/about.gd
Normal file
|
|
@ -0,0 +1,125 @@
|
|||
@tool
|
||||
extends AcceptDialog
|
||||
|
||||
var GutEditorGlobals = load('res://addons/gut/gui/editor_globals.gd')
|
||||
|
||||
var _bbcode = \
|
||||
"""
|
||||
[center]GUT {gut_version}[/center]
|
||||
|
||||
[center][b]GUT Links[/b]
|
||||
{gut_link_table}[/center]
|
||||
|
||||
[center][b]VSCode Extension Links[/b]
|
||||
{vscode_link_table}[/center]
|
||||
|
||||
[center]You can support GUT development at
|
||||
{donate_link}
|
||||
|
||||
Thanks for using GUT!
|
||||
[/center]
|
||||
"""
|
||||
|
||||
var _gut_links = [
|
||||
[&"Documentation", &"https://gut.readthedocs.io"],
|
||||
[&"What's New", &"https://github.com/bitwes/Gut/releases/tag/v{gut_version}"],
|
||||
[&"Repo", &"https://github.com/bitwes/gut"],
|
||||
[&"Report Bugs", &"https://github.com/bitwes/gut/issues"]
|
||||
]
|
||||
|
||||
var _vscode_links = [
|
||||
["Repo", "https://github.com/bitwes/gut-extension"],
|
||||
["Market Place", "https://marketplace.visualstudio.com/items?itemName=bitwes.gut-extension"]
|
||||
]
|
||||
|
||||
var _donate_link = "https://buymeacoffee.com/bitwes"
|
||||
|
||||
@onready var _logo = $Logo
|
||||
|
||||
|
||||
func _ready():
|
||||
if(get_parent() is SubViewport):
|
||||
return
|
||||
|
||||
_vert_center_logo()
|
||||
$Logo.disabled = true
|
||||
$HBox/Scroll/RichTextLabel.text = _make_text()
|
||||
|
||||
|
||||
func _color_link(link_text):
|
||||
return str("[color=ROYAL_BLUE]", link_text, "[/color]")
|
||||
|
||||
|
||||
func _link_table(entries):
|
||||
var text = ''
|
||||
for entry in entries:
|
||||
text += str("[cell][right]", entry[0], "[/right][/cell]")
|
||||
var link = str("[url]", entry[1], "[/url]")
|
||||
if(entry[1].length() > 60):
|
||||
link = str("[url=", entry[1], "]", entry[1].substr(0, 50), "...[/url]")
|
||||
|
||||
text += str("[cell][left]", _color_link(link), "[/left][/cell]\n")
|
||||
return str('[table=2]', text, '[/table]')
|
||||
|
||||
|
||||
func _make_text():
|
||||
var gut_link_table = _link_table(_gut_links)
|
||||
var vscode_link_table = _link_table(_vscode_links)
|
||||
|
||||
var text = _bbcode.format({
|
||||
"gut_link_table":gut_link_table,
|
||||
"vscode_link_table":vscode_link_table,
|
||||
"donate_link":_color_link(str('[url]', _donate_link, '[/url]')),
|
||||
"gut_version":GutUtils.version_numbers.gut_version,
|
||||
})
|
||||
return text
|
||||
|
||||
|
||||
func _vert_center_logo():
|
||||
_logo.position.y = size.y / 2.0
|
||||
|
||||
|
||||
# -----------
|
||||
# Events
|
||||
# -----------
|
||||
func _on_rich_text_label_meta_clicked(meta: Variant) -> void:
|
||||
OS.shell_open(str(meta))
|
||||
|
||||
|
||||
func _on_mouse_entered() -> void:
|
||||
pass#_logo.active = true
|
||||
|
||||
|
||||
func _on_mouse_exited() -> void:
|
||||
pass#_logo.active = false
|
||||
|
||||
|
||||
var _odd_ball_eyes_l = 1.1
|
||||
var _odd_ball_eyes_r = .7
|
||||
func _on_rich_text_label_meta_hover_started(meta: Variant) -> void:
|
||||
if(meta == _gut_links[0][1]):
|
||||
_logo.set_eye_color(Color.RED)
|
||||
elif(meta.find("releases/tag/") > 0):
|
||||
_logo.set_eye_color(Color.GREEN)
|
||||
elif(meta == _gut_links[2][1]):
|
||||
_logo.set_eye_color(Color.PURPLE)
|
||||
elif(meta == _gut_links[3][1]):
|
||||
_logo.set_eye_scale(1.2)
|
||||
elif(meta == _vscode_links[0][1]):
|
||||
_logo.set_eye_scale(.5, .5)
|
||||
elif(meta == _vscode_links[1][1]):
|
||||
_logo.set_eye_scale(_odd_ball_eyes_l, _odd_ball_eyes_r)
|
||||
var temp = _odd_ball_eyes_l
|
||||
_odd_ball_eyes_l = _odd_ball_eyes_r
|
||||
_odd_ball_eyes_r = temp
|
||||
elif(meta == _donate_link):
|
||||
_logo.active = false
|
||||
|
||||
|
||||
func _on_rich_text_label_meta_hover_ended(meta: Variant) -> void:
|
||||
if(meta == _donate_link):
|
||||
_logo.active = true
|
||||
|
||||
|
||||
func _on_logo_pressed() -> void:
|
||||
_logo.disabled = !_logo.disabled
|
||||
1
addons/gut/gui/about.gd.uid
Normal file
1
addons/gut/gui/about.gd.uid
Normal file
|
|
@ -0,0 +1 @@
|
|||
uid://g7qu8ihdt3pd
|
||||
56
addons/gut/gui/about.tscn
Normal file
56
addons/gut/gui/about.tscn
Normal file
|
|
@ -0,0 +1,56 @@
|
|||
[gd_scene load_steps=5 format=3 uid="uid://dqbkylpsatcqm"]
|
||||
|
||||
[ext_resource type="Script" uid="uid://g7qu8ihdt3pd" path="res://addons/gut/gui/about.gd" id="1_bg86c"]
|
||||
[ext_resource type="PackedScene" uid="uid://bjkn8mhx2fmt1" path="res://addons/gut/gui/GutLogo.tscn" id="3_kpic4"]
|
||||
|
||||
[sub_resource type="StyleBoxFlat" id="StyleBoxFlat_q8rky"]
|
||||
bg_color = Color(0, 0, 0, 0.49803922)
|
||||
|
||||
[sub_resource type="StyleBoxEmpty" id="StyleBoxEmpty_kpic4"]
|
||||
|
||||
[node name="About" type="AcceptDialog"]
|
||||
oversampling_override = 1.0
|
||||
title = "About GUT"
|
||||
position = Vector2i(0, 36)
|
||||
size = Vector2i(1500, 800)
|
||||
visible = true
|
||||
min_size = Vector2i(800, 800)
|
||||
script = ExtResource("1_bg86c")
|
||||
|
||||
[node name="HBox" type="HBoxContainer" parent="."]
|
||||
offset_left = 8.0
|
||||
offset_top = 8.0
|
||||
offset_right = 1492.0
|
||||
offset_bottom = 751.0
|
||||
alignment = 1
|
||||
|
||||
[node name="MakeRoomForLogo" type="CenterContainer" parent="HBox"]
|
||||
custom_minimum_size = Vector2(200, 0)
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Scroll" type="ScrollContainer" parent="HBox"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
|
||||
[node name="RichTextLabel" type="RichTextLabel" parent="HBox/Scroll"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
size_flags_vertical = 3
|
||||
theme_override_styles/normal = SubResource("StyleBoxFlat_q8rky")
|
||||
theme_override_styles/focus = SubResource("StyleBoxEmpty_kpic4")
|
||||
bbcode_enabled = true
|
||||
fit_content = true
|
||||
|
||||
[node name="Logo" parent="." instance=ExtResource("3_kpic4")]
|
||||
modulate = Color(0.74509805, 0.74509805, 0.74509805, 1)
|
||||
position = Vector2(151, 265)
|
||||
scale = Vector2(0.8, 0.8)
|
||||
active = true
|
||||
disabled = true
|
||||
|
||||
[connection signal="mouse_entered" from="." to="." method="_on_mouse_entered"]
|
||||
[connection signal="mouse_exited" from="." to="." method="_on_mouse_exited"]
|
||||
[connection signal="meta_clicked" from="HBox/Scroll/RichTextLabel" to="." method="_on_rich_text_label_meta_clicked"]
|
||||
[connection signal="meta_hover_ended" from="HBox/Scroll/RichTextLabel" to="." method="_on_rich_text_label_meta_hover_ended"]
|
||||
[connection signal="meta_hover_started" from="HBox/Scroll/RichTextLabel" to="." method="_on_rich_text_label_meta_hover_started"]
|
||||
[connection signal="pressed" from="Logo" to="." method="_on_logo_pressed"]
|
||||
|
|
@ -18,6 +18,8 @@ dest_files=["res://.godot/imported/arrow.png-2b5b2d838b5b3467cf300ac2da1630d9.ct
|
|||
compress/mode=0
|
||||
compress/high_quality=false
|
||||
compress/lossy_quality=0.7
|
||||
compress/uastc_level=0
|
||||
compress/rdo_quality_loss=0.0
|
||||
compress/hdr_compression=1
|
||||
compress/normal_map=0
|
||||
compress/channel_pack=0
|
||||
|
|
@ -25,6 +27,10 @@ mipmaps/generate=false
|
|||
mipmaps/limit=-1
|
||||
roughness/mode=0
|
||||
roughness/src_normal=""
|
||||
process/channel_remap/red=0
|
||||
process/channel_remap/green=1
|
||||
process/channel_remap/blue=2
|
||||
process/channel_remap/alpha=3
|
||||
process/fix_alpha_border=true
|
||||
process/premult_alpha=false
|
||||
process/normal_map_invert_y=false
|
||||
|
|
|
|||
|
|
@ -11,9 +11,10 @@ static var editor_run_gut_config_path = 'gut_editor_config.json':
|
|||
get: return temp_directory.path_join(editor_run_gut_config_path)
|
||||
# Should this print a message or something instead? Probably, but then I'd
|
||||
# be repeating even more code than if this was just a constant. So I didn't,
|
||||
# even though I wanted to put make the message a easter eggish fun message.
|
||||
# even though I wanted to make the message a easter eggish fun message.
|
||||
# I didn't, so this dumb comment will have to serve as the easter eggish fun.
|
||||
set(v): pass
|
||||
set(v):
|
||||
print("Be sure to document your code. Never trust comments.")
|
||||
|
||||
|
||||
static var editor_run_bbcode_results_path = 'gut_editor.bbcode':
|
||||
|
|
@ -30,6 +31,9 @@ static var editor_shortcuts_path = 'gut_editor_shortcuts.cfg' :
|
|||
get: return temp_directory.path_join(editor_shortcuts_path)
|
||||
set(v): pass
|
||||
|
||||
static var run_externally_options_path = 'gut_editor_run_externally.cfg' :
|
||||
get: return temp_directory.path_join(run_externally_options_path)
|
||||
set(v): pass
|
||||
|
||||
static var _user_prefs = null
|
||||
static var user_prefs = _user_prefs :
|
||||
|
|
@ -38,10 +42,27 @@ static var user_prefs = _user_prefs :
|
|||
# editor.
|
||||
get:
|
||||
if(_user_prefs == null and Engine.is_editor_hint()):
|
||||
_user_prefs = GutUserPreferences.new(EditorInterface.get_editor_settings())
|
||||
# This is sometimes used when not in the editor. Avoid parser error
|
||||
# for EditorInterface.
|
||||
_user_prefs = GutUserPreferences.new(GutUtils.get_editor_interface().get_editor_settings())
|
||||
return _user_prefs
|
||||
|
||||
static var gut_plugin = null
|
||||
|
||||
static func create_temp_directory():
|
||||
DirAccess.make_dir_recursive_absolute(temp_directory)
|
||||
|
||||
|
||||
static func is_being_edited_in_editor(which):
|
||||
if(!Engine.is_editor_hint()):
|
||||
return false
|
||||
|
||||
var trav = which
|
||||
var is_scene_root = false
|
||||
var editor_root = which.get_tree().edited_scene_root
|
||||
while(trav != null and !is_scene_root):
|
||||
is_scene_root = editor_root == trav
|
||||
if(!is_scene_root):
|
||||
trav = trav.get_parent()
|
||||
return is_scene_root
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -1 +1 @@
|
|||
uid://b0cay8uv6i2kn
|
||||
uid://cbi00ubn046c2
|
||||
|
|
|
|||
|
|
@ -3,105 +3,33 @@ var GutConfig = load('res://addons/gut/gut_config.gd')
|
|||
|
||||
const DIRS_TO_LIST = 6
|
||||
|
||||
var _base_container = null
|
||||
# All the various PanelControls indexed by thier gut_config keys.
|
||||
var _cfg_ctrls = {}
|
||||
|
||||
# specific titles that we need to do stuff with
|
||||
var _titles = {
|
||||
dirs = null
|
||||
}
|
||||
# All titles so we can free them when we want.
|
||||
var _all_titles = []
|
||||
|
||||
var _cfg_ctrls = {}
|
||||
var opt_maker = null
|
||||
|
||||
func _init(cont):
|
||||
_base_container = cont
|
||||
|
||||
|
||||
func _add_title(text):
|
||||
var row = PanelControls.BaseGutPanelControl.new(text, text)
|
||||
_base_container.add_child(row)
|
||||
row.connect('draw', _on_title_cell_draw.bind(row))
|
||||
_all_titles.append(row)
|
||||
return row
|
||||
|
||||
func _add_ctrl(key, ctrl):
|
||||
_cfg_ctrls[key] = ctrl
|
||||
_base_container.add_child(ctrl)
|
||||
|
||||
|
||||
func _add_number(key, value, disp_text, v_min, v_max, hint=''):
|
||||
var ctrl = PanelControls.NumberControl.new(disp_text, value, v_min, v_max, hint)
|
||||
_add_ctrl(key, ctrl)
|
||||
return ctrl
|
||||
|
||||
|
||||
func _add_select(key, value, values, disp_text, hint=''):
|
||||
var ctrl = PanelControls.SelectControl.new(disp_text, value, values, hint)
|
||||
_add_ctrl(key, ctrl)
|
||||
return ctrl
|
||||
|
||||
|
||||
func _add_value(key, value, disp_text, hint=''):
|
||||
var ctrl = PanelControls.StringControl.new(disp_text, value, hint)
|
||||
_add_ctrl(key, ctrl)
|
||||
return ctrl
|
||||
|
||||
|
||||
func _add_boolean(key, value, disp_text, hint=''):
|
||||
var ctrl = PanelControls.BooleanControl.new(disp_text, value, hint)
|
||||
_add_ctrl(key, ctrl)
|
||||
return ctrl
|
||||
|
||||
|
||||
func _add_directory(key, value, disp_text, hint=''):
|
||||
var ctrl = PanelControls.DirectoryControl.new(disp_text, value, hint)
|
||||
_add_ctrl(key, ctrl)
|
||||
ctrl.dialog.title = disp_text
|
||||
return ctrl
|
||||
|
||||
|
||||
func _add_file(key, value, disp_text, hint=''):
|
||||
var ctrl = PanelControls.DirectoryControl.new(disp_text, value, hint)
|
||||
_add_ctrl(key, ctrl)
|
||||
ctrl.dialog.file_mode = ctrl.dialog.FILE_MODE_OPEN_FILE
|
||||
ctrl.dialog.title = disp_text
|
||||
return ctrl
|
||||
|
||||
|
||||
func _add_save_file_anywhere(key, value, disp_text, hint=''):
|
||||
var ctrl = PanelControls.DirectoryControl.new(disp_text, value, hint)
|
||||
_add_ctrl(key, ctrl)
|
||||
ctrl.dialog.file_mode = ctrl.dialog.FILE_MODE_SAVE_FILE
|
||||
ctrl.dialog.access = ctrl.dialog.ACCESS_FILESYSTEM
|
||||
ctrl.dialog.title = disp_text
|
||||
return ctrl
|
||||
|
||||
|
||||
func _add_color(key, value, disp_text, hint=''):
|
||||
var ctrl = PanelControls.ColorControl.new(disp_text, value, hint)
|
||||
_add_ctrl(key, ctrl)
|
||||
return ctrl
|
||||
opt_maker = GutUtils.OptionMaker.new(cont)
|
||||
_cfg_ctrls = opt_maker.controls
|
||||
# _base_container = cont
|
||||
|
||||
|
||||
func _add_save_load():
|
||||
var ctrl = PanelControls.SaveLoadControl.new('Config', '', '')
|
||||
_base_container.add_child(ctrl)
|
||||
|
||||
ctrl.save_path_chosen.connect(_on_save_path_chosen)
|
||||
ctrl.load_path_chosen.connect(_on_load_path_chosen)
|
||||
|
||||
_cfg_ctrls['save_load'] = ctrl
|
||||
#_cfg_ctrls['save_load'] = ctrl
|
||||
opt_maker.add_ctrl('save_load', ctrl)
|
||||
return ctrl
|
||||
|
||||
# ------------------
|
||||
# Events
|
||||
# ------------------
|
||||
func _on_title_cell_draw(which):
|
||||
which.draw_rect(Rect2(Vector2(0, 0), which.size), Color(0, 0, 0, .15))
|
||||
|
||||
|
||||
func _on_save_path_chosen(path):
|
||||
save_file(path)
|
||||
|
||||
|
|
@ -145,15 +73,7 @@ func get_config_issues():
|
|||
|
||||
|
||||
func clear():
|
||||
for key in _cfg_ctrls:
|
||||
_cfg_ctrls[key].free()
|
||||
|
||||
_cfg_ctrls.clear()
|
||||
|
||||
for entry in _all_titles:
|
||||
entry.free()
|
||||
|
||||
_all_titles.clear()
|
||||
opt_maker.clear()
|
||||
|
||||
|
||||
func save_file(path):
|
||||
|
|
@ -191,54 +111,65 @@ func set_options(opts):
|
|||
# _add_title('Save/Load')
|
||||
_add_save_load()
|
||||
|
||||
_add_title("Settings")
|
||||
_add_number("log_level", options.log_level, "Log Level", 0, 3,
|
||||
opt_maker.add_title("Settings")
|
||||
opt_maker.add_number("log_level", options.log_level, "Log Level", 0, 3,
|
||||
"Detail level for log messages.\n" + \
|
||||
"\t0: Errors and failures only.\n" + \
|
||||
"\t1: Adds all test names + warnings + info\n" + \
|
||||
"\t2: Shows all asserts\n" + \
|
||||
"\t3: Adds more stuff probably, maybe not.")
|
||||
_add_boolean('ignore_pause', options.ignore_pause, 'Ignore Pause',
|
||||
opt_maker.add_float("wait_log_delay", options.wait_log_delay, "Wait Log Delay", 0.1, 0.0, 999.1,
|
||||
"How long to wait before displaying 'Awaiting' messages.")
|
||||
opt_maker.add_boolean('ignore_pause', options.ignore_pause, 'Ignore Pause',
|
||||
"Ignore calls to pause_before_teardown")
|
||||
_add_boolean('hide_orphans', options.hide_orphans, 'Hide Orphans',
|
||||
opt_maker.add_boolean('hide_orphans', options.hide_orphans, 'Hide Orphans',
|
||||
'Do not display orphan counts in output.')
|
||||
_add_boolean('should_exit', options.should_exit, 'Exit on Finish',
|
||||
opt_maker.add_boolean('should_exit', options.should_exit, 'Exit on Finish',
|
||||
"Exit when tests finished.")
|
||||
_add_boolean('should_exit_on_success', options.should_exit_on_success, 'Exit on Success',
|
||||
opt_maker.add_boolean('should_exit_on_success', options.should_exit_on_success, 'Exit on Success',
|
||||
"Exit if there are no failures. Does nothing if 'Exit on Finish' is enabled.")
|
||||
_add_select('double_strategy', 'Script Only', ['Include Native', 'Script Only'], 'Double Strategy',
|
||||
opt_maker.add_select('double_strategy', 'Script Only', ['Include Native', 'Script Only'], 'Double Strategy',
|
||||
'"Include Native" will include native methods in Doubles. "Script Only" will not. ' + "\n" + \
|
||||
'The native method override warning is disabled when creating Doubles.' + "\n" + \
|
||||
'This is the default, you can override this at the script level or when creating doubles.')
|
||||
_cfg_ctrls.double_strategy.value = GutUtils.get_enum_value(
|
||||
options.double_strategy, GutUtils.DOUBLE_STRATEGY, GutUtils.DOUBLE_STRATEGY.SCRIPT_ONLY)
|
||||
_add_boolean('errors_cause_failure', !options.errors_do_not_cause_failure, 'Errors cause failures.',
|
||||
"When GUT generates an error (not an engine error) it causes tests to fail.")
|
||||
|
||||
|
||||
_add_title('Runner Appearance')
|
||||
hide_this = _add_boolean("gut_on_top", options.gut_on_top, "On Top",
|
||||
opt_maker.add_title("Fail Error Types")
|
||||
opt_maker.add_boolean("error_tracking", !options.no_error_tracking, 'Track Errors',
|
||||
"Enable/Disable GUT's ability to detect engine and push errors.")
|
||||
opt_maker.add_boolean('engine_errors_cause_failure', options.failure_error_types.has(GutConfig.FAIL_ERROR_TYPE_ENGINE),
|
||||
'Engine', 'Any script/engine error that occurs during a test will cause the test to fail.')
|
||||
opt_maker.add_boolean('push_error_errors_cause_failure', options.failure_error_types.has(GutConfig.FAIL_ERROR_TYPE_PUSH_ERROR),
|
||||
'Push', 'Any error generated by a call to push_error that occurs during a test will cause the test to fail.')
|
||||
opt_maker.add_boolean('gut_errors_cause_failure', options.failure_error_types.has(GutConfig.FAIL_ERROR_TYPE_GUT),
|
||||
'GUT', 'Any internal GUT error that occurs while a test is running will cause it to fail..')
|
||||
|
||||
|
||||
opt_maker.add_title('Runner Appearance')
|
||||
hide_this = opt_maker.add_boolean("gut_on_top", options.gut_on_top, "On Top",
|
||||
"The GUT Runner appears above children added during tests.")
|
||||
_add_number('opacity', options.opacity, 'Opacity', 0, 100,
|
||||
opt_maker.add_number('opacity', options.opacity, 'Opacity', 0, 100,
|
||||
"The opacity of GUT when tests are running.")
|
||||
hide_this = _add_boolean('should_maximize', options.should_maximize, 'Maximize',
|
||||
hide_this = opt_maker.add_boolean('should_maximize', options.should_maximize, 'Maximize',
|
||||
"Maximize GUT when tests are being run.")
|
||||
_add_boolean('compact_mode', options.compact_mode, 'Compact Mode',
|
||||
opt_maker.add_boolean('compact_mode', options.compact_mode, 'Compact Mode',
|
||||
'The runner will be in compact mode. This overrides Maximize.')
|
||||
_add_select('font_name', options.font_name, GutUtils.avail_fonts, 'Font',
|
||||
opt_maker.add_select('font_name', options.font_name, GutUtils.avail_fonts, 'Font',
|
||||
"The font to use for text output in the Gut Runner.")
|
||||
_add_number('font_size', options.font_size, 'Font Size', 5, 100,
|
||||
opt_maker.add_number('font_size', options.font_size, 'Font Size', 5, 100,
|
||||
"The font size for text output in the Gut Runner.")
|
||||
hide_this = _add_color('font_color', options.font_color, 'Font Color',
|
||||
hide_this = opt_maker.add_color('font_color', options.font_color, 'Font Color',
|
||||
"The font color for text output in the Gut Runner.")
|
||||
_add_color('background_color', options.background_color, 'Background Color',
|
||||
opt_maker.add_color('background_color', options.background_color, 'Background Color',
|
||||
"The background color for text output in the Gut Runner.")
|
||||
_add_boolean('disable_colors', options.disable_colors, 'Disable Formatting',
|
||||
opt_maker.add_boolean('disable_colors', options.disable_colors, 'Disable Formatting',
|
||||
'Disable formatting and colors used in the Runner. Does not affect panel output.')
|
||||
|
||||
|
||||
_titles.dirs = _add_title('Test Directories')
|
||||
_add_boolean('include_subdirs', options.include_subdirs, 'Include Subdirs',
|
||||
_titles.dirs = opt_maker.add_title('Test Directories')
|
||||
opt_maker.add_boolean('include_subdirs', options.include_subdirs, 'Include Subdirs',
|
||||
"Include subdirectories of the directories configured below.")
|
||||
|
||||
var dirs_to_load = options.configured_dirs
|
||||
|
|
@ -250,40 +181,35 @@ func set_options(opts):
|
|||
if(dirs_to_load.size() > i):
|
||||
value = dirs_to_load[i]
|
||||
|
||||
var test_dir = _add_directory(str('directory_', i), value, str(i))
|
||||
var test_dir = opt_maker.add_directory(str('directory_', i), value, str(i))
|
||||
test_dir.enabled_button.visible = true
|
||||
test_dir.enabled_button.button_pressed = options.dirs.has(value)
|
||||
|
||||
|
||||
_add_title("XML Output")
|
||||
_add_save_file_anywhere("junit_xml_file", options.junit_xml_file, "Output Path",
|
||||
"Path3D and filename where GUT should create a JUnit compliant XML file. " +
|
||||
opt_maker.add_title("XML Output")
|
||||
opt_maker.add_save_file_anywhere("junit_xml_file", options.junit_xml_file, "Output Path",
|
||||
"Path and filename where GUT should create a JUnit compliant XML file. " +
|
||||
"This file will contain the results of the last test run. To avoid " +
|
||||
"overriding the file use Include Timestamp.")
|
||||
_add_boolean("junit_xml_timestamp", options.junit_xml_timestamp, "Include Timestamp",
|
||||
opt_maker.add_boolean("junit_xml_timestamp", options.junit_xml_timestamp, "Include Timestamp",
|
||||
"Include a timestamp in the filename so that each run gets its own xml file.")
|
||||
|
||||
|
||||
_add_title('Hooks')
|
||||
_add_file('pre_run_script', options.pre_run_script, 'Pre-Run Hook',
|
||||
opt_maker.add_title('Hooks')
|
||||
opt_maker.add_file('pre_run_script', options.pre_run_script, 'Pre-Run Hook',
|
||||
'This script will be run by GUT before any tests are run.')
|
||||
_add_file('post_run_script', options.post_run_script, 'Post-Run Hook',
|
||||
opt_maker.add_file('post_run_script', options.post_run_script, 'Post-Run Hook',
|
||||
'This script will be run by GUT after all tests are run.')
|
||||
|
||||
|
||||
_add_title('Misc')
|
||||
_add_value('prefix', options.prefix, 'Script Prefix',
|
||||
opt_maker.add_title('Misc')
|
||||
opt_maker.add_value('prefix', options.prefix, 'Script Prefix',
|
||||
"The filename prefix for all test scripts.")
|
||||
_add_value('suffix', options.suffix, 'Script Suffix',
|
||||
opt_maker.add_value('suffix', options.suffix, 'Script Suffix',
|
||||
"Script suffix, including .gd extension. For example '_foo.gd'.")
|
||||
_add_number('paint_after', options.paint_after, 'Paint After', 0.0, 1.0,
|
||||
opt_maker.add_float('paint_after', options.paint_after, 'Paint After', .05, 0.0, 1.0,
|
||||
"How long GUT will wait before pausing for 1 frame to paint the screen. 0 is never.")
|
||||
|
||||
# since _add_number doesn't set step property, it will default to a step of
|
||||
# 1 and cast values to int. Give it a .5 step and re-set the value.
|
||||
_cfg_ctrls.paint_after.value_ctrl.step = .05
|
||||
_cfg_ctrls.paint_after.value = options.paint_after
|
||||
|
||||
|
||||
|
||||
func get_options(base_opts):
|
||||
|
|
@ -291,13 +217,12 @@ func get_options(base_opts):
|
|||
|
||||
# Settings
|
||||
to_return.log_level = _cfg_ctrls.log_level.value
|
||||
to_return.wait_log_delay = _cfg_ctrls.wait_log_delay.value
|
||||
to_return.ignore_pause = _cfg_ctrls.ignore_pause.value
|
||||
to_return.hide_orphans = _cfg_ctrls.hide_orphans.value
|
||||
to_return.should_exit = _cfg_ctrls.should_exit.value
|
||||
to_return.should_exit_on_success = _cfg_ctrls.should_exit_on_success.value
|
||||
to_return.double_strategy = _cfg_ctrls.double_strategy.value
|
||||
to_return.errors_do_not_cause_failure = !_cfg_ctrls.errors_cause_failure.value
|
||||
|
||||
|
||||
# Runner Appearance
|
||||
to_return.font_name = _cfg_ctrls.font_name.text
|
||||
|
|
@ -311,6 +236,17 @@ func get_options(base_opts):
|
|||
to_return.gut_on_top = _cfg_ctrls.gut_on_top.value
|
||||
to_return.paint_after = _cfg_ctrls.paint_after.value
|
||||
|
||||
# Fail Error Types
|
||||
to_return.no_error_tracking = !_cfg_ctrls.error_tracking
|
||||
|
||||
var fail_error_types = []
|
||||
if(_cfg_ctrls.engine_errors_cause_failure.value):
|
||||
fail_error_types.append(GutConfig.FAIL_ERROR_TYPE_ENGINE)
|
||||
if(_cfg_ctrls.push_error_errors_cause_failure.value):
|
||||
fail_error_types.append(GutConfig.FAIL_ERROR_TYPE_PUSH_ERROR)
|
||||
if(_cfg_ctrls.gut_errors_cause_failure.value):
|
||||
fail_error_types.append(GutConfig.FAIL_ERROR_TYPE_GUT)
|
||||
to_return.failure_error_types = fail_error_types
|
||||
|
||||
# Directories
|
||||
to_return.include_subdirs = _cfg_ctrls.include_subdirs.value
|
||||
|
|
|
|||
|
|
@ -1 +1 @@
|
|||
uid://xlv525p30gpr
|
||||
uid://chosc1tvfaduq
|
||||
|
|
|
|||
37
addons/gut/gui/gut_dock.gd
Normal file
37
addons/gut/gui/gut_dock.gd
Normal file
|
|
@ -0,0 +1,37 @@
|
|||
extends EditorDock
|
||||
|
||||
|
||||
var _panel : Control = null
|
||||
var _current_layout = -1
|
||||
|
||||
|
||||
func _update_layout(layout):
|
||||
_current_layout = layout
|
||||
if(_panel != null):
|
||||
if(layout == DOCK_LAYOUT_FLOATING):
|
||||
_windowed_mode()
|
||||
else:
|
||||
_dock_mode()
|
||||
|
||||
|
||||
# -------------
|
||||
# Private
|
||||
# -------------
|
||||
func _windowed_mode():
|
||||
_panel.show_layout_buttons(true)
|
||||
|
||||
|
||||
func _dock_mode():
|
||||
_panel.results_horiz_layout()
|
||||
_panel.show_layout_buttons(false)
|
||||
|
||||
|
||||
# -------------
|
||||
# Public
|
||||
# -------------
|
||||
func add_bottom_panel(gut_bottom_panel):
|
||||
_panel = gut_bottom_panel
|
||||
# Make floating button not supported right now
|
||||
add_child(_panel)
|
||||
_panel.make_floating_btn.visible = false
|
||||
_update_layout(_current_layout)
|
||||
1
addons/gut/gui/gut_dock.gd.uid
Normal file
1
addons/gut/gui/gut_dock.gd.uid
Normal file
|
|
@ -0,0 +1 @@
|
|||
uid://cmj50k82tckur
|
||||
|
|
@ -24,6 +24,7 @@ var _ctrls = {
|
|||
time_label = null,
|
||||
title = null,
|
||||
title_bar = null,
|
||||
tgl_word_wrap = null, # optional
|
||||
}
|
||||
|
||||
var _title_mouse = {
|
||||
|
|
@ -42,6 +43,8 @@ func _ready():
|
|||
_ctrls.btn_continue.pressed.connect(_on_continue_pressed)
|
||||
_ctrls.switch_modes.pressed.connect(_on_switch_modes_pressed)
|
||||
_ctrls.title_bar.gui_input.connect(_on_title_bar_input)
|
||||
if(_ctrls.tgl_word_wrap != null):
|
||||
_ctrls.tgl_word_wrap.toggled.connect(_on_word_wrap_toggled)
|
||||
|
||||
_ctrls.prog_script.value = 0
|
||||
_ctrls.prog_test.value = 0
|
||||
|
|
@ -79,6 +82,7 @@ func _populate_ctrls():
|
|||
_ctrls.time_label = _get_first_child_named('TimeLabel', self)
|
||||
_ctrls.title = _get_first_child_named("Title", self)
|
||||
_ctrls.title_bar = _get_first_child_named("TitleBar", self)
|
||||
_ctrls.tgl_word_wrap = _get_first_child_named("WordWrap", self)
|
||||
|
||||
|
||||
func _get_first_child_named(obj_name, parent_obj):
|
||||
|
|
@ -96,7 +100,7 @@ func _get_first_child_named(obj_name, parent_obj):
|
|||
to_return = _get_first_child_named(obj_name, kids[index])
|
||||
if(to_return == null):
|
||||
index += 1
|
||||
|
||||
|
||||
return to_return
|
||||
|
||||
|
||||
|
|
@ -157,6 +161,9 @@ func _on_gut_end_pause():
|
|||
func _on_switch_modes_pressed():
|
||||
switch_modes.emit()
|
||||
|
||||
|
||||
func _on_word_wrap_toggled(toggled):
|
||||
_ctrls.rtl.autowrap_mode = toggled
|
||||
# ------------------
|
||||
# Public
|
||||
# ------------------
|
||||
|
|
|
|||
|
|
@ -1 +1 @@
|
|||
uid://xsm23flin7t3
|
||||
uid://blvhsbnsvfyow
|
||||
|
|
|
|||
225
addons/gut/gui/gut_logo.gd
Normal file
225
addons/gut/gui/gut_logo.gd
Normal file
|
|
@ -0,0 +1,225 @@
|
|||
@tool
|
||||
extends Node2D
|
||||
|
||||
class Eyeball:
|
||||
extends Node2D
|
||||
|
||||
var _should_draw_laser = false
|
||||
var _laser_end_pos = Vector2.ZERO
|
||||
var _laser_timer : Timer = null
|
||||
var _color_tween : Tween
|
||||
var _size_tween : Tween
|
||||
|
||||
var sprite : Sprite2D = null
|
||||
var default_position = Vector2(0, 0)
|
||||
var move_radius = 25
|
||||
var move_center = Vector2(0, 0)
|
||||
var default_color = Color(0.31, 0.31, 0.31)
|
||||
var _color = default_color :
|
||||
set(val):
|
||||
_color = val
|
||||
queue_redraw()
|
||||
var color = _color :
|
||||
set(val):
|
||||
_start_color_tween(_color, val)
|
||||
get(): return _color
|
||||
var default_size = 70
|
||||
var _size = default_size :
|
||||
set(val):
|
||||
_size = val
|
||||
queue_redraw()
|
||||
var size = _size :
|
||||
set(val):
|
||||
_start_size_tween(_size, val)
|
||||
get(): return _size
|
||||
|
||||
|
||||
func _init(node):
|
||||
sprite = node
|
||||
default_position = sprite.position
|
||||
move_center = sprite.position
|
||||
# hijack the original sprite, because I want to draw it here but keep
|
||||
# the original in the scene for layout.
|
||||
position = sprite.position
|
||||
sprite.get_parent().add_child(self)
|
||||
sprite.visible = false
|
||||
|
||||
|
||||
func _ready():
|
||||
_laser_timer = Timer.new()
|
||||
_laser_timer.wait_time = .1
|
||||
_laser_timer.one_shot = true
|
||||
add_child(_laser_timer)
|
||||
_laser_timer.timeout.connect(func(): _should_draw_laser = false)
|
||||
|
||||
|
||||
func _process(_delta):
|
||||
if(_should_draw_laser):
|
||||
queue_redraw()
|
||||
|
||||
|
||||
func _start_color_tween(old_color, new_color):
|
||||
if(_color_tween != null and _color_tween.is_running()):
|
||||
_color_tween.kill()
|
||||
_color_tween = create_tween()
|
||||
_color_tween.tween_property(self, '_color', new_color, .3).from(old_color)
|
||||
_color_tween.play()
|
||||
|
||||
|
||||
func _start_size_tween(old_size, new_size):
|
||||
if(_size_tween != null and _size_tween.is_running()):
|
||||
_size_tween.kill()
|
||||
_size_tween = create_tween()
|
||||
_size_tween.tween_property(self, '_size', new_size, .3).from(old_size)
|
||||
_size_tween.play()
|
||||
|
||||
|
||||
var _laser_size = 20.0
|
||||
func _draw() -> void:
|
||||
draw_circle(Vector2.ZERO, size, color, true, -1, true)
|
||||
if(_should_draw_laser):
|
||||
var end_pos = (_laser_end_pos - global_position) * 2
|
||||
var laser_size = _laser_size * (float(size)/float(default_size))
|
||||
draw_line(Vector2.ZERO, end_pos, color, laser_size)
|
||||
draw_line(Vector2.ZERO, end_pos, Color(1, 1, 1, .5), laser_size * .8)
|
||||
|
||||
|
||||
# There's a bug in here where the eye shakes like crazy. It's a feature
|
||||
# now. Don't fix it.
|
||||
func look_at_local_position(local_pos):
|
||||
var dir = position.direction_to(local_pos)
|
||||
var dist = position.distance_to(local_pos)
|
||||
position = move_center + (dir * min(dist, move_radius))
|
||||
position.x = clamp(position.x, move_center.x - move_radius, move_center.x + move_radius)
|
||||
position.y = clamp(position.y, move_center.y - move_radius, move_center.y + move_radius)
|
||||
|
||||
|
||||
func reset():
|
||||
color = default_color
|
||||
size = default_size
|
||||
|
||||
|
||||
func eye_laser(global_pos):
|
||||
_should_draw_laser = true
|
||||
_laser_end_pos = global_pos
|
||||
_laser_timer.start()
|
||||
|
||||
|
||||
func _stop_laser():
|
||||
_should_draw_laser = false
|
||||
|
||||
|
||||
|
||||
# ------------------------------------------------------------------------------
|
||||
# ------------------------------------------------------------------------------
|
||||
var GutEditorGlobals = load('res://addons/gut/gui/editor_globals.gd')
|
||||
# Active means it's actively doing stuff. When this is not active the eyes
|
||||
# won't follow, but you can still make the sizes change by calling methods on
|
||||
# this.
|
||||
@export var active = false :
|
||||
set(val):
|
||||
active = val
|
||||
if(!active and is_inside_tree()):
|
||||
left_eye.position = left_eye.default_position
|
||||
right_eye.position = right_eye.default_position
|
||||
# When disabled, this will reset to default and you can't make it do anything.
|
||||
@export var disabled = false :
|
||||
set(val):
|
||||
disabled = val
|
||||
if(disabled and is_inside_tree()):
|
||||
left_eye.position = left_eye.default_position
|
||||
right_eye.position = right_eye.default_position
|
||||
left_eye.reset()
|
||||
right_eye.reset()
|
||||
modulate = Color.GRAY
|
||||
$BaseLogo.texture = _no_shine
|
||||
else:
|
||||
$BaseLogo.texture = _normal
|
||||
modulate = Color.WHITE
|
||||
|
||||
@onready var _reset_timer = $ResetTimer
|
||||
@onready var _face_button = $FaceButton
|
||||
@onready var left_eye : Eyeball = Eyeball.new($BaseLogo/LeftEye)
|
||||
@onready var right_eye : Eyeball = Eyeball.new($BaseLogo/RightEye)
|
||||
|
||||
var _no_shine = load("res://addons/gut/images/GutIconV2_no_shine.png")
|
||||
var _normal = load("res://addons/gut/images/GutIconV2_base.png")
|
||||
var _is_in_edited_scene = false
|
||||
|
||||
signal pressed
|
||||
|
||||
func _debug_ready():
|
||||
position = Vector2(500, 500)
|
||||
active = true
|
||||
|
||||
|
||||
func _ready():
|
||||
_is_in_edited_scene = GutEditorGlobals.is_being_edited_in_editor(self)
|
||||
|
||||
if(get_parent() == get_tree().root):
|
||||
_debug_ready()
|
||||
|
||||
disabled = disabled
|
||||
active = active
|
||||
left_eye.move_center.x -= 20
|
||||
right_eye.move_center.x += 10
|
||||
_face_button.modulate.a = 0.0
|
||||
|
||||
|
||||
func _process(_delta):
|
||||
if(active and !disabled and !_is_in_edited_scene):
|
||||
left_eye.look_at_local_position(get_local_mouse_position())
|
||||
right_eye.look_at_local_position(get_local_mouse_position())
|
||||
|
||||
|
||||
# ----------------
|
||||
# Events
|
||||
# ----------------
|
||||
func _on_reset_timer_timeout() -> void:
|
||||
left_eye.reset()
|
||||
right_eye.reset()
|
||||
|
||||
|
||||
func _on_face_button_pressed() -> void:
|
||||
pressed.emit()
|
||||
|
||||
|
||||
# ----------------
|
||||
# Public
|
||||
# ----------------
|
||||
func set_eye_scale(left, right=left):
|
||||
if(disabled or _is_in_edited_scene):
|
||||
return
|
||||
left_eye.size = left_eye.default_size * left
|
||||
right_eye.size = right_eye.default_size * right
|
||||
_reset_timer.start()
|
||||
|
||||
|
||||
func reset_eye_size():
|
||||
if(disabled or _is_in_edited_scene):
|
||||
return
|
||||
left_eye.size = left_eye.default_size
|
||||
right_eye.size = right_eye.default_size
|
||||
|
||||
|
||||
func set_eye_color(left, right=left):
|
||||
if(disabled or _is_in_edited_scene):
|
||||
return
|
||||
left_eye.color = left
|
||||
right_eye.color = right
|
||||
_reset_timer.start()
|
||||
|
||||
|
||||
func reset_eye_color():
|
||||
if(disabled or _is_in_edited_scene):
|
||||
return
|
||||
left_eye.color = left_eye.default_color
|
||||
right_eye.color = right_eye.default_color
|
||||
|
||||
|
||||
# I removed the eye lasers because they aren't ready yet. I've already spent
|
||||
# too much time on this logo. It's great, I love it...but it's been long
|
||||
# enough. This gives me, or someone else, something to do later.
|
||||
#func eye_lasers(global_pos):
|
||||
#left_eye.eye_laser(global_pos)
|
||||
#right_eye.eye_laser(global_pos)
|
||||
1
addons/gut/gui/gut_logo.gd.uid
Normal file
1
addons/gut/gui/gut_logo.gd.uid
Normal file
|
|
@ -0,0 +1 @@
|
|||
uid://b8lvgepb64m8t
|
||||
|
|
@ -37,12 +37,11 @@ var hide_result_tree = null
|
|||
var hide_output_text = null
|
||||
var hide_settings = null
|
||||
var use_colors = null # ? might be output panel
|
||||
|
||||
# var shortcut_run_all = null
|
||||
# var shortcut_run_current_script = null
|
||||
# var shortcut_run_current_inner = null
|
||||
# var shortcut_run_current_test = null
|
||||
# var shortcut_panel_button = null
|
||||
var run_externally = null
|
||||
var run_externally_options_dialog_size = null
|
||||
var shortcuts_dialog_size = null
|
||||
var gut_window_size = null
|
||||
var gut_window_on_top = null
|
||||
|
||||
|
||||
func _init(editor_settings):
|
||||
|
|
@ -52,12 +51,12 @@ func _init(editor_settings):
|
|||
hide_output_text = GutEditorPref.new('hide_output_text', false, editor_settings)
|
||||
hide_settings = GutEditorPref.new('hide_settings', false, editor_settings)
|
||||
use_colors = GutEditorPref.new('use_colors', true, editor_settings)
|
||||
run_externally = GutEditorPref.new('run_externally', false, editor_settings)
|
||||
run_externally_options_dialog_size = GutEditorPref.new('run_externally_options_dialog_size', Vector2i(-1, -1), editor_settings)
|
||||
shortcuts_dialog_size = GutEditorPref.new('shortcuts_dialog_size', Vector2i(-1, -1), editor_settings)
|
||||
gut_window_size = GutEditorPref.new('editor_window_size', Vector2i(-1, -1), editor_settings)
|
||||
gut_window_on_top = GutEditorPref.new('editor_window_on_top', false, editor_settings)
|
||||
|
||||
# shortcut_run_all = GutEditorPref.new('shortcut_run_all', EMPTY, editor_settings)
|
||||
# shortcut_run_current_script = GutEditorPref.new('shortcut_run_current_script', EMPTY, editor_settings)
|
||||
# shortcut_run_current_inner = GutEditorPref.new('shortcut_run_current_inner', EMPTY, editor_settings)
|
||||
# shortcut_run_current_test = GutEditorPref.new('shortcut_run_current_test', EMPTY, editor_settings)
|
||||
# shortcut_panel_button = GutEditorPref.new('shortcut_panel_button', EMPTY, editor_settings)
|
||||
|
||||
func save_it():
|
||||
for prop in get_property_list():
|
||||
|
|
@ -77,4 +76,4 @@ func erase_all():
|
|||
for prop in get_property_list():
|
||||
var val = get(prop.name)
|
||||
if(val is GutEditorPref):
|
||||
val.erase()
|
||||
val.erase()
|
||||
|
|
|
|||
|
|
@ -1 +1 @@
|
|||
uid://3n0bh8lrcprr
|
||||
uid://dsndkn6whyiov
|
||||
|
|
|
|||
124
addons/gut/gui/option_maker.gd
Normal file
124
addons/gut/gui/option_maker.gd
Normal file
|
|
@ -0,0 +1,124 @@
|
|||
var PanelControls = load("res://addons/gut/gui/panel_controls.gd")
|
||||
|
||||
# All titles so we can free them when we want.
|
||||
var _all_titles = []
|
||||
|
||||
|
||||
var base_container = null
|
||||
# All the various PanelControls indexed by thier keys.
|
||||
var controls = {}
|
||||
|
||||
|
||||
func _init(cont):
|
||||
base_container = cont
|
||||
|
||||
|
||||
func add_title(text):
|
||||
var row = PanelControls.BaseGutPanelControl.new(text, text)
|
||||
base_container.add_child(row)
|
||||
row.connect('draw', _on_title_cell_draw.bind(row))
|
||||
_all_titles.append(row)
|
||||
return row
|
||||
|
||||
|
||||
func add_ctrl(key, ctrl):
|
||||
controls[key] = ctrl
|
||||
base_container.add_child(ctrl)
|
||||
|
||||
|
||||
func add_number(key, value, disp_text, v_min, v_max, hint=''):
|
||||
var ctrl = PanelControls.NumberControl.new(disp_text, value, v_min, v_max, hint)
|
||||
add_ctrl(key, ctrl)
|
||||
return ctrl
|
||||
|
||||
|
||||
func add_float(key, value, disp_text, step, v_min, v_max, hint=''):
|
||||
var ctrl = PanelControls.FloatControl.new(disp_text, value, step, v_min, v_max, hint)
|
||||
add_ctrl(key, ctrl)
|
||||
return ctrl
|
||||
|
||||
|
||||
func add_select(key, value, values, disp_text, hint=''):
|
||||
var ctrl = PanelControls.SelectControl.new(disp_text, value, values, hint)
|
||||
add_ctrl(key, ctrl)
|
||||
return ctrl
|
||||
|
||||
|
||||
func add_value(key, value, disp_text, hint=''):
|
||||
var ctrl = PanelControls.StringControl.new(disp_text, value, hint)
|
||||
add_ctrl(key, ctrl)
|
||||
return ctrl
|
||||
|
||||
func add_multiline_text(key, value, disp_text, hint=''):
|
||||
var ctrl = PanelControls.MultiLineStringControl.new(disp_text, value, hint)
|
||||
add_ctrl(key, ctrl)
|
||||
return ctrl
|
||||
|
||||
func add_boolean(key, value, disp_text, hint=''):
|
||||
var ctrl = PanelControls.BooleanControl.new(disp_text, value, hint)
|
||||
add_ctrl(key, ctrl)
|
||||
return ctrl
|
||||
|
||||
|
||||
func add_directory(key, value, disp_text, hint=''):
|
||||
var ctrl = PanelControls.DirectoryControl.new(disp_text, value, hint)
|
||||
add_ctrl(key, ctrl)
|
||||
ctrl.dialog.title = disp_text
|
||||
return ctrl
|
||||
|
||||
|
||||
func add_file(key, value, disp_text, hint=''):
|
||||
var ctrl = PanelControls.DirectoryControl.new(disp_text, value, hint)
|
||||
add_ctrl(key, ctrl)
|
||||
ctrl.dialog.file_mode = ctrl.dialog.FILE_MODE_OPEN_FILE
|
||||
ctrl.dialog.title = disp_text
|
||||
return ctrl
|
||||
|
||||
|
||||
func add_save_file_anywhere(key, value, disp_text, hint=''):
|
||||
var ctrl = PanelControls.DirectoryControl.new(disp_text, value, hint)
|
||||
add_ctrl(key, ctrl)
|
||||
ctrl.dialog.file_mode = ctrl.dialog.FILE_MODE_SAVE_FILE
|
||||
ctrl.dialog.access = ctrl.dialog.ACCESS_FILESYSTEM
|
||||
ctrl.dialog.title = disp_text
|
||||
return ctrl
|
||||
|
||||
|
||||
func add_color(key, value, disp_text, hint=''):
|
||||
var ctrl = PanelControls.ColorControl.new(disp_text, value, hint)
|
||||
add_ctrl(key, ctrl)
|
||||
return ctrl
|
||||
|
||||
|
||||
var _blurbs = 0
|
||||
func add_blurb(text):
|
||||
var ctrl = RichTextLabel.new()
|
||||
ctrl.fit_content = true
|
||||
ctrl.bbcode_enabled = true
|
||||
ctrl.autowrap_mode = TextServer.AUTOWRAP_WORD_SMART
|
||||
ctrl.text = text
|
||||
add_ctrl(str("blurb_", _blurbs), ctrl)
|
||||
return ctrl
|
||||
|
||||
|
||||
# ------------------
|
||||
# Events
|
||||
# ------------------
|
||||
func _on_title_cell_draw(which):
|
||||
which.draw_rect(Rect2(Vector2(0, 0), which.size), Color(0, 0, 0, .15))
|
||||
|
||||
|
||||
# ------------------
|
||||
# Public
|
||||
# ------------------
|
||||
|
||||
func clear():
|
||||
for key in controls:
|
||||
controls[key].free()
|
||||
|
||||
controls.clear()
|
||||
|
||||
for entry in _all_titles:
|
||||
entry.free()
|
||||
|
||||
_all_titles.clear()
|
||||
1
addons/gut/gui/option_maker.gd.uid
Normal file
1
addons/gut/gui/option_maker.gd.uid
Normal file
|
|
@ -0,0 +1 @@
|
|||
uid://bjahqsqo645sf
|
||||
|
|
@ -78,6 +78,17 @@ class NumberControl:
|
|||
value_ctrl.value = val
|
||||
|
||||
|
||||
# ------------------------------------------------------------------------------
|
||||
# ------------------------------------------------------------------------------
|
||||
class FloatControl:
|
||||
extends NumberControl
|
||||
|
||||
func _init(title, val, step, v_min, v_max, hint=""):
|
||||
super._init(title, val, v_min, v_max, hint)
|
||||
value_ctrl.step = step
|
||||
value_ctrl.value = val
|
||||
|
||||
|
||||
# ------------------------------------------------------------------------------
|
||||
# ------------------------------------------------------------------------------
|
||||
class StringControl:
|
||||
|
|
@ -93,6 +104,38 @@ class StringControl:
|
|||
value_ctrl.text_changed.connect(_on_text_changed)
|
||||
value_ctrl.select_all_on_focus = true
|
||||
add_child(value_ctrl)
|
||||
if(title == ''):
|
||||
label.visible = false
|
||||
|
||||
func _on_text_changed(new_value):
|
||||
changed.emit()
|
||||
|
||||
func get_value():
|
||||
return value_ctrl.text
|
||||
|
||||
func set_value(val):
|
||||
value_ctrl.text = val
|
||||
|
||||
|
||||
|
||||
# ------------------------------------------------------------------------------
|
||||
# ------------------------------------------------------------------------------
|
||||
class MultiLineStringControl:
|
||||
extends BaseGutPanelControl
|
||||
|
||||
var value_ctrl = TextEdit.new()
|
||||
|
||||
func _init(title, val, hint=""):
|
||||
super._init(title, val, hint)
|
||||
var vbox = VBoxContainer.new()
|
||||
vbox.size_flags_horizontal = SIZE_EXPAND_FILL
|
||||
add_child(vbox)
|
||||
label.reparent(vbox)
|
||||
value_ctrl.size_flags_horizontal = value_ctrl.SIZE_EXPAND_FILL
|
||||
value_ctrl.text = val
|
||||
value_ctrl.text_changed.connect(_on_text_changed)
|
||||
value_ctrl.scroll_fit_content_height = true
|
||||
vbox.add_child(value_ctrl)
|
||||
|
||||
func _on_text_changed(new_value):
|
||||
changed.emit()
|
||||
|
|
|
|||
|
|
@ -1 +1 @@
|
|||
uid://48ebclaq0ewd
|
||||
uid://db54jy04d8w7p
|
||||
|
|
|
|||
|
|
@ -18,6 +18,8 @@ dest_files=["res://.godot/imported/play.png-5c90e88e8136487a183a099d67a7de24.cte
|
|||
compress/mode=0
|
||||
compress/high_quality=false
|
||||
compress/lossy_quality=0.7
|
||||
compress/uastc_level=0
|
||||
compress/rdo_quality_loss=0.0
|
||||
compress/hdr_compression=1
|
||||
compress/normal_map=0
|
||||
compress/channel_pack=0
|
||||
|
|
@ -25,6 +27,10 @@ mipmaps/generate=false
|
|||
mipmaps/limit=-1
|
||||
roughness/mode=0
|
||||
roughness/src_normal=""
|
||||
process/channel_remap/red=0
|
||||
process/channel_remap/green=1
|
||||
process/channel_remap/blue=2
|
||||
process/channel_remap/alpha=3
|
||||
process/fix_alpha_border=true
|
||||
process/premult_alpha=false
|
||||
process/normal_map_invert_y=false
|
||||
|
|
|
|||
|
|
@ -16,4 +16,3 @@ func _ready() -> void:
|
|||
var runner : Node = load("res://addons/gut/gui/GutRunner.tscn").instantiate()
|
||||
add_child(runner)
|
||||
runner.run_from_editor()
|
||||
GutLoader.restore_ignore_addons()
|
||||
|
|
|
|||
|
|
@ -1 +1 @@
|
|||
uid://dkqis5sjx5mb4
|
||||
uid://bwf2iuidqfkpl
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
[gd_scene load_steps=2 format=3 uid="uid://bgj3fm5d8yvjw"]
|
||||
|
||||
[ext_resource type="Script" path="res://addons/gut/gui/run_from_editor.gd" id="1_53pap"]
|
||||
[ext_resource type="Script" uid="uid://bwf2iuidqfkpl" path="res://addons/gut/gui/run_from_editor.gd" id="1_53pap"]
|
||||
|
||||
[node name="RunFromEditor" type="Node2D"]
|
||||
script = ExtResource("1_53pap")
|
||||
|
|
|
|||
|
|
@ -1,239 +0,0 @@
|
|||
# Holds weakrefs to a ScriptTextEditor and related children nodes
|
||||
# that might be useful. Though the CodeEdit is really the only one, but
|
||||
# since the tree may change, the first TextEdit under a CodeTextEditor is
|
||||
# the one we use...so we hold a ref to the CodeTextEditor too.
|
||||
class ScriptEditorControlRef:
|
||||
var _text_edit = null
|
||||
var _script_editor = null
|
||||
var _code_editor = null
|
||||
|
||||
func _init(script_edit):
|
||||
_script_editor = weakref(script_edit)
|
||||
_populate_controls()
|
||||
# print("_script_editor = ", script_edit, ' vis = ', is_visible())
|
||||
|
||||
|
||||
func _populate_controls():
|
||||
# who knows if the tree will change so get the first instance of each
|
||||
# type of control we care about. Chances are there won't be more than
|
||||
# one of these in the future, but their position in the tree may change.
|
||||
_code_editor = weakref(_get_first_child_named('CodeTextEditor', _script_editor.get_ref()))
|
||||
_text_edit = weakref(_get_first_child_named("CodeEdit", _code_editor.get_ref()))
|
||||
|
||||
|
||||
func _get_first_child_named(obj_name, parent_obj):
|
||||
if(parent_obj == null):
|
||||
return null
|
||||
|
||||
var kids = parent_obj.get_children()
|
||||
var index = 0
|
||||
var to_return = null
|
||||
|
||||
while(index < kids.size() and to_return == null):
|
||||
if(str(kids[index]).find(str("<", obj_name)) != -1):
|
||||
to_return = kids[index]
|
||||
else:
|
||||
to_return = _get_first_child_named(obj_name, kids[index])
|
||||
if(to_return == null):
|
||||
index += 1
|
||||
|
||||
return to_return
|
||||
|
||||
|
||||
func get_script_text_edit():
|
||||
return _script_editor.get_ref()
|
||||
|
||||
|
||||
func get_text_edit():
|
||||
# ScriptTextEditors that are loaded when the project is opened
|
||||
# do not have their children populated yet. So if we may have to
|
||||
# _populate_controls again if we don't have one.
|
||||
if(_text_edit == null):
|
||||
_populate_controls()
|
||||
return _text_edit.get_ref()
|
||||
|
||||
|
||||
func get_script_editor():
|
||||
return _script_editor
|
||||
|
||||
|
||||
func is_visible():
|
||||
var to_return = false
|
||||
if(_script_editor.get_ref()):
|
||||
to_return = _script_editor.get_ref().visible
|
||||
return to_return
|
||||
|
||||
# ##############################################################################
|
||||
#
|
||||
# ##############################################################################
|
||||
|
||||
# Used to make searching for the controls easier and faster.
|
||||
var _script_editors_parent = null
|
||||
# reference the ScriptEditor instance
|
||||
var _script_editor = null
|
||||
# Array of ScriptEditorControlRef containing all the opened ScriptTextEditors
|
||||
# and related controls at the time of the last refresh.
|
||||
var _script_editor_controls = []
|
||||
|
||||
var _method_prefix = 'test_'
|
||||
var _inner_class_prefix = 'Test'
|
||||
|
||||
func _init(script_edit):
|
||||
_script_editor = script_edit
|
||||
refresh()
|
||||
|
||||
|
||||
func _is_script_editor(obj):
|
||||
return str(obj).find('<ScriptTextEditor') != -1
|
||||
|
||||
|
||||
# Find the first ScriptTextEditor and then get its parent. Done this way
|
||||
# because who knows if the parent object will change. This is somewhat
|
||||
# future proofed.
|
||||
func _find_script_editors_parent():
|
||||
var _first_editor = _get_first_child_of_type_name("ScriptTextEditor", _script_editor)
|
||||
if(_first_editor != null):
|
||||
_script_editors_parent = _first_editor.get_parent()
|
||||
|
||||
|
||||
func _populate_editors():
|
||||
if(_script_editors_parent == null):
|
||||
return
|
||||
|
||||
_script_editor_controls.clear()
|
||||
for child in _script_editors_parent.get_children():
|
||||
if(_is_script_editor(child)):
|
||||
var ref = ScriptEditorControlRef.new(child)
|
||||
_script_editor_controls.append(ref)
|
||||
|
||||
# Yes, this is the same as the one above but with a different name. This was
|
||||
# easier than trying to find a place where it could be used by both.
|
||||
func _get_first_child_of_type_name(obj_name, parent_obj):
|
||||
if(parent_obj == null):
|
||||
# print('aborting search for ', obj_name, ' parent is null')
|
||||
return null
|
||||
|
||||
var kids = parent_obj.get_children()
|
||||
var index = 0
|
||||
var to_return = null
|
||||
|
||||
var search_for = str("<", obj_name)
|
||||
# print('searching for ', search_for, ' in ', parent_obj, ' kids ', kids.size())
|
||||
while(index < kids.size() and to_return == null):
|
||||
var this_one = str(kids[index])
|
||||
# print(search_for, ' :: ', this_one)
|
||||
if(this_one.find(search_for) != -1):
|
||||
to_return = kids[index]
|
||||
else:
|
||||
to_return = _get_first_child_of_type_name(obj_name, kids[index])
|
||||
if(to_return == null):
|
||||
index += 1
|
||||
|
||||
return to_return
|
||||
|
||||
|
||||
func _get_func_name_from_line(text):
|
||||
text = text.strip_edges()
|
||||
var left = text.split("(")[0]
|
||||
var func_name = left.split(" ")[1]
|
||||
return func_name
|
||||
|
||||
|
||||
func _get_class_name_from_line(text):
|
||||
text = text.strip_edges()
|
||||
var right = text.split(" ")[1]
|
||||
var the_name = right.rstrip(":")
|
||||
return the_name
|
||||
|
||||
func refresh():
|
||||
if(_script_editors_parent == null):
|
||||
_find_script_editors_parent()
|
||||
# print("script editors parent = ", _script_editors_parent)
|
||||
|
||||
if(_script_editors_parent != null):
|
||||
_populate_editors()
|
||||
|
||||
# print("script editor controls = ", _script_editor_controls)
|
||||
|
||||
|
||||
func get_current_text_edit():
|
||||
var cur_script_editor = null
|
||||
var idx = 0
|
||||
|
||||
while(idx < _script_editor_controls.size() and cur_script_editor == null):
|
||||
if(_script_editor_controls[idx].is_visible()):
|
||||
cur_script_editor = _script_editor_controls[idx]
|
||||
else:
|
||||
idx += 1
|
||||
|
||||
var to_return = null
|
||||
if(cur_script_editor != null):
|
||||
to_return = cur_script_editor.get_text_edit()
|
||||
|
||||
return to_return
|
||||
|
||||
|
||||
func get_script_editor_controls():
|
||||
var to_return = []
|
||||
for ctrl_ref in _script_editor_controls:
|
||||
to_return.append(ctrl_ref.get_script_text_edit())
|
||||
|
||||
return to_return
|
||||
|
||||
|
||||
func get_line_info():
|
||||
var editor = get_current_text_edit()
|
||||
if(editor == null):
|
||||
return
|
||||
|
||||
var info = {
|
||||
script = null,
|
||||
inner_class = null,
|
||||
test_method = null
|
||||
}
|
||||
|
||||
var line = editor.get_caret_line()
|
||||
var done_func = false
|
||||
var done_inner = false
|
||||
while(line > 0 and (!done_func or !done_inner)):
|
||||
if(editor.can_fold_line(line)):
|
||||
var text = editor.get_line(line)
|
||||
var strip_text = text.strip_edges(true, false) # only left
|
||||
|
||||
if(!done_func and strip_text.begins_with("func ")):
|
||||
var func_name = _get_func_name_from_line(text)
|
||||
if(func_name.begins_with(_method_prefix)):
|
||||
info.test_method = func_name
|
||||
done_func = true
|
||||
# If the func line is left justified then there won't be any
|
||||
# inner classes above it.
|
||||
if(strip_text == text):
|
||||
done_inner = true
|
||||
|
||||
if(!done_inner and strip_text.begins_with("class")):
|
||||
var inner_name = _get_class_name_from_line(text)
|
||||
if(inner_name.begins_with(_inner_class_prefix)):
|
||||
info.inner_class = inner_name
|
||||
done_inner = true
|
||||
# if we found an inner class then we are already past
|
||||
# any test the cursor could be in.
|
||||
done_func = true
|
||||
line -= 1
|
||||
|
||||
return info
|
||||
|
||||
|
||||
func get_method_prefix():
|
||||
return _method_prefix
|
||||
|
||||
|
||||
func set_method_prefix(method_prefix):
|
||||
_method_prefix = method_prefix
|
||||
|
||||
|
||||
func get_inner_class_prefix():
|
||||
return _inner_class_prefix
|
||||
|
||||
|
||||
func set_inner_class_prefix(inner_class_prefix):
|
||||
_inner_class_prefix = inner_class_prefix
|
||||
|
|
@ -1 +0,0 @@
|
|||
uid://dsc4xxr52mh52
|
||||
Loading…
Add table
Add a link
Reference in a new issue