1

I have native JNI implementation and for now I have my media files under the app dir /storage/emulated/0/Android/data/com.my_app.debug/files/Models/my_media_file.mp4 in order to start read one of the files I need to pass a path to JNI where inside I use such method that expect to get path_to_mp4_file

bool Decoder::InitFromFile(std::string const &filename)
{
    m_file.open(filename, std::ios::binary);
    if (!m_file.is_open())
    {
        return false;
    }
...
}

And all works, but now I need to read from build-in raw folder, so now in order to get path to my file I am using this way

fun foo()
{
...
        val path = "android.resource://" + activity!!.packageName + "/" + R.raw.my_media_file
        val uri = Uri.parse(path)
        JNIImplementation.InitFromFile(uri.path)
...
}

But now uri = android.resource://com.my_app.debug/2131492865 if I get uri.path = /2131492865.

Issue is that if I pass this uri.path as a path to InitFromFile method I get an error, because I can't open file by path /2131492865.

So, as far as I understand there is should be a way to read from raw or assert folder native way or something like this

How to do it?

Or maybe there is a way how to put this media file in app (build-in) and have access to get path as to regular file? I mean somehow look at this file not as a resource, but as a simple file?

Sirop4ik
  • 4,543
  • 2
  • 54
  • 121
  • 1
    If files are shipped in assets or raw folder one cannot use classic file paths as those files are resources. Under java one would use for instance assets manager to open an input stream. Or something like get raw resource to open an inputstream too. – blackapps Apr 13 '20 at 10:37
  • 1
    `"android.resource://"` is only understood by WebView component. – blackapps Apr 13 '20 at 10:38
  • @blackapps Maybe there is a way to put this media file under app like `build-in` and get a regular path to this file? I mean somehow look at this file not as a resource, but as a simple file? – Sirop4ik Apr 13 '20 at 11:05
  • In Kotlin / Java we can access a resource file with resource ID. It seems like the only way to access a resource file is using its resource ID, and I **did not find a way to access them using NDK API**. To [access original files](https://developer.android.com/guide/topics/resources/providing-resources#OriginalFiles), Android documentation recommends to keep those files in `asset/` directory. In NDK there is a way to read asset files. For that you check see [this](https://stackoverflow.com/a/33957074/2443657). – Lakindu May 10 '20 at 18:59
  • But I **do not see a way to access asset file using a file path in file system**. When installing the APK, they are not being saved as separate individual files to the file system. Only way to access assets is using AAssetManager and AAsset NDK APIs. – Lakindu May 10 '20 at 19:03
  • So what you can do is, read the asset file, save it to [app's internal storage directory](https://developer.android.com/training/data-storage/app-specific#internal), and use that file path. Then you will be able to use `std::ifstream` to open by file path and access the file data. To know how to copy asset file to the file system, check [this](https://stackoverflow.com/a/13317651/2443657). – Lakindu May 10 '20 at 19:05
  • [answered two years later](https://stackoverflow.com/a/33957074/192373) – Alex Cohn May 13 '20 at 07:56
  • 1
    @Lakindu that's right. An asset does not exist in the file system. You can get a file handle to it through AAsset API (with offset). Actually, for uncompressed assets (like mp3), the handle is to the APK file. If for some reason you don't have access to AssetManager, you can parse the APK file as zip and find the asset that you need. System will provide **zlib** for you. – Alex Cohn May 13 '20 at 08:08

0 Answers0