changeset 13869:5642f4658b59

[gaim-migrate @ 16335] A bunch of stuff that doesn't really do much. I am trying to get the "expose" thingy going where a widget will redraw some of its parts when some other widget covering it is destroyed. committer: Tailor Script <tailor@pidgin.im>
author Sadrul Habib Chowdhury <imadil@gmail.com>
date Sun, 25 Jun 2006 03:15:41 +0000
parents b355f7ed1814
children 983fd420e86b
files console/Makefile console/gntblist.c console/gntgaim.c console/libgnt/Makefile console/libgnt/gnt.h console/libgnt/gntbox.c console/libgnt/gntmain.c console/libgnt/gntwidget.c
diffstat 8 files changed, 120 insertions(+), 16 deletions(-) [+]
line wrap: on
line diff
--- a/console/Makefile	Sat Jun 24 22:52:59 2006 +0000
+++ b/console/Makefile	Sun Jun 25 03:15:41 2006 +0000
@@ -1,5 +1,5 @@
 CFLAGS=`pkg-config --cflags gaim gobject-2.0` -g -I./libgnt/
-LDFLAGS=`pkg-config --libs gaim gobject-2.0 libxml-2.0` -lncursesw -L./libgnt/ -lgnt
+LDFLAGS=`pkg-config --libs gaim gobject-2.0 libxml-2.0` -lncursesw -L./libgnt/ -lgnt -pg
 
 GG_SOURCES = \
 	gntblist.c \
@@ -13,7 +13,9 @@
 	gntblist.o \
 	gntui.o
 
-all: gntgaim
+all:
+	cd libgnt && make
+	make gntgaim
 
 gntgaim: gntgaim.o $(GG_OBJECTS)
 	$(CC) -o gntgaim gntgaim.o $(GG_OBJECTS) $(LDFLAGS)
@@ -22,6 +24,7 @@
 gntui.o: gntui.c $(GG_HEADERS)
 
 clean:
+	cd libgnt && make clean
 	rm *.o
 	rm gntgaim
 
--- a/console/gntblist.c	Sat Jun 24 22:52:59 2006 +0000
+++ b/console/gntblist.c	Sun Jun 25 03:15:41 2006 +0000
@@ -222,6 +222,8 @@
 
 	if (ggblist->tooltip)
 	{
+		/* XXX: Once we can properly redraw on expose events, this can be removed at the end
+		 * to avoid the blinking*/
 		remove_tooltip(ggblist);
 	}
 
@@ -293,6 +295,8 @@
 	g_string_free(str, TRUE);
 	ggblist->tooltip = box;
 	ggblist->tnode = node;
+
+	gnt_widget_set_name(ggblist->tooltip, "tooltip");
 }
 
 static void
@@ -333,6 +337,7 @@
 	gaim_get_blist()->ui_data = ggblist;
 
 	ggblist->window = gnt_box_new(FALSE, FALSE);
+	gnt_widget_set_name(ggblist->window, "buddylist");
 	gnt_box_set_toplevel(GNT_BOX(ggblist->window), TRUE);
 	gnt_box_set_title(GNT_BOX(ggblist->window), _("Buddy List"));
 	gnt_box_set_pad(GNT_BOX(ggblist->window), 0);
