home *** CD-ROM | disk | FTP | other *** search
/ Usenet 1994 January / usenetsourcesnewsgroupsinfomagicjanuary1994.iso / sources / misc / volume11 / quadtree / part01 / xqtdisp.c < prev   
Encoding:
C/C++ Source or Header  |  1990-04-03  |  5.2 KB  |  228 lines

  1. #include <stdio.h>
  2. #include <quadtree.h>
  3. #include <X11/Xlib.h>
  4. #include <X11/Xatom.h>
  5. #include <X11/Xutil.h>
  6.  
  7. extern char    *getenv(), *optarg, *malloc();
  8. extern int      optind;
  9. extern FILE    *fopen();
  10.  
  11. Display        *QTDisplay;
  12. Window          QTWindow;
  13. GC              WhiteRegion, BlackRegion;
  14. int             Verbose;
  15.  
  16. struct Qentry {
  17.     QT_TreeNode_t  *node;
  18.     struct Qentry  *next, *prev;
  19.     short           x, y, width, height, parent;
  20. }              *Head, *Tail, *Freelist;
  21.  
  22. #define ColorsAgree(c1,c2) ((c1)?(c2):(!(c2)))
  23.  
  24. struct Qentry  *NewQentry()
  25. {
  26.     struct Qentry  *result, *ptr;
  27.     int             i;
  28.  
  29.     if (result = Freelist) {
  30.     Freelist = result->next;
  31.     return (result);
  32.     }
  33.     result = (struct Qentry *) malloc(64 *
  34.                       (sizeof(struct Qentry)));
  35.     for (i = 0, ptr = result; i < 63; ++ptr, ++i) {
  36.     ptr->next = ptr + 1;
  37.     }
  38.     ptr->next = Freelist;
  39.     Freelist = result->next;
  40.     return (result);
  41. }
  42.  
  43. void            ReleaseQentry(qe)
  44. struct Qentry  *qe;
  45. {
  46.     qe->next = Freelist;
  47.     Freelist = qe;
  48. }
  49.  
  50. main(argc, argv)
  51. int             argc;
  52. char          **argv;
  53. {
  54.     int             c, breadth = 0, screen;
  55.     short           width, height;
  56.     QT_TreeNode_t  *Tree;
  57.     FILE           *fp;
  58.     char           *displayname;
  59.     Window          rwindow;
  60.     XGCValues       gcv;
  61.  
  62.     Freelist = 0;
  63.     Verbose = 0;
  64.     while ((c = getopt(argc, argv, "bdv")) != EOF) {
  65.     switch (c) {
  66.         case 'b':
  67.         breadth = 1;
  68.         break;
  69.         case 'd':
  70.         breadth = 0;
  71.         break;
  72.         case 'v':
  73.         ++Verbose;
  74.         break;
  75.     }
  76.     }
  77.     if (!(fp = fopen(argv[optind], "r"))) {
  78.     exit(1);
  79.     }
  80.     Tree = QT_Tree_Read(fp, &width, &height);
  81.     if (!(displayname = getenv("DISPLAY")))
  82.     displayname = ":0";
  83.     QTDisplay = XOpenDisplay(displayname);
  84.     screen = DefaultScreen(QTDisplay);
  85.     rwindow = RootWindow(QTDisplay, screen);
  86.     QTWindow = XCreateSimpleWindow(QTDisplay, rwindow,
  87.                    0, 0, width, height,
  88.                    1, WhitePixel(QTDisplay, screen),
  89.                    BlackPixel(QTDisplay, screen));
  90.     XMapWindow(QTDisplay, QTWindow);
  91.     XSync(QTDisplay, 0);
  92.     gcv.foreground = WhitePixel(QTDisplay, screen);
  93.     gcv.function = GXset;
  94.     WhiteRegion = XCreateGC(QTDisplay, QTWindow,
  95.                 GCFunction | GCForeground, &gcv);
  96.     gcv.function = GXclear;
  97.     BlackRegion = XCreateGC(QTDisplay, QTWindow,
  98.                 GCFunction | GCForeground, &gcv);
  99.     puts("Press ENTER to begin");
  100.     while ('\n' != getchar());
  101.     if (breadth)
  102.     BreadthDraw(Tree, width, height);
  103.     else
  104.     DepthDraw(Tree, width, height);
  105.     XSync(QTDisplay, 0);
  106.     puts("Press ENTER to terminate");
  107.     while ('\n' != getchar());
  108.     exit(0);
  109. }
  110.  
  111. depthdraw(node, x, y, w, h, parent)
  112. QT_TreeNode_t  *node;
  113. int             x, y, w, h, parent;
  114. {
  115.     int             color = QT_TreeNode_Color(node), w2, h2;
  116.     QT_TreeNode_t  *child;
  117.  
  118.     if (!(ColorsAgree(color, parent))) {
  119.     if (Verbose) {
  120.         fprintf(stderr, "Filling (%d,%d) (%dx%d) [%s]\n",
  121.             x, y, w, h,
  122.             color ? "black" : "white");
  123.     }
  124.     XFillRectangle(QTDisplay, QTWindow,
  125.                color ? BlackRegion : WhiteRegion,
  126.                x, y, w, h);
  127.     }
  128.     w2 = w >> 1;
  129.     h2 = h >> 1;
  130.     if (child = QT_TreeNode_UpperLeft(node)) {
  131.     depthdraw(child, x, y, w2, h2, color);
  132.     }
  133.     if (child = QT_TreeNode_UpperRight(node)) {
  134.     depthdraw(child, x + w2, y, w - w2, h2, color);
  135.     }
  136.     if (child = QT_TreeNode_LowerLeft(node)) {
  137.     depthdraw(child, x, y + h2, w2, h - h2, color);
  138.     }
  139.     if (child = QT_TreeNode_LowerRight(node)) {
  140.     depthdraw(child, x + w2, y + h2, w - w2, h - h2, color);
  141.     }
  142. }
  143.  
  144. DepthDraw(node, width, height)
  145. QT_TreeNode_t  *node;
  146. int             width, height;
  147. {
  148.     depthdraw(node, 0, 0, width, height, 1);
  149. }
  150.  
  151. QueueInit()
  152. {
  153.     Head = Tail = 0;
  154. }
  155.  
  156. QueueAdd(node, x, y, w, h, parent)
  157. QT_TreeNode_t  *node;
  158. int             x, y, w, h, parent;
  159. {
  160.     struct Qentry  *result = NewQentry();
  161.  
  162.     result->node = node;
  163.     result->x = x;
  164.     result->y = y;
  165.     result->width = w;
  166.     result->height = h;
  167.     result->parent = parent;
  168.     result->next = 0;
  169.     result->prev = Tail;
  170.     if (Tail)
  171.     Tail->next = result;
  172.     Tail = result;
  173.     if (!Head)
  174.     Head = result;
  175. }
  176.  
  177. QueueDo()
  178. {
  179.     struct Qentry  *entry;
  180.     QT_TreeNode_t  *node, *child;
  181.     int             x, y, w, h, color, parent, w2, h2;
  182.  
  183.     for (entry = Head; entry; entry = entry->next) {
  184.     if (entry->prev)
  185.         ReleaseQentry(entry->prev);
  186.     node = entry->node;
  187.     x = entry->x;
  188.     y = entry->y;
  189.     w = entry->width;
  190.     h = entry->height;
  191.     color = QT_TreeNode_Color(node);
  192.     parent = entry->parent;
  193.     if (!(ColorsAgree(color, parent))) {
  194.         if (Verbose) {
  195.         fprintf(stderr, "Filling (%d,%d) (%dx%d) [%s]\n",
  196.             x, y, w, h,
  197.             color ? "black" : "white");
  198.         }
  199.         XFillRectangle(QTDisplay, QTWindow,
  200.                color ? BlackRegion : WhiteRegion,
  201.                x, y, w, h);
  202.     }
  203.     w2 = w >> 1;
  204.     h2 = h >> 1;
  205.     if (child = QT_TreeNode_UpperLeft(node)) {
  206.         QueueAdd(child, x, y, w2, h2, color);
  207.     }
  208.     if (child = QT_TreeNode_UpperRight(node)) {
  209.         QueueAdd(child, x + w2, y, w - w2, h2, color);
  210.     }
  211.     if (child = QT_TreeNode_LowerLeft(node)) {
  212.         QueueAdd(child, x, y + h2, w2, h - h2, color);
  213.     }
  214.     if (child = QT_TreeNode_LowerRight(node)) {
  215.         QueueAdd(child, x + w2, y + h2, w - w2, h - h2, color);
  216.     }
  217.     }
  218. }
  219.  
  220. BreadthDraw(node, width, height)
  221. QT_TreeNode_t  *node;
  222. int             width, height;
  223. {
  224.     QueueInit();
  225.     QueueAdd(node, 0, 0, width, height, 1);
  226.     QueueDo();
  227. }
  228.