Open willnationsdev opened 5 years ago
I really like graph databases and feel that one could work well as the backend to support this proposed system. However, I would not push for Cypher as the query language. Rather, I would adopt an API similar to the NetworkX Python library. Such an API could conform more easily to GDScript and various gdnative implementations without introducing another language.
@clayheaton I'll look into it (haven't worked much with Python at all). Thanks for the feedback!
cc @xDGameStudios
'godot-journey' also shoud implements global variables in like my RakugoVars:
[]
(Ren'Py like markup) or {}
(bbcode)int
,float
, Dictionary
, Array
, String
Character
, Subquest
, Quest
@jebedaia360
'godot-journey' also shoud implements global variables in like my RakugoVars:
I would like to provide an avenue for storing information related to the story, but I would like to explicitly define an optimal API that allows for namespacing the information and allow users to dictate how their tools interact with the API. Perhaps we can make it a global object, but just use slash-delimiters in the property names, the same way that Godot does things for its global ProjectSettings and EditorSettings objects. For example, the Core might see a variable as "thing1/thing2/thing3/property" whereas a scripting language might do something like [thing1.thing2.thing3.property]
, etc. What the public-facing interface does would be completely implementation-specific. So, Rakugo, for example, might only deal with global variables, or you might choose to modify the parsed string before passing it along to the low-level API, etc.
On the other hand, I would really like to offer people the opportunity to have Intellisense support on the stored data. This would mean using a Dictionary
or underlying HashMap<StringName, Variant>
to track the properties at each stage so that you can easily ask, "okay, what are the keys at this stage?" Either that, or you keep the properties (which provide much faster runtime access since it's only one .get()
operation), but then you maintain a Dictionary cache of each subgroups options, maybe with toggling on that feature only at editor-time or something.
You can put them in to text using [](Ren'Py like markup) or {}(bbcode)
As mentioned above, I anticipate other APIs having their own specific way of passing information to the Core.
They emit right singnal when value of it or it part is changed
I'm toying around with the idea of having a signal that fires every time a property is updated and then also potentially having a procedurally-generated GDScript that reloads at runtime as the story state expands with new variables and it would generate a property_changed_<name>(old_value, new_value)
signal. Then, once users define that the variable exists, then they would be able to connect to a signal with a custom name for it. This would be a way for objects to track changes to an individual property as opposed to having every object receive a callback when any property is updated.
func _ready():
Core.connect("property_changed_dogs_owned", self, "_on_property_changed_dogs_owned")
func _on_property_changed_dogs_owned(old_value: int, new_value: int) -> void:
pass # update GUI
Then the dialogue runtime, also driven by Core, can actually update the variable and suddenly the GUI updates.
They are wapers for: int,float, Dictionary, Array, String
Is there a reason that you only use these wrappers? You can just as easily do str2var(value)
to interpret the text and convert it into a Godot runtime value, correct? I believe Godot already has tools for this kind of thing. Godot 3.1 also introduced a new Expression object which can help evaluate expressions, even in the context of an object instance's member variables, etc.
They are Rakugo's:Character, Subquest, Quest
This is where we might have custom serialized queries for the story database for data pertaining to certain Labels, and you might have classes that wrap these query objects to provide a user-friendly interface for accessing the data.
Personally, I would like to implement a Composite pattern approach to any quest or task system. Whether a task is considered to be a project, a goal, an objective, a task, a quest, a subquest, whatever. There is still a finite set of states it can be in, there are conditions upon which it may be considered complete, whether it is complete or not may, or may not, be reversible, and there are things that might happen when it does complete (or fail, whatever the case may be).
I plan to create a single structure in the database that can handle all of these, and then we'll use unidirectional relationships between the nodes to form the hierarchical tree structure that the nodes have. But I don't want to assign arbitrary organizational structures to the templated nodes for the system. If the application chooses to assign additional Labels to the nodes to form certain super-hierarchies, that would be application-dependent.
When and what we do first for it?
Well, the first step is creating the low-level StoryGraph data structure. The fastest and most efficient way to do that is to incorporate a third-party library that already has a fast and powerful API with a variety of built-in algorithms for handling the graph structure (searching in various ways, etc.). Once we've ironed out all of the details and come up with an implementation that meets our criteria, THEN we can store creating the Events, Timelines, and ultimately start on the Core implementation which manages the story graph.
Also, while Git / VCS isn't a necessary part of this project, it would make sense to work on that if someone else who is highly motivated wants to jump in and try to build a generic VCS interface that can work through making libgit2 C++ compatible with that base API.
Edit: I'm thinking of integrating the LEMON C++ tree/graph library as a GDNativeLibrary and then putting it into a subsection of godot-next/references/data_structures
or something, so that individual C++ data structures (like MinHeap and SplayTree to name a few) can be expanded there.
I think that my descriptio of RakugoVar was bad here is RakugoDict to show my idea more clear: https://github.com/jebedaia360/Rakugo/blob/resource-saver/addons/Rakugo/types/rakugo_dict.gd
You might be interested in this one: https://grakn.ai/
For those wondering about the status of this repository, the main roadblock is that I would prefer for there to be a better standard of addon structure and development workflow with regard to addons that make use GDNative libraries. For that, Godot needs integrated support for compiling GDNative libraries with built-in support for compiling C++ specifically as a first-party language (since it's an industry standard).
This means that not only does Godot need resources and tools for building C++ (similar to an IDE), but the Godot Asset Library and Godot community need support and consensus, respectively, on how to organize addons that use C++ source code, dynamic libraries, and any other manner of GDNative codebases.
I would prefer to resume work on this after such features are done because, otherwise, I will need to maintain an unstable and potentially shifting standard on such things. In addition, the workflow of using this addon would not be very user-friendly without such tools being provided by Godot itself. Since the entire purpose of the tool is to provide a great user experience for each of the tasks, I feel that investing in improving the Godot ecosystem before diving into this further is the best use of my time.
The necessary changes are largely summarized by godotengine/godot-proposals#119 for anyone who is interested in tackling the issue themselves. My main Godot task at the moment is resolving some other issues related to script classes.
Come chat about the project on the Godot Extended Libraries Discord!
Sources
The ideas that follow stem from a desire to emulate and synchronize features from the following applications into a single, cohesive Godot plugin that may also involve git submodules for the integration of project-specific views, editors, and APIs:
API Suggestions
Okay, so that was a lot of stuff. What parts of this am I actually suggesting we build into a Godot project? We'll get into it below.
The names of things aren't specific. They're just so that I can refer to them during the course of the proposal.
These are merely idealized concepts / speculated implementations. It's not necessarily true that these are required, but each piece works with the other pieces, so the more you strip away from this API, the less the pieces are able to work together, so they consequently give less benefit. The API is also constructed as it is for maximum performance benefits and re-usability of concepts throughout Godot Engine's codebase.
I have specifically outlined each concept under a single numbered list so that we can reference individual points using their numeric identifiers.
Facade
Singleton
must exist which tracks all story information related to a Godot project.MATCH (item:MAGICAL:ITEM)-[:LOCATED_IN]->(:PLACE)<-[:VISITED]-(:PROTAGONIST {first_name:"John"}) RETURN item;
git
. StoryGraphs are Repositories. Timelines are Branches. Events are Commits. StoryItems/Relationships are Files. We should be able attach commit messages, merge and rebase events, diff Timelines, reset to alternate Timeline points, branch off into alternate Timelines, etc.Universe
which tracks a statically-defined universe of content.This is what I envision for
godot-journey
. It would serve as a basis for any and all future story management plugins as other plugins would merely create a particular visualization - like Rakugo's Phone Mode, or interface - like Rakugo's GDScript API or future RakugoScript, etc. and add to the available ways of interacting with the Core.