QNX Screen Entry Point#

/*!***************************************************************************
 \File         OpenGLESHelloAPI_QNXScreen.cpp
 \Title        OpenGL ES 2.0 HelloAPI Tutorial
 \Author       PowerVR by Imagination, Developer Technology Team
 \Copyright    Copyright (c) Imagination Technologies Limited.
 \brief        Basic Tutorial that shows step-by-step how to initialise OpenGL ES 2.0, use it for drawing a triangle and terminate it.
              Entry Point: main
 *****************************************************************************/
 #include <stdio.h>
 #include <stdlib.h>
 #include <string.h>

 #include <sys/time.h>
 #include <errno.h>
 #include <fcntl.h>
 #include <termios.h>

 #include <screen/screen.h>

 #include "OpenGLESHelloAPI.h"

 #if !defined(CONNAME)
 #define CONNAME "/dev/tty"
 #endif

 #if !defined(KEYPAD_INPUT)
 #define KEYPAD_INPUT "/dev/con1"
 #endif

 uint32_t display;
 screen_context_t screen_context;
 screen_window_t screen_window;

 int devfd;
 struct termios termio;
 struct termios termio_orig;
 int keypad_fd;
 int keyboard_fd;
 bool keyboardShiftHeld; // Is one of the shift keys on the keyboard being held down? (Keyboard device only - not terminal).

 void initInput()
 {

If this app is in the background, ignore SIGTTIN and SIGTTOU.

signal(SIGTTIN, SIG_IGN);
signal(SIGTTOU, SIG_IGN);

Keyboard handling.

if ((devfd = open(CONNAME, O_RDWR | O_NDELAY)) <= 0)
{
    printf("Can't open tty '" CONNAME "'");
}
else
{
    tcgetattr(devfd, &termio_orig);
    tcgetattr(devfd, &termio);
    cfmakeraw(&termio);
    termio.c_oflag |= OPOST | ONLCR; // Turn back on CR-LF expansion on output.
    termio.c_cc[VMIN] = 1;
    termio.c_cc[VTIME] = 0;

    if (tcsetattr(devfd, TCSANOW, &termio) == -1)
    {
        printf("Can't set tty attributes for '" CONNAME "'");
    }
}

Keypad handling.

if ((keypad_fd = open(KEYPAD_INPUT, O_RDONLY | O_NDELAY)) <= 0)
{
    printf("Can't open keypad input device (%s)\n", KEYPAD_INPUT);
}

Construct read and write path.

   pid_t ourPid = getpid();
   char *exePath, srcLink[64];
   int len = 256;
   int res;
   FILE* fp;

   sprintf(srcLink, "/proc/%d/exefile", ourPid);
   exePath = 0;

   do
   {
       len *= 2;
       delete[] exePath;
       exePath = new char[len];
       fp = fopen(srcLink, "r");
       fgets(exePath, len, fp);
       res = strlen(exePath);
       fclose(fp);

       if (res < 0)
       {
           printf("Readlink %s failed. The application name, read path and write path have not been set.\n", exePath);
           break;
       }
   } while (res >= len);

   if (res >= 0)
   {
       exePath[res] = '\0'; // Null-terminate readlink's result.
   }

   delete[] exePath;

   /*
    Remove the blinking cursor on a screen.

    This is the equivalent of:
    echo -n -e "\033[?25l" > /dev/tty0

    The above command can be undone with:
    echo -n -e "\033[?25h" > /dev/tty0
    */
   FILE* tty = 0;
   tty = fopen("/dev/tty0", "w");
   if (tty != 0)
   {
       const char txt[] = { 27 /* the ESCAPE ASCII character */
           ,
           '[', '?', '2', '5', 'l', 0 };

       fprintf(tty, "%s", txt);
       fclose(tty);
   }
}

bool initializeWindow()
{
   int size[2];
   int ePixelFormat;
   int usage = SCREEN_USAGE_NATIVE;

   screen_create_context(&screen_context, SCREEN_APPLICATION_CONTEXT);

   if (screen_context == 0)
   {
       printf("Failed to Create Screen Context");
       return false;
   }

   screen_create_window(&screen_window, screen_context);

   if (screen_window == 0)
   {
       printf("Failed to Create Screen Window");
       return false;
   }

   screen_get_window_property_iv(screen_window, SCREEN_PROPERTY_BUFFER_SIZE, size);

   screen_set_window_property_iv(screen_window, SCREEN_PROPERTY_FORMAT, &ePixelFormat);
   screen_set_window_property_iv(screen_window, SCREEN_PROPERTY_USAGE, &usage);
   screen_create_window_buffers(screen_window, 2);

   initInput();

   return true;
}

void releaseWindow()
{
   screen_window = 0;
   screen_context = 0;
   display = 0xFFFF;

   close(keyboard_fd);
   close(keypad_fd);
}

/*!***************************************************************************
\param[in]         argc           Number of arguments passed to the application, ignored.
\param[in]         argv           Command line strings passed to the application, ignored.
\return        Result code to send to the Operating System
\brief Main function of the program, executes other functions.
*****************************************************************************/
int main(int /*argc*/, char** /*argv*/)
{
   OpenGLESAPI helloAPI;

Get access to a native display.

initializeWindow();

helloAPI._surfaceData.deviceContext = (EGLNativeDisplayType)screen_context;
helloAPI._surfaceData.window = (EGLNativeWindowType)screen_window;

helloAPI.initializeEGL();
helloAPI.initializeGLES();

Renders a triangle for 800 frames using the state setup in the previous function.

for (int i = 0; i < 800; ++i)
{
    if (!helloAPI.drawFrame() || !helloAPI.swapEGLBuffers())
    {
        break;
    }
}

helloAPI.releaseGLState();
helloAPI.releaseEGLState();

Destroy the eglWindow.

   return 0;
}