Added gtkpacker

Thu Jun 11 14:38:33 CDT 1998 Shawn T. Amundson <amundson@gtk.org>

        * gtk/gtkpacker.c, gtk/gtkpacker.h, gtk/gtk.h, gtk/Makefile.am:
          Added gtkpacker

        * examples/packer/pack.c, examples/packer/Makefile: Added
          gtkpacker example
This commit is contained in:
CDT 1998 Shawn T. Amundson 1998-06-12 00:49:11 +00:00 committed by Shawn Amundson
parent d0ff2dbc79
commit cab220ee8b
14 changed files with 1753 additions and 0 deletions

View File

@ -1,3 +1,11 @@
Thu Jun 11 14:38:33 CDT 1998 Shawn T. Amundson <amundson@gtk.org>
* gtk/gtkpacker.c, gtk/gtkpacker.h, gtk/gtk.h, gtk/Makefile.am:
Added gtkpacker
* examples/packer/pack.c, examples/packer/Makefile: Added
gtkpacker example
Thu Jun 11 13:09:00 1998 Owen Taylor <otaylor@gtk.org>
* gtk/gtktext.c (remove_cache_line): Fixed broken

View File

@ -1,3 +1,11 @@
Thu Jun 11 14:38:33 CDT 1998 Shawn T. Amundson <amundson@gtk.org>
* gtk/gtkpacker.c, gtk/gtkpacker.h, gtk/gtk.h, gtk/Makefile.am:
Added gtkpacker
* examples/packer/pack.c, examples/packer/Makefile: Added
gtkpacker example
Thu Jun 11 13:09:00 1998 Owen Taylor <otaylor@gtk.org>
* gtk/gtktext.c (remove_cache_line): Fixed broken

View File

@ -1,3 +1,11 @@
Thu Jun 11 14:38:33 CDT 1998 Shawn T. Amundson <amundson@gtk.org>
* gtk/gtkpacker.c, gtk/gtkpacker.h, gtk/gtk.h, gtk/Makefile.am:
Added gtkpacker
* examples/packer/pack.c, examples/packer/Makefile: Added
gtkpacker example
Thu Jun 11 13:09:00 1998 Owen Taylor <otaylor@gtk.org>
* gtk/gtktext.c (remove_cache_line): Fixed broken

View File

@ -1,3 +1,11 @@
Thu Jun 11 14:38:33 CDT 1998 Shawn T. Amundson <amundson@gtk.org>
* gtk/gtkpacker.c, gtk/gtkpacker.h, gtk/gtk.h, gtk/Makefile.am:
Added gtkpacker
* examples/packer/pack.c, examples/packer/Makefile: Added
gtkpacker example
Thu Jun 11 13:09:00 1998 Owen Taylor <otaylor@gtk.org>
* gtk/gtktext.c (remove_cache_line): Fixed broken

View File

@ -1,3 +1,11 @@
Thu Jun 11 14:38:33 CDT 1998 Shawn T. Amundson <amundson@gtk.org>
* gtk/gtkpacker.c, gtk/gtkpacker.h, gtk/gtk.h, gtk/Makefile.am:
Added gtkpacker
* examples/packer/pack.c, examples/packer/Makefile: Added
gtkpacker example
Thu Jun 11 13:09:00 1998 Owen Taylor <otaylor@gtk.org>
* gtk/gtktext.c (remove_cache_line): Fixed broken

View File

@ -1,3 +1,11 @@
Thu Jun 11 14:38:33 CDT 1998 Shawn T. Amundson <amundson@gtk.org>
* gtk/gtkpacker.c, gtk/gtkpacker.h, gtk/gtk.h, gtk/Makefile.am:
Added gtkpacker
* examples/packer/pack.c, examples/packer/Makefile: Added
gtkpacker example
Thu Jun 11 13:09:00 1998 Owen Taylor <otaylor@gtk.org>
* gtk/gtktext.c (remove_cache_line): Fixed broken

View File

@ -1,3 +1,11 @@
Thu Jun 11 14:38:33 CDT 1998 Shawn T. Amundson <amundson@gtk.org>
* gtk/gtkpacker.c, gtk/gtkpacker.h, gtk/gtk.h, gtk/Makefile.am:
Added gtkpacker
* examples/packer/pack.c, examples/packer/Makefile: Added
gtkpacker example
Thu Jun 11 13:09:00 1998 Owen Taylor <otaylor@gtk.org>
* gtk/gtktext.c (remove_cache_line): Fixed broken

View File

@ -41,6 +41,8 @@ EXTRA_DIST = \
examples/menu/mfmain.h \
examples/notebook/Makefile \
examples/notebook/notebook.c \
examples/packer/Makefile \
examples/packer/pack.c \
examples/packbox/Makefile \
examples/packbox/packbox.c \
examples/paned/Makefile \

8
examples/packer/Makefile Normal file
View File

@ -0,0 +1,8 @@
CC = gcc
pack: pack.c
$(CC) `gtk-config --cflags` `gtk-config --libs` pack.c -o pack
clean:
rm -f pack

664
examples/packer/pack.c Normal file
View File

