summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/corelib/kernel/qjnitypes.h14
-rw-r--r--tests/auto/corelib/kernel/qjnienvironment/testdata/src/org/qtproject/qt/android/testdata/QtJniEnvironmentTestClass.java18
-rw-r--r--tests/auto/corelib/kernel/qjnienvironment/tst_qjnienvironment.cpp71
3 files changed, 103 insertions, 0 deletions
diff --git a/src/corelib/kernel/qjnitypes.h b/src/corelib/kernel/qjnitypes.h
index bbe0bb2cc7..73b5db297c 100644
--- a/src/corelib/kernel/qjnitypes.h
+++ b/src/corelib/kernel/qjnitypes.h
@@ -367,6 +367,20 @@ static const JNINativeMethod Method##_method = { \
#define Q_JNI_NATIVE_METHOD(Method) QtJniMethods::Method##_method
+#define Q_DECLARE_JNI_NATIVE_METHOD_IN_CURRENT_SCOPE(...) \
+ QT_OVERLOADED_MACRO(QT_DECLARE_JNI_NATIVE_METHOD_IN_CURRENT_SCOPE, __VA_ARGS__) \
+
+#define QT_DECLARE_JNI_NATIVE_METHOD_IN_CURRENT_SCOPE_2(Method, Name) \
+ static inline constexpr auto Method##_signature = QtJniTypes::nativeMethodSignature(Method); \
+ static inline const JNINativeMethod Method##_method = { \
+ #Name, Method##_signature.data(), reinterpret_cast<void *>(Method) \
+ };
+
+#define QT_DECLARE_JNI_NATIVE_METHOD_IN_CURRENT_SCOPE_1(Method) \
+ QT_DECLARE_JNI_NATIVE_METHOD_IN_CURRENT_SCOPE_2(Method, Method) \
+
+#define Q_JNI_NATIVE_SCOPED_METHOD(Method, Scope) Scope::Method##_method
+
QT_END_NAMESPACE
#endif
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 342342c548..984307d57d 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
@@ -7,6 +7,9 @@ public class QtJniEnvironmentTestClass
{
private static native void callbackFromJava(String message);
private static native void namedCallbackFromJava(String message);
+ private static native void memberCallbackFromJava(String message);
+ private static native void namedMemberCallbackFromJava(String message);
+ private static native void namespaceCallbackFromJava(String message);
private static native void intCallbackFromJava(int value);
public final int INT_FIELD = 123;
@@ -24,6 +27,21 @@ public class QtJniEnvironmentTestClass
namedCallbackFromJava("From Java (named): " + message);
}
+ public static void memberAppendJavaToString(String message)
+ {
+ memberCallbackFromJava("From Java (member): " + message);
+ }
+
+ public static void namedMemberAppendJavaToString(String message)
+ {
+ namedMemberCallbackFromJava("From Java (named member): " + message);
+ }
+
+ public static void namespaceAppendJavaToString(String message)
+ {
+ namespaceCallbackFromJava("From Java (namespace): " + message);
+ }
+
public static void convertToInt(String message)
{
intCallbackFromJava(Integer.parseInt(message));
diff --git a/tests/auto/corelib/kernel/qjnienvironment/tst_qjnienvironment.cpp b/tests/auto/corelib/kernel/qjnienvironment/tst_qjnienvironment.cpp
index 4809505f47..da72b6d32b 100644
--- a/tests/auto/corelib/kernel/qjnienvironment/tst_qjnienvironment.cpp
+++ b/tests/auto/corelib/kernel/qjnienvironment/tst_qjnienvironment.cpp
@@ -115,6 +115,34 @@ static void callbackFromJavaNoCtor(JNIEnv *env, jobject /*thiz*/, jstring value)
}
Q_DECLARE_JNI_NATIVE_METHOD(callbackFromJavaNoCtor);
+class CallbackClass {
+public:
+ static void memberCallbackFromJava(JNIEnv *env, jobject /*thiz*/, jstring value)
+ {
+ Q_UNUSED(env)
+ registerNativesString = QJniObject(value).toString();
+ }
+ Q_DECLARE_JNI_NATIVE_METHOD_IN_CURRENT_SCOPE(memberCallbackFromJava)
+
+ static void tediouslyLongNamed_memberCallbackFromJava(JNIEnv *env, jobject /*thiz*/,
+ jstring value)
+ {
+ Q_UNUSED(env)
+ registerNativesString = QJniObject(value).toString();
+ }
+ Q_DECLARE_JNI_NATIVE_METHOD_IN_CURRENT_SCOPE(tediouslyLongNamed_memberCallbackFromJava,
+ namedMemberCallbackFromJava)
+};
+
+namespace CallbackNamespace {
+ static void namespaceCallbackFromJava(JNIEnv *env, jobject /*thiz*/, jstring value)
+ {
+ Q_UNUSED(env)
+ registerNativesString = QJniObject(value).toString();
+ }
+ Q_DECLARE_JNI_NATIVE_METHOD_IN_CURRENT_SCOPE(namespaceCallbackFromJava)
+}
+
void tst_QJniEnvironment::registerNativeMethods()
{
QJniObject QtString = QJniObject::fromString(registerNativesString);
@@ -147,6 +175,49 @@ void tst_QJniEnvironment::registerNativeMethods()
QVERIFY(registerNativesString == QStringLiteral("From Java (named): Qt"));
}
+ // Static class member as callback
+ {
+ QVERIFY(env.registerNativeMethods(javaTestClass, {
+ Q_JNI_NATIVE_SCOPED_METHOD(memberCallbackFromJava, CallbackClass)
+ }));
+
+ QJniObject::callStaticMethod<void>(javaTestClass,
+ "memberAppendJavaToString",
+ "(Ljava/lang/String;)V",
+ QtString.object<jstring>());
+ QTest::qWait(200);
+ QVERIFY(registerNativesString == QStringLiteral("From Java (member): Qt"));
+ }
+
+ // Static named class member as callback
+ {
+ QVERIFY(env.registerNativeMethods(javaTestClass, {
+ Q_JNI_NATIVE_SCOPED_METHOD(tediouslyLongNamed_memberCallbackFromJava,
+ CallbackClass)
+ }));
+
+ QJniObject::callStaticMethod<void>(javaTestClass,
+ "namedMemberAppendJavaToString",
+ "(Ljava/lang/String;)V",
+ QtString.object<jstring>());
+ QTest::qWait(200);
+ QVERIFY(registerNativesString == QStringLiteral("From Java (named member): Qt"));
+ }
+
+ // Function generally just in namespace as callback
+ {
+ QVERIFY(env.registerNativeMethods(javaTestClass, {
+ Q_JNI_NATIVE_SCOPED_METHOD(namespaceCallbackFromJava, CallbackNamespace)
+ }));
+
+ QJniObject::callStaticMethod<void>(javaTestClass,
+ "namespaceAppendJavaToString",
+ "(Ljava/lang/String;)V",
+ QtString.object<jstring>());
+ QTest::qWait(200);
+ QVERIFY(registerNativesString == QStringLiteral("From Java (namespace): Qt"));
+ }
+
// No default constructor in class
{
QVERIFY(env.registerNativeMethods(javaTestClassNoCtor, {