<para />\r
<section id="ProgressBar">\r
<title>Progress Bar</title>\r
- <para>The Progress bar updates to display the current state of thumbnail generation. When this section contains no text, thumbnail generation is idle. When “Loading thumbs...” is displayed, thumbnails are currently being generated when Geeqie is idle; the progress bar will update to display the percentage of thumbnails that are completed.</para>\r
- <para />\r
+ <para>\r
+ The Progress bar updates to display the current state of thumbnail generation, or the reading of metadata in the current folder.\r
+ <para />\r
+ When “Loading thumbs...” is displayed, thumbnails are currently being generated when Geeqie is idle; the progress bar will update to display the percentage of thumbnails that are completed.\r
+ <para />\r
+ When “Loading meta...” is displayed, certain metadata is being loaded when Geeqie is idle; the progress bar will update to display the percentage of files that have been read. Refer to\r
+ <link linkend="PreLoadMetadata">Preferences metadata.</link>\r
+ </para>\r
</section>\r
<section id="Sortmethod">\r
<title>Sort method</title>\r
</itemizedlist>\r
<para />\r
</section>\r
+ <section id="PreLoadMetadata">\r
+ <title>Pre-load metadata</title>\r
+ <itemizedlist>\r
+ <listitem>\r
+ <para>\r
+ <guilabel>Read metadata in background</guilabel>\r
+ <para />\r
+ Using the folder sorting options:\r
+ <para />\r
+ <guilabel>Exif date original</guilabel>\r
+ <para />\r
+ <guilabel>Exif date digitized</guilabel>\r
+ <para />\r
+ <guilabel>Rating</guilabel>\r
+ <para />\r
+ requires metadata to be read from all files in a folder before the sort action can be made. If a folder contains a large number of file, this can take a noticeable period of time.\r
+ <para />\r
+ If this option is checked, Geeqie will automatically read the required metatada in the background as soon as a folder is opened. This will reduce the amount of time you have to wait until the sort is completed.\r
+ <para />\r
+ If you do not use these sort otions, leave this option unchecked.\r
+ </para>\r
+ </listitem>\r
+ </itemizedlist>\r
+ <para />\r
+ </section>\r
</section>\r
fd->ref = 1;
fd->magick = FD_MAGICK;
fd->exifdate = 0;
- fd->rating = 0;
+ fd->rating = STAR_RATING_NOT_READ;
fd->format_class = filter_file_get_class(path_utf8);
if (disable_sidecars) fd->disable_grouping = TRUE;
return;
}
- file->exif = exif_read_fd(file);
+ if (!file->exif)
+ {
+ exif_read_fd(file);
+ }
if (file->exif)
{
return;
}
- file->exif = exif_read_fd(file);
+ if (!file->exif)
+ {
+ exif_read_fd(file);
+ }
if (file->exif)
{
}
}
+void read_rating_data(FileData *file)
+{
+ gchar *rating_str;
+
+ rating_str = metadata_read_string(file, RATING_KEY, METADATA_PLAIN);
+ if (rating_str)
+ {
+ file->rating = atoi(rating_str);
+ g_free(rating_str);
+ }
+}
+
void set_exif_time_data(GList *files)
{
DEBUG_1("%s set_exif_time_data: ...", get_exec_time());
GList *filelist_sort(GList *list, SortType method, gboolean ascend)
{
- if (method == SORT_EXIFTIME)
- {
- set_exif_time_data(list);
- }
- if (method == SORT_EXIFTIMEDIGITIZED)
- {
- set_exif_time_digitized_data(list);
- }
- if (method == SORT_RATING)
- {
- set_rating_data(list);
- }
return filelist_sort_full(list, method, ascend, (GCompareFunc) filelist_sort_file_cb);
}
gboolean marks_list_save(gchar *path, gboolean clear);
gboolean marks_list_load(const gchar *path);
void marks_clear_all();
+void read_rating_data(FileData *file);
#endif
/* vim: set shiftwidth=8 softtabstop=0 cindent cinoptions={1s: */
type = (SortType)GPOINTER_TO_INT(data);
+ if (type == SORT_EXIFTIME || type == SORT_EXIFTIMEDIGITIZED || type == SORT_RATING)
+ {
+ vf_read_metadata_in_idle(lw->vf);
+ }
layout_sort_set(lw, type, lw->sort_ascend);
}
void layout_status_update_progress(LayoutWindow *lw, gdouble val, const gchar *text)
{
+ static gdouble thumb = 0;
+ static gdouble meta = 0;
+
if (!layout_valid(&lw)) return;
if (!lw->info_progress_bar) return;
+ /* Give priority to the loading meta data message
+ */
+ if(!g_strcmp0(text, "Loading thumbs..."))
+ {
+ thumb = val;
+ if (meta)
+ {
+ return;
+ }
+ }
+ else
+ {
+ meta = val;
+ }
+
gtk_progress_bar_set_fraction(GTK_PROGRESS_BAR(lw->info_progress_bar), val);
- gtk_progress_bar_set_text(GTK_PROGRESS_BAR(lw->info_progress_bar), (text) ? text : " ");
+ gtk_progress_bar_set_text(GTK_PROGRESS_BAR(lw->info_progress_bar),
+ val ? ((text) ? text : " ") : " ");
}
void layout_status_update_info(LayoutWindow *lw, const gchar *text)
if (options->metadata.confirm_on_dir_change && dir_changed)
metadata_write_queue_confirm(FALSE, NULL, NULL);
+ if (lw->vf && (options->read_metadata_in_idle || (lw->sort_method == SORT_EXIFTIME || lw->sort_method == SORT_EXIFTIMEDIGITIZED || lw->sort_method == SORT_RATING)))
+ {
+ vf_read_metadata_in_idle(lw->vf);
+ }
+
return TRUE;
}
static void image_alter_rating(FileData *fd_n, const gchar *rating)
{
metadata_write_string(fd_n, RATING_KEY, rating);
+ read_rating_data(fd_n);
}
void layout_image_rating(LayoutWindow *lw, const gchar *rating)
#define TIMEZONE_DATABASE "timezone21.bin"
#define HELP_SEARCH_ENGINE "https://duckduckgo.com/?q=site:geeqie.org/help "
+
+#define STAR_RATING_NOT_READ -12345
/*
*----------------------------------------------------------------------------
* main.c
options->log_window.paused = FALSE;
options->log_window.timer_data = FALSE;
+ options->read_metadata_in_idle = FALSE;
return options;
}
gboolean line_wrap;
gboolean timer_data;
} log_window;
+
+ gboolean read_metadata_in_idle;
};
ConfOptions *options;
options->with_rename = c_options->with_rename;
config_entry_to_option(help_search_engine_entry, &options->help_search_engine, NULL);
+ options->read_metadata_in_idle = c_options->read_metadata_in_idle;
#ifdef DEBUG
set_debug_level(debug_c);
#endif
pref_checkbox_new_int(group, _("Write metadata on directory change"),
options->metadata.confirm_on_dir_change, &c_options->metadata.confirm_on_dir_change);
+
+ group = pref_group_new(vbox, FALSE, _("Pre-load metadata"), GTK_ORIENTATION_VERTICAL);
+
+ ct_button = pref_checkbox_new_int(group, _("Read metadata in background"),
+ options->read_metadata_in_idle, &c_options->read_metadata_in_idle);
+ gtk_widget_set_tooltip_text(ct_button,"On folder change, read DateTimeOriginal, DateTimeDigitized and Star Rating in the idle loop.\nIf this is not selected, initial loading of the folder will be faster but sorting on these items will be slower");
}
/* metadata tab */
WRITE_NL(); WRITE_INT(*options, stereo.fixed_x2);
WRITE_NL(); WRITE_INT(*options, stereo.fixed_y2);
+ WRITE_NL(); WRITE_BOOL(*options, read_metadata_in_idle);
+
/* copy move rename */
WRITE_NL(); WRITE_INT(*options, cp_mv_rn.auto_start);
WRITE_NL(); WRITE_INT(*options, cp_mv_rn.auto_padding);
if (READ_INT(*options, stereo.fixed_x2)) continue;
if (READ_INT(*options, stereo.fixed_y2)) continue;
+ if (READ_BOOL(*options, read_metadata_in_idle)) continue;
+
/* copy move rename */
if (READ_INT(*options, cp_mv_rn.auto_start)) continue;
if (READ_INT(*options, cp_mv_rn.auto_padding)) continue;
GHashTable *modified_xmp; // hash table which contains unwritten xmp metadata in format: key->list of string values
GList *cached_metadata;
gint rating;
+ gboolean metadata_in_idle_loaded;
SelectionType selected; // Used by view_file_icon.
};
/* file list for edit menu */
GList *editmenu_fd_list;
+
+ guint read_metadata_in_idle_id;
};
struct _ViewFileInfoList
void vf_thumb_update(ViewFile *vf);
void vf_thumb_cleanup(ViewFile *vf);
void vf_thumb_stop(ViewFile *vf);
-
+void vf_read_metadata_in_idle(ViewFile *vf);
#endif /* VIEW_FILE_H */
/* vim: set shiftwidth=8 softtabstop=0 cindent cinoptions={1s: */
type = (SortType)GPOINTER_TO_INT(data);
+ if (type == SORT_EXIFTIME || type == SORT_EXIFTIMEDIGITIZED || type == SORT_RATING)
+ {
+ vf_read_metadata_in_idle(vf);
+ }
+
if (vf->layout)
{
layout_sort_set(vf->layout, type, vf->sort_ascend);
gtk_widget_destroy(vf->popup);
}
+ if (vf->read_metadata_in_idle_id)
+ {
+ g_idle_remove_by_data(vf);
+ }
file_data_unref(vf->dir_fd);
g_free(vf->info);
g_free(vf);
vf->type = type;
vf->sort_method = SORT_NAME;
vf->sort_ascend = TRUE;
+ vf->read_metadata_in_idle_id = 0;
vf->scrolled = gtk_scrolled_window_new(NULL, NULL);
gtk_scrolled_window_set_shadow_type(GTK_SCROLLED_WINDOW(vf->scrolled), GTK_SHADOW_IN);
return (gdouble)done / count;
}
+static gdouble vf_read_metadata_in_idle_progress(ViewFile *vf)
+{
+ gint count = 0;
+ gint done = 0;
+
+ switch (vf->type)
+ {
+ case FILEVIEW_LIST: vflist_read_metadata_progress_count(vf->list, &count, &done); break;
+ case FILEVIEW_ICON: vficon_read_metadata_progress_count(vf->list, &count, &done); break;
+ }
+
+ return (gdouble)done / count;
+}
+
static void vf_set_thumb_fd(ViewFile *vf, FileData *fd)
{
switch (vf->type)
}
}
+static gboolean vf_read_metadata_in_idle_cb(gpointer data)
+{
+ FileData *fd;
+ ViewFile *vf = data;
+ GList *list_entry;
+ GList *work;
+
+ vf_thumb_status(vf, vf_read_metadata_in_idle_progress(vf), _("Loading meta..."));
+
+ work = vf->list;
+
+ while (work)
+ {
+ fd = work->data;
+
+ if (fd && !fd->metadata_in_idle_loaded)
+ {
+ if (!fd->exifdate)
+ {
+ read_exif_time_data(fd);
+ }
+ if (!fd->exifdate_digitized)
+ {
+ read_exif_time_digitized_data(fd);
+ }
+ if (fd->rating == STAR_RATING_NOT_READ)
+ {
+ read_rating_data(fd);
+ }
+ fd->metadata_in_idle_loaded = TRUE;
+ return TRUE;
+ }
+ work = work->next;
+ }
+
+ vf_thumb_status(vf, 0.0, NULL);
+ vf->read_metadata_in_idle_id = 0;
+ vf_refresh(vf);
+ return FALSE;
+}
+
+static void vf_read_metadata_in_idle_finished_cb(gpointer data)
+{
+ ViewFile *vf = data;
+
+ vf_thumb_status(vf, 0.0, "Loading meta...");
+ vf->read_metadata_in_idle_id = 0;
+}
+
+void vf_read_metadata_in_idle(ViewFile *vf)
+{
+ GList *work;
+ FileData *fd;
+
+ if (!vf) return;
+
+ if (vf->read_metadata_in_idle_id)
+ {
+ g_idle_remove_by_data(vf);
+ }
+ vf->read_metadata_in_idle_id = 0;
+
+ if (vf->list)
+ {
+ vf->read_metadata_in_idle_id = g_idle_add_full(G_PRIORITY_LOW, vf_read_metadata_in_idle_cb, vf, vf_read_metadata_in_idle_finished_cb);
+ }
+
+ return;
+}
+
/* vim: set shiftwidth=8 softtabstop=0 cindent cinoptions={1s: */
}
}
+void vficon_read_metadata_progress_count(GList *list, gint *count, gint *done)
+{
+ GList *work = list;
+ while (work)
+ {
+ FileData *fd = work->data;
+ work = work->next;
+
+ if (fd->metadata_in_idle_loaded) (*done)++;
+ (*count)++;
+ }
+}
+
void vficon_set_thumb_fd(ViewFile *vf, FileData *fd)
{
GtkTreeModel *store;
void vficon_thumb_progress_count(GList *list, gint *count, gint *done);
+void vficon_read_metadata_progress_count(GList *list, gint *count, gint *done);
void vficon_set_thumb_fd(ViewFile *vf, FileData *fd);
FileData *vficon_thumb_next_fd(ViewFile *vf);
void vficon_thumb_reset_all(ViewFile *vf);
}
}
+void vflist_read_metadata_progress_count(GList *list, gint *count, gint *done)
+{
+ GList *work = list;
+ while (work)
+ {
+ FileData *fd = work->data;
+ work = work->next;
+
+ if (fd->metadata_in_idle_loaded) (*done)++;
+
+ if (fd->sidecar_files)
+ {
+ vflist_read_metadata_progress_count(fd->sidecar_files, count, done);
+ }
+ (*count)++;
+ }
+}
+
void vflist_set_thumb_fd(ViewFile *vf, FileData *fd)
{
GtkTreeStore *store;
void vflist_color_set(ViewFile *vf, FileData *fd, gboolean color_set);
void vflist_thumb_progress_count(GList *list, gint *count, gint *done);
+void vflist_read_metadata_progress_count(GList *list, gint *count, gint *done);
void vflist_set_thumb_fd(ViewFile *vf, FileData *fd);
FileData *vflist_thumb_next_fd(ViewFile *vf);
void vflist_thumb_reset_all(ViewFile *vf);
</ul></div>
<div class="division section">
<a name="ProgressBar"></a><div class="header"><h2 class="section title"><span class="title"><span class="label">2.6.1. </span>Progress Bar</span></h2></div>
-<p class="para block block-first">The Progress bar updates to display the current state of thumbnail generation. When this section contains no text, thumbnail generation is idle. When “Loading thumbs...” is displayed, thumbnails are currently being generated when Geeqie is idle; the progress bar will update to display the percentage of thumbnails that are completed.</p>
-<p class="para block"></p>
+<p class="para block block-first">
+ The Progress bar updates to display the current state of thumbnail generation, or the reading of metadata in the current folder.
+ <p class="para block block-first"></p>
+ When “Loading thumbs...” is displayed, thumbnails are currently being generated when Geeqie is idle; the progress bar will update to display the percentage of thumbnails that are completed.
+ <p class="para block"></p>
+ When “Loading meta...” is displayed, certain metadata is being loaded when Geeqie is idle; the progress bar will update to display the percentage of files that have been read. Refer to
+ <a class="link" href="GuideOptionsMetadata.html#PreLoadMetadata" title="Pre-load metadata">Preferences metadata.</a>
+ </p>
</div>
<div class="division section">
<a name="Sortmethod"></a><div class="header"><h2 class="section title"><span class="title"><span class="label">2.6.2. </span>Sort method</span></h2></div>
<li>
<span class="label">11.6.5. </span><a class="xref" href="GuideOptionsMetadata.html#AutoSaveOptions" title="Auto-save options">Auto-save options</a>
</li>
+<li>
+<span class="label">11.6.6. </span><a class="xref" href="GuideOptionsMetadata.html#PreLoadMetadata" title="Pre-load metadata">Pre-load metadata</a>
+</li>
</ul></div>
<div class="division section">
<a name="MetadataWritingProcess"></a><div class="header"><h2 class="section title"><span class="title"><a name="titleMetadataWritingProcess"></a><span class="label">11.6.1. </span>Metadata writing process</span></h2></div>
</ul></div>
<p class="para block"></p>
</div>
+<div class="division section">
+<a name="PreLoadMetadata"></a><div class="header"><h2 class="section title"><span class="title"><span class="label">11.6.6. </span>Pre-load metadata</span></h2></div>
+<div class="block list itemizedlist"><ul class="itemizedlist"><li class="li-first">
+ <span class="para">
+ <span class="guilabel">Read metadata in background</span>
+ <p class="para block"></p>
+ Using the folder sorting options:
+ <p class="para block"></p>
+ <span class="guilabel">Exif date original</span>
+ <p class="para block"></p>
+ <span class="guilabel">Exif date digitized</span>
+ <p class="para block"></p>
+ <span class="guilabel">Rating</span>
+ <p class="para block"></p>
+ requires metadata to be read from all files in a folder before the sort action can be made. If a folder contains a large number of file, this can take a noticeable period of time.
+ <p class="para block"></p>
+ If this option is checked, Geeqie will automatically read the required metatada in the background as soon as a folder is opened. This will reduce the amount of time you have to wait until the sort is completed.
+ <p class="para block"></p>
+ If you do not use these sort otions, leave this option unchecked.
+ </span>
+ </li></ul></div>
+<p class="para block"></p>
+</div>
</div></div>
<div class="navbar navbar-bottom"><table class="navbar"><tr>
<td class="navbar-prev"><a class="navbar-prev" href="GuideOptionsFiltering.html" title="Files Options">Files Options</a></td>
</td>
</tr>
<tr class="tr-shade">
-<td class="td-colsep">
+<td class="td-colsep td-rowsep">
<span class="para">formatted.timezone</span>
</td>
-<td class="td-colsep">
+<td class="td-colsep td-rowsep">
<span class="para">
Exif.GPSInfo.GPSLatitude
<p class="para block block-first"></p>
Exif.GPSInfo.GPSLongitudeRef
</span>
</td>
-<td>
+<td class="td-rowsep">
<span class="para">
Timezone indicated by lat/long
<a name="-noteref-ref1"></a><sup><a class="footnote" href="#ref1">2</a></sup>
</span>
</td>
</tr>
+<tr>
+<td class="td-colsep">
+ <span class="para">formatted.star_rating</span>
+ </td>
+<td class="td-colsep">
+ <span class="para">Xmp.xmp.Rating</span>
+ </td>
+<td>
+ <span class="para">Rating shown as a set of 🟊 characters</span>
+ </td>
+</tr>
</tbody>
</table>
</div>
<td class="td-rowsep">file date and time in human readable form</td>
</tr>
<tr class="tr-shade">
-<td class="td-colsep">file.mode</td>
-<td>file mode flags</td>
+<td class="td-colsep td-rowsep">file.mode</td>
+<td class="td-rowsep">file mode flags</td>
+</tr>
+<tr>
+<td class="td-colsep">file.ctime</td>
+<td>refer to operating system documentation for the meaning of ctime</td>
</tr>
</tbody></table>
</div>