src/video/SDL_renderer_gles.c
author Sam Lantinga <slouken@libsdl.org>
Sat, 20 Dec 2008 12:00:00 +0000
changeset 2884 9dde605c7540
parent 2859 99210400e8b9
child 2936 066384910f50
permissions -rw-r--r--
Date: Fri, 19 Dec 2008 20:17:35 +0100
From: Couriersud
Subject: Re: Aw: Experience using SDL1.3 in sdlmame/Proposal for api additions

> For consistency you'd probably want:
> SDL_SetRenderDrawColor(Uint8 r, Uint8 g, Uint8 b, Uint8 a);
> SDL_SetRenderDrawBlendMode(SDL_BlendMode blendMode);
> SDL_RenderLine(int x1, int y1, int x2, int y2);
> SDL_RenderFill(SDL_Rect *rect);
>
> You probably also want to add API functions query the current state.
>

I have implemented the above api for the opengl, x11, directfb and
software renderers. I have also renamed *TEXTUREBLENDMODE* constants to
BLENDMODE*. The unix build compiles. The windows renderer still needs to
be updated, but I have no windows development machine at hand. Have a
look at the x11 renderer for a sample.

Vector games now run at 90% both on opengl and directfb in comparison to
sdlmame's own opengl renderer. The same applies to raster games.

The diff also includes

a) Changed XDrawRect to XFillRect in x11 renderer
b) A number of changes to fix blending and modulation issues in the
directfb renderer.
hfutrell@2739
     1
/*
hfutrell@2739
     2
    SDL - Simple DirectMedia Layer
slouken@2859
     3
    Copyright (C) 1997-2009 Sam Lantinga
hfutrell@2739
     4
hfutrell@2739
     5
    This library is free software; you can redistribute it and/or
hfutrell@2739
     6
    modify it under the terms of the GNU Lesser General Public
hfutrell@2739
     7
    License as published by the Free Software Foundation; either
hfutrell@2739
     8
    version 2.1 of the License, or (at your option) any later version.
hfutrell@2739
     9
hfutrell@2739
    10
    This library is distributed in the hope that it will be useful,
hfutrell@2739
    11
    but WITHOUT ANY WARRANTY; without even the implied warranty of
hfutrell@2739
    12
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
hfutrell@2739
    13
    Lesser General Public License for more details.
hfutrell@2739
    14
hfutrell@2739
    15
    You should have received a copy of the GNU Lesser General Public
hfutrell@2739
    16
    License along with this library; if not, write to the Free Software
hfutrell@2739
    17
    Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
hfutrell@2739
    18
hfutrell@2739
    19
    Sam Lantinga
hfutrell@2739
    20
    slouken@libsdl.org
hfutrell@2739
    21
*/
hfutrell@2739
    22
#include "SDL_config.h"
hfutrell@2739
    23
hfutrell@2739
    24
#if SDL_VIDEO_RENDER_OGL_ES
hfutrell@2739
    25
hfutrell@2739
    26
#include "SDL_video.h"
hfutrell@2739
    27
#include "SDL_opengles.h"
hfutrell@2739
    28
#include "SDL_sysvideo.h"
hfutrell@2739
    29
#include "SDL_pixels_c.h"
hfutrell@2739
    30
#include "SDL_rect_c.h"
hfutrell@2739
    31
#include "SDL_yuv_sw_c.h"
hfutrell@2739
    32
hfutrell@2739
    33
/* OpenGL ES 1.1 renderer implementation, based on the OpenGL renderer */
hfutrell@2739
    34
hfutrell@2739
    35
static const float inv255f = 1.0f / 255.0f;
hfutrell@2739
    36
hfutrell@2739
    37
static SDL_Renderer *GLES_CreateRenderer(SDL_Window * window, Uint32 flags);
hfutrell@2739
    38
static int GLES_ActivateRenderer(SDL_Renderer * renderer);
hfutrell@2739
    39
static int GLES_DisplayModeChanged(SDL_Renderer * renderer);
hfutrell@2739
    40
static int GLES_CreateTexture(SDL_Renderer * renderer, SDL_Texture * texture);
hfutrell@2739
    41
static int GLES_QueryTexturePixels(SDL_Renderer * renderer,
slouken@2753
    42
                                   SDL_Texture * texture, void **pixels,
slouken@2753
    43
                                   int *pitch);
hfutrell@2739
    44
static int GLES_SetTexturePalette(SDL_Renderer * renderer,
slouken@2753
    45
                                  SDL_Texture * texture,
slouken@2753
    46
                                  const SDL_Color * colors, int firstcolor,
slouken@2753
    47
                                  int ncolors);
hfutrell@2739
    48
static int GLES_GetTexturePalette(SDL_Renderer * renderer,
slouken@2753
    49
                                  SDL_Texture * texture, SDL_Color * colors,
slouken@2753
    50
                                  int firstcolor, int ncolors);
hfutrell@2739
    51
static int GLES_SetTextureColorMod(SDL_Renderer * renderer,
slouken@2753
    52
                                   SDL_Texture * texture);
hfutrell@2739
    53
static int GLES_SetTextureAlphaMod(SDL_Renderer * renderer,
slouken@2753
    54
                                   SDL_Texture * texture);
hfutrell@2739
    55
static int GLES_SetTextureBlendMode(SDL_Renderer * renderer,
slouken@2753
    56
                                    SDL_Texture * texture);
hfutrell@2739
    57
static int GLES_SetTextureScaleMode(SDL_Renderer * renderer,
slouken@2753
    58
                                    SDL_Texture * texture);
hfutrell@2739
    59
static int GLES_UpdateTexture(SDL_Renderer * renderer, SDL_Texture * texture,
slouken@2753
    60
                              const SDL_Rect * rect, const void *pixels,
slouken@2753
    61
                              int pitch);
hfutrell@2739
    62
static int GLES_LockTexture(SDL_Renderer * renderer, SDL_Texture * texture,
slouken@2753
    63
                            const SDL_Rect * rect, int markDirty,
slouken@2753
    64
                            void **pixels, int *pitch);
slouken@2753
    65
static void GLES_UnlockTexture(SDL_Renderer * renderer,
slouken@2753
    66
                               SDL_Texture * texture);
hfutrell@2739
    67
static void GLES_DirtyTexture(SDL_Renderer * renderer, SDL_Texture * texture,
slouken@2753
    68
                              int numrects, const SDL_Rect * rects);
hfutrell@2739
    69
static int GLES_RenderFill(SDL_Renderer * renderer, Uint8 r, Uint8 g, Uint8 b,
slouken@2753
    70
                           Uint8 a, const SDL_Rect * rect);
hfutrell@2739
    71
static int GLES_RenderCopy(SDL_Renderer * renderer, SDL_Texture * texture,
slouken@2753
    72
                           const SDL_Rect * srcrect,
slouken@2753
    73
                           const SDL_Rect * dstrect);
