Implemented first demo quest line #15

Merged
Jonathan merged 11 commits from feature/implement_quests into develop 5 months ago

@ -1,6 +1,12 @@
<wpf:ResourceDictionary xml:space="preserve" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:s="clr-namespace:System;assembly=mscorlib" xmlns:ss="urn:shemas-jetbrains-com:settings-storage-xaml" xmlns:wpf="http://schemas.microsoft.com/winfx/2006/xaml/presentation">
<s:String x:Key="/Default/CodeInspection/ExcludedFiles/FilesAndFoldersToSkip2/=7020124F_002D9FFC_002D4AC3_002D8F3D_002DAAB8E0240759_002Ff_003AArea3D_002Ecs_002Fl_003A_002E_002E_003F_002E_002E_003F_002E_002E_003F_002E_002E_003F_002Econfig_003FJetBrains_003FRider2024_002E3_003Fresharper_002Dhost_003FSourcesCache_003F8a54226fa2e1c9371a8091f24cfd744aef11fe6869527dc23b9b837623a29b9_003FArea3D_002Ecs/@EntryIndexedValue">ForceIncluded</s:String>
<s:String x:Key="/Default/CodeInspection/ExcludedFiles/FilesAndFoldersToSkip2/=7020124F_002D9FFC_002D4AC3_002D8F3D_002DAAB8E0240759_002Ff_003AAudioStreamPlayer2D_002Ecs_002Fl_003A_002E_002E_003F_002E_002E_003F_002E_002E_003F_002E_002E_003F_002Econfig_003FJetBrains_003FRider2025_002E1_003Fresharper_002Dhost_003FSourcesCache_003F848324b1c23114c3f5e8bbb5a42c4ade394c59a7a7a133a66b76581ca571_003FAudioStreamPlayer2D_002Ecs/@EntryIndexedValue">ForceIncluded</s:String>
<s:String x:Key="/Default/CodeInspection/ExcludedFiles/FilesAndFoldersToSkip2/=7020124F_002D9FFC_002D4AC3_002D8F3D_002DAAB8E0240759_002Ff_003ABabushka_002Escripts_002ECSharp_002ECommon_002EFarming_002EVesnaBehaviour2D_005FScriptProperties_002Egenerated_002Ecs_002Fl_003AC_0021_003FUsers_003FJonathan_003FAppData_003FRoaming_003FJetBrains_003FRider2025_002E1_003Fresharper_002Dhost_003FSourcesCache_003F4298b0f293f987511fc1b7956ee691fd778f8378_003FBabushka_002Escripts_002ECSharp_002ECommon_002EFarming_002EVesnaBehaviour2D_005FScriptProperties_002Egenerated_002Ecs/@EntryIndexedValue">ForceIncluded</s:String>
<s:String x:Key="/Default/CodeInspection/ExcludedFiles/FilesAndFoldersToSkip2/=7020124F_002D9FFC_002D4AC3_002D8F3D_002DAAB8E0240759_002Ff_003ABabushka_002Escripts_002ECSharp_002ECommon_002EQuest_002EQuestListItemUi_005FScriptMethods_002Egenerated_002Ecs_002Fl_003AC_0021_003FUsers_003FJonathan_003FAppData_003FRoaming_003FJetBrains_003FRider2025_002E1_003Fresharper_002Dhost_003FSourcesCache_003F48fad7e7f3c9e292b3fdbddf9d363f0d1752aa_003FBabushka_002Escripts_002ECSharp_002ECommon_002EQuest_002EQuestListItemUi_005FScriptMethods_002Egenerated_002Ecs/@EntryIndexedValue">ForceIncluded</s:String>
<s:String x:Key="/Default/CodeInspection/ExcludedFiles/FilesAndFoldersToSkip2/=7020124F_002D9FFC_002D4AC3_002D8F3D_002DAAB8E0240759_002Ff_003ACastHelpers_002Ecs_002Fl_003AC_0021_003FUsers_003FJonathan_003FAppData_003FRoaming_003FJetBrains_003FRider2025_002E1_003Fresharper_002Dhost_003FSourcesCache_003F3c92637ae2e83da0a63791071c41eae291d594156062866d8621b7ed7245c_003FCastHelpers_002Ecs/@EntryIndexedValue">ForceIncluded</s:String>
<s:String x:Key="/Default/CodeInspection/ExcludedFiles/FilesAndFoldersToSkip2/=7020124F_002D9FFC_002D4AC3_002D8F3D_002DAAB8E0240759_002Ff_003ACastHelpers_002Ecs_002Fl_003A_002E_002E_003F_002E_002E_003F_002E_002E_003F_002E_002E_003F_002Econfig_003FJetBrains_003FRider2025_002E1_003Fresharper_002Dhost_003FDecompilerCache_003Fdecompiler_003Fd111abf504bf42b5968a609b168fd093b2e200_003Fbb_003F1c116fcd_003FCastHelpers_002Ecs/@EntryIndexedValue">ForceIncluded</s:String>
<s:String x:Key="/Default/CodeInspection/ExcludedFiles/FilesAndFoldersToSkip2/=7020124F_002D9FFC_002D4AC3_002D8F3D_002DAAB8E0240759_002Ff_003ACharacterBody2D_002Ecs_002Fl_003A_002E_002E_003F_002E_002E_003F_002E_002E_003F_002E_002E_003F_002Econfig_003FJetBrains_003FRider2025_002E1_003Fresharper_002Dhost_003FSourcesCache_003Fbba0bbd7a98ee58286e9484fbe86e01afff6232283f6efd3556eb7116453_003FCharacterBody2D_002Ecs/@EntryIndexedValue">ForceIncluded</s:String>
<s:String x:Key="/Default/CodeInspection/ExcludedFiles/FilesAndFoldersToSkip2/=7020124F_002D9FFC_002D4AC3_002D8F3D_002DAAB8E0240759_002Ff_003ANode_002Ecs_002Fl_003A_002E_002E_003F_002E_002E_003F_002E_002E_003F_002E_002E_003F_002Econfig_003FJetBrains_003FRider2025_002E1_003Fresharper_002Dhost_003FSourcesCache_003Ff1d69ec2da76ccf9bc8a75c8e0fdca9a7ba1adf8c8c9d5047e2fa5991c02eca_003FNode_002Ecs/@EntryIndexedValue">ForceIncluded</s:String></wpf:ResourceDictionary>
<s:String x:Key="/Default/CodeInspection/ExcludedFiles/FilesAndFoldersToSkip2/=7020124F_002D9FFC_002D4AC3_002D8F3D_002DAAB8E0240759_002Ff_003ADictionary_00602_002Ecs_002Fl_003A_002E_002E_003F_002E_002E_003F_002E_002E_003F_002E_002E_003F_002E_002E_003F_002E_002E_003Fhome_003Fjonathan_003F_002Econfig_003FJetBrains_003FRider2025_002E1_003Fresharper_002Dhost_003FDecompilerCache_003Fdecompiler_003Fe37dc1faf08a4d5ea030ad59bdf77522523400_003Fd4_003Fbd338aeb_003FDictionary_00602_002Ecs/@EntryIndexedValue">ForceIncluded</s:String>
<s:String x:Key="/Default/CodeInspection/ExcludedFiles/FilesAndFoldersToSkip2/=7020124F_002D9FFC_002D4AC3_002D8F3D_002DAAB8E0240759_002Ff_003ANode_002Ecs_002Fl_003A_002E_002E_003F_002E_002E_003F_002E_002E_003F_002E_002E_003F_002Econfig_003FJetBrains_003FRider2025_002E1_003Fresharper_002Dhost_003FSourcesCache_003Ff1d69ec2da76ccf9bc8a75c8e0fdca9a7ba1adf8c8c9d5047e2fa5991c02eca_003FNode_002Ecs/@EntryIndexedValue">ForceIncluded</s:String>
<s:String x:Key="/Default/CodeInspection/ExcludedFiles/FilesAndFoldersToSkip2/=7020124F_002D9FFC_002D4AC3_002D8F3D_002DAAB8E0240759_002Ff_003AResourceLoader_002Ecs_002Fl_003AC_0021_003FUsers_003FJonathan_003FAppData_003FRoaming_003FJetBrains_003FRider2025_002E1_003Fresharper_002Dhost_003FSourcesCache_003F9f4e8eb124d11f8219cb513a19bed22b2120ed29f9d6785ba56e3367b48d581_003FResourceLoader_002Ecs/@EntryIndexedValue">ForceIncluded</s:String>
<s:String x:Key="/Default/CodeInspection/ExcludedFiles/FilesAndFoldersToSkip2/=7020124F_002D9FFC_002D4AC3_002D8F3D_002DAAB8E0240759_002Ff_003AThrowHelper_002Ecs_002Fl_003AC_0021_003FUsers_003FJonathan_003FAppData_003FRoaming_003FJetBrains_003FRider2025_002E1_003Fresharper_002Dhost_003FSourcesCache_003Fc7102cd0ffb8973777e61b1942c3fffac7e14016a511d055c3adf73ff91748_003FThrowHelper_002Ecs/@EntryIndexedValue">ForceIncluded</s:String></wpf:ResourceDictionary>

@ -0,0 +1,22 @@
@tool
extends EditorPlugin
func _enter_tree() -> void:
if !ProjectSettings.has_setting("babushka/hacks/speed_hack"):
ProjectSettings.set_setting("babushka/hacks/speed_hack",-1)
var property_info = {
"name": "babushka/hacks/speed_hack",
"type": TYPE_FLOAT,
"hint": PROPERTY_HINT_RANGE,
"hint_string": "-1,20,0.5"
}
ProjectSettings.add_property_info(property_info)
ProjectSettings.set_initial_value("babushka/hacks/speed_hack",-1)
func _exit_tree() -> void:
# Clean-up of the plugin goes here.
pass

@ -0,0 +1,7 @@
[plugin]
name="BabushkaHelpers"
description=""
author="Cozy Raven"
version=""
script="babushkahelpers.gd"

@ -96,6 +96,8 @@ func _save_external_data() -> void:
if _editor_view_and_manager_exist():
editor_view.editors_manager.save_current_resource()
DialogicResourceUtil.update_directory('.tres')
func _get_unsaved_status(for_scene:String) -> String:
if for_scene.is_empty():

@ -0,0 +1,55 @@
@tool
extends DialogicEvent
class_name DialogicQuestActivateEvent
# Define properties of the event here
var quest_resource: String
func _execute() -> void:
var resource = ResourceLoader.load(quest_resource)
QuestManager.ChangeQuestStatus(resource,QuestEventUtils.QuestStatus.AVAILABLE)
QuestManager.SetActiveQuest(resource)
finish() # called to continue with the next event
#region INITIALIZE
################################################################################
# Set fixed settings of this event
func _init() -> void:
event_name = "Activate Quest"
event_category = "Quest"
#endregion
#region SAVING/LOADING
################################################################################
func get_shortcode() -> String:
return "quest_activate"
func get_shortcode_parameters() -> Dictionary:
return {
#param_name : property_info
"quest_resource" : {"property": "quest_resource", "default": ""},
}
# You can alternatively overwrite these 3 functions: to_text(), from_text(), is_valid_event()
#endregion
#region EDITOR REPRESENTATION
################################################################################
func build_event_editor() -> void:
add_header_label("Activate Quest")
add_header_edit(
"quest_resource",
ValueType.DYNAMIC_OPTIONS,
{
"mode":2,
"suggestions_func":QuestEventUtils.quest_resource_suggestrions
})
#endregion

