home *** CD-ROM | disk | FTP | other *** search
/ OS/2 Shareware BBS: 22 gnu / 22-gnu.zip / gwm18a.zip / wob.c < prev    next >
C/C++ Source or Header  |  1995-07-03  |  11KB  |  540 lines

  1. /* Copyright 1989 GROUPE BULL -- See license conditions in file COPYRIGHT
  2.  * Copyright 1989 Massachusetts Institute of Technology
  3.  */
  4. /*******************************************************\
  5. *                                 *
  6. *     BULL WINDOW MANAGER for X11                *
  7. *                                 *
  8. *         module managing Wobs.                *
  9. * Object Oriented Programming, but NO reference count!  *
  10. *                                 *
  11. \*******************************************************/
  12.  
  13. /*  include  */
  14.  
  15. #include        "EXTERN.h"
  16. #include     "gwm.h"
  17. #include    "wl_atom.h"
  18. #include    "wl_list.h"
  19. #include    "wl_number.h"
  20. #include    "wl_cursor.h"
  21. #include    "wl_pixmap.h"
  22.  
  23.  
  24. /*  external  */
  25.  
  26. /*  local  */
  27.  
  28. /*  global  */
  29.  
  30. extern WOB_METHOD       BarClass[], PlugClass[], ClientWindowClass[], 
  31.             ScreenClass[];
  32.  
  33.  
  34. /*
  35.  * search all wobs for the one having the same X window as the evnt and
  36.  * returns it.
  37.  */
  38.  
  39. Wob 
  40. LookUpWob(window)
  41. Window           window;
  42. {
  43.     Wob             wob;
  44.  
  45.     if (!XFindContext(dpy, window, wob_context, (char **)&wob))
  46.     return wob;
  47.     else
  48.     return 0;
  49. }
  50.  
  51. /* same but callable from wool
  52.  */
  53.  
  54. WOOL_OBJECT
  55. LookUpWobW(wl_window)
  56. WOOL_Number           wl_window;
  57. {
  58.     Wob             wob;
  59.  
  60.     if (!XFindContext(dpy, wl_window->number, wob_context, (char **)&wob))
  61.     return (WOOL_OBJECT) WLNumber_make(wob);
  62.     else if (!XFindContext(dpy,  wl_window->number, client_context, (char **)&wob))
  63.     return (WOOL_OBJECT) WLNumber_make(wob);
  64.     else
  65.     return NIL;
  66. }
  67.  
  68. WobRecordHook(wob)
  69. Wob    wob;
  70. {
  71.     XSaveContext(dpy, wob -> hook, wob_context, (char *)wob);
  72. }
  73.  
  74. ClientWindow
  75. LookUpClient(window)
  76. Window           window;
  77. {
  78.     Wob             wob;
  79.  
  80.     if (!XFindContext(dpy, window, client_context, (char **)&wob))
  81.     return (ClientWindow)  wob;
  82.     else
  83.     return 0;
  84. }
  85.  
  86. WOOL_OBJECT
  87. Client2WindowW(clientid)
  88.     WOOL_Number clientid;
  89. {
  90.     ClientWindow cw;
  91.  
  92.     must_be_number(clientid, 0);
  93.     if (cw = LookUpClient(clientid->number)) {
  94.     return (WOOL_OBJECT) WLNumber_make(cw);
  95.     } else {
  96.     return NIL;
  97.     }
  98. }
  99.  
  100. WOOL_OBJECT
  101. Window2ClientW(w)
  102.     WOOL_Number w;
  103. {
  104.     ClientWindow cw;
  105.  
  106.     must_be_number(w, 0);
  107.     cw = (ClientWindow) w->number;
  108.     if (WobIsValid(cw) && cw->type == ClientWindowClass && cw->client) {
  109.     return (WOOL_OBJECT) WLNumber_make(cw->client);
  110.     } else {
  111.     return NIL;
  112.     }
  113. }
  114.  
  115. int
  116. IsAnAncestor(parent, child)
  117. Wob parent, child;
  118. {
  119.     Wob             wob = child;
  120.  
  121.     while (wob){
  122.     if(wob == parent)
  123.         return TRUE;
  124.     wob = wob -> parent;
  125.     }
  126.     return FALSE;    
  127. }
  128.  
  129. Wob 
  130. NewWob(size)
  131. int             size;
  132. {
  133.     Wob         new;
  134.  
  135.     new = (Wob) Malloc(size);
  136.     bzero(new, size);
  137.     new -> valid = WobMAGIC;
  138.     return new;
  139. }
  140.  
  141. WobRelease(wob)
  142. Wob             wob;
  143. {
  144.     decrease_reference(wob -> bordertile);
  145.     decrease_reference(wob -> menu);
  146.     decrease_reference(wob -> fsm);
  147.     decrease_reference(wob -> cursor);
  148.     decrease_reference(wob -> tile);
  149.     decrease_reference(wob -> property);
  150.     XDeleteContext(dpy, wob -> hook, wob_context);
  151.     XDestroyWindow(dpy, wob -> hook);
  152.     wob -> valid = 0;
  153.     DelayedFree(wob);
  154. }
  155.  
  156. WobEventHandler(wob, evt)
  157. Wob    wob;
  158. Event    evt;
  159. {
  160.     WLFsm_action(wob->fsm, wob, evt);
  161. }
  162.  
  163. /*
  164.  * default routines to respond to methods
  165.  */
  166.  
  167. WobEval(wob)
  168. Wob wob;
  169. {
  170.     wool_error(INTERNAL_ERROR, "Trying to eval a Wob!");
  171. }
  172.  
  173. WobPrint(wob)
  174. Wob wob;
  175. {
  176.     wool_puts("{");
  177.     wool_print_type(wob);
  178.     wool_printf("[0x%x", wob);
  179.     wool_printf("/0x%x]}", wob -> hook);
  180. }
  181.  
  182. WobExecute(wob)
  183. Wob wob;
  184. {
  185.     wool_error(INTERNAL_ERROR, "Trying to execute a Wob!");
  186. }
  187.  
  188. WobSet(wob)
  189. Wob wob;
  190. {
  191.     wool_error(INTERNAL_ERROR, "Trying to set a Wob!");
  192. }
  193.  
  194. WobGetCValue(wob)
  195. Wob wob;
  196. {
  197.     wool_error(INTERNAL_ERROR, "Trying to get the c_value of a Wob!");
  198. }
  199.  
  200. WobActionRoutine(wob)
  201. Wob wob;
  202. {
  203.     wool_error(INTERNAL_ERROR, "No Action defined for this wob!");
  204. }
  205.  
  206. /*
  207.  * functions to query about wobs
  208.  */
  209.  
  210. WOOL_OBJECT
  211. wool_current_wob()
  212. {
  213.     return (WOOL_OBJECT) WLNumber_make(TargetWob);
  214. }
  215.  
  216. WOOL_OBJECT
  217. wool_current_wob_set(wob)
  218. WOOL_Number wob;
  219. {
  220.     must_be_number(wob, 0);
  221.     if (!WobIsValid(wob->number))
  222.     wool_error(INTERNAL_ERROR, "Not a Wob!");
  223.     SetTarget(wob -> number);
  224.     return (WOOL_OBJECT) wob;
  225. }
  226.  
  227. #ifdef USE_STANDARD_MALLOC
  228. int
  229. WobIsValid(w) 
  230.     Wob w;
  231. {
  232.     return (((Wob)(w))->valid == WobMAGIC);
  233. }
  234. #endif
  235.  
  236.  
  237. WOOL_OBJECT
  238. wool_wob_is_valid(wob)
  239. WOOL_Number wob;
  240. {
  241.     must_be_number(wob, 0);
  242.     if (WobIsValid(wob->number))
  243.     return (WOOL_OBJECT) wob;
  244.     else
  245.     return NIL;
  246. }
  247.  
  248. WOOL_OBJECT
  249. wool_window_is_valid(wob)
  250. WOOL_Number wob;
  251. {
  252.     must_be_number(wob, 0);
  253.     if (WobIsValid(wob->number) &&
  254.     ((Wob)(wob->number))->type == ClientWindowClass)
  255.     return (WOOL_OBJECT) wob;
  256.     else
  257.     return NIL;
  258. }
  259.  
  260. WOOL_OBJECT
  261. wool_current_wob_width()
  262. {
  263.     return (WOOL_OBJECT) WLNumber_make(TargetWob -> box.width);
  264. }
  265.  
  266. WOOL_OBJECT
  267. wool_current_wob_height()
  268. {
  269.     return (WOOL_OBJECT) WLNumber_make(TargetWob -> box.height);
  270. }
  271.  
  272. WOOL_OBJECT
  273. current_wob_get_bitmap()
  274. {
  275.     return TargetWob -> tile;
  276. }
  277.  
  278. WOOL_OBJECT
  279. current_wob_set_bitmap(bitmap)
  280. WOOL_Pixmap bitmap;
  281. {
  282.     if (TargetWob -> type == BarClass)
  283.     set_bar_bitmap(TargetWob, bitmap);
  284.     else if (TargetWob -> type == PlugClass)
  285.     set_plug_bitmap(TargetWob, bitmap);
  286.     else if (TargetWob -> type == ScreenClass)
  287.         wool_set_screen_background(bitmap);
  288.     return (WOOL_OBJECT) bitmap;
  289. }
  290.  
  291. WOOL_OBJECT
  292. current_wob_get_borderpixel()
  293. {
  294.     return (WOOL_OBJECT) WLNumber_make(TargetWob -> box.borderpixel);
  295. }
  296.  
  297. WOOL_OBJECT
  298. current_wob_set_borderpixel(color)
  299. WOOL_Number    color;
  300. {
  301.     if (color -> type == WLNumber) {
  302.     TargetWob -> box.borderpixel = color -> number;
  303.     XSetWindowBorder(dpy, TargetWob -> hook, color -> number);
  304.     } else {
  305.     decrease_reference(TargetWob -> bordertile);
  306.     increase_reference(TargetWob -> bordertile = (WOOL_OBJECT) color);
  307.     XSetWindowBorderPixmap(dpy, TargetWob -> hook,
  308.              ((WOOL_Pixmap) (TargetWob -> bordertile)) -> pixmap);
  309.     }
  310.     return (WOOL_OBJECT) color;
  311. }
  312.  
  313. WOOL_OBJECT
  314. current_wob_get_background()
  315. {
  316.     return (WOOL_OBJECT) WLNumber_make(TargetWob -> box.background);
  317. }
  318.  
  319. WOOL_OBJECT
  320. current_wob_set_background(color)
  321. WOOL_Number    color;
  322. {
  323.     if (color -> type == WLNumber) {
  324.     TargetWob -> box.background = color -> number;
  325.     XSetWindowBackground(dpy, TargetWob -> hook, color -> number);
  326.     }
  327.     if (TargetWob -> type == PlugClass) {
  328.     WOOL_send(WOOL_redraw, ((Plug) TargetWob) -> graphic,
  329.           (((Plug) TargetWob) -> graphic, TargetWob));
  330.     } else {
  331.     XClearWindow(dpy, TargetWob -> hook);
  332.     }
  333.     return (WOOL_OBJECT) color;
  334. }
  335.  
  336.  
  337. WOOL_OBJECT
  338. current_wob_get_borderwidth()
  339. {
  340.     return (WOOL_OBJECT) WLNumber_make(TargetWob -> box.borderwidth);
  341. }
  342.  
  343. /* change a wob's borderwidth
  344.  * If it is not a window on the screen reconfigure the father
  345.  */
  346.  
  347. WOOL_OBJECT
  348. current_wob_set_borderwidth(width)
  349. WOOL_Number width;
  350. {
  351.     extern WOB_METHOD ScreenClass[];
  352.  
  353.     must_be_number(width, 0);
  354.     XSetWindowBorderWidth(dpy, TargetWob -> hook,
  355.               TargetWob -> box.borderwidth = width -> number);
  356.     /* TO_DO: reconfigure inside of bars! or composite wobs hack follows*/
  357.     if (TargetWob -> type == BarClass && TargetWob -> parent &&
  358.     TargetWob -> parent -> type == ClientWindowClass)
  359.     ReconfigureBar(TargetWob, TargetWob -> parent);
  360.  
  361.     if (TargetWob -> parent) {
  362.     if (TargetWob -> parent -> type != ScreenClass) {
  363.         WOOL_send(WOOL_reconfigure, TargetWob -> parent,
  364.               (TargetWob -> parent, TargetWob));
  365.     }
  366.     }
  367.     return (WOOL_OBJECT) width;
  368. }
  369.  
  370. WOOL_OBJECT
  371. current_wob_invert_aera()
  372. {
  373.     XSetForeground(dpy, Context->gc.Draw, Context -> pixel.InvertColor);
  374.     XFillRectangle(dpy, TargetWob -> hook, Context->gc.Draw, 0, 0,
  375.            TargetWob -> box.width, TargetWob -> box.height);
  376.     return NIL;
  377. }
  378.     
  379. WOOL_OBJECT
  380. Wob_set_property(property)
  381. WOOL_OBJECT property;
  382. {
  383.     WOOL_OBJECT     object = TargetWob -> property;
  384.  
  385.     must_be_or_nil(WLList, property, 0);
  386.     increase_reference(TargetWob -> property = property);
  387.     decrease_reference(object);
  388.     return (property);
  389. }
  390.     
  391. WOOL_OBJECT
  392. Wob_get_property()
  393. {
  394.     return (TargetWob -> property);
  395. }
  396.     
  397. WOOL_OBJECT
  398. Wob_set_menu(menu)
  399. WOOL_OBJECT menu;
  400. {
  401.     WOOL_OBJECT     object = TargetWob -> menu;
  402.  
  403.     increase_reference(TargetWob -> menu = menu);
  404.     decrease_reference(object);
  405.     return (menu);
  406. }
  407.     
  408. WOOL_OBJECT
  409. Wob_get_menu()
  410. {
  411.     return (TargetWob -> menu);
  412. }
  413.     
  414. WOOL_OBJECT
  415. Wob_set_fsm(fsm)
  416. WOOL_OBJECT fsm;
  417. {
  418.     WOOL_OBJECT     object = TargetWob -> fsm;
  419.  
  420.     increase_reference(TargetWob -> fsm = fsm);
  421.     decrease_reference(object);
  422.     TargetWob -> curstate = (int)
  423.     WOOL_send(WOOL_open, TargetWob -> fsm, (TargetWob -> fsm));
  424.     return (fsm);
  425. }
  426.     
  427. WOOL_OBJECT
  428. Wob_get_fsm()
  429. {
  430.     return (TargetWob -> fsm);
  431. }
  432.  
  433. int
  434. WobGetDimensions(wob, box)
  435. Wob    wob;
  436. Box    box;
  437. {
  438.     box -> x = wob -> box.x;
  439.     box -> y = wob -> box.y;
  440.     box -> width = wob -> box.width + 2 * wob -> box.borderwidth;
  441.     box -> height = wob -> box.height + 2 * wob -> box.borderwidth;
  442.     return 0;
  443. }
  444.  
  445. /* if given a number, returns the wobs at this adress, otherwise returns type
  446.  */
  447.  
  448. WOOL_OBJECT
  449. GetWobOfNumber(number)
  450. WOOL_Number number;
  451. {
  452.     if (number -> type == WLNumber)
  453.     return (WOOL_OBJECT) number -> number;
  454.     else
  455.     return (WOOL_OBJECT) number;
  456. }
  457.  
  458. /* to set/get the cursor of a wob
  459.  */
  460.  
  461. WOOL_OBJECT
  462. wool_wob_cursor_get()
  463. {
  464.     return TargetWob -> cursor;
  465. }
  466.  
  467. WOOL_OBJECT
  468. wool_wob_cursor_set(cursor)
  469. WOOL_Cursor    cursor;
  470. {
  471.     XSetWindowAttributes wa;
  472.  
  473.     must_be_or_nil(WLCursor, cursor, 0);
  474.     decrease_reference(TargetWob -> cursor);
  475.     increase_reference(TargetWob -> cursor = (WOOL_OBJECT) cursor);
  476.     wa.cursor = cursor -> cursor;
  477.     XChangeWindowAttributes(dpy, TargetWob -> hook, CWCursor, &wa);
  478.     return (WOOL_OBJECT) cursor;
  479. }
  480.  
  481. /* function called when a wob is tried to be open with a 0 dimension
  482.  */
  483.  
  484. GWM_no_size_window_error(wob)
  485. Wob    wob;
  486. {
  487.     char           *explanation;
  488.  
  489.     if (wob -> box.width) {
  490.     if (wob -> box.height)
  491.         return;
  492.     else
  493.         wob -> box.height = 1, explanation = "height";
  494.     } else {
  495.     if (wob -> box.height)
  496.         wob -> box.width = 1, explanation = "width";
  497.     else
  498.         wob -> box.height = 1, wob -> box.width = 1, explanation = "size";
  499.     }
  500.     wool_puts("GWM error: attempted to create a ");
  501.     WLAtom_print(wob -> type[0]);
  502.     wool_printf(" with null %s, using 1 instead\n", explanation);
  503.     stop_if_in_dbx();
  504. }
  505.  
  506. /* absolute position (% screen) of current wob
  507.  */
  508.  
  509. WOOL_OBJECT
  510. wool_wob_x_get()
  511. {
  512.     Wob wob = TargetWob;
  513.     int x = 0;
  514.  
  515.     while (wob -> type != ScreenClass) {
  516.     x += wob -> box.x;
  517.     if ((wob -> status & TopLevelXWindowStatus) || ! wob -> parent)
  518.         break;
  519.     wob = wob -> parent;
  520.     x += wob -> box.borderwidth;
  521.     }
  522.     return (WOOL_OBJECT) WLNumber_make(x);
  523. }
  524.  
  525. WOOL_OBJECT
  526. wool_wob_y_get()
  527. {
  528.     Wob wob = TargetWob;
  529.     int y = 0;
  530.  
  531.     while (wob -> type != ScreenClass) {
  532.     y += wob -> box.y;
  533.     if ((wob -> status & TopLevelXWindowStatus) || ! wob -> parent)
  534.         break;
  535.     wob = wob -> parent;
  536.     y += wob -> box.borderwidth;
  537.     }
  538.     return (WOOL_OBJECT) WLNumber_make(y);
  539. }
  540.