@ -0,0 +1,664 @@
/*
* This is a demo of gtkpacker.
*/
#include <gtk/gtk.h>
void add_widget (GtkWidget *widget, gpointer data);
void toggle_side (GtkWidget *widget, gpointer data);
void toggle_anchor (GtkWidget *widget, gpointer data);
void toggle_options (GtkWidget *widget, gpointer data);
typedef struct {
GList *widgets;
GtkWidget *packer;
GtkWidget *current;
GtkPackerChild *pchild;
GtkWidget *button_top;
GtkWidget *button_bottom;
GtkWidget *button_left;
GtkWidget *button_right;
GtkWidget *button_n;
GtkWidget *button_ne;
GtkWidget *button_nw;
GtkWidget *button_e;
GtkWidget *button_w;
GtkWidget *button_s;
GtkWidget *button_se;
GtkWidget *button_sw;
GtkWidget *button_center;
GtkWidget *button_fillx;
GtkWidget *button_filly;
GtkWidget *button_expand;
} Info;
void destroy (GtkWidget *widget, gpointer data)
{
gtk_main_quit ();
}
int
main (int argv, char **argc)
{
GtkWidget *window;
GtkWidget *window_pack;
GtkWidget *top_pack;
GtkWidget *frame;
GtkWidget *packer;
GtkWidget *button_pack;
GtkWidget *button_add;
GtkWidget *button_quit;
GtkWidget *bottom_pack;
GtkWidget *side_frame;
GtkWidget *side_pack;
GtkWidget *button_top;
GtkWidget *button_bottom;
GtkWidget *button_left;
GtkWidget *button_right;
GtkWidget *anchor_table;
GtkWidget *anchor_frame;
GtkWidget *button_n;
GtkWidget *button_ne;
GtkWidget *button_nw;
GtkWidget *button_e;
GtkWidget *button_w;
GtkWidget *button_center;
GtkWidget *button_s;
GtkWidget *button_se;
GtkWidget *button_sw;
GtkWidget *button_expand;
GtkWidget *button_fillx;
GtkWidget *button_filly;
GtkWidget *options_pack;
GtkWidget *options_frame;
GtkWidget *anchor_pack;
Info *info;
gtk_init(&argv, &argc);
info = g_malloc(sizeof(Info));
window = gtk_window_new(GTK_TOPLEVEL);
gtk_signal_connect (GTK_OBJECT (window), "destroy",
GTK_SIGNAL_FUNC (destroy), NULL);
window_pack = gtk_packer_new();
gtk_container_add(GTK_CONTAINER(window), window_pack);
gtk_container_border_width(GTK_CONTAINER(window), 4);
top_pack = gtk_packer_new();
gtk_packer_add_defaults(GTK_PACKER(window_pack),
top_pack,
GTK_SIDE_TOP,
GTK_ANCHOR_CENTER,
GTK_FILL_X | GTK_FILL_Y | GTK_EXPAND);
frame = gtk_frame_new("Packing Area");
gtk_widget_set_usize(frame, 400, 400);
gtk_packer_add(GTK_PACKER(top_pack),
frame,
GTK_SIDE_LEFT,
GTK_ANCHOR_CENTER,
GTK_FILL_X | GTK_FILL_Y | GTK_EXPAND,
0, 8, 8, 0, 0);
packer = gtk_packer_new();
gtk_container_add(GTK_CONTAINER(frame), packer);
button_pack = gtk_packer_new();
gtk_packer_add(GTK_PACKER(top_pack),
button_pack,
GTK_SIDE_LEFT,
GTK_ANCHOR_N,
0,
0, 0, 0, 0, 0);
button_add = gtk_button_new_with_label("Add Button");
gtk_packer_add(GTK_PACKER(top_pack),
button_add,
GTK_SIDE_TOP,
GTK_ANCHOR_CENTER,
GTK_FILL_X,
0, 8, 8, 8, 0);
gtk_signal_connect (GTK_OBJECT (button_add), "clicked",
GTK_SIGNAL_FUNC (add_widget), (gpointer) info);
button_quit = gtk_button_new_with_label("Quit");
gtk_packer_add(GTK_PACKER(top_pack),
button_quit,
GTK_SIDE_TOP,
GTK_ANCHOR_CENTER,
GTK_FILL_X,
0, 8, 8, 0, 0);
gtk_signal_connect_object (GTK_OBJECT (button_quit), "clicked",
GTK_SIGNAL_FUNC (gtk_widget_destroy),
GTK_OBJECT (window));
bottom_pack = gtk_packer_new();
gtk_packer_add_defaults(GTK_PACKER(window_pack),
bottom_pack,
GTK_SIDE_TOP,
GTK_ANCHOR_CENTER,
GTK_FILL_X);
side_frame = gtk_frame_new("Side");
gtk_packer_add(GTK_PACKER(window_pack),
side_frame,
GTK_SIDE_LEFT,
GTK_ANCHOR_W,
GTK_FILL_Y,
0, 10, 10, 0, 0);
side_pack = gtk_packer_new();
gtk_container_add(GTK_CONTAINER(side_frame), side_pack);
button_top = gtk_toggle_button_new_with_label("Top");
button_bottom = gtk_toggle_button_new_with_label("Bottom");
button_left = gtk_toggle_button_new_with_label("Left");
button_right = gtk_toggle_button_new_with_label("Right");
gtk_object_set_data(GTK_OBJECT(button_top), "side", (gpointer) GTK_SIDE_TOP);
gtk_object_set_data(GTK_OBJECT(button_bottom), "side", (gpointer) GTK_SIDE_BOTTOM);
gtk_object_set_data(GTK_OBJECT(button_left), "side", (gpointer) GTK_SIDE_LEFT);
gtk_object_set_data(GTK_OBJECT(button_right), "side", (gpointer) GTK_SIDE_RIGHT);
gtk_widget_set_usize(button_top, 50, -1);
gtk_widget_set_usize(button_bottom, 50, -1);
gtk_widget_set_usize(button_left, 50, -1);
gtk_widget_set_usize(button_right, 50, -1);
gtk_packer_add(GTK_PACKER(side_pack),
button_top,
GTK_SIDE_TOP,
GTK_ANCHOR_CENTER,
0,
0, 5, 5, 0, 0);
gtk_packer_add(GTK_PACKER(side_pack),
button_bottom,
GTK_SIDE_BOTTOM,
GTK_ANCHOR_CENTER,
0,
0, 5, 5, 0, 0);
gtk_packer_add(GTK_PACKER(side_pack),
button_left,
GTK_SIDE_LEFT,
GTK_ANCHOR_CENTER,
0,
0, 10, 5, 0, 0);
gtk_packer_add(GTK_PACKER(side_pack),
button_right,
GTK_SIDE_RIGHT,
GTK_ANCHOR_CENTER,
0,
0, 10, 5, 0, 0);
gtk_signal_connect (GTK_OBJECT (button_top), "toggled",
GTK_SIGNAL_FUNC (toggle_side), (gpointer) info);
gtk_signal_connect (GTK_OBJECT (button_bottom), "toggled",
GTK_SIGNAL_FUNC (toggle_side), (gpointer) info);
gtk_signal_connect (GTK_OBJECT (button_left), "toggled",
GTK_SIGNAL_FUNC (toggle_side), (gpointer) info);
gtk_signal_connect (GTK_OBJECT (button_right), "toggled",
GTK_SIGNAL_FUNC (toggle_side), (gpointer) info);
anchor_frame = gtk_frame_new("Anchor");
gtk_packer_add(GTK_PACKER(window_pack),
anchor_frame,
GTK_SIDE_LEFT,
GTK_ANCHOR_W,
GTK_FILL_Y,
0, 10, 10, 0, 0);
anchor_pack = gtk_packer_new();
gtk_container_add(GTK_CONTAINER(anchor_frame), anchor_pack);
anchor_table = gtk_table_new(3,3,TRUE);
gtk_packer_add(GTK_PACKER(anchor_pack),
anchor_table,
GTK_SIDE_TOP,
GTK_ANCHOR_CENTER,
GTK_FILL_Y | GTK_FILL_X | GTK_PACK_EXPAND,
0, 10, 5, 0, 0);
button_n = gtk_toggle_button_new_with_label("N");
button_s = gtk_toggle_button_new_with_label("S");
button_w = gtk_toggle_button_new_with_label("W");
button_e = gtk_toggle_button_new_with_label("E");
button_ne = gtk_toggle_button_new_with_label("NE");
button_nw = gtk_toggle_button_new_with_label("NW");
button_se = gtk_toggle_button_new_with_label("SE");
button_sw = gtk_toggle_button_new_with_label("SW");
button_center = gtk_toggle_button_new_with_label("");
gtk_object_set_data(GTK_OBJECT(button_n), "anchor", (gpointer) GTK_ANCHOR_N);
gtk_object_set_data(GTK_OBJECT(button_nw), "anchor", (gpointer) GTK_ANCHOR_NW);
gtk_object_set_data(GTK_OBJECT(button_ne), "anchor", (gpointer) GTK_ANCHOR_NE);
gtk_object_set_data(GTK_OBJECT(button_s), "anchor", (gpointer) GTK_ANCHOR_S);
gtk_object_set_data(GTK_OBJECT(button_sw), "anchor", (gpointer) GTK_ANCHOR_SW);
gtk_object_set_data(GTK_OBJECT(button_se), "anchor", (gpointer) GTK_ANCHOR_SE);
gtk_object_set_data(GTK_OBJECT(button_w), "anchor", (gpointer) GTK_ANCHOR_W);
gtk_object_set_data(GTK_OBJECT(button_e), "anchor", (gpointer) GTK_ANCHOR_E);
gtk_object_set_data(GTK_OBJECT(button_center), "anchor", (gpointer) GTK_ANCHOR_CENTER);
gtk_signal_connect (GTK_OBJECT (button_n), "toggled",
GTK_SIGNAL_FUNC (toggle_anchor), (gpointer) info);
gtk_signal_connect (GTK_OBJECT (button_nw), "toggled",
GTK_SIGNAL_FUNC (toggle_anchor), (gpointer) info);
gtk_signal_connect (GTK_OBJECT (button_ne), "toggled",
GTK_SIGNAL_FUNC (toggle_anchor), (gpointer) info);
gtk_signal_connect (GTK_OBJECT (button_s), "toggled",
GTK_SIGNAL_FUNC (toggle_anchor), (gpointer) info);
gtk_signal_connect (GTK_OBJECT (button_sw), "toggled",
GTK_SIGNAL_FUNC (toggle_anchor), (gpointer) info);
gtk_signal_connect (GTK_OBJECT (button_se), "toggled",
GTK_SIGNAL_FUNC (toggle_anchor), (gpointer) info);
gtk_signal_connect (GTK_OBJECT (button_w), "toggled",
GTK_SIGNAL_FUNC (toggle_anchor), (gpointer) info);
gtk_signal_connect (GTK_OBJECT (button_e), "toggled",
GTK_SIGNAL_FUNC (toggle_anchor), (gpointer) info);
gtk_signal_connect (GTK_OBJECT (button_center), "toggled",
GTK_SIGNAL_FUNC (toggle_anchor), (gpointer) info);
gtk_table_attach_defaults(GTK_TABLE(anchor_table),
button_nw,
0, 1, 0, 1);
gtk_table_attach_defaults(GTK_TABLE(anchor_table),
button_n,
1, 2, 0, 1);
gtk_table_attach_defaults(GTK_TABLE(anchor_table),
button_ne,
2, 3, 0, 1);
gtk_table_attach_defaults(GTK_TABLE(anchor_table),
button_w,
0, 1, 1, 2);
gtk_table_attach_defaults(GTK_TABLE(anchor_table),
button_center,
1, 2, 1, 2);
gtk_table_attach_defaults(GTK_TABLE(anchor_table),
button_e,
2, 3, 1, 2);
gtk_table_attach_defaults(GTK_TABLE(anchor_table),
button_sw,
0, 1, 2, 3);
gtk_table_attach_defaults(GTK_TABLE(anchor_table),
button_s,
1, 2, 2, 3);
gtk_table_attach_defaults(GTK_TABLE(anchor_table),
button_se,
2, 3, 2, 3);
options_frame = gtk_frame_new("Options");
gtk_packer_add(GTK_PACKER(window_pack),
options_frame,
GTK_SIDE_LEFT,
GTK_ANCHOR_W,
GTK_FILL_Y,
0, 10, 10, 0, 0);
options_pack = gtk_packer_new();
gtk_container_add(GTK_CONTAINER(options_frame), options_pack);
button_fillx = gtk_toggle_button_new_with_label("Fill X");
button_filly = gtk_toggle_button_new_with_label("Fill Y");
button_expand = gtk_toggle_button_new_with_label("Expand");
gtk_packer_add(GTK_PACKER(options_pack),
button_fillx,
GTK_SIDE_TOP,
GTK_ANCHOR_N,
GTK_FILL_X | GTK_PACK_EXPAND,
0, 10, 5, 0, 0);
gtk_packer_add(GTK_PACKER(options_pack),
button_filly,
GTK_SIDE_TOP,
GTK_ANCHOR_CENTER,
GTK_FILL_X | GTK_PACK_EXPAND,
0, 10, 5, 0, 0);
gtk_packer_add(GTK_PACKER(options_pack),
button_expand,
GTK_SIDE_TOP,
GTK_ANCHOR_S,
GTK_FILL_X | GTK_PACK_EXPAND,
0, 10, 5, 0, 0);
gtk_object_set_data(GTK_OBJECT(button_fillx), "option", (gpointer) GTK_FILL_X);
gtk_object_set_data(GTK_OBJECT(button_filly), "option", (gpointer) GTK_FILL_Y);
gtk_object_set_data(GTK_OBJECT(button_expand), "option", (gpointer) GTK_PACK_EXPAND);
gtk_signal_connect (GTK_OBJECT (button_fillx), "toggled",
GTK_SIGNAL_FUNC (toggle_options), (gpointer) info);
gtk_signal_connect (GTK_OBJECT (button_filly), "toggled",
GTK_SIGNAL_FUNC (toggle_options), (gpointer) info);
gtk_signal_connect (GTK_OBJECT (button_expand), "toggled",
GTK_SIGNAL_FUNC (toggle_options), (gpointer) info);
info->widgets = NULL;
info->packer = packer;
info->button_top = button_top;
info->button_bottom = button_bottom;
info->button_left = button_left;
info->button_right = button_right;
info->button_n = button_n;
info->button_nw = button_nw;
info->button_ne = button_ne;
info->button_e = button_e;
info->button_w = button_w;
info->button_center = button_center;
info->button_s = button_s;
info->button_sw = button_sw;
info->button_se = button_se;
info->button_fillx = button_fillx;
info->button_filly = button_filly;
info->button_expand = button_expand;
add_widget(NULL, (gpointer) info);
gtk_widget_show_all(window);
gtk_main();
return 0;
}
void
toggle_options (GtkWidget *widget, gpointer data)
{
Info *info;
gint option;
GList *list;
GtkPackerChild *pchild;
gint fillx, filly, expand;
info = (Info*) data;
option = (gint) gtk_object_get_data(GTK_OBJECT(widget), "option");
pchild = info->pchild;
if (pchild == NULL) {
abort();
};
fillx = filly = expand = 0;
if (GTK_TOGGLE_BUTTON(info->button_fillx)->active)
fillx = GTK_FILL_X;
if (GTK_TOGGLE_BUTTON(info->button_filly)->active)
filly = GTK_FILL_Y;
if (GTK_TOGGLE_BUTTON(info->button_expand)->active)
expand = GTK_PACK_EXPAND;
gtk_packer_configure(GTK_PACKER(info->packer),
info->current,
pchild->side,
pchild->anchor,
fillx | filly | expand,
pchild->border_width,
pchild->padX,
pchild->padY,
pchild->iPadX,
pchild->iPadY);
}
void
toggle_anchor (GtkWidget *widget, gpointer data)
{
Info *info;
gint anchor;
GList *list;
GtkPackerChild *pchild;
info = (Info*) data;
if (GTK_TOGGLE_BUTTON(widget)->active) {
anchor = (gint) gtk_object_get_data(GTK_OBJECT(widget), "anchor");
pchild = info->pchild;
if (pchild == NULL) {
abort();
};
gtk_packer_configure(GTK_PACKER(info->packer),
info->current,
pchild->side,
anchor,
pchild->options,
pchild->border_width,
pchild->padX,
pchild->padY,
pchild->iPadX,
pchild->iPadY);
if (info->button_n != widget) {
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_n),0);
gtk_widget_set_sensitive(info->button_n, 1);
}
if (info->button_nw != widget) {
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_nw),0);
gtk_widget_set_sensitive(info->button_nw, 1);
}
if (info->button_ne != widget) {
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_ne),0);
gtk_widget_set_sensitive(info->button_ne, 1);
}
if (info->button_s != widget) {
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_s),0);
gtk_widget_set_sensitive(info->button_s, 1);
}
if (info->button_sw != widget) {
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_sw),0);
gtk_widget_set_sensitive(info->button_sw, 1);
}
if (info->button_se != widget) {
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_se),0);
gtk_widget_set_sensitive(info->button_se, 1);
}
if (info->button_e != widget) {
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_e),0);
gtk_widget_set_sensitive(info->button_e, 1);
}
if (info->button_w != widget) {
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_w),0);
gtk_widget_set_sensitive(info->button_w, 1);
}
if (info->button_center != widget) {
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_center),0);
gtk_widget_set_sensitive(info->button_center, 1);
}
gtk_widget_set_sensitive(widget, 0);
}
}
void
toggle_side (GtkWidget *widget, gpointer data)
{
Info *info;
gint side;
GList *list;
GtkPackerChild *pchild;
info = (Info*) data;
if (GTK_TOGGLE_BUTTON(widget)->active) {
side = (gint) gtk_object_get_data(GTK_OBJECT(widget), "side");
pchild = info->pchild;
if (pchild == NULL) {
abort();
};
gtk_packer_configure(GTK_PACKER(info->packer),
info->current,
side,
pchild->anchor,
pchild->options,
pchild->border_width,
pchild->padX,
pchild->padY,
pchild->iPadX,
pchild->iPadY);
if (info->button_top != widget) {
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_top),0);
gtk_widget_set_sensitive(info->button_top, 1);
}
if (info->button_bottom != widget) {
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_bottom),0);
gtk_widget_set_sensitive(info->button_bottom, 1);
}
if (info->button_left != widget) {
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_left),0);
gtk_widget_set_sensitive(info->button_left, 1);
}
if (info->button_right != widget) {
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_right),0);
gtk_widget_set_sensitive(info->button_right, 1);
}
gtk_widget_set_sensitive(widget, 0);
}
}
void
set_widget (GtkWidget *w, gpointer data) {
Info *info;
GList *list;
GtkWidget *widget;
GtkPackerChild *pchild;
gint options;
if (GTK_TOGGLE_BUTTON(w)->active) {
info = (Info*) data;
info->current = w;
pchild = NULL;
list = g_list_first(GTK_PACKER(info->packer)->children);
while (list) {
if (((GtkPackerChild*)(list->data))->widget == info->current) {
pchild = (GtkPackerChild*)(list->data);
break;
}
list = g_list_next(list);
}
if (pchild == NULL) {
abort();
};
info->pchild = pchild;
switch (pchild->side) {
case GTK_SIDE_TOP:
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_top),1);
break;
case GTK_SIDE_BOTTOM:
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_bottom),1);
break;
case GTK_SIDE_LEFT:
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_left),1);
break;
case GTK_SIDE_RIGHT:
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_right),1);
break;
default:
printf("foo... side == %d\n", pchild->side);
};
switch (pchild->anchor) {
case GTK_ANCHOR_N:
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_n),1);
break;
case GTK_ANCHOR_NW:
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_nw),1);
break;
case GTK_ANCHOR_NE:
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_ne),1);
break;
case GTK_ANCHOR_S:
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_s),1);
break;
case GTK_ANCHOR_SW:
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_sw),1);
break;
case GTK_ANCHOR_SE:
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_se),1);
break;
case GTK_ANCHOR_W:
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_w),1);
break;
case GTK_ANCHOR_E:
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_e),1);
break;
case GTK_ANCHOR_CENTER:
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_center),1);
break;
default:
};
options = pchild->options;
if (options & GTK_PACK_EXPAND) {
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_expand),1);
} else {
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_expand),0);
}
if (options & GTK_FILL_X) {
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_fillx),1);
} else {
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_fillx),0);
}
if (options & GTK_FILL_Y) {
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_filly),1);
} else {
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(info->button_filly),0);
}
gtk_widget_set_sensitive(w, 0);
list = g_list_first(info->widgets);
while (list) {
widget = (GtkWidget*)(list->data);
if (widget != info->current) {
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(widget),0);
gtk_widget_set_sensitive(widget, 1);
}
list = g_list_next(list);
}
}
}
void
add_widget (GtkWidget *w, gpointer data)
{
static gint n = 0;
GtkPacker *packer;
GtkWidget *widget;
gchar str[255];
Info *info;
info = (Info*) data;
packer = GTK_PACKER(info->packer);
sprintf(str, "%d", n);
widget = gtk_toggle_button_new_with_label(str);
gtk_widget_set_usize(widget, 50, 50);
gtk_container_add(GTK_CONTAINER(packer), widget);
gtk_widget_show(widget);
gtk_signal_connect (GTK_OBJECT (widget), "toggled",
GTK_SIGNAL_FUNC (set_widget), (gpointer) info);
info->widgets = g_list_append(info->widgets, (gpointer) widget);
gtk_toggle_button_set_state(GTK_TOGGLE_BUTTON(widget),1);
set_widget(widget, info);
n++;
}