--- a/console/gntgaim.c	Sat Jun 24 22:52:59 2006 +0000
+++ b/console/gntgaim.c	Sun Jun 25 03:15:41 2006 +0000
@@ -169,7 +169,7 @@
 int main(int argc, char **argv)
 {
 	/* XXX: Don't puke */
-	freopen("/dev/null", "w", stderr);
+	freopen(".error", "w", stderr);
 
 	/* Initialize the libgaim stuff */
 	init_libgaim();
--- a/console/libgnt/Makefile	Sat Jun 24 22:52:59 2006 +0000
+++ b/console/libgnt/Makefile	Sun Jun 25 03:15:41 2006 +0000
@@ -1,5 +1,5 @@
 CFLAGS=`pkg-config --cflags gobject-2.0` -g
-LDFLAGS=`pkg-config --libs gobject-2.0` -lncursesw
+LDFLAGS=`pkg-config --libs gobject-2.0` -lncursesw -pg
 
 HEADERS = \
 	gntwidget.h \
--- a/console/libgnt/gnt.h	Sat Jun 24 22:52:59 2006 +0000
+++ b/console/libgnt/gnt.h	Sun Jun 25 03:15:41 2006 +0000
@@ -3,15 +3,11 @@
 #include "gntcolors.h"
 #include "gntkeys.h"
 
-/* XXX: Find a better place for this */
-#define SCROLL_HEIGHT	4096
-#define SCROLL_WIDTH 512
-
 void gnt_init();
 
 void gnt_main();
 
-void gnt_screen_take_focus(GntWidget *widget);
+void gnt_screen_occupy(GntWidget *widget);
 
-void gnt_screen_remove_widget(GntWidget *widget);
+void gnt_screen_release(GntWidget *widget);
 
--- a/console/libgnt/gntbox.c	Sat Jun 24 22:52:59 2006 +0000
+++ b/console/libgnt/gntbox.c	Sun Jun 25 03:15:41 2006 +0000
@@ -16,7 +16,9 @@
 
 	for (iter = box->list; iter; iter = iter->next)
 	{
-		gnt_widget_draw(GNT_WIDGET(iter->data));
+		GntWidget *w = GNT_WIDGET(iter->data);
+		gnt_widget_draw(w);
+		overwrite(w->window, widget->window);
 	}
 
 	if (box->title)
@@ -39,6 +41,8 @@
 		g_free(title);
 	}
 	wrefresh(widget->window);
+
+	gnt_screen_occupy(widget);
 	
 	DEBUG;
 }
@@ -263,10 +267,21 @@
 		gnt_widget_destroy(iter->data);
 	}
 
+	gnt_screen_release(w);
+	
 	g_list_free(box->list);
 }
 
 static void