hfutrell@2739
    74
static void GLES_RenderPresent(SDL_Renderer * renderer);
slouken@2753
    75
static void GLES_DestroyTexture(SDL_Renderer * renderer,
slouken@2753
    76
                                SDL_Texture * texture);
hfutrell@2739
    77
static void GLES_DestroyRenderer(SDL_Renderer * renderer);
hfutrell@2739
    78
hfutrell@2739
    79
hfutrell@2739
    80
SDL_RenderDriver GL_ES_RenderDriver = {
hfutrell@2739
    81
    GLES_CreateRenderer,
hfutrell@2739
    82
    {
hfutrell@2739
    83
     "opengl_es",
hfutrell@2739
    84
     (SDL_RENDERER_SINGLEBUFFER | SDL_RENDERER_PRESENTDISCARD |
hfutrell@2739
    85
      SDL_RENDERER_PRESENTVSYNC | SDL_RENDERER_ACCELERATED),
hfutrell@2739
    86
     (SDL_TEXTUREMODULATE_NONE | SDL_TEXTUREMODULATE_COLOR |
hfutrell@2739
    87
      SDL_TEXTUREMODULATE_ALPHA),
slouken@2884
    88
     (SDL_BLENDMODE_NONE | SDL_BLENDMODE_MASK |
slouken@2884
    89
      SDL_BLENDMODE_BLEND | SDL_BLENDMODE_ADD | SDL_BLENDMODE_MOD),
hfutrell@2739
    90
     (SDL_TEXTURESCALEMODE_NONE | SDL_TEXTURESCALEMODE_FAST |
hfutrell@2739
    91
      SDL_TEXTURESCALEMODE_SLOW), 2,
slouken@2753
    92
     {
slouken@2753
    93
      SDL_PIXELFORMAT_RGB24,
slouken@2753
    94
      SDL_PIXELFORMAT_ABGR8888,
slouken@2753
    95
      },
slouken@2753
    96
     0,
hfutrell@2739
    97
     0}
hfutrell@2739
    98
};
hfutrell@2739
    99
hfutrell@2739
   100
typedef struct
hfutrell@2739
   101
{
hfutrell@2739
   102
    SDL_GLContext context;
hfutrell@2739
   103
    SDL_bool updateSize;
hfutrell@2739
   104
    int blendMode;
slouken@2753
   105
hfutrell@2739
   106
#ifndef APIENTRY
hfutrell@2739
   107
#define APIENTRY
hfutrell@2739
   108
#endif
slouken@2753
   109
slouken@2753
   110
    SDL_bool useDrawTexture;
slouken@2753
   111
    SDL_bool GL_OES_draw_texture_supported;
slouken@2753
   112
slouken@2753
   113
    /* OpenGL ES functions */
slouken@2753
   114
#define SDL_PROC(ret,func,params) ret (APIENTRY *func) params;
slouken@2753
   115
#include "SDL_glesfuncs.h"
slouken@2753
   116
#undef SDL_PROC
hfutrell@2739
   117
hfutrell@2739
   118
} GLES_RenderData;
hfutrell@2739
   119
hfutrell@2739
   120
typedef struct
hfutrell@2739
   121
{
hfutrell@2739
   122
    GLuint texture;
hfutrell@2739
   123
    GLenum type;
hfutrell@2739
   124
    GLfloat texw;
hfutrell@2739
   125
    GLfloat texh;
hfutrell@2739
   126
    GLenum format;
hfutrell@2739
   127
    GLenum formattype;
hfutrell@2739
   128
    void *pixels;
hfutrell@2739
   129
    int pitch;
hfutrell@2739
   130
    SDL_DirtyRectList dirty;
hfutrell@2739
   131
} GLES_TextureData;
hfutrell@2739
   132
hfutrell@2739
   133
static void
hfutrell@2739
   134
GLES_SetError(const char *prefix, GLenum result)
hfutrell@2739
   135
{
hfutrell@2739
   136
    const char *error;
hfutrell@2739
   137
hfutrell@2739
   138
    switch (result) {
hfutrell@2739
   139
    case GL_NO_ERROR:
hfutrell@2739
   140
        error = "GL_NO_ERROR";
hfutrell@2739
   141
        break;
hfutrell@2739
   142
    case GL_INVALID_ENUM:
hfutrell@2739
   143
        error = "GL_INVALID_ENUM";
hfutrell@2739
   144
        break;
hfutrell@2739
   145
    case GL_INVALID_VALUE:
hfutrell@2739
   146
        error = "GL_INVALID_VALUE";
hfutrell@2739
   147
        break;
hfutrell@2739
   148
    case GL_INVALID_OPERATION:
hfutrell@2739
   149
        error = "GL_INVALID_OPERATION";
hfutrell@2739
   150
        break;
hfutrell@2739
   151
    case GL_STACK_OVERFLOW:
hfutrell@2739
   152
        error = "GL_STACK_OVERFLOW";
hfutrell@2739
   153
        break;
hfutrell@2739
   154
    case GL_STACK_UNDERFLOW:
hfutrell@2739
   155
        error = "GL_STACK_UNDERFLOW";
hfutrell@2739
   156
        break;
hfutrell@2739
   157
    case GL_OUT_OF_MEMORY:
hfutrell@2739
   158
        error = "GL_OUT_OF_MEMORY";
hfutrell@2739
   159
        break;
hfutrell@2739
   160
    default:
hfutrell@2739
   161
        error = "UNKNOWN";
hfutrell@2739
   162
        break;
hfutrell@2739
   163
    }
hfutrell@2739
   164
    SDL_SetError("%s: %s", prefix, error);
hfutrell@2739
   165
}
hfutrell@2739
   166
hfutrell@2739
   167
static int
hfutrell@2739
   168
GLES_LoadFunctions(GLES_RenderData * data)
hfutrell@2739
   169
{
slouken@2753
   170
slouken@2753
   171
#define SDL_PROC(ret,func,params) \
hfutrell@2739
   172
	data->func = func;
slouken@2753
   173
#include "SDL_glesfuncs.h"
slouken@2753
   174
#undef SDL_PROC
slouken@2753
   175
hfutrell@2739
   176
    return 0;
hfutrell@2739
   177
}
hfutrell@2739
   178
hfutrell@2739
   179
void
hfutrell@2739
   180
GLES_AddRenderDriver(_THIS)
hfutrell@2739
   181
{
hfutrell@2739
   182
    if (_this->GL_CreateContext) {
hfutrell@2739
   183
        SDL_AddRenderDriver(0, &GL_ES_RenderDriver);
hfutrell@2739
   184
    }
hfutrell@2739
   185
}
hfutrell@2739
   186
hfutrell@2739
   187
SDL_Renderer *
hfutrell@2739
   188
