⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 collect-table.c

📁 Gqview,Linux下基于GTK+库写成的轻量级而能丰富的图像浏览程序。
💻 C
📖 第 1 页 / 共 4 页
字号:
/* * GQview * (C) 2004 John Ellis * * Author: John Ellis * * This software is released under the GNU General Public License (GNU GPL). * Please read the included file COPYING for more information. * This software comes with no warranty of any kind, use at your own risk! */#include "gqview.h"#include "collect-table.h"#include "cellrenderericon.h"#include "collect-dlg.h"#include "collect-io.h"#include "dnd.h"#include "dupe.h"#include "editors.h"#include "filelist.h"#include "img-view.h"#include "info.h"#include "layout.h"#include "layout_image.h"#include "menu.h"#include "print.h"#include "utilops.h"#include "ui_bookmark.h"#include "ui_fileops.h"#include "ui_menu.h"#include "ui_tree_edit.h"#include "icons/marker.xpm"#define MARKER_WIDTH 26#define MARKER_HEIGHT 32#include <gdk/gdkkeysyms.h> /* for keyboard values *//* between these, the icon width is increased by thumb_max_width / 2 */#define THUMB_MIN_ICON_WIDTH 128#define THUMB_MAX_ICON_WIDTH 150#define COLLECT_TABLE_MAX_COLUMNS 32#define THUMB_BORDER_PADDING 2#define COLLECT_TABLE_TIP_DELAY 500enum {	CTABLE_COLUMN_POINTER = 0,	CTABLE_COLUMN_COUNT};typedef enum {	SELECTION_NONE		= 0,	SELECTION_SELECTED	= 1 << 0,	SELECTION_PRELIGHT	= 1 << 1,	SELECTION_FOCUS		= 1 << 2} SelectionType;#define INFO_SELECTED(x) (x->flag_mask & SELECTION_SELECTED)static void collection_table_populate_at_new_size(CollectTable *ct, gint w, gint h, gint force);/* *------------------------------------------------------------------- * more misc *------------------------------------------------------------------- */static gint collection_table_find_position(CollectTable *ct, CollectInfo *info, gint *row, gint *col){	gint n;	n = g_list_index(ct->cd->list, info);	if (n < 0) return FALSE;	*row = n / ct->columns;	*col = n - (*row * ct->columns);	return TRUE;}static gint collection_table_find_iter(CollectTable *ct, CollectInfo *info, GtkTreeIter *iter, gint *column){	GtkTreeModel *store;	gint row, col;	store = gtk_tree_view_get_model(GTK_TREE_VIEW(ct->listview));	if (!collection_table_find_position(ct, info, &row, &col)) return FALSE;	if (!gtk_tree_model_iter_nth_child(store, iter, NULL, row)) return FALSE;	if (column) *column = col;	return TRUE;}static CollectInfo *collection_table_find_data(CollectTable *ct, gint row, gint col, GtkTreeIter *iter){	GtkTreeModel *store;	GtkTreeIter p;	if (row < 0 || col < 0) return NULL;	store = gtk_tree_view_get_model(GTK_TREE_VIEW(ct->listview));	if (gtk_tree_model_iter_nth_child(store, &p, NULL, row))		{		GList *list;		gtk_tree_model_get(store, &p, CTABLE_COLUMN_POINTER, &list, -1);		if (!list) return NULL;		if (iter) *iter = p;		return g_list_nth_data(list, col);		}	return NULL;}static CollectInfo *collection_table_find_data_by_coord(CollectTable *ct, gint x, gint y, GtkTreeIter *iter){	GtkTreePath *tpath;	GtkTreeViewColumn *column;	if (gtk_tree_view_get_path_at_pos(GTK_TREE_VIEW(ct->listview), x, y,					  &tpath, &column, NULL, NULL))		{		GtkTreeModel *store;		GtkTreeIter row;		GList *list;		gint n;		store = gtk_tree_view_get_model(GTK_TREE_VIEW(ct->listview));		gtk_tree_model_get_iter(store, &row, tpath);		gtk_tree_path_free(tpath);		gtk_tree_model_get(store, &row, CTABLE_COLUMN_POINTER, &list, -1);		n = GPOINTER_TO_INT(g_object_get_data(G_OBJECT(column), "column_number"));		if (list)			{			if (iter) *iter = row;			return g_list_nth_data(list, n);			}		}	return NULL;}static void collection_table_update_status(CollectTable *ct){	if (ct->status_label)		{		gchar *buf;		if (!ct->cd->list)			{			buf = g_strdup(_("Empty"));			}		else if (ct->selection)			{			buf = g_strdup_printf(_("%d images (%d)"), g_list_length(ct->cd->list), g_list_length(ct->selection));			}		else			{			buf = g_strdup_printf(_("%d images"), g_list_length(ct->cd->list));			}		gtk_label_set_text(GTK_LABEL(ct->status_label), buf);		g_free(buf);		}}static void collection_table_update_extras(CollectTable *ct, gint loading, gdouble value){	if (ct->extra_label)		{		gchar *text;		if (loading)			text = _("Loading thumbs...");		else			text = " ";		gtk_progress_bar_set_fraction(GTK_PROGRESS_BAR(ct->extra_label), value);		gtk_progress_bar_set_text(GTK_PROGRESS_BAR(ct->extra_label), text);		}}static void collection_table_toggle_filenames(CollectTable *ct){	ct->show_text = !ct->show_text;	show_icon_names = ct->show_text;	collection_table_populate_at_new_size(ct, ct->listview->allocation.width, ct->listview->allocation.height, TRUE);}static gint collection_table_get_icon_width(CollectTable *ct){	gint width;	if (!ct->show_text) return thumb_max_width;	width = thumb_max_width + thumb_max_width / 2;	if (width < THUMB_MIN_ICON_WIDTH) width = THUMB_MIN_ICON_WIDTH;	if (width > THUMB_MAX_ICON_WIDTH) width = thumb_max_width;	return width;}/* *------------------------------------------------------------------- * cell updates *------------------------------------------------------------------- */static void collection_table_selection_set(CollectTable *ct, CollectInfo *info, SelectionType value, GtkTreeIter *iter){	GtkTreeModel *store;	GList *list;	if (!info) return;	if (info->flag_mask == value) return;	info->flag_mask = value;	store = gtk_tree_view_get_model(GTK_TREE_VIEW(ct->listview));	if (iter)		{		gtk_tree_model_get(store, iter, CTABLE_COLUMN_POINTER, &list, -1);		if (list) gtk_list_store_set(GTK_LIST_STORE(store), iter, CTABLE_COLUMN_POINTER, list, -1);		}	else		{		GtkTreeIter row;		if (collection_table_find_iter(ct, info, &row, NULL))			{			gtk_tree_model_get(store, &row, CTABLE_COLUMN_POINTER, &list, -1);			if (list) gtk_list_store_set(GTK_LIST_STORE(store), &row, CTABLE_COLUMN_POINTER, list, -1);			}		}}static void collection_table_selection_add(CollectTable *ct, CollectInfo *info, SelectionType mask, GtkTreeIter *iter){	if (!info) return;	collection_table_selection_set(ct, info, info->flag_mask | mask, iter);}static void collection_table_selection_remove(CollectTable *ct, CollectInfo *info, SelectionType mask, GtkTreeIter *iter){	if (!info) return;	collection_table_selection_set(ct, info, info->flag_mask & ~mask, iter);}/* *------------------------------------------------------------------- * selections *------------------------------------------------------------------- */static void collection_table_verify_selections(CollectTable *ct){	GList *work;	work = ct->selection;	while (work)		{		CollectInfo *info = work->data;		work = work->next;		if (!g_list_find(ct->cd->list, info))			{			ct->selection = g_list_remove(ct->selection, info);			}		}}void collection_table_select_all(CollectTable *ct){	GList *work;	g_list_free(ct->selection);	ct->selection = NULL;	work = ct->cd->list;	while(work)		{		ct->selection = g_list_append(ct->selection, work->data);		collection_table_selection_add(ct, work->data, SELECTION_SELECTED, NULL);		work = work->next;		}	collection_table_update_status(ct);}void collection_table_unselect_all(CollectTable *ct){	GList *work;	work = ct->selection;	while (work)		{		collection_table_selection_remove(ct, work->data, SELECTION_SELECTED, NULL);		work = work->next;		}	g_list_free(ct->selection);	ct->selection = NULL;	collection_table_update_status(ct);}static void collection_table_select(CollectTable *ct, CollectInfo *info){	ct->prev_selection = info;	if (!info || INFO_SELECTED(info)) return;	ct->selection = g_list_append(ct->selection, info);	collection_table_selection_add(ct, info, SELECTION_SELECTED, NULL);	collection_table_update_status(ct);}static void collection_table_unselect(CollectTable *ct, CollectInfo *info){	ct->prev_selection = info;	if (!info || !INFO_SELECTED(info) ) return;	ct->selection = g_list_remove(ct->selection, info);	collection_table_selection_remove(ct, info, SELECTION_SELECTED, NULL);	collection_table_update_status(ct);}static void collection_table_select_util(CollectTable *ct, CollectInfo *info, gint select){	if (select)		{		collection_table_select(ct, info);		}	else		{		collection_table_unselect(ct, info);		}}static void collection_table_select_region_util(CollectTable *ct, CollectInfo *start, CollectInfo *end, gint select){	gint row1, col1;	gint row2, col2;	gint t;	gint i, j;	if (!collection_table_find_position(ct, start, &row1, &col1) ||	    !collection_table_find_position(ct, end, &row2, &col2) ) return;	ct->prev_selection = end;	if (!collection_rectangular_selection)		{		GList *work;		CollectInfo *info;		if (g_list_index(ct->cd->list, start) > g_list_index(ct->cd->list, end))			{			info = start;			start = end;			end = info;			}		work = g_list_find(ct->cd->list, start);		while (work)			{			info = work->data;			collection_table_select_util(ct, info, select);						if (work->data != end)				work = work->next;			else				work = NULL;			}		return;		}	if (row2 < row1)		{		t = row1;		row1 = row2;		row2 = t;		}	if (col2 < col1)		{		t = col1;		col1 = col2;		col2 = t;		}	if (debug) printf("table: %d x %d to %d x %d\n", row1, col1, row2, col2);	for (i = row1; i <= row2; i++)		{		for (j = col1; j <= col2; j++)			{			CollectInfo *info = collection_table_find_data(ct, i, j, NULL);			if (info) collection_table_select_util(ct, info, select);			}		}}GList *collection_table_selection_get_list(CollectTable *ct){	return collection_list_to_path_list(ct->selection);}static GList *collection_table_get_list(CollectTable *ct){	return collection_list_to_path_list(ct->cd->list);}/* *------------------------------------------------------------------- * tooltip type window *------------------------------------------------------------------- */static void tip_show(CollectTable *ct){	GtkWidget *label;	gint x, y;	if (ct->tip_window) return;	gdk_window_get_pointer(ct->listview->window, &x, &y, NULL);	ct->tip_info = collection_table_find_data_by_coord(ct, x, y, NULL);	if (!ct->tip_info) return;	ct->tip_window = gtk_window_new(GTK_WINDOW_POPUP);	gtk_window_set_resizable(GTK_WINDOW(ct->tip_window), FALSE);	gtk_container_set_border_width(GTK_CONTAINER(ct->tip_window), 2);	label = gtk_label_new(filename_from_path(ct->tip_info->path));	g_object_set_data(G_OBJECT(ct->tip_window), "tip_label", label);	gtk_container_add(GTK_CONTAINER(ct->tip_window), label);	gtk_widget_show(label);	gdk_window_get_pointer(NULL, &x, &y, NULL);	if (!GTK_WIDGET_REALIZED(ct->tip_window)) gtk_widget_realize(ct->tip_window);	gtk_window_move(GTK_WINDOW(ct->tip_window), x + 16, y + 16);	gtk_widget_show(ct->tip_window);}static void tip_hide(CollectTable *ct){	if (ct->tip_window) gtk_widget_destroy(ct->tip_window);	ct->tip_window = NULL;}static gint tip_schedule_cb(gpointer data){	CollectTable *ct = data;	if (ct->tip_delay_id == -1) return FALSE;	tip_show(ct);	ct->tip_delay_id = -1;	return FALSE;}static void tip_schedule(CollectTable *ct){	tip_hide(ct);	if (ct->tip_delay_id != -1)		{		g_source_remove(ct->tip_delay_id);		ct->tip_delay_id = -1;		}	if (!ct->show_text)		{		ct->tip_delay_id = g_timeout_add(COLLECT_TABLE_TIP_DELAY, tip_schedule_cb, ct);		}}static void tip_unschedule(CollectTable *ct){	tip_hide(ct);	if (ct->tip_delay_id != -1) g_source_remove(ct->tip_delay_id);	ct->tip_delay_id = -1;}static void tip_update(CollectTable *ct, CollectInfo *info){	if (ct->tip_window)		{		gint x, y;		gdk_window_get_pointer(NULL, &x, &y, NULL);		gtk_window_move(GTK_WINDOW(ct->tip_window), x + 16, y + 16);		if (info != ct->tip_info)			{			GtkWidget *label;			ct->tip_info = info;			if (!ct->tip_info)				{				tip_hide(ct);				tip_schedule(ct);				return;				}			label = g_object_get_data(G_OBJECT(ct->tip_window), "tip_label");			gtk_label_set_text(GTK_LABEL(label), filename_from_path(ct->tip_info->path));			}		}	else		{		tip_schedule(ct);		}}/* *------------------------------------------------------------------- * popup menus *------------------------------------------------------------------- */static void collection_table_popup_save_as_cb(GtkWidget *widget, gpointer data){	CollectTable *ct = data;	collection_dialog_save_as(NULL, ct->cd);}static void collection_table_popup_save_cb(GtkWidget *widget, gpointer data){	CollectTable *ct = data;	if (!ct->cd->path)		{		collection_table_popup_save_as_cb(widget, data);		return;		}	if (!collection_save(ct->cd, ct->cd->path))		{		printf("failed saving to collection path: %s\n", ct->cd->path);		}}static GList *collection_table_popup_file_list(CollectTable *ct){	if (!ct->click_info) return NULL;	if (INFO_SELECTED(ct->click_info))		{		return collection_table_selection_get_list(ct);		}	return g_list_append(NULL, g_strdup(ct->click_info->path));}static void collection_table_popup_edit_cb(GtkWidget *widget, gpointer data){	CollectTable *ct;	gint n;	GList *list;	ct = submenu_item_get_data(widget);	if (!ct) return;	n = GPOINTER_TO_INT(data);	list = collection_table_popup_file_list(ct);	if (list)		{		start_editor_from_path_list(n, list);		path_list_free(list);		}}static void collection_table_popup_info_cb(GtkWidget *widget, gpointer data){	CollectTable *ct = data;	info_window_new(NULL, collection_table_popup_file_list(ct));}static void collection_table_popup_copy_cb(GtkWidget *widget, gpointer data){	CollectTable *ct = data;	file_util_copy(NULL, collection_table_popup_file_list(ct), NULL, ct->listview);}static void collection_table_popup_move_cb(GtkWidget *widget, gpointer data){

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -