Restructured files and worked on more complex quest progression

This commit is contained in:
2025-08-11 02:16:39 -04:00
parent 434216ca29
commit 95a7db036b
47 changed files with 475 additions and 53 deletions

View File

@@ -27,6 +27,7 @@ var job : JobData
var stats : StatBlock
var gold : int = 0
var quest : Quest
var inventory : Dictionary[Vector2, Item] = {}
func _init() -> void:
stats = StatBlock.new()
@@ -53,6 +54,20 @@ func assign_quest(quest : Quest) -> void:
func full_name() -> String:
return given_name + " " + surname
func gain_level() -> void:
level += 1
#TODO: Make stats improve based on job
Game.notice("%s has reached level %d!" % [full_name(), level])
func gain_exp(amount : int) -> void:
exp += amount
while exp >= get_tnl():
exp -= get_tnl()
gain_level()
func gain_gold(amount :int) -> void:
gold += amount
func get_tnl() -> int:
if job:
return job.get_tnl(level)

View File

@@ -6,14 +6,11 @@ var quest_log : QuestLog = null
var top_menu : TopMenu = null
var active : bool = true
var end_shift_confirmation : ConfirmationDialog
var end_shift_confirm_template = preload("res://end_shift_confirmation.tscn")
var end_shift_confirm_template = preload("res://templates/end_shift_confirmation.tscn")
func _ready() -> void:
DisplayServer.register_additional_output(self)
end_shift_confirmation = end_shift_confirm_template.instantiate()
add_child(end_shift_confirmation)
#var file =FileAccess.open("res://name.txt",FileAccess.READ)
#var text =file.get_line()
#var nmnames = text.remove_chars(" ").split(",")
func _process(delta: float) -> void:
if active and Input.is_action_just_pressed("switch modes"):

View File

@@ -15,8 +15,7 @@ func generate_quest() -> void:
func update_quest_window() -> void:
if quest:
%NameField.text = quest.name
match(quest.difficulty):
1: %DifficultyField.text = "Trivial"
%DifficultyField.text = quest.difficulty_name()
%LocationField.text = quest.location
#for reward in quest.rewards.:

View File

@@ -3,8 +3,8 @@ extends Node
const visitors = {
"test": {
"data":preload("res://test_adventurer.tscn"),
"sprite":preload("res://test_adventurer_sprite.tscn")
"data":preload("res://templates/test_adventurer.tscn"),
"sprite":preload("res://templates/test_adventurer_sprite.tscn")
}
}

View File

@@ -1,7 +1,7 @@
class_name GamePanel extends MarginContainer
const notice_template = preload("res://notice_panel.tscn")
const quest_progress_bar_template = preload("res://quest_progress_bar.tscn")
const notice_template = preload("res://templates/notice_panel.tscn")
const quest_progress_bar_template = preload("res://templates/quest_progress_bar.tscn")
signal time_changed(time : float)
@@ -15,8 +15,8 @@ func _process(delta: float) -> void:
func add_quest_progress_bar(quest : Quest) -> void:
var qpb : QuestProgressBar = quest_progress_bar_template.instantiate()
qpb.setup(quest)
%QuestList.add_child(qpb)
qpb.setup(quest)
#TODO: Change the hero portrait to match
if quest.steps > 1:
for i in range(quest.steps-1):

View File

@@ -1,6 +1,6 @@
extends PanelContainer
const npc_profile_window_template = preload("res://npc_profile_window.tscn")
const npc_profile_window_template = preload("res://templates/npc_profile_window.tscn")
var _enabled: bool
var enabled: bool:
get:

View File

@@ -1,6 +1,6 @@
class_name Npc extends Person
const popup_template = preload("res://profile_popup.tscn")
const popup_template = preload("res://templates/profile_popup.tscn")
var profile_popup
@export var is_player : bool = false

View File

@@ -6,9 +6,27 @@ enum Status{
TAKEN,
IN_PROGRESS,
COMPLETED,
FAILED
FAILED,
CLOSED
}
class Event:
enum Type{
WAIT,
COMBAT,
CHOICE
}
var type : Type = Type.WAIT
var enemies : Array[String] = []
var time : float = 1
var time_elapsed
signal completed()
func process(delta : float) -> void:
#TODO: Make quest combat work
time_elapsed += delta
if time_elapsed >= time:
completed.emit()
var name : String = "A Basic Quest"
var desc : String = "The default quest, with no special anything."
@@ -17,10 +35,7 @@ var location : String
var steps : int = 1
var rewards : Dictionary
var length : float = 10
var step_outcomes : Array = [
{"pass":"I succeeded!", "fail":"I failed!"}
]
var events : Array[Event] = []
var progress : float = 0
@@ -57,6 +72,8 @@ func complete() -> void:
#else it's a guild item they'll bring back for us
Game.notice("%s completed the quest '%s'!" % [questor.full_name(), name])
func num_events() -> int:
return len(events)
#TODO: Put in quest requirements
func is_eligible(member : AdventurerData) -> bool:
return !taken