GLES_CreateRenderer(SDL_Window * window, Uint32 flags)
hfutrell@2739
   189
{
slouken@2753
   190
hfutrell@2739
   191
    SDL_Renderer *renderer;
hfutrell@2739
   192
    GLES_RenderData *data;
hfutrell@2739
   193
    GLint value;
hfutrell@2739
   194
    int doublebuffer;
hfutrell@2739
   195
hfutrell@2739
   196
    if (!(window->flags & SDL_WINDOW_OPENGL)) {
hfutrell@2739
   197
        if (SDL_RecreateWindow(window, window->flags | SDL_WINDOW_OPENGL) < 0) {
hfutrell@2739
   198
            return NULL;
hfutrell@2739
   199
        }
hfutrell@2739
   200
    }
hfutrell@2739
   201
hfutrell@2739
   202
    renderer = (SDL_Renderer *) SDL_calloc(1, sizeof(*renderer));
hfutrell@2739
   203
    if (!renderer) {
hfutrell@2739
   204
        SDL_OutOfMemory();
hfutrell@2739
   205
        return NULL;
hfutrell@2739
   206
    }
hfutrell@2739
   207
hfutrell@2739
   208
    data = (GLES_RenderData *) SDL_calloc(1, sizeof(*data));
hfutrell@2739
   209
    if (!data) {
hfutrell@2739
   210
        GLES_DestroyRenderer(renderer);
hfutrell@2739
   211
        SDL_OutOfMemory();
hfutrell@2739
   212
        return NULL;
hfutrell@2739
   213
    }
hfutrell@2739
   214
hfutrell@2739
   215
    renderer->ActivateRenderer = GLES_ActivateRenderer;
hfutrell@2739
   216
    renderer->DisplayModeChanged = GLES_DisplayModeChanged;
hfutrell@2739
   217
    renderer->CreateTexture = GLES_CreateTexture;
hfutrell@2739
   218
    renderer->QueryTexturePixels = GLES_QueryTexturePixels;
hfutrell@2739
   219
    renderer->SetTexturePalette = GLES_SetTexturePalette;
hfutrell@2739
   220
    renderer->GetTexturePalette = GLES_GetTexturePalette;
hfutrell@2739
   221
    renderer->SetTextureColorMod = GLES_SetTextureColorMod;
hfutrell@2739
   222
    renderer->SetTextureAlphaMod = GLES_SetTextureAlphaMod;
hfutrell@2739
   223
    renderer->SetTextureBlendMode = GLES_SetTextureBlendMode;
hfutrell@2739
   224
    renderer->SetTextureScaleMode = GLES_SetTextureScaleMode;
hfutrell@2739
   225
    renderer->UpdateTexture = GLES_UpdateTexture;
hfutrell@2739
   226
    renderer->LockTexture = GLES_LockTexture;
hfutrell@2739
   227
    renderer->UnlockTexture = GLES_UnlockTexture;
hfutrell@2739
   228
    renderer->DirtyTexture = GLES_DirtyTexture;
hfutrell@2739
   229
    renderer->RenderFill = GLES_RenderFill;
hfutrell@2739
   230
    renderer->RenderCopy = GLES_RenderCopy;
hfutrell@2739
   231
    renderer->RenderPresent = GLES_RenderPresent;
hfutrell@2739
   232
    renderer->DestroyTexture = GLES_DestroyTexture;
hfutrell@2739
   233
    renderer->DestroyRenderer = GLES_DestroyRenderer;
hfutrell@2739
   234
    renderer->info = GL_ES_RenderDriver.info;
hfutrell@2739
   235
    renderer->window = window->id;
hfutrell@2739
   236
    renderer->driverdata = data;
slouken@2753
   237
slouken@2753
   238
slouken@2753
   239
    renderer->info.flags =
slouken@2753
   240
        (SDL_RENDERER_PRESENTDISCARD | SDL_RENDERER_ACCELERATED);
hfutrell@2739
   241
hfutrell@2739
   242
    if (GLES_LoadFunctions(data) < 0) {
hfutrell@2739
   243
        GLES_DestroyRenderer(renderer);
hfutrell@2739
   244
        return NULL;
hfutrell@2739
   245
    }
hfutrell@2739
   246
hfutrell@2739
   247
    data->context = SDL_GL_CreateContext(window->id);
hfutrell@2739
   248
    if (!data->context) {
hfutrell@2739
   249
        GLES_DestroyRenderer(renderer);
hfutrell@2739
   250
        return NULL;
hfutrell@2739
   251
    }
hfutrell@2739
   252
    if (SDL_GL_MakeCurrent(window->id, data->context) < 0) {
hfutrell@2739
   253
        GLES_DestroyRenderer(renderer);
hfutrell@2739
   254
        return NULL;
hfutrell@2739
   255
    }
hfutrell@2739
   256
hfutrell@2739
   257
    if (flags & SDL_RENDERER_PRESENTVSYNC) {
hfutrell@2739
   258
        SDL_GL_SetSwapInterval(1);
hfutrell@2739
   259
    } else {
hfutrell@2739
   260
        SDL_GL_SetSwapInterval(0);
hfutrell@2739
   261
    }
hfutrell@2739
   262
    if (SDL_GL_GetSwapInterval() > 0) {
hfutrell@2739
   263
        renderer->info.flags |= SDL_RENDERER_PRESENTVSYNC;
hfutrell@2739
   264
    }
hfutrell@2739
   265
hfutrell@2739
   266
    if (SDL_GL_GetAttribute(SDL_GL_DOUBLEBUFFER, &doublebuffer) == 0) {
hfutrell@2739
   267
        if (!doublebuffer) {
hfutrell@2739
   268
            renderer->info.flags |= SDL_RENDERER_SINGLEBUFFER;
hfutrell@2739
   269
        }
hfutrell@2739
   270
    }
slouken@2753
   271
slouken@2753
   272
    if (SDL_GL_ExtensionSupported("GL_OES_draw_texture")) {
slouken@2753
   273
        data->GL_OES_draw_texture_supported = SDL_TRUE;
slouken@2753
   274
        data->useDrawTexture = SDL_TRUE;
slouken@2753
   275
    } else {
slouken@2753
   276
        data->GL_OES_draw_texture_supported = SDL_FALSE;
slouken@2753
   277
        data->useDrawTexture = SDL_FALSE;
slouken@2753
   278
    }
hfutrell@2739
   279
hfutrell@2739
   280
    data->glGetIntegerv(GL_MAX_TEXTURE_SIZE, &value);
hfutrell@2739
   281
    renderer->info.max_texture_width = value;
hfutrell@2739
   282
    data->glGetIntegerv(GL_MAX_TEXTURE_SIZE, &value);
hfutrell@2739
   283
    renderer->info.max_texture_height = value;
hfutrell@2739
   284
hfutrell@2739
   285
    /* Set up parameters for rendering */
hfutrell@2739
   286
    data->blendMode = -1;
hfutrell@2739
   287
    data->glDisable(GL_DEPTH_TEST);
hfutrell@2739
   288
    data->glDisable(GL_CULL_FACE);
slouken@2753
   289
    data->glEnable(GL_TEXTURE_2D);
hfutrell@2739
   290
    data->updateSize = SDL_TRUE;
hfutrell@2739
   291
hfutrell@2739
   292
    return renderer;
hfutrell@2739
   293
}
hfutrell@2739
   294
