source: trunk/src/eglapp.cpp @ 1673

Last change on this file since 1673 was 1673, checked in by sam, 8 years ago

core: remove debug code that caused all builds to fail.

  • Property svn:keywords set to Id
File size: 6.2 KB
Line 
1//
2// Lol Engine
3//
4// Copyright: (c) 2010-2011 Sam Hocevar <sam@hocevar.net>
5//   This program is free software; you can redistribute it and/or
6//   modify it under the terms of the Do What The Fuck You Want To
7//   Public License, Version 2, as published by Sam Hocevar. See
8//   http://sam.zoy.org/projects/COPYING.WTFPL for more details.
9//
10
11#if defined HAVE_CONFIG_H
12#   include "config.h"
13#endif
14
15#if defined USE_EGL
16#   if defined HAVE_BCM_HOST_H
17#       include <bcm_host.h>
18#   else
19#       include <X11/Xlib.h>
20#       include <X11/Xatom.h>
21#       include <X11/Xutil.h>
22#   endif
23#   include <EGL/egl.h>
24#   include <EGL/eglext.h>
25#endif
26
27#include "core.h"
28#include "lolgl.h"
29#include "eglapp.h"
30
31namespace lol
32{
33
34/*
35 * EGL App implementation class
36 */
37
38class EglAppData
39{
40    friend class EglApp;
41
42private:
43#if defined USE_EGL
44    EGLDisplay egl_dpy;
45    EGLContext egl_ctx;
46    EGLSurface egl_surf;
47    uvec2 screen_size;
48#   if defined HAVE_BCM_HOST_H
49    EGL_DISPMANX_WINDOW_T nativewindow;
50#   else
51    Display *dpy;
52    Window win;
53#   endif
54#endif
55};
56
57/*
58 * Public EglApp class
59 */
60
61EglApp::EglApp(char const *title, ivec2 res, float fps) :
62    data(new EglAppData())
63{
64#if defined USE_EGL
65#   if defined HAVE_BCM_HOST_H
66    bcm_host_init();
67
68    data->egl_dpy = eglGetDisplay(EGL_DEFAULT_DISPLAY);
69#   else
70    data->dpy = XOpenDisplay(NULL);
71    if (data->dpy == NULL)
72    {
73        Log::Error("cannot connect to X server\n");
74        exit(EXIT_FAILURE);
75    }
76
77    Window root = DefaultRootWindow(data->dpy);
78
79    XSetWindowAttributes swa;
80    swa.event_mask = ExposureMask | PointerMotionMask | KeyPressMask;
81
82    data->win = XCreateWindow(data->dpy, root, 0, 0, res.x, res.y, 0,
83                              CopyFromParent, InputOutput,
84                              CopyFromParent, CWEventMask, &swa);
85
86    XSetWindowAttributes xattr;
87
88    xattr.override_redirect = False;
89    XChangeWindowAttributes(data->dpy, data->win, CWOverrideRedirect, &xattr);
90
91    XWMHints hints;
92    hints.flags = InputHint;
93    hints.input = True;
94    XSetWMHints(data->dpy, data->win, &hints);
95
96    XMapWindow(data->dpy, data->win);
97    XStoreName(data->dpy, data->win, title);
98
99    data->egl_dpy = eglGetDisplay((EGLNativeDisplayType)data->dpy);
100#   endif
101    if (data->egl_dpy == EGL_NO_DISPLAY)
102    {
103        Log::Error("cannot get EGL display\n");
104        exit(EXIT_FAILURE);
105    }
106
107    if (!eglInitialize(data->egl_dpy, NULL, NULL))
108    {
109        Log::Error("cannot initialize EGL\n");
110        exit(EXIT_FAILURE);
111    }
112
113    EGLint attr[] =
114    {
115        EGL_BUFFER_SIZE, 16,
116        EGL_RENDERABLE_TYPE,
117#if defined HAVE_GLES_2X
118        EGL_OPENGL_ES2_BIT,
119#endif
120        EGL_NONE
121    };
122
123    EGLConfig ecfg;
124    EGLint num_config;
125    if (!eglChooseConfig(data->egl_dpy, attr, &ecfg, 1, &num_config))
126    {
127        Log::Error("cannot choose EGL config (%i)\n", eglGetError());
128        exit(EXIT_FAILURE);
129    }
130
131    if (num_config != 1)
132    {
133        Log::Error("cannot choose between %i EGL configs\n", num_config);
134        exit(EXIT_FAILURE);
135    }
136
137    if (!eglBindAPI(EGL_OPENGL_ES_API))
138    {
139        Log::Error("cannot bind OpenGL ES API (%i)\n", eglGetError());
140        exit(EXIT_FAILURE);
141    }
142
143#   if defined HAVE_BCM_HOST_H
144    DISPMANX_ELEMENT_HANDLE_T dispman_element;
145    DISPMANX_DISPLAY_HANDLE_T dispman_display;
146    DISPMANX_UPDATE_HANDLE_T dispman_update;
147    VC_RECT_T dst_rect;
148    VC_RECT_T src_rect;
149
150    graphics_get_display_size(0 /* LCD */, &data->screen_size.x, &data->screen_size.y);
151
152    dst_rect.x = 0;
153    dst_rect.y = 0;
154    dst_rect.width = data->screen_size.x;
155    dst_rect.height = data->screen_size.y;
156
157    src_rect.x = 0;
158    src_rect.y = 0;
159    src_rect.width = data->screen_size.x << 16;
160    src_rect.height = data->screen_size.y << 16;
161
162    dispman_display = vc_dispmanx_display_open(0 /* LCD */);
163    dispman_update = vc_dispmanx_update_start(0);
164
165    dispman_element = vc_dispmanx_element_add(dispman_update, dispman_display,
166        0/*layer*/, &dst_rect, 0/*src*/, &src_rect, DISPMANX_PROTECTION_NONE,
167        0 /*alpha*/, 0/*clamp*/, (DISPMANX_TRANSFORM_T)0/*transform*/);
168
169    data->nativewindow.element = dispman_element;
170    data->nativewindow.width = data->screen_size.x;
171    data->nativewindow.height = data->screen_size.y;
172    vc_dispmanx_update_submit_sync(dispman_update);
173
174    data->egl_surf = eglCreateWindowSurface(data->egl_dpy, ecfg,
175                                            &data->nativewindow, NULL);
176#   else
177    data->egl_surf = eglCreateWindowSurface(data->egl_dpy, ecfg,
178                                            (EGLNativeWindowType)data->win,
179                                            NULL);
180#   endif
181    if (data->egl_surf == EGL_NO_SURFACE)
182    {
183        Log::Error("cannot create EGL surface (%i)\n", eglGetError());
184        exit(EXIT_FAILURE);
185    }
186
187    EGLint ctxattr[] =
188    {
189#if defined HAVE_GLES_2X
190        EGL_CONTEXT_CLIENT_VERSION, 2,
191#endif
192        EGL_NONE
193    };
194    data->egl_ctx = eglCreateContext(data->egl_dpy, ecfg,
195                                     EGL_NO_CONTEXT, ctxattr);
196    if (data->egl_ctx == EGL_NO_CONTEXT)
197    {
198        Log::Error("cannot create EGL context (%i)\n", eglGetError());
199        exit(EXIT_FAILURE);
200    }
201
202    eglMakeCurrent(data->egl_dpy, data->egl_surf,
203                   data->egl_surf, data->egl_ctx);
204
205#   if !defined HAVE_BCM_HOST_H
206    XWindowAttributes gwa;
207    XGetWindowAttributes(data->dpy, data->win, &gwa);
208    data->screen_size = ivec2(gwa.width, gwa.height);
209#   endif
210
211    /* Initialise everything */
212    Ticker::Setup(fps);
213    Video::Setup((ivec2)data->screen_size);
214    Audio::Setup(2);
215#endif
216}
217
218void EglApp::ShowPointer(bool show)
219{
220    ;
221}
222
223void EglApp::Run()
224{
225    while (!Ticker::Finished())
226    {
227        /* Tick the renderer, show the frame and clamp to desired framerate. */
228        Ticker::TickDraw();
229#if defined USE_EGL
230        eglSwapBuffers(data->egl_dpy, data->egl_surf);
231#endif
232    }
233}
234
235EglApp::~EglApp()
236{
237#if defined USE_EGL
238    eglDestroyContext(data->egl_dpy, data->egl_ctx);
239    eglDestroySurface(data->egl_dpy, data->egl_surf);
240    eglTerminate(data->egl_dpy);
241#   if defined HAVE_BCM_HOST_H
242    /* FIXME */
243#   else
244    XDestroyWindow(data->dpy, data->win);
245    XCloseDisplay(data->dpy);
246#   endif
247#endif
248
249    delete data;
250}
251
252} /* namespace lol */
253
Note: See TracBrowser for help on using the repository browser.