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

📄 collect-table.c

📁 Gqview,Linux下基于GTK+库写成的轻量级而能丰富的图像浏览程序。
💻 C
📖 第 1 页 / 共 4 页
字号:
	return info;}static CollectInfo *collection_table_insert_point(CollectTable *ct, gint x, gint y){	CollectInfo *info;	GdkRectangle cell;	gint after = FALSE;	info = collection_table_insert_find(ct, NULL, &after, &cell, TRUE, x, y);	if (info && after)		{		GList *work;		work = g_list_find(ct->cd->list, info);		if (work && work->next)			{			info = work->next->data;			}		else			{			info = NULL;			}		}	return info;}static void collection_table_insert_marker(CollectTable *ct, CollectInfo *info, gint enable){	gint row, col;	gint after = FALSE;	GdkRectangle cell;	if (!enable)		{		if (ct->marker_window) gdk_window_destroy(ct->marker_window);		ct->marker_window = NULL;		return;		}	info = collection_table_insert_find(ct, info, &after, &cell, FALSE, 0, 0);	/* this setting does not take into account (after), but since it is not really used... */	ct->marker_info = info;	row = -1;	col = -1;	if (!ct->marker_window)		{		GdkWindow *parent;		GdkWindowAttr attributes;		gint attributes_mask;		GdkPixmap *pixmap;		GdkBitmap *mask;		GdkPixbuf *pb;		gint w, h;		parent = gtk_tree_view_get_bin_window(GTK_TREE_VIEW(ct->listview));		pb = gdk_pixbuf_new_from_xpm_data((const char **)marker_xpm);		gdk_pixbuf_render_pixmap_and_mask(pb, &pixmap, &mask, 128);		gdk_pixbuf_unref(pb);		gdk_drawable_get_size(pixmap, &w, &h);		attributes.window_type = GDK_WINDOW_CHILD;		attributes.wclass = GDK_INPUT_OUTPUT;		attributes.width = w;		attributes.height = h;		attributes.event_mask = gtk_widget_get_events(ct->listview);		attributes_mask = 0;		ct->marker_window = gdk_window_new(parent, &attributes, attributes_mask);		gdk_window_set_back_pixmap(ct->marker_window, pixmap, FALSE);		gdk_window_shape_combine_mask(ct->marker_window, mask, 0, 0);		g_object_unref(pixmap);		if (mask) g_object_unref(mask);		}	if (info)		{		gint x, y;		gint w, h;		gdk_drawable_get_size(ct->marker_window, &w, &h);		if (!after)			{			x = cell.x;			}		else			{			x = cell.x + cell.width;			}		x -= (w / 2);		y = cell.y + (cell.height / 2) - (h / 2);		gdk_window_move(ct->marker_window, x, y);		gdk_window_clear(ct->marker_window);		if (!gdk_window_is_visible(ct->marker_window)) gdk_window_show(ct->marker_window);		}	else		{		if (gdk_window_is_visible(ct->marker_window)) gdk_window_hide(ct->marker_window);		}}/* *------------------------------------------------------------------- * mouse drag auto-scroll *------------------------------------------------------------------- */static void collection_table_motion_update(CollectTable *ct, gint x, gint y, gint drop_event){	CollectInfo *info;	info = collection_table_find_data_by_coord(ct, x, y, NULL);	if (drop_event)		{		tip_unschedule(ct);		collection_table_insert_marker(ct, info, TRUE);		}	else		{		tip_update(ct, info);		}}static gint collection_table_auto_scroll_idle_cb(gpointer data){	CollectTable *ct = data;	GdkWindow *window;	gint x, y;	gint w, h;	if (ct->drop_idle_id == -1) return FALSE;	window = ct->listview->window;	gdk_window_get_pointer(window, &x, &y, NULL);	gdk_drawable_get_size(window, &w, &h);	if (x >= 0 && x < w && y >= 0 && y < h)		{		collection_table_motion_update(ct, x, y, TRUE);		}	ct->drop_idle_id = -1;	return FALSE;}static gint collection_table_auto_scroll_notify_cb(GtkWidget *widget, gint x, gint y, gpointer data){	CollectTable *ct = data;	if (ct->drop_idle_id == -1) ct->drop_idle_id = g_idle_add(collection_table_auto_scroll_idle_cb, ct);	return TRUE;}static void collection_table_scroll(CollectTable *ct, gint scroll){	if (!scroll)		{		if (ct->drop_idle_id != -1)			{			g_source_remove(ct->drop_idle_id);			ct->drop_idle_id = -1;			}		widget_auto_scroll_stop(ct->listview);		collection_table_insert_marker(ct, NULL, FALSE);		}	else		{		GtkAdjustment *adj = gtk_tree_view_get_vadjustment(GTK_TREE_VIEW(ct->listview));		widget_auto_scroll_start(ct->listview, adj, -1, thumb_max_height / 2,					 collection_table_auto_scroll_notify_cb, ct);		}}/* *------------------------------------------------------------------- * mouse callbacks *------------------------------------------------------------------- */static gint collection_table_motion_cb(GtkWidget *widget, GdkEventButton *bevent, gpointer data){	CollectTable *ct = data;	collection_table_motion_update(ct, (gint)bevent->x, (gint)bevent->y, FALSE);	return FALSE;}static gint collection_table_press_cb(GtkWidget *widget, GdkEventButton *bevent, gpointer data){	CollectTable *ct = data;	GtkTreeIter iter;	CollectInfo *info;	tip_unschedule(ct);	info = collection_table_find_data_by_coord(ct, (gint)bevent->x, (gint)bevent->y, &iter);	ct->click_info = info;	collection_table_selection_add(ct, ct->click_info, SELECTION_PRELIGHT, &iter);	switch (bevent->button)		{		case 1:			if (bevent->type == GDK_2BUTTON_PRESS)				{				if (info)					{					layout_image_set_collection(NULL, ct->cd, info);					}				}			else if (!GTK_WIDGET_HAS_FOCUS(ct->listview))				{				gtk_widget_grab_focus(ct->listview);				}			break;		case 3:			ct->popup = collection_table_popup_menu(ct, (info != NULL));			gtk_menu_popup(GTK_MENU(ct->popup), NULL, NULL, NULL, NULL, bevent->button, bevent->time);			break;		default:			break;		}	return TRUE;}static gint collection_table_release_cb(GtkWidget *widget, GdkEventButton *bevent, gpointer data){	CollectTable *ct = data;	GtkTreeIter iter;	CollectInfo *info = NULL;	tip_schedule(ct);	if ((gint)bevent->x != 0 || (gint) bevent->y != 0)		{		info = collection_table_find_data_by_coord(ct, (gint)bevent->x, (gint)bevent->y, &iter);		}	if (ct->click_info)		{		collection_table_selection_remove(ct, ct->click_info, SELECTION_PRELIGHT, NULL);		}	if (bevent->button == 1 &&	    info && ct->click_info == info)		{		collection_table_set_focus(ct, info);		if (bevent->state & GDK_CONTROL_MASK)			{			gint select;			select = !INFO_SELECTED(info);			if ((bevent->state & GDK_SHIFT_MASK) && ct->prev_selection)				{				collection_table_select_region_util(ct, ct->prev_selection, info, select);				}			else				{				collection_table_select_util(ct, info, select);				}			}		else			{			collection_table_unselect_all(ct);			if ((bevent->state & GDK_SHIFT_MASK) &&			    ct->prev_selection)				{				collection_table_select_region_util(ct, ct->prev_selection, info, TRUE);				}			else				{				collection_table_select_util(ct, info, TRUE);				}			}		}	else if (bevent->button == 2 &&		 info && ct->click_info == info)		{		collection_table_select_util(ct, info, !INFO_SELECTED(info));		}	return TRUE;}static gint collection_table_leave_cb(GtkWidget *widget, GdkEventCrossing *event, gpointer data){	CollectTable *ct = data;	tip_unschedule(ct);	return FALSE;}/* *------------------------------------------------------------------- * populate, add, insert, etc. *------------------------------------------------------------------- */static gboolean collection_table_destroy_node_cb(GtkTreeModel *store, GtkTreePath *tpath, GtkTreeIter *iter, gpointer data){	GList *list;	gtk_tree_model_get(store, iter, CTABLE_COLUMN_POINTER, &list, -1);	g_list_free(list);	return FALSE;}static void collection_table_clear_store(CollectTable *ct){	GtkTreeModel *store;	store = gtk_tree_view_get_model(GTK_TREE_VIEW(ct->listview));	gtk_tree_model_foreach(store, collection_table_destroy_node_cb, NULL);	gtk_list_store_clear(GTK_LIST_STORE(store));}static GList *collection_table_add_row(CollectTable *ct, GtkTreeIter *iter){	GtkListStore *store;	GList *list = NULL;	gint i;	for (i = 0; i < ct->columns; i++) list = g_list_prepend(list, NULL);	store = GTK_LIST_STORE(gtk_tree_view_get_model(GTK_TREE_VIEW(ct->listview)));	gtk_list_store_append(store, iter);	gtk_list_store_set(store, iter, CTABLE_COLUMN_POINTER, list, -1);	return list;}static void collection_table_populate(CollectTable *ct, gint resize){	gint row;	GList *work;	collection_table_verify_selections(ct);	collection_table_clear_store(ct);	if (resize)		{		gint i;		gint thumb_width;		thumb_width = collection_table_get_icon_width(ct);		for (i = 0; i < COLLECT_TABLE_MAX_COLUMNS; i++)			{			GtkTreeViewColumn *column;			GtkCellRenderer *cell;			GList *list;			column = gtk_tree_view_get_column(GTK_TREE_VIEW(ct->listview), i);			gtk_tree_view_column_set_visible(column, (i < ct->columns));			gtk_tree_view_column_set_fixed_width(column, thumb_width + (THUMB_BORDER_PADDING * 6));			list = gtk_tree_view_column_get_cell_renderers(column);			cell = (list) ? list->data : NULL;			g_list_free(list);			if (cell && GQV_IS_CELL_RENDERER_ICON(cell))				{				g_object_set(G_OBJECT(cell), "fixed_width", thumb_width,							     "fixed_height", thumb_max_height,							     "show_text", ct->show_text, NULL);				}			}		if (GTK_WIDGET_REALIZED(ct->listview)) gtk_tree_view_columns_autosize(GTK_TREE_VIEW(ct->listview));		}	row = -1;	work = ct->cd->list;	while (work)		{		GList *list;		GtkTreeIter iter;		row++;		list = collection_table_add_row(ct, &iter);		while (work && list)			{			list->data = work->data;			list = list->next;			work = work->next;			}		}	ct->rows = row + 1;	collection_table_update_focus(ct);	collection_table_update_status(ct);}static void collection_table_populate_at_new_size(CollectTable *ct, gint w, gint h, gint force){	gint new_cols;	gint thumb_width;	thumb_width = collection_table_get_icon_width(ct);	new_cols = w / (thumb_width + (THUMB_BORDER_PADDING * 6));	if (new_cols < 1) new_cols = 1;	if (!force && new_cols == ct->columns) return;	ct->columns = new_cols;	collection_table_populate(ct, TRUE);	if (debug) printf("col tab pop cols=%d rows=%d\n", ct->columns, ct->rows);}static void collection_table_sync(CollectTable *ct){	GtkTreeModel *store;	GtkTreeIter iter;	GList *work;	gint r, c;	store = gtk_tree_view_get_model(GTK_TREE_VIEW(ct->listview));	r = -1;	c = 0;	work = ct->cd->list;	while (work)		{		GList *list;		r++;		c = 0;		if (gtk_tree_model_iter_nth_child(store, &iter, NULL, r))			{			gtk_tree_model_get(store, &iter, CTABLE_COLUMN_POINTER, &list, -1);			gtk_list_store_set(GTK_LIST_STORE(store), &iter, CTABLE_COLUMN_POINTER, list, -1);			}		else			{			list = collection_table_add_row(ct, &iter);			}		while (list)			{			CollectInfo *info;			if (work)				{				info = work->data;				work = work->next;				c++;				}			else				{				info = NULL;				}			if (list)				{				list->data = info;				list = list->next;				}			}		}	r++;	while (gtk_tree_model_iter_nth_child(store, &iter, NULL, r))		{		GList *list;		gtk_tree_model_get(store, &iter, CTABLE_COLUMN_POINTER, &list, -1);		gtk_list_store_remove(GTK_LIST_STORE(store), &iter);		g_list_free(list);		}	ct->rows = r;	collection_table_update_focus(ct);	collection_table_update_status(ct);}static gint collection_table_sync_idle_cb(gpointer data){	CollectTable *ct = data;	if (ct->sync_idle_id == -1) return FALSE;	ct->sync_idle_id = -1;	collection_table_sync(ct);	return FALSE;}static void collection_table_sync_idle(CollectTable *ct){	if (ct->sync_idle_id == -1)		{		/* high priority, the view needs to be resynced before a redraw		 * may contain invalid pointers at this time		 */		ct->sync_idle_id = g_idle_add_full(G_PRIORITY_HIGH, collection_table_sync_idle_cb, ct, NULL);		}}void collection_table_add_path_list(CollectTable *ct, GList *list){	GList *work;	if (!list) return;	work = list;	while (work)		{		collection_add(ct->cd, (gchar *)work->data, FALSE);		work = work->next;		}}static void collection_table_insert_path_list(CollectTable *ct, GList *list, CollectInfo *insert_info){	GList *work;	if (!list) return;	work = list;	while (work)		{		collection_insert(ct->cd, (gchar *)work->data, insert_info, FALSE);		work = work->next;		}	collection_table_sync_idle(ct);}static void collection_table_move_by_info_list(CollectTable *ct, GList *info_list, gint row, gint col){	GList *work;	GList *insert_pos = NULL;	GList *temp;	CollectInfo *info;	if (!info_list) return;	info = collection_table_find_data(ct, row, col, NULL);	if (!info_list->next && info_list->data == info) return;	if (info) insert_pos = g_list_find(ct->cd->list, info);	/* FIXME: this may get slow for large lists */	work = info_list;	while (insert_pos && work)		{		if (insert_pos->data == work->data)			{			insert_pos = insert_pos->next;			work = info_list;			}		else			{			work = work->next;			}		}	work = info_list;	while (work)		{		ct->cd->list = g_list_remove(ct->cd->list, work->data);		work = work->next;		}	/* place them back in */	temp = g_list_copy(info_list);	if (insert_pos)		{		ct->cd->list = uig_list_insert_list(ct->cd->list, insert_pos, temp);		}	else if (info)		{		ct->cd->list = g_list_concat(temp, ct->cd->list);		}	else		{		ct->cd->list = g_list_concat(ct->cd->list, temp);		}	ct->cd->changed = TRUE;	collection_table_sync_idle(ct);}/* *------------------------------------------------------------------- * updating *------------------------------------------------------------------- */

⌨️ 快捷键说明

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