@ -0,0 +1,55 @@
@tool
extends DialogicEvent
class_name DialogicQuestCompleteEvent
# Define properties of the event here
var quest_resource: String
func _execute() -> void:
var resource = ResourceLoader.load(quest_resource)
QuestManager.ChangeQuestStatus(resource,QuestEventUtils.QuestStatus.DONE)
QuestManager.SetActiveQuest(null)
finish() # called to continue with the next event
#region INITIALIZE
################################################################################
# Set fixed settings of this event
func _init() -> void:
event_name = "Complete Quest"
event_category = "Quest"
#endregion
#region SAVING/LOADING
################################################################################
func get_shortcode() -> String:
return "quest_complete"
func get_shortcode_parameters() -> Dictionary:
return {
#param_name : property_info
"quest_resource" : {"property": "quest_resource", "default": ""},
}
# You can alternatively overwrite these 3 functions: to_text(), from_text(), is_valid_event()
#endregion
#region EDITOR REPRESENTATION
################################################################################
func build_event_editor() -> void:
add_header_label("Complete Quest")
add_header_edit(
"quest_resource",
ValueType.DYNAMIC_OPTIONS,
{
"mode":2,
"suggestions_func":QuestEventUtils.quest_resource_suggestrions
})
#endregion

@ -0,0 +1,163 @@
@tool
extends DialogicEvent
class_name DialogicQuestConditionEvent
## Event that allows branching a timeline based on a condition.
#enum ConditionTypes {IF, ELIF, ELSE}
### Settings
## condition type (see [ConditionTypes]). Defaults to if.
#var condition_type := ConditionTypes.IF
## The condition as a string. Will be executed as an Expression.
#var condition := ""
var quest_resource: String
var compare_status: QuestEventUtils.QuestStatusOrActive
################################################################################
## EXECUTE
################################################################################
func _execute() -> void:
var resource = ResourceLoader.load(quest_resource)
var result: bool
if compare_status == QuestEventUtils.QuestStatusOrActive.ACTIVE:
result = QuestManager.GetActiveQuest() == resource
elif compare_status == QuestEventUtils.QuestStatusOrActive.NOT_ACTIVE:
result = QuestManager.GetActiveQuest() != resource
else:
result = QuestManager.GetQuestStatus(resource).status == compare_status
if not result:
var idx: int = dialogic.current_event_idx
var ignore := 1
while true:
idx += 1
if not dialogic.current_timeline.get_event(idx) or ignore == 0:
break
elif dialogic.current_timeline.get_event(idx).can_contain_events:
ignore += 1
elif dialogic.current_timeline.get_event(idx) is DialogicEndBranchEvent:
ignore -= 1
dialogic.current_event_idx = idx-1
finish()
## only called if the previous event was an end-branch event
## return true if this event should be executed if the previous event was an end-branch event
func should_execute_this_branch() -> bool:
return true
################################################################################
## INITIALIZE
################################################################################
func _init() -> void:
event_name = "Quest Condition"
set_default_color('Color3')
event_category = "Quest"
event_sorting_index = 1
can_contain_events = true
# return a control node that should show on the END BRANCH node
func get_end_branch_control() -> Control:
return load(get_script().resource_path.get_base_dir().path_join('ui_quest_condition_end.tscn')).instantiate()
################################################################################
## SAVING/LOADING
################################################################################
func to_text() -> String:
return 'ifquest ' + quest_resource + ', ' + str(compare_status) + ':'
func from_text(string:String) -> void:
#if string.strip_edges().begins_with('if'):
# condition = string.strip_edges().trim_prefix('if ').trim_suffix(':').strip_edges()
# condition_type = ConditionTypes.IF
var strings:Array[String]
strings.assign(string.strip_edges().trim_prefix('ifquest ').trim_suffix(':').strip_edges().split(','))
quest_resource = strings[0].strip_edges()
var compare_string: String = strings[1].strip_edges()
if compare_string.is_valid_int():
compare_status = compare_string.to_int()
else:
compare_status = QuestEventUtils.QuestStatusOrActive.get(compare_string)
func is_valid_event(string:String) -> bool:
if string.strip_edges().begins_with('ifquest '):
return true
return false
################################################################################
## EDITOR REPRESENTATION
################################################################################
func build_event_editor() -> void:
add_header_label("IF")
add_header_edit(
"quest_resource",
ValueType.DYNAMIC_OPTIONS,
{
"mode":2,
"suggestions_func":QuestEventUtils.quest_resource_suggestrions
})
add_header_label("IS")
add_header_edit("compare_status",ValueType.FIXED_OPTIONS,{
'options': [
{
'label': 'HIDDEN',
'value': QuestEventUtils.QuestStatusOrActive.HIDDEN,
},
{
'label': 'AVAILABLE',
'value': QuestEventUtils.QuestStatusOrActive.AVAILABLE,
},
{
'label': 'DONE',
'value': QuestEventUtils.QuestStatusOrActive.DONE,
},
{
'label': 'CANCLED',
'value': QuestEventUtils.QuestStatusOrActive.CANCLED,
},
{
'label': 'ACTIVE',
'value': QuestEventUtils.QuestStatusOrActive.ACTIVE,
},
{
'label': 'NOT_ACTIVE',
'value': QuestEventUtils.QuestStatusOrActive.NOT_ACTIVE,
}
]})
func _get_icon() -> Resource:
return load("res://addons/dialogic/Modules/Condition/icon.svg")
####################### CODE COMPLETION ########################################
################################################################################
func _get_code_completion(CodeCompletionHelper:Node, TextNode:TextEdit, line:String, _word:String, symbol:String) -> void:
pass
func _get_start_code_completion(_CodeCompletionHelper:Node, TextNode:TextEdit) -> void:
TextNode.add_code_completion_option(CodeEdit.KIND_PLAIN_TEXT, 'ifquest', 'ifquest ', TextNode.syntax_highlighter.code_flow_color)
#################### SYNTAX HIGHLIGHTING #######################################
################################################################################
func _get_syntax_highlighting(Highlighter:SyntaxHighlighter, dict:Dictionary, line:String) -> Dictionary:
var word := line.get_slice(' ', 0)
dict[line.find(word)] = {"color":Highlighter.code_flow_color}
dict[line.find(word)+len(word)] = {"color":Highlighter.normal_color}
dict = Highlighter.color_condition(dict, line)
return dict

@ -0,0 +1,43 @@
@tool
class_name QuestEventUtils
enum QuestStatus{
HIDDEN = 0,
AVAILABLE = 1,
DONE = 2,
CANCLED = 3
}
enum QuestStatusOrActive{
HIDDEN = 0,
AVAILABLE = 1,
DONE = 2,
CANCLED = 3,
ACTIVE = 4,
NOT_ACTIVE = 5
}
static func quest_resource_suggestrions(search_text:String) -> Dictionary:
var ret_val = {}
var quest_paths = get_all_file_paths("res://resources/quests")
for path in quest_paths:
var res = ResourceLoader.load(path)
ret_val[res.id]= {"value":path, "tooltip":res.title + "\n\n" + res.description}
return ret_val
static func get_all_file_paths(path: String) -> Array[String]:
var file_paths: Array[String] = []
var dir = DirAccess.open(path)
dir.list_dir_begin()
var file_name = dir.get_next()
while file_name != "":
var file_path = path + "/" + file_name
if dir.current_is_dir():
file_paths += get_all_file_paths(file_path)
else:
file_paths.append(file_path)
file_name = dir.get_next()
return file_paths

@ -0,0 +1,9 @@
@tool
extends DialogicIndexer
func _get_events() -> Array:
return [
this_folder.path_join('event_quest_activate.gd'),
this_folder.path_join('event_quest_complete.gd'),
this_folder.path_join('event_quest_condition.gd')
]

@ -0,0 +1,51 @@
@tool
extends HBoxContainer
var parent_resource: DialogicEvent = null
func _ready() -> void:
$AddElif.button_up.connect(add_elif)
$AddElse.button_up.connect(add_else)
func refresh() -> void:
if parent_resource is DialogicQuestConditionEvent:
# hide add elif and add else button on ELSE event
$AddElif.visible = false# parent_resource.condition_type != DialogicConditionEvent.ConditionTypes.ELSE
$AddElse.visible = true# parent_resource.condition_type != DialogicConditionEvent.ConditionTypes.ELSE
$Label.text = "End of If Quest" #"End of "+["IF", "ELIF", "ELSE"][parent_resource.condition_type]+" ("+parent_resource.condition+")"
# hide add add else button if followed by ELIF or ELSE event
var timeline_editor := find_parent('VisualEditor')
if timeline_editor:
var next_event: DialogicEvent = null
if timeline_editor.get_block_below(get_parent()):
next_event = timeline_editor.get_block_below(get_parent()).resource
if next_event is DialogicConditionEvent:
if next_event.condition_type != DialogicConditionEvent.ConditionTypes.IF:
$AddElse.hide()
#if parent_resource.condition_type == DialogicConditionEvent.ConditionTypes.ELSE:
# $Label.text = "End of ELSE"
else:
hide()
func add_elif() -> void:
var timeline := find_parent('VisualEditor')
if timeline:
var resource := DialogicConditionEvent.new()
resource.condition_type = DialogicConditionEvent.ConditionTypes.ELIF
timeline.add_event_undoable(resource, get_parent().get_index()+1)
timeline.indent_events()
timeline.something_changed()
func add_else() -> void:
var timeline := find_parent('VisualEditor')
if timeline:
var resource := DialogicConditionEvent.new()
resource.condition_type = DialogicConditionEvent.ConditionTypes.ELSE
timeline.add_event_undoable(resource, get_parent().get_index()+1)
timeline.indent_events()
timeline.something_changed()

@ -0,0 +1,20 @@
[gd_scene load_steps=2 format=3 uid="uid://dnrpcgjkyoiau"]
[ext_resource type="Script" uid="uid://dlrnhnnonum4o" path="res://addons/dialogic_additions/Quest/ui_condition_end.gd" id="1_f3miq"]
[node name="Condition_End" type="HBoxContainer"]
offset_right = 90.0
offset_bottom = 23.0
script = ExtResource("1_f3miq")
[node name="Label" type="Label" parent="."]
layout_mode = 2
text = "End of condition X"
[node name="AddElif" type="Button" parent="."]
layout_mode = 2
text = "Add Elif"
[node name="AddElse" type="Button" parent="."]
layout_mode = 2
text = "Add Else"

@ -1,6 +1,8 @@
[quest_complete quest_resource="res://resources/quests/demo/7_talk_yeli_inside_1.tres"]
join Yeli center
Yeli: Thank you for your help out there.
Yeli: You must be tired. Please rest. I prepared a bed for you. It's in the room to the left.
Yeli: There is nothing interesting to see here.
leave Yeli
[quest_activate quest_resource="res://resources/quests/demo/8_goto_bed.tres"]
[end_timeline]

@ -1,3 +1,5 @@
join vesna center
[quest_complete quest_resource="res://resources/quests/demo/2_collect_ducks.tres"]
Thats the last one. I should get back to Yeli.
[quest_activate quest_resource="res://resources/quests/demo/3_talk_yeli_2.tres"]
[end_timeline]

@ -1,8 +1,10 @@
join Yeli right
join vesna left
[quest_complete quest_resource="res://resources/quests/demo/1_talk_yeli_1.tres"]
Yeli (_part_side): Come here, you little quacking beast!
- What a mess!
- How did you call me?
Yeli (_part_side): Vesna, oh, thank goodness!
Yeli (_part_side): Please could you get the runner ducks back into their coop?
[quest_activate quest_resource="res://resources/quests/demo/2_collect_ducks.tres"]
[end_timeline]

@ -1,3 +1,4 @@
[quest_complete quest_resource="res://resources/quests/demo/9_talk_to_chuga.tres"]
join vesna center
join Chuga center
Chuga: Look who it is!
@ -19,4 +20,5 @@ Chuga: So, listen\: “I wear a crown, but Im no king.” Vesna, what am I?
- Soup
Chuga: Hate the player, not the game.
Chuga: Here you go!
[quest_activate quest_resource="res://resources/quests/demo/10_fight_the_monsters.tres"]
[end_timeline]

