int
main(int argc, char *argv[])
{
  int c;
  TexGlyphInfo tgi;
  int usageError = 0;
  char *varname, *fontname;
  XFontStruct *xfont;
  int i;

  if (argc == 3) {
     varname  = argv[1];
     fontname = argv[2];
     }
  else
     usageError = 1;

  if (usageError) {
    fprintf(stderr, "\n");
    fprintf(stderr, "usage: genfontfile variable_name X_font_name\n");
    fprintf(stderr, "\n");
    exit(1);
  }

  dpy = XOpenDisplay(NULL);
  if (!dpy) {
    fprintf(stderr, "could not open display\n");
    exit(1);
  }
  /* find an OpenGL-capable RGB visual with depth buffer */
  xfont = XLoadQueryFont(dpy, fontname);
  if (!xfont) {
    fprintf(stderr, "could not get load X font: %s\n", fontname);
    exit(1);
  }
  fontinfo = SuckGlyphsFromServer(dpy, xfont->fid);
  if (!fontinfo) {
    fprintf(stderr, "could not get font glyphs\n");
    exit(1);
  }

  printf("static const %s[][%d] = {\n", varname, fontinfo->max_ascent + fontinfo->max_descent + 2);
  for (c = 32; c < 256; c++) {
      getMetric(fontinfo, c, &tgi);
      printGlyph(fontinfo, c);
      }
  printf("  };\n");
  return 0;
}
Beispiel #2
0
SetupMessageDisplayList(FontEntryPtr fontEntry, int num, char *message[])
{
    FontInfoPtr     fontinfo = fontEntry->fontinfo;
    GLfloat         scaleFactor;
    int             totalHeight, maxWidth, height, width;
    int             i;

    if (!fontinfo) {
	fontinfo = SuckGlyphsFromServer(dpy, fontEntry->xfont->fid);
	fontEntry->fontinfo = fontinfo;
    }
    height = fontinfo->max_ascent + fontinfo->max_descent;
    maxWidth = 0;
    for (i = 0; i < num; i++) {
	MakeStringDisplayList(fontinfo, message[i], base + i + 1);
	width = GetStringLength(fontinfo, message[i]);
	if (width > maxWidth)
	    maxWidth = width;
    }

#define SHRINK_FACTOR 25.0	/* empirical */

    totalHeight = height * num - fontinfo->max_descent;
    if (maxWidth > totalHeight) {
	scaleFactor = SHRINK_FACTOR / maxWidth;
    } else {
	scaleFactor = SHRINK_FACTOR / totalHeight;
    }

    glNewList(base, GL_COMPILE);
    glScalef(scaleFactor, scaleFactor, 1); /* 1 in Z gives glyphs constant depth */
    for (i = 0; i < num; i++) {
	glPushMatrix();
	width = GetStringLength(fontinfo, message[i]);
	glTranslatef(-width / 2.0, height * (num - i - 1) - totalHeight / 2.0, 0);
	glCallList(base + i + 1);
	glPopMatrix();
    }
    glEndList();
}
Beispiel #3
0
void
main(int argc, char *argv[])
{
    int             i;
#ifdef IRIX_5_1_MOTIF_BUG_WORKAROUND
    /*
     * XXX Unfortunately a bug in the IRIX 5.1 Motif shared library
     * causes a BadMatch X protocol error if the SGI look&feel
     * is enabled for this program.  If we detect we are on an
     * IRIX 5.1 system, skip the first two fallback resources which
     * specify using the SGI look&feel.
     */
    struct utsname versionInfo;

    if(uname(&versionInfo) >= 0) {
        if(!strcmp(versionInfo.sysname, "IRIX") &&
	   !strncmp(versionInfo.release, "5.1", 3)) {
    	    toplevel = XtAppInitialize(&app, "Textfun", NULL, 0, &argc, argv,
				       &fallbackResources[2], NULL, 0);
        }
    }
    if(toplevel == NULL) {
        toplevel = XtAppInitialize(&app, "Textfun", NULL, 0, &argc, argv,
			           fallbackResources, NULL, 0);
    }
#else
    toplevel = XtAppInitialize(&app, "Textfun", NULL, 0, &argc, argv,
			       fallbackResources, NULL, 0);
#endif
    dpy = XtDisplay(toplevel);
    /* find an OpenGL-capable RGB visual with depth buffer */
    vi = glXChooseVisual(dpy, DefaultScreen(dpy), dblBuf);
    if (vi == NULL) {
	vi = glXChooseVisual(dpy, DefaultScreen(dpy), snglBuf);
	if (vi == NULL)
	    XtAppError(app, "no RGB visual with depth buffer");
	doubleBuffer = GL_FALSE;
    }
    for (i = 0; i < NUM_FONT_ENTRIES; i++) {
	fontEntry[i].xfont = XLoadQueryFont(dpy, fontEntry[i].xlfd);
	if (i == 0 && !fontEntry[i].xfont)
	    XtAppError(app, "could not get basic font");
    }

    fontEntry[0].fontinfo = SuckGlyphsFromServer(dpy, fontEntry[0].xfont->fid);
    if (!fontEntry[0].fontinfo)
	XtAppError(app, "could not get font glyphs");

    /* create an OpenGL rendering context */
    cx = glXCreateContext(dpy, vi, /* no display list sharing */ None,
			   /* favor direct */ GL_TRUE);
    if (cx == NULL)
	XtAppError(app, "could not create rendering context");

    /* create an X colormap since probably not using default visual */
    cmap = XCreateColormap(dpy, RootWindow(dpy, vi->screen),
			   vi->visual, AllocNone);
    XtVaSetValues(toplevel, XtNvisual, vi->visual, XtNdepth, vi->depth,
		  XtNcolormap, cmap, NULL);
    XtAddEventHandler(toplevel, StructureNotifyMask, False,
		      map_state_changed, NULL);
    mainw = XmCreateMainWindow(toplevel, "mainw", NULL, 0);
    XtManageChild(mainw);

    /* create menu bar */
    menubar = XmCreateMenuBar(mainw, "menubar", NULL, 0);
    XtManageChild(menubar);
    /* hack around Xt's ignorance of visuals */
    XtSetArg(menuPaneArgs[0], XmNdepth, DefaultDepthOfScreen(XtScreen(mainw)));
    XtSetArg(menuPaneArgs[1],
	     XmNcolormap, DefaultColormapOfScreen(XtScreen(mainw)));

    /* create File pulldown menu: Quit */
    menupane = XmCreatePulldownMenu(menubar, "menupane", menuPaneArgs, 2);
    btn = XmCreatePushButton(menupane, "Quit", NULL, 0);
    XtAddCallback(btn, XmNactivateCallback, quit, NULL);
    XtManageChild(btn);
    XtSetArg(args[0], XmNsubMenuId, menupane);
    cascade = XmCreateCascadeButton(menubar, "File", args, 1);
    XtManageChild(cascade);

    /* create Options pulldown menu: Motion, Dolly, Rotate, Wobble */
    menupane = XmCreatePulldownMenu(menubar, "menupane", menuPaneArgs, 2);
    btn = XmCreateToggleButton(menupane, "Motion", NULL, 0);
    XtAddCallback(btn, XmNvalueChangedCallback, (XtCallbackProc) toggle, NULL);
    XtManageChild(btn);
    btn = XmCreateToggleButton(menupane, "Dolly", NULL, 0);
    XtAddCallback(btn, XmNvalueChangedCallback, (XtCallbackProc) dolly, NULL);
    XtVaSetValues(btn, XmNset, True, NULL);
    XtManageChild(btn);
    btn = XmCreateToggleButton(menupane, "Rotate", NULL, 0);
    XtAddCallback(btn, XmNvalueChangedCallback, (XtCallbackProc) rotate, NULL);
    XtManageChild(btn);
    btn = XmCreateToggleButton(menupane, "Wobble", NULL, 0);
    XtAddCallback(btn, XmNvalueChangedCallback, (XtCallbackProc) wobble, NULL);
    XtManageChild(btn);
    XtSetArg(args[0], XmNsubMenuId, menupane);
    cascade = XmCreateCascadeButton(menubar, "Options", args, 1);
    XtManageChild(cascade);

    XtSetArg(menuPaneArgs[2], XmNradioBehavior, True);
    XtSetArg(menuPaneArgs[3], XmNradioAlwaysOne, True);
    menupane = XmCreatePulldownMenu(menubar, "menupane", menuPaneArgs, 4);
    XtAddCallback(menupane, XmNentryCallback, (XtCallbackProc) fontSelect, NULL);
    for (i = 0; i < NUM_FONT_ENTRIES; i++) {
	btn = XmCreateToggleButton(menupane, fontEntry[i].name, NULL, 0);
	XtAddCallback(btn, XmNvalueChangedCallback, (XtCallbackProc) neverCalled, &fontEntry[i]);
	if (i == 0)
	    XtVaSetValues(btn, XmNset, True, NULL);
        if (!fontEntry[i].xfont)
	    XtSetSensitive(btn, False);
	XtManageChild(btn);
    }
    XtSetArg(args[0], XmNsubMenuId, menupane);
    cascade = XmCreateCascadeButton(menubar, "Font", args, 1);
    XtManageChild(cascade);

    /* create framed drawing area for OpenGL rendering */
    frame = XmCreateFrame(mainw, "frame", NULL, 0);
    XtManageChild(frame);
    glxarea = XtCreateManagedWidget("glxarea", xmDrawingAreaWidgetClass,
				    frame, NULL, 0);
    XtAddCallback(glxarea, XmNexposeCallback, (XtCallbackProc) draw, NULL);
    XtAddCallback(glxarea, XmNresizeCallback, resize, NULL);
    XtAddCallback(glxarea, XmNinputCallback, input, NULL);
    /* set up application's window layout */
    XmMainWindowSetAreas(mainw, menubar, NULL, NULL, NULL, frame);
    XtRealizeWidget(toplevel);

    /*
     * Once widget is realized (ie, associated with a created X window), we
     * can bind the OpenGL rendering context to the window.
     */
    glXMakeCurrent(dpy, XtWindow(glxarea), cx);
    made_current = GL_TRUE;
    /* setup OpenGL state */
    glEnable(GL_DEPTH_TEST);
    glDepthFunc(GL_LEQUAL);
    glClearDepth(1.0);
    glMatrixMode(GL_PROJECTION);
    glFrustum(-1.0, 1.0, -1.0, 1.0, 1.0, 80);
    glMatrixMode(GL_MODELVIEW);

    MakeCube();

    if (argv[1] != NULL) {
	numMessages = argc - 1;
	messages = &argv[1];
    } else {
	numMessages = NUM_DEFAULT_MESSAGES;
	messages = defaultMessage;
    }

    base = glGenLists(numMessages + 1);
    SetupMessageDisplayList(&fontEntry[0], numMessages, messages);

    tick();

    /* start event processing */
    XtAppMainLoop(app);
}
Beispiel #4
0
int
main(int argc, char *argv[])
{
  int texw, texh;
  unsigned char *texarea, *texbitmap;
  FILE *file;
  int len, stride;
  unsigned char *glist;
  int width, height;
  int px, py, maxheight;
  TexGlyphInfo tgi;
  int usageError = 0;
  char *fontname, *filename;
  XFontStruct *xfont;
  int endianness;
  int i, j;

  texw = texh = 256;
  glist = " ABCDEFGHIJKLMNOPQRSTUVWXYZ1234567890abcdefghijmklmnopqrstuvwxyz?.;,!*:\"/+@#$%^&()";
  fontname = "-adobe-courier-bold-r-normal--46-*-100-100-m-*-iso8859-1";
  filename = "default.txf";

  for (i = 1; i < argc; i++) {
    if (!strcmp(argv[i], "-w")) {
      i++;
      texw = atoi(argv[i]);
    } else if (!strcmp(argv[i], "-h")) {
      i++;
      texh = atoi(argv[i]);
    } else if (!strcmp(argv[i], "-gap")) {
      i++;
      gap = atoi(argv[i]);
    } else if (!strcmp(argv[i], "-byte")) {
      format = TXF_FORMAT_BYTE;
      break;
    } else if (!strcmp(argv[i], "-bitmap")) {
      format = TXF_FORMAT_BITMAP;
    } else if (!strcmp(argv[i], "-glist")) {
      i++;
      glist = (unsigned char *) argv[i];
    } else if (!strcmp(argv[i], "-fn")) {
      i++;
      fontname = argv[i];
    } else if (!strcmp(argv[i], "-file")) {
      i++;
      filename = argv[i];
    } else {
      usageError = 1;
    }
  }

  if (usageError) {
    putchar('\n');
    printf("usage: texfontgen [options] txf-file\n");
    printf(" -w #          textureWidth (def=%d)\n", texw);
    printf(" -h #          textureHeight (def=%d)\n", texh);
    printf(" -gap #        gap between glyphs (def=%d)\n", gap);
    printf(" -bitmap       use a bitmap encoding (default)\n");
    printf(" -byte         use a byte encoding (less compact)\n");
    printf(" -glist ABC    glyph list (def=%s)\n", glist);
    printf(" -fn name      X font name (def=%s)\n", fontname);
    printf(" -file name    output file for textured font (def=%s)\n", fontname);
    putchar('\n');
    exit(1);
  }
  texarea = calloc(texw * texh, sizeof(unsigned char));
  glist = (unsigned char *) nodupstring((char *) glist);

  dpy = XOpenDisplay(NULL);
  if (!dpy) {
    printf("could not open display\n");
    exit(1);
  }
  /* find an OpenGL-capable RGB visual with depth buffer */
  xfont = XLoadQueryFont(dpy, fontname);
  if (!xfont) {
    printf("could not get load X font: %s\n", fontname);
    exit(1);
  }
  fontinfo = SuckGlyphsFromServer(dpy, xfont->fid);
  if (!fontinfo) {
    printf("could not get font glyphs\n");
    exit(1);
  }
  len = (int) strlen((char *) glist);
  qsort(glist, len, sizeof(unsigned char), glyphCompare);

  file = fopen(filename, "wb");
  if (!file) {
    printf("could not open %s for writing\n", filename);
    exit(1);
  }
  fwrite("\377txf", 1, 4, file);
  endianness = 0x12345678;
  /*CONSTANTCONDITION*/
  assert(sizeof(int) == 4);  /* Ensure external file format size. */
  fwrite(&endianness, sizeof(int), 1, file);
  fwrite(&format, sizeof(int), 1, file);
  fwrite(&texw, sizeof(int), 1, file);
  fwrite(&texh, sizeof(int), 1, file);
  fwrite(&fontinfo->max_ascent, sizeof(int), 1, file);
  fwrite(&fontinfo->max_descent, sizeof(int), 1, file);
  fwrite(&len, sizeof(int), 1, file);

  px = gap;
  py = gap;
  maxheight = 0;
  for (i = 0; i < len; i++) {
    if (glist[i] != 0) {  /* If not already processed... */

      /* Try to find a character from the glist that will fit on the
         remaining space on the current row. */

      int foundWidthFit = 0;
      int c;

      getMetric(fontinfo, glist[i], &tgi);
      width = tgi.width;
      height = tgi.height;
      if (height > 0 && width > 0) {
        for (j = i; j < len;) {
          if (height > 0 && width > 0) {
            if (px + width + gap < texw) {
              foundWidthFit = 1;
              if (j != i) {
                i--;  /* Step back so i loop increment leaves us at same character. */
              }
              break;
            }
          }
          j++;
          getMetric(fontinfo, glist[j], &tgi);
          width = tgi.width;
          height = tgi.height;
        }

        /* If a fit was found, use that character; otherwise, advance a line
           in  the texture. */
        if (foundWidthFit) {
          if (height > maxheight) {
            maxheight = height;
          }
          c = j;
        } else {
          getMetric(fontinfo, glist[i], &tgi);
          width = tgi.width;
          height = tgi.height;

          py += maxheight + gap;
          px = gap;
          maxheight = height;
          if (py + height + gap >= texh) {
            printf("Overflowed texture space.\n");
            exit(1);
          }
          c = i;
        }

        /* Place the glyph in the texture image. */
        placeGlyph(fontinfo, glist[c], texarea, texw, px, py);

        /* Assign glyph's texture coordinate. */
        tgi.x = px;
        tgi.y = py;

        /* Advance by glyph width, remaining in the current line. */
        px += width + gap;
      } else {
        /* No texture image; assign invalid bogus texture coordinates. */
        tgi.x = -1;
        tgi.y = -1;
      }
      glist[c] = 0;     /* Mark processed; don't process again. */
      /*CONSTANTCONDITION*/
      assert(sizeof(tgi) == 12);  /* Ensure external file format size. */
      fwrite(&tgi, sizeof(tgi), 1, file);
    }
  }

  switch (format) {
  case TXF_FORMAT_BYTE:
    fwrite(texarea, texw * texh, 1, file);
    break;
  case TXF_FORMAT_BITMAP:
    stride = (texw + 7) >> 3;
    texbitmap = (unsigned char *) calloc(stride * texh, 1);
    for (i = 0; i < texh; i++) {
      for (j = 0; j < texw; j++) {
        if (texarea[i * texw + j] >= 128) {
          texbitmap[i * stride + (j >> 3)] |= 1 << (j & 7);
        }
      }
    }
    fwrite(texbitmap, stride * texh, 1, file);
    free(texbitmap);
    break;
  default:
    printf("Unknown texture font format.\n");
    exit(1);
  }