slouken@2753
   295
static int
slouken@2753
   296
GLES_ActivateRenderer(SDL_Renderer * renderer)
hfutrell@2739
   297
{
slouken@2753
   298
slouken@2753
   299
    GLES_RenderData *data = (GLES_RenderData *) renderer->driverdata;
hfutrell@2739
   300
    SDL_Window *window = SDL_GetWindowFromID(renderer->window);
slouken@2753
   301
hfutrell@2739
   302
    if (SDL_GL_MakeCurrent(window->id, data->context) < 0) {
hfutrell@2739
   303
        return -1;
hfutrell@2739
   304
    }
hfutrell@2739
   305
    if (data->updateSize) {
hfutrell@2739
   306
        data->glMatrixMode(GL_PROJECTION);
hfutrell@2739
   307
        data->glLoadIdentity();
hfutrell@2739
   308
        data->glMatrixMode(GL_MODELVIEW);
hfutrell@2739
   309
        data->glLoadIdentity();
hfutrell@2739
   310
        data->glViewport(0, 0, window->w, window->h);
slouken@2753
   311
        data->glOrthof(0.0, (GLfloat) window->w, (GLfloat) window->h, 0.0,
slouken@2753
   312
                       0.0, 1.0);
hfutrell@2739
   313
        data->updateSize = SDL_FALSE;
hfutrell@2739
   314
    }
hfutrell@2739
   315
    return 0;
hfutrell@2739
   316
}
hfutrell@2739
   317
hfutrell@2739
   318
static int
hfutrell@2739
   319
GLES_DisplayModeChanged(SDL_Renderer * renderer)
hfutrell@2739
   320
{
hfutrell@2739
   321
    GLES_RenderData *data = (GLES_RenderData *) renderer->driverdata;
hfutrell@2739
   322
hfutrell@2739
   323
    data->updateSize = SDL_TRUE;
hfutrell@2739
   324
    return 0;
hfutrell@2739
   325
}
hfutrell@2739
   326
hfutrell@2739
   327
static __inline__ int
hfutrell@2739
   328
power_of_2(int input)
hfutrell@2739
   329
{
hfutrell@2739
   330
    int value = 1;
hfutrell@2739
   331
hfutrell@2739
   332
    while (value < input) {
hfutrell@2739
   333
        value <<= 1;
hfutrell@2739
   334
    }
hfutrell@2739
   335
    return value;
hfutrell@2739
   336
}
hfutrell@2739
   337
hfutrell@2739
   338
static int
hfutrell@2739
   339
GLES_CreateTexture(SDL_Renderer * renderer, SDL_Texture * texture)
hfutrell@2739
   340
{
hfutrell@2739
   341
    GLES_RenderData *renderdata = (GLES_RenderData *) renderer->driverdata;
hfutrell@2739
   342
    SDL_Window *window = SDL_GetWindowFromID(renderer->window);
hfutrell@2739
   343
    GLES_TextureData *data;
hfutrell@2739
   344
    GLint internalFormat;
hfutrell@2739
   345
    GLenum format, type;
hfutrell@2739
   346
    int texture_w, texture_h;
hfutrell@2739
   347
    GLenum result;
slouken@2753
   348
    switch (texture->format) {
slouken@2753
   349
    case SDL_PIXELFORMAT_INDEX1LSB:
slouken@2753
   350
    case SDL_PIXELFORMAT_INDEX1MSB:
slouken@2753
   351
    case SDL_PIXELFORMAT_INDEX8:
slouken@2753
   352
    case SDL_PIXELFORMAT_RGB332:
slouken@2753
   353
    case SDL_PIXELFORMAT_RGB444:
slouken@2753
   354
    case SDL_PIXELFORMAT_RGB555:
slouken@2753
   355
    case SDL_PIXELFORMAT_ARGB4444:
slouken@2753
   356
    case SDL_PIXELFORMAT_ARGB1555:
slouken@2753
   357
    case SDL_PIXELFORMAT_BGR24:
slouken@2753
   358
    case SDL_PIXELFORMAT_BGR888:
slouken@2753
   359
    case SDL_PIXELFORMAT_RGB888:
slouken@2753
   360
    case SDL_PIXELFORMAT_RGBA8888:
slouken@2753
   361
    case SDL_PIXELFORMAT_ARGB2101010:
slouken@2753
   362
    case SDL_PIXELFORMAT_ARGB8888:
slouken@2753
   363
    case SDL_PIXELFORMAT_RGB24:
slouken@2753
   364
        internalFormat = GL_RGB;
slouken@2753
   365
        format = GL_RGB;
slouken@2753
   366
        type = GL_UNSIGNED_BYTE;
slouken@2753
   367
        break;
slouken@2753
   368
    case SDL_PIXELFORMAT_ABGR8888:
slouken@2753
   369
        internalFormat = GL_RGBA;
slouken@2753
   370
        format = GL_RGBA;
slouken@2753
   371
        type = GL_UNSIGNED_BYTE;
slouken@2753
   372
        break;
slouken@2753
   373
        /*
slouken@2753
   374
           These formats would be supported if SDL had the necessary pixel formats
slouken@2753
   375
           case SDL_PIXELFORMAT_BGR565:
slouken@2753
   376
           internalFormat = GL_RGB;
slouken@2753
   377
           format = GL_RGB;
slouken@2753
   378
           type = GL_UNSIGNED_SHORT_5_6_5;
slouken@2753
   379
           break;                       
slouken@2753
   380
           case SDL_PIXELFORMAT_ABGR5551:
slouken@2753
   381
           internalFormat = GL_RGBA;
slouken@2753
   382
           format = GL_RGBA;
slouken@2753
   383
           type = GL_UNSIGNED_SHORT_5_5_5_1;
slouken@2753
   384
           break;
slouken@2753
   385
           case SDL_PIXELFORMAT_ABGR4444:
slouken@2753
   386
           internalFormat = GL_RGBA;
slouken@2753
   387
           format = GL_RGBA;
slouken@2753
   388
           type = GL_UNSIGNED_SHORT_4_4_4_4;
slouken@2753
   389
           break;
slouken@2753
   390
         */
slouken@2753
   391
    default:
slouken@2753
   392
        SDL_SetError("Unsupported texture format");
slouken@2753
   393
        return -1;
hfutrell@2739
   394
    }
slouken@2753
   395
slouken@2753
   396
    data = (GLES_TextureData *) SDL_calloc(1, sizeof(*data));
hfutrell@2739
   397
    if (!data) {
hfutrell@2739
   398
        SDL_OutOfMemory();
hfutrell@2739
   399
        return -1;
hfutrell@2739
   400
    }
hfutrell@2739
   401
hfutrell@2739
   402
    if (texture->access == SDL_TEXTUREACCESS_STREAMING) {
hfutrell@2739
   403
        data->pitch = texture->w * SDL_BYTESPERPIXEL(texture->format);
hfutrell@2739
   404
        data->pixels = SDL_malloc(texture->h * data->pitch);
hfutrell@2739
   405
        if (!data->pixels) {
hfutrell@2739
   406
            SDL_OutOfMemory();
hfutrell@2739
   407
            SDL_free(data);
hfutrell@2739
   408
            return -1;
hfutrell@2739
   409
        }
hfutrell@2739
   410
    }
hfutrell@2739
   411
hfutrell@2739
   412
    texture->driverdata = data;
hfutrell@2739
   413
hfutrell@2739
   414
    renderdata->glGetError();
hfutrell@2739
   415
    renderdata->glGenTextures(1, &data->texture);
slouken@2753
   416
slouken@2753
   417
    data->type = GL_TEXTURE_2D;
slouken@2753
   418
    /* no NPOV textures allowed in OpenGL ES (yet) */
slouken@2753
   419
    texture_w = power_of_2(texture->w);
slouken@2753
   420
    texture_h = power_of_2(texture->h);
slouken@2753
   421
    data->texw = (GLfloat) texture->w / texture_w;
slouken@2753
   422
    data->texh = (GLfloat) texture->h / texture_h;
slouken@2753
   423
hfutrell@2739
   424
    data->format = format;
hfutrell@2739
   425
    data->formattype = type;
hfutrell@2739
   426
    renderdata->glBindTexture(data->type, data->texture);
hfutrell@2739
   427
    renderdata->glTexParameteri(data->type, GL_TEXTURE_MIN_FILTER,
hfutrell@2739
   428
                                GL_NEAREST);
hfutrell@2739
   429
    renderdata->glTexParameteri(data->type, GL_TEXTURE_MAG_FILTER,
hfutrell@2739
   430
                                GL_NEAREST);
hfutrell@2739
   431
    renderdata->glTexParameteri(data->type, GL_TEXTURE_WRAP_S,
hfutrell@2739
   432
                                GL_CLAMP_TO_EDGE);
hfutrell@2739
   433
    renderdata->glTexParameteri(data->type, GL_TEXTURE_WRAP_T,
hfutrell@2739
   434
                                GL_CLAMP_TO_EDGE);
slouken@2753
   435
slouken@2753
   436
    renderdata->glTexImage2D(data->type, 0, internalFormat, texture_w,
slouken@2753
   437
                             texture_h, 0, format, type, NULL);
hfutrell@2739
   438
hfutrell@2739
   439
    result = renderdata->glGetError();
hfutrell@2739
   440
    if (result != GL_NO_ERROR) {
hfutrell@2739
   441
        GLES_SetError("glTexImage2D()", result);
hfutrell@2739
   442
        return -1;
hfutrell@2739
   443
    }
hfutrell@2739
   444
    return 0;
hfutrell@2739
   445
}
hfutrell@2739
   446
