// Method that draws all elements in each set starting with the root and then
  // calling traverse to get the rest of the tree
  void drawSets(LinkedList llist, draw d) {
    int temp;
    double stringLength = 0.0;
    String s = "";
    StringTokenizer getWeight;
    GTN gtn = new GTN();
    GTN TempChild;

    x = .0;
    y = TitleEndy - .24;

    nodelist.reset();
    while (nodelist.hasMoreElements()) {
      if (nodelist.hasMoreElements()) gtn = (GTN) (nodelist.nextElement());
      else gtn = (GTN) (nodelist.currentElement());

      // traverse down current tree
      s = traverse(gtn, s, llist, d, true);
      s += "}";

      BufferedImage buffer =
          new BufferedImage(
              GaigsAV.preferred_width, GaigsAV.preferred_height, BufferedImage.TYPE_BYTE_GRAY);

      temp = buffer.getGraphics().getFontMetrics(defaultFont).stringWidth(s);

      //		temp = d.getGraphics().getFontMetrics(defaultFont).stringWidth(s);

      stringLength = ((double) temp / (double) d.getSize().width);

      // gets the weight of the current set
      getWeight = new StringTokenizer(s, ",");
      LGKS.set_text_align(0, 2, llist, d);
      LGKS.text(gtn.Gx, (gtn.Gy + Lenx + .02), ("" + getWeight.countTokens()), llist, d);

      LGKS.set_text_align(1, 2, llist, d);
      // these checks insure that the set info will be drawn within
      // the bounds of the window
      if ((x + stringLength) >= 1.0) {
        x = 0;
        y -= .05;
        LGKS.text(x, y, s, llist, d);
        x = stringLength + .05;
      } else {
        LGKS.text(x, y, s, llist, d);
        x += stringLength + .05;
      }

      s = "";
    }
  }
  //                 PROCEDURE DrawGeneralTree                            *)
  //                                                                      *)
  // This procedure calls on xCoord to obtain the x coordinate of each    *)
  // node in the tree, and then calls on ApplyModifier to to make any     *)
  // adjustments to the node positions that couldn't be made in xCoord.   *)
  // Finally, it does a pre-order traversal of the tree and draws each    *)
  // node to its rightful place in the tree, and connects appropriate     *)
  // nodes to form the binary tree.                                       *)
  void drawStructure(LinkedList llist, draw d) {
    int x;
    double TempLoc, xline[], yline[];
    double scootch = 0.0;
    GTN gtn = new GTN();
    String text, c;
    StringTokenizer checkCommand;

    super.drawStructure(llist, d);
    xline = new double[2];
    yline = new double[2];
    yline[0] = TitleEndy - .05;
    yline[1] = yline[0];
    xline[0] = 0;
    xline[1] = 1;
    // The polyline is drawn immediately under the title/caption
    LGKS.polyline(2, xline, yline, llist, d);

    if (emptyStruct()) {
      super.drawStructure(llist, d); // to handle empty structure
      return;
    }
    for (x = 0; x < MaxLevels; ++x) {
      Modifier[x] = 0.0;
      NextPos[x] =
          0.1; // 0.025;//TreeSideBorder+(Lenx/2.0); // The rightmost position at which we can plot
      // a node *)
    }

    // Scale drawings for more then 10 items
    if (nn >= 10) {
      xspacing -= (nn - 9) * .065;
    }

    // adjust the node starting position so that the sets don't overlap
    Starty -= ((nn / 7 + 2)) * .05;

    nodelist.reset();
    while (nodelist.hasMoreElements()) {
      if (nodelist.hasMoreElements()) gtn = (GTN) (nodelist.nextElement());
      else gtn = (GTN) (nodelist.currentElement());
      TempLoc = xCoord(gtn);
      ApplyModifier(gtn);
    }

    if (maxXCord + (Lenx / 2) < 1.0) {
      ModifierSum = Lenx / 2;
      if (nodelist.size() > 2)
        scootch = ((.975 - (maxXCord + (Lenx / 2))) / ((double) nodelist.size() - 1.0));
      else {
        scootch = ((1.0 - (maxXCord + (Lenx / 2))) / (double) nodelist.size());
        ModifierSum = scootch / 2;
      }
    } else ModifierSum = (((maxXCord - minXCord) / 2) - .5) * -1;

    nodelist.reset();
    x = 0;
    while (nodelist.hasMoreElements()) {
      if (nodelist.hasMoreElements()) gtn = (GTN) (nodelist.nextElement());
      else gtn = (GTN) (nodelist.currentElement());

      ApplyModifier(gtn);
      if (x == (nodelist.size() / 2) && badCommand == 1) {
        LGKS.set_text_align(0, 2, llist, d);
        LGKS.set_textline_color(4, llist, d);
        text = "Bad command!  No action taken.";
        LGKS.text(CenterScreen, (gtn.Gy + .13), text, llist, d);
        LGKS.set_text_align(1, 2, llist, d);
      }
      // The factor needed to shift the tree to the center *)
      xMin = CenterScreen - (0.5 * Maxtitlelength);
      xMax = CenterScreen + (0.5 * Maxtitlelength);
      yMax = Topy - IconHeight - IconToTitleGap;
      yMin = yMax;
      drawWalk(gtn, llist, d);
      Xcenter = (xMin + xMax) / 2.0;
      Ycenter = (yMin + yMax) / 2;
      snapheight = yMax - yMin;
      snapwidth = xMax - xMin;

      ModifierSum += scootch;
      x++;
    }

    LGKS.set_text_align(1, 2, llist, d);
    // Print Text info to screen
    if (weight == 0) text = "Weighted Union: On";
    else text = "Weighted Union: Off";
    LGKS.text(.0, (TitleEndy - .06), text, llist, d);

    if (path == 0) text = "Path Compresion: On";
    else text = "Path Compresion: Off";
    LGKS.text(.45, (TitleEndy - .06), text, llist, d);

    text = "Current Command:";
    LGKS.set_textline_color(2, llist, d);
    LGKS.text(.0, (TitleEndy - .11), text, llist, d);
    LGKS.text(.0, (TitleEndy - .15), command, llist, d);
    LGKS.set_textline_color(3, llist, d);
    text = "Average Comparsions Per Find: " + cpf;
    LGKS.text(.45, (TitleEndy - .11), text, llist, d);
    text = "Average Comparsions Per Union: " + cpu;
    LGKS.text(.45, (TitleEndy - .15), text, llist, d);

    LGKS.set_textline_color(1, llist, d);
    drawSets(llist, d);
  }