Godot-docs: Clarify what an imported resource really is and how to load external files (png, jpg, ogg, wav...)

Created on 18 Jan 2019  路  5Comments  路  Source: godotengine/godot-docs

it's not the first time (and won't be the last) where an user tries to load an external file (a file that has not been imported) with load() or ResourceLoader.load() and gets confused because it doesn't load or it fails.

We need to explain them that those functions only work with imported files and what they should do to load external files. I think we need to specify somewhere that imported resources aren't the same as files and how to load external files but I have no idea where.

I'll try to explain it and hope that someone can unmess the mess I write 馃槄

In godot, imported resources aren't the same as files.

Explanation on what godot does when you import a file here https://docs.godotengine.org/en/latest/getting_started/workflow/assets/import_process.html

So a resource links a file with one or more converted files. For example, the path res://icon.png doesn't point to the file my_project/icon.png but it will read the icon.png.import file and this file will contain the path to the converted files something like my_project/.import/icon-47---.stex and my_project/.import/icon-12---.stex which are the files that the engine has created from your file and they are the ones that it will use at runtime.

When you export your project my_project/icon.png won't be in exported into the pck file but only the icon.png.import file pointing to those converted files.

And some examples to load different files:

Load an ogg file:

func play_external_file(path):
    var ogg = AudioStreamOGGVorbis.new()
    var file = File.new()   
    file.open(path, File.READ)
    ogg.data = file.get_buffer(file.get_len())
    file.close()
    $AudioStreamPlayer.stream = ogg
    $AudioStreamPlayer.play()

Load a png file:

func get_external_texture(path):
    var img = Image.new()
    img.load(path)
    var texture = ImageTexture.new()
    texture.create_from_image(img)
    return texture
enhancement

Most helpful comment

it's not the first time (and won't be the last) ...

Damn right. I also stepped into that hell of confusion and so I want to ping this issue (or just mark it as a reminder for myself).

As discussed in the referenced issue of the godot repository there are currently a few file formats which can be loaded at runtime:

By a combination of gdscript functions:

  • jpg
  • png
  • ogg

Or by using a plugin:

  • obj
  • dscn

A simple page in the I/O section of the docs which sums this up and collects the mentioned code snippets that were posted in those related issues would be of great benefit.

All 5 comments

Good one. This probably belongs in the "I/O" section of Tutorials.

Updated the load an image example. Image already has a load() function that will do all the work for us (reading the file and using the correct loader to load the image)

it's not the first time (and won't be the last) ...

Damn right. I also stepped into that hell of confusion and so I want to ping this issue (or just mark it as a reminder for myself).

As discussed in the referenced issue of the godot repository there are currently a few file formats which can be loaded at runtime:

By a combination of gdscript functions:

  • jpg
  • png
  • ogg

Or by using a plugin:

  • obj
  • dscn

A simple page in the I/O section of the docs which sums this up and collects the mentioned code snippets that were posted in those related issues would be of great benefit.

Is this working guys? Every time I fail I get more hope like achieving almost

func get_external_texture(path):
var img = Image.new()
img.load(path)
var texture = ImageTexture.new()
texture.create_from_image(img)
return texture

This does not work for me on Android
I get the following errors:

E 0:00:00.266 load_image: Error opening file '/storage/emulated/0/Pictures/cardgame/00000001.jpg'.
core/io/image_loader.cpp:56 @ load_image()
E 0:00:00.266 texture_set_data: Condition "!read.ptr()" is true.
drivers/gles3/rasterizer_storage_gles3.cpp:836 @ texture_set_data()
E 0:00:24.465 load_source_code: Condition "err" is true. Returned: err
modules/gdscript/gdscript.cpp:829 @ load_source_code()

It does work fine on Windows though.
I had the same issues on Android with the same errors with this this answer from Zylann:
https://godotengine.org/qa/50876/load-texture-from-file-and-assign-to-texture

Any help how to load external image data as a sprite texture on Android would be greatly appreciated!

Edit: Ok so after a hole day of painful trail and error, I figured out I apparently I have to check "Media Content Control", "Read External Storage", "Write External Storage", and call

OS.request_permissions()
print(OS.get_granted_permissions())

Any single one of those options won't do.
With that the errors are gone, however the image is still not shown. I do see a black rectangle in the exact size of my texture at the exact location of my sprite, but unlike in Windows where the texture shows, on Android it does not.
What else is there to do?
I really wish those error messages would be more useful and this process was documented somewhere.

Was this page helpful?
0 / 5 - 0 ratings