Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/joomla/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Android NDK装载资产_Android_Android Ndk - Fatal编程技术网

Android NDK装载资产

Android NDK装载资产,android,android-ndk,Android,Android Ndk,我使用此方法在NDK中加载资产: jclass localRefCls = myEnv->FindClass("(...)/AssetLoaderHelper"); helperClass = reinterpret_cast<jclass>(myEnv->NewGlobalRef(localRefCls)); myEnv->DeleteLocalRef(localRefCls); helperMethod1ID = myEnv->GetStaticMeth

我使用此方法在NDK中加载资产:

jclass localRefCls = myEnv->FindClass("(...)/AssetLoaderHelper");
helperClass = reinterpret_cast<jclass>(myEnv->NewGlobalRef(localRefCls));
myEnv->DeleteLocalRef(localRefCls);

helperMethod1ID = myEnv->GetStaticMethodID(helperClass, "getFileData", "(Ljava/lang/String;)[B");

...

myEnv->PushLocalFrame(10);

jstring pathString = myEnv->NewStringUTF(path);
jbyteArray data = (jbyteArray) myEnv->CallStaticObjectMethod(helperClass, helperMethod1ID, pathString);

char* buffer = new char[len];
myEnv->GetByteArrayRegion(data, 0, len, (jbyte*)buffer);

myEnv->DeleteLocalRef(pathString);
myEnv->DeleteLocalRef(data);

jobject result;
myEnv->PopLocalFrame(result);
myEnv->DeleteLocalRef(result);

return buffer;

它可以工作,但当我加载许多资产时,会出现崩溃或系统锁定。我是否犯了错误,或者有人知道将资产加载到NDK的更好方法?也许这是我的设备内存不足的唯一问题?

我不确定您的确切问题,但我可以提供另一种解决方案来打开JNI端的资产:

  • Java端为每个有问题的文件创建一个AssetFileDescriptor(现在调用这个fd
  • 将fd.getFileDescriptor()、fd.getStartOffset()和fd.getLength()的值传递给JNI函数
  • JNI端现在可以使用#2中的信息使用fdopen()、fseek()、fread()等
  • 在JNI工作之后,不要忘记调用fd.close()

  • 希望这对您有所帮助

    我不确定您的确切问题,但我可能会提供另一种解决方案来打开JNI方面的资产:

  • Java端为每个有问题的文件创建一个AssetFileDescriptor(现在调用这个fd
  • 将fd.getFileDescriptor()、fd.getStartOffset()和fd.getLength()的值传递给JNI函数
  • JNI端现在可以使用#2中的信息使用fdopen()、fseek()、fread()等
  • 在JNI工作之后,不要忘记调用fd.close()

  • 希望这有帮助,如果我在ndk中使用需要文件路径的库,该怎么办?例如,sqlite open()函数获取数据库文件的路径。在这种情况下,最好的解决方案是什么?如果需要路径,只需使用路径。在您的sqlite_open()示例中,您很可能需要使用getExternalStorageDirectory()在Java端构建一些东西然后通过JNI传递给SQLite。不,我的意思是,如何打开作为apk资源包含的SQLite数据库。然后,您需要按照我的回答中所述进行操作。如果我在ndk中使用需要文件路径的库,该怎么办?例如SQLite open()函数获取数据库文件的路径。在这种情况下,最好的解决方案是什么?如果需要路径,只需使用该路径即可。在使用sqlite_open()的示例中,您很可能需要使用getExternalStorageDirectory()在Java端构建某些内容然后通过JNI传递给SQLite。不,我的意思是,如何打开作为apk资源包含的SQLite数据库。然后您需要按照我的回答中所述的操作。
    public static byte[] getFileData(String path)
    {
    InputStream asset = getAsset(path); //my method using InputStream.open
    
    byte[] b = null;
    try
    {
        int size = asset.available();
        b = new byte[size];
        asset.read(b, 0, size);
        asset.close();
    }
    catch (IOException e1)
    {
        Log.e("getFileData", e1.getMessage());
    }
    
    return b;
    }