View File

@@ -1,7 +1,7 @@
class_name QuestBoardEntry extends Button
const quest_window_template = preload("res://quest_window.tscn")
const quest_window_template = preload("res://templates/quest_window.tscn")
var quest : Quest = null
@onready var tex_icon : TextureRect = %Icon
@onready var name_label : Label = %NameLabel

View File

@@ -1,6 +1,6 @@
class_name QuestBoardWindow extends Popup
const entry_template = preload("res://quest_board_entry.tscn")
const entry_template = preload("res://templates/quest_board_entry.tscn")
@onready var entry_list : VBoxContainer = %Entries

View File

@@ -0,0 +1,45 @@
extends Window
@onready var nameLabel : Label = %NameLabel
@onready var difficultyLabel : Label = %DifficultyLabel
@onready var locationLabel : Label = %LocationLabel
@onready var advRewardList : GridContainer = %AdventurerRewardList
@onready var guildRewardList : GridContainer = %GuildRewardList
var quest : Quest
func setup(qst : Quest) -> void:
quest = qst
quest.status_changed.connect(_on_quest_changed)
update()
#TODO: Show quest rewards
func update() -> void:
nameLabel.text = quest.name
difficultyLabel.text = quest.difficulty_name()
locationLabel.text = quest.location
#TODO: Show the current status of the quest
func close() -> void:
hide()
queue_free()
func _on_quest_changed(status : Quest.Status) -> void:
if status == Quest.Status.CLOSED:
close()
else:
update()
func _on_remove_quest_confirm() -> void:
Guild.remove_quest(quest)
close()
func _on_remove_quest_cancel() -> void:
%ConfirmDialog.hide()
func _on_remove_button_pressed() -> void:
pass
func _on_back_button_pressed() -> void:
close()

View File

@@ -0,0 +1 @@
uid://cip5x34n08ilk

View File

@@ -1,6 +1,6 @@
class_name QuestLog extends Control
const entry_template = preload("res://quest_log_entry.tscn")
const entry_template = preload("res://templates/quest_log_entry.tscn")
@onready var entry_list : VBoxContainer = %Entries
var entries : Array[QuestLogEntry] = []

View File

@@ -1,5 +1,6 @@
extends PanelContainer
const quest_info_window_template = preload("res://templates/quest_info_window.tscn")
var _enabled: bool
var enabled: bool:
@@ -30,7 +31,10 @@ func setup(qst : Quest) -> void:
func _on_gui_input(event: InputEvent) -> void:
var evt = event as InputEventMouseButton
if evt and evt.button_index == MOUSE_BUTTON_LEFT and evt.pressed:
print("Quest clicked!")
var wnd = quest_info_window_template.instantiate()
add_child(wnd)
wnd.setup(quest)
wnd.popup_centered()
func _on_quest_status_changed(status: Quest.Status) -> void:
match(status):

View File