hfutrell@2739
   447
static int
hfutrell@2739
   448
GLES_QueryTexturePixels(SDL_Renderer * renderer, SDL_Texture * texture,
slouken@2753
   449
                        void **pixels, int *pitch)
hfutrell@2739
   450
{
hfutrell@2739
   451
    GLES_TextureData *data = (GLES_TextureData *) texture->driverdata;
hfutrell@2739
   452
hfutrell@2739
   453
    *pixels = data->pixels;
hfutrell@2739
   454
    *pitch = data->pitch;
hfutrell@2739
   455
    return 0;
hfutrell@2739
   456
}
hfutrell@2739
   457
hfutrell@2739
   458
static int
hfutrell@2739
   459
GLES_SetTexturePalette(SDL_Renderer * renderer, SDL_Texture * texture,
slouken@2753
   460
                       const SDL_Color * colors, int firstcolor, int ncolors)
hfutrell@2739
   461
{
slouken@2753
   462
    SDL_SetError("OpenGL ES does not support paletted textures");
hfutrell@2739
   463
    return -1;
hfutrell@2739
   464
}
hfutrell@2739
   465
hfutrell@2739
   466
static int
hfutrell@2739
   467
GLES_GetTexturePalette(SDL_Renderer * renderer, SDL_Texture * texture,
slouken@2753
   468
                       SDL_Color * colors, int firstcolor, int ncolors)
hfutrell@2739
   469
{
slouken@2753
   470
    SDL_SetError("OpenGL ES does not support paletted textures");
hfutrell@2739
   471
    return -1;
hfutrell@2739
   472
}
hfutrell@2739
   473
hfutrell@2739
   474
static void
hfutrell@2739
   475
SetupTextureUpdate(GLES_RenderData * renderdata, SDL_Texture * texture,
hfutrell@2739
   476
                   int pitch)
hfutrell@2739
   477
{
slouken@2753
   478
slouken@2753
   479
slouken@2753
   480
    GLES_TextureData *data = (GLES_TextureData *) texture->driverdata;
slouken@2753
   481
    renderdata->glBindTexture(data->type, data->texture);
hfutrell@2739
   482
    renderdata->glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
hfutrell@2739
   483
}
hfutrell@2739
   484
hfutrell@2739
   485
static int
hfutrell@2739
   486
GLES_SetTextureColorMod(SDL_Renderer * renderer, SDL_Texture * texture)
hfutrell@2739
   487
{
hfutrell@2739
   488
    return 0;
hfutrell@2739
   489
}
hfutrell@2739
   490
hfutrell@2739
   491
static int
hfutrell@2739
   492
GLES_SetTextureAlphaMod(SDL_Renderer * renderer, SDL_Texture * texture)
hfutrell@2739
   493
{
hfutrell@2739
   494
    return 0;
hfutrell@2739
   495
}
hfutrell@2739
   496
hfutrell@2739
   497
static int
hfutrell@2739
   498
GLES_SetTextureBlendMode(SDL_Renderer * renderer, SDL_Texture * texture)
hfutrell@2739
   499
{
hfutrell@2739
   500
    switch (texture->blendMode) {
slouken@2884
   501
    case SDL_BLENDMODE_NONE:
slouken@2884
   502
    case SDL_BLENDMODE_MASK:
slouken@2884
   503
    case SDL_BLENDMODE_BLEND:
slouken@2884
   504
    case SDL_BLENDMODE_ADD:
slouken@2884
   505
    case SDL_BLENDMODE_MOD:
hfutrell@2739
   506
        return 0;
hfutrell@2739
   507
    default:
hfutrell@2739
   508
        SDL_Unsupported();
slouken@2884
   509
        texture->blendMode = SDL_BLENDMODE_NONE;
hfutrell@2739
   510
        return -1;
hfutrell@2739
   511
    }
hfutrell@2739
   512
}
hfutrell@2739
   513
