Trying to add Thumbnail Previews for 3D Models to the FileSystem Dock

Godot Version

4.2.1

Question

Hi, I’ve been experimenting with ChatGPT to help generate a plugin that creates thumbnails previews for 3D models in the FileSystem Dock. It’s totally not my area of knowledge, but I thought I’d give it a go for fun. It’s an important feature currently missing for Godot and until the devs implement it I thought it might be useful to to make a quick plugin.

The script that was generated appears to be logical, however I’ve no idea if this is the correct way to generate the thumbnails for 3D models in the FileSystem dock, but anyhu :wink:

I’m getting a few errors though, some I think are to do with the GDScript being for V3 of Godot instead of v4. For example the Yield statement changing to Await. But there’s other issue’s, such as the signal at the start. Plus I’m surprised that the script is so short - so it might just be useless.

I’ve only ever thinkered with ChatGPT for small bits of code and it’s typically hit and miss as I’m sure you’re aware.

Anyway, here’s the plugin script that was generated:

@tool
extends EditorPlugin

func _enter_tree():
	connect("resource_pre_save", self, "_on_resource_pre_save")

func _on_resource_pre_save(resource):
	if resource is MeshInstance:
		var model = resource
		var viewport = Viewport.new()
		var camera = Camera.new()
		var light = OmniLight.new()
		
		viewport.add_child(camera)
		viewport.add_child(light)
		viewport.render_target_v_flip = true
		viewport.size = Vector2(64, 64)
		
		model.add_child(viewport)
		model.show()
		
		yield(get_tree(), "idle_frame")
		yield(get_tree(), "idle_frame")
		
		var image = viewport.get_texture().get_data()
		var thumbnail = ImageTexture.new()
		thumbnail.create_from_image(image)
		
		model.set("thumbnail/icon", thumbnail)
		model.remove_child(viewport)
		viewport.queue_free()


*In the description it says:*
This code connects the "resource_pre_save" signal to a function called "_on_resource_pre_save". When this function is called, it checks if the resource is a MeshInstance. If it is, it creates a Viewport, Camera, and Light, adds them to the Viewport, and sets up the Viewport to render the MeshInstance.

Then, it yields to allow the rendering to happen. Once the rendering is complete, it retrieves the rendered image, creates a thumbnail texture from the image, and sets the thumbnail texture as the icon for the MeshInstance.

    Finally, make sure to add your plugin to the list of enabled plugins in the project settings.

After completing these steps, your plugin should be able to generate thumbnail icons for 3D models in the File System dock in Godot Engine version 4.

Anyone want to see if they can fix it?```

Resource preview generation is available with the EditorResourcePreview singleton and EditorResourcePreviewGenerator class.

1 Like

Could you elaborate further as I’m not familiar with this script, as I said it was ai generated. I’ve never scripted plugins for Godot before and I’m not sure even if it will work :wink:

It actually works! Kinda. I had to change a few things, here is my modified script using version 4.2.1:

  • updated “yield” to “await”
  • updated “connect” to new syntax
  • used Camera3D and OmniLight3D as well as “get_viewport()” instead of creating new Viewport.
  • used PackedScene instead of MeshInstance as I tested it with “Prefab” resources
  • I don’t think “resource_pre_save” is a real signal, maybe the AI was hallucinating, I changed it to “resource_saved”. This means the script will trigger only after the resource is saved.

The preview thumbnail will appear immediately after saving the resource and the screenshot will be based on the position of the user camera.

This is already good for some use cases that want to generate a custom thumbnail for some resource. One thing left to see is if there is a way to trigger the saving for all resources in the project, so all thumbnails for existing assets will get automatically generated, although I don’t know if the generated image will actually be useful as the default position of the camera might not be perfect to represent the asset.

@tool
extends EditorPlugin

func _enter_tree():
	resource_saved.connect(_on_resource_saved)

func _on_resource_saved(resource):
	if resource is PackedScene:
		var model = resource
		var viewport = get_viewport().new()
		var camera = Camera3D.new()
		var light = OmniLight3D.new()
		
		viewport.add_child(camera)
		viewport.add_child(light)
		viewport.render_target_v_flip = true
		viewport.size = Vector2(64, 64)
		
		model.add_child(viewport)
		model.show()
		
		await get_tree().idle_frame
		await get_tree().idle_frame
		
		var image = viewport.get_texture().get_data()
		var thumbnail = ImageTexture.new()
		thumbnail.create_from_image(image)
		
		model.set("thumbnail/icon", thumbnail)
		model.remove_child(viewport)
		viewport.queue_free()

1 Like

Thanks for the reply. I created the plugin from your modified script, enabled it and added some 3D models (GLTF and FBX), but I’m not seeing any thumbnails generated in the File Browser.

You mentioned that the thumbnails are generated after the resource is saved, but I’m not sure what you mean by this as the script was meant to create thumbnails of the imported 3D models. Maybe it’s not doing what I expected and works differently.

Am I missing something? :wink:

ok, I was totally wrong, I confused an out-of-the-box feature (thumbnail generation on scene save) with this script working :sweat_smile:.
I have a huge project with a collection of imported assets that were never opened and thus didn’t have the thumbnail, so when I opened them and the preview was generated I was convinced it was because of this.

In any case, this will not work directly on GLTF or FBX, because Godot cannot save them, it can only open them in a view-only window, thus they need to be converted to a “.scn” or “.tscn” file first.

I was looking for a way to do this automatically myself and thought this could help.

Sorry for the confusion!

Someone smarter than me developed something that might just be what you need: GitHub - 4d49/scene-library: A tool for easy work with your scenes in Godot 4.2+

They developed it as a separate dock, you can drag and drop your GLTF or FBX there and it should cover your use case!

See here original thread: Scene Library Tool