comparison src/skins/ui_dock.c @ 3158:8b97f9560dc3

More clean-up of roll-up code (should fix bug #37; if not, it's a WM problem).
author John Lindgren <john.lindgren@tds.net>
date Fri, 01 May 2009 16:59:54 -0400
parents 9978be206b93
children 1ffcad5f406c
comparison
equal deleted inserted replaced
3157:d73418aa0db3 3158:8b97f9560dc3
250 window->y = y + dw->offset_y; 250 window->y = y + dw->offset_y;
251 } 251 }
252 } 252 }
253 } 253 }
254 254
255 static GList * 255 void dock_window_resize (GtkWindow * widget, int width, int height) {
256 shade_move_list(GList * list, GtkWindow * widget, gint offset) 256 GdkGeometry hints;
257 { 257 hints.min_width = width;
258 gint x, y, w, h; 258 hints.min_height = height;
259 GList *node; 259 hints.max_width = width;
260 DockedWindow *dw; 260 hints.max_height = height;
261 261 gtk_window_resize (widget, width, height);
262 gtk_window_get_position(widget, &x, &y); 262 gtk_window_set_geometry_hints (widget, 0, & hints,
263 gtk_window_get_size(widget, &w, &h); 263 GDK_HINT_MIN_SIZE | GDK_HINT_MAX_SIZE);
264 264 }
265 265
266 for (node = list; node;) { 266 static void move_attached (GtkWindow * window, GList * * others, int offset) {
267 gint dx, dy, dwidth, dheight; 267 int x, y, width, height, x2, y2;
268 268 GList * move, * scan, * next;
269 dw = node->data; 269 gtk_window_get_position (window, & x, & y);
270 gtk_window_get_position(dw->w, &dx, &dy); 270 gtk_window_get_size (window, & width, & height);
271 gtk_window_get_size(dw->w, &dwidth, &dheight); 271 move = 0;
272 if (is_docked(x, y, w, h, dx, dy, dwidth, dheight) && 272 for (scan = * others; scan; scan = next) {
273 ((dx + dwidth) > x && dx < (x + w))) { 273 next = g_list_next (scan);
274 list = g_list_remove_link(list, node); 274 gtk_window_get_position (scan->data, & x2, & y2);
275 g_list_free_1(node); 275 if (y2 == y + height) {
276 276 * others = g_list_remove_link (* others, scan);
277 node = list = shade_move_list(list, dw->w, offset); 277 move = g_list_concat (move, scan);
278 } 278 }
279 else 279 }
280 node = g_list_next(node); 280 for (; move; move = g_list_delete_link (move, move))
281 } 281 move_attached (move->data, others, offset);
282 gtk_window_move(widget, x, y + offset); 282 gtk_window_move (window, x, y + offset);
283 return list; 283 }
284 } 284
285 285 void dock_shade (GList * window_list, GtkWindow * window, int new_height) {
286 /* 286 int x, y, width, height, x2, y2;
287 * Builds a list of the windows in the list of DockedWindows "winlist" 287 GList * move, * others, * scan, * next;
288 * that are docked to the top or bottom of the window, and recursively 288 if (! config.show_wm_decorations) {
289 * adds all windows that are docked to the top or bottom of that window, 289 gtk_window_get_position (window, & x, & y);
290 * and so on... 290 gtk_window_get_size (window, & width, & height);
291 * Note: The data in "winlist" is not copied. 291 others = g_list_copy (window_list);
292 */ 292 others = g_list_remove (others, window);
293 static GList * 293 move = 0;
294 find_shade_list(GtkWindow * widget, GList * winlist, GList * shade_list) 294 for (scan = others; scan; scan = next) {
295 { 295 next = g_list_next (scan);
296 gint x, y, w, h; 296 gtk_window_get_position (scan->data, & x2, & y2);
297 gint dx, dy, dwidth, dheight; 297 if (y2 == y + height) {
298 GList *node; 298 others = g_list_remove_link (others, scan);
299 299 move = g_list_concat (move, scan);
300 gtk_window_get_position(widget, &x, &y); 300 }
301 gtk_window_get_size(widget, &w, &h); 301 }
302 for (node = winlist; node; node = g_list_next(node)) { 302 for (; move; move = g_list_delete_link (move, move))
303 DockedWindow *dw = node->data; 303 move_attached (move->data, & others, new_height - height);
304 if (g_list_find_custom 304 g_list_free (others);
305 (shade_list, dw, (GCompareFunc) docked_list_compare)) 305 }
306 continue; 306 dock_window_resize (window, width, new_height);
307 gtk_window_get_position(dw->w, &dx, &dy);
308 gtk_window_get_size(dw->w, &dwidth, &dheight);
309
310 /* FIXME. Is the is_docked() necessary? */
311 if (is_docked(x, y, w, h, dx, dy, dwidth, dheight) &&
312 ((dx + dwidth) > x && dx < (x + w))) {
313 shade_list = g_list_append(shade_list, dw);
314 shade_list = find_shade_list(dw->w, winlist, shade_list);
315 }
316 }
317 return shade_list;
318 }
319
320 void
321 dock_window_resize(GtkWindow * widget, gint new_w, gint new_h, gint w, gint h)
322 {
323 GdkGeometry hints;
324 hints.min_width = new_w;
325 hints.min_height = new_h;
326 hints.max_width = new_w;
327 hints.max_height = new_h;
328 gtk_window_resize (widget, new_w, new_h);
329 gtk_window_set_geometry_hints (widget, 0, & hints,
330 GDK_HINT_MIN_SIZE | GDK_HINT_MAX_SIZE);
331 }
332
333 void
334 dock_shade(GList * window_list, GtkWindow * widget, gint new_h)
335 {
336 gint x, y, w, h, off_y, orig_off_y;
337 GList *node, *docked_list, *slist;
338 DockedWindow *dw;
339
340 gtk_window_get_position(widget, &x, &y);
341 gtk_window_get_size(widget, &w, &h);
342
343 if (config.show_wm_decorations) {
344 dock_window_resize(widget, w, new_h, w, h);
345 return;
346 }
347
348 docked_list = get_docked_list(NULL, window_list, widget, 0, 0);
349 slist = find_shade_list(widget, docked_list, NULL);
350
351 off_y = new_h - h;
352 do {
353 orig_off_y = off_y;
354 for (node = slist; node; node = g_list_next(node)) {
355 gint dx, dy, dwidth, dheight;
356
357 dw = node->data;
358 if (dw->w == widget)
359 continue;
360 gtk_window_get_position(dw->w, &dx, &dy);
361 gtk_window_get_size(dw->w, &dwidth, &dheight);
362 if ((dy >= y) && ((dy + off_y + dheight) > gdk_screen_height()))
363 off_y -= (dy + off_y + dheight) - gdk_screen_height();
364 else if ((dy >= y) && ((dy + dheight) == gdk_screen_height()))
365 off_y = 0;
366
367 if (((dy >= y) && ((dy + off_y) < 0)))
368 off_y -= dy + off_y;
369 if ((dy < y) && ((dy + (off_y - (new_h - h))) < 0))
370 off_y -= dy + (off_y - (new_h - h));
371 }
372 } while (orig_off_y != off_y);
373 if (slist) {
374 GList *mlist = g_list_copy(slist);
375
376 /* Remove this widget from the list */
377 for (node = mlist; node; node = g_list_next(node)) {
378 dw = node->data;
379 if (dw->w == widget) {
380 mlist = g_list_remove_link(mlist, node);
381 g_list_free_1(node);
382 break;
383 }
384 }
385 for (node = mlist; node;) {
386 GList *temp;
387 gint dx, dy, dwidth, dheight;
388
389 dw = node->data;
390
391 gtk_window_get_position(dw->w, &dx, &dy);
392 gtk_window_get_size(dw->w, &dwidth, &dheight);
393 /*
394 * Find windows that are directly docked to this window,
395 * move it, and any windows docked to that window again
396 */
397 if (is_docked(x, y, w, h, dx, dy, dwidth, dheight) &&
398 ((dx + dwidth) > x && dx < (x + w))) {
399 mlist = g_list_remove_link(mlist, node);
400 g_list_free_1(node);
401 if (dy > y)
402 temp = shade_move_list(mlist, dw->w, off_y);
403 else if (off_y - (new_h - h) != 0)
404 temp = shade_move_list(mlist, dw->w, off_y - (new_h - h));
405 else
406 temp = mlist;
407 node = mlist = temp;
408 }
409 else
410 node = g_list_next(node);
411 }
412 g_list_free(mlist);
413 }
414 g_list_free(slist);
415 free_docked_list(docked_list);
416 dock_window_resize(widget, w, new_h, w, h);
417 } 307 }
418 308
419 void 309 void
420 dock_move_press(GList * window_list, GtkWindow * w, 310 dock_move_press(GList * window_list, GtkWindow * w,
421 GdkEventButton * event, gboolean move_list) 311 GdkEventButton * event, gboolean move_list)