@ -1,5 +1,6 @@
join Yeli center
join vesna center
[quest_complete quest_resource="res://resources/quests/demo/5_talk_yeli_3.tres"]
Yeli (_part_side): Great! Now I need you to plant some tomatoes!
label plant tomatoes
Yeli (_part_side): Use the hoe to break up the soil. Then plant the seeds and water the fields.
@ -7,4 +8,5 @@ Yeli (_part_side): Got it?
- Of course!
- Wait … How do I plant the tomatoes again?
jump plant tomatoes
[quest_activate quest_resource="res://resources/quests/demo/6_till_and_water.tres"]
[end_timeline]

@ -1,5 +1,6 @@
join Yeli center
join vesna center
[quest_complete quest_resource="res://resources/quests/demo/3_talk_yeli_2.tres"]
Yeli (_part_side): Thank you, my child! Your Yeli is not so agile anymore.
vesna: But youre diligent! Youve started with the preparation for dinner.
Yeli (_part_side): Indeed, I have.
@ -7,4 +8,5 @@ Yeli (_part_side): But, oh my, those ducks messed up the tomatos.
Yeli (_part_side): Oh, would you like to assist me?
vesna: What do I have to do?
Yeli (_part_side): First, take the hoe and watering can over there! Then come back to me!
[quest_activate quest_resource="res://resources/quests/demo/4_collect_tools.tres"]
[end_timeline]

@ -0,0 +1,15 @@
Quest\: {ACTIVEQUEST}
ifquest res://resources/quests/test/test_01.tres, 4:
Test 1 active
else:
Test 1 is not active
ifquest res://resources/quests/test/test_01.tres, 1:
But its available
else:
And not available
ifquest res://resources/quests/test/test_02.tres, 4:
Test 2 active
ifquest res://resources/quests/test/test_02.tres, 1:
And Available
else:
Else 2

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

@ -0,0 +1,10 @@
ifquest res://resources/quests/demo/1_talk_yeli_1.tres, 1:
jump quest1_ducks_start/
[end_timeline]
ifquest res://resources/quests/demo/3_talk_yeli_2.tres, 1:
jump quest2_tomatoes_start/
[end_timeline]
ifquest res://resources/quests/demo/5_talk_yeli_3.tres, 1:
jump quest2_tomatoes_interim/
[end_timeline]
No Dialog for active quest "{ACTIVEQUEST}"

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

@ -1,7 +1,7 @@
[gd_scene load_steps=11 format=3 uid="uid://cgjc4wurbgimy"]
[ext_resource type="Script" uid="uid://hg7jay2kt441" path="res://scripts/CSharp/Common/Inventory/InventoryUi.cs" id="1_6wusm"]
[ext_resource type="Script" uid="uid://cvkw4qd2hxksi" path="res://scripts/GdScript/dialogic_toggle.gd" id="1_l3npx"]
[ext_resource type="Script" path="res://scripts/GdScript/dialogic_toggle.gd" id="1_l3npx"]
[ext_resource type="Texture2D" uid="uid://3ln8aleyxgp1" path="res://art/ui/UI/UI_bag_export_01.png" id="3_vvo7l"]
[ext_resource type="Texture2D" uid="uid://u0dku75l17re" path="res://art/ui/UI/UI_bag_export_highlight_01.png" id="5_df8i8"]
[ext_resource type="PackedScene" uid="uid://c0kmdjeqkqrwv" path="res://prefabs/UI/Inventory/Slot.tscn" id="5_u7kje"]
@ -458,7 +458,6 @@ expand_mode = 1
[node name="QuestLogRoot" parent="." instance=ExtResource("7_vvo7l")]
[node name="Control" type="Control" parent="."]
visible = false
layout_mode = 3
anchors_preset = 2
anchor_top = 1.0

@ -473,7 +473,7 @@
[ext_resource type="Texture2D" uid="uid://x8hr8287ff2n" path="res://art/farm/farming/farmobjekte/tools atlas.png" id="816_1a3c1"]
[ext_resource type="Script" uid="uid://bcskt5ckh3rqa" path="res://scripts/CSharp/Common/Farming/FarmingControls2D.cs" id="817_6nrw3"]
[ext_resource type="PackedScene" uid="uid://b1d2e7ely6hyw" path="res://prefabs/farm/tomato_field.tscn" id="818_16w6h"]
[ext_resource type="Script" uid="uid://cvkw4qd2hxksi" path="res://scripts/GdScript/dialogic_toggle.gd" id="819_4na52"]
[ext_resource type="Script" path="res://scripts/GdScript/dialogic_toggle.gd" id="819_4na52"]
[sub_resource type="CircleShape2D" id="CircleShape2D_ssqtd"]
radius = 110.018
@ -2071,7 +2071,7 @@ y_sort_enabled = true
script = ExtResource("1_yd5ep")
_farmingControls = NodePath("FarmingControls")
_player2d = NodePath("CharacterBody2D")
_vesnaAnimations = NodePath("CharacterBody2D/visuals/Animated Sprites")
_vesnaAnimations = NodePath("CharacterBody2D/visuals")
[node name="CharacterBody2D" type="CharacterBody2D" parent="." groups=["PlantGrowing"]]
position = Vector2(0, 374)

@ -43,7 +43,7 @@
[ext_resource type="Texture2D" uid="uid://droj8w1mbm5k3" path="res://art/animation/Yeli2D/F02-Yeli_Talk/0019.png" id="39_vg7xi"]
[ext_resource type="Texture2D" uid="uid://by5vtadhdwwag" path="res://art/animation/Yeli2D/F02-Yeli_Talk/0020.png" id="40_ipyxb"]
[ext_resource type="PackedScene" uid="uid://cqc72e4hq6bcd" path="res://prefabs/interactions/interaction_area_2d.tscn" id="42_ahrat"]
[ext_resource type="Script" uid="uid://cvkw4qd2hxksi" path="res://scripts/GdScript/dialogic_toggle.gd" id="44_aqu1t"]
[ext_resource type="Script" path="res://scripts/GdScript/dialogic_toggle.gd" id="44_aqu1t"]
[sub_resource type="CircleShape2D" id="CircleShape2D_at1n1"]
resource_local_to_scene = true
@ -212,9 +212,6 @@ offset = Vector2(0, -450)
[node name="Dialogic starter" type="Node2D" parent="."]
script = ExtResource("1_at1n1")
[node name="DialogicToggle" type="Node2D" parent="Dialogic starter"]
script = ExtResource("44_aqu1t")
[node name="AnimatableBody2D" type="AnimatableBody2D" parent="."]
position = Vector2(0, -172)
@ -229,6 +226,5 @@ itemToToggle = NodePath("../TalkingControl/AnimatedSprite")
[connection signal="Talking" from="." to="Dialogic starter" method="open"]
[connection signal="Interacted" from="InteractionArea" to="." method="ToggleTalking"]
[connection signal="timelineEnded" from="Dialogic starter/DialogicToggle" to="." method="ToggleTalking"]
[editable path="InteractionArea"]

@ -0,0 +1,12 @@
[gd_scene load_steps=3 format=3 uid="uid://bworek1jcmq0e"]
[ext_resource type="Script" uid="uid://dl2uhq12p3qks" path="res://scripts/CSharp/Common/Quest/QuestManager.cs" id="1_anowe"]
[ext_resource type="Script" path="res://scripts/GdScript/dialogic_var_setter.gd" id="4_v86gc"]
[node name="QuestManager" type="Node"]
script = ExtResource("1_anowe")
[node name="DialogicRelay" type="Node" parent="."]
script = ExtResource("4_v86gc")
[connection signal="DialogicActiveQuest" from="." to="DialogicRelay" method="_SetActiveQuestVar"]