+gnt_box_expose(GntWidget *widget, int x, int y, int width, int height)
+{
+	WINDOW *win = newwin(height, width, widget->priv.y + y, widget->priv.x + x);
+	copywin(widget->window, win, y, x, 0, 0, height - 1, width - 1, FALSE);
+	wrefresh(win);
+	delwin(win);
+}
+
+static void
 gnt_box_class_init(GntBoxClass *klass)
 {
 	GObjectClass *obj_class = G_OBJECT_CLASS(klass);
@@ -274,6 +289,7 @@
 	parent_class = GNT_WIDGET_CLASS(klass);
 	parent_class->destroy = gnt_box_destroy;
 	parent_class->draw = gnt_box_draw;
+	parent_class->expose = gnt_box_expose;
 	parent_class->map = gnt_box_map;
 	parent_class->size_request = gnt_box_size_request;
 	parent_class->set_position = gnt_box_set_position;
--- a/console/libgnt/gntmain.c	Sat Jun 24 22:52:59 2006 +0000
+++ b/console/libgnt/gntmain.c	Sun Jun 25 03:15:41 2006 +0000
@@ -9,6 +9,10 @@
 static int max_x;
 static int max_y;
 
+static GHashTable *nodes;
+
+static void free_node(gpointer data);
+
 void gnt_screen_take_focus(GntWidget *widget)
 {
 	focus_list = g_list_prepend(focus_list, widget);
@@ -95,6 +99,8 @@
 	max_x = getmaxx(stdscr);
 	max_y = getmaxy(stdscr);
 
+	nodes = g_hash_table_new_full(g_direct_hash, g_direct_equal, NULL, free_node);
+
 	wbkgdset(stdscr, '\0' | COLOR_PAIR(GNT_COLOR_NORMAL));
 	noecho();
 	refresh();
@@ -108,3 +114,83 @@
 	g_main_run(loop);
 }
 
+/*********************************
+ * Stuff for 'window management' *
+ *********************************/
+
+typedef struct
+{
+	GntWidget *me;
+	GList *below;		/* List of widgets below me */
+	GList *above;		/* List of widgets above me */
+} GntNode;
+
+static void
+free_node(gpointer data)
+{
+	GntNode *node = data;
+	g_list_free(node->below);
+	g_list_free(node->above);
+	g_free(node);
+}
+
+static void
+check_intersection(gpointer key, gpointer value, gpointer data)
+{
+	GntNode *n = value;
+	GntNode *nu = data;
+
+	if (value == NULL)
+		return;
+
+	if (n->me->priv.x + n->me->priv.width < nu->me->priv.x)
+		return;
+	if (nu->me->priv.x + nu->me->priv.width < n->me->priv.x)
+		return;
+
+	if (n->me->priv.y + n->me->priv.height < nu->me->priv.y)
+		return;
+	if (nu->me->priv.y + nu->me->priv.height < n->me->priv.y)
+		return;
+
+	n->above = g_list_prepend(n->above, nu->me);
+	nu->below = g_list_prepend(nu->below, n->me);
+}
+
+void gnt_screen_occupy(GntWidget *widget)
+{
+	/* XXX: what happens if this is called more than once for the same widget?
+	 *      perhaps _release first? */
+	GntNode *node = g_new0(GntNode, 1);
+	node->me = widget;
+
+	g_hash_table_foreach(nodes, check_intersection, node);
+	g_hash_table_replace(nodes, widget, node);
+}
+
+void gnt_screen_release(GntWidget *widget)
+{
+	GList *iter;
+	GntNode *node = g_hash_table_lookup(nodes, widget);
+	if (node == NULL || node->below == NULL)	/* Yay! Nothing to do. */
+		return;
+
+	/* XXX: This is not going to work.
+	 *      It will be necessary to build a topology and go from there. */
+	for (iter = node->below; iter; iter = iter->next)
+	{
+		GntWidget *w = iter->data;
+		int left, right, top, bottom;
+
+		left = MAX(widget->priv.x, w->priv.x) - w->priv.x;
+		right = MIN(widget->priv.x + widget->priv.width, w->priv.x + w->priv.width) - w->priv.x;
+		
+		top = MAX(widget->priv.y, w->priv.y) - w->priv.y;
+		bottom = MIN(widget->priv.y + widget->priv.height, w->priv.y + w->priv.height) - w->priv.y;
+		
+		gnt_widget_expose(w, left, top, right - left, bottom - top);
+	}
+
+	g_hash_table_remove(nodes, widget);
+}
+
--- a/console/libgnt/gntwidget.c	Sat Jun 24 22:52:59 2006 +0000
+++ b/console/libgnt/gntwidget.c	Sun Jun 25 03:15:41 2006 +0000
@@ -225,8 +225,6 @@
 	delwin(obj->window);
 	if(!(GNT_WIDGET_FLAGS(obj) & GNT_WIDGET_DESTROYING))
 		g_object_run_dispose(G_OBJECT(obj));
-	/* XXX: This may be the wrong place */
-	/*gnt_screen_remove_widget(obj);*/
 	DEBUG;
 }
 
@@ -264,11 +262,10 @@
 	else
 		werase(widget->window);
 
+#if 0
+	/* XXX: No shadow for now :( */
 	if (!(GNT_WIDGET_FLAGS(widget) & GNT_WIDGET_NO_SHADOW))
 	{
-		/* XXX: Find out the actual windows beneath this window, and 
-		 * draw the shadow on them */
-		/* XXX: Or perhaps do all these from a psedo-WM! */
 		widget->back = newwin(widget->priv.height, widget->priv.width,
 						widget->priv.y + 1, widget->priv.x + 1);
 		wbkgd(widget->back, COLOR_PAIR(GNT_COLOR_SHADOW));
@@ -279,6 +276,7 @@
 		touchline(widget->back, 0, widget->priv.height);
 		wrefresh(widget->back);
 	}
+#endif
 
 	wrefresh(widget->window);
 	g_signal_emit(widget, signals[SIG_DRAW], 0);