@@ -1,16 +1,20 @@
class_name QuestProgressBar extends Control
const waypoint_template = preload("res://waypoint.tscn")
const waypoint_template = preload("res://templates/waypoint.tscn")
var length : float
var waypoints : Array = []
var waypoints : Array[Waypoint] = []
@onready var hero_offset : Vector2 = %Hero.position
@onready var hero : HeroIcon = %Hero
@onready var heroLabel : Label = %HeroLabel
@onready var startpoint : Endpoint = %Start
@onready var endpoint : Endpoint = %End
@onready var bar : TextureProgressBar = $ProgressBar
@onready var path : Control = %Path
@onready var speech_bubble = %SpeechBubble
var quest : Quest = null
var current_event : Quest.Event = null
var time_elapsed : float = 0
var next_waypoint = 0
#signal value_changed(value : float)
#var min_value
#var max_value
@@ -22,17 +26,16 @@ var time_elapsed : float = 0
#var allow_greater
func _ready() -> void:
length = path.size.x
if quest:
#Generate the waypoints
generate_waypoints()
#TODO: Change the hero's portrait
bar.value = quest.progress
hero.position = hero_offset + Vector2(length * bar.value / bar.max_value, 0)
func _process(delta: float) -> void:
if time_elapsed < quest.length:
time_elapsed += delta
progress_quest()
if current_event != null:
if current_event.type != Quest.Event.Type.COMBAT:
current_event.process(delta)
else:
time_elapsed += delta
progress_quest()
func generate_waypoints():
if len(waypoints) > 0:
@@ -40,16 +43,20 @@ func generate_waypoints():
wp.queue_free()
waypoints = []
for i in range(1,quest.steps):
var pct : float = i / float(quest.steps)
add_waypoint( pct, quest.step_outcomes[i])
#Include the "end" in the count
var num = quest.num_events()+1
for i in range(1,num):
var pct : float = i / float(num)
add_waypoint( pct, quest.events[i-1])
func add_waypoint(pct : float, msgs : Dictionary):
func add_waypoint(pct : float, event : Quest.Event):
var wp = waypoint_template.instantiate()
waypoints.append(wp)
wp.percent = pct
#TODO: Make events matter
wp.event = event
%Waypoints.add_child(wp)
wp.global_position = global_position + Vector2(pct * length - 16, -9)
wp.global_position = %Waypoints.global_position + Vector2(pct * length - 16, -9)
if bar.value / bar.max_value >= pct:
wp.fill = true
@@ -59,13 +66,36 @@ func update_waypoints(value : float) -> void:
wp.fill = (bar.value / bar.max_value >= wp.percent)
endpoint.fill = (bar.value / bar.max_value >= endpoint.percent)
func start_event(event : Quest.Event, offset : float) -> void:
current_event = event
current_event.completed.connect(_on_event_complete)
event.time_elapsed = offset
func setup(quest : Quest) -> void:
self.quest = quest
heroLabel.text = quest.questor.full_name()
time_elapsed = 0
#Generate the waypoints
generate_waypoints()
#TODO: Change the hero's portrait
bar.value = quest.progress
func progress_quest() -> void:
bar.value = clampf(time_elapsed / quest.length, 0, bar.max_value)
var pct = time_elapsed / quest.length
if next_waypoint < len(waypoints) and pct >= waypoints[next_waypoint].percent:
start_event(waypoints[next_waypoint].event, (pct - waypoints[next_waypoint].percent) * quest.length)
pct = waypoints[next_waypoint].percent
waypoints[next_waypoint].blink(true)
bar.value = clampf(pct, 0, bar.max_value)
hero.position = hero_offset + Vector2(length * bar.value / bar.max_value, 0)
if time_elapsed >= quest.length:
quest.complete()
update_waypoints(bar.value)
func _on_event_complete() -> void:
#TODO: Show event message!
speech_bubble.show_message("Event complete!")
waypoints[next_waypoint].blink(false)
next_waypoint += 1
current_event = null

View File

@@ -2,4 +2,4 @@ extends Control
func _on_button_pressed() -> void:
get_tree().change_scene_to_file()
get_tree().change_scene_to_file("res://scenes/active_scene.tscn")

View File

@@ -1,8 +1,11 @@
extends Node2D
var test_adv = preload("res://test_adventurer.tscn")
var test_adv = preload("res://templates/test_adventurer.tscn")
func _ready() -> void:
#var adv : AdventurerData = test_adv.instantiate() as AdventurerData
#Guild.register_guild_member(adv)
var quest : Quest = Quest.new()
var evt : Quest.Event = Quest.Event.new()
evt.time = 10
quest.events.append(evt)
Guild.add_quest(quest)

View File

@@ -1,8 +1,8 @@
class_name TopMenu extends Control
const member_panel_entry_template = preload("res://member_panel_entry.tscn")
const quest_panel_entry_template = preload("res://quest_panel_entry.tscn")
const guild_info_window_template = preload("res://guild_info_window.tscn")
const member_panel_entry_template = preload("res://templates/member_panel_entry.tscn")
const quest_panel_entry_template = preload("res://templates/quest_panel_entry.tscn")
const guild_info_window_template = preload("res://templates/guild_info_window.tscn")
@onready var members_list = %MembersList
@onready var members = %Members

View File

@@ -4,7 +4,7 @@ extends NinePatchRect
@onready var timer : Timer = %Timer
func _ready() -> void:
show_message("TESTING, 1 2 3\nTESTING!!!!")
pass
func show_message(msg : String, show_time : float = 1.0) -> void:

View File

@@ -1,7 +1,10 @@
class_name Waypoint extends Control
var event : Quest.Event = null
var percent : float = 0
var filled: bool
var blink_tween : Tween
var blinking : bool = false
var fill: bool :
get:
return filled
@@ -9,10 +12,22 @@ var fill: bool :
if value != filled:
set_fill(value)
func blink(blnk : bool) -> void:
if blinking == blnk:
return
blinking = blnk
if blinking:
blink_tween = create_tween()
blink_tween.tween_property($Dot,"modulate:a", 0, .5)
blink_tween.tween_property($Dot,"modulate:a", 1, .5)
blink_tween.set_loops(-1)
else:
blink_tween.stop()
blink_tween = null
func set_fill(value : bool) -> void:
filled = value
if value:
if value and !blinking:
$Dot.visible = true
$Fill.modulate = Color.SEA_GREEN
else: