home *** CD-ROM | disk | FTP | other *** search
/ Magazyn Amiga 5 / MA_Cover_5.iso / ppc / mesa / src-glut / glut_init.c < prev    next >
Encoding:
C/C++ Source or Header  |  1998-01-31  |  9.6 KB  |  349 lines

  1. /* Copyright (c) Mark J. Kilgard, 1994. */
  2.  
  3. /* This program is freely distributable without licensing fees
  4.    and is provided without guarantee or warrantee expressed or
  5.    implied. This program is -not- in the public domain. */
  6.  
  7. #include <stdlib.h>
  8. #include <string.h>
  9. #include <stdio.h>
  10.  
  11. #if !defined(WIN32)
  12. #include <X11/Xlib.h>
  13. #include <X11/Xatom.h>
  14. #endif /* !WIN32 */
  15.  
  16. /* SGI optimization introduced in IRIX 6.3 to avoid X server
  17.    round trips for interning common X atoms. */
  18. #if defined(_SGI_EXTRA_PREDEFINES) && !defined(NO_FAST_ATOMS)
  19. #include <X11/SGIFastAtom.h>
  20. #else
  21. #define XSGIFastInternAtom(dpy,string,fast_name,how) XInternAtom(dpy,string,how)
  22. #endif
  23.  
  24. #include <GL/glut.h>
  25. #include "glutint.h"
  26.  
  27. /* GLUT inter-file variables */
  28. /* *INDENT-OFF* */
  29. char *__glutProgramName = NULL;
  30. int __glutArgc = 0;
  31. char **__glutArgv = NULL;
  32. char *__glutGeometry = NULL;
  33. Display *__glutDisplay = NULL;
  34. int __glutScreen;
  35. Window __glutRoot;
  36. int __glutScreenHeight;
  37. int __glutScreenWidth;
  38. GLboolean __glutIconic = GL_FALSE;
  39. GLboolean __glutDebug = GL_FALSE;
  40. unsigned int __glutDisplayMode =
  41.   GLUT_RGB | GLUT_SINGLE | GLUT_DEPTH;
  42. char *__glutDisplayString = NULL;
  43. int __glutConnectionFD;
  44. XSizeHints __glutSizeHints = {0};
  45. int __glutInitWidth = 300, __glutInitHeight = 300;
  46. int __glutInitX = -1, __glutInitY = -1;
  47. GLboolean __glutForceDirect = GL_FALSE,
  48.   __glutTryDirect = GL_TRUE;
  49. Atom __glutWMDeleteWindow;
  50. #if defined(WIN32)
  51. int __glutMinWindowWidth, __glutMinWindowHeight;
  52. #endif
  53. /* *INDENT-ON* */
  54.  
  55. static Bool synchronize = False;
  56.  
  57. #if defined(WIN32)
  58. void
  59. __glutOpenWin32Connection(char* display)
  60. {
  61.   static char *classname;
  62.   WNDCLASS  wc;
  63.   HINSTANCE hInstance = GetModuleHandle(NULL);
  64.   
  65.   /* make sure we register the window only once */
  66.   if(classname)
  67.     return;
  68.  
  69.   classname = "GLUT";
  70.  
  71.   /* clear (important!) and then fill in the window class structure */
  72.   memset(&wc, 0, sizeof(WNDCLASS));
  73.   wc.style         = CS_OWNDC;
  74.   wc.lpfnWndProc   = (WNDPROC)__glutWindowProc;
  75.   wc.hInstance     = hInstance;
  76.   wc.hIcon         = LoadIcon(hInstance, "GLUT_ICON");
  77.   wc.hCursor       = LoadCursor(hInstance, IDC_ARROW);
  78.   wc.hbrBackground = NULL;
  79.   wc.lpszMenuName  = NULL;
  80.   wc.lpszClassName = classname;
  81.  
  82.   /* fill in a default icon if one isn't specified as a resource */
  83.   if(!wc.hIcon)
  84.     wc.hIcon = LoadIcon(NULL, IDI_WINLOGO);
  85.   
  86.   if(!RegisterClass(&wc)) {
  87.     __glutFatalError("RegisterClass() failed:"
  88.              "Cannot register GLUT window class.");
  89.   }
  90.  
  91.   __glutScreenWidth     = GetSystemMetrics(SM_CXSCREEN);
  92.   __glutScreenHeight    = GetSystemMetrics(SM_CYSCREEN);
  93.   __glutMinWindowWidth  = GetSystemMetrics(SM_CXMIN);
  94.   __glutMinWindowHeight = GetSystemMetrics(SM_CYMIN);
  95.  
  96.   /* set the root window to NULL because windows creates a top-level
  97.      window when the parent is NULL.  X creates a top-level window
  98.      when the parent is the root window. */
  99.   __glutRoot            = NULL;
  100.  
  101.   /* set the display to 1 -- we shouldn't be using this anywhere
  102.      (except as an argument to X calls). */
  103.   __glutDisplay         = (Display*)1;
  104.  
  105.   /* there isn't any concept of multiple screens in Win32, therefore,
  106.      we don't need to keep track of the screen we're on...it's always
  107.      the same one. */
  108.   __glutScreen          = 0;
  109. }
  110. #else /* !WIN32 */
  111. void
  112. __glutOpenXConnection(char *display)
  113. {
  114.   int errorBase, eventBase;
  115.  
  116.   __glutDisplay = XOpenDisplay(display);
  117.   if (!__glutDisplay)
  118.     __glutFatalError("could not open display: %s",
  119.       XDisplayName(display));
  120.   if (synchronize)
  121.     XSynchronize(__glutDisplay, True);
  122.   if (!glXQueryExtension(__glutDisplay, &errorBase, &eventBase))
  123.     __glutFatalError(
  124.       "OpenGL GLX extension not supported by display: %s",
  125.       XDisplayName(display));
  126.   __glutScreen = DefaultScreen(__glutDisplay);
  127.   __glutRoot = RootWindow(__glutDisplay, __glutScreen);
  128.   __glutScreenWidth = DisplayWidth(__glutDisplay, __glutScreen);
  129.   __glutScreenHeight = DisplayHeight(__glutDisplay,
  130.     __glutScreen);
  131.   __glutConnectionFD = ConnectionNumber(__glutDisplay);
  132.   __glutWMDeleteWindow = XSGIFastInternAtom(__glutDisplay,
  133.     "WM_DELETE_WINDOW", SGI_XA_WM_DELETE_WINDOW, False);
  134. }
  135. #endif /* WIN32 */
  136.  
  137. void
  138. __glutInitTime(struct timeval *beginning)
  139. {
  140.   static int beenhere = 0;
  141.   static struct timeval genesis;
  142.  
  143.   if (!beenhere) {
  144.     GETTIMEOFDAY(&genesis);
  145.     beenhere = 1;
  146.   }
  147.   *beginning = genesis;
  148. }
  149.  
  150. static void
  151. removeArgs(int *argcp, char **argv, int numToRemove)
  152. {
  153.   int i, j;
  154.  
  155.   for (i = 0, j = numToRemove; argv[j]; i++, j++) {
  156.     argv[i] = argv[j];
  157.   }
  158.   argv[i] = NULL;
  159.   *argcp -= numToRemove;
  160. }
  161.  
  162. void APIENTRY 
  163. glutInit(int *argcp, char **argv)
  164. {
  165.   char *display = NULL;
  166.   char *str, *geometry = NULL;
  167.   struct timeval unused;
  168.   int i;
  169.  
  170.   if (__glutDisplay) {
  171.     __glutWarning("glutInit being called a second time.");
  172.     return;
  173.   }
  174.   /* Determine temporary program name. */
  175.   str = strrchr(argv[0], '/');
  176.   if (str == NULL) {
  177.     __glutProgramName = argv[0];
  178.   } else {
  179.     __glutProgramName = str + 1;
  180.   }
  181.  
  182.   /* Make private copy of command line arguments. */
  183.   __glutArgc = *argcp;
  184.   __glutArgv = (char **) malloc(__glutArgc * sizeof(char *));
  185.   if (!__glutArgv)
  186.     __glutFatalError("out of memory.");
  187.   for (i = 0; i < __glutArgc; i++) {
  188.     __glutArgv[i] = __glutStrdup(argv[i]);
  189.     if (!__glutArgv[i])
  190.       __glutFatalError("out of memory.");
  191.   }
  192.  
  193.   /* determine permanent program name */
  194.   str = strrchr(__glutArgv[0], '/');
  195.   if (str == NULL) {
  196.     __glutProgramName = __glutArgv[0];
  197.   } else {
  198.     __glutProgramName = str + 1;
  199.   }
  200.  
  201.   /* parse arguments for standard options */
  202.   for (i = 1; i < __glutArgc; i++) {
  203.     if (!strcmp(__glutArgv[i], "-display")) {
  204. #if defined(WIN32)
  205.       __glutWarning("-display option invalid for win32 glut.");
  206. #endif /* WIN32 */
  207.       if (++i >= __glutArgc) {
  208.         __glutFatalError(
  209.           "follow -display option with X display name.");
  210.       }
  211.       display = __glutArgv[i];
  212.       removeArgs(argcp, &argv[1], 2);
  213.     } else if (!strcmp(__glutArgv[i], "-geometry")) {
  214.       if (++i >= __glutArgc) {
  215.         __glutFatalError(
  216.           "follow -geometry option with geometry parameter.");
  217.       }
  218.       geometry = __glutArgv[i];
  219.       removeArgs(argcp, &argv[1], 2);
  220.     } else if (!strcmp(__glutArgv[i], "-direct")) {
  221. #if defined(WIN32)
  222.       __glutWarning("-direct option invalid for win32 glut.");
  223. #endif /* WIN32 */
  224.       if (!__glutTryDirect)
  225.         __glutFatalError(
  226.           "cannot force both direct and indirect rendering.");
  227.       __glutForceDirect = GL_TRUE;
  228.       removeArgs(argcp, &argv[1], 1);
  229.     } else if (!strcmp(__glutArgv[i], "-indirect")) {
  230. #if defined(WIN32)
  231.       __glutWarning("-indirect option invalid for win32 glut.");
  232. #endif /* WIN32 */
  233.       if (__glutForceDirect)
  234.         __glutFatalError(
  235.           "cannot force both direct and indirect rendering.");
  236.       __glutTryDirect = GL_FALSE;
  237.       removeArgs(argcp, &argv[1], 1);
  238.     } else if (!strcmp(__glutArgv[i], "-iconic")) {
  239.       __glutIconic = GL_TRUE;
  240.       removeArgs(argcp, &argv[1], 1);
  241.     } else if (!strcmp(__glutArgv[i], "-gldebug")) {
  242.       __glutDebug = GL_TRUE;
  243.       removeArgs(argcp, &argv[1], 1);
  244.     } else if (!strcmp(__glutArgv[i], "-sync")) {
  245. #if defined(WIN32)
  246.       __glutWarning("-indirect option invalid for win32 glut.");
  247. #endif /* WIN32 */
  248.       synchronize = GL_TRUE;
  249.       removeArgs(argcp, &argv[1], 1);
  250.     } else {
  251.       /* Once unknown option encountered, stop command line
  252.          processing. */
  253.       break;
  254.     }
  255.   }
  256. #if defined(WIN32)
  257.   __glutOpenWin32Connection(display);
  258. #else
  259.   __glutOpenXConnection(display);
  260. #endif /* WIN32 */
  261.   if (geometry) {
  262.     int flags, x, y, width, height;
  263.  
  264.     /* Fix bogus "{width|height} may be used before set"
  265.        warning */
  266.     width = 0;
  267.     height = 0;
  268.  
  269.     flags = XParseGeometry(geometry, &x, &y,
  270.       (unsigned int *) &width, (unsigned int *) &height);
  271.     if (WidthValue & flags) {
  272.       /* Careful because X does not allow zero or negative
  273.          width windows */
  274.       if (width > 0)
  275.         __glutInitWidth = width;
  276. #if defined(WIN32)
  277.       if (width < __glutMinWindowWidth)
  278.     __glutWarning("requested width is less than minimum allowed.");
  279. #endif /* WIN32 */
  280.     }
  281.     if (HeightValue & flags) {
  282.       /* Careful because X does not allow zero or negative
  283.          height windows */
  284.       if (height > 0)
  285.         __glutInitHeight = height;
  286. #if defined(WIN32)
  287.       if (height < __glutMinWindowHeight)
  288.     __glutWarning("requested height is less than minimum allowed.");
  289. #endif /* WIN32 */
  290.     }
  291.     glutInitWindowSize(__glutInitWidth, __glutInitHeight);
  292.     if (XValue & flags) {
  293.       if (XNegative & flags)
  294.         x = DisplayWidth(__glutDisplay, __glutScreen) +
  295.           x - __glutSizeHints.width;
  296.       /* Play safe: reject negative X locations */
  297.       if (x >= 0)
  298.         __glutInitX = x;
  299.     }
  300.     if (YValue & flags) {
  301.       if (YNegative & flags)
  302.         y = DisplayHeight(__glutDisplay, __glutScreen) +
  303.           y - __glutSizeHints.height;
  304.       /* Play safe: reject negative Y locations */
  305.       if (y >= 0)
  306.         __glutInitY = y;
  307.     }
  308.     glutInitWindowPosition(__glutInitX, __glutInitY);
  309.   }
  310.   __glutInitTime(&unused);
  311. }
  312.  
  313. /* CENTRY */
  314. void APIENTRY 
  315. glutInitWindowPosition(int x, int y)
  316. {
  317.   __glutInitX = x;
  318.   __glutInitY = y;
  319.   if (x >= 0 && y >= 0) {
  320.     __glutSizeHints.x = x;
  321.     __glutSizeHints.y = y;
  322.     __glutSizeHints.flags |= USPosition;
  323.   } else {
  324.     __glutSizeHints.flags &= ~USPosition;
  325.   }
  326. }
  327.  
  328. void APIENTRY 
  329. glutInitWindowSize(int width, int height)
  330. {
  331.   __glutInitWidth = width;
  332.   __glutInitHeight = height;
  333.   if (width > 0 && height > 0) {
  334.     __glutSizeHints.width = width;
  335.     __glutSizeHints.height = height;
  336.     __glutSizeHints.flags |= USSize;
  337.   } else {
  338.     __glutSizeHints.flags &= ~USSize;
  339.   }
  340. }
  341.  
  342. void APIENTRY 
  343. glutInitDisplayMode(unsigned int mask)
  344. {
  345.   __glutDisplayMode = mask;
  346. }
  347.  
  348. /* ENDCENTRY */
  349.