diff options
author | Alexander Larsson <alexl@redhat.com> | 2003-10-14 16:00:32 +0000 |
---|---|---|
committer | Alexander Larsson <alexl@src.gnome.org> | 2003-10-14 16:00:32 +0000 |
commit | f950720caa6d1ff3b805ab23a1267d0dcfd60282 (patch) | |
tree | 9cc2907667c53f86a1afb277509c010a191d97a9 /components | |
parent | b5fd55155ac4dea22949c5fd71525055166f4720 (diff) | |
download | nautilus-f950720caa6d1ff3b805ab23a1267d0dcfd60282.tar.gz |
Support for exif info.
2003-10-14 Alexander Larsson <alexl@redhat.com>
* acconfig.h:
* components/image_properties/Makefile.am:
* components/image_properties/nautilus-image-properties-view.c:
* configure.in:
Support for exif info.
Diffstat (limited to 'components')
-rw-r--r-- | components/image_properties/Makefile.am | 6 | ||||
-rw-r--r-- | components/image_properties/nautilus-image-properties-view.c | 229 |
2 files changed, 206 insertions, 29 deletions
diff --git a/components/image_properties/Makefile.am b/components/image_properties/Makefile.am index dd96e54b5..073497c55 100644 --- a/components/image_properties/Makefile.am +++ b/components/image_properties/Makefile.am @@ -11,7 +11,8 @@ INCLUDES = \ -I$(top_srcdir) \ -I$(top_builddir) \ $(DISABLE_DEPRECATED_CFLAGS) \ - $(COMPONENT_CFLAGS) + $(COMPONENT_CFLAGS) \ + $(EXIF_CFLAGS) bonobodir = $(libdir)/bonobo bonobo_LTLIBRARIES = libnautilus-image-properties-view.la @@ -23,7 +24,8 @@ libnautilus_image_properties_view_la_SOURCES = \ libnautilus_image_properties_view_la_LIBADD = \ $(top_builddir)/libnautilus/libnautilus.la \ - $(COMPONENT_LIBS) + $(COMPONENT_LIBS) \ + $(EXIF_LIBS) libnautilus_image_properties_view_la_LDFLAGS = -module -avoid-version -no-undefined diff --git a/components/image_properties/nautilus-image-properties-view.c b/components/image_properties/nautilus-image-properties-view.c index 92bdaea7b..21024ca37 100644 --- a/components/image_properties/nautilus-image-properties-view.c +++ b/components/image_properties/nautilus-image-properties-view.c @@ -32,6 +32,18 @@ #include <eel/eel-gnome-extensions.h> #include <string.h> +#ifdef HAVE_EXIF + #include <libexif/exif-data.h> + #include <libexif/exif-ifd.h> + #include <libexif/exif-loader.h> + #include <gtk/gtkliststore.h> + #include <gtk/gtktreestore.h> + #include <gtk/gtktreeview.h> + #include <gtk/gtkscrolledwindow.h> + #include <gtk/gtkcellrenderertext.h> + #include <eel/eel-vfs-extensions.h> +#endif + #define LOAD_BUFFER_SIZE 8192 struct NautilusImagePropertiesViewDetails { @@ -41,8 +53,22 @@ struct NautilusImagePropertiesViewDetails { GnomeVFSAsyncHandle *vfs_handle; GdkPixbufLoader *loader; gboolean got_size; + gboolean pixbuf_still_loading; char buffer[LOAD_BUFFER_SIZE]; + int width; + int height; +#ifdef HAVE_EXIF + ExifLoader *exifldr; +#endif /*HAVE_EXIF*/ +}; + +#ifdef HAVE_EXIF +struct ExifAttribute { + ExifTag tag; + char *value; + gboolean found; }; +#endif /*HAVE_EXIF*/ enum { PROP_URI, @@ -57,8 +83,9 @@ nautilus_image_properties_view_finalize (GObject *object) view = NAUTILUS_IMAGE_PROPERTIES_VIEW (object); - if (view->details->vfs_handle != NULL) + if (view->details->vfs_handle != NULL) { gnome_vfs_async_cancel (view->details->vfs_handle); + } view->details->vfs_handle = NULL; g_free (view->details->location); @@ -75,23 +102,162 @@ file_closed_callback (GnomeVFSAsyncHandle *handle, { } +#ifdef HAVE_EXIF +static char * +exif_string_to_utf8 (const char *exif_str) +{ + char *utf8_str; + + if (g_utf8_validate (exif_str, -1, NULL)) { + return g_strdup (exif_str); + } + + utf8_str = g_locale_to_utf8 (exif_str, -1, NULL, NULL, NULL); + if (utf8_str != NULL) { + return utf8_str; + } + + return eel_make_valid_utf8 (exif_str); +} + +static void +exif_content_callback (ExifContent *content, gpointer data) +{ + struct ExifAttribute *attribute; + + attribute = (struct ExifAttribute *)data; + if (attribute->found) { + return; + } + + attribute->value = g_strdup (exif_content_get_value (content, attribute->tag)); + if (attribute->value != NULL) { + attribute->found = TRUE; + } +} + +static char * +exifdata_get_tag_name_utf8 (ExifTag tag) +{ + return exif_string_to_utf8 (exif_tag_get_name (tag)); +} + +static char * +exifdata_get_tag_value_utf8 (ExifData *data, ExifTag tag) +{ + struct ExifAttribute attribute; + char *utf8_value; + + attribute.tag = tag; + attribute.value = NULL; + attribute.found = FALSE; + + exif_data_foreach_content (data, exif_content_callback, &attribute); + + if (attribute.found) { + utf8_value = exif_string_to_utf8 (attribute.value); + g_free (attribute.value); + } else { + utf8_value = NULL; + } + + return utf8_value; +} + +static void +append_tag_value_pair (GString *string, ExifData *data, ExifTag tag, gchar *description) +{ + char *utf_attribute; + char *utf_value; + + utf_attribute = exifdata_get_tag_name_utf8 (tag); + utf_value = exifdata_get_tag_value_utf8 (data, tag); + + if ((utf_attribute == NULL) || (utf_value == NULL)) { + g_free (utf_attribute); + g_free (utf_value); + return; + } + + g_string_append_printf (string, "<b>%s:</b> %s\n", (description != NULL) ? description : utf_attribute, utf_value); + + g_free (utf_attribute); + g_free (utf_value); +} + +static void +append_exifdata_string (ExifData *exifdata, GString *string) +{ + gchar *camera_make, *camera_model; + + if (exifdata->ifd[0] && exifdata->ifd[0]->count) { + camera_make = exifdata_get_tag_value_utf8 (exifdata, EXIF_TAG_MAKE); + camera_model = exifdata_get_tag_value_utf8 (exifdata, EXIF_TAG_MODEL); + if (camera_make != NULL) { + g_string_append_printf (string, "<b>%s:</b> %s %s\n", + _("Camera"), + camera_make, + camera_model); + } + append_tag_value_pair (string, exifdata, EXIF_TAG_DATE_TIME, _("Date Taken")); + append_tag_value_pair (string, exifdata, EXIF_TAG_EXPOSURE_TIME, _("Exposure Time")); + append_tag_value_pair (string, exifdata, EXIF_TAG_EXPOSURE_PROGRAM, _("Exposure Program")); + append_tag_value_pair (string, exifdata, EXIF_TAG_APERTURE_VALUE, _("Aperture Value")); + append_tag_value_pair (string, exifdata, EXIF_TAG_METERING_MODE, _("Metering Mode")); + append_tag_value_pair (string, exifdata, EXIF_TAG_FLASH,_("Flash Fired")); + append_tag_value_pair (string, exifdata, EXIF_TAG_FOCAL_LENGTH,_("Focal Lenght")); + append_tag_value_pair (string, exifdata, EXIF_TAG_SHUTTER_SPEED_VALUE, _("Shutter Speed")); + append_tag_value_pair (string, exifdata, EXIF_TAG_ISO_SPEED_RATINGS, _("ISO Speed Rating")); + append_tag_value_pair (string, exifdata, EXIF_TAG_SOFTWARE, _("Software")); + + } +} +#endif /*HAVE_EXIF*/ + static void load_finished (NautilusImagePropertiesView *view) { + GdkPixbufFormat *format; + char *name, *desc; + GString *str; + + if (view->details->got_size) { + str = g_string_new (NULL); + format = gdk_pixbuf_loader_get_format (view->details->loader); + + name = gdk_pixbuf_format_get_name (format); + desc = gdk_pixbuf_format_get_description (format); + g_string_append_printf (str, _("<b>Image Type:</b> %s (%s)\n<b>Resolution:</b> %dx%d pixels\n"), + name, desc, view->details->width, view->details->height); + g_free (name); + g_free (desc); + +#ifdef HAVE_EXIF + append_exifdata_string (exif_loader_get_data (view->details->exifldr), str); +#endif /*HAVE_EXIF*/ + + gtk_label_set_markup (GTK_LABEL (view->details->resolution), str->str); + g_string_free (str, TRUE); + } else { + gtk_label_set_text (GTK_LABEL (view->details->resolution), _("Failed to load image information")); + } + if (view->details->loader != NULL) { gdk_pixbuf_loader_close (view->details->loader, NULL); g_object_unref (view->details->loader); view->details->loader = NULL; } +#ifdef HAVE_EXIF + if (view->details->exifldr != NULL) { + exif_loader_unref (view->details->exifldr); + view->details->exifldr = NULL; + } +#endif /*HAVE_EXIF*/ if (view->details->vfs_handle != NULL) { gnome_vfs_async_close (view->details->vfs_handle, file_closed_callback, NULL); view->details->vfs_handle = NULL; } - - if (!view->details->got_size) { - gtk_label_set_text (GTK_LABEL (view->details->resolution), _("Failed to load image information")); - } } static void @@ -103,16 +269,31 @@ file_read_callback (GnomeVFSAsyncHandle *vfs_handle, gpointer callback_data) { NautilusImagePropertiesView *view; +#ifdef HAVE_EXIF + int exif_still_loading; +#endif view = NAUTILUS_IMAGE_PROPERTIES_VIEW (callback_data); if (result == GNOME_VFS_OK && bytes_read != 0) { - if (!gdk_pixbuf_loader_write (view->details->loader, - buffer, - bytes_read, - NULL)) { - result = GNOME_VFS_ERROR_WRONG_FORMAT; - } else if (!view->details->got_size) { +#ifdef HAVE_EXIF + exif_still_loading = exif_loader_write (view->details->exifldr, + buffer, + bytes_read); +#endif + if (view->details->pixbuf_still_loading) { + if (!gdk_pixbuf_loader_write (view->details->loader, + buffer, + bytes_read, + NULL)) { + view->details->pixbuf_still_loading = FALSE; + } + } + if (view->details->pixbuf_still_loading +#ifdef HAVE_EXIF + && (exif_still_loading == 1) +#endif + ) { gnome_vfs_async_read (view->details->vfs_handle, view->details->buffer, sizeof (view->details->buffer), @@ -121,7 +302,6 @@ file_read_callback (GnomeVFSAsyncHandle *vfs_handle, return; } } - load_finished (view); } @@ -132,24 +312,13 @@ size_prepared_callback (GdkPixbufLoader *loader, gpointer callback_data) { NautilusImagePropertiesView *view; - GdkPixbufFormat *format; - char *str; - char *name, *desc; view = NAUTILUS_IMAGE_PROPERTIES_VIEW (callback_data); - - format = gdk_pixbuf_loader_get_format (loader); - - name = gdk_pixbuf_format_get_name (format); - desc = gdk_pixbuf_format_get_description (format); - str = g_strdup_printf (_("<b>Image Type:</b> %s (%s)\n<b>Resolution:</b> %dx%d pixels\n"), - name, desc, width, height); - gtk_label_set_markup (GTK_LABEL (view->details->resolution), str); - g_free (str); - g_free (name); - g_free (desc); + view->details->height = height; + view->details->width = width; view->details->got_size = TRUE; + view->details->pixbuf_still_loading = FALSE; } static void @@ -167,6 +336,12 @@ file_opened_callback (GnomeVFSAsyncHandle *vfs_handle, } view->details->loader = gdk_pixbuf_loader_new (); + view->details->pixbuf_still_loading = TRUE; + view->details->width = 0; + view->details->height = 0; +#ifdef HAVE_EXIF + view->details->exifldr = exif_loader_new (); +#endif /*HAVE_EXIF*/ g_signal_connect (view->details->loader, "size_prepared", G_CALLBACK (size_prepared_callback), view); @@ -257,7 +432,7 @@ nautilus_image_properties_view_init (NautilusImagePropertiesView *view) gtk_box_pack_start (GTK_BOX (view->details->vbox), view->details->resolution, FALSE, TRUE, 2); - + gtk_widget_show_all (view->details->vbox); bonobo_control_construct (BONOBO_CONTROL (view), view->details->vbox); |