Zylann / godot_heightmap_plugin

HeightMap terrain for Godot implemented in GDScript
Other
1.73k stars 159 forks source link

Intermittent `No loader found` error #427

Open Tshmofen opened 7 months ago

Tshmofen commented 7 months ago

Describe the bug Sometimes on project start data.hterrain just fails to load, thus the terrain itself doesn't appear and all physics bodies just fall through.

Not sure what exactly might be causing it. It happens in 90% of times I build the project (.NET) and very rarely on usual start. Second immediate start is always fixes the issue and all the data gets loaded correctly.

It might be a problem on my side, but have no idea what might be wrong... Maybe Godot for some reason locks the files after build? (but it wouldn't explain rare random fails with usual starts). I also do not reference terrain data in any way in my project, so nothing should be interfering concurrently with plugin (and it wouldn't be connected to build process anyway). It will be very appreciated if someone proposes any ideas on how to fix that.

It's not much of problem for now as I can always just restart the scene, but it's a little annoying; and might become a real problem if it might happen on any release builds.

To Reproduce No reliable way to reproduce, unfortunately.

Expected behavior Every time I build & start the project terrain should be loading just fine.

Screenshots image

Environment OS: Windows 11 Pro 23H2 Graphics card: 1070 TI Godot version: 4.2.1 .NET Plugin version: 1.7.2 Renderer used: Forward+

Zylann commented 7 months ago

All I can say is that this is somehow a Godot bug. The terrain uses a custom loader here: https://github.com/Zylann/godot_heightmap_plugin/blob/master/addons/zylann.hterrain/hterrain_resource_loader.gd "no loader found" is a Godot error... as in, no code from that plugin even has a chance to run, it's like Godot is litterally not calling that code and fails earlier for unexplained reasons.

There seems to have been weird heisenbugs with custom savers and loaders for a very long time (notably saving). I suspect all the changes that have been done to GDScript over the years have somehow broken it in very unintuitive ways and nobody has looked into it. I could never do that either because these issues just never reproduced on my end...

Btw I find it extremely weird that on your screenshot Godot goes through NativeCalls.cs, a C# file, and somehow ends up printing an error about failing to load splat.png, which is terrain data file while this plugin is written in GDScript. (that doesn't mean you can't use C# with a GDScript plugin, but I'm curious why C# gets involved here)

Tshmofen commented 7 months ago

I see, thanks. Thought you may have any ideas or already saw something similar. Terrain saving and in-editor behavior is all working just fine for me, never had any issues there, only that strange project build/start bug.

Looks like I will have to inspect the original C++ eventually if want to find out the cause 🙂 I will update the issue if I get any mood to do a deep dive in Godot sources and get to find the source of the issue.

Oh, splat.png is on my side, I'm loading it separately (in C#) to determine the textures used on different parts of the terrain and map them to correct steps sounds. But this problem was present before I've added this system. Though, now it looks like the whole data directory is not accessible at this point, strange

Zylann commented 7 months ago

And is the data directory actually present? Like, its contents have not been erased or anything?

Tshmofen commented 7 months ago

I mean not accessible when that issue happens. The directory is obviously always here as I'm able to load the project correctly with restart later

Tshmofen commented 7 months ago

Just had a thought. Could it be connected to a plugin saving the data on a scene save? When Godot starting/building the project it's always saving the opened scenes; maybe sometimes it doesn't do it fast enough and just started in-game plugin fails to load because the files are still being written to? Maybe you have any functionality connected to that save scene logic?

Zylann commented 7 months ago

The thing is, you would expect any saving to be completed before Godot starts the game... so there shouldn't be file locking issues (but I don't know for sure if Godot actually respects that). The only known issue you might encounter is that if you made unsaved changes and play, Godot won't re-import the saved PNGs until you unfocus/refocus the editor so in the worst case you might just see a slightly out-of-date terrain. But flat-out being unable to load even a PNG from this folder is unexpected and I don't know what could be done to figure out what's really happening.

Maybe as a test, try to comment out all the code in the saver to prevent those files to be eventually written to, to check if it's some weird permissions issue (and restart the editor to make sure the plugin reloads properly), but again if that's the cause, that would mean Godot is wrongly starting the game too early which the plugin can't possibly workaround.

Tshmofen commented 7 months ago

Can't test right now, maybe will do it tomorrow. I will let you know in this thread if I happen to found out anything. Thanks a lot

Tshmofen commented 6 months ago

Ok, I found out the culprit. For some reason Godot sometimes doesn't register yours hterrain_resource_loader.gd after rebuild and nobody can handle *.hterrain resource type in that case, thus terrain doesn't appear.

Previous part is understandable, but it's strange that separately after that my another C# script cannot load the splat.png. It is throwing error 7, which is according to those Godot headers is ERR_FILE_NOT_FOUND. I'm using Godot library to load this file, so something goes wrong inside, because I tried to locate the files with .NET internal library just before it gets accessed by Godot and it seems fine / existing.

Oh, yes, and it is definitely not saving-lock issue, commented your saver to just return Ok without saving, but it have not prevented the issue in any way.

Yea, crazy stuff... :)