@ -28,10 +28,10 @@ buses/default_bus_layout="uid://b6dwkmkyb0axk"
SceneTransition="*res://scenes/SceneTransition.tscn"
Dialogic="*res://addons/dialogic/Core/DialogicGameHandler.gd"
InventoryManager="*res://scripts/CSharp/Common/Inventory/InventoryManager.cs"
Signal_Debugger="*res://addons/SignalVisualizer/Debugger/SignalDebugger.gd"
QuestManager="*res://scripts/CSharp/Common/Quest/QuestManager.cs"
FightManagerAutoload="*res://prefabs/fight/fight_manager_autoload.tscn"
InputService="*res://scripts/CSharp/Common/Services/InputService.cs"
QuestManager="*res://prefabs/quests/quest_manager_autoload.tscn"
Signal_Debugger="*res://addons/SignalVisualizer/Debugger/SignalDebugger.gd"
[dialogic]
@ -59,14 +59,17 @@ directories/dtl_directory={
"quest5_forest_start": "res://dialog/quests/forest/quest5_forest_start.dtl",
"semi_cat": "res://dialog/semi_cat.dtl",
"talk_to_plant": "res://dialog/talk_to_plant.dtl",
"test_1": "res://dialog/testing/test_1.dtl",
"test_time_line": "res://dialog/test_time_line.dtl",
"yeli_intro_01": "res://dialog/Scene1_farm_outside/yeli_intro_01.dtl",
"yeli_intro_02": "res://dialog/Scene1_farm_outside/yeli_intro_02.dtl",
"yeli_intro_03": "res://dialog/Scene1_farm_outside/yeli_intro_03.dtl",
"yeli_intro_04": "res://dialog/Scene1_farm_outside/yeli_intro_04.dtl",
"yeli_intro_05": "res://dialog/Scene1_farm_outside/yeli_intro_05.dtl"
"yeli_intro_05": "res://dialog/Scene1_farm_outside/yeli_intro_05.dtl",
"yeli_quest_select": "res://dialog/yeli_quest_select.dtl"
}
variables={
"ACTIVEQUEST": "none",
"MAGICWORD": "Hokus Pokus!s",
"PLAYERMOOD": "Good",
"SHOW": "IGF"
@ -106,6 +109,64 @@ translation/id_counter=22
translation/locales=["de", "en"]
text/autopauses={}
glossary/glossary_files=["res://dialog/farming_equipment_glossary.tres"]
directories/tres_directory={
"10_fight_the_monsters": "res://resources/quests/demo/10_fight_the_monsters.tres",
"1_talk_yeli_1": "res://resources/quests/demo/1_talk_yeli_1.tres",
"2_collect_ducks": "res://resources/quests/demo/2_collect_ducks.tres",
"3_talk_yeli_2": "res://resources/quests/demo/3_talk_yeli_2.tres",
"4_collect_tools": "res://resources/quests/demo/4_collect_tools.tres",
"5_talk_yeli_3": "res://resources/quests/demo/5_talk_yeli_3.tres",
"6_till_and_water": "res://resources/quests/demo/6_till_and_water.tres",
"7_talk_yeli_inside_1": "res://resources/quests/demo/7_talk_yeli_inside_1.tres",
"8_goto_bed": "res://resources/quests/demo/8_goto_bed.tres",
"9_talk_to_chuga": "res://resources/quests/demo/9_talk_to_chuga.tres",
"Babushka_NPC_Namebox_background": "res://dialog/Babushka_NPC_Namebox_background.tres",
"InputFieldsStyle": "res://addons/dialogic/Editor/Events/styles/InputFieldsStyle.tres",
"MainTheme": "res://addons/dialogic/Editor/Theme/MainTheme.tres",
"NPC_narrative": "res://dialog/NPC_narrative.tres",
"New_File": "res://addons/dialogic/New_File.tres",
"PickerTheme": "res://addons/dialogic/Editor/Theme/PickerTheme.tres",
"ResourceMenuHover": "res://addons/dialogic/Editor/Events/styles/ResourceMenuHover.tres",
"ResourceMenuNormal": "res://addons/dialogic/Editor/Events/styles/ResourceMenuNormal.tres",
"ResourceMenuPanelBackground": "res://addons/dialogic/Editor/Events/styles/ResourceMenuPanelBackground.tres",
"SectionPanel": "res://addons/dialogic/Editor/Events/styles/SectionPanel.tres",
"SimpleButtonHover": "res://addons/dialogic/Editor/Events/styles/SimpleButtonHover.tres",
"SimpleButtonNormal": "res://addons/dialogic/Editor/Events/styles/SimpleButtonNormal.tres",
"TextBackground": "res://addons/dialogic/Editor/Events/styles/TextBackground.tres",
"TitleBgStylebox": "res://addons/dialogic/Editor/Common/TitleBgStylebox.tres",
"beet": "res://resources/items/beet.tres",
"beetRoot": "res://resources/quests/beetRoot.tres",
"choice_panel_focus": "res://addons/dialogic/Modules/DefaultLayoutParts/Layer_VN_Choices/choice_panel_focus.tres",
"choice_panel_hover": "res://addons/dialogic/Modules/DefaultLayoutParts/Layer_VN_Choices/choice_panel_hover.tres",
"choice_panel_normal": "res://addons/dialogic/Modules/DefaultLayoutParts/Layer_VN_Choices/choice_panel_normal.tres",
"default_bus_layout": "res://audio/default_bus_layout.tres",
"default_stylebox": "res://addons/dialogic/Modules/DefaultLayoutParts/Layer_SpeakerPortraitTextbox/default_stylebox.tres",
"default_vn_style": "res://addons/dialogic/Modules/DefaultLayoutParts/Style_VN_Default/default_vn_style.tres",
"farming_equipment_glossary": "res://dialog/farming_equipment_glossary.tres",
"hoe": "res://resources/items/hoe.tres",
"inventory_interactable_outline": "res://art/materials/inventory_interactable_outline.tres",
"preview_character": "res://addons/dialogic/Modules/Character/preview_character.tres",
"rake": "res://resources/items/rake.tres",
"scythe": "res://resources/items/scythe.tres",
"selected_styleboxflat": "res://addons/dialogic/Editor/Events/styles/selected_styleboxflat.tres",
"shovel": "res://resources/items/shovel.tres",
"simple_fade": "res://addons/dialogic/Modules/Background/Transitions/Defaults/simple_fade.tres",
"simple_interactable_outline": "res://art/materials/simple_interactable_outline.tres",
"simple_swipe_gradient": "res://addons/dialogic/Modules/Background/Transitions/simple_swipe_gradient.tres",
"speaker_textbox_style": "res://addons/dialogic/Modules/DefaultLayoutParts/Style_SpeakerTextbox/speaker_textbox_style.tres",
"speechbubble": "res://dialog/speechbubble.tres",
"test": "res://resources/items/test.tres",
"test/test_01": "res://resources/quests/test/test_01.tres",
"test/test_02": "res://resources/quests/test/test_02.tres",
"test/test_03": "res://resources/quests/test/test_03.tres",
"textbubble_style": "res://addons/dialogic/Modules/DefaultLayoutParts/Style_TextBubbles/textbubble_style.tres",
"tomato": "res://resources/items/tomato.tres",
"tomato_seed": "res://resources/items/tomato_seed.tres",
"unselected_stylebox": "res://addons/dialogic/Editor/Events/styles/unselected_stylebox.tres",
"vn_textbox_default_panel": "res://addons/dialogic/Modules/DefaultLayoutParts/Layer_VN_Textbox/vn_textbox_default_panel.tres",
"vn_textbox_name_label_panel": "res://addons/dialogic/Modules/DefaultLayoutParts/Layer_VN_Textbox/vn_textbox_name_label_panel.tres",
"wateringcan": "res://resources/items/wateringcan.tres"
}
[display]
@ -124,7 +185,7 @@ movie_writer/movie_file="/home/kaddi/Documents/Repos/Godot/Babushka/_clips/clip.
[editor_plugins]
enabled=PackedStringArray("res://addons/SignalVisualizer/plugin.cfg", "res://addons/anthonyec.camera_preview/plugin.cfg", "res://addons/dialogic/plugin.cfg")
enabled=PackedStringArray("res://addons/SignalVisualizer/plugin.cfg", "res://addons/anthonyec.camera_preview/plugin.cfg", "res://addons/babushkahelpers/plugin.cfg", "res://addons/dialogic/plugin.cfg")
[file_customization]

@ -0,0 +1,10 @@
[gd_resource type="Resource" script_class="QuestResource" load_steps=2 format=3 uid="uid://cv3wtnn0138ax"]
[ext_resource type="Script" uid="uid://vji5lp4qc8pp" path="res://scripts/CSharp/Common/Quest/QuestResource.cs" id="1_m0nkd"]
[resource]
script = ExtResource("1_m0nkd")
id = "10_fight_the_monsters"
title = "Fight the monsters"
description = "A dangerous path lies before you. Be brave and slay the monsters to reach the other side."
metadata/_custom_type_script = "uid://vji5lp4qc8pp"

@ -0,0 +1,10 @@
[gd_resource type="Resource" script_class="QuestResource" load_steps=2 format=3 uid="uid://cm8kftow8br00"]
[ext_resource type="Script" uid="uid://vji5lp4qc8pp" path="res://scripts/CSharp/Common/Quest/QuestResource.cs" id="1_xjwrv"]
[resource]
script = ExtResource("1_xjwrv")
id = "1_talk_yeli_1"
title = "Talk to Yeli"
description = ""
metadata/_custom_type_script = "uid://vji5lp4qc8pp"

@ -0,0 +1,10 @@
[gd_resource type="Resource" script_class="QuestResource" load_steps=2 format=3 uid="uid://cy0na3ukvpoou"]
[ext_resource type="Script" uid="uid://vji5lp4qc8pp" path="res://scripts/CSharp/Common/Quest/QuestResource.cs" id="1_wactd"]
[resource]
script = ExtResource("1_wactd")
id = "2_collect_ducks"
title = "Collect the Ducks"
description = "Collect all 6 ducks running around the farm by aporaching them and pressing [E]"
metadata/_custom_type_script = "uid://vji5lp4qc8pp"

@ -0,0 +1,10 @@
[gd_resource type="Resource" script_class="QuestResource" load_steps=2 format=3 uid="uid://mf0rdejw8fuk"]
[ext_resource type="Script" uid="uid://vji5lp4qc8pp" path="res://scripts/CSharp/Common/Quest/QuestResource.cs" id="1_70pjl"]
[resource]
script = ExtResource("1_70pjl")
id = "3_talk_yeli_2"
title = "Talk to Yeli again"
description = "All ducks are collected. Head back to yeli."
metadata/_custom_type_script = "uid://vji5lp4qc8pp"

@ -0,0 +1,10 @@
[gd_resource type="Resource" script_class="QuestResource" load_steps=2 format=3 uid="uid://d2swjixbnqkbw"]
[ext_resource type="Script" uid="uid://vji5lp4qc8pp" path="res://scripts/CSharp/Common/Quest/QuestResource.cs" id="1_e51xd"]
[resource]
script = ExtResource("1_e51xd")
id = "4_collect_tools"
title = "Collect the farm tools"
description = "Collect the Watering Can next to the well and the Hoe by the fence."
metadata/_custom_type_script = "uid://vji5lp4qc8pp"

@ -0,0 +1,10 @@
[gd_resource type="Resource" script_class="QuestResource" load_steps=2 format=3 uid="uid://5t8g0firdif0"]
[ext_resource type="Script" uid="uid://vji5lp4qc8pp" path="res://scripts/CSharp/Common/Quest/QuestResource.cs" id="1_x7fvu"]
[resource]
script = ExtResource("1_x7fvu")
id = "5_talk_yeli_3"
title = "Talk to Yeli again"
description = "After the long and agonizing task of finding and collecting two tools, go talk to Yeli once again."
metadata/_custom_type_script = "uid://vji5lp4qc8pp"

@ -0,0 +1,10 @@
[gd_resource type="Resource" script_class="QuestResource" load_steps=2 format=3 uid="uid://h05jgxqtq37m"]
[ext_resource type="Script" uid="uid://vji5lp4qc8pp" path="res://scripts/CSharp/Common/Quest/QuestResource.cs" id="1_745w5"]
[resource]
script = ExtResource("1_745w5")
id = "6_till_and_water"
title = "Till and water the fields"
description = "Use the hoe to break up the soil. Then plant the seeds and water the fields."
metadata/_custom_type_script = "uid://vji5lp4qc8pp"

@ -0,0 +1,10 @@
[gd_resource type="Resource" script_class="QuestResource" load_steps=2 format=3 uid="uid://byjqeukpibkvi"]
[ext_resource type="Script" uid="uid://vji5lp4qc8pp" path="res://scripts/CSharp/Common/Quest/QuestResource.cs" id="1_f2jsb"]
[resource]
script = ExtResource("1_f2jsb")
id = "7_talk_yeli_inside_1"
title = "Talk to Yeli in the house"
description = "Go inside the house and find yeli again"
metadata/_custom_type_script = "uid://vji5lp4qc8pp"

@ -0,0 +1,10 @@
[gd_resource type="Resource" script_class="QuestResource" load_steps=2 format=3 uid="uid://csj15gnlx1jmx"]
[ext_resource type="Script" uid="uid://vji5lp4qc8pp" path="res://scripts/CSharp/Common/Quest/QuestResource.cs" id="1_y6h00"]
[resource]
script = ExtResource("1_y6h00")
id = "8_goto_bed"
title = "Go to sleep"
description = "Go into Vesnas room on the left of the house. Go to bed to unexaust you."
metadata/_custom_type_script = "uid://vji5lp4qc8pp"

@ -0,0 +1,10 @@
[gd_resource type="Resource" script_class="QuestResource" load_steps=2 format=3 uid="uid://c3mwhrvk12oml"]
[ext_resource type="Script" uid="uid://vji5lp4qc8pp" path="res://scripts/CSharp/Common/Quest/QuestResource.cs" id="1_hrrlk"]
[resource]
script = ExtResource("1_hrrlk")
id = "9_talk_to_chuga"
title = "Talk to Chuga"
description = "A strange creature is standing infront of you. Go talk to him. I promise, he won't hurt you... for now."
metadata/_custom_type_script = "uid://vji5lp4qc8pp"

@ -5,6 +5,5 @@
[node name="BabushkaSceneBootstrap" type="Node2D"]
[node name="BabushkaSceneStartMenu" parent="." instance=ExtResource("1_15ton")]
_sceneNamesToLoad = PackedStringArray("res://scenes/Babushka_scene_farm_outside_2d.tscn")
[node name="SceneParent" type="Node" parent="."]

@ -1,4 +1,4 @@
[gd_scene load_steps=107 format=3 uid="uid://gigb28qk8t12"]
[gd_scene load_steps=119 format=3 uid="uid://gigb28qk8t12"]
[ext_resource type="PackedScene" uid="uid://c25udixd5m6l0" path="res://prefabs/characters/Player2D.tscn" id="1_7wfwe"]
[ext_resource type="Texture2D" uid="uid://8sr11ex30n0m" path="res://art/mockups/Kenney_Backgrounds/Samples/uncolored_hills.png" id="2_7b2ri"]
@ -67,6 +67,16 @@
[ext_resource type="Script" uid="uid://d2486x6upmwqq" path="res://scripts/GdScript/dialogic_starter.gd" id="52_lwk6t"]
[ext_resource type="PackedScene" uid="uid://sbf12hin4kes" path="res://prefabs/Interactables/trash_object.tscn" id="53_ycj14"]
[ext_resource type="PackedScene" uid="uid://muuxxgvx33fp" path="res://prefabs/farm/duck.tscn" id="62_i36hd"]
[ext_resource type="Script" uid="uid://cldtt4atgymm5" path="res://scripts/CSharp/Common/Quest/QuestTrigger.cs" id="66_2065p"]
[ext_resource type="Resource" uid="uid://cm8kftow8br00" path="res://resources/quests/demo/1_talk_yeli_1.tres" id="67_tm0yg"]
[ext_resource type="Script" uid="uid://c741nyedy26mx" path="res://scripts/CSharp/Common/QuestBehaviour/DetectInventoryContains.cs" id="68_hux6i"]
[ext_resource type="Resource" uid="uid://d2swjixbnqkbw" path="res://resources/quests/demo/4_collect_tools.tres" id="68_lbnqo"]
[ext_resource type="Script" uid="uid://be54lnb6gg81f" path="res://scripts/CSharp/Common/Inventory/ItemInstance.cs" id="69_4rgbr"]
[ext_resource type="Resource" uid="uid://5t8g0firdif0" path="res://resources/quests/demo/5_talk_yeli_3.tres" id="69_l4wxt"]
[ext_resource type="Script" uid="uid://bhbldab74vmhy" path="res://scripts/CSharp/Common/QuestBehaviour/DetectFieldWork.cs" id="74_fv1t2"]
[ext_resource type="Resource" uid="uid://h05jgxqtq37m" path="res://resources/quests/demo/6_till_and_water.tres" id="75_l7ekk"]
[ext_resource type="Resource" uid="uid://byjqeukpibkvi" path="res://resources/quests/demo/7_talk_yeli_inside_1.tres" id="76_xcwle"]
[ext_resource type="Script" uid="uid://dih1b0opgc3f7" path="res://scripts/GdScript/dialogic_start_specific.gd" id="77_l7ekk"]
[sub_resource type="ShaderMaterial" id="ShaderMaterial_wtdui"]
shader = ExtResource("13_7p0hq")
@ -260,6 +270,18 @@ stream_0/stream = ExtResource("39_di1ed")
stream_1/stream = ExtResource("40_ceriq")
stream_2/stream = ExtResource("49_d77e7")
[sub_resource type="Resource" id="Resource_y820s"]
script = ExtResource("69_4rgbr")
blueprint = ExtResource("28_ipqaa")
amount = 1
metadata/_custom_type_script = "uid://be54lnb6gg81f"
[sub_resource type="Resource" id="Resource_50loj"]
script = ExtResource("69_4rgbr")
blueprint = ExtResource("28_6b2nr")
amount = 1
metadata/_custom_type_script = "uid://be54lnb6gg81f"
[node name="BabushkaSceneFarmOutside2d" type="Node2D"]
script = ExtResource("34_e5b7x")
_sceneNamesToLoad = PackedStringArray("res://scenes/Babushka_scene_indoor_common_room.tscn")
@ -1021,7 +1043,8 @@ y_sort_enabled = true
[node name="Yeli" parent="YSorted" instance=ExtResource("24_wtdui")]
position = Vector2(6403, 3362)
_timelinesToPlay = PackedStringArray("quest1_ducks_start", "quest2_tomatoes_start", "quest2_tomatoes_interim", "quest2_tomatoes_end")
_timelinesToPlay = PackedStringArray("yeli_quest_select")
_retriggerSameTimeline = true
[node name="Vesna" parent="YSorted" node_paths=PackedStringArray("_fieldParent") instance=ExtResource("1_7wfwe")]
z_index = 1
@ -2350,6 +2373,31 @@ max_distance = 2e+07
playback_type = 2
script = ExtResource("40_w3jkj")
[node name="SpeicialQuestTrigger" type="Node" parent="."]
[node name="QuestInstantStart" type="Node" parent="SpeicialQuestTrigger"]
[node name="QuestTrigger" type="Node" parent="SpeicialQuestTrigger/QuestInstantStart"]
script = ExtResource("66_2065p")
questResource = ExtResource("67_tm0yg")
toStatus = 1
makeActive = true
[node name="ToolsCollectedTrigger" type="Node" parent="SpeicialQuestTrigger"]
script = ExtResource("68_hux6i")
_itemsToContain = Array[Resource]([SubResource("Resource_y820s"), SubResource("Resource_50loj")])
_onAvailableQuest = ExtResource("68_lbnqo")
_toNextQuest = ExtResource("69_l4wxt")
[node name="FieldWorkTrigger" type="Node" parent="SpeicialQuestTrigger"]
script = ExtResource("74_fv1t2")
_onAvailableQuest = ExtResource("75_l7ekk")
_toNextQuest = ExtResource("76_xcwle")
[node name="StartDialog" type="Node" parent="SpeicialQuestTrigger/FieldWorkTrigger"]
script = ExtResource("77_l7ekk")
timeline = "quest2_tomatoes_end"
[connection signal="FilledWateringCan" from="YSorted/Vesna" to="Audio/SFX/FillWater SFX2" method="PlayOneShot"]
[connection signal="WateringField" from="YSorted/Vesna/FarmingControls" to="Audio/SFX/Watering SFX" method="PlayOneShot"]
[connection signal="InteractedTool" from="YSorted/Brünnen/InteractionArea" to="YSorted/Vesna" method="TryFillWateringCan"]
@ -2367,6 +2415,8 @@ script = ExtResource("40_w3jkj")
[connection signal="DuckCollected" from="YSorted/ducks/Duck7" to="YSorted/ducks" method="Increment"]
[connection signal="Dialogue" from="YSorted/ducks/DialogicToggle" to="YSorted/ducks/dialogic starter" method="open"]
[connection signal="finished" from="Audio/Background Music Ramp up" to="Audio/Background Music loop" method="PlayFromOffset"]
[connection signal="ready" from="SpeicialQuestTrigger/QuestInstantStart" to="SpeicialQuestTrigger/QuestInstantStart/QuestTrigger" method="Trigger"]
[connection signal="OnFulfilled" from="SpeicialQuestTrigger/FieldWorkTrigger" to="SpeicialQuestTrigger/FieldWorkTrigger/StartDialog" method="open"]
[editable path="YSorted/Vesna"]
[editable path="YSorted/Brünnen/InteractionArea"]

@ -2256,12 +2256,6 @@ script = ExtResource("59_0knno")
[connection signal="FieldCreated" from="YSorted/Farm visuals/FieldParent" to="Audio/SFX/Farming SFX" method="PlayOneShot"]
[connection signal="input_event" from="YSorted/Farm visuals/FieldParent/Area2D" to="YSorted/Vesna/FarmingControls" method="InputEventPressedOn"]
[connection signal="GoalReached" from="YSorted/ducks" to="YSorted/ducks/DialogicToggle" method="ToggleDialogue"]
[connection signal="DuckCollected" from="YSorted/ducks/Duck2" to="YSorted/ducks" method="Increment"]
[connection signal="DuckCollected" from="YSorted/ducks/Duck3" to="YSorted/ducks" method="Increment"]
[connection signal="DuckCollected" from="YSorted/ducks/Duck4" to="YSorted/ducks" method="Increment"]
[connection signal="DuckCollected" from="YSorted/ducks/Duck5" to="YSorted/ducks" method="Increment"]
[connection signal="DuckCollected" from="YSorted/ducks/Duck6" to="YSorted/ducks" method="Increment"]
[connection signal="DuckCollected" from="YSorted/ducks/Duck7" to="YSorted/ducks" method="Increment"]
[connection signal="Dialogue" from="YSorted/ducks/DialogicToggle" to="YSorted/ducks/dialogic starter" method="open"]
[connection signal="finished" from="Audio/Background Music Ramp up" to="Audio/Background Music loop" method="PlayFromOffset"]

@ -1,4 +1,4 @@
[gd_scene load_steps=70 format=3 uid="uid://bb6r385qvyoba"]
[gd_scene load_steps=72 format=3 uid="uid://bb6r385qvyoba"]
[ext_resource type="Script" uid="uid://cssdu8viimwm6" path="res://scripts/CSharp/Common/SceneTransition.cs" id="1_vl6d5"]
[ext_resource type="Script" uid="uid://bqomwxclsbhd3" path="res://scripts/CSharp/Common/Camera/CameraController.cs" id="3_jrqoq"]
@ -28,7 +28,7 @@
[ext_resource type="PackedScene" uid="uid://hk8ahyp6dgl6" path="res://prefabs/fight/fight_base_scene.tscn" id="27_55b52"]
[ext_resource type="PackedScene" uid="uid://bp64p6y72j71w" path="res://prefabs/fight/fighters/enemy_blob_fighter.tscn" id="27_hfhye"]
[ext_resource type="PackedScene" uid="uid://c25udixd5m6l0" path="res://prefabs/characters/Player2D.tscn" id="29_3jjxs"]
[ext_resource type="PackedScene" path="res://prefabs/characters/Chugar.tscn" id="29_26tkn"]
[ext_resource type="PackedScene" uid="uid://ddpl8cbck7e6s" path="res://prefabs/characters/Chugar.tscn" id="29_26tkn"]
[ext_resource type="PackedScene" uid="uid://cr66tpdr5rma5" path="res://prefabs/fight/fighters/enemy_mavkha_fighter.tscn" id="29_hfhye"]
[ext_resource type="Resource" uid="uid://dlcmqfjvgphqu" path="res://resources/items/rake.tres" id="30_l10vl"]
[ext_resource type="Resource" uid="uid://cndd64batns31" path="res://resources/items/wateringcan.tres" id="31_c2gvt"]
@ -48,7 +48,9 @@
[ext_resource type="Script" uid="uid://clxb3n668oud3" path="res://scripts/CSharp/Common/Audio/AudioDebugger.cs" id="52_x1mmf"]
[ext_resource type="AudioStream" uid="uid://vcftvrpi6c7k" path="res://audio/sfx/Farming/SFX_Harke_03_Solo.wav" id="54_4l7ky"]
[ext_resource type="AudioStream" uid="uid://bxh5m04vdo0sr" path="res://audio/sfx/Farming/SFX_Harke_04_Solo.wav" id="55_dk5xw"]
[ext_resource type="Script" uid="uid://cldtt4atgymm5" path="res://scripts/CSharp/Common/Quest/QuestTrigger.cs" id="55_ub0r7"]
[ext_resource type="Script" uid="uid://cfnrd5k1k0gxw" path="res://scripts/CSharp/Common/AudioPlayer.cs" id="56_bjj0f"]
[ext_resource type="Resource" uid="uid://c3mwhrvk12oml" path="res://resources/quests/demo/9_talk_to_chuga.tres" id="56_q833x"]
[ext_resource type="AudioStream" uid="uid://dapsknn486aee" path="res://audio/sfx/Farming/SFX_WateringPlants_01.wav" id="57_ehh6a"]
[ext_resource type="AudioStream" uid="uid://dnyne8wov50so" path="res://audio/sfx/Farming/SFX_WateringPlants_02.wav" id="58_mfld1"]
[ext_resource type="AudioStream" uid="uid://fsiypqhql67w" path="res://audio/sfx/Farming/SFX_GettingWater_01.wav" id="59_soiyx"]
@ -2064,7 +2066,7 @@ region_rect = Rect2(1483.92, 1280.2, 1139.55, 367.598)
[node name="BorderCollisionBody" type="StaticBody2D" parent="YSorted/ForestVisuals"]
[node name="CollisionPolygon2D" type="CollisionPolygon2D" parent="YSorted/ForestVisuals/BorderCollisionBody"]
polygon = PackedVector2Array(5543, 1787, 8663, 1938, 15008, 1914, 15121, 2882, 15601, 3074, 15636, 3574, 14122, 3569, 12930, 3737, 11502, 3599, 9887, 3658, 7936, 3924, 7712, 2967, 4629, 2917, 3880, 3351, 3891, 3646, 3919, 4843, 7970, 4459, 16532, 4289, 16365, 821, 1765, 1202, 1437, 4559, 3142, 4814, 3154, 4225, 2749, 3323, 2196, 2523, 2379, 1787)
polygon = PackedVector2Array(5543, 1787, 8663, 1938, 15008, 1914, 15121, 2882, 15601, 3074, 15636, 3574, 14122, 3569, 12930, 3737, 11502, 3599, 9887, 3658, 7936, 3924, 7712, 2967, 4629, 2917, 3880, 3351, 3891, 3646, 3919, 4843, 7970, 4459, 16532, 4289, 16365, 821, 1765, 1202, 1437, 4559, 3849, 4849, 3860, 4193, 3304, 4193, 2749, 3323, 2196, 2523, 2379, 1787)
[node name="Blocker" type="Node2D" parent="YSorted"]
@ -2178,6 +2180,14 @@ max_distance = 2e+07
playback_type = 2
script = ExtResource("56_bjj0f")
[node name="SpecialQuestNodes" type="Node" parent="."]
[node name="InstantStartQuest" type="Node" parent="SpecialQuestNodes"]
script = ExtResource("55_ub0r7")
questResource = ExtResource("56_q833x")
toStatus = 1
makeActive = true
[connection signal="body_entered" from="Fight1/FightStarter/TriggerArea" to="Fight1/FightStarter" method="Start"]
[connection signal="FightEnded" from="Fight1/FightBaseScene" to="YSorted/Vesna" method="show"]
[connection signal="FightEnded" from="Fight1/FightBaseScene" to="YSorted/Vesna" method="EnableMovement"]
@ -2194,6 +2204,7 @@ script = ExtResource("56_bjj0f")
[connection signal="FilledWateringCan" from="YSorted/Vesna" to="Audio/SFX/FillWater SFX2" method="PlayOneShot"]
[connection signal="WateringField" from="YSorted/Vesna/FarmingControls" to="Audio/SFX/Watering SFX" method="PlayOneShot"]
[connection signal="finished" from="Audio/Background Music Ramp up" to="Audio/Background Music loop" method="PlayFromOffset"]
[connection signal="ready" from="SpecialQuestNodes/InstantStartQuest" to="SpecialQuestNodes/InstantStartQuest" method="Trigger"]
[editable path="Fight1/FightBaseScene"]
[editable path="Fight2/FightBaseScene"]

@ -22,7 +22,7 @@
[ext_resource type="AudioStream" uid="uid://cohyenfo1rtxh" path="res://audio/sfx/Animals/SFX_Cat_Meow_01.wav" id="16_d7yky"]
[ext_resource type="PackedScene" uid="uid://dfvgp1my5rydh" path="res://prefabs/characters/Yeli.tscn" id="16_dhsxs"]
[ext_resource type="AudioStream" uid="uid://b2cmf5ie7cwka" path="res://audio/sfx/Animals/SFX_Cat_Meow_02.wav" id="17_7a68a"]
[ext_resource type="Script" uid="uid://cvkw4qd2hxksi" path="res://scripts/GdScript/dialogic_toggle.gd" id="17_k0k8c"]
[ext_resource type="Script" path="res://scripts/GdScript/dialogic_toggle.gd" id="17_k0k8c"]
[ext_resource type="AudioStream" uid="uid://cttisejnt2l8f" path="res://audio/sfx/Animals/SFX_Cat_Meow_03.wav" id="18_dhsxs"]
[ext_resource type="Script" uid="uid://bqomwxclsbhd3" path="res://scripts/CSharp/Common/Camera/CameraController.cs" id="18_dw4nn"]
[ext_resource type="AudioStream" uid="uid://cbmagiou0n0t3" path="res://audio/sfx/Animals/SFX_Cat_Meow_04.wav" id="19_k0k8c"]
@ -30,7 +30,7 @@
[ext_resource type="Script" uid="uid://cldtt4atgymm5" path="res://scripts/CSharp/Common/Quest/QuestTrigger.cs" id="21_blyw3"]
[ext_resource type="AudioStream" uid="uid://r2f6xmjvyyjv" path="res://audio/sfx/Animals/SFX_Cat_Purr_01.wav" id="21_ytap8"]
[ext_resource type="Script" uid="uid://cfnrd5k1k0gxw" path="res://scripts/CSharp/Common/AudioPlayer.cs" id="22_tggq2"]
[ext_resource type="Resource" uid="uid://cbpurnewhyefa" path="res://resources/quests/beetRoot.tres" id="22_yd2gv"]
[ext_resource type="Resource" path="res://resources/quests/beetRoot.tres" id="22_yd2gv"]
[ext_resource type="PackedScene" uid="uid://cgjc4wurbgimy" path="res://prefabs/UI/Inventory/Inventory.tscn" id="24_yd2gv"]
[sub_resource type="RectangleShape2D" id="RectangleShape2D_a2ood"]
@ -558,13 +558,12 @@ position = Vector2(-565, 464)
[node name="dialogic_toggle" type="Node2D" parent="Yeli"]
script = ExtResource("17_k0k8c")
metadata/_custom_type_script = "uid://cvkw4qd2hxksi"
[node name="Beetroot Quest trigger" type="Node2D" parent="Yeli"]
script = ExtResource("21_blyw3")
questResource = ExtResource("22_yd2gv")
toStatus = 1
makeCurrent = true
makeActive = true
[node name="Camera2D" type="Camera2D" parent="." node_paths=PackedStringArray("_followNode")]
position = Vector2(-1534, -26)

@ -1,8 +1,10 @@
[gd_scene load_steps=11 format=3 uid="uid://ceaa2qj2bmw43"]
[gd_scene load_steps=13 format=3 uid="uid://ceaa2qj2bmw43"]
[ext_resource type="Script" uid="uid://cssdu8viimwm6" path="res://scripts/CSharp/Common/SceneTransition.cs" id="1_c6eln"]
[ext_resource type="Texture2D" uid="uid://cugtxcfuds31r" path="res://art/indoor/Babushka_bg_01.png" id="2_j25a2"]
[ext_resource type="Script" uid="uid://cldtt4atgymm5" path="res://scripts/CSharp/Common/Quest/QuestTrigger.cs" id="8_j25a2"]
[ext_resource type="PackedScene" uid="uid://cqc72e4hq6bcd" path="res://prefabs/interactions/interaction_area_2d.tscn" id="8_phqdf"]
[ext_resource type="Resource" uid="uid://csj15gnlx1jmx" path="res://resources/quests/demo/8_goto_bed.tres" id="9_heyef"]
[ext_resource type="Texture2D" uid="uid://cop1vjvhwlsec" path="res://art/indoor/room export/Room_01_shelf.png" id="13_11fdt"]
[ext_resource type="PackedScene" uid="uid://c25udixd5m6l0" path="res://prefabs/characters/Player2D.tscn" id="18_3gevq"]
[ext_resource type="Script" uid="uid://bqomwxclsbhd3" path="res://scripts/CSharp/Common/Camera/CameraController.cs" id="23_408bg"]
@ -100,6 +102,11 @@ _useOutline = false
_useSprite = false
_id = 1
[node name="QuestCompleter" type="Node" parent="BedInteraction"]
script = ExtResource("8_j25a2")
questResource = ExtResource("9_heyef")
toStatus = 2
[node name="DoorInteraction" parent="." instance=ExtResource("8_phqdf")]
position = Vector2(777, 201)
_useOutline = false
@ -109,6 +116,7 @@ _id = 0
[node name="CollisionShape3D" parent="DoorInteraction/Area2D" index="0"]
shape = SubResource("CircleShape2D_2spkc")
[connection signal="Interacted" from="BedInteraction" to="BedInteraction/QuestCompleter" method="Trigger"]
[connection signal="InteractedTool" from="BedInteraction" to="." method="LoadSceneAtIndex"]
[connection signal="Interacted" from="DoorInteraction" to="." method="LoadScene"]

@ -6,7 +6,7 @@
[node name="BabushkaSceneStartMenu" type="Node2D"]
script = ExtResource("1_fj2fh")
_sceneNamesToLoad = PackedStringArray("res://scenes/Babushka_scene_disclaimer.tscn")
_sceneNamesToLoad = PackedStringArray("res://scenes/Babushka_scene_farm_outside_2d.tscn")
[node name="CanvasLayer" type="CanvasLayer" parent="."]

@ -2,9 +2,9 @@
[ext_resource type="PackedScene" uid="uid://cqcs80xsgygeb" path="res://prefabs/UI/Book/Book.tscn" id="1_bd7dq"]
[ext_resource type="Script" uid="uid://cg0oqug38c81n" path="res://scripts/CSharp/Common/Quest/QuestTestingScript.cs" id="2_sv6jn"]
[ext_resource type="Resource" uid="uid://0aruj4lm74n6" path="res://resources/quests/test_01.tres" id="3_nhtae"]
[ext_resource type="Resource" uid="uid://be1dmc6d2mxl5" path="res://resources/quests/test_02.tres" id="4_kr4yw"]
[ext_resource type="Resource" uid="uid://tmmnsg1bge2" path="res://resources/quests/test_03.tres" id="5_4cktu"]
[ext_resource type="Resource" uid="uid://0aruj4lm74n6" path="res://resources/quests/test/test_01.tres" id="3_nhtae"]
[ext_resource type="Resource" uid="uid://be1dmc6d2mxl5" path="res://resources/quests/test/test_02.tres" id="4_kr4yw"]
[ext_resource type="Resource" uid="uid://tmmnsg1bge2" path="res://resources/quests/test/test_03.tres" id="5_4cktu"]
[node name="BabushkaTestsBook" type="Node"]

@ -0,0 +1,74 @@
[gd_scene load_steps=5 format=3 uid="uid://baunkb4wwtl32"]
[ext_resource type="Script" uid="uid://cldtt4atgymm5" path="res://scripts/CSharp/Common/Quest/QuestTrigger.cs" id="1_wnfrg"]
[ext_resource type="Resource" uid="uid://0aruj4lm74n6" path="res://resources/quests/test/test_01.tres" id="2_nud5h"]
[ext_resource type="Resource" uid="uid://be1dmc6d2mxl5" path="res://resources/quests/test/test_02.tres" id="3_tb5fn"]
[ext_resource type="Script" uid="uid://d2486x6upmwqq" path="res://scripts/GdScript/dialogic_starter.gd" id="4_6p0xc"]
[node name="BabushkaTestsQuestDialogic" type="Node2D"]
[node name="Button" type="Button" parent="."]
offset_left = 105.0
offset_top = 47.0
offset_right = 423.0
offset_bottom = 185.0
text = "Start Quest 1"
[node name="Node" type="Node" parent="Button"]
script = ExtResource("1_wnfrg")
questResource = ExtResource("2_nud5h")
toStatus = 1
makeActive = true
[node name="Button2" type="Button" parent="."]
offset_left = 460.0
offset_top = 49.0
offset_right = 778.0
offset_bottom = 187.0
text = "End Quest 1"
[node name="Node" type="Node" parent="Button2"]
script = ExtResource("1_wnfrg")
questResource = ExtResource("2_nud5h")
toStatus = 2
[node name="Button3" type="Button" parent="."]
offset_left = 105.0
offset_top = 215.0
offset_right = 423.0
offset_bottom = 353.0
text = "Start Quest 2"
[node name="Node" type="Node" parent="Button3"]
script = ExtResource("1_wnfrg")
questResource = ExtResource("3_tb5fn")
toStatus = 1
makeActive = true
[node name="Button4" type="Button" parent="."]
offset_left = 460.0
offset_top = 217.0
offset_right = 778.0
offset_bottom = 355.0
text = "End Quest 2"
[node name="Node" type="Node" parent="Button4"]
script = ExtResource("1_wnfrg")
questResource = ExtResource("3_tb5fn")
toStatus = 2
[node name="Button5" type="Button" parent="."]
offset_left = 1314.0
offset_top = 67.0
offset_right = 1632.0
offset_bottom = 205.0
text = "Start Dialog"
[node name="Node" type="Node" parent="Button5"]
script = ExtResource("4_6p0xc")
[connection signal="pressed" from="Button" to="Button/Node" method="Trigger"]
[connection signal="pressed" from="Button2" to="Button2/Node" method="Trigger"]
[connection signal="pressed" from="Button3" to="Button3/Node" method="Trigger"]
[connection signal="pressed" from="Button4" to="Button4/Node" method="Trigger"]
[connection signal="pressed" from="Button5" to="Button5/Node" method="open" binds= ["test_1"]]

@ -2,9 +2,9 @@
[ext_resource type="PackedScene" uid="uid://cgjc4wurbgimy" path="res://prefabs/UI/Inventory/Inventory.tscn" id="1_opxcj"]
[ext_resource type="Script" uid="uid://cldtt4atgymm5" path="res://scripts/CSharp/Common/Quest/QuestTrigger.cs" id="3_sx4ix"]
[ext_resource type="Resource" uid="uid://0aruj4lm74n6" path="res://resources/quests/test_01.tres" id="4_qyyck"]
[ext_resource type="Resource" uid="uid://be1dmc6d2mxl5" path="res://resources/quests/test_02.tres" id="5_sokiv"]
[ext_resource type="Resource" uid="uid://tmmnsg1bge2" path="res://resources/quests/test_03.tres" id="6_ajsa7"]
[ext_resource type="Resource" uid="uid://0aruj4lm74n6" path="res://resources/quests/test/test_01.tres" id="4_qyyck"]
[ext_resource type="Resource" uid="uid://be1dmc6d2mxl5" path="res://resources/quests/test/test_02.tres" id="5_sokiv"]
[ext_resource type="Resource" uid="uid://tmmnsg1bge2" path="res://resources/quests/test/test_03.tres" id="6_ajsa7"]
[node name="BabushkaTestsQuests" type="Node2D"]
@ -41,7 +41,7 @@ text = "Active"
script = ExtResource("3_sx4ix")
questResource = ExtResource("4_qyyck")
toStatus = 1
makeCurrent = true
makeActive = true
[node name="Done" type="Button" parent="CanvasLayer2/VBoxContainer/HBoxContainer"]
layout_mode = 2

@ -1,4 +1,3 @@
using System.Threading.Tasks;
using Babushka.scripts.CSharp.Common.Inventory;
using Babushka.scripts.CSharp.Common.Services;
@ -8,58 +7,65 @@ namespace Babushka.scripts.CSharp.Common.CharacterControls;
public partial class PlayerMovement : CharacterBody2D
{
[Export] private float _speed = 1000f;
[Export] private float _speed = 1000f;
private InventoryManager _inventoryManager;
private InventoryManager _inventoryManager;
public override void _Process(double delta)
{
bool anyActionPressed = false;
Vector2 currentVelocity = Vector2.Zero;
public override void _Process(double delta)
{
bool anyActionPressed = false;
Vector2 currentVelocity = Vector2.Zero;
if (!InputService.Instance.InputEnabled)
return;
if (!InputService.Instance.InputEnabled)
return;
bool right = Input.IsActionPressed("move_right");
bool left = Input.IsActionPressed("move_left");
bool up = Input.IsActionPressed("move_up");
bool down = Input.IsActionPressed("move_down");
bool right = Input.IsActionPressed("move_right");
bool left = Input.IsActionPressed("move_left");
bool up = Input.IsActionPressed("move_up");
bool down = Input.IsActionPressed("move_down");
if (up)
{
currentVelocity += new Vector2(0, -_speed);
anyActionPressed = true;
}
if (up)
{
currentVelocity += new Vector2(0, -_speed);
anyActionPressed = true;
}
if (down)
{
currentVelocity += new Vector2(0, _speed);
anyActionPressed = true;
}
if (down)
{
currentVelocity += new Vector2(0, _speed);
anyActionPressed = true;
}
if (right)
{
currentVelocity += new Vector2(_speed, 0);
if (right)
{
currentVelocity += new Vector2(_speed, 0);
anyActionPressed = true;
}
anyActionPressed = true;
}
if (left)
{
currentVelocity += new Vector2(-_speed, 0);
if (left)
{
currentVelocity += new Vector2(-_speed, 0);
anyActionPressed = true;
}
anyActionPressed = true;
}
if (anyActionPressed)
{
if (currentVelocity.X != 0 && currentVelocity.Y != 0)
{
currentVelocity *= 0.7f;
}
if (anyActionPressed)
{
if (currentVelocity.X != 0 && currentVelocity.Y != 0)
{
currentVelocity *= 0.7f;
}
// speed hack
var setting = ProjectSettings.GetSetting("babushka/hacks/speed_hack",-1).AsSingle();
if (setting > 0)
{
currentVelocity *= setting;
}
Velocity = currentVelocity;
MoveAndSlide();
}
}
Velocity = currentVelocity;
MoveAndSlide();
}
}
}

@ -1,3 +1,5 @@
using System;
namespace Babushka.scripts.CSharp.Common.Farming;
/// <summary>
@ -26,6 +28,7 @@ public static class WateringCanState
public delegate void WateringCanDelegate(bool state);
public static event WateringCanDelegate WateringCanActiveStateChanged;
public static event Action? OnWater;
@ -43,7 +46,10 @@ public static class WateringCanState
public static void Water()
{
if(_fillstate > 0)
{
_fillstate--;
OnWater?.Invoke();
Jonathan marked this conversation as resolved
Review

Wofür genau soll diese Action nachher verwendet werden?
Wenn das signalisieren soll, wenn Vesna sich auf einer Watered-Tile befindet (z.B. für Geh-Sounds), dann würde ich dafür vermutlich eher den Fieldservice verwenden.

Wofür genau soll diese Action nachher verwendet werden? Wenn das signalisieren soll, wenn Vesna sich auf einer Watered-Tile befindet (z.B. für Geh-Sounds), dann würde ich dafür vermutlich eher den Fieldservice verwenden.
Review

Das wird immer aufgerufen, wenn etwas gegossen wird. Das ist ne Quick-and-dirty-Lösung, die von QuestBehaviour/DetectFieldWork.cs genutzt wird, um Feldarbeit als abgeschlossen zu erkennen.

Das wird immer aufgerufen, wenn etwas gegossen wird. Das ist ne Quick-and-dirty-Lösung, die von `QuestBehaviour/DetectFieldWork.cs` genutzt wird, um Feldarbeit als abgeschlossen zu erkennen.
}
}
/// <summary>

@ -2,6 +2,7 @@
using System;
using Godot;
using System.Collections.Generic;
using System.Linq;
namespace Babushka.scripts.CSharp.Common.Inventory;
@ -128,4 +129,21 @@ public partial class InventoryInstance : Node
EmitSignal(SignalName.InventoryContentsChanged);
return InventoryActionResult.Success;
}
public int TotalItemsOfBlueprint(ItemResource blueprint)
{
return _slots
.Where(i => !i.IsEmpty() && i.itemInstance!.blueprint == blueprint)
.Sum(i => i.itemInstance!.amount);
}
public bool HasItems(ItemInstance item)
{
return TotalItemsOfBlueprint(item.blueprint) >= item.amount;
}
public bool HasItems(IEnumerable<ItemInstance> items)
{
return items.All(HasItems);
}
}

