Initial Commit
Initial commit of Code Base.
This commit is contained in:
parent
293b1213e1
commit
c11a4ebbc2
653 changed files with 36893 additions and 1 deletions
55
addons/twitcher/editor/setup/file_select.gd
Normal file
55
addons/twitcher/editor/setup/file_select.gd
Normal file
|
|
@ -0,0 +1,55 @@
|
|||
@tool
|
||||
extends Control
|
||||
|
||||
class_name FileSelect
|
||||
|
||||
@export var default_path: String
|
||||
@export var path: String: set = update_filepath
|
||||
@export var filters: PackedStringArray: set = update_filters
|
||||
|
||||
@onready var line_edit: LineEdit = %LineEdit
|
||||
@onready var button: Button = %Button
|
||||
@onready var file_dialog: FileDialog = %FileDialog
|
||||
|
||||
signal file_selected(path: String)
|
||||
|
||||
|
||||
func _ready() -> void:
|
||||
var icon = EditorInterface.get_editor_theme().get_icon(&"FileBrowse", &"EditorIcons")
|
||||
button.icon = icon
|
||||
button.pressed.connect(_on_open_file_dialog)
|
||||
file_dialog.file_selected.connect(_on_file_selected)
|
||||
line_edit.text_changed.connect(_on_path_changed)
|
||||
update_filepath(path)
|
||||
update_filters(filters)
|
||||
|
||||
|
||||
func update_filepath(new_path: String) -> void:
|
||||
if new_path == null || new_path == "":
|
||||
new_path = default_path
|
||||
path = new_path
|
||||
if is_inside_tree():
|
||||
line_edit.text = new_path
|
||||
file_dialog.current_path = new_path
|
||||
|
||||
|
||||
func update_filters(new_filters: PackedStringArray) -> void:
|
||||
filters = new_filters
|
||||
if is_inside_tree():
|
||||
file_dialog.filters = new_filters
|
||||
|
||||
|
||||
func _on_open_file_dialog() -> void:
|
||||
file_dialog.show()
|
||||
|
||||
|
||||
func _on_path_changed(new_path: String) -> void:
|
||||
file_dialog.current_path = new_path
|
||||
path = new_path
|
||||
file_selected.emit(new_path)
|
||||
|
||||
|
||||
func _on_file_selected(new_path: String) -> void:
|
||||
line_edit.text = new_path
|
||||
path = new_path
|
||||
file_selected.emit(new_path)
|
||||
1
addons/twitcher/editor/setup/file_select.gd.uid
Normal file
1
addons/twitcher/editor/setup/file_select.gd.uid
Normal file
|
|
@ -0,0 +1 @@
|
|||
uid://cgfc1nq4f4nae
|
||||
40
addons/twitcher/editor/setup/file_select.tscn
Normal file
40
addons/twitcher/editor/setup/file_select.tscn
Normal file
|
|
@ -0,0 +1,40 @@
|
|||
[gd_scene load_steps=4 format=3 uid="uid://b7smp156mdns6"]
|
||||
|
||||
[ext_resource type="Script" uid="uid://cgfc1nq4f4nae" path="res://addons/twitcher/editor/setup/file_select.gd" id="1_lnnjv"]
|
||||
|
||||
[sub_resource type="Image" id="Image_lnnjv"]
|
||||
data = {
|
||||
"data": PackedByteArray(0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 0, 0, 0, 0, 225, 225, 225, 127, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 0, 0, 0, 0, 224, 224, 224, 255, 225, 225, 225, 127, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 0, 0, 0, 0, 224, 224, 224, 255, 224, 224, 224, 255, 225, 225, 225, 127, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 0, 0, 0, 0, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 225, 225, 225, 127, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 238, 225, 225, 225, 150, 225, 225, 225, 150, 224, 224, 224, 221, 224, 224, 224, 148, 224, 224, 224, 168, 224, 224, 224, 228, 224, 224, 224, 156, 224, 224, 224, 160, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 238, 230, 230, 230, 30, 255, 255, 255, 1, 255, 255, 255, 1, 0, 0, 0, 0, 255, 255, 255, 1, 255, 255, 255, 1, 0, 0, 0, 0, 255, 255, 255, 1, 255, 255, 255, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 224, 224, 224, 255, 224, 224, 224, 255, 225, 225, 225, 150, 0, 0, 0, 0, 224, 224, 224, 194, 224, 224, 224, 193, 0, 0, 0, 0, 224, 224, 224, 194, 224, 224, 224, 193, 0, 0, 0, 0, 224, 224, 224, 194, 224, 224, 224, 193, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 224, 224, 224, 255, 224, 224, 224, 255, 224, 224, 224, 153, 0, 0, 0, 0, 225, 225, 225, 191, 224, 224, 224, 189, 0, 0, 0, 0, 225, 225, 225, 191, 224, 224, 224, 189, 0, 0, 0, 0, 225, 225, 225, 191, 224, 224, 224, 189, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0),
|
||||
"format": "RGBA8",
|
||||
"height": 16,
|
||||
"mipmaps": false,
|
||||
"width": 16
|
||||
}
|
||||
|
||||
[sub_resource type="ImageTexture" id="ImageTexture_7udr7"]
|
||||
image = SubResource("Image_lnnjv")
|
||||
|
||||
[node name="FileSelect" type="HBoxContainer"]
|
||||
anchors_preset = 15
|
||||
anchor_right = 1.0
|
||||
anchor_bottom = 1.0
|
||||
grow_horizontal = 2
|
||||
grow_vertical = 2
|
||||
size_flags_horizontal = 3
|
||||
script = ExtResource("1_lnnjv")
|
||||
|
||||
[node name="LineEdit" type="LineEdit" parent="."]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
tooltip_text = "Location where the OAuth Settings get saved to."
|
||||
|
||||
[node name="Button" type="Button" parent="."]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
icon = SubResource("ImageTexture_7udr7")
|
||||
|
||||
[node name="FileDialog" type="FileDialog" parent="."]
|
||||
unique_name_in_owner = true
|
||||
auto_translate_mode = 1
|
||||
initial_position = 1
|
||||
24
addons/twitcher/editor/setup/focus_child_show.gd
Normal file
24
addons/twitcher/editor/setup/focus_child_show.gd
Normal file
|
|
@ -0,0 +1,24 @@
|
|||
extends Node
|
||||
|
||||
@export var show_elements: Array[Control] = []
|
||||
|
||||
|
||||
func _ready() -> void:
|
||||
for element: Control in show_elements:
|
||||
element.hide()
|
||||
|
||||
for child in get_children():
|
||||
if child.has_signal(&"focus_entered"):
|
||||
child.connect(&"focus_entered", _on_focus_entered)
|
||||
if child.has_signal(&"focus_exited"):
|
||||
child.connect(&"focus_exited", _on_focus_exited)
|
||||
|
||||
|
||||
func _on_focus_entered() -> void:
|
||||
for element: Node in show_elements:
|
||||
element.show()
|
||||
|
||||
|
||||
func _on_focus_exited() -> void:
|
||||
for element: Node in show_elements:
|
||||
element.hide()
|
||||
1
addons/twitcher/editor/setup/focus_child_show.gd.uid
Normal file
1
addons/twitcher/editor/setup/focus_child_show.gd.uid
Normal file
|
|
@ -0,0 +1 @@
|
|||
uid://ddugotjvuahex
|
||||
101
addons/twitcher/editor/setup/page_authorization.gd
Normal file
101
addons/twitcher/editor/setup/page_authorization.gd
Normal file
|
|
@ -0,0 +1,101 @@
|
|||
@tool
|
||||
extends Node
|
||||
|
||||
const TwitchEditorSettings = preload("res://addons/twitcher/editor/twitch_editor_settings.gd")
|
||||
const TwitchTweens = preload("res://addons/twitcher/editor/twitch_tweens.gd")
|
||||
const TWITCH_SERVICE = preload("res://addons/twitcher/twitch_service.tscn")
|
||||
|
||||
@onready var authorization_explaination: RichTextLabel = %AuthExplain
|
||||
|
||||
@onready var client_id: LineEdit = %ClientId
|
||||
@onready var client_secret: LineEdit = %ClientSecret
|
||||
@onready var redirect_url: LineEdit = %RedirectURL
|
||||
|
||||
@onready var oauth_setting_file_select: FileSelect = %OauthSettingFileSelect
|
||||
@onready var token_file_select: FileSelect = %TokenFileSelect
|
||||
|
||||
@onready var to_documentation: Button = %ToDocumentation
|
||||
|
||||
@onready var o_auth_save: Button = %OAuthSave
|
||||
@onready var test_response: Label = %TestResponse
|
||||
|
||||
var has_changes: bool:
|
||||
set(val):
|
||||
has_changes = val
|
||||
changed.emit.call_deferred()
|
||||
o_auth_save.text = o_auth_save.text.trim_suffix(" (unsaved changes)")
|
||||
if has_changes: o_auth_save.text += " (unsaved changes)"
|
||||
|
||||
signal changed
|
||||
|
||||
|
||||
func _ready() -> void:
|
||||
authorization_explaination.meta_clicked.connect(_on_link_clicked)
|
||||
|
||||
redirect_url.text_changed.connect(_on_text_changed)
|
||||
client_id.text_changed.connect(_on_text_changed)
|
||||
client_secret.text_changed.connect(_on_text_changed)
|
||||
to_documentation.pressed.connect(_on_to_documentation_pressed)
|
||||
oauth_setting_file_select.file_selected.connect(_on_file_changed)
|
||||
token_file_select.file_selected.connect(_on_file_changed)
|
||||
|
||||
o_auth_save.pressed.connect(_on_save)
|
||||
|
||||
_load_oauth_setting()
|
||||
|
||||
|
||||
func _load_oauth_setting() -> void:
|
||||
var setting: OAuthSetting = TwitchEditorSettings.editor_oauth_setting
|
||||
client_id.text = setting.client_id
|
||||
client_secret.text = setting.get_client_secret()
|
||||
redirect_url.text = setting.redirect_url
|
||||
|
||||
|
||||
func _on_link_clicked(link: Variant) -> void:
|
||||
OS.shell_open(link)
|
||||
|
||||
|
||||
func _on_text_changed(val: String) -> void:
|
||||
reset_response_message()
|
||||
var setting: OAuthSetting = TwitchEditorSettings.editor_oauth_setting
|
||||
setting.client_id = client_id.text
|
||||
setting.set_client_secret(client_secret.text)
|
||||
setting.redirect_url = redirect_url.text
|
||||
has_changes = true
|
||||
|
||||
|
||||
func reset_response_message() -> void:
|
||||
test_response.text = ""
|
||||
|
||||
|
||||
func _on_file_changed() -> void:
|
||||
has_changes = true
|
||||
|
||||
|
||||
func is_auth_existing() -> bool:
|
||||
return is_instance_valid(TwitchEditorSettings.editor_oauth_setting)
|
||||
|
||||
|
||||
func _on_save() -> void:
|
||||
TwitchEditorSettings.save_editor_oauth_setting()
|
||||
TwitchEditorSettings.save_editor_oauth_token()
|
||||
|
||||
var setting_path = oauth_setting_file_select.path
|
||||
var setting = TwitchEditorSettings.editor_oauth_setting.duplicate(true)
|
||||
setting.take_over_path(setting_path)
|
||||
ResourceSaver.save(setting, setting_path)
|
||||
TwitchEditorSettings.game_oauth_setting = setting
|
||||
|
||||
var token_path = token_file_select.path
|
||||
var token = TwitchEditorSettings.editor_oauth_token.duplicate()
|
||||
token.take_over_path(token_path)
|
||||
ResourceSaver.save(token, token_path)
|
||||
TwitchEditorSettings.game_oauth_token = token
|
||||
|
||||
TwitchTweens.flash(o_auth_save, Color.GREEN)
|
||||
ProjectSettings.save()
|
||||
has_changes = false
|
||||
|
||||
|
||||
func _on_to_documentation_pressed() -> void:
|
||||
OS.shell_open("https://dev.twitch.tv/docs/authentication/")
|
||||
1
addons/twitcher/editor/setup/page_authorization.gd.uid
Normal file
1
addons/twitcher/editor/setup/page_authorization.gd.uid
Normal file
|
|
@ -0,0 +1 @@
|
|||
uid://dxql15j5ornlc
|
||||
182
addons/twitcher/editor/setup/page_authorization.tscn
Normal file
182
addons/twitcher/editor/setup/page_authorization.tscn
Normal file
|
|
@ -0,0 +1,182 @@
|
|||
[gd_scene load_steps=6 format=3 uid="uid://dm6jvnuikxtei"]
|
||||
|
||||
[ext_resource type="Script" uid="uid://dxql15j5ornlc" path="res://addons/twitcher/editor/setup/page_authorization.gd" id="1_78hk7"]
|
||||
[ext_resource type="LabelSettings" uid="uid://bnsxy6gcm8q11" path="res://addons/twitcher/assets/title_label_settings.tres" id="2_owlil"]
|
||||
[ext_resource type="PackedScene" uid="uid://b7smp156mdns6" path="res://addons/twitcher/editor/setup/file_select.tscn" id="3_dbhpx"]
|
||||
[ext_resource type="Script" uid="uid://ddugotjvuahex" path="res://addons/twitcher/editor/setup/focus_child_show.gd" id="3_o4tdm"]
|
||||
[ext_resource type="PackedScene" uid="uid://bfksyo3klyvdn" path="res://addons/twitcher/editor/setup/test_credentials.tscn" id="5_dbhpx"]
|
||||
|
||||
[node name="Authorization" type="MarginContainer"]
|
||||
anchors_preset = 15
|
||||
anchor_right = 1.0
|
||||
anchor_bottom = 1.0
|
||||
grow_horizontal = 2
|
||||
grow_vertical = 2
|
||||
theme_override_constants/margin_left = 10
|
||||
theme_override_constants/margin_top = 10
|
||||
theme_override_constants/margin_right = 10
|
||||
theme_override_constants/margin_bottom = 10
|
||||
script = ExtResource("1_78hk7")
|
||||
metadata/_tab_index = 1
|
||||
|
||||
[node name="Layout" type="VBoxContainer" parent="."]
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 3
|
||||
|
||||
[node name="Title" type="Label" parent="Layout"]
|
||||
layout_mode = 2
|
||||
text = "Step 2: Authorization"
|
||||
label_settings = ExtResource("2_owlil")
|
||||
horizontal_alignment = 1
|
||||
|
||||
[node name="ToDocumentation" type="Button" parent="Layout/Title"]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 1
|
||||
anchors_preset = 6
|
||||
anchor_left = 1.0
|
||||
anchor_top = 0.5
|
||||
anchor_right = 1.0
|
||||
anchor_bottom = 0.5
|
||||
offset_left = -52.0
|
||||
offset_top = -15.5
|
||||
offset_bottom = 15.5
|
||||
grow_horizontal = 0
|
||||
grow_vertical = 2
|
||||
text = "DOCS"
|
||||
metadata/_edit_use_anchors_ = true
|
||||
|
||||
[node name="PanelContainer" type="PanelContainer" parent="Layout"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="MarginContainer" type="MarginContainer" parent="Layout/PanelContainer"]
|
||||
layout_mode = 2
|
||||
theme_override_constants/margin_left = 10
|
||||
theme_override_constants/margin_top = 10
|
||||
theme_override_constants/margin_right = 10
|
||||
theme_override_constants/margin_bottom = 10
|
||||
|
||||
[node name="VBoxContainer" type="VBoxContainer" parent="Layout/PanelContainer/MarginContainer"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="AuthorizationTitle" type="Label" parent="Layout/PanelContainer/MarginContainer/VBoxContainer"]
|
||||
layout_mode = 2
|
||||
text = "General"
|
||||
label_settings = ExtResource("2_owlil")
|
||||
horizontal_alignment = 1
|
||||
|
||||
[node name="AuthExplain" type="RichTextLabel" parent="Layout/PanelContainer/MarginContainer/VBoxContainer"]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/normal_font_size = 12
|
||||
bbcode_enabled = true
|
||||
text = "The credentials that are used by the editor and game to connect to Twitch. You can request your credentials [url=https://dev.twitch.tv/console/apps/create]Twitch Dev Console[/url] for more informations see [url=https://twitcher.kani.dev/#authorization]Documentation[/url]"
|
||||
fit_content = true
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="AuthorizationOptions" type="GridContainer" parent="Layout/PanelContainer/MarginContainer/VBoxContainer" node_paths=PackedStringArray("show_elements")]
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 3
|
||||
size_flags_stretch_ratio = 3.0
|
||||
columns = 2
|
||||
script = ExtResource("3_o4tdm")
|
||||
show_elements = [NodePath("../AuthExplain")]
|
||||
|
||||
[node name="ClientIdLabel" type="Label" parent="Layout/PanelContainer/MarginContainer/VBoxContainer/AuthorizationOptions"]
|
||||
layout_mode = 2
|
||||
text = "Client ID:"
|
||||
|
||||
[node name="ClientId" type="LineEdit" parent="Layout/PanelContainer/MarginContainer/VBoxContainer/AuthorizationOptions"]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
text = "1ae0idgxbvn6vi97ls7d89cyd919oq"
|
||||
|
||||
[node name="ClientSecretLabel" type="Label" parent="Layout/PanelContainer/MarginContainer/VBoxContainer/AuthorizationOptions"]
|
||||
layout_mode = 2
|
||||
text = "Client Secret:"
|
||||
|
||||
[node name="ClientSecret" type="LineEdit" parent="Layout/PanelContainer/MarginContainer/VBoxContainer/AuthorizationOptions"]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
text = "k22x037lmmrmkmwvy79xr19qfy993g"
|
||||
secret = true
|
||||
|
||||
[node name="RedirectURLLabel" type="Label" parent="Layout/PanelContainer/MarginContainer/VBoxContainer/AuthorizationOptions"]
|
||||
layout_mode = 2
|
||||
text = "Redirect URL:"
|
||||
|
||||
[node name="RedirectURL" type="LineEdit" parent="Layout/PanelContainer/MarginContainer/VBoxContainer/AuthorizationOptions"]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
tooltip_text = "Location that Twitch is calling after the login process. Take care that this one is the same that you used during creation of the application within the twitch dev console."
|
||||
text = "http://localhost:7170"
|
||||
|
||||
[node name="HSeparator2" type="HSeparator" parent="Layout/PanelContainer/MarginContainer/VBoxContainer"]
|
||||
layout_mode = 2
|
||||
theme_override_constants/separation = 10
|
||||
|
||||
[node name="GameSettingTitle" type="Label" parent="Layout/PanelContainer/MarginContainer/VBoxContainer"]
|
||||
layout_mode = 2
|
||||
text = "Game"
|
||||
label_settings = ExtResource("2_owlil")
|
||||
horizontal_alignment = 1
|
||||
|
||||
[node name="GameExplain" type="RichTextLabel" parent="Layout/PanelContainer/MarginContainer/VBoxContainer"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/normal_font_size = 12
|
||||
bbcode_enabled = true
|
||||
text = "These settings are needed for the game to connect with Twitch."
|
||||
fit_content = true
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="GameSetting" type="GridContainer" parent="Layout/PanelContainer/MarginContainer/VBoxContainer" node_paths=PackedStringArray("show_elements")]
|
||||
layout_mode = 2
|
||||
columns = 2
|
||||
script = ExtResource("3_o4tdm")
|
||||
show_elements = [NodePath("../GameExplain")]
|
||||
|
||||
[node name="OauthSettingLabel" type="Label" parent="Layout/PanelContainer/MarginContainer/VBoxContainer/GameSetting"]
|
||||
layout_mode = 2
|
||||
text = "Auth File Path:"
|
||||
|
||||
[node name="OauthSettingFileSelect" parent="Layout/PanelContainer/MarginContainer/VBoxContainer/GameSetting" instance=ExtResource("3_dbhpx")]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
default_path = "res://addons/twitcher/twitch_oauth_setting.tres"
|
||||
path = "res://addons/twitcher/twitch_oauth_setting.tres"
|
||||
filters = PackedStringArray("*.tres", "*.res")
|
||||
|
||||
[node name="TokenLabel" type="Label" parent="Layout/PanelContainer/MarginContainer/VBoxContainer/GameSetting"]
|
||||
layout_mode = 2
|
||||
text = "Token File Path:"
|
||||
|
||||
[node name="TokenFileSelect" parent="Layout/PanelContainer/MarginContainer/VBoxContainer/GameSetting" instance=ExtResource("3_dbhpx")]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
default_path = "res://addons/twitcher/default_oauth_token.tres"
|
||||
path = "res://addons/twitcher/default_oauth_token.tres"
|
||||
filters = PackedStringArray("*.tres", "*.res")
|
||||
|
||||
[node name="HSeparator" type="HSeparator" parent="Layout/PanelContainer/MarginContainer/VBoxContainer"]
|
||||
layout_mode = 2
|
||||
theme_override_constants/separation = 10
|
||||
|
||||
[node name="HBoxContainer" type="HBoxContainer" parent="Layout"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="TestCredentials" parent="Layout/HBoxContainer" node_paths=PackedStringArray("test_response") instance=ExtResource("5_dbhpx")]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
test_response = NodePath("../../TestResponse")
|
||||
|
||||
[node name="OAuthSave" type="Button" parent="Layout/HBoxContainer"]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
text = "Save"
|
||||
|
||||
[node name="TestResponse" type="Label" parent="Layout"]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
139
addons/twitcher/editor/setup/page_use_case.gd
Normal file
139
addons/twitcher/editor/setup/page_use_case.gd
Normal file
|
|
@ -0,0 +1,139 @@
|
|||
@tool
|
||||
extends MarginContainer
|
||||
|
||||
enum UseCase {
|
||||
Overlay, Game, Other
|
||||
}
|
||||
|
||||
const PRESET_GAME_SCOPES = preload("res://addons/twitcher/auth/preset_game_scopes.tres")
|
||||
const PRESET_OVERLAY_SCOPES = preload("res://addons/twitcher/auth/preset_overlay_scopes.tres")
|
||||
const TwitchScopeProperty = preload("res://addons/twitcher/editor/inspector/twitch_scope_property.gd")
|
||||
const TwitchEditorSettings = preload("res://addons/twitcher/editor/twitch_editor_settings.gd")
|
||||
const TwitchTweens = preload("res://addons/twitcher/editor/twitch_tweens.gd")
|
||||
|
||||
@export var choose_button_group: ButtonGroup
|
||||
|
||||
@onready var overlay: CheckBox = %Overlay
|
||||
@onready var game: CheckBox = %Game
|
||||
@onready var something_else: CheckBox = %SomethingElse
|
||||
@onready var scope_list: RichTextLabel = %ScopeList
|
||||
@onready var to_documentation: Button = %ToDocumentation
|
||||
@onready var scope_file_select: FileSelect = %ScopeFileSelect
|
||||
@onready var scopes_container: HBoxContainer = %Scopes
|
||||
@onready var advanced_edit: CheckButton = %AdvancedEdit
|
||||
@onready var other_scope_options: PanelContainer = %OtherScopeOptions
|
||||
@onready var extended_scope_info: PanelContainer = %ExtendedScopeInfo
|
||||
@onready var save: Button = %Save
|
||||
|
||||
var other_scope_property: TwitchScopeProperty = TwitchScopeProperty.new()
|
||||
var scopes: TwitchOAuthScopes: set = update_scopes
|
||||
var has_changes: bool:
|
||||
set(val):
|
||||
has_changes = val
|
||||
changed.emit()
|
||||
save.text = save.text.trim_suffix(" (unsaved changes)")
|
||||
if has_changes: save.text += " (unsaved changes)"
|
||||
|
||||
signal changed
|
||||
signal use_case_changed(use_case: UseCase)
|
||||
|
||||
|
||||
func _ready() -> void:
|
||||
to_documentation.pressed.connect(_on_to_documentation_pressed)
|
||||
choose_button_group.pressed.connect(_on_choose)
|
||||
scope_file_select.file_selected.connect(_on_scope_file_selected)
|
||||
save.pressed.connect(_on_save_pressed)
|
||||
other_scope_property.scope_selected.connect(_on_scope_info)
|
||||
advanced_edit.toggled.connect(_on_toggle_advanced_edit)
|
||||
|
||||
scopes_container.hide()
|
||||
extended_scope_info.hide()
|
||||
extended_scope_info.add_child(other_scope_property)
|
||||
|
||||
# Reset radio buttons cause it's a tool script and the radio button stay and won't throw another signal otherwise
|
||||
game.set_pressed_no_signal(false)
|
||||
overlay.set_pressed_no_signal(false)
|
||||
something_else.set_pressed_no_signal(false)
|
||||
|
||||
scope_file_select.path = TwitchEditorSettings.get_scope_path()
|
||||
match TwitchEditorSettings.project_preset:
|
||||
TwitchEditorSettings.PRESET_GAME:
|
||||
game.button_pressed = true
|
||||
TwitchEditorSettings.PRESET_OVERLAY:
|
||||
overlay.button_pressed = true
|
||||
TwitchEditorSettings.PRESET_OTHER:
|
||||
something_else.button_pressed = true
|
||||
|
||||
# Needs to be resetted cause the radio reset will change the has_changges to true
|
||||
has_changes = false
|
||||
|
||||
func _on_scope_file_selected(path: String) -> void:
|
||||
has_changes = true
|
||||
if FileAccess.file_exists(path):
|
||||
var resource = load(path)
|
||||
if resource is OAuthScopes: scopes = resource
|
||||
else: OS.alert("The selected scope is not a scope file, it will be overwritten!")
|
||||
|
||||
|
||||
func _on_toggle_advanced_edit(toggled_on: bool) -> void:
|
||||
extended_scope_info.visible = toggled_on
|
||||
|
||||
|
||||
func _on_choose(button: BaseButton) -> void:
|
||||
match button:
|
||||
overlay:
|
||||
use_case_changed.emit(UseCase.Overlay)
|
||||
scopes = PRESET_OVERLAY_SCOPES.duplicate(true)
|
||||
advanced_edit.button_pressed = false
|
||||
TwitchEditorSettings.project_preset = TwitchEditorSettings.PRESET_OVERLAY
|
||||
game:
|
||||
use_case_changed.emit(UseCase.Game)
|
||||
scopes = PRESET_GAME_SCOPES.duplicate(true)
|
||||
advanced_edit.button_pressed = false
|
||||
TwitchEditorSettings.project_preset = TwitchEditorSettings.PRESET_GAME
|
||||
something_else:
|
||||
use_case_changed.emit(UseCase.Other)
|
||||
scopes = TwitchOAuthScopes.new()
|
||||
advanced_edit.button_pressed = true
|
||||
TwitchEditorSettings.project_preset = TwitchEditorSettings.PRESET_OTHER
|
||||
|
||||
_show_selected_scopes()
|
||||
has_changes = true
|
||||
|
||||
func _on_scope_info(scope: TwitchScope.Definition) -> void:
|
||||
_show_selected_scopes()
|
||||
|
||||
|
||||
func _on_save_pressed() -> void:
|
||||
var s_path = scope_file_select.path
|
||||
scopes.take_over_path(s_path)
|
||||
ResourceSaver.save(scopes, s_path)
|
||||
TwitchEditorSettings.set_scope_path(s_path)
|
||||
TwitchTweens.flash(save, Color.GREEN)
|
||||
has_changes = false
|
||||
|
||||
|
||||
func _show_selected_scopes() -> void:
|
||||
scopes_container.show()
|
||||
|
||||
if scopes.used_scopes.is_empty():
|
||||
scope_list.text = "[i]No scopes selected yet[/i]"
|
||||
return
|
||||
|
||||
var scope_description: String = ""
|
||||
for scope_name: StringName in scopes.used_scopes:
|
||||
var scope: TwitchScope.Definition = TwitchScope.SCOPE_MAP[scope_name]
|
||||
scope_description += "[b]%s[/b] - %s\n\n" % [scope.value, scope.description]
|
||||
|
||||
scope_list.text = scope_description
|
||||
|
||||
|
||||
func _on_to_documentation_pressed() -> void:
|
||||
OS.shell_open("https://dev.twitch.tv/docs/authentication/scopes/")
|
||||
|
||||
|
||||
func update_scopes(val: TwitchOAuthScopes) -> void:
|
||||
scopes = val
|
||||
other_scope_property.set_object_and_property(scopes, "")
|
||||
other_scope_property.update_property()
|
||||
_show_selected_scopes()
|
||||
1
addons/twitcher/editor/setup/page_use_case.gd.uid
Normal file
1
addons/twitcher/editor/setup/page_use_case.gd.uid
Normal file
|
|
@ -0,0 +1 @@
|
|||
uid://cjni881olloyf
|
||||
162
addons/twitcher/editor/setup/page_use_case.tscn
Normal file
162
addons/twitcher/editor/setup/page_use_case.tscn
Normal file
|
|
@ -0,0 +1,162 @@
|
|||
[gd_scene load_steps=5 format=3 uid="uid://c7pja1druikbn"]
|
||||
|
||||
[ext_resource type="Script" uid="uid://cjni881olloyf" path="res://addons/twitcher/editor/setup/page_use_case.gd" id="1_2qemh"]
|
||||
[ext_resource type="LabelSettings" uid="uid://bnsxy6gcm8q11" path="res://addons/twitcher/assets/title_label_settings.tres" id="1_r6qea"]
|
||||
[ext_resource type="ButtonGroup" uid="uid://bkocyfdqvh4t" path="res://addons/twitcher/editor/setup/use_case_button_group.tres" id="1_vqr26"]
|
||||
[ext_resource type="PackedScene" uid="uid://b7smp156mdns6" path="res://addons/twitcher/editor/setup/file_select.tscn" id="4_c6y6e"]
|
||||
|
||||
[node name="UseCase" type="MarginContainer"]
|
||||
anchors_preset = 15
|
||||
anchor_right = 1.0
|
||||
anchor_bottom = 1.0
|
||||
grow_horizontal = 2
|
||||
grow_vertical = 2
|
||||
theme_override_constants/margin_left = 10
|
||||
theme_override_constants/margin_top = 10
|
||||
theme_override_constants/margin_right = 10
|
||||
theme_override_constants/margin_bottom = 10
|
||||
script = ExtResource("1_2qemh")
|
||||
choose_button_group = ExtResource("1_vqr26")
|
||||
metadata/_tab_index = 0
|
||||
|
||||
[node name="ScrollContainer" type="ScrollContainer" parent="."]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="SelectionContainer" type="VBoxContainer" parent="ScrollContainer"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
size_flags_vertical = 3
|
||||
|
||||
[node name="Title" type="Label" parent="ScrollContainer/SelectionContainer"]
|
||||
layout_mode = 2
|
||||
text = "Step 1: Use Case"
|
||||
label_settings = ExtResource("1_r6qea")
|
||||
horizontal_alignment = 1
|
||||
|
||||
[node name="ToDocumentation" type="Button" parent="ScrollContainer/SelectionContainer/Title"]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 1
|
||||
anchors_preset = 6
|
||||
anchor_left = 1.0
|
||||
anchor_top = 0.5
|
||||
anchor_right = 1.0
|
||||
anchor_bottom = 0.5
|
||||
offset_left = -52.0
|
||||
offset_top = -15.5
|
||||
offset_bottom = 15.5
|
||||
grow_horizontal = 0
|
||||
grow_vertical = 2
|
||||
text = "DOCS"
|
||||
metadata/_edit_use_anchors_ = true
|
||||
|
||||
[node name="Explaination" type="RichTextLabel" parent="ScrollContainer/SelectionContainer"]
|
||||
layout_mode = 2
|
||||
theme_override_font_sizes/normal_font_size = 12
|
||||
bbcode_enabled = true
|
||||
text = "To help you with scopes and authentication please select your use case."
|
||||
fit_content = true
|
||||
vertical_alignment = 1
|
||||
|
||||
[node name="ChooseLabel" type="Label" parent="ScrollContainer/SelectionContainer"]
|
||||
layout_mode = 2
|
||||
text = "What do you want to make:"
|
||||
|
||||
[node name="Overlay" type="CheckBox" parent="ScrollContainer/SelectionContainer"]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
button_pressed = true
|
||||
button_group = ExtResource("1_vqr26")
|
||||
text = "Overlay"
|
||||
|
||||
[node name="Game" type="CheckBox" parent="ScrollContainer/SelectionContainer"]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
button_group = ExtResource("1_vqr26")
|
||||
text = "Game"
|
||||
|
||||
[node name="SomethingElse" type="CheckBox" parent="ScrollContainer/SelectionContainer"]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
button_group = ExtResource("1_vqr26")
|
||||
text = "I know what I do / Something else"
|
||||
|
||||
[node name="HSeparator" type="HSeparator" parent="ScrollContainer/SelectionContainer"]
|
||||
layout_mode = 2
|
||||
theme_override_constants/separation = 20
|
||||
|
||||
[node name="Scopes" type="HBoxContainer" parent="ScrollContainer/SelectionContainer"]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 3
|
||||
|
||||
[node name="ExtendedScopeInfo" type="PanelContainer" parent="ScrollContainer/SelectionContainer/Scopes"]
|
||||
unique_name_in_owner = true
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
|
||||
[node name="OtherScopeOptions" type="PanelContainer" parent="ScrollContainer/SelectionContainer/Scopes"]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
|
||||
[node name="VBoxContainer" type="VBoxContainer" parent="ScrollContainer/SelectionContainer/Scopes/OtherScopeOptions"]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="ScopeListLabel" type="Label" parent="ScrollContainer/SelectionContainer/Scopes/OtherScopeOptions/VBoxContainer"]
|
||||
layout_mode = 2
|
||||
text = "Scopes:"
|
||||
label_settings = ExtResource("1_r6qea")
|
||||
|
||||
[node name="AdvancedEdit" type="CheckButton" parent="ScrollContainer/SelectionContainer/Scopes/OtherScopeOptions/VBoxContainer/ScopeListLabel"]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 1
|
||||
anchors_preset = 6
|
||||
anchor_left = 1.0
|
||||
anchor_top = 0.5
|
||||
anchor_right = 1.0
|
||||
anchor_bottom = 0.5
|
||||
offset_left = -168.0
|
||||
offset_top = -15.5
|
||||
offset_bottom = 15.5
|
||||
grow_horizontal = 0
|
||||
grow_vertical = 2
|
||||
text = "Edit (Advanced)"
|
||||
|
||||
[node name="ScopeList" type="RichTextLabel" parent="ScrollContainer/SelectionContainer/Scopes/OtherScopeOptions/VBoxContainer"]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
bbcode_enabled = true
|
||||
text = "[b]user:read:chat[/b] - Receive chatroom messages and informational notifications relating to a channel’s chatroom.
|
||||
|
||||
[b]user:write:chat[/b] - Send chat messages to a chatroom.
|
||||
|
||||
[b]moderator:read:followers[/b] - Read the followers of a broadcaster.
|
||||
|
||||
[b]bits:read[/b] - View Bits information for a channel.
|
||||
|
||||
[b]channel:read:redemptions[/b] - View Channel Points custom rewards and their redemptions on a channel.
|
||||
|
||||
[b]channel:manage:redemptions[/b] - Manage Channel Points custom rewards and their redemptions on a channel.
|
||||
|
||||
"
|
||||
fit_content = true
|
||||
|
||||
[node name="HSeparator" type="HSeparator" parent="ScrollContainer/SelectionContainer/Scopes/OtherScopeOptions/VBoxContainer"]
|
||||
layout_mode = 2
|
||||
theme_override_constants/separation = 10
|
||||
|
||||
[node name="ScopeFileLabel" type="Label" parent="ScrollContainer/SelectionContainer/Scopes/OtherScopeOptions/VBoxContainer"]
|
||||
layout_mode = 2
|
||||
text = "Save selected scopes:"
|
||||
|
||||
[node name="ScopeFileSelect" parent="ScrollContainer/SelectionContainer/Scopes/OtherScopeOptions/VBoxContainer" instance=ExtResource("4_c6y6e")]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
default_path = "res://twitch_scopes.tres"
|
||||
path = "res://twitch_scopes.tres"
|
||||
filters = PackedStringArray("*.tres", "*.res")
|
||||
|
||||
[node name="Save" type="Button" parent="ScrollContainer/SelectionContainer/Scopes/OtherScopeOptions/VBoxContainer"]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
text = "Save Scopes"
|
||||
74
addons/twitcher/editor/setup/page_utilities.gd
Normal file
74
addons/twitcher/editor/setup/page_utilities.gd
Normal file
|
|
@ -0,0 +1,74 @@
|
|||
@tool
|
||||
extends MarginContainer
|
||||
|
||||
const script_path: String = "res://addons/twitcher/twitch_service.tscn"
|
||||
const autoload_name: String = "Twitch"
|
||||
const setting_key: String = "autoload/%s" % autoload_name
|
||||
const setting_value: String = "*" + script_path
|
||||
|
||||
@onready var autoload_install: Button = %AutoloadInstall
|
||||
@onready var autoload_info: Label = %AutoloadInfo
|
||||
@onready var autoload_description: RichTextLabel = %AutoloadDescription
|
||||
|
||||
|
||||
func _ready() -> void:
|
||||
autoload_description.text = autoload_description.text.format({
|
||||
"autoload_name": autoload_name
|
||||
})
|
||||
autoload_install.pressed.connect(_on_install_autoload_pressed)
|
||||
_update_install_autoload()
|
||||
|
||||
|
||||
func _update_install_autoload() -> void:
|
||||
if ProjectSettings.has_setting(setting_key):
|
||||
autoload_install.text = "Uninstall Autoload"
|
||||
else:
|
||||
autoload_install.text = "Install Autoload"
|
||||
|
||||
|
||||
func _on_install_autoload_pressed() -> void:
|
||||
if ProjectSettings.has_setting(setting_key):
|
||||
_uninstall_autoload()
|
||||
else:
|
||||
_install_autload()
|
||||
_update_install_autoload()
|
||||
|
||||
|
||||
func _uninstall_autoload() -> void:
|
||||
ProjectSettings.clear(setting_key)
|
||||
|
||||
var err = ProjectSettings.save()
|
||||
|
||||
if err == OK:
|
||||
autoload_info.text = "Autoload '%s' uninstalled successfully!\nYou might need to reload the current project for changes to fully apply everywhere in the editor immediately." % autoload_name
|
||||
print("Successfully removed autoload: %s" % autoload_name)
|
||||
else:
|
||||
autoload_info.text = "Failed to save project settings.\nError code: %s" % error_string(err)
|
||||
printerr("Failed to save project settings! Error: ", error_string(err))
|
||||
|
||||
|
||||
func _install_autload() -> void:
|
||||
if not FileAccess.file_exists(script_path):
|
||||
OS.alert("The TwitchService file does not exist at:\n" + script_path, "Error")
|
||||
return
|
||||
|
||||
var setting_key: String = "autoload/%s" % autoload_name
|
||||
var setting_value: String = "*" + script_path
|
||||
if ProjectSettings.has_setting(setting_key):
|
||||
var existing_value = ProjectSettings.get_setting(setting_key)
|
||||
if existing_value == setting_value:
|
||||
autoload_info.text = "Autoload '%s' with the same path is already installed." % autoload_name
|
||||
return
|
||||
else:
|
||||
autoload_info.text = "Autoload '%s' already exists but points to a different path (%s)." % [autoload_name, existing_value]
|
||||
return
|
||||
|
||||
ProjectSettings.set_setting(setting_key, setting_value)
|
||||
var err = ProjectSettings.save()
|
||||
|
||||
if err == OK:
|
||||
autoload_info.text = "Autoload '%s' installed successfully!\nYou might need to reload the current project for changes to fully apply everywhere in the editor immediately." % autoload_name
|
||||
print("Successfully added autoload: %s -> %s" % [autoload_name, script_path])
|
||||
else:
|
||||
autoload_info.text = "Failed to save project settings.\nError code: %s" % error_string(err)
|
||||
printerr("Failed to save project settings! Error: ", error_string(err))
|
||||
1
addons/twitcher/editor/setup/page_utilities.gd.uid
Normal file
1
addons/twitcher/editor/setup/page_utilities.gd.uid
Normal file
|
|
@ -0,0 +1 @@
|
|||
uid://dw37fk6mah3jk
|
||||
96
addons/twitcher/editor/setup/page_utilities.tscn
Normal file
96
addons/twitcher/editor/setup/page_utilities.tscn
Normal file
|
|
@ -0,0 +1,96 @@
|
|||
[gd_scene load_steps=4 format=3 uid="uid://d4l63q706mkhw"]
|
||||
|
||||
[ext_resource type="Script" uid="uid://dw37fk6mah3jk" path="res://addons/twitcher/editor/setup/page_utilities.gd" id="1_sexj5"]
|
||||
[ext_resource type="LabelSettings" uid="uid://bnsxy6gcm8q11" path="res://addons/twitcher/assets/title_label_settings.tres" id="1_yi5sa"]
|
||||
[ext_resource type="LabelSettings" uid="uid://cng881nsuud80" path="res://addons/twitcher/assets/warning_label_settings.tres" id="3_fj7h2"]
|
||||
|
||||
[node name="Utilities" type="MarginContainer"]
|
||||
anchors_preset = 15
|
||||
anchor_right = 1.0
|
||||
anchor_bottom = 1.0
|
||||
grow_horizontal = 2
|
||||
grow_vertical = 2
|
||||
theme_override_constants/margin_left = 10
|
||||
theme_override_constants/margin_top = 10
|
||||
theme_override_constants/margin_right = 10
|
||||
theme_override_constants/margin_bottom = 10
|
||||
script = ExtResource("1_sexj5")
|
||||
metadata/_tab_index = 2
|
||||
|
||||
[node name="ScrollContainer" type="ScrollContainer" parent="."]
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Container" type="VBoxContainer" parent="ScrollContainer"]
|
||||
layout_mode = 2
|
||||
size_flags_horizontal = 3
|
||||
size_flags_vertical = 3
|
||||
|
||||
[node name="Header" type="Label" parent="ScrollContainer/Container"]
|
||||
layout_mode = 2
|
||||
text = "Utilities"
|
||||
label_settings = ExtResource("1_yi5sa")
|
||||
horizontal_alignment = 1
|
||||
|
||||
[node name="HSeparator" type="HSeparator" parent="ScrollContainer/Container"]
|
||||
layout_mode = 2
|
||||
theme_override_constants/separation = 20
|
||||
|
||||
[node name="AutoloadDescription" type="RichTextLabel" parent="ScrollContainer/Container"]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
bbcode_enabled = true
|
||||
text = "For basic use cases an autoload is the easiest way to setup Twitcher. Adds an autoload named [b]{autoload_name}[/b]
|
||||
|
||||
[i]Advantage:[/i]
|
||||
+ easy access everywhere
|
||||
[i]Disadvantage:[/i]
|
||||
- It will be always initialized, even when you want to test a small scene standalone Tiwtcher will do authorization, subscribing to eventsub etc.
|
||||
|
||||
[b]Alternative:[/b]
|
||||
The first nodes in the scene tree of every major nodes like TwitchAPI, TwitchEventsub, TwitchChat, TwitchMediaLoader and TwitchService are available as Singleton via their instance variable.
|
||||
|
||||
Example
|
||||
[code]TwitchAPI.instance.get_users(...)[/code]"
|
||||
fit_content = true
|
||||
|
||||
[node name="AutoloadInstall" type="Button" parent="ScrollContainer/Container"]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
text = "Uninstall Autoload"
|
||||
|
||||
[node name="AutoloadInfo" type="Label" parent="ScrollContainer/Container"]
|
||||
unique_name_in_owner = true
|
||||
custom_minimum_size = Vector2(0, 100)
|
||||
layout_mode = 2
|
||||
label_settings = ExtResource("3_fj7h2")
|
||||
autowrap_mode = 3
|
||||
|
||||
[node name="HSeparator2" type="HSeparator" parent="ScrollContainer/Container"]
|
||||
layout_mode = 2
|
||||
theme_override_constants/separation = 20
|
||||
|
||||
[node name="AutoloadDescription2" type="RichTextLabel" parent="ScrollContainer/Container"]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
bbcode_enabled = true
|
||||
text = "For a game with Twitch integration you probably want to read the chat from the streamer to act on the commands. For that the streamer need to authorize your application. For the authorization flow use the [url=https://dev.twitch.tv/docs/authentication/getting-tokens-oauth/#device-code-grant-flow]Device Code Flow[/url] so that you don't share the client secret in the code.
|
||||
|
||||
|
||||
[b]Hints:[/b]
|
||||
- Take care that you take the least amount of scopes for the game otherwise you could scare the streamer away.
|
||||
[i]Advantage:[/i]
|
||||
+ easy access everywhere
|
||||
[i]Disadvantage:[/i]
|
||||
- It will be always initialized, even when you want to test a small scene standalone Tiwtcher will do authorization, subscribing to eventsub etc.
|
||||
|
||||
[b]Alternative:[/b]
|
||||
The first nodes in the scene tree of every major nodes like TwitchAPI, TwitchEventsub, TwitchChat, TwitchMediaLoader and TwitchService are available as Singleton via their instance variable.
|
||||
|
||||
Example
|
||||
[code]TwitchAPI.instance.get_users(...)[/code]"
|
||||
fit_content = true
|
||||
|
||||
[node name="Button" type="Button" parent="ScrollContainer/Container"]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
text = "Add Game Example"
|
||||
58
addons/twitcher/editor/setup/setup.gd
Normal file
58
addons/twitcher/editor/setup/setup.gd
Normal file
|
|
@ -0,0 +1,58 @@
|
|||
@tool
|
||||
extends Window
|
||||
|
||||
const PageUseCase = preload("res://addons/twitcher/editor/setup/page_use_case.gd")
|
||||
const TwitchEditorSettings = preload("res://addons/twitcher/editor/twitch_editor_settings.gd")
|
||||
const PageAuthorization = preload("res://addons/twitcher/editor/setup/page_authorization.gd")
|
||||
|
||||
#Setup
|
||||
#- Check for Authorization Stuff
|
||||
#-- Client Credentials
|
||||
#-- Editor Token
|
||||
#-- Scopes
|
||||
#- Auth Button
|
||||
#- Create Base Node Structure
|
||||
|
||||
@onready var authorization: PageAuthorization = %Authorization
|
||||
@onready var use_case: PageUseCase = %UseCase as PageUseCase
|
||||
@onready var close: Button = %Close
|
||||
@onready var startup_check: CheckButton = %StartupCheck
|
||||
|
||||
|
||||
func _ready():
|
||||
close_requested.connect(_on_close)
|
||||
close.pressed.connect(_on_close)
|
||||
startup_check.toggled.connect(_on_toggle_startup_check)
|
||||
startup_check.button_pressed = TwitchEditorSettings.show_setup_on_startup
|
||||
use_case.changed.connect(_on_changed)
|
||||
authorization.changed.connect(_on_changed)
|
||||
pass
|
||||
|
||||
|
||||
func _on_changed() -> void:
|
||||
close.text = close.text.trim_suffix(" (unsaved changes)")
|
||||
if use_case.has_changes || authorization.has_changes:
|
||||
close.text = close.text + " (unsaved changes)"
|
||||
|
||||
|
||||
func _on_toggle_startup_check(toggle_on: bool) -> void:
|
||||
TwitchEditorSettings.show_setup_on_startup = toggle_on
|
||||
ProjectSettings.save()
|
||||
|
||||
|
||||
func _input(event: InputEvent) -> void:
|
||||
if event is InputEventKey:
|
||||
var key_event: InputEventKey = event as InputEventKey
|
||||
if key_event.keycode == KEY_ESCAPE:
|
||||
_on_close()
|
||||
|
||||
|
||||
func _on_close() -> void:
|
||||
if use_case.has_changes || authorization.has_changes:
|
||||
var popup = ConfirmationDialog.new()
|
||||
popup.dialog_text = "You have unsaved changes! Are you sure to close the setup?"
|
||||
popup.confirmed.connect(queue_free)
|
||||
add_child(popup)
|
||||
popup.popup_centered()
|
||||
else:
|
||||
queue_free()
|
||||
1
addons/twitcher/editor/setup/setup.gd.uid
Normal file
1
addons/twitcher/editor/setup/setup.gd.uid
Normal file
|
|
@ -0,0 +1 @@
|
|||
uid://bbguje3a0cl8t
|
||||
51
addons/twitcher/editor/setup/setup.tscn
Normal file
51
addons/twitcher/editor/setup/setup.tscn
Normal file
|
|
@ -0,0 +1,51 @@
|
|||
[gd_scene load_steps=6 format=3 uid="uid://wu1fprbhr62"]
|
||||
|
||||
[ext_resource type="Script" uid="uid://bbguje3a0cl8t" path="res://addons/twitcher/editor/setup/setup.gd" id="1_o5snq"]
|
||||
[ext_resource type="PackedScene" uid="uid://c7pja1druikbn" path="res://addons/twitcher/editor/setup/page_use_case.tscn" id="2_6678v"]
|
||||
[ext_resource type="PackedScene" uid="uid://dm6jvnuikxtei" path="res://addons/twitcher/editor/setup/page_authorization.tscn" id="3_qcivh"]
|
||||
[ext_resource type="PackedScene" uid="uid://d4l63q706mkhw" path="res://addons/twitcher/editor/setup/page_utilities.tscn" id="4_qcivh"]
|
||||
|
||||
[sub_resource type="ButtonGroup" id="ButtonGroup_6678v"]
|
||||
|
||||
[node name="SetupWindow" type="Window"]
|
||||
title = "Setup Twitcher"
|
||||
initial_position = 2
|
||||
size = Vector2i(800, 800)
|
||||
script = ExtResource("1_o5snq")
|
||||
|
||||
[node name="VBoxContainer" type="VBoxContainer" parent="."]
|
||||
anchors_preset = 15
|
||||
anchor_right = 1.0
|
||||
anchor_bottom = 1.0
|
||||
grow_horizontal = 2
|
||||
grow_vertical = 2
|
||||
|
||||
[node name="Setup" type="TabContainer" parent="VBoxContainer"]
|
||||
layout_mode = 2
|
||||
size_flags_vertical = 3
|
||||
current_tab = 0
|
||||
|
||||
[node name="UseCase" parent="VBoxContainer/Setup" instance=ExtResource("2_6678v")]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
choose_button_group = SubResource("ButtonGroup_6678v")
|
||||
|
||||
[node name="Authorization" parent="VBoxContainer/Setup" instance=ExtResource("3_qcivh")]
|
||||
unique_name_in_owner = true
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
|
||||
[node name="Utilities" parent="VBoxContainer/Setup" instance=ExtResource("4_qcivh")]
|
||||
visible = false
|
||||
layout_mode = 2
|
||||
|
||||
[node name="StartupCheck" type="CheckButton" parent="VBoxContainer"]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
button_pressed = true
|
||||
text = "Show on startup (you can open it via 'Project/Tools/Twitcher Setup')"
|
||||
|
||||
[node name="Close" type="Button" parent="VBoxContainer"]
|
||||
unique_name_in_owner = true
|
||||
layout_mode = 2
|
||||
text = "Close"
|
||||
58
addons/twitcher/editor/setup/test_credentials.gd
Normal file
58
addons/twitcher/editor/setup/test_credentials.gd
Normal file
|
|
@ -0,0 +1,58 @@
|
|||
@tool
|
||||
extends Button
|
||||
|
||||
const TwitchTweens = preload("res://addons/twitcher/editor/twitch_tweens.gd")
|
||||
const TwitchEditorSettings = preload("res://addons/twitcher/editor/twitch_editor_settings.gd")
|
||||
|
||||
@export var oauth_setting: OAuthSetting: set = update_oauth_setting
|
||||
@export var oauth_token: OAuthToken: set = update_oauth_token
|
||||
@export var test_response: Label
|
||||
|
||||
@onready var twitch_auth: TwitchAuth = %TwitchAuth
|
||||
|
||||
signal authorized
|
||||
|
||||
func _ready() -> void:
|
||||
pressed.connect(_pressed)
|
||||
oauth_setting = TwitchEditorSettings.editor_oauth_setting
|
||||
oauth_token = TwitchEditorSettings.editor_oauth_token
|
||||
|
||||
|
||||
func _notification(what: int) -> void:
|
||||
if what == NOTIFICATION_PREDELETE:
|
||||
oauth_token.authorized.disconnect(_on_authorized)
|
||||
|
||||
|
||||
func _pressed() -> void:
|
||||
TwitchTweens.loading(self)
|
||||
await twitch_auth.authorize()
|
||||
|
||||
if twitch_auth.token.is_token_valid():
|
||||
if test_response:
|
||||
test_response.text = "Credentials are valid!"
|
||||
test_response.add_theme_color_override(&"font_color", Color.GREEN)
|
||||
TwitchTweens.flash(self, Color.GREEN)
|
||||
authorized.emit()
|
||||
else:
|
||||
if test_response:
|
||||
test_response.text = "Credentials are invalid!"
|
||||
test_response.add_theme_color_override(&"font_color", Color.RED)
|
||||
TwitchTweens.flash(self, Color.RED)
|
||||
|
||||
|
||||
func update_oauth_token(new_oauth_token: OAuthToken) -> void:
|
||||
oauth_token = new_oauth_token
|
||||
oauth_token.authorized.connect(_on_authorized)
|
||||
if is_inside_tree():
|
||||
twitch_auth.token = new_oauth_token
|
||||
|
||||
|
||||
func update_oauth_setting(new_oauth_setting: OAuthSetting) -> void:
|
||||
oauth_setting = new_oauth_setting
|
||||
disabled = not oauth_setting.is_valid()
|
||||
if is_inside_tree():
|
||||
twitch_auth.oauth_setting = oauth_setting
|
||||
|
||||
|
||||
func _on_authorized() -> void:
|
||||
if is_inside_tree(): authorized.emit()
|
||||
1
addons/twitcher/editor/setup/test_credentials.gd.uid
Normal file
1
addons/twitcher/editor/setup/test_credentials.gd.uid
Normal file
|
|
@ -0,0 +1 @@
|
|||
uid://13afcys4swos
|
||||
37
addons/twitcher/editor/setup/test_credentials.tscn
Normal file
37
addons/twitcher/editor/setup/test_credentials.tscn
Normal file
|
|
@ -0,0 +1,37 @@
|
|||
[gd_scene load_steps=9 format=3 uid="uid://bfksyo3klyvdn"]
|
||||
|
||||
[ext_resource type="Script" uid="uid://13afcys4swos" path="res://addons/twitcher/editor/setup/test_credentials.gd" id="1_j2v3o"]
|
||||
[ext_resource type="Script" uid="uid://iv0mgv0lu8b0" path="res://addons/twitcher/auth/twitch_auth.gd" id="1_kojf4"]
|
||||
[ext_resource type="Script" uid="uid://b3n3et8mebjcc" path="res://addons/twitcher/auth/twitch_oauth_scopes.gd" id="3_2rqpn"]
|
||||
[ext_resource type="Resource" path="user://editor_oauth_setting.tres" id="3_kojf4"]
|
||||
[ext_resource type="Resource" path="user://editor_oauth_token.tres" id="4_j2v3o"]
|
||||
[ext_resource type="Script" uid="uid://bf0wi70haua35" path="res://addons/twitcher/lib/oOuch/oauth.gd" id="6_hkawa"]
|
||||
[ext_resource type="Script" uid="uid://blnbogtrshw4r" path="res://addons/twitcher/auth/twitch_token_handler.gd" id="7_v5ghs"]
|
||||
|
||||
[sub_resource type="Resource" id="Resource_1cpcx"]
|
||||
script = ExtResource("3_2rqpn")
|
||||
used_scopes = Array[StringName]([])
|
||||
metadata/_custom_type_script = "uid://b3n3et8mebjcc"
|
||||
|
||||
[node name="TestCredentials" type="Button"]
|
||||
text = "Test Credentials"
|
||||
script = ExtResource("1_j2v3o")
|
||||
|
||||
[node name="TwitchAuth" type="Node" parent="."]
|
||||
unique_name_in_owner = true
|
||||
script = ExtResource("1_kojf4")
|
||||
oauth_setting = ExtResource("3_kojf4")
|
||||
token = ExtResource("4_j2v3o")
|
||||
scopes = SubResource("Resource_1cpcx")
|
||||
metadata/_custom_type_script = "uid://iv0mgv0lu8b0"
|
||||
|
||||
[node name="OAuth" type="Node" parent="TwitchAuth" node_paths=PackedStringArray("token_handler")]
|
||||
script = ExtResource("6_hkawa")
|
||||
oauth_setting = ExtResource("3_kojf4")
|
||||
scopes = SubResource("Resource_1cpcx")
|
||||
token_handler = NodePath("../TokenHandler")
|
||||
|
||||
[node name="TokenHandler" type="Node" parent="TwitchAuth"]
|
||||
script = ExtResource("7_v5ghs")
|
||||
oauth_setting = ExtResource("3_kojf4")
|
||||
token = ExtResource("4_j2v3o")
|
||||
3
addons/twitcher/editor/setup/use_case_button_group.tres
Normal file
3
addons/twitcher/editor/setup/use_case_button_group.tres
Normal file
|
|
@ -0,0 +1,3 @@
|
|||
[gd_resource type="ButtonGroup" format=3 uid="uid://bkocyfdqvh4t"]
|
||||
|
||||
[resource]
|
||||
Loading…
Add table
Add a link
Reference in a new issue