forked from osmocom/wireshark
Move a bunch of common code in the file chooser dialog loops into a
routine to run a file chooser dialog. On Windows, add to that code to resolve shell links ("shortcuts"), adopted from the Sylpheed mail reader. (That code requires a pile of OLE stuff, so link with the OLE library.) Make it a bit easier to configure ui/gtk/capture_file_dlg.c to use GTK+ dialogs on Windows, but continue to default to using the Win32 dialogs, at least for now. svn path=/trunk/; revision=43439
This commit is contained in:
parent
a0148735c1
commit
204ea39c5d
|
@ -73,7 +73,7 @@ dumpcap_OBJECTS = $(dumpcap_SOURCES:.c=.obj)
|
|||
randpkt_OBJECTS = $(randpkt_SOURCES:.c=.obj)
|
||||
|
||||
wireshark_LIBS= wiretap\wiretap-$(WTAP_VERSION).lib \
|
||||
wsock32.lib user32.lib shell32.lib comctl32.lib \
|
||||
wsock32.lib user32.lib shell32.lib comctl32.lib ole32.lib \
|
||||
$(GTHREAD_LIBS) \
|
||||
$(HHC_LIBS) \
|
||||
wsutil\libwsutil.lib \
|
||||
|
|
|
@ -47,7 +47,6 @@
|
|||
#include <wsutil/file_util.h>
|
||||
|
||||
#include "ui/alert_box.h"
|
||||
#include "ui/last_open_dir.h"
|
||||
#include "ui/recent.h"
|
||||
#include "ui/simple_dialog.h"
|
||||
#include "ui/ui_util.h"
|
||||
|
@ -70,7 +69,11 @@
|
|||
#include "ui/gtk/range_utils.h"
|
||||
#include "ui/gtk/filter_autocomplete.h"
|
||||
|
||||
#if _WIN32
|
||||
#ifdef _WIN32
|
||||
#define USE_WIN32_FILE_DIALOGS
|
||||
#endif
|
||||
|
||||
#ifdef USE_WIN32_FILE_DIALOGS
|
||||
#include <gdk/gdkwin32.h>
|
||||
#include <windows.h>
|
||||
#include "ui/win32/file_dlg_win32.h"
|
||||
|
@ -422,9 +425,9 @@ preview_new(void)
|
|||
static void
|
||||
file_open_cmd(GtkWidget *w)
|
||||
{
|
||||
#if _WIN32
|
||||
#ifdef USE_WIN32_FILE_DIALOGS
|
||||
win32_open_file(GDK_WINDOW_HWND(gtk_widget_get_window(top_level)));
|
||||
#else /* _WIN32 */
|
||||
#else /* USE_WIN32_FILE_DIALOGS */
|
||||
GtkWidget *file_open_w;
|
||||
GtkWidget *main_hb, *main_vb, *filter_hbox, *filter_bt, *filter_te,
|
||||
*m_resolv_cb, *n_resolv_cb, *t_resolv_cb, *prev;
|
||||
|
@ -541,26 +544,12 @@ file_open_cmd(GtkWidget *w)
|
|||
* Loop until the user either selects a file or gives up.
|
||||
*/
|
||||
for (;;) {
|
||||
if (gtk_dialog_run(GTK_DIALOG(file_open_w)) != GTK_RESPONSE_ACCEPT) {
|
||||
/* They clicked "Cancel" or closed the dialog or.... */
|
||||
window_destroy(file_open_w);
|
||||
cf_name = file_selection_run(file_open_w);
|
||||
if (cf_name == NULL) {
|
||||
/* User cancelled or closed the dialog. */
|
||||
return;
|
||||
}
|
||||
|
||||
cf_name = gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(file_open_w));
|
||||
|
||||
/* Perhaps the user specified a directory instead of a file.
|
||||
Check whether they did. */
|
||||
if (test_for_directory(cf_name) == EISDIR) {
|
||||
/* It's a directory - set the file selection box to display that
|
||||
directory, and go back and re-run it; don't try to open the
|
||||
directory as a capture file. */
|
||||
set_last_open_dir(cf_name);
|
||||
g_free(cf_name);
|
||||
file_selection_set_current_folder(file_open_w, get_last_open_dir());
|
||||
continue;
|
||||
}
|
||||
|
||||
/* Get the specified read filter and try to compile it. */
|
||||
rfilter = gtk_entry_get_text(GTK_ENTRY(filter_te));
|
||||
if (!dfilter_compile(rfilter, &rfcode)) {
|
||||
|
@ -633,7 +622,7 @@ file_open_cmd(GtkWidget *w)
|
|||
g_free(cf_name);
|
||||
return;
|
||||
}
|
||||
#endif /* _WIN32 */
|
||||
#endif /* USE_WIN32_FILE_DIALOGS */
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -648,11 +637,11 @@ file_open_cmd_cb(GtkWidget *widget, gpointer data _U_) {
|
|||
static void
|
||||
file_merge_cmd(GtkWidget *w)
|
||||
{
|
||||
#if _WIN32
|
||||
#ifdef USE_WIN32_FILE_DIALOGS
|
||||
win32_merge_file(GDK_WINDOW_HWND(gtk_widget_get_window(top_level)));
|
||||
new_packet_list_freeze();
|
||||
new_packet_list_thaw();
|
||||
#else /* _WIN32 */
|
||||
#else /* USE_WIN32_FILE_DIALOGS */
|
||||
GtkWidget *file_merge_w;
|
||||
GtkWidget *main_hb, *main_vb, *ft_hb, *ft_lb, *ft_combo_box, *filter_hbox,
|
||||
*filter_bt, *filter_te, *prepend_rb, *chrono_rb,
|
||||
|
@ -794,26 +783,12 @@ file_merge_cmd(GtkWidget *w)
|
|||
* Loop until the user either selects a file or gives up.
|
||||
*/
|
||||
for (;;) {
|
||||
if (gtk_dialog_run(GTK_DIALOG(file_merge_w)) != GTK_RESPONSE_ACCEPT) {
|
||||
/* They clicked "Cancel" or closed the dialog or.... */
|
||||
window_destroy(file_merge_w);
|
||||
cf_name = file_selection_run(file_merge_w);
|
||||
if (cf_name == NULL) {
|
||||
/* User cancelled or closed the dialog. */
|
||||
return;
|
||||
}
|
||||
|
||||
cf_name = gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(file_merge_w));
|
||||
|
||||
/* Perhaps the user specified a directory instead of a file.
|
||||
Check whether they did. */
|
||||
if (test_for_directory(cf_name) == EISDIR) {
|
||||
/* It's a directory - set the file selection box to display that
|
||||
directory, and go back and re-run it; don't try to open the
|
||||
directory as a capture file. */
|
||||
set_last_open_dir(cf_name);
|
||||
g_free(cf_name);
|
||||
file_selection_set_current_folder(file_merge_w, get_last_open_dir());
|
||||
continue;
|
||||
}
|
||||
|
||||
/* Get the specified read filter and try to compile it. */
|
||||
rfilter = gtk_entry_get_text(GTK_ENTRY(filter_te));
|
||||
if (!dfilter_compile(rfilter, &rfcode)) {
|
||||
|
@ -903,7 +878,7 @@ file_merge_cmd(GtkWidget *w)
|
|||
set_last_open_dir(s);
|
||||
return;
|
||||
}
|
||||
#endif /* _WIN32 */
|
||||
#endif /* USE_WIN32_FILE_DIALOGS */
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -1594,9 +1569,9 @@ static void
|
|||
do_file_save_as(capture_file *cf, gboolean must_support_comments,
|
||||
gboolean dont_reopen)
|
||||
{
|
||||
#if _WIN32
|
||||
#ifdef USE_WIN32_FILE_DIALOGS
|
||||
win32_save_as_file(GDK_WINDOW_HWND(gtk_widget_get_window(top_level)));
|
||||
#else /* _WIN32 */
|
||||
#else /* USE_WIN32_FILE_DIALOGS */
|
||||
GtkWidget *file_save_as_w;
|
||||
GtkWidget *main_vb, *ft_hb, *ft_lb, *ft_combo_box, *compressed_cb;
|
||||
char *cf_name;
|
||||
|
@ -1648,26 +1623,12 @@ do_file_save_as(capture_file *cf, gboolean must_support_comments,
|
|||
* Loop until the user either selects a file or gives up.
|
||||
*/
|
||||
for (;;) {
|
||||
if (gtk_dialog_run(GTK_DIALOG(file_save_as_w)) != GTK_RESPONSE_ACCEPT) {
|
||||
/* They clicked "Cancel" or closed the dialog or.... */
|
||||
window_destroy(file_save_as_w);
|
||||
cf_name = file_selection_run(file_save_as_w);
|
||||
if (cf_name == NULL) {
|
||||
/* User cancelled or closed the dialog. */
|
||||
return;
|
||||
}
|
||||
|
||||
cf_name = gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(file_save_as_w));
|
||||
|
||||
/* Perhaps the user specified a directory instead of a file.
|
||||
Check whether they did. */
|
||||
if (test_for_directory(cf_name) == EISDIR) {
|
||||
/* It's a directory - set the file selection box to display that
|
||||
directory, and go back and re-run it; don't try to write onto
|
||||
the directory (which won't work anyway). */
|
||||
set_last_open_dir(cf_name);
|
||||
g_free(cf_name);
|
||||
file_selection_set_current_folder(file_save_as_w, get_last_open_dir());
|
||||
continue;
|
||||
}
|
||||
|
||||
/* If the file has comments, does the format the user selected
|
||||
support them? If not, ask the user whether they want to
|
||||
discard the comments or choose a different format. */
|
||||
|
@ -1704,6 +1665,7 @@ do_file_save_as(capture_file *cf, gboolean must_support_comments,
|
|||
return;
|
||||
}
|
||||
|
||||
#ifndef _WIN32
|
||||
/* If the file exists and it's user-immutable or not writable,
|
||||
ask the user whether they want to override that. */
|
||||
if (!file_target_unwritable_ui(file_save_as_w, cf_name)) {
|
||||
|
@ -1711,6 +1673,7 @@ do_file_save_as(capture_file *cf, gboolean must_support_comments,
|
|||
g_free(cf_name);
|
||||
continue;
|
||||
}
|
||||
#endif
|
||||
|
||||
/* Attempt to save the file */
|
||||
g_free(cf_name);
|
||||
|
@ -1733,7 +1696,7 @@ do_file_save_as(capture_file *cf, gboolean must_support_comments,
|
|||
return;
|
||||
}
|
||||
}
|
||||
#endif /* _WIN32 */
|
||||
#endif /* USE_WIN32_FILE_DIALOGS */
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -1806,9 +1769,9 @@ file_save_as_cb(GtkWidget *fs, gboolean discard_comments,
|
|||
void
|
||||
file_export_specified_packets_cmd_cb(GtkWidget *widget _U_, gpointer data _U_)
|
||||
{
|
||||
#if _WIN32
|
||||
#ifdef USE_WIN32_FILE_DIALOGS
|
||||
win32_export_specified_packets_file(GDK_WINDOW_HWND(gtk_widget_get_window(top_level)));
|
||||
#else /* _WIN32 */
|
||||
#else /* USE_WIN32_FILE_DIALOGS */
|
||||
GtkWidget *file_export_specified_packets_w;
|
||||
GtkWidget *main_vb, *ft_hb, *ft_lb, *ft_combo_box, *range_fr, *range_tb,
|
||||
*compressed_cb;
|
||||
|
@ -1881,26 +1844,12 @@ file_export_specified_packets_cmd_cb(GtkWidget *widget _U_, gpointer data _U_)
|
|||
* Loop until the user either selects a file or gives up.
|
||||
*/
|
||||
for (;;) {
|
||||
if (gtk_dialog_run(GTK_DIALOG(file_export_specified_packets_w)) != GTK_RESPONSE_ACCEPT) {
|
||||
/* They clicked "Cancel" or closed the dialog or.... */
|
||||
window_destroy(file_export_specified_packets_w);
|
||||
cf_name = file_selection_run(file_export_specified_packets_w);
|
||||
if (cf_name == NULL) {
|
||||
/* User cancelled or closed the dialog. */
|
||||
return;
|
||||
}
|
||||
|
||||
cf_name = gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(file_export_specified_packets_w));
|
||||
|
||||
/* Perhaps the user specified a directory instead of a file.
|
||||
Check whether they did. */
|
||||
if (test_for_directory(cf_name) == EISDIR) {
|
||||
/* It's a directory - set the file selection box to display that
|
||||
directory, and go back and re-run it; don't try to write onto
|
||||
the directory (which won't work anyway). */
|
||||
set_last_open_dir(cf_name);
|
||||
g_free(cf_name);
|
||||
file_selection_set_current_folder(file_export_specified_packets_w, get_last_open_dir());
|
||||
continue;
|
||||
}
|
||||
|
||||
/* Check whether the range is valid. */
|
||||
if (!range_check_validity_modal(file_export_specified_packets_w, &range)) {
|
||||
/* The range isn't valid; the user was told that, and dismissed
|
||||
|
@ -1935,6 +1884,7 @@ file_export_specified_packets_cmd_cb(GtkWidget *widget _U_, gpointer data _U_)
|
|||
continue;
|
||||
}
|
||||
|
||||
#ifndef _WIN32
|
||||
/* If the file exists and it's user-immutable or not writable,
|
||||
ask the user whether they want to override that. */
|
||||
if (!file_target_unwritable_ui(file_export_specified_packets_w, cf_name)) {
|
||||
|
@ -1942,6 +1892,7 @@ file_export_specified_packets_cmd_cb(GtkWidget *widget _U_, gpointer data _U_)
|
|||
g_free(cf_name);
|
||||
continue;
|
||||
}
|
||||
#endif
|
||||
|
||||
/* attempt to export the packets */
|
||||
g_free(cf_name);
|
||||
|
@ -1961,7 +1912,7 @@ file_export_specified_packets_cmd_cb(GtkWidget *widget _U_, gpointer data _U_)
|
|||
return;
|
||||
}
|
||||
}
|
||||
#endif /* _WIN32 */
|
||||
#endif /* USE_WIN32_FILE_DIALOGS */
|
||||
}
|
||||
|
||||
/* all tests ok, we only have to write out the packets */
|
||||
|
@ -2062,9 +2013,9 @@ color_global_cb(GtkWidget *widget _U_, gpointer data)
|
|||
void
|
||||
file_color_import_cmd_cb(GtkWidget *color_filters, gpointer filter_list _U_)
|
||||
{
|
||||
#if _WIN32
|
||||
#ifdef USE_WIN32_FILE_DIALOGS
|
||||
win32_import_color_file(GDK_WINDOW_HWND(gtk_widget_get_window(top_level)), color_filters);
|
||||
#else /* _WIN32 */
|
||||
#else /* USE_WIN32_FILE_DIALOGS */
|
||||
GtkWidget *main_vb, *cfglobal_but;
|
||||
gchar *cf_name, *s;
|
||||
|
||||
|
@ -2090,26 +2041,12 @@ file_color_import_cmd_cb(GtkWidget *color_filters, gpointer filter_list _U_)
|
|||
* Loop until the user either selects a file or gives up.
|
||||
*/
|
||||
for (;;) {
|
||||
if (gtk_dialog_run(GTK_DIALOG(file_color_import_w)) != GTK_RESPONSE_ACCEPT) {
|
||||
/* They clicked "Cancel" or closed the dialog or.... */
|
||||
window_destroy(file_color_import_w);
|
||||
cf_name = file_selection_run(file_color_import_w);
|
||||
if (cf_name == NULL) {
|
||||
/* User cancelled or closed the dialog. */
|
||||
return;
|
||||
}
|
||||
|
||||
cf_name = gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(file_color_import_w));
|
||||
|
||||
/* Perhaps the user specified a directory instead of a file.
|
||||
Check whether they did. */
|
||||
if (test_for_directory(cf_name) == EISDIR) {
|
||||
/* It's a directory - set the file selection box to display that
|
||||
directory, and go back and re-run it; don't try to open the
|
||||
directory as a color filter file. */
|
||||
set_last_open_dir(cf_name);
|
||||
g_free(cf_name);
|
||||
file_selection_set_current_folder(file_color_import_w, get_last_open_dir());
|
||||
continue;
|
||||
}
|
||||
|
||||
/* Try to open the color filter file. */
|
||||
if (!color_filters_import(cf_name, color_filters)) {
|
||||
/* We couldn't open it; don't dismiss the open dialog box,
|
||||
|
@ -2132,7 +2069,7 @@ file_color_import_cmd_cb(GtkWidget *color_filters, gpointer filter_list _U_)
|
|||
g_free(cf_name);
|
||||
return;
|
||||
}
|
||||
#endif /* _WIN32 */
|
||||
#endif /* USE_WIN32_FILE_DIALOGS */
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -2167,9 +2104,9 @@ color_toggle_selected_cb(GtkWidget *widget, gpointer data _U_)
|
|||
void
|
||||
file_color_export_cmd_cb(GtkWidget *w _U_, gpointer filter_list)
|
||||
{
|
||||
#if _WIN32
|
||||
#if USE_WIN32_FILE_DIALOGS
|
||||
win32_export_color_file(GDK_WINDOW_HWND(gtk_widget_get_window(top_level)), filter_list);
|
||||
#else /* _WIN32 */
|
||||
#else /* USE_WIN32_FILE_DIALOGS */
|
||||
GtkWidget *file_color_export_w;
|
||||
GtkWidget *main_vb, *cfglobal_but;
|
||||
GtkWidget *cfselect_cb;
|
||||
|
@ -2207,26 +2144,13 @@ file_color_export_cmd_cb(GtkWidget *w _U_, gpointer filter_list)
|
|||
* Loop until the user either selects a file or gives up.
|
||||
*/
|
||||
for (;;) {
|
||||
if (gtk_dialog_run(GTK_DIALOG(file_color_export_w)) != GTK_RESPONSE_ACCEPT) {
|
||||
/* They clicked "Cancel" or closed the dialog or.... */
|
||||
window_destroy(file_color_export_w);
|
||||
cf_name = file_selection_run(file_color_export_w);
|
||||
if (cf_name == NULL) {
|
||||
/* User cancelled or closed the dialog. */
|
||||
return;
|
||||
}
|
||||
|
||||
cf_name = gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(file_color_export_w));
|
||||
|
||||
/* Perhaps the user specified a directory instead of a file.
|
||||
Check whether they did. */
|
||||
if (test_for_directory(cf_name) == EISDIR) {
|
||||
/* It's a directory - set the file selection box to display that
|
||||
directory, and go back and re-run it; don't try to write onto
|
||||
the directory (which wn't work anyway). */
|
||||
set_last_open_dir(cf_name);
|
||||
g_free(cf_name);
|
||||
file_selection_set_current_folder(file_color_export_w, get_last_open_dir());
|
||||
continue;
|
||||
}
|
||||
|
||||
#ifndef _WIN32
|
||||
/* If the file exists and it's user-immutable or not writable,
|
||||
ask the user whether they want to override that. */
|
||||
if (!file_target_unwritable_ui(file_color_export_w, cf_name)) {
|
||||
|
@ -2234,6 +2158,7 @@ file_color_export_cmd_cb(GtkWidget *w _U_, gpointer filter_list)
|
|||
g_free(cf_name);
|
||||
continue;
|
||||
}
|
||||
#endif
|
||||
|
||||
/* Write out the filters (all, or only the ones that are currently
|
||||
displayed or selected) to the file with the specified name. */
|
||||
|
@ -2253,5 +2178,5 @@ file_color_export_cmd_cb(GtkWidget *w _U_, gpointer filter_list)
|
|||
set_last_open_dir(dirname);
|
||||
g_free(cf_name);
|
||||
}
|
||||
#endif /* _WIN32 */
|
||||
#endif /* USE_WIN32_FILE_DIALOGS */
|
||||
}
|
||||
|
|
|
@ -22,6 +22,15 @@
|
|||
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
||||
*/
|
||||
|
||||
/*
|
||||
* Code to handle Windows shortcuts courtesy of:
|
||||
*
|
||||
* Sylpheed -- a GTK+ based, lightweight, and fast e-mail client
|
||||
* Copyright (C) 1999-2012 Hiroyuki Yamamoto
|
||||
*
|
||||
* licensed under the GPL2 or later.
|
||||
*/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
# include "config.h"
|
||||
#endif
|
||||
|
@ -30,12 +39,22 @@
|
|||
|
||||
#include <gtk/gtk.h>
|
||||
|
||||
#ifdef _WIN32
|
||||
# define COBJMACROS
|
||||
# include <windows.h>
|
||||
# include <objbase.h>
|
||||
# include <objidl.h>
|
||||
# include <shlobj.h>
|
||||
#endif
|
||||
|
||||
#include <wsutil/file_util.h>
|
||||
|
||||
#ifndef _WIN32
|
||||
#include <epan/filesystem.h>
|
||||
#endif
|
||||
|
||||
#include "ui/last_open_dir.h"
|
||||
|
||||
#include "ui/gtk/gtkglobals.h"
|
||||
#include "ui/gtk/gui_utils.h"
|
||||
#include "ui/gtk/file_dlg.h"
|
||||
|
@ -157,6 +176,110 @@ file_selection_set_extra_widget(GtkWidget *fs, GtkWidget *extra)
|
|||
gtk_file_chooser_set_extra_widget(GTK_FILE_CHOOSER(fs), extra);
|
||||
}
|
||||
|
||||
#ifdef _WIN32
|
||||
static gchar *filesel_get_link(const gchar *link_file)
|
||||
{
|
||||
WIN32_FIND_DATAW wfd;
|
||||
IShellLinkW *psl;
|
||||
IPersistFile *ppf;
|
||||
wchar_t *wlink_file;
|
||||
wchar_t wtarget[MAX_PATH];
|
||||
gchar *target = NULL;
|
||||
|
||||
wtarget[0] = 0L;
|
||||
|
||||
CoInitialize(NULL);
|
||||
if (S_OK == CoCreateInstance(&CLSID_ShellLink, NULL, CLSCTX_INPROC_SERVER,
|
||||
&IID_IShellLinkW, (void **)&psl)) {
|
||||
if (S_OK == IShellLinkW_QueryInterface(psl, &IID_IPersistFile,
|
||||
(void **)&ppf)) {
|
||||
wlink_file = g_utf8_to_utf16(link_file, -1, NULL, NULL, NULL);
|
||||
if (S_OK == IPersistFile_Load(ppf, wlink_file, STGM_READ)) {
|
||||
if (S_OK == IShellLinkW_GetPath(psl, wtarget, MAX_PATH, &wfd,
|
||||
SLGP_UNCPRIORITY)) {
|
||||
target = g_utf16_to_utf8(wtarget, -1, NULL, NULL, NULL);
|
||||
}
|
||||
}
|
||||
IPersistFile_Release(ppf);
|
||||
g_free(wlink_file);
|
||||
}
|
||||
IShellLinkW_Release(psl);
|
||||
}
|
||||
CoUninitialize();
|
||||
|
||||
return target;
|
||||
}
|
||||
#endif /* _WIN32 */
|
||||
|
||||
/* Run the dialog, and handle some common operations, such as, if the
|
||||
user selects a directory, browsing that directory, and handling
|
||||
shortcuts on Windows.
|
||||
|
||||
Returns NULL if the user decided not to open/write to a file,
|
||||
returns the pathname of the selected file if they selected a
|
||||
file. */
|
||||
gchar *
|
||||
file_selection_run(GtkWidget *fs)
|
||||
{
|
||||
gchar *cf_name;
|
||||
#ifdef _WIN32
|
||||
gchar *target;
|
||||
const gchar *ext;
|
||||
#endif
|
||||
|
||||
for (;;) {
|
||||
if (gtk_dialog_run(GTK_DIALOG(fs)) != GTK_RESPONSE_ACCEPT) {
|
||||
/* They clicked "Cancel" or closed the dialog or...;
|
||||
destroy the dialog and tell our caller the user decided
|
||||
not to do anything with the file. */
|
||||
window_destroy(fs);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
cf_name = gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(fs));
|
||||
|
||||
/* Perhaps the user specified a directory instead of a file.
|
||||
Check whether they did. */
|
||||
if (test_for_directory(cf_name) == EISDIR) {
|
||||
/* It's a directory - set the file selection box to display that
|
||||
directory, and go back and re-run it; don't try to open the
|
||||
directory as a file (you'll get crap if you get anything) or
|
||||
write to it (which won't work anyway). */
|
||||
set_last_open_dir(cf_name);
|
||||
g_free(cf_name);
|
||||
file_selection_set_current_folder(fs, get_last_open_dir());
|
||||
continue;
|
||||
}
|
||||
|
||||
#ifdef _WIN32
|
||||
/* Perhaps the user specified a "shortcut" instead of a file.
|
||||
Check whether they did. */
|
||||
if ((ext = strrchr(cf_name, '.')) && g_ascii_strcasecmp(ext, ".lnk") == 0) {
|
||||
/* It ends with ".lnk", so it might be a shortcut. */
|
||||
target = filesel_get_link(cf_name);
|
||||
if (target != NULL) {
|
||||
/* We resolved it, so it must've been a shortcut. */
|
||||
g_free(cf_name);
|
||||
if (test_for_directory(target)) {
|
||||
/* It's a shortcut that points to a directory; treat it the same
|
||||
way we treat a directory. */
|
||||
set_last_open_dir(target);
|
||||
g_free(target);
|
||||
file_selection_set_current_folder(fs, get_last_open_dir());
|
||||
continue;
|
||||
}
|
||||
/* It's a shortcut that points to a file; act as if the target
|
||||
is what's selected. */
|
||||
cf_name = target;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
break;
|
||||
}
|
||||
|
||||
return cf_name;
|
||||
}
|
||||
|
||||
#ifndef _WIN32
|
||||
/* If the specified file doesn't exist, return TRUE.
|
||||
If it exists and is neither user-immutable nor not writable, return
|
||||
|
|
|
@ -85,6 +85,15 @@ extern gboolean file_selection_set_current_folder(GtkWidget *fs, const gchar *fi
|
|||
*/
|
||||
extern void file_selection_set_extra_widget(GtkWidget *fs, GtkWidget *extra);
|
||||
|
||||
/** Run the dialog, and handle some common operations, such as, if the
|
||||
* user selects a directory, browsing that directory, and handling
|
||||
* shortcuts on Windows.
|
||||
* @param fs the file selection dialog from file_selection_new()
|
||||
* @return the pathname of the selected file if the user selected a
|
||||
* file, NULL if they cancelled or closed the dialog.
|
||||
*/
|
||||
extern gchar *file_selection_run(GtkWidget *fs);
|
||||
|
||||
#ifndef _WIN32
|
||||
/** If the specified file doesn't exist, return TRUE.
|
||||
* If it exists and is neither user-immutable nor not writable, return
|
||||
|
|
Loading…
Reference in New Issue