@ -1,9 +1,13 @@
namespace Babushka.scripts.CSharp.Common.Inventory;
using Godot;
namespace Babushka.scripts.CSharp.Common.Inventory;
public class ItemInstance
// Do not instantiate this resource
// But it has to be a resource because Godot
[GlobalClass]
public partial class ItemInstance: Resource
{
public ItemResource blueprint;
public int amount = 1;
[Export] public ItemResource blueprint;
[Export] public int amount = 1;
public ItemInstance Clone()
{

@ -6,7 +6,7 @@ public partial class TalkingCharacter : Node2D
{
[Export] private AnimatedSprite2D? _sprite;
[Export] private string[] _timelinesToPlay;
[Export] private bool _retriggerSameTimeline = false;
Jonathan marked this conversation as resolved
Review

Für den Anfang okay, aber auf lange Sicht brauchen wir nen automatisierten Mechanismus, der das mit einem Quest- oder Inventarzustand verknüpft und nur dann zur nächsten Timeline übergeht.

Für den Anfang okay, aber auf lange Sicht brauchen wir nen automatisierten Mechanismus, der das mit einem Quest- oder Inventarzustand verknüpft und nur dann zur nächsten Timeline übergeht.
private bool _isTalking = true;
private int _timelineIndex = 0;
@ -32,7 +32,8 @@ public partial class TalkingCharacter : Node2D
_sprite.Animation = "talk";
_isTalking = true;
EmitSignal(SignalName.Talking, _timelinesToPlay[_timelineIndex]);
_timelineIndex++;
if (!_retriggerSameTimeline)
_timelineIndex++;
}
if (_sprite != null)
_sprite.Play();

@ -1,22 +0,0 @@
using Godot;
using System;
using Babushka.scripts.CSharp.Common.Quest;
public partial class PopUpPostIt : Control
{
private Label Text => GetNode<Label>("Text");
private AnimationPlayer Animation => GetNode<AnimationPlayer>("AnimationPlayer");
QuestManager QM => QuestManager.Instance!;
public override void _EnterTree()
{
QM.QuestBecomesActive += NewQuestPostIt;
}
private void NewQuestPostIt(QuestResource questResource)
{
Text.Text = questResource.title;
Animation.Play("NewPostit");
}
}

@ -1,6 +1,6 @@
using Godot;
using System;
using Babushka.scripts.CSharp.Common.Util;
namespace Babushka.scripts.CSharp.Common.Quest;
public partial class QuestDescriptionUi : RichTextLabel
{

@ -24,11 +24,10 @@ public partial class QuestListItemUi : Control
_ => ""
};
UpdateCircled(questResource == QuestManager.Instance.GetFollowQuest());
UpdateCircled(questResource == QuestManager.Instance.GetActiveQuest());
ShowName(name);
TitleButton.Pressed += ClickedTitleButton;
}
private void UpdateCircled(bool value)
{
CircleTexture.Visible = value;

@ -1,42 +1,50 @@
#nullable enable
using Godot;
using System;
using Babushka.scripts.CSharp.Common.Quest;
namespace Babushka.scripts.CSharp.Common.Quest;
public partial class QuestLog : Control
{
[Signal]
public delegate void DetailQuestChangedEventHandler(QuestLog questLog);
[Export]
private Vector2 _closedPos;
[Export] private Vector2 _closedPos;
[Export]
private Vector2 _openedPos;
[Export] private Vector2 _openedPos;
private bool _isClosed = true;
private Tween? _closeOpenTween;
public QuestResource? currentDetailQuest
{
get => QuestManager.Instance!.GetFollowQuest();
get => QuestManager.Instance!.GetActiveQuest();
set
{
QuestManager.Instance!.SetFollowQuest(value); // TODO: fix setup
QuestManager.Instance!.SetActiveQuest(value); // TODO: fix setup
EmitSignalDetailQuestChanged(this);
}
}
public override void _EnterTree()
{
QuestManager.Instance!.QuestsChanged += () => EmitSignalDetailQuestChanged(this);
QuestManager.Instance!.QuestsChanged += OnQuestsChanged;
}
public override void _ExitTree()
{
QuestManager.Instance!.QuestsChanged -= OnQuestsChanged;
}
private void OnQuestsChanged()
{
EmitSignalDetailQuestChanged(this);
}
public override void _Input(InputEvent inputEvent)
{
if (inputEvent.IsActionPressed("ui_inventory_journal_open_close"))
{
if(_closeOpenTween != null)
if (_closeOpenTween != null)
_closeOpenTween.Kill();
_isClosed = !_isClosed;
@ -48,6 +56,4 @@ public partial class QuestLog : Control
.SetTrans(Tween.TransitionType.Cubic);
}
}
//private QuestResource? _currentDetailQuestBacking;
}

@ -11,11 +11,14 @@ public partial class QuestManager : Node
public static QuestManager? Instance { get; private set; }
[Signal]
public delegate void QuestBecomesActiveEventHandler(QuestResource questResource);
public delegate void QuestBecomesAvailableEventHandler(QuestResource questResource);
[Signal]
public delegate void QuestsChangedEventHandler();
[Signal]
public delegate void DialogicActiveQuestEventHandler(string value);
public override void _EnterTree()
{
Instance = this;
@ -23,7 +26,7 @@ public partial class QuestManager : Node
private Godot.Collections.Dictionary<QuestResource, QuestStatus> _questStatus = new();
private QuestResource? _followQuest;
private QuestResource? _activeQuest;
public void ChangeQuestStatus(QuestResource questResource, QuestStatus.Status newStatus)
@ -37,10 +40,11 @@ public partial class QuestManager : Node
value.status = newStatus;
EmitSignalQuestsChanged();
EmitSignalDialogicActiveQuest(_activeQuest?.id ?? "none");
if (newStatus == QuestStatus.Status.Active)
if (newStatus == QuestStatus.Status.Available)
{
EmitSignalQuestBecomesActive(questResource);
EmitSignalQuestBecomesAvailable(questResource);
}
}
@ -49,9 +53,9 @@ public partial class QuestManager : Node
return _questStatus.Where(qs => qs.Value.status != QuestStatus.Status.Hidden);
}
public IEnumerable<QuestPair> GetActiveQuests()
public IEnumerable<QuestPair> GetAvailableQuests()
{
return _questStatus.Where(qs => qs.Value.status == QuestStatus.Status.Active);
return _questStatus.Where(qs => qs.Value.status == QuestStatus.Status.Available);
}
public QuestStatus GetQuestStatus(QuestResource questResource)
{
@ -63,14 +67,15 @@ public partial class QuestManager : Node
return status;
}
public QuestResource? GetFollowQuest()
public QuestResource? GetActiveQuest()
{
return _followQuest;
return _activeQuest;
}
public void SetFollowQuest(QuestResource? questResource)
public void SetActiveQuest(QuestResource? questResource)
{
_followQuest = questResource;
_activeQuest = questResource;
EmitSignalQuestsChanged();
EmitSignalDialogicActiveQuest(_activeQuest?.id ?? "none");
}
}