hfutrell@2739
   514
static int
hfutrell@2739
   515
GLES_SetTextureScaleMode(SDL_Renderer * renderer, SDL_Texture * texture)
hfutrell@2739
   516
{
hfutrell@2739
   517
    switch (texture->scaleMode) {
hfutrell@2739
   518
    case SDL_TEXTURESCALEMODE_NONE:
hfutrell@2739
   519
    case SDL_TEXTURESCALEMODE_FAST:
hfutrell@2739
   520
    case SDL_TEXTURESCALEMODE_SLOW:
hfutrell@2739
   521
        return 0;
hfutrell@2739
   522
    case SDL_TEXTURESCALEMODE_BEST:
hfutrell@2739
   523
        SDL_Unsupported();
slouken@2753
   524
        texture->scaleMode = SDL_TEXTURESCALEMODE_SLOW;
hfutrell@2739
   525
        return -1;
hfutrell@2739
   526
    default:
hfutrell@2739
   527
        SDL_Unsupported();
hfutrell@2739
   528
        texture->scaleMode = SDL_TEXTURESCALEMODE_NONE;
hfutrell@2739
   529
        return -1;
hfutrell@2739
   530
    }
hfutrell@2739
   531
}
hfutrell@2739
   532
hfutrell@2739
   533
static int
hfutrell@2739
   534
GLES_UpdateTexture(SDL_Renderer * renderer, SDL_Texture * texture,
slouken@2753
   535
                   const SDL_Rect * rect, const void *pixels, int pitch)
hfutrell@2739
   536
{
hfutrell@2739
   537
    GLES_RenderData *renderdata = (GLES_RenderData *) renderer->driverdata;
hfutrell@2739
   538
    GLES_TextureData *data = (GLES_TextureData *) texture->driverdata;
hfutrell@2739
   539
    GLenum result;
hfutrell@2739
   540
hfutrell@2739
   541
    SetupTextureUpdate(renderdata, texture, pitch);
slouken@2753
   542
    renderdata->glGetError();
slouken@2753
   543
    renderdata->glTexSubImage2D(data->type, 0, rect->x, rect->y, rect->w,
hfutrell@2739
   544
                                rect->h, data->format, data->formattype,
hfutrell@2739
   545
                                pixels);
hfutrell@2739
   546
    result = renderdata->glGetError();
hfutrell@2739
   547
    if (result != GL_NO_ERROR) {
hfutrell@2739
   548
        GLES_SetError("glTexSubImage2D()", result);
hfutrell@2739
   549
        return -1;
hfutrell@2739
   550
    }
hfutrell@2739
   551
    return 0;
hfutrell@2739
   552
}
hfutrell@2739
   553
hfutrell@2739
   554
static int
hfutrell@2739
   555
GLES_LockTexture(SDL_Renderer * renderer, SDL_Texture * texture,
slouken@2753
   556
                 const SDL_Rect * rect, int markDirty, void **pixels,
slouken@2753
   557
                 int *pitch)
hfutrell@2739
   558
{
hfutrell@2739
   559
    GLES_TextureData *data = (GLES_TextureData *) texture->driverdata;
hfutrell@2739
   560
hfutrell@2739
   561
    if (markDirty) {
hfutrell@2739
   562
        SDL_AddDirtyRect(&data->dirty, rect);
hfutrell@2739
   563
    }
hfutrell@2739
   564
hfutrell@2739
   565
    *pixels =
hfutrell@2739
   566
        (void *) ((Uint8 *) data->pixels + rect->y * data->pitch +
hfutrell@2739
   567
                  rect->x * SDL_BYTESPERPIXEL(texture->format));
hfutrell@2739
   568
    *pitch = data->pitch;
hfutrell@2739
   569
    return 0;
hfutrell@2739
   570
}
hfutrell@2739
   571
hfutrell@2739
   572
static void
hfutrell@2739
   573
GLES_UnlockTexture(SDL_Renderer * renderer, SDL_Texture * texture)
hfutrell@2739
   574
{
hfutrell@2739
   575
}
hfutrell@2739
   576
hfutrell@2739
   577
static void
slouken@2753
   578
GLES_DirtyTexture(SDL_Renderer * renderer, SDL_Texture * texture,
slouken@2753
   579
                  int numrects, const SDL_Rect * rects)
hfutrell@2739
   580
{
hfutrell@2739
   581
    GLES_TextureData *data = (GLES_TextureData *) texture->driverdata;
hfutrell@2739
   582
    int i;
hfutrell@2739
   583
hfutrell@2739
   584
    for (i = 0; i < numrects; ++i) {
hfutrell@2739
   585
        SDL_AddDirtyRect(&data->dirty, &rects[i]);
hfutrell@2739
   586
    }
hfutrell@2739
   587
}
hfutrell@2739
   588
hfutrell@2739
   589
static int
hfutrell@2739
   590
GLES_RenderFill(SDL_Renderer * renderer, Uint8 r, Uint8 g, Uint8 b, Uint8 a,
slouken@2753
   591
                const SDL_Rect * rect)
hfutrell@2739
   592
{
slouken@2753
   593
slouken@2753
   594
    GLES_RenderData *data = (GLES_RenderData *) renderer->driverdata;
hfutrell@2739
   595
    SDL_Window *window = SDL_GetWindowFromID(renderer->window);
slouken@2753
   596
slouken@2753
   597
    /* set proper drawing color */
slouken@2753
   598
    GLfloat oldClearColor[4];
slouken@2753
   599
slouken@2753
   600
    data->glGetFloatv(GL_COLOR_CLEAR_VALUE, oldClearColor);
slouken@2753
   601
slouken@2753
   602
    data->glClearColor((GLclampf) r * inv255f, (GLclampf) g * inv255f,
slouken@2753
   603
                       (GLclampf) b * inv255f, (GLclampf) a * inv255f);
slouken@2753
   604
slouken@2753
   605
    data->glScissor(rect->x, window->h - rect->y - rect->h, rect->w, rect->h);
slouken@2753
   606
    data->glEnable(GL_SCISSOR_TEST);
slouken@2753
   607
    data->glClear(GL_COLOR_BUFFER_BIT);
slouken@2753
   608
    data->glDisable(GL_SCISSOR_TEST);
slouken@2753
   609
slouken@2753
   610
    /* reset clear color */
slouken@2753
   611
    data->glClearColor(oldClearColor[0], oldClearColor[1], oldClearColor[2],
slouken@2753
   612
                       oldClearColor[2]);
slouken@2753
   613
slouken@2753
   614
    return 0;
hfutrell@2739
   615
}
hfutrell@2739
   616
