From b59e89c907e349ecbb11efdcea51e7928a1799fd Mon Sep 17 00:00:00 2001 From: Assam Boudjelthia Date: Thu, 8 Dec 2022 03:42:13 +0200 Subject: [PATCH] Android: pass EXTRA_INITIAL_URI to native FileDialog Allow setting the initial directory where the file dialog will be opened. Change-Id: I1395b367c74d28fb2890ac53a90456c3ac4c1b05 Reviewed-by: Andy Shaw (cherry picked from commit 609e14724edfd8d8cef23c5f30ad7812a359ed8d) Reviewed-by: Qt Cherry-pick Bot --- .../qandroidplatformfiledialoghelper.cpp | 28 ++++++++++++++++--- .../qandroidplatformfiledialoghelper.h | 6 ++-- 2 files changed, 28 insertions(+), 6 deletions(-) diff --git a/src/plugins/platforms/android/qandroidplatformfiledialoghelper.cpp b/src/plugins/platforms/android/qandroidplatformfiledialoghelper.cpp index 6d28bd23882..3723e33371b 100644 --- a/src/plugins/platforms/android/qandroidplatformfiledialoghelper.cpp +++ b/src/plugins/platforms/android/qandroidplatformfiledialoghelper.cpp @@ -97,6 +97,22 @@ void QAndroidPlatformFileDialogHelper::setInitialFileName(const QString &title) extraTitle.object(), QJniObject::fromString(title).object()); } +void QAndroidPlatformFileDialogHelper::setInitialDirectoryUri(const QString &directory) +{ + if (directory.isEmpty()) + return; + + if (QNativeInterface::QAndroidApplication::sdkVersion() < 26) + return; + + const auto extraInitialUri = QJniObject::getStaticObjectField( + "android/provider/DocumentsContract", "EXTRA_INITIAL_URI", "Ljava/lang/String;"); + m_intent.callObjectMethod("putExtra", + "(Ljava/lang/String;Ljava/lang/String;)Landroid/content/Intent;", + extraInitialUri.object(), + QJniObject::fromString(directory).object()); +} + void QAndroidPlatformFileDialogHelper::setOpenableCategory() { const QJniObject CATEGORY_OPENABLE = QJniObject::getStaticObjectField( @@ -179,11 +195,8 @@ bool QAndroidPlatformFileDialogHelper::show(Qt::WindowFlags windowFlags, Qt::Win if (options()->acceptMode() == QFileDialogOptions::AcceptSave) { m_intent = getFileDialogIntent("ACTION_CREATE_DOCUMENT"); const QList selectedFiles = options()->initiallySelectedFiles(); - if (selectedFiles.size() > 0) { - // TODO: The initial folder to show at the start should be handled by EXTRA_INITIAL_URI - // Take only the file name. + if (selectedFiles.size() > 0) setInitialFileName(selectedFiles.first().fileName()); - } } else if (options()->acceptMode() == QFileDialogOptions::AcceptOpen) { switch (options()->fileMode()) { case QFileDialogOptions::FileMode::DirectoryOnly: @@ -207,6 +220,8 @@ bool QAndroidPlatformFileDialogHelper::show(Qt::WindowFlags windowFlags, Qt::Win setMimeTypes(); } + setInitialDirectoryUri(m_directory.toString()); + QtAndroidPrivate::registerActivityResultListener(this); m_activity.callMethod("startActivityForResult", "(Landroid/content/Intent;I)V", m_intent.object(), REQUEST_CODE); @@ -220,6 +235,11 @@ void QAndroidPlatformFileDialogHelper::hide() QtAndroidPrivate::unregisterActivityResultListener(this); } +void QAndroidPlatformFileDialogHelper::setDirectory(const QUrl &directory) +{ + m_directory = directory; +} + void QAndroidPlatformFileDialogHelper::exec() { m_eventLoop.exec(QEventLoop::DialogExec); diff --git a/src/plugins/platforms/android/qandroidplatformfiledialoghelper.h b/src/plugins/platforms/android/qandroidplatformfiledialoghelper.h index 4281cb8198e..156eda91424 100644 --- a/src/plugins/platforms/android/qandroidplatformfiledialoghelper.h +++ b/src/plugins/platforms/android/qandroidplatformfiledialoghelper.h @@ -32,8 +32,8 @@ public: void setFilter() override {} QList selectedFiles() const override { return m_selectedFile; } void selectFile(const QUrl &) override {} - QUrl directory() const override { return QUrl(); } - void setDirectory(const QUrl &) override {} + QUrl directory() const override { return m_directory; } + void setDirectory(const QUrl &directory) override; bool defaultNameFilterDisables() const override { return false; } bool handleActivityResult(jint requestCode, jint resultCode, jobject data) override; @@ -41,12 +41,14 @@ private: QJniObject getFileDialogIntent(const QString &intentType); void takePersistableUriPermission(const QJniObject &uri); void setInitialFileName(const QString &title); + void setInitialDirectoryUri(const QString &directory); void setOpenableCategory(); void setAllowMultipleSelections(bool allowMultiple); void setMimeTypes(); QEventLoop m_eventLoop; QList m_selectedFile; + QUrl m_directory; QJniObject m_intent; const QJniObject m_activity; };