X-Git-Url: http://review.tizen.org/git/?a=blobdiff_plain;f=gio%2Fgwin32appinfo.c;h=f1697c8a19c9cdac08dd9591fb8d566a1678f82c;hb=f14a66e3df9e5e3f0f170b68e976011c80ffc041;hp=704181242a3a96ff4328bd52861749f2ad4be220;hpb=a2ca589703273fca80cb126430a8b058aba3eb52;p=platform%2Fupstream%2Fglib.git diff --git a/gio/gwin32appinfo.c b/gio/gwin32appinfo.c index 7041812..f1697c8 100644 --- a/gio/gwin32appinfo.c +++ b/gio/gwin32appinfo.c @@ -13,27 +13,26 @@ * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General - * Public License along with this library; if not, write to the - * Free Software Foundation, Inc., 59 Temple Place, Suite 330, - * Boston, MA 02111-1307, USA. + * Public License along with this library; if not, see . * * Author: Alexander Larsson */ -#include +#include "config.h" #include -#include "gcontenttypeprivate.h" +#include "gcontenttype.h" #include "gwin32appinfo.h" +#include "gappinfo.h" #include "gioerror.h" +#include "gfile.h" #include #include "glibintl.h" #include #include -#include "gioalias.h" #ifndef ASSOCF_INIT_BYEXENAME #define ASSOCF_INIT_BYEXENAME 0x00000002 @@ -45,6 +44,9 @@ #define REAL_ASSOCSTR_FRIENDLYDOCNAME 3 #define REAL_ASSOCSTR_FRIENDLYAPPNAME 4 +#ifndef AssocQueryString +#pragma message("AssocQueryString not available with SDK used") +#endif static void g_win32_app_info_iface_init (GAppInfoIface *iface); @@ -75,9 +77,8 @@ g_win32_app_info_finalize (GObject *object) g_free (info->id_utf8); g_free (info->name); g_free (info->executable); - - if (G_OBJECT_CLASS (g_win32_app_info_parent_class)->finalize) - (*G_OBJECT_CLASS (g_win32_app_info_parent_class)->finalize) (object); + + G_OBJECT_CLASS (g_win32_app_info_parent_class)->finalize (object); } static void @@ -97,7 +98,9 @@ static GAppInfo * g_desktop_app_info_new_from_id (wchar_t *id /* takes ownership */, gboolean id_is_exename) { +#ifdef AssocQueryString ASSOCF flags; +#endif wchar_t buffer[1024]; DWORD buffer_size; GWin32AppInfo *info; @@ -108,6 +111,7 @@ g_desktop_app_info_new_from_id (wchar_t *id /* takes ownership */, info->id_utf8 = g_utf16_to_utf8 (id, -1, NULL, NULL, NULL); info->id_is_exename = id_is_exename; +#ifdef AssocQueryString flags = 0; if (id_is_exename) flags |= ASSOCF_INIT_BYEXENAME; @@ -129,6 +133,7 @@ g_desktop_app_info_new_from_id (wchar_t *id /* takes ownership */, buffer, &buffer_size) == S_OK) info->name = g_utf16_to_utf8 (buffer, -1, NULL, NULL, NULL); +#endif if (info->name == NULL) { @@ -139,6 +144,7 @@ g_desktop_app_info_new_from_id (wchar_t *id /* takes ownership */, info->name = g_strdup (info->id_utf8); } +#ifdef AssocQueryString if (AssocQueryKeyW(flags, ASSOCKEY_APP, info->id, @@ -150,6 +156,7 @@ g_desktop_app_info_new_from_id (wchar_t *id /* takes ownership */, info->no_open_with = TRUE; RegCloseKey (app_key); } +#endif return G_APP_INFO (info); } @@ -229,7 +236,7 @@ g_win32_app_info_get_executable (GAppInfo *appinfo) return info->executable; } -static const char * +static GIcon * g_win32_app_info_get_icon (GAppInfo *appinfo) { /* GWin32AppInfo *info = G_WIN32_APP_INFO (appinfo); */ @@ -239,19 +246,21 @@ g_win32_app_info_get_icon (GAppInfo *appinfo) } static gboolean -g_win32_app_info_launch (GAppInfo *appinfo, - GList *files, - GAppLaunchContext *launch_context, - GError **error) +g_win32_app_info_launch_locations (GAppInfo *appinfo, + GList *locations, + GAppLaunchContext *launch_context, + GError **error) { GWin32AppInfo *info = G_WIN32_APP_INFO (appinfo); +#ifdef AssocQueryString ASSOCF flags; +#endif HKEY class_key; SHELLEXECUTEINFOW exec_info = {0}; GList *l; /* TODO: What might startup_id mean on win32? */ - +#ifdef AssocQueryString flags = 0; if (info->id_is_exename) flags |= ASSOCF_INIT_BYEXENAME; @@ -262,50 +271,44 @@ g_win32_app_info_launch (GAppInfo *appinfo, NULL, &class_key) != S_OK) { - g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, _("Can't find application")); + g_set_error_literal (error, G_IO_ERROR, G_IO_ERROR_FAILED, _("Can't find application")); return FALSE; } +#endif - for (l = file; l != NULL; l = l->next) - { - char *path = g_file_get_path (l->data); - wchar_t *wfilename = g_utf8_to_utf16 (path, -1, NULL, NULL, NULL); + /* FIXME: Need to do something with + * g_app_launch_context_get_environment()... ShellExecuteExW() + * doesn't have any way to pass an environment though. We need to + * either (a) update environment, ShellExecuteExW(), revert + * environment; or (b) find an API to figure out what app + * ShellExecuteExW() would launch, and then use g_spawn_async() + * instead. + */ - g_free (path); + for (l = locations; l != NULL; l = l->next) + { + wchar_t *wloc = g_utf8_to_utf16 (l->data, -1, NULL, NULL, NULL); memset (&exec_info, 0, sizeof (exec_info)); exec_info.cbSize = sizeof (exec_info); exec_info.fMask = SEE_MASK_FLAG_DDEWAIT | SEE_MASK_CLASSKEY; - exec_info.lpFile = wfilename; + exec_info.lpFile = wloc; exec_info.nShow = SW_SHOWNORMAL; exec_info.hkeyClass = class_key; - if (!ShellExecuteExW(&exec_info)) + if (!ShellExecuteExW (&exec_info)) { - DWORD last_error; - LPVOID message; - char *message_utf8; - - last_error = GetLastError (); - FormatMessage (FORMAT_MESSAGE_ALLOCATE_BUFFER | - FORMAT_MESSAGE_FROM_SYSTEM, - NULL, - last_error, - MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), - (LPTSTR) &message, - 0, NULL ); - - message_utf8 = g_utf16_to_utf8 (message, -1, NULL, NULL, NULL); + char *message_utf8 = g_win32_error_message (GetLastError ()); + g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, _("Error launching application: %s"), message_utf8); g_free (message_utf8); - LocalFree (message); - g_free (wfilename); + g_free (wloc); RegCloseKey (class_key); return FALSE; } - g_free (wfilename); + g_free (wloc); } RegCloseKey (class_key); @@ -316,7 +319,32 @@ g_win32_app_info_launch (GAppInfo *appinfo, static gboolean g_win32_app_info_supports_uris (GAppInfo *appinfo) { - return FALSE; + /* TODO: is there some way to determine this on windows? */ + return TRUE; +} + +static gboolean +g_win32_app_info_supports_files (GAppInfo *appinfo) +{ + return TRUE; +} + +static gboolean +g_win32_app_info_launch (GAppInfo *appinfo, + GList *files, + GAppLaunchContext *launch_context, + GError **error) +{ + gboolean success; + GList *paths = g_list_copy_deep (files, (GCopyFunc) g_file_get_path, + NULL); + + success = g_win32_app_info_launch_locations (appinfo, paths, + launch_context, error); + + g_list_free_full (paths, g_free); + + return success; } static gboolean @@ -325,15 +353,12 @@ g_win32_app_info_launch_uris (GAppInfo *appinfo, GAppLaunchContext *launch_context, GError **error) { - g_set_error (error, G_IO_ERROR, - G_IO_ERROR_NOT_SUPPORTED, - _("URIs not supported")); - return FALSE; + return g_win32_app_info_launch_locations (appinfo, uris, + launch_context, error); } static gboolean -g_win32_app_info_should_show (GAppInfo *appinfo, - const char *win32_env) +g_win32_app_info_should_show (GAppInfo *appinfo) { GWin32AppInfo *info = G_WIN32_APP_INFO (appinfo); @@ -348,9 +373,9 @@ g_win32_app_info_set_as_default_for_type (GAppInfo *appinfo, const char *content_type, GError **error) { - g_set_error (error, G_IO_ERROR, - G_IO_ERROR_NOT_SUPPORTED, - _("association changes not supported on win32")); + g_set_error_literal (error, G_IO_ERROR, + G_IO_ERROR_NOT_SUPPORTED, + _("association changes not supported on win32")); return FALSE; } @@ -360,9 +385,9 @@ g_app_info_create_from_commandline (const char *commandline, GAppInfoCreateFlags flags, GError **error) { - g_set_error (error, G_IO_ERROR, - G_IO_ERROR_NOT_SUPPORTED, - _("Association creation not supported on win32")); + g_set_error_literal (error, G_IO_ERROR, + G_IO_ERROR_NOT_SUPPORTED, + _("Association creation not supported on win32")); return NULL; } @@ -379,6 +404,7 @@ g_win32_app_info_iface_init (GAppInfoIface *iface) iface->get_icon = g_win32_app_info_get_icon; iface->launch = g_win32_app_info_launch; iface->supports_uris = g_win32_app_info_supports_uris; + iface->supports_files = g_win32_app_info_supports_files; iface->launch_uris = g_win32_app_info_launch_uris; iface->should_show = g_win32_app_info_should_show; iface->set_as_default_for_type = g_win32_app_info_set_as_default_for_type; @@ -582,17 +608,44 @@ g_app_info_get_all_for_type (const char *content_type) return g_list_reverse (infos); } -GAppInfo * -g_app_info_get_default_for_type (const char *content_type, - gboolean must_support_uris) +GList * +g_app_info_get_recommended_for_type (const char *content_type) +{ + /* FIXME: this should generate a list of applications that are registered + * as direct handlers for the given content type, without using MIME subclassing. + * See g_app_info_get_recommended_for_type() in gdesktopappinfo.c for a reference + * UNIX implementation. + */ + return g_app_info_get_all_for_type (content_type); +} + +GList * +g_app_info_get_fallback_for_type (const char *content_type) +{ + /* FIXME: this should generate a list of applications that are registered + * as handlers for a superclass of the given content type, but are not + * direct handlers for the content type itself. See g_app_info_get_fallback_for_type() + * in gdesktopappinfo.c for a reference UNIX implementation. + */ + return g_app_info_get_all_for_type (content_type); +} + +/* + * The windows api (AssocQueryString) doesn't distinguish between uri schemes + * and file type extensions here, so we use the same implementation for both + * g_app_info_get_default_for_type and g_app_info_get_default_for_uri_scheme + */ +static GAppInfo * +get_default_for_association (const char *association) { wchar_t *wtype; wchar_t buffer[1024]; DWORD buffer_size; - wtype = g_utf8_to_utf16 (content_type, -1, NULL, NULL, NULL); + wtype = g_utf8_to_utf16 (association, -1, NULL, NULL, NULL); /* Verify that we have some sort of app registered for this type */ +#ifdef AssocQueryString buffer_size = 1024; if (AssocQueryStringW (0, REAL_ASSOCSTR_COMMAND, @@ -602,16 +655,23 @@ g_app_info_get_default_for_type (const char *content_type, &buffer_size) == S_OK) /* Takes ownership of wtype */ return g_desktop_app_info_new_from_id (wtype, FALSE); +#endif g_free (wtype); return NULL; } GAppInfo * +g_app_info_get_default_for_type (const char *content_type, + gboolean must_support_uris) +{ + return get_default_for_association (content_type); +} + +GAppInfo * g_app_info_get_default_for_uri_scheme (const char *uri_scheme) { - /* TODO: Implement */ - return NULL; + return get_default_for_association (uri_scheme); } GList * @@ -653,3 +713,9 @@ g_app_info_get_all (void) return g_list_reverse (infos); } + +void +g_app_info_reset_type_associations (const char *content_type) +{ + /* nothing to do */ +}