From 3857a6bc542e89ecfe319c3f529b8ad0ac22adea Mon Sep 17 00:00:00 2001 From: Heiko Klare Date: Thu, 25 Jan 2024 15:32:20 +0100 Subject: [PATCH] Expose cancel state of FileDialog The FileDialog implementations do currently not provide any way to identify that the dialog was canceled. The dialogs return a null string in case no file was selected, but is not possible to identify whether this was intended (via a cancel action) or if there was some unexpected error (such as too long file paths on Windows). This change introduces a `wasCanceled()` method to the FileDialog implementations for all three operating systems. The dialogs evaluate the operating system's response code for the system's dialog control and store it to be retrieved by the added method. --- .../cocoa/org/eclipse/swt/internal/cocoa/OS.java | 5 +++-- .../win32/org/eclipse/swt/internal/win32/OS.java | 1 + .../cocoa/org/eclipse/swt/widgets/FileDialog.java | 10 ++++++++++ .../gtk/org/eclipse/swt/widgets/FileDialog.java | 10 ++++++++++ .../win32/org/eclipse/swt/widgets/FileDialog.java | 10 ++++++++++ 5 files changed, 34 insertions(+), 2 deletions(-) diff --git a/bundles/org.eclipse.swt/Eclipse SWT PI/cocoa/org/eclipse/swt/internal/cocoa/OS.java b/bundles/org.eclipse.swt/Eclipse SWT PI/cocoa/org/eclipse/swt/internal/cocoa/OS.java index 873c785a1ed..2f8c5feec27 100644 --- a/bundles/org.eclipse.swt/Eclipse SWT PI/cocoa/org/eclipse/swt/internal/cocoa/OS.java +++ b/bundles/org.eclipse.swt/Eclipse SWT PI/cocoa/org/eclipse/swt/internal/cocoa/OS.java @@ -179,7 +179,7 @@ public static void beginSheetModalForWindow(NSObject id, NSWindow window, long h * Custom message that will be sent when setTheme is called for example from Platform UI code. */ public static final long sel_appAppearanceChanged = OS.sel_registerName("appAppearanceChanged"); - + /** * Experimental API for dark theme. *

@@ -194,7 +194,7 @@ public static void beginSheetModalForWindow(NSObject id, NSWindow window, long h * On GTK, behavior may be different as the boolean flag doesn't force dark * theme instead it specify that dark theme is preferred. *

- * + * * @param isDarkTheme true for dark theme */ public static void setTheme(boolean isDarkTheme) { @@ -2216,6 +2216,7 @@ public static Selector getSelector (long value) { public static final int NSEventTypeMagnify = 30; public static final int NSEventTypeRotate = 18; public static final int NSEventTypeSwipe = 31; +public static final int NSFileHandlingPanelCancelButton = 0; public static final int NSFileHandlingPanelOKButton = 1; public static final int NSFlagsChanged = 12; public static final int NSFocusRingTypeNone = 1; diff --git a/bundles/org.eclipse.swt/Eclipse SWT PI/win32/org/eclipse/swt/internal/win32/OS.java b/bundles/org.eclipse.swt/Eclipse SWT PI/win32/org/eclipse/swt/internal/win32/OS.java index fd5606d9b4e..c3cfd904f28 100644 --- a/bundles/org.eclipse.swt/Eclipse SWT PI/win32/org/eclipse/swt/internal/win32/OS.java +++ b/bundles/org.eclipse.swt/Eclipse SWT PI/win32/org/eclipse/swt/internal/win32/OS.java @@ -452,6 +452,7 @@ public class OS extends C { public static final int EP_EDITTEXT = 1; public static final int ERROR_FILE_NOT_FOUND = 0x2; public static final int ERROR_NO_MORE_ITEMS = 0x103; + public static final int ERROR_CANCELED = 0x4C7; public static final int ESB_DISABLE_BOTH = 0x3; public static final int ESB_ENABLE_BOTH = 0x0; public static final int ES_AUTOHSCROLL = 0x80; diff --git a/bundles/org.eclipse.swt/Eclipse SWT/cocoa/org/eclipse/swt/widgets/FileDialog.java b/bundles/org.eclipse.swt/Eclipse SWT/cocoa/org/eclipse/swt/widgets/FileDialog.java index 33f5fc3f2f5..310b753bb2f 100644 --- a/bundles/org.eclipse.swt/Eclipse SWT/cocoa/org/eclipse/swt/widgets/FileDialog.java +++ b/bundles/org.eclipse.swt/Eclipse SWT/cocoa/org/eclipse/swt/widgets/FileDialog.java @@ -58,6 +58,7 @@ public class FileDialog extends Dialog { long methodImpl_overwriteExistingFileCheck = 0; long method_performKeyEquivalent = 0; long methodImpl_performKeyEquivalent = 0; + boolean canceled; static final char EXTENSION_SEPARATOR = ';'; private String selectedExtension; boolean overwrite = (OS.VERSION >= OS.VERSION(10, 15, 0)) ? true : false; @@ -333,6 +334,7 @@ void handleResponse (long response) { } } } + canceled = response == OS.NSFileHandlingPanelCancelButton; releaseHandles(); } @@ -446,6 +448,14 @@ public String open () { return fullPath; } +/** + * {@return whether the dialog has been canceled when last opened or has not been opened at all} + * @since 3.125 + */ +public boolean wasCanceled() { + return canceled; +} + long panel_shouldEnableURL (long id, long sel, long arg0, long arg1) { if ((style & SWT.SAVE) != 0) { /* All filenames are always disabled in the NSSavePanel, so return from here. */ diff --git a/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/FileDialog.java b/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/FileDialog.java index ef7f487dca3..fb872f4e66e 100644 --- a/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/FileDialog.java +++ b/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/FileDialog.java @@ -53,6 +53,7 @@ public class FileDialog extends Dialog { boolean overwrite = false; boolean uriMode; long handle; + boolean canceled; static final char SEPARATOR = File.separatorChar; static final char EXTENSION_SEPARATOR = ';'; static final char FILE_EXTENSION_SEPARATOR = '.'; @@ -374,6 +375,7 @@ String openNativeChooserDialog () { display.externalEventLoop = false; display.sendPostExternalEventDispatchEvent (); } + canceled = response == GTK.GTK_RESPONSE_CANCEL; if ((style & SWT.RIGHT_TO_LEFT) != 0) { OS.g_signal_remove_emission_hook (signalId, hookId); @@ -385,6 +387,14 @@ String openNativeChooserDialog () { return answer; } +/** + * {@return whether the dialog has been canceled when last opened or has not been opened at all} + * @since 3.125 + */ +public boolean wasCanceled() { + return canceled; +} + void presetChooserDialog () { /* MULTI is only valid if the native dialog's action is Open */ if ((style & (SWT.SAVE | SWT.MULTI)) == SWT.MULTI) { diff --git a/bundles/org.eclipse.swt/Eclipse SWT/win32/org/eclipse/swt/widgets/FileDialog.java b/bundles/org.eclipse.swt/Eclipse SWT/win32/org/eclipse/swt/widgets/FileDialog.java index c09ef6e4471..c49e759ba17 100644 --- a/bundles/org.eclipse.swt/Eclipse SWT/win32/org/eclipse/swt/widgets/FileDialog.java +++ b/bundles/org.eclipse.swt/Eclipse SWT/win32/org/eclipse/swt/widgets/FileDialog.java @@ -46,6 +46,7 @@ public class FileDialog extends Dialog { String filterPath = "", fileName = ""; int filterIndex = 0; boolean overwrite = false; + boolean canceled; static final String DEFAULT_FILTER = "*.*"; static final String LONG_PATH_PREFIX = "\\\\?\\"; @@ -322,6 +323,7 @@ public String open () { display.externalEventLoop = true; display.sendPreExternalEventDispatchEvent(); hr = fileDialog.Show(parent.handle); + canceled = hr == OS.HRESULT_FROM_WIN32(OS.ERROR_CANCELED); display.externalEventLoop = false; display.sendPostExternalEventDispatchEvent(); @@ -389,6 +391,14 @@ public String open () { return fullPath; } +/** + * {@return whether the dialog has been canceled when last opened or has not been opened at all} + * @since 3.125 + */ +public boolean wasCanceled() { + return canceled; +} + /** * Set the initial filename which the dialog will * select by default when opened to the argument,