summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorAssam Boudjelthia <assam.boudjelthia@qt.io>2021-06-01 18:32:05 +0300
committerAssam Boudjelthia <assam.boudjelthia@qt.io>2021-06-04 10:46:57 +0300
commit965fc1148d5ae241972589fcbf772a0244656f14 (patch)
treedd7040bc45f20aaf2e2fa4f1003631299daaa378
parentdc794f7622bc00f7ca50fab65d6965695d6d2972 (diff)
JNI: Add calls to get field IDs
Task-number: QTBUG-92952 Change-Id: Ie68ede4b00a411064a29925b28b1f60a84d2d678 Reviewed-by: Ivan Solovev <ivan.solovev@qt.io> Reviewed-by: Ville Voutilainen <ville.voutilainen@qt.io>
-rw-r--r--src/corelib/kernel/qjnienvironment.cpp45
-rw-r--r--src/corelib/kernel/qjnienvironment.h2
-rw-r--r--tests/auto/corelib/kernel/qjnienvironment/testdata/src/org/qtproject/qt/android/testdata/QtJniEnvironmentTestClass.java5
-rw-r--r--tests/auto/corelib/kernel/qjnienvironment/tst_qjnienvironment.cpp48
4 files changed, 100 insertions, 0 deletions
diff --git a/src/corelib/kernel/qjnienvironment.cpp b/src/corelib/kernel/qjnienvironment.cpp
index 841fe747dc..4c21267b35 100644
--- a/src/corelib/kernel/qjnienvironment.cpp
+++ b/src/corelib/kernel/qjnienvironment.cpp
@@ -255,6 +255,51 @@ jmethodID QJniEnvironment::findStaticMethod(jclass clazz, const char *methodName
return id;
}
+
+/*!
+ Searches for an member field of a class \a clazz. The field is specified
+ by its \a fieldName and \a signature.
+
+ Returns the field ID or \c nullptr if the field is not found.
+
+ A usecase for this method is searching for class fields and caching their
+ IDs, so that they could later be used for getting/setting the fields.
+
+ \since 6.2
+*/
+jfieldID QJniEnvironment::findField(jclass clazz, const char *fieldName, const char *signature)
+{
+ if (clazz) {
+ jfieldID id = d->jniEnv->GetFieldID(clazz, fieldName, signature);
+ if (!checkAndClearExceptions())
+ return id;
+ }
+
+ return nullptr;
+}
+
+/*!
+ Searches for a static field of a class \a clazz. The field is specified
+ by its \a fieldName and \a signature.
+
+ Returns the field ID or \c nullptr if the field is not found.
+
+ A usecase for this method is searching for class fields and caching their
+ IDs, so that they could later be used for getting/setting the fields.
+
+ \since 6.2
+*/
+jfieldID QJniEnvironment::findStaticField(jclass clazz, const char *fieldName, const char *signature)
+{
+ if (clazz) {
+ jfieldID id = d->jniEnv->GetStaticFieldID(clazz, fieldName, signature);
+ if (!checkAndClearExceptions())
+ return id;
+ }
+
+ return nullptr;
+}
+
/*!
\fn JavaVM *QJniEnvironment::javaVM()
diff --git a/src/corelib/kernel/qjnienvironment.h b/src/corelib/kernel/qjnienvironment.h
index 610dd054fe..df3753da83 100644
--- a/src/corelib/kernel/qjnienvironment.h
+++ b/src/corelib/kernel/qjnienvironment.h
@@ -61,6 +61,8 @@ public:
jclass findClass(const char *className);
jmethodID findMethod(jclass clazz, const char *methodName, const char *signature);
jmethodID findStaticMethod(jclass clazz, const char *methodName, const char *signature);
+ jfieldID findField(jclass clazz, const char *fieldName, const char *signature);
+ jfieldID findStaticField(jclass clazz, const char *fieldName, const char *signature);
static JavaVM *javaVM();
bool registerNativeMethods(const char *className, const JNINativeMethod methods[], int size);
bool registerNativeMethods(jclass clazz, const JNINativeMethod methods[], int size);
diff --git a/tests/auto/corelib/kernel/qjnienvironment/testdata/src/org/qtproject/qt/android/testdata/QtJniEnvironmentTestClass.java b/tests/auto/corelib/kernel/qjnienvironment/testdata/src/org/qtproject/qt/android/testdata/QtJniEnvironmentTestClass.java
index 8f36dcc5fd..7bf6a7455a 100644
--- a/tests/auto/corelib/kernel/qjnienvironment/testdata/src/org/qtproject/qt/android/testdata/QtJniEnvironmentTestClass.java
+++ b/tests/auto/corelib/kernel/qjnienvironment/testdata/src/org/qtproject/qt/android/testdata/QtJniEnvironmentTestClass.java
@@ -33,6 +33,11 @@ public class QtJniEnvironmentTestClass
private static native void callbackFromJava(String message);
private static native void intCallbackFromJava(int value);
+ public final int INT_FIELD = 123;
+ public static final int S_INT_FIELD = 321;
+
+ QtJniEnvironmentTestClass() {}
+
public static void appendJavaToString(String message)
{
callbackFromJava("From Java: " + message);
diff --git a/tests/auto/corelib/kernel/qjnienvironment/tst_qjnienvironment.cpp b/tests/auto/corelib/kernel/qjnienvironment/tst_qjnienvironment.cpp
index 06372ebad2..079de48948 100644
--- a/tests/auto/corelib/kernel/qjnienvironment/tst_qjnienvironment.cpp
+++ b/tests/auto/corelib/kernel/qjnienvironment/tst_qjnienvironment.cpp
@@ -49,6 +49,8 @@ private slots:
void registerNativeMethodsByJclass();
void findMethod();
void findStaticMethod();
+ void findField();
+ void findStaticField();
};
void tst_QJniEnvironment::jniEnv()
@@ -203,6 +205,52 @@ void tst_QJniEnvironment::findStaticMethod()
QVERIFY(!env.checkAndClearExceptions());
}
+void tst_QJniEnvironment::findField()
+{
+ QJniEnvironment env;
+ jclass clazz = env.findClass(javaTestClass);
+ QVERIFY(clazz != nullptr);
+
+ // valid field
+ jfieldID validId = env.findField(clazz, "INT_FIELD", "I");
+ QVERIFY(validId != nullptr);
+
+ jmethodID constructorId = env.findMethod(clazz, "<init>", "()V");
+ QVERIFY(constructorId != nullptr);
+ jobject obj = env->NewObject(clazz, constructorId);
+ QVERIFY(!env.checkAndClearExceptions());
+ int value = env->GetIntField(obj, validId);
+ QVERIFY(!env.checkAndClearExceptions());
+ QVERIFY(value == 123);
+
+ // invalid signature
+ jfieldID invalidId = env.findField(clazz, "unknown", "I");
+ QVERIFY(invalidId == nullptr);
+ // check that all exceptions are already cleared
+ QVERIFY(!env.checkAndClearExceptions());
+}
+
+void tst_QJniEnvironment::findStaticField()
+{
+ QJniEnvironment env;
+ jclass clazz = env.findClass(javaTestClass);
+ QVERIFY(clazz != nullptr);
+
+ // valid field
+ jfieldID validId = env.findStaticField(clazz, "S_INT_FIELD", "I");
+ QVERIFY(validId != nullptr);
+
+ int size = env->GetStaticIntField(clazz, validId);
+ QVERIFY(!env.checkAndClearExceptions());
+ QVERIFY(size == 321);
+
+ // invalid signature
+ jfieldID invalidId = env.findStaticField(clazz, "unknown", "I");
+ QVERIFY(invalidId == nullptr);
+ // check that all exceptions are already cleared
+ QVERIFY(!env.checkAndClearExceptions());
+}
+
QTEST_MAIN(tst_QJniEnvironment)
#include "tst_qjnienvironment.moc"