Closed i-void closed 3 years ago
I've experienced this as well. After removing them all and replacing with MeshInstance planes, FPS returned to normal.
I've noticed this also on 3.1, quite bad fps on 2 android devices I tried (GLES2) with just a couple of sprite3d's. If I use the builtin quadmesh instead to display my texture the fps is perfectly fine.
Same here, I had to get rid of them, and now I know what to use in replacement. I've taken a bit of my time to make a sample project, that, if you run on pc, it doesn't make a huge difference, but as you export to a mobile you can see the incredible difference. On my MYA-L11 I can run at 50+fps more than a hundred plane meshes (that is not that much, but in comparison), while it can't stay above 10fps with barely 10 Sprite3D. Sprite3D_Mobile_Test.zip
I think this is indeed a quite old issue: https://github.com/godotengine/godot/issues/2096 And afaik also ImmediateGeometry displays similar, hum... symptoms.
I'm not sure, but, if the class has the _draw method, that means it overrides it right? Might be there the problem? As I can't debug (and I know very little about C++) I can't tell for sure, but can it be that it's doing too many things at every frame? Like checking properties, calculating frame offset, and more: https://github.com/godotengine/godot/blob/24e1039eb6fe32115e8d1a62a84965e9be19a2ed/scene/3d/sprite_3d.cpp#L397-L526
ImmediateGeometry isn't intended to manage large amounts of geometry, so it should probably be replaced to use some other kind of mesh generation (like ArrayMesh?).
ImmediateGeometry isn't intended to manage large amounts of geometry, so it should probably be replaced to use some other kind of mesh generation (like ArrayMesh?).
Yeah I am referring to a few lines drawn (I was reusing part of the navmesh code for my game, and let the path as it was, found out it was slowing down a lot on mobile). But, never mind, I'll open a new issue or add to existing ones as I have time to make another test/benchmark project.
I am also getting hit by this / #31023 in my WOLF3D project. As a workaround, I am looking into replacing all my Sprite3Ds with MeshInstances of a QuadMesh. Sure would be nice if Sprite3D was actually fixed though
I'm also having this issue. They almost should put a disclaimer on the sprit3d node. Now I'm going through ~20+ nodes and changing them to meshes. It would be REALLY nice to have a feature like the 2d sprite where you can convert it to a mesh2D with just a click.
Does Sprite3D need a refactor? Surely an object that simple should not be so slow to render.
@semirix it should probably just be removed and made into a thin shell for a billboarded quad.
@clayjohn What about AnimatedSprite3D? It's surely possible to emulate its functionality using a MeshInstance + QuadMesh, but it sounds tedious to set up.
Yeah... as someone working on a mixed 2D and 3D game I really want that sprite functionality.
I can only draw about 100 Sprite3D before i drop below 100fps, but i can draw almost 1000 QuadMesh.
For anyone trying to work around this by using an AtlasTexture
on a MeshInstance
material, here's a shader and script that might help: https://gist.github.com/t-mw/0b78167372ed97e7c78e3f3844f3ae75.
I started looking at this as well but my knowledge of rendering isn't to the point where I can be much help. Is this currently using immediate geometry to create quads on which the frames are drawn? Seems like the goal would be to put a SpriteFrames resource in 3d space which looks like would somehow need to inherit from a visual instance.
Seems like ios (ipad mini 2) handles lighting, normal maps and sprite3d objects much better in its pipeline where as even a couple sprite3d objects on galaxy s7 causes huge fps drops.
I feel this is pretty huge even for 2d games where you see games like hollow knight leveraging 3d for parallax effects. Also anything mixed mode like using meshes instead of sprites for character skins / items.
Another workaround I've used is to create an animated texture resource in a spreadsheet for parsing and import it into the engine. It has a max of 256 frames and very limited control but works for basic playback.
Really hoping this gets cherry picked for the 4.0 release.
Is this currently using immediate geometry to create quads on which the frames are drawn? Seems like the goal would be to put a SpriteFrames resource in 3d space which looks like would somehow need to inherit from a visual instance.
Yes. We should probably use ArrayMesh instead of relying on ImmediateGeometry. I don't know how difficult it would be; maybe it's actually really easy. I don't know if anyone actually attempted to rework it to use ArrayMesh :slightly_smiling_face:
Seems like ios (ipad mini 2) handles lighting, normal maps and sprite3d objects much better in its pipeline where as even a couple sprite3d objects on galaxy s7 causes huge fps drops.
iOS devices have better performance and better GLES3 support across the board, so that makes sense.
I feel this is pretty huge even for 2d games where you see games like hollow knight leveraging 3d for parallax effects.
Godot supports pseudo "3D in 2D" since 3.2, without having to rely on the 3D engine for this.
Really hoping this gets cherry picked for the 4.0 release.
It's the other way around :wink: Pull requests in the master
branch get cherry-picked to the 3.2
branch if they're backwards-compatible.
I'm going to just replace the backend of the Sprite3D with a proper mesh instead of using ImmediateGeometry.
PR is up now! Please test it if you are having performance issues with Sprite3D!
Fixed by #39867 in the 3.2
branch.
It's not fixed in master
yet though, so keeping this issue open. A different fix will be used there.
This has already been fixed, hasn't it? Can we close it?
See my comment above yours: https://github.com/godotengine/godot/issues/20855#issuecomment-654278054
See my comment above yours: #20855 (comment)
Sorry, I thought it was a hanging comment. I didn't realize master
is 4.0.
This was resolved for master
by https://github.com/godotengine/godot/pull/50014, closing.
To confirm this, I benchmarked 3.x
against master
to compare the current rendering performance of 900 Sprite3Ds in a blank scene (no lights, fallback environment).
OS: Fedora 34
CPU: Intel Core i7-6700K
GPU: GeForce GTX 1080
Resolution: 2560×1440
Godot versions: 3.x
a05aefb74, master
fe6c65a1a
Testing projects:
master
- Vulkan ClusteredProject FPS: 1198 (0.8 mspf)
Project FPS: 1195 (0.8 mspf)
Project FPS: 1198 (0.8 mspf)
Project FPS: 1198 (0.8 mspf)
Project FPS: 1199 (0.8 mspf)
master
- Vulkan MobileRuns faster than Vulkan Clustered thanks to its lower base cost. However, its performance will fall behind compared to Vulkan Clustered in a more complex scene with many lights.
Project FPS: 1380 (0.7 mspf)
Project FPS: 1376 (0.7 mspf)
Project FPS: 1380 (0.7 mspf)
Project FPS: 1379 (0.7 mspf)
Project FPS: 1349 (0.7 mspf)
3.x
- GLES3Project FPS: 1691 (0.5 mspf)
Project FPS: 1704 (0.5 mspf)
Project FPS: 1667 (0.5 mspf)
Project FPS: 1690 (0.5 mspf)
Project FPS: 1689 (0.5 mspf)
3.x
- GLES2Despite the GLES2 renderer's lowest base cost (out of all the renderers tested here), this is by far the slowest result.
Project FPS: 546 (1.8 mspf)
Project FPS: 548 (1.8 mspf)
Project FPS: 550 (1.8 mspf)
Project FPS: 548 (1.8 mspf)
Project FPS: 550 (1.8 mspf)
I tried so much variations with/without shading with gdScript, nativeScript (Nim) and different import settings without luck. One archer walk animation, with 8 frame costs 14 fps (reduced to 46fps) . It slows to 19-20fps when I exported it to android also. I'm adding screen shots from my computer with GeForce 940MX screen card (I can play Anno 1404 without any lag with this screen card).
I have only
one
archer on the screen, and I scripted with nim (very fast programming language). I supposed in this example I made the fastest things I can do. If not please share my mistake.Version: Godot 3.0 System: Linux Manjaro (ArchLinux derive) Frame rate drops too much (14fps for only one node). I expect it to work with 60fps.
Screen shots:
I have only one scene as Archer and I'm using a sprite image only. Nothing more.