View File

@ -61,6 +61,7 @@ libgtk_1_1_la_SOURCES = \
gtknotebook.c \
gtkobject.c \
gtkoptionmenu.c \
gtkpacker.c \
gtkpaned.c \
gtkpixmap.c \
gtkpreview.c \
@ -162,6 +163,7 @@ gtkinclude_HEADERS = \
gtknotebook.h \
gtkobject.h \
gtkoptionmenu.h \
gtkpacker.h \
gtkpaned.h \
gtkpixmap.h \
gtkpreview.h \

View File

@ -78,6 +78,7 @@
#include <gtk/gtknotebook.h>
#include <gtk/gtkobject.h>
#include <gtk/gtkoptionmenu.h>
#include <gtk/gtkpacker.h>
#include <gtk/gtkpaned.h>
#include <gtk/gtkpixmap.h>
#include <gtk/gtkpreview.h>

878
gtk/gtkpacker.c Normal file
View File

@ -0,0 +1,878 @@
/* GTK - The GIMP Toolkit
* Copyright (C) 1995-1997 Peter Mattis, Spencer Kimball and Josh MacDonald
*
* GtkPacker Widget
* Copyright (C) 1998 Shawn T. Amundson, James S. Mitchell, Michael L. Staiger
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Library General Public
* License as published by the Free Software Foundation; either
* version 2 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Library General Public License for more details.
*
* You should have received a copy of the GNU Library General Public
* License along with this library; if not, write to the
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
* Boston, MA 02111-1307, USA.
*/
/*
* This file contains modified code derived from Tk 8.0. Below is the header of
* the relevant file. The file 'license.terms' is included inline below.
*
* tkPack.c --
*
* This file contains code to implement the "packer"
* geometry manager for Tk.
*
* Copyright (c) 1990-1994 The Regents of the University of California.
* Copyright (c) 1994-1995 Sun Microsystems, Inc.
*
* See the file "license.terms" for information on usage and redistribution
* of this file, and for a DISCLAIMER OF ALL WARRANTIES.
*
* SCCS: @(#) tkPack.c 1.64 96/05/03 10:51:52
*
* The file license.terms is below. NOTE: THE FOLLOWING APPLIES ONLY TO
* PORTIONS DERIVED FROM TK 8.0. THE LICENSE FOR THIS FILE IS LGPL, AS
* STATED ABOVE AND ALLOWED BELOW.
-- BEGIN license.terms --
This software is copyrighted by the Regents of the University of
California, Sun Microsystems, Inc., and other parties. The following
terms apply to all files associated with the software unless explicitly
disclaimed in individual files.
The authors hereby grant permission to use, copy, modify, distribute,
and license this software and its documentation for any purpose, provided
that existing copyright notices are retained in all copies and that this
notice is included verbatim in any distributions. No written agreement,
license, or royalty fee is required for any of the authorized uses.
Modifications to this software may be copyrighted by their authors
and need not follow the licensing terms described here, provided that
the new terms are clearly indicated on the first page of each file where
they apply.
IN NO EVENT SHALL THE AUTHORS OR DISTRIBUTORS BE LIABLE TO ANY PARTY
FOR DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
ARISING OUT OF THE USE OF THIS SOFTWARE, ITS DOCUMENTATION, OR ANY
DERIVATIVES THEREOF, EVEN IF THE AUTHORS HAVE BEEN ADVISED OF THE
POSSIBILITY OF SUCH DAMAGE.
THE AUTHORS AND DISTRIBUTORS SPECIFICALLY DISCLAIM ANY WARRANTIES,
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE, AND NON-INFRINGEMENT. THIS SOFTWARE
IS PROVIDED ON AN "AS IS" BASIS, AND THE AUTHORS AND DISTRIBUTORS HAVE
NO OBLIGATION TO PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR
MODIFICATIONS.
GOVERNMENT USE: If you are acquiring this software on behalf of the
U.S. government, the Government shall have only "Restricted Rights"
in the software and related documentation as defined in the Federal
Acquisition Regulations (FARs) in Clause 52.227.19 (c) (2). If you
are acquiring the software on behalf of the Department of Defense, the
software shall be classified as "Commercial Computer Software" and the
Government shall have only "Restricted Rights" as defined in Clause
252.227-7013 (c) (1) of DFARs. Notwithstanding the foregoing, the
authors grant the U.S. Government and others acting in its behalf
permission to use and distribute the software in accordance with the
terms specified in this license.
-- END license.terms --
*
*/
#include "gtkpacker.h"
static void gtk_packer_class_init (GtkPackerClass *klass);
static void gtk_packer_init (GtkPacker *packer);
static void gtk_packer_map (GtkWidget *widget);
static void gtk_packer_unmap (GtkWidget *widget);
static void gtk_packer_draw (GtkWidget *widget,
GdkRectangle *area);
static gint gtk_packer_expose (GtkWidget *widget,
GdkEventExpose *event);
static void gtk_packer_size_request (GtkWidget *widget,
GtkRequisition *requisition);
static void gtk_packer_size_allocate (GtkWidget *widget,
GtkAllocation *allocation);
static void gtk_packer_container_add (GtkContainer *container,
GtkWidget *child);
static void gtk_packer_remove (GtkContainer *container,
GtkWidget *widget);
static void gtk_packer_foreach (GtkContainer *container,
GtkCallback callback,
gpointer callback_data);
static GtkPackerClass *parent_class;
GtkType
gtk_packer_get_type (void)
{
static GtkType packer_type = 0;
if (!packer_type)
{
GtkTypeInfo packer_info =
{
"GtkPacker",
sizeof (GtkPacker),
sizeof (GtkPackerClass),
(GtkClassInitFunc) gtk_packer_class_init,
(GtkObjectInitFunc) gtk_packer_init,
(GtkArgSetFunc) NULL,
(GtkArgGetFunc) NULL
};
packer_type = gtk_type_unique (gtk_container_get_type (), &packer_info);
}
return packer_type;
}
static void
gtk_packer_class_init (GtkPackerClass *klass)
{
GtkWidgetClass *widget_class;
GtkContainerClass *container_class;
widget_class = (GtkWidgetClass*) klass;
container_class = (GtkContainerClass*) klass;
parent_class = gtk_type_class (gtk_container_get_type ());
widget_class->map = gtk_packer_map;
widget_class->unmap = gtk_packer_unmap;
widget_class->draw = gtk_packer_draw;
widget_class->expose_event = gtk_packer_expose;
widget_class->size_request = gtk_packer_size_request;
widget_class->size_allocate = gtk_packer_size_allocate;
container_class->add = gtk_packer_container_add;
container_class->remove = gtk_packer_remove;
container_class->foreach = gtk_packer_foreach;
}
static void
gtk_packer_init (GtkPacker *packer)
{
GTK_WIDGET_SET_FLAGS (packer, GTK_NO_WINDOW | GTK_BASIC);
packer->children = NULL;
packer->spacing = 0;
}
void
gtk_packer_set_spacing (GtkPacker *packer, gint spacing)
{
g_return_if_fail (packer != NULL);
g_return_if_fail (GTK_IS_PACKER (packer));
if (spacing != packer->spacing)
{
packer->spacing = spacing;
gtk_widget_queue_resize(GTK_WIDGET(packer));
}
};
GtkWidget*
gtk_packer_new (void)
{
return GTK_WIDGET (gtk_type_new (gtk_packer_get_type ()));
}
static void
redo_defaults_children (GtkPacker *packer) {
GList *list;
GtkPackerChild *child;
list = g_list_first(packer->children);
while (list != NULL)
{
child = list->data;
if (child->use_default)
{
child->border_width = packer->default_border_width;
child->padX = packer->default_padX;
child->padY = packer->default_padY;
child->iPadX = packer->default_iPadX;
child->iPadY = packer->default_iPadY;
gtk_widget_queue_resize(GTK_WIDGET(packer));
}
list = g_list_next(list);
}
}
void
gtk_packer_set_default_border_width (GtkPacker *packer, gint border)
{
g_return_if_fail (packer != NULL);
g_return_if_fail (GTK_IS_PACKER (packer));
if (packer->default_border_width != border)
{
packer->default_border_width = border;;
redo_defaults_children(packer);
}
}
void
gtk_packer_set_default_pad(GtkPacker *packer, gint padX ,gint padY)
{
g_return_if_fail (packer != NULL);
g_return_if_fail (GTK_IS_PACKER (packer));
if (packer->default_padX != padX ||
packer->default_padY != padY)
{
packer->default_padX = padX;;
packer->default_padY = padY;;
redo_defaults_children(packer);
}
}
void
gtk_packer_set_default_ipad(GtkPacker *packer, gint iPadX ,gint iPadY)
{
g_return_if_fail (packer != NULL);
g_return_if_fail (GTK_IS_PACKER (packer));
if (packer->default_iPadX != iPadX ||
packer->default_iPadY != iPadY) {
packer->default_iPadX = iPadX;;
packer->default_iPadY = iPadY;;
redo_defaults_children(packer);
}
}
static void
gtk_packer_container_add (GtkContainer *packer, GtkWidget *child)
{
gtk_packer_add_defaults(GTK_PACKER(packer), child,
GTK_SIDE_TOP, GTK_ANCHOR_CENTER, 0);
}
void
gtk_packer_add_defaults (GtkPacker *packer, GtkWidget *child,
GtkSide side,
GtkAnchor anchor,
GtkPackerOptions options)
{
GtkPackerChild *pchild;
g_return_if_fail (packer != NULL);
g_return_if_fail (GTK_IS_PACKER (packer));
g_return_if_fail (child != NULL);
pchild = (GtkPackerChild*) g_malloc(sizeof(GtkPackerChild));
pchild->widget = child;
pchild->side = side;
pchild->options = options;
pchild->anchor = anchor;
pchild->use_default = 1;
pchild->border_width = packer->default_border_width;
pchild->padX = packer->default_padX;
pchild->padY = packer->default_padY;
pchild->iPadX = packer->default_iPadX;
pchild->iPadY = packer->default_iPadY;
packer->children = g_list_append(packer->children, (gpointer) pchild);
gtk_widget_set_parent (child, GTK_WIDGET (packer));
if (GTK_WIDGET_VISIBLE (GTK_WIDGET (packer)))
{
if (GTK_WIDGET_REALIZED (GTK_WIDGET (packer)) &&
!GTK_WIDGET_REALIZED (child))
gtk_widget_realize (child);
if (GTK_WIDGET_MAPPED (GTK_WIDGET (packer)) &&
!GTK_WIDGET_MAPPED (child))
gtk_widget_map (child);
}
if (GTK_WIDGET_VISIBLE (child) && GTK_WIDGET_VISIBLE (packer))
gtk_widget_queue_resize (child);
}
void
gtk_packer_add (GtkPacker *packer,
GtkWidget *child,
GtkSide side,
GtkAnchor anchor,
GtkPackerOptions options,
gint border_width,
gint padX,
gint padY,
gint iPadX,
gint iPadY)
{
GtkPackerChild *pchild;
g_return_if_fail (packer != NULL);
g_return_if_fail (GTK_IS_PACKER (packer));
g_return_if_fail (child != NULL);
pchild = (GtkPackerChild*) g_malloc(sizeof(GtkPackerChild));
pchild->widget = child;
pchild->side = side;
pchild->options = options;
pchild->anchor = anchor;
pchild->use_default = 0;
pchild->border_width = border_width;
pchild->padX = padX;
pchild->padY = padY;
pchild->iPadX = iPadX;
pchild->iPadY = iPadY;
packer->children = g_list_append(packer->children, (gpointer) pchild);
gtk_widget_set_parent (child, GTK_WIDGET (packer));
if (GTK_WIDGET_VISIBLE (GTK_WIDGET (packer)))
{
if (GTK_WIDGET_REALIZED (GTK_WIDGET (packer)) &&
!GTK_WIDGET_REALIZED (child))
gtk_widget_realize (child);
if (GTK_WIDGET_MAPPED (GTK_WIDGET (packer)) &&
!GTK_WIDGET_MAPPED (child))
gtk_widget_map (child);
}
if (GTK_WIDGET_VISIBLE (child) && GTK_WIDGET_VISIBLE (packer))
gtk_widget_queue_resize (child);
}
void
gtk_packer_configure (GtkPacker *packer,
GtkWidget *child,
GtkSide side,
GtkAnchor anchor,
GtkPackerOptions options,
gint border_width,
gint padX,
gint padY,
gint ipadX,
gint ipadY)
{
GList *list;
GtkPackerChild *pchild;
g_return_if_fail (packer != NULL);
g_return_if_fail (GTK_IS_PACKER (packer));
g_return_if_fail (child != NULL);
list = g_list_first(packer->children);
while (list != NULL)
{
pchild = (GtkPackerChild*) list->data;
if (pchild->widget == child)
{
pchild->side = side;
pchild->anchor = anchor;
pchild->options = options;
pchild->use_default = 0;
pchild->border_width = border_width;
pchild->padX = padX;
pchild->padY = padY;
pchild->iPadX = ipadX;
pchild->iPadY = ipadY;
if (GTK_WIDGET_VISIBLE (child) && GTK_WIDGET_VISIBLE (packer))
gtk_widget_queue_resize (child);
return;
}
list = g_list_next(list);
}
g_warning ("gtk_packer_configure(): couldn't find child `%s' amongst the packer's children", gtk_type_name (GTK_OBJECT_TYPE (child)));
}
static void
gtk_packer_remove (GtkContainer *container, GtkWidget *widget)
{
GtkPacker *packer;
GtkPackerChild *child;
GList *children;
gint visible;
g_return_if_fail (container != NULL);
g_return_if_fail (widget != NULL);
packer = GTK_PACKER (container);
children = g_list_first(packer->children);
while (children)
{
child = children->data;
if (child->widget == widget)
{
visible = GTK_WIDGET_VISIBLE (widget);
gtk_widget_unparent (widget);
packer->children = g_list_remove_link (packer->children, children);
g_list_free (children);
g_free (child);
if (visible && GTK_WIDGET_VISIBLE (container))
gtk_widget_queue_resize (GTK_WIDGET (container));
break;
}
children = g_list_next(children);
}
}
static void
gtk_packer_map (GtkWidget *widget)
{
GtkPacker *packer;
GtkPackerChild *child;
GList *children;
g_return_if_fail (widget != NULL);
g_return_if_fail (GTK_IS_PACKER (widget));
packer = GTK_PACKER (widget);
GTK_WIDGET_SET_FLAGS (packer, GTK_MAPPED);
children = g_list_first(packer->children);
while (children != NULL)
{
child = children->data;
children = g_list_next(children);
if (GTK_WIDGET_VISIBLE (child->widget) &&
!GTK_WIDGET_MAPPED (child->widget))
gtk_widget_map (child->widget);
}
}
static void
gtk_packer_unmap (GtkWidget *widget)
{
GtkPacker *packer;
GtkPackerChild *child;
GList *children;
g_return_if_fail (widget != NULL);
g_return_if_fail (GTK_IS_PACKER (widget));
packer = GTK_PACKER (widget);
GTK_WIDGET_UNSET_FLAGS (packer, GTK_MAPPED);
children = g_list_first(packer->children);
while (children)
{
child = children->data;
children = g_list_next(children);
if (GTK_WIDGET_VISIBLE (child->widget) &&
GTK_WIDGET_MAPPED (child->widget))
gtk_widget_unmap (child->widget);
}
}
static void
gtk_packer_draw (GtkWidget *widget, GdkRectangle *area)
{
GtkPacker *packer;
GtkPackerChild *child;
GdkRectangle child_area;
GList *children;
g_return_if_fail (widget != NULL);
g_return_if_fail (GTK_IS_PACKER (widget));
if (GTK_WIDGET_DRAWABLE (widget))
{
packer = GTK_PACKER (widget);
children = g_list_first(packer->children);
while (children != NULL)
{
child = children->data;
children = g_list_next(children);
if (gtk_widget_intersect (child->widget, area, &child_area))
gtk_widget_draw (child->widget, &child_area);
}
}
}
static gint
gtk_packer_expose (GtkWidget *widget, GdkEventExpose *event)
{
GtkPacker *packer;
GtkPackerChild *child;
GdkEventExpose child_event;
GList *children;
g_return_val_if_fail (widget != NULL, FALSE);
g_return_val_if_fail (GTK_IS_PACKER (widget), FALSE);
g_return_val_if_fail (event != NULL, FALSE);
if (GTK_WIDGET_DRAWABLE (widget))
{
packer = GTK_PACKER (widget);
child_event = *event;
children = g_list_first(packer->children);
while (children)
{
child = children->data;
children = g_list_next(children);
if (GTK_WIDGET_NO_WINDOW (child->widget) &&
gtk_widget_intersect (child->widget, &event->area, &child_event.area))
gtk_widget_event (child->widget, (GdkEvent*) &child_event);
}
}
return FALSE;
}
static void
gtk_packer_size_request (GtkWidget *widget, GtkRequisition *requisition)
{
GtkPacker *packer;
GtkPackerChild *child;
GList *children;
gint nvis_vert_children;
gint nvis_horz_children;
gint width, height;
gint maxWidth, maxHeight;
g_return_if_fail (widget != NULL);
g_return_if_fail (GTK_IS_PACKER (widget));
g_return_if_fail (requisition != NULL);
packer = GTK_PACKER (widget);
requisition->width = 0;
requisition->height = 0;
nvis_vert_children = 0;
nvis_horz_children = 0;
width = height = maxWidth = maxHeight = 0;
children = g_list_first(packer->children);
while (children != NULL)
{
child = children->data;
if (GTK_WIDGET_VISIBLE (child->widget))
{
gtk_widget_size_request (child->widget, &child->widget->requisition);
if((child->side == GTK_SIDE_TOP) || (child->side == GTK_SIDE_BOTTOM))
{
maxWidth = MAX(maxWidth, (child->widget->requisition.width
+ 2 * child->border_width
+ child->padX + child->iPadX
+ width));
height += child->widget->requisition.height
+ 2 * child->border_width
+ child->padY + child->iPadY;
}
else
{
maxHeight = MAX(maxHeight,(child->widget->requisition.height
+ 2 * child->border_width +
child->padY + child->iPadY
+ height));
width += child->widget->requisition.width
+ 2 * child->border_width
+ child->padX + child->iPadX;
}
}
children = g_list_next(children);
}
requisition->width = MAX (maxWidth, width);
requisition->height = MAX (maxHeight, height);
}
static gint
YExpansion (GList *children, gint cavityHeight)
{
GList *list;
GtkPackerChild *child;
GtkWidget *widget;
gint numExpand, minExpand, curExpand;
gint childHeight;
minExpand = cavityHeight;
numExpand = 0;
list = children;
while (list != NULL)
{
child = list->data;
widget = child->widget;
childHeight = widget->requisition.height + 2 * child->border_width +
child->iPadY + child->padY;
if ((child->side == GTK_SIDE_LEFT) || (child->side == GTK_SIDE_RIGHT))
{
curExpand = (cavityHeight - childHeight)/numExpand;
minExpand = MIN(minExpand, curExpand);
}
else
{
cavityHeight -= childHeight;
if (child->options & GTK_PACK_EXPAND)
numExpand++;
}
list = g_list_next(list);
}
curExpand = cavityHeight/numExpand;
if (curExpand < minExpand)
minExpand = curExpand;
return (minExpand < 0) ? 0 : minExpand;
}
static gint
XExpansion (GList *children, gint cavityWidth)
{
GList *list;
GtkPackerChild *child;
GtkWidget *widget;
gint numExpand, minExpand, curExpand;
gint childWidth;
minExpand = cavityWidth;
numExpand = 0;
list = children;
while (list != NULL)
{
child = list->data;
widget = child->widget;
childWidth = widget->requisition.width + 2 * child->border_width
+ child->iPadX + child->padX;
if ((child->side == GTK_SIDE_TOP) || (child->side == GTK_SIDE_BOTTOM))
{
curExpand = (cavityWidth - childWidth)/numExpand;
minExpand = MIN(minExpand, curExpand);
}
else
{
cavityWidth -= childWidth;
if (child->options & GTK_PACK_EXPAND)
numExpand++;
}
list = g_list_next(list);
}
curExpand = cavityWidth/numExpand;
if (curExpand < minExpand)
minExpand = curExpand;
return (minExpand < 0) ? 0 : minExpand;
};
static void
gtk_packer_size_allocate (GtkWidget *widget, GtkAllocation *allocation)
{
GtkPacker *packer;
GtkAllocation child_allocation;
GList *list;
GtkPackerChild *child;
gint cavityX, cavityY;
gint cavityWidth, cavityHeight;
gint width, height, x, y;
gint frameHeight, frameWidth, frameX, frameY;
gint borderX, borderY;
g_return_if_fail (widget != NULL);
g_return_if_fail (GTK_IS_PACKER (widget));
g_return_if_fail (allocation != NULL);
x = y = 0;
widget->allocation = *allocation;
packer = GTK_PACKER(widget);
cavityX = widget->allocation.x;
cavityY = widget->allocation.y;
cavityWidth = widget->allocation.width;
cavityHeight = widget->allocation.height;
list = g_list_first(packer->children);
while (list != NULL)
{
child = list->data;
if ((child->side == GTK_SIDE_TOP) || (child->side == GTK_SIDE_BOTTOM))
{
frameWidth = cavityWidth;
frameHeight = child->widget->requisition.height +
2 * child->border_width + child->padY + child->iPadY;
if (child->options & GTK_PACK_EXPAND)
frameHeight += YExpansion(list, cavityHeight);
cavityHeight -= frameHeight;
if (cavityHeight < 0)
{
frameHeight += cavityHeight;
cavityHeight = 0;
}
frameX = cavityX;
if (child->side == GTK_SIDE_TOP)
{
frameY = cavityY;
cavityY += frameHeight;
}
else
{
frameY = cavityY + cavityHeight;
}
}
else
{
frameHeight = cavityHeight;
frameWidth = child->widget->requisition.width +
2 * child->border_width + child->padX + child->iPadX;
if (child->options & GTK_PACK_EXPAND)
frameWidth += XExpansion(list, cavityWidth);
cavityWidth -= frameWidth;
if (cavityWidth < 0) {
frameWidth += cavityWidth;
cavityWidth = 0;
}
frameY = cavityY;
if (child->side == GTK_SIDE_LEFT)
{
frameX = cavityX;
cavityX += frameWidth;
}
else
{
frameX = cavityX + cavityWidth;
}
}
borderX = child->padX + 2 * child->border_width;
borderY = child->padY + 2 * child->border_width;
width = child->widget->requisition.width +
2 * child->border_width + child->iPadX;
if ((child->options & GTK_FILL_X) || (width > (frameWidth - borderX)))
width = frameWidth - borderX;
height = child->widget->requisition.height +
2 * child->border_width + child->iPadY;
if ((child->options & GTK_FILL_Y) || (height > (frameHeight - borderY)))
height = frameHeight - borderY;
borderX /= 2;
borderY /= 2;
switch (child->anchor)
{
case GTK_ANCHOR_N:
x = frameX + (frameWidth - width)/2;
y = frameY + borderY;
break;
case GTK_ANCHOR_NE:
x = frameX + frameWidth - width - borderX;
y = frameY + borderY;
break;
case GTK_ANCHOR_E:
x = frameX + frameWidth - width - borderX;
y = frameY + (frameHeight - height)/2;
break;
case GTK_ANCHOR_SE:
x = frameX + frameWidth - width - borderX;
y = frameY + frameHeight - height - borderY;
break;
case GTK_ANCHOR_S:
x = frameX + (frameWidth - width)/2;
y = frameY + frameHeight - height - borderY;
break;
case GTK_ANCHOR_SW:
x = frameX + borderX;
y = frameY + frameHeight - height - borderY;
break;
case GTK_ANCHOR_W:
x = frameX + borderX;
y = frameY + (frameHeight - height)/2;
break;
case GTK_ANCHOR_NW:
x = frameX + borderX;
y = frameY + borderY;
break;
case GTK_ANCHOR_CENTER:
x = frameX + (frameWidth - width)/2;
y = frameY + (frameHeight - height)/2;
break;
default:
g_warning ("gtk_packer_size_allocate(): bad anchor type: %d", child->anchor);
}
if (width <= 0 || height <= 0)
{
gtk_widget_unmap(child->widget);
}
else
{
child_allocation.x = x;
child_allocation.y = y;
child_allocation.width = width;
child_allocation.height = height;
gtk_widget_size_allocate (child->widget, &child_allocation);
if (GTK_WIDGET_MAPPED (widget) &&
!(GTK_WIDGET_MAPPED (child->widget)))
gtk_widget_map(child->widget);
}
list = g_list_next(list);
}
}
static void
gtk_packer_foreach (GtkContainer *container,
GtkCallback callback,
gpointer callback_data)
{
GtkPacker *packer;
GtkPackerChild *child;
GList *children;
g_return_if_fail (container != NULL);
g_return_if_fail (GTK_IS_PACKER (container));
g_return_if_fail (callback != NULL);
packer = GTK_PACKER (container);
children = g_list_first(packer->children);
while (children != NULL)
{
child = children->data;
children = g_list_next(children);
(* callback) (child->widget, callback_data);
}
}

