[education/rkward] rkward/rbackend: Add rk.select.file() function; not yet documented
Thomas Friedrichsmeier
null at kde.org
Fri Sep 8 21:42:25 BST 2023
Git commit 4ed0423c313072a5fbd83ff4b9561e0f56e5950f by Thomas Friedrichsmeier.
Committed on 08/09/2023 at 22:41.
Pushed by tfry into branch 'master'.
Add rk.select.file() function; not yet documented
M +8 -9 rkward/rbackend/rkrbackend.cpp
M +2 -3 rkward/rbackend/rkrbackendprotocol_shared.h
M +32 -8 rkward/rbackend/rkrinterface.cpp
M +1 -0 rkward/rbackend/rpackages/rkward/NAMESPACE
M +10 -0 rkward/rbackend/rpackages/rkward/R/rk.KDE_GUI-functions.R
https://invent.kde.org/education/rkward/-/commit/4ed0423c313072a5fbd83ff4b9561e0f56e5950f
diff --git a/rkward/rbackend/rkrbackend.cpp b/rkward/rbackend/rkrbackend.cpp
index 77ebb401a..01dfa9ab9 100644
--- a/rkward/rbackend/rkrbackend.cpp
+++ b/rkward/rbackend/rkrbackend.cpp
@@ -636,19 +636,18 @@ QStringList charPArrayToQStringList (const char** chars, int count) {
return ret;
}
-int RChooseFile (int isnew, char *buf, int len) {
+int RChooseFile(int isnew, char *buf, int len) {
RK_TRACE (RBACKEND);
- RBackendRequest request (true, RBackendRequest::ChooseFile);
- request.params["new"] = QVariant ((bool) isnew);
+ QStringList params;
+ params << "choosefile" << QString() /* caption */ << QString() /* initial */ << "*" /* filter */ << (isnew ? "newfile" : "file");
+ auto res = RKRBackend::this_pointer->handlePlainGenericRequest(params, true);
- RKRBackend::this_pointer->handleRequest (&request);
-
- QByteArray localres = RKRBackend::fromUtf8 (request.params["result"].toString ());
- qstrncpy ((char *) buf, localres.data (), len);
+ QByteArray localres = RKRBackend::fromUtf8(res.ret.toString());
+ qstrncpy ((char *) buf, localres.data(), len);
-// return length of filename (strlen (buf))
- return (qMin (len - 1, localres.size ()));
+// return length of filename (strlen(buf))
+ return (qMin(len - 1, localres.size()));
}
/* There are about one million possible entry points to editing / showing files. We try to cover them all, using the
diff --git a/rkward/rbackend/rkrbackendprotocol_shared.h b/rkward/rbackend/rkrbackendprotocol_shared.h
index 9b1780d2f..f452730fc 100644
--- a/rkward/rbackend/rkrbackendprotocol_shared.h
+++ b/rkward/rbackend/rkrbackendprotocol_shared.h
@@ -31,14 +31,13 @@ public:
BackendExit,
ShowMessage,
ShowFiles,
- ChooseFile,
EditFiles,
- ReadLine, // 5
+ ReadLine, // 4
CommandOut, /**< Request the next command, and notify about the result of the previus. TODO split. */
Started,
EvalRequest,
CallbackRequest,
- GenericRequestWithSubcommands, // 10
+ GenericRequestWithSubcommands, // 9
PlainGenericRequest,
SetParamsFromBackend,
Debugger,
diff --git a/rkward/rbackend/rkrinterface.cpp b/rkward/rbackend/rkrinterface.cpp
index a6dfeb9d0..325ab23d2 100644
--- a/rkward/rbackend/rkrinterface.cpp
+++ b/rkward/rbackend/rkrinterface.cpp
@@ -16,6 +16,7 @@ SPDX-License-Identifier: GPL-2.0-or-later
#include "../settings/rksettingsmoduleoutput.h"
#include "../settings/rksettingsmodulegraphics.h"
#include "../settings/rksettingsmoduleplugins.h"
+#include "../settings/rkrecenturls.h"
#include "../core/robjectlist.h"
#include "../core/renvironmentobject.h"
#include "../core/rkmodificationtracker.h"
@@ -624,6 +625,37 @@ GenericRRequestResult RInterface::processPlainGenericRequest(const QStringList &
QStringList results = RKSelectListDialog::doSelect (QApplication::activeWindow(), title, choices, preselects, multiple);
if (results.isEmpty ()) results.append (""); // R wants to have it that way
return GenericRRequestResult(results);
+ } else if (call == "choosefile") {
+ QFileDialog d(nullptr, calllist.value(1)); // caption
+ QString initial = calllist.value(2);
+ QString cat;
+ if (initial.startsWith('#')) {
+ cat = initial.mid(1);
+ initial = QFileInfo(RKRecentUrls::mostRecentUrl(cat).toLocalFile()).absolutePath();
+ }
+
+ d.setDirectory(initial);
+ QString filter = calllist.value(3);
+ if (!filter.isEmpty()) {
+ if (!filter.contains('(')) filter += '(' + filter + ')';
+ d.setNameFilter(filter);
+ }
+ QString mode = calllist.value(4);
+ if (mode == "file") d.setFileMode(QFileDialog::ExistingFile);
+ else if (mode == "files") d.setFileMode(QFileDialog::ExistingFiles);
+ else if (mode == "dir") d.setFileMode(QFileDialog::Directory);
+ else if (mode == "newfile") {
+ d.setFileMode(QFileDialog::AnyFile);
+ d.setAcceptMode(QFileDialog::AcceptSave);
+ } else RK_ASSERT(false);
+
+ d.exec();
+ auto res = d.selectedFiles();
+ if (!res.isEmpty() && !cat.isEmpty()) {
+ RKRecentUrls::addRecentUrl(cat, QUrl::fromLocalFile(res.value(0)));
+ }
+
+ return GenericRRequestResult(res);
} else if (call == "commandHistory") {
if (calllist.value (1) == "get") {
return GenericRRequestResult(RKConsole::mainConsole()->commandHistory());
@@ -868,14 +900,6 @@ void RInterface::processRBackendRequest (RBackendRequest *request) {
} else if ((type == RBackendRequest::ShowFiles) || (type == RBackendRequest::EditFiles)) {
ShowEditTextFileAgent::showEditFiles (request);
return; // we are not done, yet!
- } else if (type == RBackendRequest::ChooseFile) {
- QString filename;
- if (request->params["new"].toBool ()) {
- filename = QFileDialog::getSaveFileName ();
- } else {
- filename = QFileDialog::getOpenFileName ();
- }
- request->params["result"] = QVariant (filename);
} else if (type == RBackendRequest::SetParamsFromBackend) {
na_real = request->params["na_real"].toDouble ();
na_int = request->params["na_int"].toInt ();
diff --git a/rkward/rbackend/rpackages/rkward/NAMESPACE b/rkward/rbackend/rpackages/rkward/NAMESPACE
index 2fb4c47d5..120820136 100644
--- a/rkward/rbackend/rpackages/rkward/NAMESPACE
+++ b/rkward/rbackend/rpackages/rkward/NAMESPACE
@@ -103,6 +103,7 @@ export(rk.save.workplace)
export(rk.screen.device)
export(rk.select.CRAN.mirror)
export(rk.select.list)
+export(rk.select.file)
export(rk.sessionInfo)
export(rk.set.label)
export(rk.set.output.html.file)
diff --git a/rkward/rbackend/rpackages/rkward/R/rk.KDE_GUI-functions.R b/rkward/rbackend/rpackages/rkward/R/rk.KDE_GUI-functions.R
index f6cfb6571..8df0491cf 100755
--- a/rkward/rbackend/rpackages/rkward/R/rk.KDE_GUI-functions.R
+++ b/rkward/rbackend/rpackages/rkward/R/rk.KDE_GUI-functions.R
@@ -185,3 +185,13 @@
.rk.do.plain.call ("select.list", params)
}
+
+# file dialog
+# NOTE: initial specifies initial directory to start at (or file to select).
+# If this starts with a "#", the last file selected in a dialog with the same initial parameter
+# will be used, instead. E.g. initial="#images".
+#' @export
+#' @rdname rk.show.messages
+"rk.select.file" <- function(caption = NULL, initial = NULL, filter = '*', mode=c("file", "files", "dir", "newfile")) {
+ .rk.do.plain.call ("choosefile", list(caption, initial, filter, mode[1]))
+}
More information about the rkward-tracker
mailing list