hfutrell@2739
   617
static int
hfutrell@2739
   618
GLES_RenderCopy(SDL_Renderer * renderer, SDL_Texture * texture,
slouken@2753
   619
                const SDL_Rect * srcrect, const SDL_Rect * dstrect)
hfutrell@2739
   620
{
slouken@2753
   621
hfutrell@2739
   622
    GLES_RenderData *data = (GLES_RenderData *) renderer->driverdata;
hfutrell@2739
   623
    GLES_TextureData *texturedata = (GLES_TextureData *) texture->driverdata;
hfutrell@2739
   624
    int minx, miny, maxx, maxy;
hfutrell@2739
   625
    GLfloat minu, maxu, minv, maxv;
slouken@2753
   626
    int i;
slouken@2753
   627
    void *temp_buffer;          /* used for reformatting dirty rect pixels */
slouken@2753
   628
    void *temp_ptr;
slouken@2753
   629
hfutrell@2739
   630
    if (texturedata->dirty.list) {
hfutrell@2739
   631
        SDL_DirtyRect *dirty;
hfutrell@2739
   632
        void *pixels;
hfutrell@2739
   633
        int bpp = SDL_BYTESPERPIXEL(texture->format);
hfutrell@2739
   634
        int pitch = texturedata->pitch;
hfutrell@2739
   635
hfutrell@2739
   636
        SetupTextureUpdate(data, texture, pitch);
slouken@2753
   637
hfutrell@2739
   638
        data->glBindTexture(texturedata->type, texturedata->texture);
hfutrell@2739
   639
        for (dirty = texturedata->dirty.list; dirty; dirty = dirty->next) {
hfutrell@2739
   640
            SDL_Rect *rect = &dirty->rect;
slouken@2753
   641
            pixels =
slouken@2753
   642
                (void *) ((Uint8 *) texturedata->pixels + rect->y * pitch +
slouken@2753
   643
                          rect->x * bpp);
slouken@2753
   644
            /*      There is no GL_UNPACK_ROW_LENGTH in OpenGLES 
slouken@2753
   645
               we must do this reformatting ourselves(!)
slouken@2753
   646
slouken@2753
   647
               maybe it'd be a good idea to keep a temp buffer around
slouken@2753
   648
               for this purpose rather than allocating it each time
slouken@2753
   649
             */
slouken@2753
   650
            temp_buffer = SDL_malloc(rect->w * rect->h * bpp);
slouken@2753
   651
            temp_ptr = temp_buffer;
slouken@2753
   652
            for (i = 0; i < rect->h; i++) {
slouken@2753
   653
                SDL_memcpy(temp_ptr, pixels, rect->w * bpp);
slouken@2753
   654
                temp_ptr += rect->w * bpp;
slouken@2753
   655
                pixels += pitch;
slouken@2753
   656
            }
slouken@2753
   657
hfutrell@2739
   658
            data->glTexSubImage2D(texturedata->type, 0, rect->x, rect->y,
hfutrell@2739
   659
                                  rect->w, rect->h, texturedata->format,
hfutrell@2739
   660
                                  texturedata->formattype, temp_buffer);
slouken@2753
   661
slouken@2753
   662
            SDL_free(temp_buffer);
slouken@2753
   663
hfutrell@2739
   664
        }
hfutrell@2739
   665
        SDL_ClearDirtyRects(&texturedata->dirty);
hfutrell@2739
   666
    }
slouken@2753
   667
hfutrell@2739
   668
    data->glBindTexture(texturedata->type, texturedata->texture);
slouken@2753
   669
    data->glEnable(GL_TEXTURE_2D);
slouken@2753
   670
hfutrell@2739
   671
    if (texture->modMode) {
hfutrell@2739
   672
        data->glColor4f((GLfloat) texture->r * inv255f,
hfutrell@2739
   673
                        (GLfloat) texture->g * inv255f,
hfutrell@2739
   674
                        (GLfloat) texture->b * inv255f,
hfutrell@2739
   675
                        (GLfloat) texture->a * inv255f);
hfutrell@2739
   676
    } else {
hfutrell@2739
   677
        data->glColor4f(1.0f, 1.0f, 1.0f, 1.0f);
hfutrell@2739
   678
    }
hfutrell@2739
   679
hfutrell@2739
   680
    if (texture->blendMode != data->blendMode) {
hfutrell@2739
   681
        switch (texture->blendMode) {
slouken@2884
   682
        case SDL_BLENDMODE_NONE:
hfutrell@2739
   683
            data->glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_DECAL);
hfutrell@2739
   684
            data->glDisable(GL_BLEND);
hfutrell@2739
   685
            break;
slouken@2884
   686
        case SDL_BLENDMODE_MASK:
slouken@2884
   687
        case SDL_BLENDMODE_BLEND:
hfutrell@2739
   688
            data->glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
hfutrell@2739
   689
            data->glEnable(GL_BLEND);
hfutrell@2739
   690
            data->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
hfutrell@2739
   691
            break;
slouken@2884
   692
        case SDL_BLENDMODE_ADD:
hfutrell@2739
   693
            data->glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
hfutrell@2739
   694
            data->glEnable(GL_BLEND);
hfutrell@2739
   695
            data->glBlendFunc(GL_SRC_ALPHA, GL_ONE);
hfutrell@2739
   696
            break;
slouken@2884
   697
        case SDL_BLENDMODE_MOD:
hfutrell@2739
   698
            data->glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
hfutrell@2739
   699
            data->glEnable(GL_BLEND);
hfutrell@2739
   700
            data->glBlendFunc(GL_ZERO, GL_SRC_COLOR);
hfutrell@2739
   701
            break;
hfutrell@2739
   702
        }
hfutrell@2739
   703
        data->blendMode = texture->blendMode;
hfutrell@2739
   704
    }
hfutrell@2739
   705
slouken@2753
   706
    switch (texture->scaleMode) {
slouken@2753
   707
    case SDL_TEXTURESCALEMODE_NONE:
slouken@2753
   708
    case SDL_TEXTURESCALEMODE_FAST:
slouken@2753
   709
        data->glTexParameteri(texturedata->type, GL_TEXTURE_MIN_FILTER,
slouken@2753
   710
                              GL_NEAREST);
slouken@2753
   711
        data->glTexParameteri(texturedata->type, GL_TEXTURE_MAG_FILTER,
slouken@2753
   712
                              GL_NEAREST);
slouken@2753
   713
        break;
slouken@2753
   714
    case SDL_TEXTURESCALEMODE_SLOW:
slouken@2753
   715
    case SDL_TEXTURESCALEMODE_BEST:
slouken@2753
   716
        data->glTexParameteri(texturedata->type, GL_TEXTURE_MIN_FILTER,
slouken@2753
   717
                              GL_LINEAR);
slouken@2753
   718
        data->glTexParameteri(texturedata->type, GL_TEXTURE_MAG_FILTER,
slouken@2753
   719
                              GL_LINEAR);
slouken@2753
   720
        break;
slouken@2753
   721
    }