142
gtk/gtkpacker.h Normal file
View File

@ -0,0 +1,142 @@
/* GTK - The GIMP Toolkit
* Copyright (C) 1995-1997 Peter Mattis, Spencer Kimball and Josh MacDonald
*
* GtkPacker Widget
* Copyright (C) 1998 Shawn T. Amundson, James S. Mitchell, Michael L. Staiger
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Library General Public
* License as published by the Free Software Foundation; either
* version 2 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Library General Public License for more details.
*
* You should have received a copy of the GNU Library General Public
* License along with this library; if not, write to the
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
* Boston, MA 02111-1307, USA.
*/
#ifndef __GTK_PACKER_H__
#define __GTK_PACKER_H__
#include <gtk/gtkcontainer.h>
#ifdef __cplusplus
extern "C" {
#endif /* __cplusplus */
#define GTK_TYPE_PACKER (gtk_packer_get_type ())
#define GTK_PACKER(obj) (GTK_CHECK_CAST ((obj), GTK_TYPE_PACKER, GtkPacker))
#define GTK_PACKER_CLASS(klass) (GTK_CHECK_CLASS_CAST ((klass), GTK_TYPE_PACKER, GtkPackerClass))
#define GTK_IS_PACKER(obj) (GTK_CHECK_TYPE ((obj), GTK_TYPE_PACKER))
#define GTK_IS_PACKER_CLASS(klass) (GTK_CHECK_CLASS_TYPE ((klass), GTK_TYPE_PACKER))
typedef struct _GtkPacker GtkPacker;
typedef struct _GtkPackerClass GtkPackerClass;
typedef struct _GtkPackerChild GtkPackerChild;
typedef enum {
GTK_PACK_EXPAND = 1 << 0,
GTK_FILL_X = 1 << 1,
GTK_FILL_Y = 1 << 2
} GtkPackerOptions;
typedef enum {
GTK_SIDE_TOP,
GTK_SIDE_BOTTOM,
GTK_SIDE_LEFT,
GTK_SIDE_RIGHT
} GtkSide;
typedef enum {
GTK_ANCHOR_CENTER,
GTK_ANCHOR_N,
GTK_ANCHOR_NW,
GTK_ANCHOR_NE,
GTK_ANCHOR_S,
GTK_ANCHOR_SW,
GTK_ANCHOR_SE,
GTK_ANCHOR_W,
GTK_ANCHOR_E
} GtkAnchor;
struct _GtkPackerChild {
GtkWidget *widget;
GtkAnchor anchor;
GtkSide side;
GtkPackerOptions options;
gint use_default;
gint border_width;
gint padX;
gint padY;
gint iPadX;
gint iPadY;
};
struct _GtkPacker {
GtkContainer parent;
GList *children;
gint spacing;
gint default_border_width;
gint default_padX;
gint default_padY;
gint default_iPadX;
gint default_iPadY;
};
struct _GtkPackerClass {
GtkContainerClass parent_class;
};
GtkType gtk_packer_get_type (void);
GtkWidget* gtk_packer_new (void);
void gtk_packer_add_defaults (GtkPacker *packer,
GtkWidget *child,
GtkSide side,
GtkAnchor anchor,
GtkPackerOptions options);
void gtk_packer_add (GtkPacker *packer,
GtkWidget *child,
GtkSide side,
GtkAnchor anchor,
GtkPackerOptions options,
gint border_width,
gint padX,
gint padY,
gint ipadX,
gint ipadY);
void gtk_packer_configure (GtkPacker *packer,
GtkWidget *child,
GtkSide side,
GtkAnchor anchor,
GtkPackerOptions options,
gint border_width,
gint padX,
gint padY,
gint ipadX,
gint ipadY);
void gtk_packer_set_spacing (GtkPacker *packer, gint spacing);
void gtk_packer_set_default_border_width(GtkPacker *packer, gint border);
void gtk_packer_set_default_pad(GtkPacker *packer, gint padX ,gint padY);
void gtk_packer_set_default_ipad(GtkPacker *packer, gint iPadX ,gint iPadY);
#ifdef __cplusplus
}
#endif /* __cplusplus */
#endif /* __GTK_PACKER_H__ */