简体   繁体   English

Android NDK-引用JNIEnv从C ++调用Java

[英]Android NDK - referencing JNIEnv to call Java from C++

I'm very new to C++ and I'm working with the Superpowered FrequencyDomain example here: https://github.com/superpoweredSDK/Low-Latency-Android-Audio-iOS-Audio-Engine/blob/master/Examples_Android/FrequencyDomain/app/src/main/jni/FrequencyDomain.cpp 我是C ++的新手,并且在此处使用Superpowered FrequencyDomain示例: https : //github.com/superpoweredSDK/Low-Latency-Android-Audio-iOS-Audio-Engine/blob/master/Examples_Android/FrequencyDomain /app/src/main/jni/FrequencyDomain.cpp

I want to continuously update a TextView with the loudest frequency being received from inside this while loop: 我想用从while循环内部接收到的最大频率不断更新TextView:

static bool audioProcessing(void * __unused clientdata, short int *audioInputOutput, int numberOfSamples, int __unused samplerate) {
SuperpoweredShortIntToFloat(audioInputOutput, inputBufferFloat, (unsigned int)numberOfSamples); // Converting the 16-bit integer samples to 32-bit floating point.
frequencyDomain->addInput(inputBufferFloat, numberOfSamples); // Input goes to the frequency domain.

// In the frequency domain we are working with 1024 magnitudes and phases for every channel (left, right), if the fft size is 2048.
while (frequencyDomain->timeDomainToFrequencyDomain(magnitudeLeft, magnitudeRight, phaseLeft, phaseRight)) {

I think I need to do something like this: 我想我需要做这样的事情:

jclass classs = env->FindClass("com/superpowered/frequencydomain/MainActivity");
jmethodID method = env->GetMethodID(classs, "updateTextViewFromJNI","(I)V");
env->CallVoidMethod(thiz, method, myJavaInt);

but those are the only lines in a example C++ function which already has access to env and thiz: 但是这些是示例C ++函数中仅有的几行已经可以访问env和thiz的行:

void callJavaMethod(JNIEnv* env,jobject thiz) {...previous 3 lines...}

Calling a Java function like this: 像这样调用Java函数:

public void updateTextViewFromJNI(int i) {
    txtLoudestFreq.setText(Integer.toString(i));
}

I've been trying different ways to getting to JNIEnv and jobject, but I haven't succeeded yet. 我一直在尝试不同的方法来获取JNIEnv和jobject,但我还没有成功。 I see they're unused here: 我看到它们在这里未使用:

extern "C" JNIEXPORT void Java_com_superpowered_frequencydomain_MainActivity_FrequencyDomain(JNIEnv * __unused javaEnvironment, jobject __unused obj, jint samplerate, jint buffersize)

but I'm not sure how to get access to them in: 但我不确定如何通过以下方式访问它们:

audioProcessing

I've tried making them global. 我尝试使它们全球化。 From what I've read, I'm trying to get a reference to them, but missing how to do it. 从我已阅读的内容中,我试图获得对它们的引用,但是却缺少如何做的参考。 What steps do I need to do in order to be able to call something like this: 为了能够调用如下内容,我需要执行哪些步骤:

env->CallVoidMethod(thiz, method, myJavaInt);

from inside audioProcessing? 从audioProcessing内部? Thank you very much! 非常感谢你!

Calling Java is not recommended from an audio processing thread, as it involves multiple blocking calls. 不建议从音频处理线程中调用Java,因为它涉及多个阻塞调用。

Env and thiz are thread specific, different from thread to thread. Env和thiz是特定于线程的,因线程而异。 Getting them for the audio processing thread is a big no-no. 不让它们进入音频处理线程是一个很大的禁忌。

It's better to think the other way around: 最好反过来考虑:

  • Update an array in the audio processing callback with the results you'd like to display. 使用您要显示的结果更新音频处理回调中的数组。
  • Create a JNI function to return with the values of the array to Java. 创建一个JNI函数以将数组的值返回给Java。
  • Periodically call that JNI function from a Runnable (in Java). 从Runnable(在Java中)定期调用该JNI函数。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM