4 * Copyright (c) Tuomo Valkonen 1999-2007.
6 * See the included file LICENSE for details.
11 #include <libtu/obj.h>
12 #include <libtu/objp.h>
13 #include <libtu/minmax.h>
14 #include <libtu/map.h>
15 #include <libmainloop/defer.h>
29 #include "frame-pointer.h"
30 #include "frame-draw.h"
38 #include "framedpholder.h"
42 extern bool frame_set_background(WFrame *frame, bool set_always);
43 extern void frame_initialise_gr(WFrame *frame);
45 static bool frame_initialise_titles(WFrame *frame);
46 static void frame_free_titles(WFrame *frame);
48 static void frame_add_mode_bindmaps(WFrame *frame);
51 WHook *frame_managed_changed_hook=NULL;
53 #define FORWARD_CWIN_RQGEOM(FRAME) framemode_is_floating(frame_mode(FRAME))
54 #define USE_MINMAX(FRAME) framemode_is_floating(frame_mode(FRAME))
55 #define DEST_EMPTY(FRAME) framemode_is_floating(frame_mode(FRAME))
58 WFrameMode framemode_unalt(WFrameMode mode)
60 if(mode==FRAME_MODE_UNKNOWN_ALT)
61 return FRAME_MODE_UNKNOWN;
62 else if(mode==FRAME_MODE_TILED_ALT)
63 return FRAME_MODE_TILED;
64 else if(mode==FRAME_MODE_FLOATING_ALT)
65 return FRAME_MODE_FLOATING;
66 else if(mode==FRAME_MODE_TRANSIENT_ALT)
67 return FRAME_MODE_TRANSIENT;
73 static WFrameMode framemode_is_floating(WFrameMode mode)
75 WFrameMode modea=framemode_unalt(mode);
77 return (modea==FRAME_MODE_FLOATING || modea==FRAME_MODE_TRANSIENT);
81 /*{{{ Destroy/create frame */
84 bool frame_init(WFrame *frame, WWindow *parent, const WFitParams *fp,
94 frame->tab_dragged_idx=-1;
99 frame->tr_mode=GR_TRANSPARENCY_DEFAULT;
101 frame->bar_brush=NULL;
104 frame->bar_max_width_q=1.0;
105 frame->quasiact_source=NULL;
107 gr_stylespec_init(&frame->baseattr);
109 if(!mplex_init((WMPlex*)frame, parent, fp))
112 frame_initialise_gr(frame);
113 frame_initialise_titles(frame);
115 region_add_bindmap((WRegion*)frame, ioncore_frame_bindmap);
116 region_add_bindmap((WRegion*)frame, ioncore_mplex_bindmap);
118 frame_add_mode_bindmaps(frame);
120 mplex_managed_geom((WMPlex*)frame, &mg);
123 frame->flags|=FRAME_SHADED;
125 ((WRegion*)frame)->flags|=REGION_PLEASE_WARP;
131 WFrame *create_frame(WWindow *parent, const WFitParams *fp, WFrameMode mode)
133 CREATEOBJ_IMPL(WFrame, frame, (p, parent, fp, mode));
137 void frame_deinit(WFrame *frame)
139 frame_free_titles(frame);
140 frame_release_brushes(frame);
141 gr_stylespec_unalloc(&frame->baseattr);
142 mplex_deinit((WMPlex*)frame);
149 /*{{{ Mode switching */
152 static void frame_add_mode_bindmaps(WFrame *frame)
154 WFrameMode modea=framemode_unalt(frame->mode);
156 if(modea==FRAME_MODE_FLOATING){
157 region_add_bindmap((WRegion*)frame, ioncore_mplex_toplevel_bindmap);
158 region_add_bindmap((WRegion*)frame, ioncore_frame_toplevel_bindmap);
159 region_add_bindmap((WRegion*)frame, ioncore_frame_floating_bindmap);
160 }else if(modea==FRAME_MODE_TRANSIENT){
161 region_add_bindmap((WRegion*)frame, ioncore_frame_transient_bindmap);
162 region_add_bindmap((WRegion*)frame, ioncore_frame_floating_bindmap);
164 /* mode==FRAME_MODE_TILED || mode==FRAME_MODE_TILED_ALT || mode==FRAME_MODE_UNKNOWN */
165 region_add_bindmap((WRegion*)frame, ioncore_mplex_toplevel_bindmap);
166 region_add_bindmap((WRegion*)frame, ioncore_frame_toplevel_bindmap);
167 region_add_bindmap((WRegion*)frame, ioncore_frame_tiled_bindmap);
172 void frame_set_mode(WFrame *frame, WFrameMode mode)
174 if(frame->mode==mode)
177 frame_clear_shape(frame);
179 frame_release_brushes(frame);
181 region_remove_bindmap((WRegion*)frame, ioncore_mplex_toplevel_bindmap);
182 region_remove_bindmap((WRegion*)frame, ioncore_frame_toplevel_bindmap);
183 region_remove_bindmap((WRegion*)frame, ioncore_frame_tiled_bindmap);
184 region_remove_bindmap((WRegion*)frame, ioncore_frame_floating_bindmap);
185 region_remove_bindmap((WRegion*)frame, ioncore_frame_transient_bindmap);
189 frame_add_mode_bindmaps(frame);
191 frame_initialise_gr(frame);
193 mplex_fit_managed(&frame->mplex);
194 frame_recalc_bar(frame, TRUE);
195 frame_set_background(frame, TRUE);
199 WFrameMode frame_mode(WFrame *frame)
205 static StringIntMap frame_modes[]={
206 {"unknown", FRAME_MODE_UNKNOWN},
207 {"unknown-alt", FRAME_MODE_UNKNOWN_ALT},
208 {"tiled", FRAME_MODE_TILED},
209 {"tiled-alt", FRAME_MODE_TILED_ALT},
210 {"floating", FRAME_MODE_FLOATING},
211 {"floating-alt", FRAME_MODE_FLOATING_ALT},
212 {"transient", FRAME_MODE_TRANSIENT},
213 {"transient-alt", FRAME_MODE_TRANSIENT_ALT},
222 EXTL_EXPORT_AS(WFrame, mode)
223 const char *frame_mode_extl(WFrame *frame)
225 return stringintmap_key(frame_modes, frame->mode, NULL);
230 * Set frame mode (one of
231 * \codestr{unknown}, \codestr{tiled}, \codestr{floating}, \codestr{transient},
232 * or any of these suffixed with \codestr{-alt}).
234 EXTL_EXPORT_AS(WFrame, set_mode)
235 bool frame_set_mode_extl(WFrame *frame, const char *modestr)
240 idx=stringintmap_ndx(frame_modes, modestr);
244 frame_set_mode(frame, frame_modes[idx].value);
256 int frame_tab_at_x(WFrame *frame, int x)
261 frame_bar_geom(frame, &bg);
263 if(x>=bg.x+bg.w || x<bg.x)
268 for(tab=0; tab<FRAME_MCOUNT(frame); tab++){
269 tx+=frame_nth_tab_w(frame, tab);
278 int frame_nth_tab_x(WFrame *frame, int n)
284 x+=frame_nth_tab_w(frame, i);
290 static int frame_nth_tab_w_iw(WFrame *frame, int n, bool inner)
293 GrBorderWidths bdw=GR_BORDER_WIDTHS_INIT;
294 int m=FRAME_MCOUNT(frame);
297 frame_bar_geom(frame, &bg);
302 if(frame->bar_brush!=NULL)
303 grbrush_get_border_widths(frame->bar_brush, &bdw);
306 w=bg.w-bdw.left-bdw.right-(bdw.tb_ileft+bdw.tb_iright+bdw.spacing)*(m-1);
311 /* Get n:th tab's portion of free area */
312 w=(((n+1)*w)/m-(n*w)/m);
314 /* Add n:th tab's borders back */
316 w+=(n==0 ? bdw.left : bdw.tb_ileft);
317 w+=(n==m-1 ? bdw.right : bdw.tb_iright+bdw.spacing);
324 int frame_nth_tab_w(WFrame *frame, int n)
326 return frame_nth_tab_w_iw(frame, n, FALSE);
330 int frame_nth_tab_iw(WFrame *frame, int n)
332 return frame_nth_tab_w_iw(frame, n, TRUE);
337 void frame_update_attr_nth(WFrame *frame, int i)
341 if(i<0 || i>=frame->titles_n)
344 frame_update_attr(frame, i, mplex_mx_nth((WMPlex*)frame, i));
348 static void frame_update_attrs(WFrame *frame)
354 FRAME_MX_FOR_ALL(sub, frame, tmp){
355 frame_update_attr(frame, i, sub);
361 static void frame_free_titles(WFrame *frame)
365 if(frame->titles!=NULL){
366 for(i=0; i<frame->titles_n; i++){
367 if(frame->titles[i].text)
368 free(frame->titles[i].text);
369 gr_stylespec_unalloc(&frame->titles[i].attr);
378 static void do_init_title(WFrame *frame, int i, WRegion *sub)
380 frame->titles[i].text=NULL;
381 frame->titles[i].iw=frame_nth_tab_iw(frame, i);
383 gr_stylespec_init(&frame->titles[i].attr);
385 frame_update_attr(frame, i, sub);
389 static bool frame_initialise_titles(WFrame *frame)
391 int i, n=FRAME_MCOUNT(frame);
393 frame_free_titles(frame);
398 frame->titles=ALLOC_N(GrTextElem, n);
399 if(frame->titles==NULL)
403 if(FRAME_MCOUNT(frame)==0){
404 do_init_title(frame, 0, NULL);
409 FRAME_MX_FOR_ALL(sub, frame, tmp){
410 do_init_title(frame, i, sub);
415 frame_recalc_bar(frame, FALSE);
424 /*{{{ Resize and reparent */
427 bool frame_fitrep(WFrame *frame, WWindow *par, const WFitParams *fp)
429 WRectangle old_geom, mg;
430 bool wchg=(REGION_GEOM(frame).w!=fp->g.w);
431 bool hchg=(REGION_GEOM(frame).h!=fp->g.h);
433 old_geom=REGION_GEOM(frame);
435 window_do_fitrep(&(frame->mplex.win), par, &(fp->g));
437 mplex_managed_geom((WMPlex*)frame, &mg);
441 frame->flags|=(FRAME_SHADED|FRAME_SAVED_VERT);
442 frame->saved_y=old_geom.y;
443 frame->saved_h=old_geom.h;
445 frame->flags&=~FRAME_SHADED;
447 frame->flags&=~FRAME_MAXED_VERT;
452 frame->flags|=(FRAME_MIN_HORIZ|FRAME_SAVED_HORIZ);
453 frame->saved_x=old_geom.x;
454 frame->saved_w=old_geom.w;
456 frame->flags&=~FRAME_MIN_HORIZ;
458 frame->flags&=~FRAME_MAXED_HORIZ;
462 mplex_fit_managed((WMPlex*)frame);
463 mplex_size_changed((WMPlex*)frame, wchg, hchg);
470 void frame_size_hints(WFrame *frame, WSizeHints *hints_ret)
477 mplex_managed_geom((WMPlex*)frame, &subgeom);
479 woff=maxof(REGION_GEOM(frame).w-subgeom.w, 0);
480 hoff=maxof(REGION_GEOM(frame).h-subgeom.h, 0);
482 if(FRAME_CURRENT(frame)!=NULL)
483 region_size_hints(FRAME_CURRENT(frame), hints_ret);
485 sizehints_clear(hints_ret);
487 FRAME_MX_FOR_ALL(sub, frame, tmp){
488 sizehints_adjust_for(hints_ret, sub);
491 if(!USE_MINMAX(frame)){
492 hints_ret->max_set=0;
493 hints_ret->min_set=0;
494 /*hints_ret->base_set=0;*/
495 hints_ret->aspect_set=0;
496 hints_ret->no_constrain=FALSE;
497 /*hints_ret->no_constrain=TRUE;*/
500 if(!hints_ret->min_set){
501 hints_ret->min_width=0;
502 hints_ret->min_height=0;
503 hints_ret->min_set=TRUE;
506 if(!hints_ret->base_set){
507 hints_ret->base_width=0;
508 hints_ret->base_height=0;
509 hints_ret->base_set=TRUE;
512 hints_ret->base_width+=woff;
513 hints_ret->base_height+=hoff;
514 hints_ret->max_width+=woff;
515 hints_ret->max_height+=hoff;
516 hints_ret->min_width+=woff;
517 hints_ret->min_height+=hoff;
519 if(frame->barmode==FRAME_BAR_SHAPED){
520 int f=frame->flags&(FRAME_SHADED|FRAME_SHADED_TOGGLE);
522 if(f==FRAME_SHADED || f==FRAME_SHADED_TOGGLE){
523 hints_ret->min_height=frame->bar_h;
524 hints_ret->max_height=frame->bar_h;
525 hints_ret->base_height=frame->bar_h;
526 if(!hints_ret->max_set){
527 hints_ret->max_width=INT_MAX;
528 hints_ret->max_set=TRUE;
541 static void frame_quasiactivation(WFrame *frame, Obj *src, bool act)
543 if(frame->quasiact_source==src || act){
546 was=(frame->quasiact_source!=NULL);
548 frame->quasiact_source=(act ? src : NULL);
550 is=(frame->quasiact_source!=NULL);
553 frame_quasiactivity_change(frame);
554 if(!REGION_IS_ACTIVE(frame))
555 window_draw((WWindow*)frame, FALSE);
561 static bool actinact(WRegion *reg, bool act)
563 WPHolder *returnph=region_get_return(reg);
568 if(returnph==NULL || pholder_stale(returnph))
571 tgt=pholder_target(returnph);
573 frame=OBJ_CAST(tgt, WFrame);
578 /* Show quasiactivation for stuff detached from
579 * groups contained in the frame as well.
581 WGroup *grp=OBJ_CAST(tgt, WGroup);
583 frame=REGION_MANAGER_CHK(grp, WFrame);
589 frame_quasiactivation(frame, src, act);
595 static bool activated(WRegion *reg)
597 return actinact(reg, TRUE);
601 static bool inactivated(WRegion *reg)
603 return actinact(reg, FALSE);
607 void ioncore_frame_quasiactivation_notify(WRegion *reg,
610 if(how==ioncore_g.notifies.activated ||
611 how==ioncore_g.notifies.pseudoactivated){
613 }else if(how==ioncore_g.notifies.inactivated ||
614 how==ioncore_g.notifies.pseudoinactivated){
616 }else if(how==ioncore_g.notifies.set_return){
617 if(REGION_IS_ACTIVE(reg) || REGION_IS_PSEUDOACTIVE(reg))
619 }else if(how==ioncore_g.notifies.unset_return){
620 if(REGION_IS_ACTIVE(reg) || REGION_IS_PSEUDOACTIVE(reg))
629 /*{{{ Client window rqgeom */
632 static void frame_managed_rqgeom_absolute(WFrame *frame, WRegion *sub,
633 const WRQGeomParams *rq,
636 if(!FORWARD_CWIN_RQGEOM(frame)){
637 region_managed_rqgeom_absolute_default((WRegion*)frame, sub,
640 WRQGeomParams rq2=RQGEOMPARAMS_INIT;
641 int gravity=ForgetGravity;
646 rq2.flags=rq->flags&(REGION_RQGEOM_WEAK_ALL
647 |REGION_RQGEOM_TRYONLY
648 |REGION_RQGEOM_ABSOLUTE);
650 if(rq->flags®ION_RQGEOM_GRAVITY)
653 mplex_managed_geom(&frame->mplex, &off);
656 off.w=REGION_GEOM(frame).w-off.w;
657 off.h=REGION_GEOM(frame).h-off.h;
659 rq2.geom.w=maxof(rq2.geom.w+off.w, 0);
660 rq2.geom.h=maxof(rq2.geom.h+off.h, 0);
662 /*region_size_hints_correct((WRegion*)frame, &(geom.w), &(geom.h), TRUE);*/
664 /* If WEAK_? is set, then geom.(x|y) is root-relative as it was not
665 * requested by the client and clientwin_handle_configure_request has
666 * no better guess. Otherwise the coordinates are those requested by
667 * the client (modulo borders/gravity) and we interpret them to be
668 * root-relative coordinates for this frame modulo gravity.
670 if(rq->flags®ION_RQGEOM_WEAK_X)
673 rq2.geom.x+=xgravity_deltax(gravity, -off.x, off.x+off.w);
675 if(rq->flags®ION_RQGEOM_WEAK_Y)
678 rq2.geom.y+=xgravity_deltay(gravity, -off.y, off.y+off.h);
680 region_rqgeom((WRegion*)frame, &rq2, geomret);
695 /*{{{ Frame recreate pholder stuff */
698 static WFramedPHolder *frame_make_recreate_pholder(WFrame *frame)
702 WFramedParam fparam=FRAMEDPARAM_INIT;
704 ph=region_make_return_pholder((WRegion*)frame);
710 fparam.mode=frame->mode;
712 fph=create_framedpholder(ph, &fparam);
715 destroy_obj((Obj*)ph);
723 static void mplex_flatten_phs(WMPlex *mplex)
728 FOR_ALL_NODES_ON_LLIST(node, mplex->mx_list, tmp){
729 WMPlexPHolder *last=(mplex->mx_phs==NULL ? NULL : mplex->mx_phs->prev);
730 mplex_move_phs(mplex, node, last, NULL);
735 static void frame_modify_pholders(WFrame *frame)
738 WMPlexPHolder *phs, *ph;
740 mplex_flatten_phs(&frame->mplex);
742 if(frame->mplex.mx_phs==NULL)
745 fph=frame_make_recreate_pholder(frame);
750 phs=frame->mplex.mx_phs;
751 frame->mplex.mx_phs=NULL;
753 phs->recreate_pholder=fph;
755 for(ph=phs; ph!=NULL; ph=ph->next)
756 watch_reset(&ph->mplex_watch);
760 bool frame_rescue_clientwins(WFrame *frame, WRescueInfo *info)
762 frame_modify_pholders(frame);
763 return mplex_rescue_clientwins(&frame->mplex, info);
773 bool frame_set_shaded(WFrame *frame, int sp)
775 bool set=(frame->flags&FRAME_SHADED);
776 bool nset=libtu_do_setparam(sp, set);
777 WRQGeomParams rq=RQGEOMPARAMS_INIT;
784 rq.flags=REGION_RQGEOM_H_ONLY;
785 rq.geom=REGION_GEOM(frame);
788 if(!(frame->flags&FRAME_SAVED_VERT))
790 rq.geom.h=frame->saved_h;
792 if(frame->barmode==FRAME_BAR_NONE){
794 }else if(frame->barmode==FRAME_BAR_SHAPED){
795 rq.geom.h=frame->bar_h;
799 frame_border_inner_geom(frame, &tmp);
801 rq.geom.h=rq.geom.h-tmp.h;
805 frame->flags|=FRAME_SHADED_TOGGLE;
807 region_rqgeom((WRegion*)frame, &rq, NULL);
809 frame->flags&=~FRAME_SHADED_TOGGLE;
811 return (frame->flags&FRAME_SHADED);
816 * Set shading state according to the parameter \var{how}
817 * (\codestr{set}, \codestr{unset}, or \codestr{toggle}).
818 * Resulting state is returned, which may not be
819 * what was requested.
821 EXTL_EXPORT_AS(WFrame, set_shaded)
822 bool frame_set_shaded_extl(WFrame *frame, const char *how)
824 return frame_set_shaded(frame, libtu_string_to_setparam(how));
829 * Is \var{frame} shaded?
833 bool frame_is_shaded(WFrame *frame)
835 return ((frame->flags&FRAME_SHADED)!=0);
840 * Is the attribute \var{attr} set?
842 bool frame_is_grattr(WFrame *frame, const char *attr)
844 GrAttr a=stringstore_alloc(attr);
845 bool set=gr_stylespec_isset(&frame->baseattr, a);
851 bool frame_set_grattr(WFrame *frame, GrAttr a, int sp)
853 bool set=gr_stylespec_isset(&frame->baseattr, a);
854 bool nset=libtu_do_setparam(sp, set);
858 gr_stylespec_set(&frame->baseattr, a);
860 gr_stylespec_unset(&frame->baseattr, a);
861 window_draw((WWindow*)frame, TRUE);
869 * Set extra drawing engine attributes for the frame.
870 * The parameter \var{attr} is the attribute, and \var{how} is
871 * one of \codestr{set}, \codestr{unset}, or \codestr{toggle}.
873 EXTL_EXPORT_AS(WFrame, set_grattr)
874 bool frame_set_grattr_extl(WFrame *frame, const char *attr, const char *how)
877 GrAttr a=stringstore_alloc(attr);
878 bool ret=frame_set_grattr(frame, a, libtu_string_to_setparam(how));
887 void frame_managed_notify(WFrame *frame, WRegion *sub, WRegionNotify how)
889 if(how==ioncore_g.notifies.activated ||
890 how==ioncore_g.notifies.inactivated ||
891 how==ioncore_g.notifies.name ||
892 how==ioncore_g.notifies.activity ||
893 how==ioncore_g.notifies.sub_activity ||
894 how==ioncore_g.notifies.tag){
896 frame_update_attrs(frame);
897 frame_recalc_bar(frame, FALSE);
898 frame_draw_bar(frame, FALSE);
903 static void frame_size_changed_default(WFrame *frame,
904 bool wchg, bool hchg)
906 int bar_w=frame->bar_w;
909 frame_recalc_bar(frame, TRUE);
911 if(frame->barmode==FRAME_BAR_SHAPED &&
912 ((!wchg && hchg) || (wchg && bar_w==frame->bar_w))){
913 frame_set_shape(frame);
918 static void frame_managed_changed(WFrame *frame, int mode, bool sw,
923 if(mode==MPLEX_CHANGE_REMOVE && (Obj*)reg==frame->quasiact_source){
924 /* Reset indirect quasiactivation through group that
927 frame->quasiact_source=NULL;
928 frame_quasiactivity_change(frame);
931 if(mode!=MPLEX_CHANGE_SWITCHONLY)
932 frame_initialise_titles(frame);
934 frame_update_attrs(frame);
937 need_draw=!frame_set_background(frame, FALSE);
940 frame_draw_bar(frame, mode!=MPLEX_CHANGE_SWITCHONLY);
942 mplex_call_changed_hook((WMPlex*)frame,
943 frame_managed_changed_hook,
948 WRegion *frame_managed_disposeroot(WFrame *frame, WRegion *reg)
950 if(DEST_EMPTY(frame) &&
951 frame->mplex.mgd!=NULL &&
952 frame->mplex.mgd->reg==reg &&
953 frame->mplex.mgd->mgr_next==NULL){
954 WRegion *tmp=region_disposeroot((WRegion*)frame);
955 return (tmp!=NULL ? tmp : reg);
962 int frame_default_index(WFrame *frame)
964 return ioncore_g.frame_default_index;
971 /*{{{ prepare_manage_transient */
974 WPHolder *frame_prepare_manage_transient(WFrame *frame,
975 const WClientWin *transient,
976 const WManageParams *param,
979 /* Transient manager searches should not cross tiled frames
980 * unless explicitly floated.
982 if(framemode_is_floating(frame_mode(frame)) ||
983 extl_table_is_bool_set(transient->proptab, "float")){
984 return region_prepare_manage_transient_default((WRegion*)frame,
1000 ExtlTab frame_get_configuration(WFrame *frame)
1002 ExtlTab tab=mplex_get_configuration(&frame->mplex);
1004 extl_table_sets_i(tab, "mode", frame->mode);
1006 if(frame->flags&FRAME_SAVED_VERT){
1007 extl_table_sets_i(tab, "saved_y", frame->saved_y);
1008 extl_table_sets_i(tab, "saved_h", frame->saved_h);
1011 if(frame->flags&FRAME_SAVED_HORIZ){
1012 extl_table_sets_i(tab, "saved_x", frame->saved_x);
1013 extl_table_sets_i(tab, "saved_w", frame->saved_w);
1021 void frame_do_load(WFrame *frame, ExtlTab tab)
1026 if(extl_table_gets_i(tab, "saved_x", &p) &&
1027 extl_table_gets_i(tab, "saved_w", &s)){
1030 frame->flags|=FRAME_SAVED_HORIZ;
1033 if(extl_table_gets_i(tab, "saved_y", &p) &&
1034 extl_table_gets_i(tab, "saved_h", &s)){
1037 frame->flags|=FRAME_SAVED_VERT;
1040 mplex_load_contents(&frame->mplex, tab);
1044 WRegion *frame_load(WWindow *par, const WFitParams *fp, ExtlTab tab)
1046 int mode=FRAME_MODE_UNKNOWN;
1049 extl_table_gets_i(tab, "mode", &mode);
1051 frame=create_frame(par, fp, mode);
1054 frame_do_load(frame, tab);
1056 if(DEST_EMPTY(frame) && frame->mplex.mgd==NULL){
1057 destroy_obj((Obj*)frame);
1061 return (WRegion*)frame;
1068 /*{{{ Dynfuntab and class info */
1071 static DynFunTab frame_dynfuntab[]={
1072 {region_size_hints, frame_size_hints},
1074 {mplex_managed_changed, frame_managed_changed},
1075 {mplex_size_changed, frame_size_changed_default},
1076 {region_managed_notify, frame_managed_notify},
1078 {region_activated, frame_activated},
1079 {region_inactivated, frame_inactivated},
1081 {(DynFun*)window_press, (DynFun*)frame_press},
1083 {(DynFun*)region_get_configuration,
1084 (DynFun*)frame_get_configuration},
1089 {mplex_managed_geom,
1090 frame_managed_geom},
1095 {(DynFun*)region_fitrep,
1096 (DynFun*)frame_fitrep},
1098 {(DynFun*)region_managed_disposeroot,
1099 (DynFun*)frame_managed_disposeroot},
1101 {region_managed_rqgeom_absolute,
1102 frame_managed_rqgeom_absolute},
1104 {(DynFun*)mplex_default_index,
1105 (DynFun*)frame_default_index},
1107 {(DynFun*)region_prepare_manage_transient,
1108 (DynFun*)frame_prepare_manage_transient},
1110 {(DynFun*)region_rescue_clientwins,
1111 (DynFun*)frame_rescue_clientwins},
1118 IMPLCLASS(WFrame, WMPlex, frame_deinit, frame_dynfuntab);