@ -20,6 +20,7 @@ public partial class QuestMessagePopup : Control
public override void _EnterTree()
{
QuestManager.Instance!.QuestsChanged += NewActiveQuest;
NewActiveQuest();
}
public override void _ExitTree()
@ -29,7 +30,7 @@ public partial class QuestMessagePopup : Control
private void NewActiveQuest()
{
var shownQuest = QuestManager.Instance!.GetFollowQuest();
var shownQuest = QuestManager.Instance!.GetActiveQuest();
if (_currentlyShown == shownQuest)
return;

@ -6,7 +6,7 @@ public partial class QuestResource : Resource
{
[Export]
public string id = "";
[Export]
[Export(PropertyHint.MultilineText)]
public string title = "";
[Export(PropertyHint.MultilineText)]
public string description = "";

@ -6,10 +6,10 @@ public partial class QuestStatus : GodotObject
{
public enum Status
Jonathan marked this conversation as resolved
Review

Was ist mit 'Available' passiert?

Was ist mit 'Available' passiert?
{
Hidden,
Active,
Done,
Canceled,
Hidden = 0,
Available = 1,
Done = 2,
Canceled = 3,
Jonathan marked this conversation as resolved
Review

Typo: Cancelled

Typo: Cancelled
Review

Geht beides. Das eine ist mehr britisch, das andere mehr amerikanisch.

https://www.merriam-webster.com/grammar/canceled-or-cancelled

Geht beides. Das eine ist mehr britisch, das andere mehr amerikanisch. https://www.merriam-webster.com/grammar/canceled-or-cancelled
}
public Status status = Status.Hidden;

@ -1,20 +1,22 @@
using Godot;
using System;
using System.Collections.Generic;
using System.Diagnostics;
using Babushka.scripts.CSharp.Common.Quest;
using Godot.Collections;
public partial class QuestTestingScript : Node
{
[Export(PropertyHint.ArrayType)]
private Array<QuestResource> _questsToActivate;
private Array<QuestResource>? _questsToMakeAvailable;
public override void _EnterTree()
{
foreach (var questResource in _questsToActivate)
Debug.Assert(_questsToMakeAvailable != null);
foreach (var questResource in _questsToMakeAvailable)
{
QuestManager.Instance.ChangeQuestStatus(questResource, QuestStatus.Status.Active);
QuestManager.Instance!.ChangeQuestStatus(questResource, QuestStatus.Status.Available);
}
}
}

@ -4,30 +4,28 @@ using Babushka.scripts.CSharp.Common.Quest;
public partial class QuestTrigger : Node
{
[Export]
public QuestResource? questResource;
[Export] public QuestResource? questResource;
[Export]
public QuestStatus.Status toStatus;
[Export] public QuestStatus.Status toStatus;
[Export]
private bool makeCurrent = false;
[Export] private bool makeActive = false;
public void Trigger()
{
GD.Print("trigger");
if(questResource== null)
if (questResource == null)
throw new Exception("QuestResource is not set on QuestTrigger node.");
if(QuestManager.Instance == null)
throw new Exception("QuestManager instance is not available. Make sure it is initialized before calling Trigger.");
if (QuestManager.Instance == null)
throw new Exception(
"QuestManager instance is not available. Make sure it is initialized before calling Trigger.");
QuestManager.Instance.ChangeQuestStatus(questResource, toStatus);
if (makeCurrent)
if (makeActive)
{
QuestManager.Instance.SetFollowQuest(questResource);
QuestManager.Instance.SetActiveQuest(questResource);
}
}
}

@ -0,0 +1,37 @@
using Godot;
using System;
using Babushka.scripts.CSharp.Common.Farming;
using Babushka.scripts.CSharp.Common.Quest;
public partial class DetectFieldWork : QuestFulfillmentBase
{
private int wateredCounter = 0;
[Export] private int _wateringNeeded = 5;
public override void _EnterTree()
{
WateringCanState.OnWater += CountWater;
QuestManager.Instance!.QuestsChanged += CheckFieldWork;
}
public override void _ExitTree()
{
WateringCanState.OnWater -= CountWater;
QuestManager.Instance!.QuestsChanged -= CheckFieldWork;
}
public void CountWater()
{
wateredCounter++;
CheckFieldWork();
}
public void CheckFieldWork()
{
if (IsQuestActive() && wateredCounter >= _wateringNeeded)
{
Fulfill();
}
}
}

@ -0,0 +1,33 @@
using Godot;
using System;
using System.Collections.Generic;
using System.Linq;
using Babushka.scripts.CSharp.Common.Inventory;
using Babushka.scripts.CSharp.Common.Quest;
public partial class DetectInventoryContains : QuestFulfillmentBase
{
[Export(PropertyHint.ArrayType)] private ItemInstance[] _itemsToContain = null!;
public override void _Ready()
{
QuestManager.Instance!.QuestsChanged += CheckInventory;
InventoryManager.Instance.playerInventory.InventoryContentsChanged += CheckInventory;
CheckInventory();
}
public override void _ExitTree()
{
QuestManager.Instance!.QuestsChanged -= CheckInventory;
InventoryManager.Instance.playerInventory.InventoryContentsChanged -= CheckInventory;
}
private void CheckInventory()
{
if (IsQuestActive() && InventoryManager.Instance.playerInventory.HasItems(_itemsToContain))
{
Fulfill();
}
}
}

@ -0,0 +1,45 @@
using Godot;
using System;
using System.Linq;
using Babushka.scripts.CSharp.Common.Quest;
/// <summary>
/// Acts as a base for scripts to check for conditions to complete quests.
///
/// The derived Class is responsible for triggering the Check.
/// It is recommended to always check on QuestManager.Instance!.QuestsChanged
/// </summary>
public abstract partial class QuestFulfillmentBase : Node
{
[Export] private QuestResource _onAvailableQuest = null!;
[Export] private QuestResource _toNextQuest = null!;
[Export] private bool _whenFulfilledSetAvailableQuestToDone = true;
[Export] private bool _whenFulfilledSetNextQuestToAvailable = true;
[Export] private bool _whenFulfilledSetNextQuestToActive = true;
Jonathan marked this conversation as resolved
Review

Hatten wir uns nicht auf ein anderes Wording geeinigt oder hat es einen Grund, warum es jetzt wieder 'Active' und 'Follow' heißt?

Hatten wir uns nicht auf ein anderes Wording geeinigt oder hat es einen Grund, warum es jetzt wieder 'Active' und 'Follow' heißt?
[Signal] private delegate void OnFulfilledEventHandler();
protected void Fulfill()
{
if (_whenFulfilledSetAvailableQuestToDone)
{
QuestManager.Instance!.ChangeQuestStatus(_onAvailableQuest, QuestStatus.Status.Done);
}
if (_whenFulfilledSetNextQuestToAvailable)
{
QuestManager.Instance!.ChangeQuestStatus(_toNextQuest, QuestStatus.Status.Available);
}
if (_whenFulfilledSetNextQuestToActive)
{
QuestManager.Instance!.SetActiveQuest(_toNextQuest);
}
EmitSignalOnFulfilled();
}
protected bool IsQuestActive()
{
return QuestManager.Instance!.GetAvailableQuests().Any(q => q.Key == _onAvailableQuest);
}
}

@ -17,7 +17,7 @@ public partial class SceneTransition : Node
public void LoadSceneAtIndex(int index)
{
string sceneName = _sceneNamesToLoad[index];
SceneTransitionThreaded.Instance.ChangeSceneToFileThreaded(sceneName);
SceneTransitionThreaded.Instance.ChangeSceneToFile(sceneName);
UnloadAfterDelay();
}

@ -0,0 +1,7 @@
extends Node
class_name DialogicStartSpecific
Jonathan marked this conversation as resolved
Review

Ich finde das naming hier nicht ganz passend:

  • DialogicStartSpecific ist ironischerweise etwas unspezifisch, weil ich daraus nicht unbedingt ableiten kann, inwiefern es sich vom DialogicStarter unterscheidet. Letzterer spielt ja auch eine spezifische timeline ab, nur eben als Parameter.
  • Ich glaube, ich würde den code einfach mit in den vorhandenen DialogicStarter hinzufügen.
  • Ich habe jetzt mehrere Minuten lang geglaubt, dass diese Klasse zu Beginn einer Szene automatisch die Timeline starten würde, weil du die Funktion Start genannt hast. Bitte keine Standardfunktionsnamen aus Unity verwenden, weil das super verwirrend ist.
Ich finde das naming hier nicht ganz passend: - `DialogicStartSpecific` ist ironischerweise etwas unspezifisch, weil ich daraus nicht unbedingt ableiten kann, inwiefern es sich vom `DialogicStarter` unterscheidet. Letzterer spielt ja auch eine spezifische timeline ab, nur eben als Parameter. - Ich glaube, ich würde den code einfach mit in den vorhandenen DialogicStarter hinzufügen. - Ich habe jetzt mehrere Minuten lang geglaubt, dass diese Klasse zu Beginn einer Szene automatisch die Timeline starten würde, weil du die Funktion `Start` genannt hast. Bitte keine Standardfunktionsnamen aus Unity verwenden, weil das super verwirrend ist.
Review

Genau das ist der Unterschied: DialogicStarter startet irgendeinen Dialog, den man als Parameter mitgeben kann. Und DialogicStartSpecific startet einen spezifischen Dialog, der schon vorher festgelegt werden muss.

Ich habe dir zuliebe die Funktion aber umbenannt.

Genau das ist der Unterschied: `DialogicStarter` startet irgendeinen Dialog, den man als Parameter mitgeben kann. Und `DialogicStartSpecific` startet einen spezifischen Dialog, der schon vorher festgelegt werden muss. Ich habe dir zuliebe die Funktion aber umbenannt.
@export var timeline : String
func open():
Dialogic.start(timeline)

@ -0,0 +1,4 @@
extends Node
func _SetActiveQuestVar(value:String):
Dialogic.VAR.ACTIVEQUEST = value
Loading…
Cancel
Save