android: the arguments arrive as a String[], not an ArrayList

The hook added in da04913 asked for getStringArrayListExtra, but `am
start --esa applicationArguments "--uitest,--workspace,/sdcard/x"`
stores a String[] -- that call answers null for an array, so the window
still started with no arguments at all. Ask for the array first, then
the list (Qt's own loader, putStringArrayListExtra), then the single
comma-separated string.

With this the uitest runs from adb on the NX789J: the fixtures and
selftest.pdf land in --workspace, which is how a device round trip is
possible without touch injection (adb cannot tap this window).
This commit is contained in:
WHC
2026-10-11 20:35:41 +08:00
parent 4c69ef39ab
commit 9d7ad9433e
+44 -4
View File
@@ -25,6 +25,7 @@
#include <QFileInfo>
#include <QFuture>
#include <QGuiApplication>
#include <QJniEnvironment>
#include <QJniObject>
#include <QMetaObject>
#include <QSemaphore>
@@ -120,12 +121,40 @@ QStringList intentArguments() {
activity.callObjectMethod("getIntent", "()Landroid/content/Intent;");
if (!intent.isValid())
return out;
const QJniObject key =
QJniObject::fromString(QStringLiteral("applicationArguments"));
/* Three shapes for the same extra, and which one arrives depends on who
* sent it: `am start --esa applicationArguments "--uitest,--workspace,/x"`
* stores a String[] (an empty launch, arguments and all, is what that cost
* us -- getStringArrayListExtra answers null for an array), a launcher or
* Qt's own loader uses putStringArrayListExtra, and `--es` puts one
* comma-separated string there. Try each, in that order. */
const QJniObject array = intent.callObjectMethod(
"getStringArrayExtra", "(Ljava/lang/String;)[Ljava/lang/String;",
key.object<jstring>());
if (array.isValid()) {
QJniEnvironment env;
const jobjectArray a = reinterpret_cast<jobjectArray>(array.object());
const jsize n = env->GetArrayLength(a);
for (jsize i = 0; i < n; i++) {
const jstring item =
reinterpret_cast<jstring>(env->GetObjectArrayElement(a, i));
if (!item)
continue;
const char *c = env->GetStringUTFChars(item, nullptr);
if (c) {
out << QString::fromUtf8(c);
env->ReleaseStringUTFChars(item, c);
}
env->DeleteLocalRef(item);
}
if (!out.isEmpty())
return out;
}
QJniObject list = intent.callObjectMethod(
"getStringArrayListExtra", "(Ljava/lang/String;)Ljava/util/ArrayList;",
QJniObject::fromString(QStringLiteral("applicationArguments"))
.object<jstring>());
if (!list.isValid())
return out;
key.object<jstring>());
if (list.isValid()) {
const jint n = list.callMethod<jint>("size", "()I");
for (jint i = 0; i < n; i++) {
QJniObject item =
@@ -133,6 +162,17 @@ QStringList intentArguments() {
if (item.isValid())
out << item.toString();
}
if (!out.isEmpty())
return out;
}
const QJniObject one = intent.callObjectMethod(
"getStringExtra", "(Ljava/lang/String;)Ljava/lang/String;",
key.object<jstring>());
if (one.isValid()) {
const QStringList parts =
one.toString().split(QLatin1Char(','), Qt::SkipEmptyParts);
out << parts;
}
return out;
}