hfutrell@2739
   722
slouken@2753
   723
    if (data->GL_OES_draw_texture_supported && data->useDrawTexture) {
slouken@2753
   724
        /* this code is a little funny because the viewport is upside down vs SDL's coordinate system */
slouken@2753
   725
        SDL_Window *window = SDL_GetWindowFromID(renderer->window);
slouken@2753
   726
        GLint cropRect[4];
slouken@2753
   727
        cropRect[0] = srcrect->x;
slouken@2753
   728
        cropRect[1] = srcrect->y + srcrect->h;
slouken@2753
   729
        cropRect[2] = srcrect->w;
slouken@2753
   730
        cropRect[3] = -srcrect->h;
slouken@2753
   731
        data->glTexParameteriv(GL_TEXTURE_2D, GL_TEXTURE_CROP_RECT_OES,
slouken@2753
   732
                               cropRect);
slouken@2753
   733
        data->glDrawTexiOES(dstrect->x, window->h - dstrect->y - dstrect->h,
slouken@2753
   734
                            0, dstrect->w, dstrect->h);
slouken@2753
   735
    } else {
slouken@2753
   736
slouken@2753
   737
        minx = dstrect->x;
slouken@2753
   738
        miny = dstrect->y;
slouken@2753
   739
        maxx = dstrect->x + dstrect->w;
slouken@2753
   740
        maxy = dstrect->y + dstrect->h;
slouken@2753
   741
slouken@2753
   742
        minu = (GLfloat) srcrect->x / texture->w;
slouken@2753
   743
        minu *= texturedata->texw;
slouken@2753
   744
        maxu = (GLfloat) (srcrect->x + srcrect->w) / texture->w;
slouken@2753
   745
        maxu *= texturedata->texw;
slouken@2753
   746
        minv = (GLfloat) srcrect->y / texture->h;
slouken@2753
   747
        minv *= texturedata->texh;
slouken@2753
   748
        maxv = (GLfloat) (srcrect->y + srcrect->h) / texture->h;
slouken@2753
   749
        maxv *= texturedata->texh;
slouken@2753
   750
slouken@2753
   751
        GLshort vertices[8];
slouken@2753
   752
        GLfloat texCoords[8];
slouken@2753
   753
slouken@2753
   754
        vertices[0] = minx;
slouken@2753
   755
        vertices[1] = miny;
slouken@2753
   756
        vertices[2] = maxx;
slouken@2753
   757
        vertices[3] = miny;
slouken@2753
   758
        vertices[4] = minx;
slouken@2753
   759
        vertices[5] = maxy;
slouken@2753
   760
        vertices[6] = maxx;
slouken@2753
   761
        vertices[7] = maxy;
slouken@2753
   762
slouken@2753
   763
        texCoords[0] = minu;
slouken@2753
   764
        texCoords[1] = minv;
slouken@2753
   765
        texCoords[2] = maxu;
slouken@2753
   766
        texCoords[3] = minv;
slouken@2753
   767
        texCoords[4] = minu;
slouken@2753
   768
        texCoords[5] = maxv;
slouken@2753
   769
        texCoords[6] = maxu;
slouken@2753
   770
        texCoords[7] = maxv;
slouken@2753
   771
slouken@2753
   772
        data->glVertexPointer(2, GL_SHORT, 0, vertices);
slouken@2753
   773
        data->glEnableClientState(GL_VERTEX_ARRAY);
slouken@2753
   774
        data->glTexCoordPointer(2, GL_FLOAT, 0, texCoords);
slouken@2753
   775
        data->glEnableClientState(GL_TEXTURE_COORD_ARRAY);
slouken@2753
   776
        data->glDrawArrays(GL_TRIANGLE_STRIP, 0, 4);
slouken@2753
   777
slouken@2753
   778
    }
slouken@2753
   779
hfutrell@2739
   780
    return 0;
hfutrell@2739
   781
}
hfutrell@2739
   782
hfutrell@2739
   783
static void
hfutrell@2739
   784
GLES_RenderPresent(SDL_Renderer * renderer)
hfutrell@2739
   785
{
hfutrell@2739
   786
    SDL_GL_SwapWindow(renderer->window);
hfutrell@2739
   787
}
hfutrell@2739
   788
hfutrell@2739
   789
static void
hfutrell@2739
   790
GLES_DestroyTexture(SDL_Renderer * renderer, SDL_Texture * texture)
hfutrell@2739
   791
{
hfutrell@2739
   792
    GLES_RenderData *renderdata = (GLES_RenderData *) renderer->driverdata;
hfutrell@2739
   793
    GLES_TextureData *data = (GLES_TextureData *) texture->driverdata;
hfutrell@2739
   794
hfutrell@2739
   795
    if (!data) {
hfutrell@2739
   796
        return;
hfutrell@2739
   797
    }
hfutrell@2739
   798
    if (data->texture) {
slouken@2753
   799
        glDeleteTextures(1, &data->texture);
hfutrell@2739
   800
    }
hfutrell@2739
   801
    if (data->pixels) {
hfutrell@2739
   802
        SDL_free(data->pixels);
hfutrell@2739
   803
    }
hfutrell@2739
   804
    SDL_FreeDirtyRects(&data->dirty);
hfutrell@2739
   805
    SDL_free(data);
hfutrell@2739
   806
    texture->driverdata = NULL;
hfutrell@2739
   807
}
hfutrell@2739
   808
hfutrell@2739
   809
static void
hfutrell@2739
   810
GLES_DestroyRenderer(SDL_Renderer * renderer)
hfutrell@2739
   811
{
hfutrell@2739
   812
    GLES_RenderData *data = (GLES_RenderData *) renderer->driverdata;
hfutrell@2739
   813
hfutrell@2739
   814
    if (data) {
hfutrell@2739
   815
        if (data->context) {
hfutrell@2739
   816
            /* SDL_GL_MakeCurrent(0, NULL); *//* doesn't do anything */
hfutrell@2739
   817
            SDL_GL_DeleteContext(data->context);
hfutrell@2739
   818
        }
hfutrell@2739
   819
        SDL_free(data);
hfutrell@2739
   820
    }
hfutrell@2739
   821
    SDL_free(renderer);
hfutrell@2739
   822
}
hfutrell@2739
   823
hfutrell@2739
   824
#endif /* SDL_VIDEO_RENDER_OGL */
hfutrell@2739
   825
hfutrell@2739
   826
/* vi: set ts=4 sw=4 expandtab: */