-
-
Notifications
You must be signed in to change notification settings - Fork 21.6k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Allow namespace for cleaner class names #21215
Comments
Just to be sure, you're talking about the new Because otherwise if you don't register your class names as global, you can keep all minigames self-contained with one game never having to know about the other game's internal classes. |
Yes, I am talking about the new class_name feature. Imagine a game composed of several minigames. The current options at the moment is to end up with either horribly long paths(If you want your folders to be nicely organized) or horribly long classnames. I know Godot was meant to work with paths, but if you work with paths and move something, you risk high breakage in your project that you can't really discover until you either grep for the old filename or run every single script. Not sure how it works when it comes to refactoring classnames. Nothing that can't be worked around, but it would be nice for me to have a solid system, the current one feels very fragile. |
I would also be interested on @vnen opinion's on this |
This is also even more relevant when you make a plugin that contains |
I was expecting someone to ask about it. I'm not against it but there are a few considerations. For instance, I assume people expect a sort of |
For this, class_name could add |
@eon-s +1 for going the pythonic way I was testing out the new class_name features today and it just felt odd, that now we have this wonderful class_name which allow extending, but I still have to do a "preload" into a constant to use it in any other script. Seems that an import statement would be much cleaner. # animal.gd
extends Reference
class_name Animal
func speak():
return "(silent)"
func name():
return "animal"
# lion.gd
extends Animal
func name():
return "lion"
func speak():
return "roar"
# test.gd
extends Node
# today we have to do this
const Animal = preload("./animal.gd")
const Lion = preload("./lion.gd")
# in the future it would be nice to be able to
import Animal
import Lion
func _speak(animal):
if animal is Animal:
print("the %d year old '%s', says '%s'" % [animal.age, animal.name, animal.speak() ])
func _ready():
var animal = Animal.new()
var lion = Lion.new()
_speak(animal)
_speak(lion)``` |
@paulhocker open a new issue for that (but search first, I think that was mentioned somewhere else), I remember having tested with static functions and these do worked with the class name. |
Technically, all you have to do to define a "namespace" is make another script class that references the other scripts as constants. So, you can already do this kind of thing out-of-the-box. It's just that there is manual work involved in creating the namespace through another script.
Right now, creating that intermediate script is done manually, and to put multiple classes in it, you have to create the scripts and then update the information in the namespace script. On the other hand, it would be more convenient if you could just namespace the type directly into the
@vnen what do you think of this idea? You seem to know the most about Godot's scripting API / script class plans over time. |
@willnationsdev aren't globally named classes a Godot feature? It's used to register in dialogs or other systems and allows to specify an icon). Since it is, C# might as well need such namespacing, even if language-wise it sounds more like a redundant burden. |
Yes, this is the "script class" system.
Well, as for accessing things by name, I am suggesting that if, say, GDScript had MyNamespace.MyClass, then we would...
Now C# has a global, namespaced access point. As for providing a namespaced name for C# types, we can program them to already do that on the backend because they are already aware of their context. Don't have to explicitly give them any kind of name. Adding a ScriptClass class attribute would be enough.
That would already exist:
Unless we also needed people to be able to "import" multiple types from MyNamespace all at once (a valid concern).
This is already what I am planning on doing. |
That's back to square one^^ I mean, being able to actually scope class name lookup by saying "I am within this namespace" at the beginning of the script, so that such |
This is the main reason why I haven't bothered with namespaces so far. Need some time to design a proper way to use it. I expect users to be able to get inside the namespace scope for the whole script, or for the rest of block, so this needs some way to do it (while it might seem trivial, there are always some edge cases hiding in the corners that we have to take in account). I also want it to be simple to use. Another point is whether or not to allow Implementation is just a detail after all questions are answered. Though I don't really like creating empty scripts just to provide namespace functionality. What if the user has their own script with the same name? The system will find a script there (since there is one) but will be empty and without the methods defined by the user, generating cryptic error messages. I think a system like this should be done properly. Probably have to change ScriptServer and how classes are stored in ProjectSettings. Well, I could simply allow (I just realized I commented on this before. I even forgot about ambiguity, which is also an issue. My concerns are the same, I just never had time to think them through). |
That's fair, but it's more of a GDScript-specific concern that shouldn't impact us being able to design/figure out the backend support in the meantime. Once we have a backend implementation in place, it will be easier to create a GDScript Issue that discusses more concrete front-end design and implementation for hooking up with the backend.
This is the crux of the backend issue. The way the data is represented has an effect on how easy it is to navigate the data. Our options, as I see it, are as follows:
Out of these options, I'm actually starting to like that last one the most.
If a user created a script that shared a name with a namespace, then the ScriptServer would need to confirm that the given script and the namespace both define the same set of access points to other namespaces / named types. And if not, then the namespace would still be used and the script would fail to load / give an error. The error would say something along the lines of "does not define requisite classes registered elsewhere," (and then the ScriptEditor can list those FQCNs/filepaths so that users can find/fix them). Only when all the requisites are satisfied would the script load successfully and replace the namespace object. You would probably have to do a secondary sweep over the script classes to validate that information. After all, you cannot know the full set of requisite classes until all script classes have been defined. That is also the time, though, that we would already need to be doing a secondary parsing process to figure out where our holes are, for the sake of generating the namespace objects. If you don't support allowing users to define scripts that replace namespaces, then I think you stand to get a lot of confusion and negative feedback since the manual process fully supports that (as described), so the automated process should also support that. If you have another idea on how to implement the backend's data structure in the ScriptServer/languages, I'd be happy to hear your ideas. |
I think the discussion can continue in godotengine/godot-proposals#1566. All feature and improvement proposals for the Godot Engine are now being discussed and reviewed in the dedicated Godot Improvement Proposals (GIP) (godotengine/godot-proposals) issue tracker. The GIP tracker has a detailed issue template designed so that proposals include all the relevant information to start a productive discussion and help the community assess the validity of the proposal for the engine. The main (godotengine/godot) tracker is now solely dedicated to bug reports and Pull Requests, enabling contributors to have a better focus on bug fixing work. Therefore, all feature proposals on the main issue tracker are being closed. |
Closing per @Xrayez's comment. |
Godot version: 3.1 custom
Issue description:
When making a game with multiple minigames, using class names becomes impossible: you need to use Objective-c style horribly long names for your classes because every classname is global.
Proposal:
Allow namespaces (nestable would be the best).
I imagine them to look like this:
The text was updated successfully, but these errors were encountered: