mirror of
https://github.com/TorqueGameEngines/Torque3D.git
synced 2026-07-11 22:54:34 +00:00
Updates SDL to version 2.0.4, which makes it compatible with VS2015.
This commit is contained in:
parent
7b52fed504
commit
b63ef177f4
924 changed files with 79241 additions and 39934 deletions
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
@ -19,6 +19,8 @@
|
|||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
#include "../SDL_internal.h"
|
||||
|
||||
#if (SDL_VIDEO_RENDER_D3D || SDL_VIDEO_RENDER_D3D11) && !SDL_RENDER_DISABLED
|
||||
#include "SDL_stdinc.h"
|
||||
|
||||
#include "SDL_d3dmath.h"
|
||||
|
|
@ -126,6 +128,9 @@ Float4X4 MatrixRotationZ(float r)
|
|||
m._33 = 1.0f;
|
||||
m._44 = 1.0f;
|
||||
return m;
|
||||
|
||||
}
|
||||
|
||||
#endif /* (SDL_VIDEO_RENDER_D3D || SDL_VIDEO_RENDER_D3D11) && !SDL_RENDER_DISABLED */
|
||||
|
||||
/* vi: set ts=4 sw=4 expandtab: */
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
@ -20,6 +20,7 @@
|
|||
*/
|
||||
#include "../SDL_internal.h"
|
||||
|
||||
#if (SDL_VIDEO_RENDER_D3D || SDL_VIDEO_RENDER_D3D11) && !SDL_RENDER_DISABLED
|
||||
|
||||
/* Direct3D matrix math functions */
|
||||
|
||||
|
|
@ -66,4 +67,6 @@ Float4X4 MatrixRotationX(float r);
|
|||
Float4X4 MatrixRotationY(float r);
|
||||
Float4X4 MatrixRotationZ(float r);
|
||||
|
||||
#endif /* (SDL_VIDEO_RENDER_D3D || SDL_VIDEO_RENDER_D3D11) && !SDL_RENDER_DISABLED */
|
||||
|
||||
/* vi: set ts=4 sw=4 expandtab: */
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
@ -115,6 +115,12 @@ SDL_RendererEventWatch(void *userdata, SDL_Event *event)
|
|||
}
|
||||
|
||||
if (event->window.event == SDL_WINDOWEVENT_SIZE_CHANGED) {
|
||||
/* Make sure we're operating on the default render target */
|
||||
SDL_Texture *saved_target = SDL_GetRenderTarget(renderer);
|
||||
if (saved_target) {
|
||||
SDL_SetRenderTarget(renderer, NULL);
|
||||
}
|
||||
|
||||
if (renderer->logical_w) {
|
||||
UpdateLogicalSize(renderer);
|
||||
} else {
|
||||
|
|
@ -140,6 +146,10 @@ SDL_RendererEventWatch(void *userdata, SDL_Event *event)
|
|||
renderer->UpdateViewport(renderer);
|
||||
}
|
||||
}
|
||||
|
||||
if (saved_target) {
|
||||
SDL_SetRenderTarget(renderer, saved_target);
|
||||
}
|
||||
} else if (event->window.event == SDL_WINDOWEVENT_HIDDEN) {
|
||||
renderer->hidden = SDL_TRUE;
|
||||
} else if (event->window.event == SDL_WINDOWEVENT_SHOWN) {
|
||||
|
|
@ -148,14 +158,16 @@ SDL_RendererEventWatch(void *userdata, SDL_Event *event)
|
|||
}
|
||||
} else if (event->window.event == SDL_WINDOWEVENT_MINIMIZED) {
|
||||
renderer->hidden = SDL_TRUE;
|
||||
} else if (event->window.event == SDL_WINDOWEVENT_RESTORED) {
|
||||
} else if (event->window.event == SDL_WINDOWEVENT_RESTORED ||
|
||||
event->window.event == SDL_WINDOWEVENT_MAXIMIZED) {
|
||||
if (!(SDL_GetWindowFlags(window) & SDL_WINDOW_HIDDEN)) {
|
||||
renderer->hidden = SDL_FALSE;
|
||||
}
|
||||
}
|
||||
}
|
||||
} else if (event->type == SDL_MOUSEMOTION) {
|
||||
if (renderer->logical_w) {
|
||||
SDL_Window *window = SDL_GetWindowFromID(event->motion.windowID);
|
||||
if (renderer->logical_w && window == renderer->window) {
|
||||
event->motion.x -= renderer->viewport.x;
|
||||
event->motion.y -= renderer->viewport.y;
|
||||
event->motion.x = (int)(event->motion.x / renderer->scale.x);
|
||||
|
|
@ -173,7 +185,8 @@ SDL_RendererEventWatch(void *userdata, SDL_Event *event)
|
|||
}
|
||||
} else if (event->type == SDL_MOUSEBUTTONDOWN ||
|
||||
event->type == SDL_MOUSEBUTTONUP) {
|
||||
if (renderer->logical_w) {
|
||||
SDL_Window *window = SDL_GetWindowFromID(event->button.windowID);
|
||||
if (renderer->logical_w && window == renderer->window) {
|
||||
event->button.x -= renderer->viewport.x;
|
||||
event->button.y -= renderer->viewport.y;
|
||||
event->button.x = (int)(event->button.x / renderer->scale.x);
|
||||
|
|
@ -350,7 +363,7 @@ SDL_GetRendererOutputSize(SDL_Renderer * renderer, int *w, int *h)
|
|||
SDL_GetWindowSize(renderer->window, w, h);
|
||||
return 0;
|
||||
} else {
|
||||
/* This should never happen */
|
||||
SDL_assert(0 && "This should never happen");
|
||||
return SDL_SetError("Renderer doesn't support querying output size");
|
||||
}
|
||||
}
|
||||
|
|
@ -404,6 +417,10 @@ SDL_CreateTexture(SDL_Renderer * renderer, Uint32 format, int access, int w, int
|
|||
if (!format) {
|
||||
format = renderer->info.texture_formats[0];
|
||||
}
|
||||
if (SDL_BYTESPERPIXEL(format) == 0) {
|
||||
SDL_SetError("Invalid texture format");
|
||||
return NULL;
|
||||
}
|
||||
if (SDL_ISPIXELFORMAT_INDEXED(format)) {
|
||||
SDL_SetError("Palettized textures are not supported");
|
||||
return NULL;
|
||||
|
|
@ -441,7 +458,7 @@ SDL_CreateTexture(SDL_Renderer * renderer, Uint32 format, int access, int w, int
|
|||
if (IsSupportedFormat(renderer, format)) {
|
||||
if (renderer->CreateTexture(renderer, texture) < 0) {
|
||||
SDL_DestroyTexture(texture);
|
||||
return 0;
|
||||
return NULL;
|
||||
}
|
||||
} else {
|
||||
texture->native = SDL_CreateTexture(renderer,
|
||||
|
|
@ -536,6 +553,10 @@ SDL_CreateTextureFromSurface(SDL_Renderer * renderer, SDL_Surface * surface)
|
|||
|
||||
/* Set up a destination surface for the texture update */
|
||||
dst_fmt = SDL_AllocFormat(format);
|
||||
if (!dst_fmt) {
|
||||
SDL_DestroyTexture(texture);
|
||||
return NULL;
|
||||
}
|
||||
temp = SDL_ConvertSurface(surface, dst_fmt, 0);
|
||||
SDL_FreeFormat(dst_fmt);
|
||||
if (temp) {
|
||||
|
|
@ -802,7 +823,9 @@ SDL_UpdateTexture(SDL_Texture * texture, const SDL_Rect * rect,
|
|||
rect = &full_rect;
|
||||
}
|
||||
|
||||
if (texture->yuv) {
|
||||
if ((rect->w == 0) || (rect->h == 0)) {
|
||||
return 0; /* nothing to do. */
|
||||
} else if (texture->yuv) {
|
||||
return SDL_UpdateTextureYUV(texture, rect, pixels, pitch);
|
||||
} else if (texture->native) {
|
||||
return SDL_UpdateTextureNative(texture, rect, pixels, pitch);
|
||||
|
|
@ -908,12 +931,12 @@ int SDL_UpdateYUVTexture(SDL_Texture * texture, const SDL_Rect * rect,
|
|||
SDL_assert(!texture->native);
|
||||
renderer = texture->renderer;
|
||||
SDL_assert(renderer->UpdateTextureYUV);
|
||||
if (renderer->UpdateTextureYUV) {
|
||||
return renderer->UpdateTextureYUV(renderer, texture, rect, Yplane, Ypitch, Uplane, Upitch, Vplane, Vpitch);
|
||||
} else {
|
||||
return SDL_Unsupported();
|
||||
}
|
||||
}
|
||||
if (renderer->UpdateTextureYUV) {
|
||||
return renderer->UpdateTextureYUV(renderer, texture, rect, Yplane, Ypitch, Uplane, Upitch, Vplane, Vpitch);
|
||||
} else {
|
||||
return SDL_Unsupported();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static int
|
||||
|
|
@ -970,8 +993,8 @@ static void
|
|||
SDL_UnlockTextureYUV(SDL_Texture * texture)
|
||||
{
|
||||
SDL_Texture *native = texture->native;
|
||||
void *native_pixels;
|
||||
int native_pitch;
|
||||
void *native_pixels = NULL;
|
||||
int native_pitch = 0;
|
||||
SDL_Rect rect;
|
||||
|
||||
rect.x = 0;
|
||||
|
|
@ -991,8 +1014,8 @@ static void
|
|||
SDL_UnlockTextureNative(SDL_Texture * texture)
|
||||
{
|
||||
SDL_Texture *native = texture->native;
|
||||
void *native_pixels;
|
||||
int native_pitch;
|
||||
void *native_pixels = NULL;
|
||||
int native_pitch = 0;
|
||||
const SDL_Rect *rect = &texture->locked_rect;
|
||||
const void* pixels = (void *) ((Uint8 *) texture->pixels +
|
||||
rect->y * texture->pitch +
|
||||
|
|
@ -1067,6 +1090,7 @@ SDL_SetRenderTarget(SDL_Renderer *renderer, SDL_Texture *texture)
|
|||
/* Make a backup of the viewport */
|
||||
renderer->viewport_backup = renderer->viewport;
|
||||
renderer->clip_rect_backup = renderer->clip_rect;
|
||||
renderer->clipping_enabled_backup = renderer->clipping_enabled;
|
||||
renderer->scale_backup = renderer->scale;
|
||||
renderer->logical_w_backup = renderer->logical_w;
|
||||
renderer->logical_h_backup = renderer->logical_h;
|
||||
|
|
@ -1089,6 +1113,7 @@ SDL_SetRenderTarget(SDL_Renderer *renderer, SDL_Texture *texture)
|
|||
} else {
|
||||
renderer->viewport = renderer->viewport_backup;
|
||||
renderer->clip_rect = renderer->clip_rect_backup;
|
||||
renderer->clipping_enabled = renderer->clipping_enabled_backup;
|
||||
renderer->scale = renderer->scale_backup;
|
||||
renderer->logical_w = renderer->logical_w_backup;
|
||||
renderer->logical_h = renderer->logical_h_backup;
|
||||
|
|
@ -1113,7 +1138,7 @@ SDL_GetRenderTarget(SDL_Renderer *renderer)
|
|||
static int
|
||||
UpdateLogicalSize(SDL_Renderer *renderer)
|
||||
{
|
||||
int w, h;
|
||||
int w = 1, h = 1;
|
||||
float want_aspect;
|
||||
float real_aspect;
|
||||
float scale;
|
||||
|
|
@ -1229,11 +1254,13 @@ SDL_RenderSetClipRect(SDL_Renderer * renderer, const SDL_Rect * rect)
|
|||
CHECK_RENDERER_MAGIC(renderer, -1)
|
||||
|
||||
if (rect) {
|
||||
renderer->clipping_enabled = SDL_TRUE;
|
||||
renderer->clip_rect.x = (int)SDL_floor(rect->x * renderer->scale.x);
|
||||
renderer->clip_rect.y = (int)SDL_floor(rect->y * renderer->scale.y);
|
||||
renderer->clip_rect.w = (int)SDL_ceil(rect->w * renderer->scale.x);
|
||||
renderer->clip_rect.h = (int)SDL_ceil(rect->h * renderer->scale.y);
|
||||
} else {
|
||||
renderer->clipping_enabled = SDL_FALSE;
|
||||
SDL_zero(renderer->clip_rect);
|
||||
}
|
||||
return renderer->UpdateClipRect(renderer);
|
||||
|
|
@ -1252,6 +1279,13 @@ SDL_RenderGetClipRect(SDL_Renderer * renderer, SDL_Rect * rect)
|
|||
}
|
||||
}
|
||||
|
||||
SDL_bool
|
||||
SDL_RenderIsClipEnabled(SDL_Renderer * renderer)
|
||||
{
|
||||
CHECK_RENDERER_MAGIC(renderer, SDL_FALSE)
|
||||
return renderer->clipping_enabled;
|
||||
}
|
||||
|
||||
int
|
||||
SDL_RenderSetScale(SDL_Renderer * renderer, float scaleX, float scaleY)
|
||||
{
|
||||
|
|
@ -1701,6 +1735,10 @@ SDL_RenderCopyEx(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
SDL_FRect frect;
|
||||
SDL_FPoint fcenter;
|
||||
|
||||
if (flip == SDL_FLIP_NONE && angle == 0) { /* fast path when we don't need rotation or flipping */
|
||||
return SDL_RenderCopy(renderer, texture, srcrect, dstrect);
|
||||
}
|
||||
|
||||
CHECK_RENDERER_MAGIC(renderer, -1);
|
||||
CHECK_TEXTURE_MAGIC(texture, -1);
|
||||
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
@ -143,6 +143,10 @@ struct SDL_Renderer
|
|||
SDL_Rect clip_rect;
|
||||
SDL_Rect clip_rect_backup;
|
||||
|
||||
/* Wether or not the clipping rectangle is used. */
|
||||
SDL_bool clipping_enabled;
|
||||
SDL_bool clipping_enabled_backup;
|
||||
|
||||
/* The render output coordinate scale */
|
||||
SDL_FPoint scale;
|
||||
SDL_FPoint scale_backup;
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
@ -1274,11 +1274,16 @@ SDL_SW_CopyYUVToRGB(SDL_SW_YUVTexture * swdata, const SDL_Rect * srcrect,
|
|||
Uint32 target_format, int w, int h, void *pixels,
|
||||
int pitch)
|
||||
{
|
||||
const int targetbpp = SDL_BYTESPERPIXEL(target_format);
|
||||
int stretch;
|
||||
int scale_2x;
|
||||
Uint8 *lum, *Cr, *Cb;
|
||||
int mod;
|
||||
|
||||
if (targetbpp == 0) {
|
||||
return SDL_SetError("Invalid target pixel format");
|
||||
}
|
||||
|
||||
/* Make sure we're set up to display in the desired format */
|
||||
if (target_format != swdata->target_format) {
|
||||
if (SDL_SW_SetupYUVDisplay(swdata, target_format) < 0) {
|
||||
|
|
@ -1366,7 +1371,7 @@ SDL_SW_CopyYUVToRGB(SDL_SW_YUVTexture * swdata, const SDL_Rect * srcrect,
|
|||
default:
|
||||
return SDL_SetError("Unsupported YUV format in copy");
|
||||
}
|
||||
mod = (pitch / SDL_BYTESPERPIXEL(target_format));
|
||||
mod = (pitch / targetbpp);
|
||||
|
||||
if (scale_2x) {
|
||||
mod -= (swdata->w * 2);
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
@ -41,6 +41,8 @@
|
|||
|
||||
|
||||
#ifdef ASSEMBLE_SHADER
|
||||
#pragma comment(lib, "d3dx9.lib")
|
||||
|
||||
/**************************************************************************
|
||||
* ID3DXBuffer:
|
||||
* ------------
|
||||
|
|
@ -124,6 +126,7 @@ static SDL_Renderer *D3D_CreateRenderer(SDL_Window * window, Uint32 flags);
|
|||
static void D3D_WindowEvent(SDL_Renderer * renderer,
|
||||
const SDL_WindowEvent *event);
|
||||
static int D3D_CreateTexture(SDL_Renderer * renderer, SDL_Texture * texture);
|
||||
static int D3D_RecreateTexture(SDL_Renderer * renderer, SDL_Texture * texture);
|
||||
static int D3D_UpdateTexture(SDL_Renderer * renderer, SDL_Texture * texture,
|
||||
const SDL_Rect * rect, const void *pixels,
|
||||
int pitch);
|
||||
|
|
@ -189,13 +192,23 @@ typedef struct
|
|||
|
||||
typedef struct
|
||||
{
|
||||
SDL_bool dirty;
|
||||
int w, h;
|
||||
DWORD usage;
|
||||
Uint32 format;
|
||||
IDirect3DTexture9 *texture;
|
||||
IDirect3DTexture9 *staging;
|
||||
} D3D_TextureRep;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
D3D_TextureRep texture;
|
||||
D3DTEXTUREFILTERTYPE scaleMode;
|
||||
|
||||
/* YV12 texture support */
|
||||
SDL_bool yuv;
|
||||
IDirect3DTexture9 *utexture;
|
||||
IDirect3DTexture9 *vtexture;
|
||||
D3D_TextureRep utexture;
|
||||
D3D_TextureRep vtexture;
|
||||
Uint8 *pixels;
|
||||
int pitch;
|
||||
SDL_Rect locked_rect;
|
||||
|
|
@ -408,6 +421,8 @@ D3D_Reset(SDL_Renderer * renderer)
|
|||
for (texture = renderer->textures; texture; texture = texture->next) {
|
||||
if (texture->access == SDL_TEXTUREACCESS_TARGET) {
|
||||
D3D_DestroyTexture(renderer, texture);
|
||||
} else {
|
||||
D3D_RecreateTexture(renderer, texture);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -452,15 +467,21 @@ D3D_ActivateRenderer(SDL_Renderer * renderer)
|
|||
if (data->updateSize) {
|
||||
SDL_Window *window = renderer->window;
|
||||
int w, h;
|
||||
Uint32 window_flags = SDL_GetWindowFlags(window);
|
||||
|
||||
SDL_GetWindowSize(window, &w, &h);
|
||||
data->pparams.BackBufferWidth = w;
|
||||
data->pparams.BackBufferHeight = h;
|
||||
if (SDL_GetWindowFlags(window) & SDL_WINDOW_FULLSCREEN) {
|
||||
data->pparams.BackBufferFormat =
|
||||
PixelFormatToD3DFMT(SDL_GetWindowPixelFormat(window));
|
||||
if (window_flags & SDL_WINDOW_FULLSCREEN && (window_flags & SDL_WINDOW_FULLSCREEN_DESKTOP) != SDL_WINDOW_FULLSCREEN_DESKTOP) {
|
||||
SDL_DisplayMode fullscreen_mode;
|
||||
SDL_GetWindowDisplayMode(window, &fullscreen_mode);
|
||||
data->pparams.Windowed = FALSE;
|
||||
data->pparams.BackBufferFormat = PixelFormatToD3DFMT(fullscreen_mode.format);
|
||||
data->pparams.FullScreen_RefreshRateInHz = fullscreen_mode.refresh_rate;
|
||||
} else {
|
||||
data->pparams.Windowed = TRUE;
|
||||
data->pparams.BackBufferFormat = D3DFMT_UNKNOWN;
|
||||
data->pparams.FullScreen_RefreshRateInHz = 0;
|
||||
}
|
||||
if (D3D_Reset(renderer) < 0) {
|
||||
return -1;
|
||||
|
|
@ -555,25 +576,16 @@ D3D_CreateRenderer(SDL_Window * window, Uint32 flags)
|
|||
pparams.hDeviceWindow = windowinfo.info.win.window;
|
||||
pparams.BackBufferWidth = w;
|
||||
pparams.BackBufferHeight = h;
|
||||
if (window_flags & SDL_WINDOW_FULLSCREEN) {
|
||||
pparams.BackBufferFormat =
|
||||
PixelFormatToD3DFMT(fullscreen_mode.format);
|
||||
} else {
|
||||
pparams.BackBufferFormat = D3DFMT_UNKNOWN;
|
||||
}
|
||||
pparams.BackBufferCount = 1;
|
||||
pparams.SwapEffect = D3DSWAPEFFECT_DISCARD;
|
||||
|
||||
if (window_flags & SDL_WINDOW_FULLSCREEN) {
|
||||
if ((window_flags & SDL_WINDOW_FULLSCREEN_DESKTOP) == SDL_WINDOW_FULLSCREEN_DESKTOP) {
|
||||
pparams.Windowed = TRUE;
|
||||
pparams.FullScreen_RefreshRateInHz = 0;
|
||||
} else {
|
||||
pparams.Windowed = FALSE;
|
||||
pparams.FullScreen_RefreshRateInHz = fullscreen_mode.refresh_rate;
|
||||
}
|
||||
if (window_flags & SDL_WINDOW_FULLSCREEN && (window_flags & SDL_WINDOW_FULLSCREEN_DESKTOP) != SDL_WINDOW_FULLSCREEN_DESKTOP) {
|
||||
pparams.Windowed = FALSE;
|
||||
pparams.BackBufferFormat = PixelFormatToD3DFMT(fullscreen_mode.format);
|
||||
pparams.FullScreen_RefreshRateInHz = fullscreen_mode.refresh_rate;
|
||||
} else {
|
||||
pparams.Windowed = TRUE;
|
||||
pparams.BackBufferFormat = D3DFMT_UNKNOWN;
|
||||
pparams.FullScreen_RefreshRateInHz = 0;
|
||||
}
|
||||
if (flags & SDL_RENDERER_PRESENTVSYNC) {
|
||||
|
|
@ -643,7 +655,7 @@ D3D_CreateRenderer(SDL_Window * window, Uint32 flags)
|
|||
}
|
||||
|
||||
/* Store the default render target */
|
||||
IDirect3DDevice9_GetRenderTarget(data->device, 0, &data->defaultRenderTarget );
|
||||
IDirect3DDevice9_GetRenderTarget(data->device, 0, &data->defaultRenderTarget);
|
||||
data->currentRenderTarget = NULL;
|
||||
|
||||
/* Set up parameters for rendering */
|
||||
|
|
@ -682,7 +694,7 @@ D3D_CreateRenderer(SDL_Window * window, Uint32 flags)
|
|||
|
||||
PS_OUTPUT YUV420( VS_OUTPUT In )
|
||||
{
|
||||
const float3 offset = {-0.0625, -0.5, -0.5};
|
||||
const float3 offset = {-0.0627451017, -0.501960814, -0.501960814};
|
||||
const float3 Rcoeff = {1.164, 0.000, 1.596};
|
||||
const float3 Gcoeff = {1.164, -0.391, -0.813};
|
||||
const float3 Bcoeff = {1.164, 2.018, 0.000};
|
||||
|
|
@ -714,7 +726,7 @@ D3D_CreateRenderer(SDL_Window * window, Uint32 flags)
|
|||
*/
|
||||
const char *shader_text =
|
||||
"ps_2_0\n"
|
||||
"def c0, -0.0625, -0.5, -0.5, 1\n"
|
||||
"def c0, -0.0627451017, -0.501960814, -0.501960814, 1\n"
|
||||
"def c1, 1.16400003, 0, 1.59599996, 0\n"
|
||||
"def c2, 1.16400003, -0.391000003, -0.813000023, 0\n"
|
||||
"def c3, 1.16400003, 2.01799989, 0, 0\n"
|
||||
|
|
@ -751,7 +763,7 @@ D3D_CreateRenderer(SDL_Window * window, Uint32 flags)
|
|||
}
|
||||
#else
|
||||
const DWORD shader_data[] = {
|
||||
0xffff0200, 0x05000051, 0xa00f0000, 0xbd800000, 0xbf000000, 0xbf000000,
|
||||
0xffff0200, 0x05000051, 0xa00f0000, 0xbd808081, 0xbf008081, 0xbf008081,
|
||||
0x3f800000, 0x05000051, 0xa00f0001, 0x3f94fdf4, 0x00000000, 0x3fcc49ba,
|
||||
0x00000000, 0x05000051, 0xa00f0002, 0x3f94fdf4, 0xbec83127, 0xbf5020c5,
|
||||
0x00000000, 0x05000051, 0xa00f0003, 0x3f94fdf4, 0x400126e9, 0x00000000,
|
||||
|
|
@ -805,74 +817,85 @@ GetScaleQuality(void)
|
|||
}
|
||||
|
||||
static int
|
||||
D3D_CreateTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
||||
D3D_CreateTextureRep(IDirect3DDevice9 *device, D3D_TextureRep *texture, DWORD usage, Uint32 format, int w, int h)
|
||||
{
|
||||
D3D_RenderData *renderdata = (D3D_RenderData *) renderer->driverdata;
|
||||
D3D_TextureData *data;
|
||||
D3DPOOL pool;
|
||||
DWORD usage;
|
||||
HRESULT result;
|
||||
|
||||
data = (D3D_TextureData *) SDL_calloc(1, sizeof(*data));
|
||||
if (!data) {
|
||||
return SDL_OutOfMemory();
|
||||
}
|
||||
data->scaleMode = GetScaleQuality();
|
||||
texture->dirty = SDL_FALSE;
|
||||
texture->w = w;
|
||||
texture->h = h;
|
||||
texture->usage = usage;
|
||||
texture->format = format;
|
||||
|
||||
texture->driverdata = data;
|
||||
|
||||
#ifdef USE_DYNAMIC_TEXTURE
|
||||
if (texture->access == SDL_TEXTUREACCESS_STREAMING) {
|
||||
pool = D3DPOOL_DEFAULT;
|
||||
usage = D3DUSAGE_DYNAMIC;
|
||||
} else
|
||||
#endif
|
||||
if (texture->access == SDL_TEXTUREACCESS_TARGET) {
|
||||
/* D3DPOOL_MANAGED does not work with D3DUSAGE_RENDERTARGET */
|
||||
pool = D3DPOOL_DEFAULT;
|
||||
usage = D3DUSAGE_RENDERTARGET;
|
||||
} else {
|
||||
pool = D3DPOOL_MANAGED;
|
||||
usage = 0;
|
||||
}
|
||||
|
||||
result =
|
||||
IDirect3DDevice9_CreateTexture(renderdata->device, texture->w,
|
||||
texture->h, 1, usage,
|
||||
PixelFormatToD3DFMT(texture->format),
|
||||
pool, &data->texture, NULL);
|
||||
result = IDirect3DDevice9_CreateTexture(device, w, h, 1, usage,
|
||||
PixelFormatToD3DFMT(format),
|
||||
D3DPOOL_DEFAULT, &texture->texture, NULL);
|
||||
if (FAILED(result)) {
|
||||
return D3D_SetError("CreateTexture()", result);
|
||||
return D3D_SetError("CreateTexture(D3DPOOL_DEFAULT)", result);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (texture->format == SDL_PIXELFORMAT_YV12 ||
|
||||
texture->format == SDL_PIXELFORMAT_IYUV) {
|
||||
data->yuv = SDL_TRUE;
|
||||
|
||||
result =
|
||||
IDirect3DDevice9_CreateTexture(renderdata->device, texture->w / 2,
|
||||
texture->h / 2, 1, usage,
|
||||
PixelFormatToD3DFMT(texture->format),
|
||||
pool, &data->utexture, NULL);
|
||||
static int
|
||||
D3D_CreateStagingTexture(IDirect3DDevice9 *device, D3D_TextureRep *texture)
|
||||
{
|
||||
HRESULT result;
|
||||
|
||||
if (texture->staging == NULL) {
|
||||
result = IDirect3DDevice9_CreateTexture(device, texture->w, texture->h, 1, 0,
|
||||
PixelFormatToD3DFMT(texture->format),
|
||||
D3DPOOL_SYSTEMMEM, &texture->staging, NULL);
|
||||
if (FAILED(result)) {
|
||||
return D3D_SetError("CreateTexture()", result);
|
||||
}
|
||||
|
||||
result =
|
||||
IDirect3DDevice9_CreateTexture(renderdata->device, texture->w / 2,
|
||||
texture->h / 2, 1, usage,
|
||||
PixelFormatToD3DFMT(texture->format),
|
||||
pool, &data->vtexture, NULL);
|
||||
if (FAILED(result)) {
|
||||
return D3D_SetError("CreateTexture()", result);
|
||||
return D3D_SetError("CreateTexture(D3DPOOL_SYSTEMMEM)", result);
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int
|
||||
D3D_UpdateTextureInternal(IDirect3DTexture9 *texture, Uint32 format, SDL_bool full_texture, int x, int y, int w, int h, const void *pixels, int pitch)
|
||||
D3D_BindTextureRep(IDirect3DDevice9 *device, D3D_TextureRep *texture, DWORD sampler)
|
||||
{
|
||||
HRESULT result;
|
||||
|
||||
if (texture->dirty && texture->staging) {
|
||||
if (!texture->texture) {
|
||||
result = IDirect3DDevice9_CreateTexture(device, texture->w, texture->h, 1, texture->usage,
|
||||
PixelFormatToD3DFMT(texture->format), D3DPOOL_DEFAULT, &texture->texture, NULL);
|
||||
if (FAILED(result)) {
|
||||
return D3D_SetError("CreateTexture(D3DPOOL_DEFAULT)", result);
|
||||
}
|
||||
}
|
||||
|
||||
result = IDirect3DDevice9_UpdateTexture(device, (IDirect3DBaseTexture9 *)texture->staging, (IDirect3DBaseTexture9 *)texture->texture);
|
||||
if (FAILED(result)) {
|
||||
return D3D_SetError("UpdateTexture()", result);
|
||||
}
|
||||
texture->dirty = SDL_FALSE;
|
||||
}
|
||||
result = IDirect3DDevice9_SetTexture(device, sampler, (IDirect3DBaseTexture9 *)texture->texture);
|
||||
if (FAILED(result)) {
|
||||
return D3D_SetError("SetTexture()", result);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int
|
||||
D3D_RecreateTextureRep(IDirect3DDevice9 *device, D3D_TextureRep *texture, Uint32 format, int w, int h)
|
||||
{
|
||||
if (texture->texture) {
|
||||
IDirect3DTexture9_Release(texture->texture);
|
||||
texture->texture = NULL;
|
||||
}
|
||||
if (texture->staging) {
|
||||
IDirect3DTexture9_AddDirtyRect(texture->staging, NULL);
|
||||
texture->dirty = SDL_TRUE;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int
|
||||
D3D_UpdateTextureRep(IDirect3DDevice9 *device, D3D_TextureRep *texture, Uint32 format, int x, int y, int w, int h, const void *pixels, int pitch)
|
||||
{
|
||||
RECT d3drect;
|
||||
D3DLOCKED_RECT locked;
|
||||
|
|
@ -881,16 +904,16 @@ D3D_UpdateTextureInternal(IDirect3DTexture9 *texture, Uint32 format, SDL_bool fu
|
|||
int row, length;
|
||||
HRESULT result;
|
||||
|
||||
if (full_texture) {
|
||||
result = IDirect3DTexture9_LockRect(texture, 0, &locked, NULL, D3DLOCK_DISCARD);
|
||||
} else {
|
||||
d3drect.left = x;
|
||||
d3drect.right = x + w;
|
||||
d3drect.top = y;
|
||||
d3drect.bottom = y + h;
|
||||
result = IDirect3DTexture9_LockRect(texture, 0, &locked, &d3drect, 0);
|
||||
if (D3D_CreateStagingTexture(device, texture) < 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
d3drect.left = x;
|
||||
d3drect.right = x + w;
|
||||
d3drect.top = y;
|
||||
d3drect.bottom = y + h;
|
||||
|
||||
result = IDirect3DTexture9_LockRect(texture->staging, 0, &locked, &d3drect, 0);
|
||||
if (FAILED(result)) {
|
||||
return D3D_SetError("LockRect()", result);
|
||||
}
|
||||
|
|
@ -913,46 +936,117 @@ D3D_UpdateTextureInternal(IDirect3DTexture9 *texture, Uint32 format, SDL_bool fu
|
|||
dst += locked.Pitch;
|
||||
}
|
||||
}
|
||||
IDirect3DTexture9_UnlockRect(texture, 0);
|
||||
result = IDirect3DTexture9_UnlockRect(texture->staging, 0);
|
||||
if (FAILED(result)) {
|
||||
return D3D_SetError("UnlockRect()", result);
|
||||
}
|
||||
texture->dirty = SDL_TRUE;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void
|
||||
D3D_DestroyTextureRep(D3D_TextureRep *texture)
|
||||
{
|
||||
if (texture->texture) {
|
||||
IDirect3DTexture9_Release(texture->texture);
|
||||
texture->texture = NULL;
|
||||
}
|
||||
if (texture->staging) {
|
||||
IDirect3DTexture9_Release(texture->staging);
|
||||
texture->staging = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
static int
|
||||
D3D_CreateTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
||||
{
|
||||
D3D_RenderData *data = (D3D_RenderData *) renderer->driverdata;
|
||||
D3D_TextureData *texturedata;
|
||||
DWORD usage;
|
||||
|
||||
texturedata = (D3D_TextureData *) SDL_calloc(1, sizeof(*texturedata));
|
||||
if (!texturedata) {
|
||||
return SDL_OutOfMemory();
|
||||
}
|
||||
texturedata->scaleMode = GetScaleQuality();
|
||||
|
||||
texture->driverdata = texturedata;
|
||||
|
||||
if (texture->access == SDL_TEXTUREACCESS_TARGET) {
|
||||
usage = D3DUSAGE_RENDERTARGET;
|
||||
} else {
|
||||
usage = 0;
|
||||
}
|
||||
|
||||
if (D3D_CreateTextureRep(data->device, &texturedata->texture, usage, texture->format, texture->w, texture->h) < 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (texture->format == SDL_PIXELFORMAT_YV12 ||
|
||||
texture->format == SDL_PIXELFORMAT_IYUV) {
|
||||
texturedata->yuv = SDL_TRUE;
|
||||
|
||||
if (D3D_CreateTextureRep(data->device, &texturedata->utexture, usage, texture->format, texture->w / 2, texture->h / 2) < 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (D3D_CreateTextureRep(data->device, &texturedata->vtexture, usage, texture->format, texture->w / 2, texture->h / 2) < 0) {
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int
|
||||
D3D_RecreateTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
||||
{
|
||||
D3D_RenderData *data = (D3D_RenderData *)renderer->driverdata;
|
||||
D3D_TextureData *texturedata = (D3D_TextureData *)texture->driverdata;
|
||||
|
||||
if (D3D_RecreateTextureRep(data->device, &texturedata->texture, texture->format, texture->w, texture->h) < 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (texturedata->yuv) {
|
||||
if (D3D_RecreateTextureRep(data->device, &texturedata->utexture, texture->format, texture->w / 2, texture->h / 2) < 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (D3D_RecreateTextureRep(data->device, &texturedata->vtexture, texture->format, texture->w / 2, texture->h / 2) < 0) {
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int
|
||||
D3D_UpdateTexture(SDL_Renderer * renderer, SDL_Texture * texture,
|
||||
const SDL_Rect * rect, const void *pixels, int pitch)
|
||||
{
|
||||
D3D_TextureData *data = (D3D_TextureData *) texture->driverdata;
|
||||
SDL_bool full_texture = SDL_FALSE;
|
||||
D3D_RenderData *data = (D3D_RenderData *)renderer->driverdata;
|
||||
D3D_TextureData *texturedata = (D3D_TextureData *) texture->driverdata;
|
||||
|
||||
#ifdef USE_DYNAMIC_TEXTURE
|
||||
if (texture->access == SDL_TEXTUREACCESS_STREAMING &&
|
||||
rect->x == 0 && rect->y == 0 &&
|
||||
rect->w == texture->w && rect->h == texture->h) {
|
||||
full_texture = SDL_TRUE;
|
||||
}
|
||||
#endif
|
||||
|
||||
if (!data) {
|
||||
if (!texturedata) {
|
||||
SDL_SetError("Texture is not currently available");
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (D3D_UpdateTextureInternal(data->texture, texture->format, full_texture, rect->x, rect->y, rect->w, rect->h, pixels, pitch) < 0) {
|
||||
if (D3D_UpdateTextureRep(data->device, &texturedata->texture, texture->format, rect->x, rect->y, rect->w, rect->h, pixels, pitch) < 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (data->yuv) {
|
||||
if (texturedata->yuv) {
|
||||
/* Skip to the correct offset into the next texture */
|
||||
pixels = (const void*)((const Uint8*)pixels + rect->h * pitch);
|
||||
|
||||
if (D3D_UpdateTextureInternal(texture->format == SDL_PIXELFORMAT_YV12 ? data->vtexture : data->utexture, texture->format, full_texture, rect->x / 2, rect->y / 2, rect->w / 2, rect->h / 2, pixels, pitch / 2) < 0) {
|
||||
if (D3D_UpdateTextureRep(data->device, texture->format == SDL_PIXELFORMAT_YV12 ? &texturedata->vtexture : &texturedata->utexture, texture->format, rect->x / 2, rect->y / 2, rect->w / 2, rect->h / 2, pixels, pitch / 2) < 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Skip to the correct offset into the next texture */
|
||||
pixels = (const void*)((const Uint8*)pixels + (rect->h * pitch)/4);
|
||||
if (D3D_UpdateTextureInternal(texture->format == SDL_PIXELFORMAT_YV12 ? data->utexture : data->vtexture, texture->format, full_texture, rect->x / 2, rect->y / 2, rect->w / 2, rect->h / 2, pixels, pitch / 2) < 0) {
|
||||
if (D3D_UpdateTextureRep(data->device, texture->format == SDL_PIXELFORMAT_YV12 ? &texturedata->utexture : &texturedata->vtexture, texture->format, rect->x / 2, rect->y / 2, rect->w / 2, rect->h / 2, pixels, pitch / 2) < 0) {
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
|
@ -966,29 +1060,21 @@ D3D_UpdateTextureYUV(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
const Uint8 *Uplane, int Upitch,
|
||||
const Uint8 *Vplane, int Vpitch)
|
||||
{
|
||||
D3D_TextureData *data = (D3D_TextureData *) texture->driverdata;
|
||||
SDL_bool full_texture = SDL_FALSE;
|
||||
D3D_RenderData *data = (D3D_RenderData *)renderer->driverdata;
|
||||
D3D_TextureData *texturedata = (D3D_TextureData *) texture->driverdata;
|
||||
|
||||
#ifdef USE_DYNAMIC_TEXTURE
|
||||
if (texture->access == SDL_TEXTUREACCESS_STREAMING &&
|
||||
rect->x == 0 && rect->y == 0 &&
|
||||
rect->w == texture->w && rect->h == texture->h) {
|
||||
full_texture = SDL_TRUE;
|
||||
}
|
||||
#endif
|
||||
|
||||
if (!data) {
|
||||
if (!texturedata) {
|
||||
SDL_SetError("Texture is not currently available");
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (D3D_UpdateTextureInternal(data->texture, texture->format, full_texture, rect->x, rect->y, rect->w, rect->h, Yplane, Ypitch) < 0) {
|
||||
if (D3D_UpdateTextureRep(data->device, &texturedata->texture, texture->format, rect->x, rect->y, rect->w, rect->h, Yplane, Ypitch) < 0) {
|
||||
return -1;
|
||||
}
|
||||
if (D3D_UpdateTextureInternal(data->utexture, texture->format, full_texture, rect->x / 2, rect->y / 2, rect->w / 2, rect->h / 2, Uplane, Upitch) < 0) {
|
||||
if (D3D_UpdateTextureRep(data->device, &texturedata->utexture, texture->format, rect->x / 2, rect->y / 2, rect->w / 2, rect->h / 2, Uplane, Upitch) < 0) {
|
||||
return -1;
|
||||
}
|
||||
if (D3D_UpdateTextureInternal(data->vtexture, texture->format, full_texture, rect->x / 2, rect->y / 2, rect->w / 2, rect->h / 2, Vplane, Vpitch) < 0) {
|
||||
if (D3D_UpdateTextureRep(data->device, &texturedata->vtexture, texture->format, rect->x / 2, rect->y / 2, rect->w / 2, rect->h / 2, Vplane, Vpitch) < 0) {
|
||||
return -1;
|
||||
}
|
||||
return 0;
|
||||
|
|
@ -998,37 +1084,45 @@ static int
|
|||
D3D_LockTexture(SDL_Renderer * renderer, SDL_Texture * texture,
|
||||
const SDL_Rect * rect, void **pixels, int *pitch)
|
||||
{
|
||||
D3D_TextureData *data = (D3D_TextureData *) texture->driverdata;
|
||||
RECT d3drect;
|
||||
D3DLOCKED_RECT locked;
|
||||
HRESULT result;
|
||||
D3D_RenderData *data = (D3D_RenderData *)renderer->driverdata;
|
||||
D3D_TextureData *texturedata = (D3D_TextureData *)texture->driverdata;
|
||||
IDirect3DDevice9 *device = data->device;
|
||||
|
||||
if (!data) {
|
||||
if (!texturedata) {
|
||||
SDL_SetError("Texture is not currently available");
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (data->yuv) {
|
||||
texturedata->locked_rect = *rect;
|
||||
|
||||
if (texturedata->yuv) {
|
||||
/* It's more efficient to upload directly... */
|
||||
if (!data->pixels) {
|
||||
data->pitch = texture->w;
|
||||
data->pixels = (Uint8 *)SDL_malloc((texture->h * data->pitch * 3) / 2);
|
||||
if (!data->pixels) {
|
||||
if (!texturedata->pixels) {
|
||||
texturedata->pitch = texture->w;
|
||||
texturedata->pixels = (Uint8 *)SDL_malloc((texture->h * texturedata->pitch * 3) / 2);
|
||||
if (!texturedata->pixels) {
|
||||
return SDL_OutOfMemory();
|
||||
}
|
||||
}
|
||||
data->locked_rect = *rect;
|
||||
*pixels =
|
||||
(void *) ((Uint8 *) data->pixels + rect->y * data->pitch +
|
||||
(void *) ((Uint8 *) texturedata->pixels + rect->y * texturedata->pitch +
|
||||
rect->x * SDL_BYTESPERPIXEL(texture->format));
|
||||
*pitch = data->pitch;
|
||||
*pitch = texturedata->pitch;
|
||||
} else {
|
||||
RECT d3drect;
|
||||
D3DLOCKED_RECT locked;
|
||||
HRESULT result;
|
||||
|
||||
if (D3D_CreateStagingTexture(device, &texturedata->texture) < 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
d3drect.left = rect->x;
|
||||
d3drect.right = rect->x + rect->w;
|
||||
d3drect.top = rect->y;
|
||||
d3drect.bottom = rect->y + rect->h;
|
||||
|
||||
result = IDirect3DTexture9_LockRect(data->texture, 0, &locked, &d3drect, 0);
|
||||
result = IDirect3DTexture9_LockRect(texturedata->texture.staging, 0, &locked, &d3drect, 0);
|
||||
if (FAILED(result)) {
|
||||
return D3D_SetError("LockRect()", result);
|
||||
}
|
||||
|
|
@ -1041,21 +1135,23 @@ D3D_LockTexture(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
static void
|
||||
D3D_UnlockTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
||||
{
|
||||
D3D_TextureData *data = (D3D_TextureData *) texture->driverdata;
|
||||
/*D3D_RenderData *data = (D3D_RenderData *)renderer->driverdata;*/
|
||||
D3D_TextureData *texturedata = (D3D_TextureData *)texture->driverdata;
|
||||
|
||||
if (!data) {
|
||||
if (!texturedata) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (data->yuv) {
|
||||
const SDL_Rect *rect = &data->locked_rect;
|
||||
if (texturedata->yuv) {
|
||||
const SDL_Rect *rect = &texturedata->locked_rect;
|
||||
void *pixels =
|
||||
(void *) ((Uint8 *) data->pixels + rect->y * data->pitch +
|
||||
(void *) ((Uint8 *) texturedata->pixels + rect->y * texturedata->pitch +
|
||||
rect->x * SDL_BYTESPERPIXEL(texture->format));
|
||||
D3D_UpdateTexture(renderer, texture, rect, pixels, data->pitch);
|
||||
D3D_UpdateTexture(renderer, texture, rect, pixels, texturedata->pitch);
|
||||
} else {
|
||||
IDirect3DTexture9_UnlockRect(data->texture, 0);
|
||||
}
|
||||
IDirect3DTexture9_UnlockRect(texturedata->texture.staging, 0);
|
||||
texturedata->texture.dirty = SDL_TRUE;
|
||||
}
|
||||
}
|
||||
|
||||
static int
|
||||
|
|
@ -1063,7 +1159,9 @@ D3D_SetRenderTargetInternal(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
{
|
||||
D3D_RenderData *data = (D3D_RenderData *) renderer->driverdata;
|
||||
D3D_TextureData *texturedata;
|
||||
D3D_TextureRep *texturerep;
|
||||
HRESULT result;
|
||||
IDirect3DDevice9 *device = data->device;
|
||||
|
||||
/* Release the previous render target if it wasn't the default one */
|
||||
if (data->currentRenderTarget != NULL) {
|
||||
|
|
@ -1082,7 +1180,25 @@ D3D_SetRenderTargetInternal(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
return -1;
|
||||
}
|
||||
|
||||
result = IDirect3DTexture9_GetSurfaceLevel(texturedata->texture, 0, &data->currentRenderTarget);
|
||||
/* Make sure the render target is updated if it was locked and written to */
|
||||
texturerep = &texturedata->texture;
|
||||
if (texturerep->dirty && texturerep->staging) {
|
||||
if (!texturerep->texture) {
|
||||
result = IDirect3DDevice9_CreateTexture(device, texturerep->w, texturerep->h, 1, texturerep->usage,
|
||||
PixelFormatToD3DFMT(texturerep->format), D3DPOOL_DEFAULT, &texturerep->texture, NULL);
|
||||
if (FAILED(result)) {
|
||||
return D3D_SetError("CreateTexture(D3DPOOL_DEFAULT)", result);
|
||||
}
|
||||
}
|
||||
|
||||
result = IDirect3DDevice9_UpdateTexture(device, (IDirect3DBaseTexture9 *)texturerep->staging, (IDirect3DBaseTexture9 *)texturerep->texture);
|
||||
if (FAILED(result)) {
|
||||
return D3D_SetError("UpdateTexture()", result);
|
||||
}
|
||||
texturerep->dirty = SDL_FALSE;
|
||||
}
|
||||
|
||||
result = IDirect3DTexture9_GetSurfaceLevel(texturedata->texture.texture, 0, &data->currentRenderTarget);
|
||||
if(FAILED(result)) {
|
||||
return D3D_SetError("GetSurfaceLevel()", result);
|
||||
}
|
||||
|
|
@ -1145,17 +1261,18 @@ D3D_UpdateViewport(SDL_Renderer * renderer)
|
|||
static int
|
||||
D3D_UpdateClipRect(SDL_Renderer * renderer)
|
||||
{
|
||||
const SDL_Rect *rect = &renderer->clip_rect;
|
||||
D3D_RenderData *data = (D3D_RenderData *) renderer->driverdata;
|
||||
RECT r;
|
||||
HRESULT result;
|
||||
|
||||
if (!SDL_RectEmpty(rect)) {
|
||||
if (renderer->clipping_enabled) {
|
||||
const SDL_Rect *rect = &renderer->clip_rect;
|
||||
RECT r;
|
||||
HRESULT result;
|
||||
|
||||
IDirect3DDevice9_SetRenderState(data->device, D3DRS_SCISSORTESTENABLE, TRUE);
|
||||
r.left = rect->x;
|
||||
r.top = rect->y;
|
||||
r.right = rect->x + rect->w;
|
||||
r.bottom = rect->y + rect->h;
|
||||
r.left = renderer->viewport.x + rect->x;
|
||||
r.top = renderer->viewport.y + rect->y;
|
||||
r.right = renderer->viewport.x + rect->x + rect->w;
|
||||
r.bottom = renderer->viewport.y + rect->y + rect->h;
|
||||
|
||||
result = IDirect3DDevice9_SetScissorRect(data->device, &r);
|
||||
if (result != D3D_OK) {
|
||||
|
|
@ -1527,11 +1644,8 @@ D3D_RenderCopy(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
|
||||
D3D_UpdateTextureScaleMode(data, texturedata, 0);
|
||||
|
||||
result =
|
||||
IDirect3DDevice9_SetTexture(data->device, 0, (IDirect3DBaseTexture9 *)
|
||||
texturedata->texture);
|
||||
if (FAILED(result)) {
|
||||
return D3D_SetError("SetTexture()", result);
|
||||
if (D3D_BindTextureRep(data->device, &texturedata->texture, 0) < 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (texturedata->yuv) {
|
||||
|
|
@ -1540,18 +1654,11 @@ D3D_RenderCopy(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
D3D_UpdateTextureScaleMode(data, texturedata, 1);
|
||||
D3D_UpdateTextureScaleMode(data, texturedata, 2);
|
||||
|
||||
result =
|
||||
IDirect3DDevice9_SetTexture(data->device, 1, (IDirect3DBaseTexture9 *)
|
||||
texturedata->utexture);
|
||||
if (FAILED(result)) {
|
||||
return D3D_SetError("SetTexture()", result);
|
||||
if (D3D_BindTextureRep(data->device, &texturedata->utexture, 1) < 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
result =
|
||||
IDirect3DDevice9_SetTexture(data->device, 2, (IDirect3DBaseTexture9 *)
|
||||
texturedata->vtexture);
|
||||
if (FAILED(result)) {
|
||||
return D3D_SetError("SetTexture()", result);
|
||||
if (D3D_BindTextureRep(data->device, &texturedata->vtexture, 2) < 0) {
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -1665,16 +1772,13 @@ D3D_RenderCopyEx(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
modelMatrix = MatrixMultiply(
|
||||
MatrixRotationZ((float)(M_PI * (float) angle / 180.0f)),
|
||||
MatrixTranslation(dstrect->x + center->x, dstrect->y + center->y, 0)
|
||||
);
|
||||
);
|
||||
IDirect3DDevice9_SetTransform(data->device, D3DTS_VIEW, (D3DMATRIX*)&modelMatrix);
|
||||
|
||||
D3D_UpdateTextureScaleMode(data, texturedata, 0);
|
||||
|
||||
result =
|
||||
IDirect3DDevice9_SetTexture(data->device, 0, (IDirect3DBaseTexture9 *)
|
||||
texturedata->texture);
|
||||
if (FAILED(result)) {
|
||||
return D3D_SetError("SetTexture()", result);
|
||||
if (D3D_BindTextureRep(data->device, &texturedata->texture, 0) < 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (texturedata->yuv) {
|
||||
|
|
@ -1682,19 +1786,12 @@ D3D_RenderCopyEx(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
|
||||
D3D_UpdateTextureScaleMode(data, texturedata, 1);
|
||||
D3D_UpdateTextureScaleMode(data, texturedata, 2);
|
||||
|
||||
result =
|
||||
IDirect3DDevice9_SetTexture(data->device, 1, (IDirect3DBaseTexture9 *)
|
||||
texturedata->utexture);
|
||||
if (FAILED(result)) {
|
||||
return D3D_SetError("SetTexture()", result);
|
||||
|
||||
if (D3D_BindTextureRep(data->device, &texturedata->utexture, 1) < 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
result =
|
||||
IDirect3DDevice9_SetTexture(data->device, 2, (IDirect3DBaseTexture9 *)
|
||||
texturedata->vtexture);
|
||||
if (FAILED(result)) {
|
||||
return D3D_SetError("SetTexture()", result);
|
||||
if (D3D_BindTextureRep(data->device, &texturedata->vtexture, 2) < 0) {
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -1734,9 +1831,10 @@ D3D_RenderReadPixels(SDL_Renderer * renderer, const SDL_Rect * rect,
|
|||
D3DLOCKED_RECT locked;
|
||||
HRESULT result;
|
||||
|
||||
result = IDirect3DDevice9_GetBackBuffer(data->device, 0, 0, D3DBACKBUFFER_TYPE_MONO, &backBuffer);
|
||||
if (FAILED(result)) {
|
||||
return D3D_SetError("GetBackBuffer()", result);
|
||||
if (data->currentRenderTarget) {
|
||||
backBuffer = data->currentRenderTarget;
|
||||
} else {
|
||||
backBuffer = data->defaultRenderTarget;
|
||||
}
|
||||
|
||||
result = IDirect3DSurface9_GetDesc(backBuffer, &desc);
|
||||
|
|
@ -1777,7 +1875,6 @@ D3D_RenderReadPixels(SDL_Renderer * renderer, const SDL_Rect * rect,
|
|||
IDirect3DSurface9_UnlockRect(surface);
|
||||
|
||||
IDirect3DSurface9_Release(surface);
|
||||
IDirect3DSurface9_Release(backBuffer);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
|
@ -1815,15 +1912,9 @@ D3D_DestroyTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
if (!data) {
|
||||
return;
|
||||
}
|
||||
if (data->texture) {
|
||||
IDirect3DTexture9_Release(data->texture);
|
||||
}
|
||||
if (data->utexture) {
|
||||
IDirect3DTexture9_Release(data->utexture);
|
||||
}
|
||||
if (data->vtexture) {
|
||||
IDirect3DTexture9_Release(data->vtexture);
|
||||
}
|
||||
D3D_DestroyTextureRep(&data->texture);
|
||||
D3D_DestroyTextureRep(&data->utexture);
|
||||
D3D_DestroyTextureRep(&data->vtexture);
|
||||
SDL_free(data->pixels);
|
||||
SDL_free(data);
|
||||
texture->driverdata = NULL;
|
||||
|
|
@ -1870,7 +1961,7 @@ SDL_RenderGetD3D9Device(SDL_Renderer * renderer)
|
|||
#if SDL_VIDEO_RENDER_D3D && !SDL_RENDER_DISABLED
|
||||
D3D_RenderData *data = (D3D_RenderData *) renderer->driverdata;
|
||||
|
||||
// Make sure that this is a D3D renderer
|
||||
/* Make sure that this is a D3D renderer */
|
||||
if (renderer->DestroyRenderer != D3D_DestroyRenderer) {
|
||||
SDL_SetError("Renderer is not a D3D renderer");
|
||||
return NULL;
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
@ -29,12 +29,17 @@
|
|||
#include "SDL_syswm.h"
|
||||
#include "../SDL_sysrender.h"
|
||||
#include "../SDL_d3dmath.h"
|
||||
/* #include "SDL_log.h" */
|
||||
|
||||
#include <d3d11_1.h>
|
||||
|
||||
|
||||
#ifdef __WINRT__
|
||||
|
||||
#if NTDDI_VERSION > NTDDI_WIN8
|
||||
#include <DXGI1_3.h>
|
||||
#endif
|
||||
|
||||
#include "SDL_render_winrt.h"
|
||||
|
||||
#if WINAPI_FAMILY == WINAPI_FAMILY_APP
|
||||
|
|
@ -134,6 +139,7 @@ typedef struct
|
|||
/* Defined here so we don't have to include uuid.lib */
|
||||
static const GUID IID_IDXGIFactory2 = { 0x50c83a1c, 0xe072, 0x4c48, { 0x87, 0xb0, 0x36, 0x30, 0xfa, 0x36, 0xa6, 0xd0 } };
|
||||
static const GUID IID_IDXGIDevice1 = { 0x77db970f, 0x6276, 0x48ba, { 0xba, 0x28, 0x07, 0x01, 0x43, 0xb4, 0x39, 0x2c } };
|
||||
static const GUID IID_IDXGIDevice3 = { 0x6007896c, 0x3244, 0x4afd, { 0xbf, 0x18, 0xa6, 0xd3, 0xbe, 0xda, 0x50, 0x23 } };
|
||||
static const GUID IID_ID3D11Texture2D = { 0x6f15aaf2, 0xd208, 0x4e89, { 0x9a, 0xb4, 0x48, 0x95, 0x35, 0xd3, 0x4f, 0x9c } };
|
||||
static const GUID IID_ID3D11Device1 = { 0xa04bfb29, 0x08ef, 0x43d6, { 0xa4, 0x9c, 0xa9, 0xbd, 0xbd, 0xcb, 0xe6, 0x86 } };
|
||||
static const GUID IID_ID3D11DeviceContext1 = { 0xbb2c6faa, 0xb5fb, 0x4082, { 0x8e, 0x6b, 0x38, 0x8b, 0x8c, 0xfa, 0x90, 0xe1 } };
|
||||
|
|
@ -357,7 +363,7 @@ static const DWORD D3D11_PixelShader_Textures[] = {
|
|||
|
||||
float4 main(PixelShaderInput input) : SV_TARGET
|
||||
{
|
||||
const float3 offset = {-0.0625, -0.5, -0.5};
|
||||
const float3 offset = {-0.0627451017, -0.501960814, -0.501960814};
|
||||
const float3 Rcoeff = {1.164, 0.000, 1.596};
|
||||
const float3 Gcoeff = {1.164, -0.391, -0.813};
|
||||
const float3 Bcoeff = {1.164, 2.018, 0.000};
|
||||
|
|
@ -381,12 +387,12 @@ static const DWORD D3D11_PixelShader_Textures[] = {
|
|||
*/
|
||||
#if defined(D3D11_USE_SHADER_MODEL_4_0_level_9_1)
|
||||
static const DWORD D3D11_PixelShader_YUV[] = {
|
||||
0x43425844, 0x04e69cba, 0x74ce6dd2, 0x7fcf84cb, 0x3003d677, 0x00000001,
|
||||
0x43425844, 0x2321c6c6, 0xf14df2d1, 0xc79d068d, 0x8e672abf, 0x00000001,
|
||||
0x000005e8, 0x00000006, 0x00000038, 0x000001dc, 0x000003bc, 0x00000438,
|
||||
0x00000540, 0x000005b4, 0x396e6f41, 0x0000019c, 0x0000019c, 0xffff0200,
|
||||
0x0000016c, 0x00000030, 0x00300000, 0x00300000, 0x00300000, 0x00240003,
|
||||
0x00300000, 0x00000000, 0x00010001, 0x00020002, 0xffff0200, 0x05000051,
|
||||
0xa00f0000, 0xbd800000, 0xbf000000, 0xbf000000, 0x3f800000, 0x05000051,
|
||||
0xa00f0000, 0xbd808081, 0xbf008081, 0xbf008081, 0x3f800000, 0x05000051,
|
||||
0xa00f0001, 0x3f94fdf4, 0x3fcc49ba, 0x00000000, 0x00000000, 0x05000051,
|
||||
0xa00f0002, 0x3f94fdf4, 0xbec83127, 0xbf5020c5, 0x00000000, 0x05000051,
|
||||
0xa00f0003, 0x3f94fdf4, 0x400126e9, 0x00000000, 0x00000000, 0x0200001f,
|
||||
|
|
@ -413,7 +419,7 @@ static const DWORD D3D11_PixelShader_YUV[] = {
|
|||
0x00000001, 0x00101046, 0x00000001, 0x00107e46, 0x00000002, 0x00106000,
|
||||
0x00000000, 0x05000036, 0x00100042, 0x00000000, 0x0010000a, 0x00000001,
|
||||
0x0a000000, 0x00100072, 0x00000000, 0x00100246, 0x00000000, 0x00004002,
|
||||
0xbd800000, 0xbf000000, 0xbf000000, 0x00000000, 0x0a00000f, 0x00100012,
|
||||
0xbd808081, 0xbf008081, 0xbf008081, 0x00000000, 0x0a00000f, 0x00100012,
|
||||
0x00000001, 0x00100086, 0x00000000, 0x00004002, 0x3f94fdf4, 0x3fcc49ba,
|
||||
0x00000000, 0x00000000, 0x0a000010, 0x00100022, 0x00000001, 0x00100246,
|
||||
0x00000000, 0x00004002, 0x3f94fdf4, 0xbec83127, 0xbf5020c5, 0x00000000,
|
||||
|
|
@ -447,12 +453,12 @@ static const DWORD D3D11_PixelShader_YUV[] = {
|
|||
};
|
||||
#elif defined(D3D11_USE_SHADER_MODEL_4_0_level_9_3)
|
||||
static const DWORD D3D11_PixelShader_YUV[] = {
|
||||
0x43425844, 0xe6d969fc, 0x63cac33c, 0xa4926502, 0x5d788135, 0x00000001,
|
||||
0x43425844, 0x6ede7360, 0x45ff5f8a, 0x34ac92ba, 0xb865f5e0, 0x00000001,
|
||||
0x000005c0, 0x00000006, 0x00000038, 0x000001b4, 0x00000394, 0x00000410,
|
||||
0x00000518, 0x0000058c, 0x396e6f41, 0x00000174, 0x00000174, 0xffff0200,
|
||||
0x00000144, 0x00000030, 0x00300000, 0x00300000, 0x00300000, 0x00240003,
|
||||
0x00300000, 0x00000000, 0x00010001, 0x00020002, 0xffff0201, 0x05000051,
|
||||
0xa00f0000, 0xbd800000, 0xbf000000, 0x3f800000, 0x00000000, 0x05000051,
|
||||
0xa00f0000, 0xbd808081, 0xbf008081, 0x3f800000, 0x00000000, 0x05000051,
|
||||
0xa00f0001, 0x3f94fdf4, 0x3fcc49ba, 0x00000000, 0x400126e9, 0x05000051,
|
||||
0xa00f0002, 0x3f94fdf4, 0xbec83127, 0xbf5020c5, 0x00000000, 0x0200001f,
|
||||
0x80000000, 0xb0030000, 0x0200001f, 0x80000000, 0xb00f0001, 0x0200001f,
|
||||
|
|
@ -477,7 +483,7 @@ static const DWORD D3D11_PixelShader_YUV[] = {
|
|||
0x09000045, 0x001000f2, 0x00000001, 0x00101046, 0x00000001, 0x00107e46,
|
||||
0x00000002, 0x00106000, 0x00000000, 0x05000036, 0x00100042, 0x00000000,
|
||||
0x0010000a, 0x00000001, 0x0a000000, 0x00100072, 0x00000000, 0x00100246,
|
||||
0x00000000, 0x00004002, 0xbd800000, 0xbf000000, 0xbf000000, 0x00000000,
|
||||
0x00000000, 0x00004002, 0xbd808081, 0xbf008081, 0xbf008081, 0x00000000,
|
||||
0x0a00000f, 0x00100012, 0x00000001, 0x00100086, 0x00000000, 0x00004002,
|
||||
0x3f94fdf4, 0x3fcc49ba, 0x00000000, 0x00000000, 0x0a000010, 0x00100022,
|
||||
0x00000001, 0x00100246, 0x00000000, 0x00004002, 0x3f94fdf4, 0xbec83127,
|
||||
|
|
@ -754,8 +760,8 @@ SDL_RenderDriver D3D11_RenderDriver = {
|
|||
};
|
||||
|
||||
|
||||
static Uint32
|
||||
DXGIFormatToSDLPixelFormat(DXGI_FORMAT dxgiFormat) {
|
||||
Uint32
|
||||
D3D11_DXGIFormatToSDLPixelFormat(DXGI_FORMAT dxgiFormat) {
|
||||
switch (dxgiFormat) {
|
||||
case DXGI_FORMAT_B8G8R8A8_UNORM:
|
||||
return SDL_PIXELFORMAT_ARGB8888;
|
||||
|
|
@ -823,9 +829,24 @@ D3D11_CreateRenderer(SDL_Window * window, Uint32 flags)
|
|||
renderer->info.flags = (SDL_RENDERER_ACCELERATED | SDL_RENDERER_TARGETTEXTURE);
|
||||
renderer->driverdata = data;
|
||||
|
||||
#if WINAPI_FAMILY == WINAPI_FAMILY_PHONE_APP
|
||||
/* VSync is required in Windows Phone, at least for Win Phone 8.0 and 8.1.
|
||||
* Failure to use it seems to either result in:
|
||||
*
|
||||
* - with the D3D11 debug runtime turned OFF, vsync seemingly gets turned
|
||||
* off (framerate doesn't get capped), but nothing appears on-screen
|
||||
*
|
||||
* - with the D3D11 debug runtime turned ON, vsync gets automatically
|
||||
* turned back on, and the following gets output to the debug console:
|
||||
*
|
||||
* DXGI ERROR: IDXGISwapChain::Present: Interval 0 is not supported, changed to Interval 1. [ UNKNOWN ERROR #1024: ]
|
||||
*/
|
||||
renderer->info.flags |= SDL_RENDERER_PRESENTVSYNC;
|
||||
#else
|
||||
if ((flags & SDL_RENDERER_PRESENTVSYNC)) {
|
||||
renderer->info.flags |= SDL_RENDERER_PRESENTVSYNC;
|
||||
}
|
||||
#endif
|
||||
|
||||
/* HACK: make sure the SDL_Renderer references the SDL_Window data now, in
|
||||
* order to give init functions access to the underlying window handle:
|
||||
|
|
@ -846,10 +867,17 @@ D3D11_CreateRenderer(SDL_Window * window, Uint32 flags)
|
|||
}
|
||||
|
||||
static void
|
||||
D3D11_DestroyRenderer(SDL_Renderer * renderer)
|
||||
D3D11_ReleaseAll(SDL_Renderer * renderer)
|
||||
{
|
||||
D3D11_RenderData *data = (D3D11_RenderData *) renderer->driverdata;
|
||||
SDL_Texture *texture = NULL;
|
||||
|
||||
/* Release all textures */
|
||||
for (texture = renderer->textures; texture; texture = texture->next) {
|
||||
D3D11_DestroyTexture(renderer, texture);
|
||||
}
|
||||
|
||||
/* Release/reset everything else */
|
||||
if (data) {
|
||||
SAFE_RELEASE(data->dxgiFactory);
|
||||
SAFE_RELEASE(data->dxgiAdapter);
|
||||
|
|
@ -873,12 +901,35 @@ D3D11_DestroyRenderer(SDL_Renderer * renderer)
|
|||
SAFE_RELEASE(data->clippedRasterizer);
|
||||
SAFE_RELEASE(data->vertexShaderConstants);
|
||||
|
||||
data->swapEffect = (DXGI_SWAP_EFFECT) 0;
|
||||
data->rotation = DXGI_MODE_ROTATION_UNSPECIFIED;
|
||||
data->currentRenderTargetView = NULL;
|
||||
data->currentRasterizerState = NULL;
|
||||
data->currentBlendState = NULL;
|
||||
data->currentShader = NULL;
|
||||
data->currentShaderResource = NULL;
|
||||
data->currentSampler = NULL;
|
||||
|
||||
/* Unload the D3D libraries. This should be done last, in order
|
||||
* to prevent IUnknown::Release() calls from crashing.
|
||||
*/
|
||||
if (data->hD3D11Mod) {
|
||||
SDL_UnloadObject(data->hD3D11Mod);
|
||||
data->hD3D11Mod = NULL;
|
||||
}
|
||||
if (data->hDXGIMod) {
|
||||
SDL_UnloadObject(data->hDXGIMod);
|
||||
data->hDXGIMod = NULL;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
D3D11_DestroyRenderer(SDL_Renderer * renderer)
|
||||
{
|
||||
D3D11_RenderData *data = (D3D11_RenderData *) renderer->driverdata;
|
||||
D3D11_ReleaseAll(renderer);
|
||||
if (data) {
|
||||
SDL_free(data);
|
||||
}
|
||||
SDL_free(renderer);
|
||||
|
|
@ -1294,15 +1345,33 @@ D3D11_IsDisplayRotated90Degrees(DXGI_MODE_ROTATION rotation)
|
|||
}
|
||||
|
||||
static int
|
||||
D3D11_GetViewportAlignedD3DRect(SDL_Renderer * renderer, const SDL_Rect * sdlRect, D3D11_RECT * outRect)
|
||||
D3D11_GetRotationForCurrentRenderTarget(SDL_Renderer * renderer)
|
||||
{
|
||||
D3D11_RenderData *data = (D3D11_RenderData *)renderer->driverdata;
|
||||
if (data->currentOffscreenRenderTargetView) {
|
||||
return DXGI_MODE_ROTATION_IDENTITY;
|
||||
} else {
|
||||
return data->rotation;
|
||||
}
|
||||
}
|
||||
|
||||
static int
|
||||
D3D11_GetViewportAlignedD3DRect(SDL_Renderer * renderer, const SDL_Rect * sdlRect, D3D11_RECT * outRect, BOOL includeViewportOffset)
|
||||
{
|
||||
D3D11_RenderData *data = (D3D11_RenderData *) renderer->driverdata;
|
||||
switch (data->rotation) {
|
||||
const int rotation = D3D11_GetRotationForCurrentRenderTarget(renderer);
|
||||
switch (rotation) {
|
||||
case DXGI_MODE_ROTATION_IDENTITY:
|
||||
outRect->left = sdlRect->x;
|
||||
outRect->right = sdlRect->x + sdlRect->w;
|
||||
outRect->top = sdlRect->y;
|
||||
outRect->bottom = sdlRect->y + sdlRect->h;
|
||||
if (includeViewportOffset) {
|
||||
outRect->left += renderer->viewport.x;
|
||||
outRect->right += renderer->viewport.x;
|
||||
outRect->top += renderer->viewport.y;
|
||||
outRect->bottom += renderer->viewport.y;
|
||||
}
|
||||
break;
|
||||
case DXGI_MODE_ROTATION_ROTATE270:
|
||||
outRect->left = sdlRect->y;
|
||||
|
|
@ -1355,6 +1424,7 @@ D3D11_CreateSwapChain(SDL_Renderer * renderer, int w, int h)
|
|||
#if WINAPI_FAMILY == WINAPI_FAMILY_PHONE_APP
|
||||
swapChainDesc.Scaling = DXGI_SCALING_STRETCH; /* On phone, only stretch and aspect-ratio stretch scaling are allowed. */
|
||||
swapChainDesc.SwapEffect = DXGI_SWAP_EFFECT_DISCARD; /* On phone, no swap effects are supported. */
|
||||
/* TODO, WinRT: see if Win 8.x DXGI_SWAP_CHAIN_DESC1 settings are available on Windows Phone 8.1, and if there's any advantage to having them on */
|
||||
#else
|
||||
if (usingXAML) {
|
||||
swapChainDesc.Scaling = DXGI_SCALING_STRETCH;
|
||||
|
|
@ -1417,6 +1487,8 @@ D3D11_CreateSwapChain(SDL_Renderer * renderer, int w, int h)
|
|||
WIN_SetErrorFromHRESULT(__FUNCTION__ ", IDXGIFactory2::CreateSwapChainForHwnd", result);
|
||||
goto done;
|
||||
}
|
||||
|
||||
IDXGIFactory_MakeWindowAssociation(data->dxgiFactory, windowinfo.info.win.window, DXGI_MWA_NO_WINDOW_CHANGES);
|
||||
#else
|
||||
SDL_SetError(__FUNCTION__", Unable to find something to attach a swap chain to");
|
||||
goto done;
|
||||
|
|
@ -1447,6 +1519,7 @@ D3D11_CreateWindowSizeDependentResources(SDL_Renderer * renderer)
|
|||
*/
|
||||
SDL_GetWindowSize(renderer->window, &w, &h);
|
||||
data->rotation = D3D11_GetCurrentRotation();
|
||||
/* SDL_Log("%s: windowSize={%d,%d}, orientation=%d\n", __FUNCTION__, w, h, (int)data->rotation); */
|
||||
if (D3D11_IsDisplayRotated90Degrees(data->rotation)) {
|
||||
int tmp = w;
|
||||
w = h;
|
||||
|
|
@ -1463,7 +1536,15 @@ D3D11_CreateWindowSizeDependentResources(SDL_Renderer * renderer)
|
|||
DXGI_FORMAT_UNKNOWN,
|
||||
0
|
||||
);
|
||||
if (FAILED(result)) {
|
||||
if (result == DXGI_ERROR_DEVICE_REMOVED) {
|
||||
/* If the device was removed for any reason, a new device and swap chain will need to be created. */
|
||||
D3D11_HandleDeviceLost(renderer);
|
||||
|
||||
/* Everything is set up now. Do not continue execution of this method. HandleDeviceLost will reenter this method
|
||||
* and correctly set up the new device.
|
||||
*/
|
||||
goto done;
|
||||
} else if (FAILED(result)) {
|
||||
WIN_SetErrorFromHRESULT(__FUNCTION__ ", IDXGISwapChain::ResizeBuffers", result);
|
||||
goto done;
|
||||
}
|
||||
|
|
@ -1476,11 +1557,21 @@ D3D11_CreateWindowSizeDependentResources(SDL_Renderer * renderer)
|
|||
}
|
||||
|
||||
#if WINAPI_FAMILY != WINAPI_FAMILY_PHONE_APP
|
||||
/* Set the proper rotation for the swap chain, and generate the
|
||||
* 3D matrix transformation for rendering to the rotated swap chain.
|
||||
/* Set the proper rotation for the swap chain.
|
||||
*
|
||||
* To note, the call for this, IDXGISwapChain1::SetRotation, is not necessary
|
||||
* on Windows Phone, nor is it supported there. It's only needed in Windows 8/RT.
|
||||
* on Windows Phone 8.0, nor is it supported there.
|
||||
*
|
||||
* IDXGISwapChain1::SetRotation does seem to be available on Windows Phone 8.1,
|
||||
* however I've yet to find a way to make it work. It might have something to
|
||||
* do with IDXGISwapChain::ResizeBuffers appearing to not being available on
|
||||
* Windows Phone 8.1 (it wasn't on Windows Phone 8.0), but I'm not 100% sure of this.
|
||||
* The call doesn't appear to be entirely necessary though, and is a performance-related
|
||||
* call, at least according to the following page on MSDN:
|
||||
* http://code.msdn.microsoft.com/windowsapps/DXGI-swap-chain-rotation-21d13d71
|
||||
* -- David L.
|
||||
*
|
||||
* TODO, WinRT: reexamine the docs for IDXGISwapChain1::SetRotation, see if might be available, usable, and prudent-to-call on WinPhone 8.1
|
||||
*/
|
||||
if (data->swapEffect == DXGI_SWAP_EFFECT_FLIP_SEQUENTIAL) {
|
||||
result = IDXGISwapChain1_SetRotation(data->swapChain, data->rotation);
|
||||
|
|
@ -1537,7 +1628,7 @@ D3D11_HandleDeviceLost(SDL_Renderer * renderer)
|
|||
D3D11_RenderData *data = (D3D11_RenderData *) renderer->driverdata;
|
||||
HRESULT result = S_OK;
|
||||
|
||||
/* FIXME: Need to release all resources - all textures are invalid! */
|
||||
D3D11_ReleaseAll(renderer);
|
||||
|
||||
result = D3D11_CreateDeviceResources(renderer);
|
||||
if (FAILED(result)) {
|
||||
|
|
@ -1551,9 +1642,37 @@ D3D11_HandleDeviceLost(SDL_Renderer * renderer)
|
|||
return result;
|
||||
}
|
||||
|
||||
/* Let the application know that the device has been reset */
|
||||
{
|
||||
SDL_Event event;
|
||||
event.type = SDL_RENDER_DEVICE_RESET;
|
||||
SDL_PushEvent(&event);
|
||||
}
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
void
|
||||
D3D11_Trim(SDL_Renderer * renderer)
|
||||
{
|
||||
#ifdef __WINRT__
|
||||
#if NTDDI_VERSION > NTDDI_WIN8
|
||||
D3D11_RenderData *data = (D3D11_RenderData *)renderer->driverdata;
|
||||
HRESULT result = S_OK;
|
||||
IDXGIDevice3 *dxgiDevice = NULL;
|
||||
|
||||
result = ID3D11Device_QueryInterface(data->d3dDevice, &IID_IDXGIDevice3, &dxgiDevice);
|
||||
if (FAILED(result)) {
|
||||
//WIN_SetErrorFromHRESULT(__FUNCTION__ ", ID3D11Device to IDXGIDevice3", result);
|
||||
return;
|
||||
}
|
||||
|
||||
IDXGIDevice3_Trim(dxgiDevice);
|
||||
SAFE_RELEASE(dxgiDevice);
|
||||
#endif
|
||||
#endif
|
||||
}
|
||||
|
||||
static void
|
||||
D3D11_WindowEvent(SDL_Renderer * renderer, const SDL_WindowEvent *event)
|
||||
{
|
||||
|
|
@ -2065,12 +2184,14 @@ D3D11_UpdateViewport(SDL_Renderer * renderer)
|
|||
SDL_FRect orientationAlignedViewport;
|
||||
BOOL swapDimensions;
|
||||
D3D11_VIEWPORT viewport;
|
||||
const int rotation = D3D11_GetRotationForCurrentRenderTarget(renderer);
|
||||
|
||||
if (renderer->viewport.w == 0 || renderer->viewport.h == 0) {
|
||||
/* If the viewport is empty, assume that it is because
|
||||
* SDL_CreateRenderer is calling it, and will call it again later
|
||||
* with a non-empty viewport.
|
||||
*/
|
||||
/* SDL_Log("%s, no viewport was set!\n", __FUNCTION__); */
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
@ -2079,7 +2200,7 @@ D3D11_UpdateViewport(SDL_Renderer * renderer)
|
|||
* default coordinate system) so rotations will be done in the opposite
|
||||
* direction of the DXGI_MODE_ROTATION enumeration.
|
||||
*/
|
||||
switch (data->rotation) {
|
||||
switch (rotation) {
|
||||
case DXGI_MODE_ROTATION_IDENTITY:
|
||||
projection = MatrixIdentity();
|
||||
break;
|
||||
|
|
@ -2130,7 +2251,7 @@ D3D11_UpdateViewport(SDL_Renderer * renderer)
|
|||
* a landscape mode, for all Windows 8/RT devices, or a portrait mode,
|
||||
* for Windows Phone devices.
|
||||
*/
|
||||
swapDimensions = D3D11_IsDisplayRotated90Degrees(data->rotation);
|
||||
swapDimensions = D3D11_IsDisplayRotated90Degrees(rotation);
|
||||
if (swapDimensions) {
|
||||
orientationAlignedViewport.x = (float) renderer->viewport.y;
|
||||
orientationAlignedViewport.y = (float) renderer->viewport.x;
|
||||
|
|
@ -2150,6 +2271,7 @@ D3D11_UpdateViewport(SDL_Renderer * renderer)
|
|||
viewport.Height = orientationAlignedViewport.h;
|
||||
viewport.MinDepth = 0.0f;
|
||||
viewport.MaxDepth = 1.0f;
|
||||
/* SDL_Log("%s: D3D viewport = {%f,%f,%f,%f}\n", __FUNCTION__, viewport.TopLeftX, viewport.TopLeftY, viewport.Width, viewport.Height); */
|
||||
ID3D11DeviceContext_RSSetViewports(data->d3dContext, 1, &viewport);
|
||||
|
||||
return 0;
|
||||
|
|
@ -2159,13 +2281,12 @@ static int
|
|||
D3D11_UpdateClipRect(SDL_Renderer * renderer)
|
||||
{
|
||||
D3D11_RenderData *data = (D3D11_RenderData *) renderer->driverdata;
|
||||
const SDL_Rect *rect = &renderer->clip_rect;
|
||||
|
||||
if (SDL_RectEmpty(rect)) {
|
||||
if (!renderer->clipping_enabled) {
|
||||
ID3D11DeviceContext_RSSetScissorRects(data->d3dContext, 0, NULL);
|
||||
} else {
|
||||
D3D11_RECT scissorRect;
|
||||
if (D3D11_GetViewportAlignedD3DRect(renderer, rect, &scissorRect) != 0) {
|
||||
if (D3D11_GetViewportAlignedD3DRect(renderer, &renderer->clip_rect, &scissorRect, TRUE) != 0) {
|
||||
/* D3D11_GetViewportAlignedD3DRect will have set the SDL error */
|
||||
return -1;
|
||||
}
|
||||
|
|
@ -2246,7 +2367,7 @@ D3D11_UpdateVertexBuffer(SDL_Renderer *renderer,
|
|||
} else {
|
||||
SAFE_RELEASE(rendererData->vertexBuffer);
|
||||
|
||||
vertexBufferDesc.ByteWidth = dataSizeInBytes;
|
||||
vertexBufferDesc.ByteWidth = (UINT) dataSizeInBytes;
|
||||
vertexBufferDesc.Usage = D3D11_USAGE_DYNAMIC;
|
||||
vertexBufferDesc.BindFlags = D3D11_BIND_VERTEX_BUFFER;
|
||||
vertexBufferDesc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE;
|
||||
|
|
@ -2293,7 +2414,7 @@ D3D11_RenderStartDrawOp(SDL_Renderer * renderer)
|
|||
rendererData->currentRenderTargetView = renderTargetView;
|
||||
}
|
||||
|
||||
if (SDL_RectEmpty(&renderer->clip_rect)) {
|
||||
if (!renderer->clipping_enabled) {
|
||||
rasterizerState = rendererData->mainRasterizer;
|
||||
} else {
|
||||
rasterizerState = rendererData->clippedRasterizer;
|
||||
|
|
@ -2383,7 +2504,7 @@ D3D11_RenderDrawPoints(SDL_Renderer * renderer,
|
|||
a = (float)(renderer->a / 255.0f);
|
||||
|
||||
vertices = SDL_stack_alloc(VertexPositionColor, count);
|
||||
for (i = 0; i < min(count, 128); ++i) {
|
||||
for (i = 0; i < count; ++i) {
|
||||
const VertexPositionColor v = { { points[i].x, points[i].y, 0.0f }, { 0.0f, 0.0f }, { r, g, b, a } };
|
||||
vertices[i] = v;
|
||||
}
|
||||
|
|
@ -2754,7 +2875,7 @@ D3D11_RenderReadPixels(SDL_Renderer * renderer, const SDL_Rect * rect,
|
|||
}
|
||||
|
||||
/* Copy the desired portion of the back buffer to the staging texture: */
|
||||
if (D3D11_GetViewportAlignedD3DRect(renderer, rect, &srcRect) != 0) {
|
||||
if (D3D11_GetViewportAlignedD3DRect(renderer, rect, &srcRect, FALSE) != 0) {
|
||||
/* D3D11_GetViewportAlignedD3DRect will have set the SDL error */
|
||||
goto done;
|
||||
}
|
||||
|
|
@ -2790,7 +2911,7 @@ D3D11_RenderReadPixels(SDL_Renderer * renderer, const SDL_Rect * rect,
|
|||
*/
|
||||
if (SDL_ConvertPixels(
|
||||
rect->w, rect->h,
|
||||
DXGIFormatToSDLPixelFormat(stagingTextureDesc.Format),
|
||||
D3D11_DXGIFormatToSDLPixelFormat(stagingTextureDesc.Format),
|
||||
textureMemory.pData,
|
||||
textureMemory.RowPitch,
|
||||
format,
|
||||
|
|
@ -2801,7 +2922,7 @@ D3D11_RenderReadPixels(SDL_Renderer * renderer, const SDL_Rect * rect,
|
|||
*/
|
||||
char errorMessage[1024];
|
||||
SDL_snprintf(errorMessage, sizeof(errorMessage), __FUNCTION__ ", Convert Pixels failed: %s", SDL_GetError());
|
||||
SDL_SetError(errorMessage);
|
||||
SDL_SetError("%s", errorMessage);
|
||||
goto done;
|
||||
}
|
||||
|
||||
|
|
@ -2827,6 +2948,8 @@ D3D11_RenderPresent(SDL_Renderer * renderer)
|
|||
HRESULT result;
|
||||
DXGI_PRESENT_PARAMETERS parameters;
|
||||
|
||||
SDL_zero(parameters);
|
||||
|
||||
#if WINAPI_FAMILY == WINAPI_FAMILY_PHONE_APP
|
||||
syncInterval = 1;
|
||||
presentFlags = 0;
|
||||
|
|
@ -2844,7 +2967,6 @@ D3D11_RenderPresent(SDL_Renderer * renderer)
|
|||
* rects to improve efficiency in certain scenarios.
|
||||
* This option is not available on Windows Phone 8, to note.
|
||||
*/
|
||||
SDL_zero(parameters);
|
||||
result = IDXGISwapChain1_Present1(data->swapChain, syncInterval, presentFlags, ¶meters);
|
||||
#endif
|
||||
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
@ -23,6 +23,7 @@
|
|||
#if SDL_VIDEO_RENDER_D3D11 && !SDL_RENDER_DISABLED
|
||||
|
||||
#include "SDL_syswm.h"
|
||||
#include "../../video/winrt/SDL_winrtvideo_cpp.h"
|
||||
extern "C" {
|
||||
#include "../SDL_sysrender.h"
|
||||
}
|
||||
|
|
@ -79,11 +80,7 @@ D3D11_GetCoreWindowFromSDLRenderer(SDL_Renderer * renderer)
|
|||
extern "C" DXGI_MODE_ROTATION
|
||||
D3D11_GetCurrentRotation()
|
||||
{
|
||||
#if NTDDI_VERSION > NTDDI_WIN8
|
||||
const DisplayOrientations currentOrientation = DisplayInformation::GetForCurrentView()->CurrentOrientation;
|
||||
#else
|
||||
const DisplayOrientations currentOrientation = DisplayProperties::CurrentOrientation;
|
||||
#endif
|
||||
const DisplayOrientations currentOrientation = WINRT_DISPLAY_PROPERTY(CurrentOrientation);
|
||||
|
||||
switch (currentOrientation) {
|
||||
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
@ -24,6 +24,7 @@
|
|||
|
||||
#include "SDL_hints.h"
|
||||
#include "SDL_log.h"
|
||||
#include "SDL_assert.h"
|
||||
#include "SDL_opengl.h"
|
||||
#include "../SDL_sysrender.h"
|
||||
#include "SDL_shaders_gl.h"
|
||||
|
|
@ -120,6 +121,7 @@ typedef struct
|
|||
GLDEBUGPROCARB next_error_callback;
|
||||
GLvoid *next_error_userparam;
|
||||
|
||||
SDL_bool GL_ARB_texture_non_power_of_two_supported;
|
||||
SDL_bool GL_ARB_texture_rectangle_supported;
|
||||
struct {
|
||||
GL_Shader shader;
|
||||
|
|
@ -163,8 +165,9 @@ typedef struct
|
|||
int pitch;
|
||||
SDL_Rect locked_rect;
|
||||
|
||||
/* YV12 texture support */
|
||||
/* YUV texture support */
|
||||
SDL_bool yuv;
|
||||
SDL_bool nv12;
|
||||
GLuint utexture;
|
||||
GLuint vtexture;
|
||||
|
||||
|
|
@ -289,7 +292,8 @@ GL_ActivateRenderer(SDL_Renderer * renderer)
|
|||
{
|
||||
GL_RenderData *data = (GL_RenderData *) renderer->driverdata;
|
||||
|
||||
if (SDL_CurrentContext != data->context) {
|
||||
if (SDL_CurrentContext != data->context ||
|
||||
SDL_GL_GetCurrentContext() != data->context) {
|
||||
if (SDL_GL_MakeCurrent(renderer->window, data->context) < 0) {
|
||||
return -1;
|
||||
}
|
||||
|
|
@ -309,7 +313,7 @@ GL_ResetState(SDL_Renderer *renderer)
|
|||
{
|
||||
GL_RenderData *data = (GL_RenderData *) renderer->driverdata;
|
||||
|
||||
if (SDL_CurrentContext == data->context) {
|
||||
if (SDL_GL_GetCurrentContext() == data->context) {
|
||||
GL_UpdateViewport(renderer);
|
||||
} else {
|
||||
GL_ActivateRenderer(renderer);
|
||||
|
|
@ -331,16 +335,18 @@ GL_ResetState(SDL_Renderer *renderer)
|
|||
}
|
||||
|
||||
static void APIENTRY
|
||||
GL_HandleDebugMessage(GLenum source, GLenum type, GLuint id, GLenum severity, GLsizei length, const char *message, void *userParam)
|
||||
GL_HandleDebugMessage(GLenum source, GLenum type, GLuint id, GLenum severity, GLsizei length, const char *message, const void *userParam)
|
||||
{
|
||||
SDL_Renderer *renderer = (SDL_Renderer *) userParam;
|
||||
GL_RenderData *data = (GL_RenderData *) renderer->driverdata;
|
||||
|
||||
if (type == GL_DEBUG_TYPE_ERROR_ARB) {
|
||||
/* Record this error */
|
||||
++data->errors;
|
||||
data->error_messages = SDL_realloc(data->error_messages, data->errors * sizeof(*data->error_messages));
|
||||
if (data->error_messages) {
|
||||
int errors = data->errors + 1;
|
||||
char **error_messages = SDL_realloc(data->error_messages, errors * sizeof(*data->error_messages));
|
||||
if (error_messages) {
|
||||
data->errors = errors;
|
||||
data->error_messages = error_messages;
|
||||
data->error_messages[data->errors-1] = SDL_strdup(message);
|
||||
}
|
||||
}
|
||||
|
|
@ -387,7 +393,8 @@ GL_CreateRenderer(SDL_Window * window, Uint32 flags)
|
|||
const char *hint;
|
||||
GLint value;
|
||||
Uint32 window_flags;
|
||||
int profile_mask, major, minor;
|
||||
int profile_mask = 0, major = 0, minor = 0;
|
||||
SDL_bool changed_window = SDL_FALSE;
|
||||
|
||||
SDL_GL_GetAttribute(SDL_GL_CONTEXT_PROFILE_MASK, &profile_mask);
|
||||
SDL_GL_GetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, &major);
|
||||
|
|
@ -396,32 +403,28 @@ GL_CreateRenderer(SDL_Window * window, Uint32 flags)
|
|||
window_flags = SDL_GetWindowFlags(window);
|
||||
if (!(window_flags & SDL_WINDOW_OPENGL) ||
|
||||
profile_mask == SDL_GL_CONTEXT_PROFILE_ES || major != RENDERER_CONTEXT_MAJOR || minor != RENDERER_CONTEXT_MINOR) {
|
||||
|
||||
|
||||
changed_window = SDL_TRUE;
|
||||
SDL_GL_SetAttribute(SDL_GL_CONTEXT_PROFILE_MASK, 0);
|
||||
SDL_GL_SetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, RENDERER_CONTEXT_MAJOR);
|
||||
SDL_GL_SetAttribute(SDL_GL_CONTEXT_MINOR_VERSION, RENDERER_CONTEXT_MINOR);
|
||||
|
||||
if (SDL_RecreateWindow(window, window_flags | SDL_WINDOW_OPENGL) < 0) {
|
||||
/* Uh oh, better try to put it back... */
|
||||
SDL_GL_SetAttribute(SDL_GL_CONTEXT_PROFILE_MASK, profile_mask);
|
||||
SDL_GL_SetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, major);
|
||||
SDL_GL_SetAttribute(SDL_GL_CONTEXT_MINOR_VERSION, minor);
|
||||
SDL_RecreateWindow(window, window_flags);
|
||||
return NULL;
|
||||
goto error;
|
||||
}
|
||||
}
|
||||
|
||||
renderer = (SDL_Renderer *) SDL_calloc(1, sizeof(*renderer));
|
||||
if (!renderer) {
|
||||
SDL_OutOfMemory();
|
||||
return NULL;
|
||||
goto error;
|
||||
}
|
||||
|
||||
data = (GL_RenderData *) SDL_calloc(1, sizeof(*data));
|
||||
if (!data) {
|
||||
GL_DestroyRenderer(renderer);
|
||||
SDL_OutOfMemory();
|
||||
return NULL;
|
||||
goto error;
|
||||
}
|
||||
|
||||
renderer->WindowEvent = GL_WindowEvent;
|
||||
|
|
@ -454,16 +457,16 @@ GL_CreateRenderer(SDL_Window * window, Uint32 flags)
|
|||
data->context = SDL_GL_CreateContext(window);
|
||||
if (!data->context) {
|
||||
GL_DestroyRenderer(renderer);
|
||||
return NULL;
|
||||
goto error;
|
||||
}
|
||||
if (SDL_GL_MakeCurrent(window, data->context) < 0) {
|
||||
GL_DestroyRenderer(renderer);
|
||||
return NULL;
|
||||
goto error;
|
||||
}
|
||||
|
||||
if (GL_LoadFunctions(data) < 0) {
|
||||
GL_DestroyRenderer(renderer);
|
||||
return NULL;
|
||||
goto error;
|
||||
}
|
||||
|
||||
#ifdef __MACOSX__
|
||||
|
|
@ -499,9 +502,13 @@ GL_CreateRenderer(SDL_Window * window, Uint32 flags)
|
|||
data->glEnable(GL_DEBUG_OUTPUT_SYNCHRONOUS_ARB);
|
||||
}
|
||||
|
||||
if (SDL_GL_ExtensionSupported("GL_ARB_texture_rectangle")
|
||||
|| SDL_GL_ExtensionSupported("GL_EXT_texture_rectangle")) {
|
||||
if (SDL_GL_ExtensionSupported("GL_ARB_texture_non_power_of_two")) {
|
||||
data->GL_ARB_texture_non_power_of_two_supported = SDL_TRUE;
|
||||
} else if (SDL_GL_ExtensionSupported("GL_ARB_texture_rectangle") ||
|
||||
SDL_GL_ExtensionSupported("GL_EXT_texture_rectangle")) {
|
||||
data->GL_ARB_texture_rectangle_supported = SDL_TRUE;
|
||||
}
|
||||
if (data->GL_ARB_texture_rectangle_supported) {
|
||||
data->glGetIntegerv(GL_MAX_RECTANGLE_TEXTURE_SIZE_ARB, &value);
|
||||
renderer->info.max_texture_width = value;
|
||||
renderer->info.max_texture_height = value;
|
||||
|
|
@ -532,6 +539,8 @@ GL_CreateRenderer(SDL_Window * window, Uint32 flags)
|
|||
if (data->shaders && data->num_texture_units >= 3) {
|
||||
renderer->info.texture_formats[renderer->info.num_texture_formats++] = SDL_PIXELFORMAT_YV12;
|
||||
renderer->info.texture_formats[renderer->info.num_texture_formats++] = SDL_PIXELFORMAT_IYUV;
|
||||
renderer->info.texture_formats[renderer->info.num_texture_formats++] = SDL_PIXELFORMAT_NV12;
|
||||
renderer->info.texture_formats[renderer->info.num_texture_formats++] = SDL_PIXELFORMAT_NV21;
|
||||
}
|
||||
|
||||
#ifdef __MACOSX__
|
||||
|
|
@ -558,6 +567,16 @@ GL_CreateRenderer(SDL_Window * window, Uint32 flags)
|
|||
GL_ResetState(renderer);
|
||||
|
||||
return renderer;
|
||||
|
||||
error:
|
||||
if (changed_window) {
|
||||
/* Uh oh, better try to put it back... */
|
||||
SDL_GL_SetAttribute(SDL_GL_CONTEXT_PROFILE_MASK, profile_mask);
|
||||
SDL_GL_SetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, major);
|
||||
SDL_GL_SetAttribute(SDL_GL_CONTEXT_MINOR_VERSION, minor);
|
||||
SDL_RecreateWindow(window, window_flags);
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static void
|
||||
|
|
@ -602,16 +621,18 @@ convert_format(GL_RenderData *renderdata, Uint32 pixel_format,
|
|||
break;
|
||||
case SDL_PIXELFORMAT_YV12:
|
||||
case SDL_PIXELFORMAT_IYUV:
|
||||
case SDL_PIXELFORMAT_NV12:
|
||||
case SDL_PIXELFORMAT_NV21:
|
||||
*internalFormat = GL_LUMINANCE;
|
||||
*format = GL_LUMINANCE;
|
||||
*type = GL_UNSIGNED_BYTE;
|
||||
break;
|
||||
#ifdef __MACOSX__
|
||||
case SDL_PIXELFORMAT_UYVY:
|
||||
*internalFormat = GL_RGB8;
|
||||
*format = GL_YCBCR_422_APPLE;
|
||||
*type = GL_UNSIGNED_SHORT_8_8_APPLE;
|
||||
break;
|
||||
*internalFormat = GL_RGB8;
|
||||
*format = GL_YCBCR_422_APPLE;
|
||||
*type = GL_UNSIGNED_SHORT_8_8_APPLE;
|
||||
break;
|
||||
#endif
|
||||
default:
|
||||
return SDL_FALSE;
|
||||
|
|
@ -663,6 +684,11 @@ GL_CreateTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
/* Need to add size for the U and V planes */
|
||||
size += (2 * (texture->h * data->pitch) / 4);
|
||||
}
|
||||
if (texture->format == SDL_PIXELFORMAT_NV12 ||
|
||||
texture->format == SDL_PIXELFORMAT_NV21) {
|
||||
/* Need to add size for the U/V plane */
|
||||
size += ((texture->h * data->pitch) / 2);
|
||||
}
|
||||
data->pixels = SDL_calloc(1, size);
|
||||
if (!data->pixels) {
|
||||
SDL_free(data);
|
||||
|
|
@ -678,14 +704,22 @@ GL_CreateTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
|
||||
GL_CheckError("", renderer);
|
||||
renderdata->glGenTextures(1, &data->texture);
|
||||
if (GL_CheckError("glGenTexures()", renderer) < 0) {
|
||||
if (GL_CheckError("glGenTextures()", renderer) < 0) {
|
||||
if (data->pixels) {
|
||||
SDL_free(data->pixels);
|
||||
}
|
||||
SDL_free(data);
|
||||
return -1;
|
||||
}
|
||||
texture->driverdata = data;
|
||||
|
||||
if ((renderdata->GL_ARB_texture_rectangle_supported)
|
||||
/* && texture->access != SDL_TEXTUREACCESS_TARGET */){
|
||||
if (renderdata->GL_ARB_texture_non_power_of_two_supported) {
|
||||
data->type = GL_TEXTURE_2D;
|
||||
texture_w = texture->w;
|
||||
texture_h = texture->h;
|
||||
data->texw = 1.0f;
|
||||
data->texh = 1.0f;
|
||||
} else if (renderdata->GL_ARB_texture_rectangle_supported) {
|
||||
data->type = GL_TEXTURE_RECTANGLE_ARB;
|
||||
texture_w = texture->w;
|
||||
texture_h = texture->h;
|
||||
|
|
@ -789,6 +823,27 @@ GL_CreateTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
renderdata->glDisable(data->type);
|
||||
}
|
||||
|
||||
if (texture->format == SDL_PIXELFORMAT_NV12 ||
|
||||
texture->format == SDL_PIXELFORMAT_NV21) {
|
||||
data->nv12 = SDL_TRUE;
|
||||
|
||||
renderdata->glGenTextures(1, &data->utexture);
|
||||
renderdata->glEnable(data->type);
|
||||
|
||||
renderdata->glBindTexture(data->type, data->utexture);
|
||||
renderdata->glTexParameteri(data->type, GL_TEXTURE_MIN_FILTER,
|
||||
scaleMode);
|
||||
renderdata->glTexParameteri(data->type, GL_TEXTURE_MAG_FILTER,
|
||||
scaleMode);
|
||||
renderdata->glTexParameteri(data->type, GL_TEXTURE_WRAP_S,
|
||||
GL_CLAMP_TO_EDGE);
|
||||
renderdata->glTexParameteri(data->type, GL_TEXTURE_WRAP_T,
|
||||
GL_CLAMP_TO_EDGE);
|
||||
renderdata->glTexImage2D(data->type, 0, GL_LUMINANCE_ALPHA, texture_w/2,
|
||||
texture_h/2, 0, GL_LUMINANCE_ALPHA, GL_UNSIGNED_BYTE, NULL);
|
||||
renderdata->glDisable(data->type);
|
||||
}
|
||||
|
||||
return GL_CheckError("", renderer);
|
||||
}
|
||||
|
||||
|
|
@ -798,14 +853,16 @@ GL_UpdateTexture(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
{
|
||||
GL_RenderData *renderdata = (GL_RenderData *) renderer->driverdata;
|
||||
GL_TextureData *data = (GL_TextureData *) texture->driverdata;
|
||||
const int texturebpp = SDL_BYTESPERPIXEL(texture->format);
|
||||
|
||||
SDL_assert(texturebpp != 0); /* otherwise, division by zero later. */
|
||||
|
||||
GL_ActivateRenderer(renderer);
|
||||
|
||||
renderdata->glEnable(data->type);
|
||||
renderdata->glBindTexture(data->type, data->texture);
|
||||
renderdata->glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
|
||||
renderdata->glPixelStorei(GL_UNPACK_ROW_LENGTH,
|
||||
(pitch / SDL_BYTESPERPIXEL(texture->format)));
|
||||
renderdata->glPixelStorei(GL_UNPACK_ROW_LENGTH, (pitch / texturebpp));
|
||||
renderdata->glTexSubImage2D(data->type, 0, rect->x, rect->y, rect->w,
|
||||
rect->h, data->format, data->formattype,
|
||||
pixels);
|
||||
|
|
@ -834,6 +891,17 @@ GL_UpdateTexture(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
rect->w/2, rect->h/2,
|
||||
data->format, data->formattype, pixels);
|
||||
}
|
||||
|
||||
if (data->nv12) {
|
||||
renderdata->glPixelStorei(GL_UNPACK_ROW_LENGTH, (pitch / 2));
|
||||
|
||||
/* Skip to the correct offset into the next texture */
|
||||
pixels = (const void*)((const Uint8*)pixels + rect->h * pitch);
|
||||
renderdata->glBindTexture(data->type, data->utexture);
|
||||
renderdata->glTexSubImage2D(data->type, 0, rect->x/2, rect->y/2,
|
||||
rect->w/2, rect->h/2,
|
||||
GL_LUMINANCE_ALPHA, GL_UNSIGNED_BYTE, pixels);
|
||||
}
|
||||
renderdata->glDisable(data->type);
|
||||
|
||||
return GL_CheckError("glTexSubImage2D()", renderer);
|
||||
|
|
@ -973,12 +1041,19 @@ GL_UpdateViewport(SDL_Renderer * renderer)
|
|||
static int
|
||||
GL_UpdateClipRect(SDL_Renderer * renderer)
|
||||
{
|
||||
const SDL_Rect *rect = &renderer->clip_rect;
|
||||
GL_RenderData *data = (GL_RenderData *) renderer->driverdata;
|
||||
|
||||
if (!SDL_RectEmpty(rect)) {
|
||||
if (renderer->clipping_enabled) {
|
||||
const SDL_Rect *rect = &renderer->clip_rect;
|
||||
data->glEnable(GL_SCISSOR_TEST);
|
||||
data->glScissor(rect->x, renderer->viewport.h - rect->y - rect->h, rect->w, rect->h);
|
||||
if (renderer->target) {
|
||||
data->glScissor(renderer->viewport.x + rect->x, renderer->viewport.y + rect->y, rect->w, rect->h);
|
||||
} else {
|
||||
int w, h;
|
||||
|
||||
SDL_GetRendererOutputSize(renderer, &w, &h);
|
||||
data->glScissor(renderer->viewport.x + rect->x, h - renderer->viewport.y - rect->y - rect->h, rect->w, rect->h);
|
||||
}
|
||||
} else {
|
||||
data->glDisable(GL_SCISSOR_TEST);
|
||||
}
|
||||
|
|
@ -1170,15 +1245,10 @@ GL_RenderFillRects(SDL_Renderer * renderer, const SDL_FRect * rects, int count)
|
|||
}
|
||||
|
||||
static int
|
||||
GL_RenderCopy(SDL_Renderer * renderer, SDL_Texture * texture,
|
||||
const SDL_Rect * srcrect, const SDL_FRect * dstrect)
|
||||
GL_SetupCopy(SDL_Renderer * renderer, SDL_Texture * texture)
|
||||
{
|
||||
GL_RenderData *data = (GL_RenderData *) renderer->driverdata;
|
||||
GL_TextureData *texturedata = (GL_TextureData *) texture->driverdata;
|
||||
GLfloat minx, miny, maxx, maxy;
|
||||
GLfloat minu, maxu, minv, maxv;
|
||||
|
||||
GL_ActivateRenderer(renderer);
|
||||
|
||||
data->glEnable(texturedata->type);
|
||||
if (texturedata->yuv) {
|
||||
|
|
@ -1190,6 +1260,12 @@ GL_RenderCopy(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
|
||||
data->glActiveTextureARB(GL_TEXTURE0_ARB);
|
||||
}
|
||||
if (texturedata->nv12) {
|
||||
data->glActiveTextureARB(GL_TEXTURE1_ARB);
|
||||
data->glBindTexture(texturedata->type, texturedata->utexture);
|
||||
|
||||
data->glActiveTextureARB(GL_TEXTURE0_ARB);
|
||||
}
|
||||
data->glBindTexture(texturedata->type, texturedata->texture);
|
||||
|
||||
if (texture->modMode) {
|
||||
|
|
@ -1201,10 +1277,33 @@ GL_RenderCopy(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
GL_SetBlendMode(data, texture->blendMode);
|
||||
|
||||
if (texturedata->yuv) {
|
||||
GL_SetShader(data, SHADER_YV12);
|
||||
GL_SetShader(data, SHADER_YUV);
|
||||
} else if (texturedata->nv12) {
|
||||
if (texture->format == SDL_PIXELFORMAT_NV12) {
|
||||
GL_SetShader(data, SHADER_NV12);
|
||||
} else {
|
||||
GL_SetShader(data, SHADER_NV21);
|
||||
}
|
||||
} else {
|
||||
GL_SetShader(data, SHADER_RGB);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int
|
||||
GL_RenderCopy(SDL_Renderer * renderer, SDL_Texture * texture,
|
||||
const SDL_Rect * srcrect, const SDL_FRect * dstrect)
|
||||
{
|
||||
GL_RenderData *data = (GL_RenderData *) renderer->driverdata;
|
||||
GL_TextureData *texturedata = (GL_TextureData *) texture->driverdata;
|
||||
GLfloat minx, miny, maxx, maxy;
|
||||
GLfloat minu, maxu, minv, maxv;
|
||||
|
||||
GL_ActivateRenderer(renderer);
|
||||
|
||||
if (GL_SetupCopy(renderer, texture) < 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
minx = dstrect->x;
|
||||
miny = dstrect->y;
|
||||
|
|
@ -1249,30 +1348,8 @@ GL_RenderCopyEx(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
|
||||
GL_ActivateRenderer(renderer);
|
||||
|
||||
data->glEnable(texturedata->type);
|
||||
if (texturedata->yuv) {
|
||||
data->glActiveTextureARB(GL_TEXTURE2_ARB);
|
||||
data->glBindTexture(texturedata->type, texturedata->vtexture);
|
||||
|
||||
data->glActiveTextureARB(GL_TEXTURE1_ARB);
|
||||
data->glBindTexture(texturedata->type, texturedata->utexture);
|
||||
|
||||
data->glActiveTextureARB(GL_TEXTURE0_ARB);
|
||||
}
|
||||
data->glBindTexture(texturedata->type, texturedata->texture);
|
||||
|
||||
if (texture->modMode) {
|
||||
GL_SetColor(data, texture->r, texture->g, texture->b, texture->a);
|
||||
} else {
|
||||
GL_SetColor(data, 255, 255, 255, 255);
|
||||
}
|
||||
|
||||
GL_SetBlendMode(data, texture->blendMode);
|
||||
|
||||
if (texturedata->yuv) {
|
||||
GL_SetShader(data, SHADER_YV12);
|
||||
} else {
|
||||
GL_SetShader(data, SHADER_RGB);
|
||||
if (GL_SetupCopy(renderer, texture) < 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
centerx = center->x;
|
||||
|
|
@ -1361,6 +1438,7 @@ GL_RenderReadPixels(SDL_Renderer * renderer, const SDL_Rect * rect,
|
|||
format, type, temp_pixels);
|
||||
|
||||
if (GL_CheckError("glReadPixels()", renderer) < 0) {
|
||||
SDL_free(temp_pixels);
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
@ -113,7 +113,7 @@ static const char *shader_source[NUM_SHADERS][2] =
|
|||
"}"
|
||||
},
|
||||
|
||||
/* SHADER_YV12 */
|
||||
/* SHADER_YUV */
|
||||
{
|
||||
/* vertex shader */
|
||||
"varying vec4 v_color;\n"
|
||||
|
|
@ -133,7 +133,7 @@ static const char *shader_source[NUM_SHADERS][2] =
|
|||
"uniform sampler2D tex2; // V \n"
|
||||
"\n"
|
||||
"// YUV offset \n"
|
||||
"const vec3 offset = vec3(-0.0625, -0.5, -0.5);\n"
|
||||
"const vec3 offset = vec3(-0.0627451017, -0.501960814, -0.501960814);\n"
|
||||
"\n"
|
||||
"// RGB coefficients \n"
|
||||
"const vec3 Rcoeff = vec3(1.164, 0.000, 1.596);\n"
|
||||
|
|
@ -150,7 +150,7 @@ static const char *shader_source[NUM_SHADERS][2] =
|
|||
" yuv.x = texture2D(tex0, tcoord).r;\n"
|
||||
"\n"
|
||||
" // Get the U and V values \n"
|
||||
" tcoord *= 0.5;\n"
|
||||
" tcoord *= UVCoordScale;\n"
|
||||
" yuv.y = texture2D(tex1, tcoord).r;\n"
|
||||
" yuv.z = texture2D(tex2, tcoord).r;\n"
|
||||
"\n"
|
||||
|
|
@ -162,6 +162,106 @@ static const char *shader_source[NUM_SHADERS][2] =
|
|||
"\n"
|
||||
" // That was easy. :) \n"
|
||||
" gl_FragColor = vec4(rgb, 1.0) * v_color;\n"
|
||||
"}"
|
||||
},
|
||||
|
||||
/* SHADER_NV12 */
|
||||
{
|
||||
/* vertex shader */
|
||||
"varying vec4 v_color;\n"
|
||||
"varying vec2 v_texCoord;\n"
|
||||
"\n"
|
||||
"void main()\n"
|
||||
"{\n"
|
||||
" gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex;\n"
|
||||
" v_color = gl_Color;\n"
|
||||
" v_texCoord = vec2(gl_MultiTexCoord0);\n"
|
||||
"}",
|
||||
/* fragment shader */
|
||||
"varying vec4 v_color;\n"
|
||||
"varying vec2 v_texCoord;\n"
|
||||
"uniform sampler2D tex0; // Y \n"
|
||||
"uniform sampler2D tex1; // U/V \n"
|
||||
"\n"
|
||||
"// YUV offset \n"
|
||||
"const vec3 offset = vec3(-0.0627451017, -0.501960814, -0.501960814);\n"
|
||||
"\n"
|
||||
"// RGB coefficients \n"
|
||||
"const vec3 Rcoeff = vec3(1.164, 0.000, 1.596);\n"
|
||||
"const vec3 Gcoeff = vec3(1.164, -0.391, -0.813);\n"
|
||||
"const vec3 Bcoeff = vec3(1.164, 2.018, 0.000);\n"
|
||||
"\n"
|
||||
"void main()\n"
|
||||
"{\n"
|
||||
" vec2 tcoord;\n"
|
||||
" vec3 yuv, rgb;\n"
|
||||
"\n"
|
||||
" // Get the Y value \n"
|
||||
" tcoord = v_texCoord;\n"
|
||||
" yuv.x = texture2D(tex0, tcoord).r;\n"
|
||||
"\n"
|
||||
" // Get the U and V values \n"
|
||||
" tcoord *= UVCoordScale;\n"
|
||||
" yuv.yz = texture2D(tex1, tcoord).ra;\n"
|
||||
"\n"
|
||||
" // Do the color transform \n"
|
||||
" yuv += offset;\n"
|
||||
" rgb.r = dot(yuv, Rcoeff);\n"
|
||||
" rgb.g = dot(yuv, Gcoeff);\n"
|
||||
" rgb.b = dot(yuv, Bcoeff);\n"
|
||||
"\n"
|
||||
" // That was easy. :) \n"
|
||||
" gl_FragColor = vec4(rgb, 1.0) * v_color;\n"
|
||||
"}"
|
||||
},
|
||||
|
||||
/* SHADER_NV21 */
|
||||
{
|
||||
/* vertex shader */
|
||||
"varying vec4 v_color;\n"
|
||||
"varying vec2 v_texCoord;\n"
|
||||
"\n"
|
||||
"void main()\n"
|
||||
"{\n"
|
||||
" gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex;\n"
|
||||
" v_color = gl_Color;\n"
|
||||
" v_texCoord = vec2(gl_MultiTexCoord0);\n"
|
||||
"}",
|
||||
/* fragment shader */
|
||||
"varying vec4 v_color;\n"
|
||||
"varying vec2 v_texCoord;\n"
|
||||
"uniform sampler2D tex0; // Y \n"
|
||||
"uniform sampler2D tex1; // U/V \n"
|
||||
"\n"
|
||||
"// YUV offset \n"
|
||||
"const vec3 offset = vec3(-0.0627451017, -0.501960814, -0.501960814);\n"
|
||||
"\n"
|
||||
"// RGB coefficients \n"
|
||||
"const vec3 Rcoeff = vec3(1.164, 0.000, 1.596);\n"
|
||||
"const vec3 Gcoeff = vec3(1.164, -0.391, -0.813);\n"
|
||||
"const vec3 Bcoeff = vec3(1.164, 2.018, 0.000);\n"
|
||||
"\n"
|
||||
"void main()\n"
|
||||
"{\n"
|
||||
" vec2 tcoord;\n"
|
||||
" vec3 yuv, rgb;\n"
|
||||
"\n"
|
||||
" // Get the Y value \n"
|
||||
" tcoord = v_texCoord;\n"
|
||||
" yuv.x = texture2D(tex0, tcoord).r;\n"
|
||||
"\n"
|
||||
" // Get the U and V values \n"
|
||||
" tcoord *= UVCoordScale;\n"
|
||||
" yuv.yz = texture2D(tex1, tcoord).ar;\n"
|
||||
"\n"
|
||||
" // Do the color transform \n"
|
||||
" yuv += offset;\n"
|
||||
" rgb.r = dot(yuv, Rcoeff);\n"
|
||||
" rgb.g = dot(yuv, Gcoeff);\n"
|
||||
" rgb.b = dot(yuv, Bcoeff);\n"
|
||||
"\n"
|
||||
" // That was easy. :) \n"
|
||||
" gl_FragColor = vec4(rgb, 1.0) * v_color;\n"
|
||||
"}"
|
||||
},
|
||||
};
|
||||
|
|
@ -218,7 +318,11 @@ CompileShaderProgram(GL_ShaderContext *ctx, int index, GL_ShaderData *data)
|
|||
if (ctx->GL_ARB_texture_rectangle_supported) {
|
||||
frag_defines =
|
||||
"#define sampler2D sampler2DRect\n"
|
||||
"#define texture2D texture2DRect\n";
|
||||
"#define texture2D texture2DRect\n"
|
||||
"#define UVCoordScale 0.5\n";
|
||||
} else {
|
||||
frag_defines =
|
||||
"#define UVCoordScale 1.0\n";
|
||||
}
|
||||
|
||||
/* Create one program object to rule them all */
|
||||
|
|
@ -276,8 +380,9 @@ GL_CreateShaderContext()
|
|||
return NULL;
|
||||
}
|
||||
|
||||
if (SDL_GL_ExtensionSupported("GL_ARB_texture_rectangle")
|
||||
|| SDL_GL_ExtensionSupported("GL_EXT_texture_rectangle")) {
|
||||
if (!SDL_GL_ExtensionSupported("GL_ARB_texture_non_power_of_two") &&
|
||||
(SDL_GL_ExtensionSupported("GL_ARB_texture_rectangle") ||
|
||||
SDL_GL_ExtensionSupported("GL_EXT_texture_rectangle"))) {
|
||||
ctx->GL_ARB_texture_rectangle_supported = SDL_TRUE;
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
@ -26,7 +26,9 @@ typedef enum {
|
|||
SHADER_NONE,
|
||||
SHADER_SOLID,
|
||||
SHADER_RGB,
|
||||
SHADER_YV12,
|
||||
SHADER_YUV,
|
||||
SHADER_NV12,
|
||||
SHADER_NV21,
|
||||
NUM_SHADERS
|
||||
} GL_Shader;
|
||||
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
@ -43,7 +43,7 @@ glDrawTexiOES(GLint x, GLint y, GLint z, GLint width, GLint height)
|
|||
return;
|
||||
}
|
||||
|
||||
#endif /* PANDORA */
|
||||
#endif /* SDL_VIDEO_DRIVER_PANDORA */
|
||||
|
||||
/* OpenGL ES 1.1 renderer implementation, based on the OpenGL renderer */
|
||||
|
||||
|
|
@ -55,6 +55,7 @@ static const float inv255f = 1.0f / 255.0f;
|
|||
static SDL_Renderer *GLES_CreateRenderer(SDL_Window * window, Uint32 flags);
|
||||
static void GLES_WindowEvent(SDL_Renderer * renderer,
|
||||
const SDL_WindowEvent *event);
|
||||
static int GLES_GetOutputSize(SDL_Renderer * renderer, int *w, int *h);
|
||||
static int GLES_CreateTexture(SDL_Renderer * renderer, SDL_Texture * texture);
|
||||
static int GLES_UpdateTexture(SDL_Renderer * renderer, SDL_Texture * texture,
|
||||
const SDL_Rect * rect, const void *pixels,
|
||||
|
|
@ -205,7 +206,7 @@ static int GLES_LoadFunctions(GLES_RenderData * data)
|
|||
do { \
|
||||
data->func = SDL_GL_GetProcAddress(#func); \
|
||||
} while ( 0 );
|
||||
#endif /* _SDL_NOGETPROCADDR_ */
|
||||
#endif /* __SDL_NOGETPROCADDR__ */
|
||||
|
||||
#include "SDL_glesfuncs.h"
|
||||
#undef SDL_PROC
|
||||
|
|
@ -219,12 +220,10 @@ GLES_FBOList *
|
|||
GLES_GetFBO(GLES_RenderData *data, Uint32 w, Uint32 h)
|
||||
{
|
||||
GLES_FBOList *result = data->framebuffers;
|
||||
while ((result) && ((result->w != w) || (result->h != h)) )
|
||||
{
|
||||
while ((result) && ((result->w != w) || (result->h != h)) ) {
|
||||
result = result->next;
|
||||
}
|
||||
if (result == NULL)
|
||||
{
|
||||
if (result == NULL) {
|
||||
result = SDL_malloc(sizeof(GLES_FBOList));
|
||||
result->w = w;
|
||||
result->h = h;
|
||||
|
|
@ -285,45 +284,43 @@ GLES_CreateRenderer(SDL_Window * window, Uint32 flags)
|
|||
SDL_Renderer *renderer;
|
||||
GLES_RenderData *data;
|
||||
GLint value;
|
||||
Uint32 windowFlags;
|
||||
int profile_mask, major, minor;
|
||||
Uint32 window_flags;
|
||||
int profile_mask = 0, major = 0, minor = 0;
|
||||
SDL_bool changed_window = SDL_FALSE;
|
||||
|
||||
SDL_GL_GetAttribute(SDL_GL_CONTEXT_PROFILE_MASK, &profile_mask);
|
||||
SDL_GL_GetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, &major);
|
||||
SDL_GL_GetAttribute(SDL_GL_CONTEXT_MINOR_VERSION, &minor);
|
||||
|
||||
windowFlags = SDL_GetWindowFlags(window);
|
||||
if (!(windowFlags & SDL_WINDOW_OPENGL) ||
|
||||
window_flags = SDL_GetWindowFlags(window);
|
||||
if (!(window_flags & SDL_WINDOW_OPENGL) ||
|
||||
profile_mask != SDL_GL_CONTEXT_PROFILE_ES || major != RENDERER_CONTEXT_MAJOR || minor != RENDERER_CONTEXT_MINOR) {
|
||||
|
||||
changed_window = SDL_TRUE;
|
||||
SDL_GL_SetAttribute(SDL_GL_CONTEXT_PROFILE_MASK, SDL_GL_CONTEXT_PROFILE_ES);
|
||||
SDL_GL_SetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, RENDERER_CONTEXT_MAJOR);
|
||||
SDL_GL_SetAttribute(SDL_GL_CONTEXT_MINOR_VERSION, RENDERER_CONTEXT_MINOR);
|
||||
|
||||
if (SDL_RecreateWindow(window, windowFlags | SDL_WINDOW_OPENGL) < 0) {
|
||||
/* Uh oh, better try to put it back... */
|
||||
SDL_GL_SetAttribute(SDL_GL_CONTEXT_PROFILE_MASK, profile_mask);
|
||||
SDL_GL_SetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, major);
|
||||
SDL_GL_SetAttribute(SDL_GL_CONTEXT_MINOR_VERSION, minor);
|
||||
SDL_RecreateWindow(window, windowFlags);
|
||||
return NULL;
|
||||
if (SDL_RecreateWindow(window, window_flags | SDL_WINDOW_OPENGL) < 0) {
|
||||
goto error;
|
||||
}
|
||||
}
|
||||
|
||||
renderer = (SDL_Renderer *) SDL_calloc(1, sizeof(*renderer));
|
||||
if (!renderer) {
|
||||
SDL_OutOfMemory();
|
||||
return NULL;
|
||||
goto error;
|
||||
}
|
||||
|
||||
data = (GLES_RenderData *) SDL_calloc(1, sizeof(*data));
|
||||
if (!data) {
|
||||
GLES_DestroyRenderer(renderer);
|
||||
SDL_OutOfMemory();
|
||||
return NULL;
|
||||
goto error;
|
||||
}
|
||||
|
||||
renderer->WindowEvent = GLES_WindowEvent;
|
||||
renderer->GetOutputSize = GLES_GetOutputSize;
|
||||
renderer->CreateTexture = GLES_CreateTexture;
|
||||
renderer->UpdateTexture = GLES_UpdateTexture;
|
||||
renderer->LockTexture = GLES_LockTexture;
|
||||
|
|
@ -351,16 +348,16 @@ GLES_CreateRenderer(SDL_Window * window, Uint32 flags)
|
|||
data->context = SDL_GL_CreateContext(window);
|
||||
if (!data->context) {
|
||||
GLES_DestroyRenderer(renderer);
|
||||
return NULL;
|
||||
goto error;
|
||||
}
|
||||
if (SDL_GL_MakeCurrent(window, data->context) < 0) {
|
||||
GLES_DestroyRenderer(renderer);
|
||||
return NULL;
|
||||
goto error;
|
||||
}
|
||||
|
||||
if (GLES_LoadFunctions(data) < 0) {
|
||||
GLES_DestroyRenderer(renderer);
|
||||
return NULL;
|
||||
goto error;
|
||||
}
|
||||
|
||||
if (flags & SDL_RENDERER_PRESENTVSYNC) {
|
||||
|
|
@ -411,6 +408,16 @@ GLES_CreateRenderer(SDL_Window * window, Uint32 flags)
|
|||
GLES_ResetState(renderer);
|
||||
|
||||
return renderer;
|
||||
|
||||
error:
|
||||
if (changed_window) {
|
||||
/* Uh oh, better try to put it back... */
|
||||
SDL_GL_SetAttribute(SDL_GL_CONTEXT_PROFILE_MASK, profile_mask);
|
||||
SDL_GL_SetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, major);
|
||||
SDL_GL_SetAttribute(SDL_GL_CONTEXT_MINOR_VERSION, minor);
|
||||
SDL_RecreateWindow(window, window_flags);
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static void
|
||||
|
|
@ -431,6 +438,13 @@ GLES_WindowEvent(SDL_Renderer * renderer, const SDL_WindowEvent *event)
|
|||
}
|
||||
}
|
||||
|
||||
static int
|
||||
GLES_GetOutputSize(SDL_Renderer * renderer, int *w, int *h)
|
||||
{
|
||||
SDL_GL_GetDrawableSize(renderer->window, w, h);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static SDL_INLINE int
|
||||
power_of_2(int input)
|
||||
{
|
||||
|
|
@ -556,8 +570,9 @@ GLES_UpdateTexture(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
GLES_ActivateRenderer(renderer);
|
||||
|
||||
/* Bail out if we're supposed to update an empty rectangle */
|
||||
if (rect->w <= 0 || rect->h <= 0)
|
||||
if (rect->w <= 0 || rect->h <= 0) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Reformat the texture data into a tightly packed array */
|
||||
srcPitch = rect->w * SDL_BYTESPERPIXEL(texture->format);
|
||||
|
|
@ -592,8 +607,7 @@ GLES_UpdateTexture(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
src);
|
||||
SDL_free(blob);
|
||||
|
||||
if (renderdata->glGetError() != GL_NO_ERROR)
|
||||
{
|
||||
if (renderdata->glGetError() != GL_NO_ERROR) {
|
||||
return SDL_SetError("Failed to update texture");
|
||||
}
|
||||
return 0;
|
||||
|
|
@ -634,7 +648,7 @@ GLES_SetRenderTarget(SDL_Renderer * renderer, SDL_Texture * texture)
|
|||
GLenum status;
|
||||
|
||||
GLES_ActivateRenderer(renderer);
|
||||
|
||||
|
||||
if (!data->GL_OES_framebuffer_object_supported) {
|
||||
return SDL_SetError("Can't enable render target support in this renderer");
|
||||
}
|
||||
|
|
@ -666,8 +680,16 @@ GLES_UpdateViewport(SDL_Renderer * renderer)
|
|||
return 0;
|
||||
}
|
||||
|
||||
data->glViewport(renderer->viewport.x, renderer->viewport.y,
|
||||
renderer->viewport.w, renderer->viewport.h);
|
||||
if (renderer->target) {
|
||||
data->glViewport(renderer->viewport.x, renderer->viewport.y,
|
||||
renderer->viewport.w, renderer->viewport.h);
|
||||
} else {
|
||||
int w, h;
|
||||
|
||||
SDL_GetRendererOutputSize(renderer, &w, &h);
|
||||
data->glViewport(renderer->viewport.x, (h - renderer->viewport.y - renderer->viewport.h),
|
||||
renderer->viewport.w, renderer->viewport.h);
|
||||
}
|
||||
|
||||
if (renderer->viewport.w && renderer->viewport.h) {
|
||||
data->glMatrixMode(GL_PROJECTION);
|
||||
|
|
@ -684,16 +706,23 @@ static int
|
|||
GLES_UpdateClipRect(SDL_Renderer * renderer)
|
||||
{
|
||||
GLES_RenderData *data = (GLES_RenderData *) renderer->driverdata;
|
||||
const SDL_Rect *rect = &renderer->clip_rect;
|
||||
|
||||
if (SDL_CurrentContext != data->context) {
|
||||
/* We'll update the clip rect after we rebind the context */
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!SDL_RectEmpty(rect)) {
|
||||
if (renderer->clipping_enabled) {
|
||||
const SDL_Rect *rect = &renderer->clip_rect;
|
||||
data->glEnable(GL_SCISSOR_TEST);
|
||||
data->glScissor(rect->x, renderer->viewport.h - rect->y - rect->h, rect->w, rect->h);
|
||||
if (renderer->target) {
|
||||
data->glScissor(renderer->viewport.x + rect->x, renderer->viewport.y + rect->y, rect->w, rect->h);
|
||||
} else {
|
||||
int w, h;
|
||||
|
||||
SDL_GetRendererOutputSize(renderer, &w, &h);
|
||||
data->glScissor(renderer->viewport.x + rect->x, h - renderer->viewport.y - rect->y - rect->h, rect->w, rect->h);
|
||||
}
|
||||
} else {
|
||||
data->glDisable(GL_SCISSOR_TEST);
|
||||
}
|
||||
|
|
@ -807,12 +836,24 @@ GLES_RenderDrawPoints(SDL_Renderer * renderer, const SDL_FPoint * points,
|
|||
int count)
|
||||
{
|
||||
GLES_RenderData *data = (GLES_RenderData *) renderer->driverdata;
|
||||
GLfloat *vertices;
|
||||
int idx;
|
||||
|
||||
GLES_SetDrawingState(renderer);
|
||||
|
||||
data->glVertexPointer(2, GL_FLOAT, 0, points);
|
||||
data->glDrawArrays(GL_POINTS, 0, count);
|
||||
/* Emit the specified vertices as points */
|
||||
vertices = SDL_stack_alloc(GLfloat, count * 2);
|
||||
for (idx = 0; idx < count; ++idx) {
|
||||
GLfloat x = points[idx].x + 0.5f;
|
||||
GLfloat y = points[idx].y + 0.5f;
|
||||
|
||||
vertices[idx * 2] = x;
|
||||
vertices[(idx * 2) + 1] = y;
|
||||
}
|
||||
|
||||
data->glVertexPointer(2, GL_FLOAT, 0, vertices);
|
||||
data->glDrawArrays(GL_POINTS, 0, count);
|
||||
SDL_stack_free(vertices);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
@ -821,10 +862,22 @@ GLES_RenderDrawLines(SDL_Renderer * renderer, const SDL_FPoint * points,
|
|||
int count)
|
||||
{
|
||||
GLES_RenderData *data = (GLES_RenderData *) renderer->driverdata;
|
||||
GLfloat *vertices;
|
||||
int idx;
|
||||
|
||||
GLES_SetDrawingState(renderer);
|
||||
|
||||
data->glVertexPointer(2, GL_FLOAT, 0, points);
|
||||
/* Emit a line strip including the specified vertices */
|
||||
vertices = SDL_stack_alloc(GLfloat, count * 2);
|
||||
for (idx = 0; idx < count; ++idx) {
|
||||
GLfloat x = points[idx].x + 0.5f;
|
||||
GLfloat y = points[idx].y + 0.5f;
|
||||
|
||||
vertices[idx * 2] = x;
|
||||
vertices[(idx * 2) + 1] = y;
|
||||
}
|
||||
|
||||
data->glVertexPointer(2, GL_FLOAT, 0, vertices);
|
||||
if (count > 2 &&
|
||||
points[0].x == points[count-1].x && points[0].y == points[count-1].y) {
|
||||
/* GL_LINE_LOOP takes care of the final segment */
|
||||
|
|
@ -835,6 +888,7 @@ GLES_RenderDrawLines(SDL_Renderer * renderer, const SDL_FPoint * points,
|
|||
/* We need to close the endpoint of the line */
|
||||
data->glDrawArrays(GL_POINTS, count-1, 1);
|
||||
}
|
||||
SDL_stack_free(vertices);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
|
@ -1165,8 +1219,12 @@ static int GLES_BindTexture (SDL_Renderer * renderer, SDL_Texture *texture, floa
|
|||
data->glEnable(GL_TEXTURE_2D);
|
||||
data->glBindTexture(texturedata->type, texturedata->texture);
|
||||
|
||||
if(texw) *texw = (float)texturedata->texw;
|
||||
if(texh) *texh = (float)texturedata->texh;
|
||||
if (texw) {
|
||||
*texw = (float)texturedata->texw;
|
||||
}
|
||||
if (texh) {
|
||||
*texh = (float)texturedata->texh;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
@ -53,7 +53,7 @@ SDL_PROC(void, glPixelStorei, (GLenum, GLint))
|
|||
SDL_PROC(void, glReadPixels, (GLint, GLint, GLsizei, GLsizei, GLenum, GLenum, GLvoid*))
|
||||
SDL_PROC(void, glScissor, (GLint, GLint, GLsizei, GLsizei))
|
||||
SDL_PROC(void, glShaderBinary, (GLsizei, const GLuint *, GLenum, const void *, GLsizei))
|
||||
SDL_PROC(void, glShaderSource, (GLuint, GLsizei, const char **, const GLint *))
|
||||
SDL_PROC(void, glShaderSource, (GLuint, GLsizei, const GLchar* const*, const GLint *))
|
||||
SDL_PROC(void, glTexImage2D, (GLenum, GLint, GLint, GLsizei, GLsizei, GLint, GLenum, GLenum, const void *))
|
||||
SDL_PROC(void, glTexParameteri, (GLenum, GLenum, GLint))
|
||||
SDL_PROC(void, glTexSubImage2D, (GLenum, GLint, GLint, GLint, GLsizei, GLsizei, GLenum, GLenum, const GLvoid *))
|
||||
|
|
@ -68,4 +68,8 @@ SDL_PROC(void, glFramebufferTexture2D, (GLenum, GLenum, GLenum, GLuint, GLint))
|
|||
SDL_PROC(GLenum, glCheckFramebufferStatus, (GLenum))
|
||||
SDL_PROC(void, glDeleteFramebuffers, (GLsizei, const GLuint *))
|
||||
SDL_PROC(GLint, glGetAttribLocation, (GLuint, const GLchar *))
|
||||
|
||||
SDL_PROC(void, glGetProgramInfoLog, (GLuint, GLsizei, GLsizei*, GLchar*))
|
||||
SDL_PROC(void, glGenBuffers, (GLsizei, GLuint *))
|
||||
SDL_PROC(void, glBindBuffer, (GLenum, GLuint))
|
||||
SDL_PROC(void, glBufferData, (GLenum, GLsizeiptr, const GLvoid *, GLenum))
|
||||
SDL_PROC(void, glBufferSubData, (GLenum, GLintptr, GLsizeiptr, const GLvoid *))
|
||||
|
|
|
|||
File diff suppressed because it is too large
Load diff
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
@ -126,6 +126,74 @@ static const Uint8 GLES2_FragmentSrc_TextureBGRSrc_[] = " \
|
|||
} \
|
||||
";
|
||||
|
||||
/* YUV to ABGR conversion */
|
||||
static const Uint8 GLES2_FragmentSrc_TextureYUVSrc_[] = " \
|
||||
precision mediump float; \
|
||||
uniform sampler2D u_texture; \
|
||||
uniform sampler2D u_texture_u; \
|
||||
uniform sampler2D u_texture_v; \
|
||||
uniform vec4 u_modulation; \
|
||||
varying vec2 v_texCoord; \
|
||||
\
|
||||
void main() \
|
||||
{ \
|
||||
mediump vec3 yuv; \
|
||||
lowp vec3 rgb; \
|
||||
yuv.x = texture2D(u_texture, v_texCoord).r; \
|
||||
yuv.y = texture2D(u_texture_u, v_texCoord).r - 0.5; \
|
||||
yuv.z = texture2D(u_texture_v, v_texCoord).r - 0.5; \
|
||||
rgb = mat3( 1, 1, 1, \
|
||||
0, -0.39465, 2.03211, \
|
||||
1.13983, -0.58060, 0) * yuv; \
|
||||
gl_FragColor = vec4(rgb, 1); \
|
||||
gl_FragColor *= u_modulation; \
|
||||
} \
|
||||
";
|
||||
|
||||
/* NV12 to ABGR conversion */
|
||||
static const Uint8 GLES2_FragmentSrc_TextureNV12Src_[] = " \
|
||||
precision mediump float; \
|
||||
uniform sampler2D u_texture; \
|
||||
uniform sampler2D u_texture_u; \
|
||||
uniform vec4 u_modulation; \
|
||||
varying vec2 v_texCoord; \
|
||||
\
|
||||
void main() \
|
||||
{ \
|
||||
mediump vec3 yuv; \
|
||||
lowp vec3 rgb; \
|
||||
yuv.x = texture2D(u_texture, v_texCoord).r; \
|
||||
yuv.yz = texture2D(u_texture_u, v_texCoord).ra - 0.5; \
|
||||
rgb = mat3( 1, 1, 1, \
|
||||
0, -0.39465, 2.03211, \
|
||||
1.13983, -0.58060, 0) * yuv; \
|
||||
gl_FragColor = vec4(rgb, 1); \
|
||||
gl_FragColor *= u_modulation; \
|
||||
} \
|
||||
";
|
||||
|
||||
/* NV21 to ABGR conversion */
|
||||
static const Uint8 GLES2_FragmentSrc_TextureNV21Src_[] = " \
|
||||
precision mediump float; \
|
||||
uniform sampler2D u_texture; \
|
||||
uniform sampler2D u_texture_u; \
|
||||
uniform vec4 u_modulation; \
|
||||
varying vec2 v_texCoord; \
|
||||
\
|
||||
void main() \
|
||||
{ \
|
||||
mediump vec3 yuv; \
|
||||
lowp vec3 rgb; \
|
||||
yuv.x = texture2D(u_texture, v_texCoord).r; \
|
||||
yuv.yz = texture2D(u_texture_u, v_texCoord).ar - 0.5; \
|
||||
rgb = mat3( 1, 1, 1, \
|
||||
0, -0.39465, 2.03211, \
|
||||
1.13983, -0.58060, 0) * yuv; \
|
||||
gl_FragColor = vec4(rgb, 1); \
|
||||
gl_FragColor *= u_modulation; \
|
||||
} \
|
||||
";
|
||||
|
||||
static const GLES2_ShaderInstance GLES2_VertexSrc_Default = {
|
||||
GL_VERTEX_SHADER,
|
||||
GLES2_SOURCE_SHADER,
|
||||
|
|
@ -168,6 +236,28 @@ static const GLES2_ShaderInstance GLES2_FragmentSrc_TextureBGRSrc = {
|
|||
GLES2_FragmentSrc_TextureBGRSrc_
|
||||
};
|
||||
|
||||
static const GLES2_ShaderInstance GLES2_FragmentSrc_TextureYUVSrc = {
|
||||
GL_FRAGMENT_SHADER,
|
||||
GLES2_SOURCE_SHADER,
|
||||
sizeof(GLES2_FragmentSrc_TextureYUVSrc_),
|
||||
GLES2_FragmentSrc_TextureYUVSrc_
|
||||
};
|
||||
|
||||
static const GLES2_ShaderInstance GLES2_FragmentSrc_TextureNV12Src = {
|
||||
GL_FRAGMENT_SHADER,
|
||||
GLES2_SOURCE_SHADER,
|
||||
sizeof(GLES2_FragmentSrc_TextureNV12Src_),
|
||||
GLES2_FragmentSrc_TextureNV12Src_
|
||||
};
|
||||
|
||||
static const GLES2_ShaderInstance GLES2_FragmentSrc_TextureNV21Src = {
|
||||
GL_FRAGMENT_SHADER,
|
||||
GLES2_SOURCE_SHADER,
|
||||
sizeof(GLES2_FragmentSrc_TextureNV21Src_),
|
||||
GLES2_FragmentSrc_TextureNV21Src_
|
||||
};
|
||||
|
||||
|
||||
/*************************************************************************************************
|
||||
* Vertex/fragment shader binaries (NVIDIA Tegra 1/2) *
|
||||
*************************************************************************************************/
|
||||
|
|
@ -692,19 +782,39 @@ static GLES2_Shader GLES2_FragmentShader_Modulated_TextureBGRSrc = {
|
|||
}
|
||||
};
|
||||
|
||||
static GLES2_Shader GLES2_FragmentShader_TextureYUVSrc = {
|
||||
1,
|
||||
{
|
||||
&GLES2_FragmentSrc_TextureYUVSrc
|
||||
}
|
||||
};
|
||||
|
||||
static GLES2_Shader GLES2_FragmentShader_TextureNV12Src = {
|
||||
1,
|
||||
{
|
||||
&GLES2_FragmentSrc_TextureNV12Src
|
||||
}
|
||||
};
|
||||
|
||||
static GLES2_Shader GLES2_FragmentShader_TextureNV21Src = {
|
||||
1,
|
||||
{
|
||||
&GLES2_FragmentSrc_TextureNV21Src
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/*************************************************************************************************
|
||||
* Shader selector *
|
||||
*************************************************************************************************/
|
||||
|
||||
const GLES2_Shader *GLES2_GetShader(GLES2_ShaderType type, SDL_BlendMode blendMode)
|
||||
{
|
||||
switch (type)
|
||||
{
|
||||
switch (type) {
|
||||
case GLES2_SHADER_VERTEX_DEFAULT:
|
||||
return &GLES2_VertexShader_Default;
|
||||
case GLES2_SHADER_FRAGMENT_SOLID_SRC:
|
||||
switch (blendMode)
|
||||
{
|
||||
switch (blendMode) {
|
||||
case SDL_BLENDMODE_NONE:
|
||||
return &GLES2_FragmentShader_None_SolidSrc;
|
||||
case SDL_BLENDMODE_BLEND:
|
||||
|
|
@ -717,8 +827,7 @@ const GLES2_Shader *GLES2_GetShader(GLES2_ShaderType type, SDL_BlendMode blendMo
|
|||
return NULL;
|
||||
}
|
||||
case GLES2_SHADER_FRAGMENT_TEXTURE_ABGR_SRC:
|
||||
switch (blendMode)
|
||||
{
|
||||
switch (blendMode) {
|
||||
case SDL_BLENDMODE_NONE:
|
||||
return &GLES2_FragmentShader_None_TextureABGRSrc;
|
||||
case SDL_BLENDMODE_BLEND:
|
||||
|
|
@ -731,8 +840,7 @@ const GLES2_Shader *GLES2_GetShader(GLES2_ShaderType type, SDL_BlendMode blendMo
|
|||
return NULL;
|
||||
}
|
||||
case GLES2_SHADER_FRAGMENT_TEXTURE_ARGB_SRC:
|
||||
switch (blendMode)
|
||||
{
|
||||
switch (blendMode) {
|
||||
case SDL_BLENDMODE_NONE:
|
||||
return &GLES2_FragmentShader_None_TextureARGBSrc;
|
||||
case SDL_BLENDMODE_BLEND:
|
||||
|
|
@ -746,8 +854,7 @@ const GLES2_Shader *GLES2_GetShader(GLES2_ShaderType type, SDL_BlendMode blendMo
|
|||
}
|
||||
|
||||
case GLES2_SHADER_FRAGMENT_TEXTURE_RGB_SRC:
|
||||
switch (blendMode)
|
||||
{
|
||||
switch (blendMode) {
|
||||
case SDL_BLENDMODE_NONE:
|
||||
return &GLES2_FragmentShader_None_TextureRGBSrc;
|
||||
case SDL_BLENDMODE_BLEND:
|
||||
|
|
@ -761,8 +868,7 @@ const GLES2_Shader *GLES2_GetShader(GLES2_ShaderType type, SDL_BlendMode blendMo
|
|||
}
|
||||
|
||||
case GLES2_SHADER_FRAGMENT_TEXTURE_BGR_SRC:
|
||||
switch (blendMode)
|
||||
{
|
||||
switch (blendMode) {
|
||||
case SDL_BLENDMODE_NONE:
|
||||
return &GLES2_FragmentShader_None_TextureBGRSrc;
|
||||
case SDL_BLENDMODE_BLEND:
|
||||
|
|
@ -774,6 +880,21 @@ const GLES2_Shader *GLES2_GetShader(GLES2_ShaderType type, SDL_BlendMode blendMo
|
|||
default:
|
||||
return NULL;
|
||||
}
|
||||
|
||||
case GLES2_SHADER_FRAGMENT_TEXTURE_YUV_SRC:
|
||||
{
|
||||
return &GLES2_FragmentShader_TextureYUVSrc;
|
||||
}
|
||||
|
||||
case GLES2_SHADER_FRAGMENT_TEXTURE_NV12_SRC:
|
||||
{
|
||||
return &GLES2_FragmentShader_TextureNV12Src;
|
||||
}
|
||||
|
||||
case GLES2_SHADER_FRAGMENT_TEXTURE_NV21_SRC:
|
||||
{
|
||||
return &GLES2_FragmentShader_TextureNV21Src;
|
||||
}
|
||||
|
||||
default:
|
||||
return NULL;
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
@ -46,7 +46,10 @@ typedef enum
|
|||
GLES2_SHADER_FRAGMENT_TEXTURE_ABGR_SRC,
|
||||
GLES2_SHADER_FRAGMENT_TEXTURE_ARGB_SRC,
|
||||
GLES2_SHADER_FRAGMENT_TEXTURE_BGR_SRC,
|
||||
GLES2_SHADER_FRAGMENT_TEXTURE_RGB_SRC
|
||||
GLES2_SHADER_FRAGMENT_TEXTURE_RGB_SRC,
|
||||
GLES2_SHADER_FRAGMENT_TEXTURE_YUV_SRC,
|
||||
GLES2_SHADER_FRAGMENT_TEXTURE_NV12_SRC,
|
||||
GLES2_SHADER_FRAGMENT_TEXTURE_NV21_SRC
|
||||
} GLES2_ShaderType;
|
||||
|
||||
#define GLES2_SOURCE_SHADER (GLenum)-1
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
@ -459,7 +459,7 @@ static int
|
|||
PSP_CreateTexture(SDL_Renderer * renderer, SDL_Texture * texture)
|
||||
{
|
||||
/* PSP_RenderData *renderdata = (PSP_RenderData *) renderer->driverdata; */
|
||||
PSP_TextureData* psp_texture = (PSP_TextureData*) SDL_calloc(1, sizeof(*psp_texture));;
|
||||
PSP_TextureData* psp_texture = (PSP_TextureData*) SDL_calloc(1, sizeof(*psp_texture));
|
||||
|
||||
if(!psp_texture)
|
||||
return -1;
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
@ -51,11 +51,12 @@ do { \
|
|||
|
||||
#define DRAW_SETPIXEL_BLEND(getpixel, setpixel) \
|
||||
do { \
|
||||
unsigned sr, sg, sb, sa; (void) sa; \
|
||||
unsigned sr, sg, sb, sa = 0xFF; \
|
||||
getpixel; \
|
||||
sr = DRAW_MUL(inva, sr) + r; \
|
||||
sg = DRAW_MUL(inva, sg) + g; \
|
||||
sb = DRAW_MUL(inva, sb) + b; \
|
||||
sa = DRAW_MUL(inva, sa) + a; \
|
||||
setpixel; \
|
||||
} while (0)
|
||||
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
@ -82,14 +82,14 @@ SDL_RenderDriver SW_RenderDriver = {
|
|||
SDL_RENDERER_SOFTWARE | SDL_RENDERER_TARGETTEXTURE,
|
||||
8,
|
||||
{
|
||||
SDL_PIXELFORMAT_RGB555,
|
||||
SDL_PIXELFORMAT_RGB565,
|
||||
SDL_PIXELFORMAT_ARGB8888,
|
||||
SDL_PIXELFORMAT_ABGR8888,
|
||||
SDL_PIXELFORMAT_RGBA8888,
|
||||
SDL_PIXELFORMAT_BGRA8888,
|
||||
SDL_PIXELFORMAT_RGB888,
|
||||
SDL_PIXELFORMAT_BGR888,
|
||||
SDL_PIXELFORMAT_ARGB8888,
|
||||
SDL_PIXELFORMAT_RGBA8888,
|
||||
SDL_PIXELFORMAT_ABGR8888,
|
||||
SDL_PIXELFORMAT_BGRA8888
|
||||
SDL_PIXELFORMAT_RGB565,
|
||||
SDL_PIXELFORMAT_RGB555
|
||||
},
|
||||
0,
|
||||
0}
|
||||
|
|
@ -146,6 +146,7 @@ SW_CreateRendererForSurface(SDL_Surface * surface)
|
|||
return NULL;
|
||||
}
|
||||
data->surface = surface;
|
||||
data->window = surface;
|
||||
|
||||
renderer->WindowEvent = SW_WindowEvent;
|
||||
renderer->GetOutputSize = SW_GetOutputSize;
|
||||
|
|
@ -252,6 +253,12 @@ static int
|
|||
SW_SetTextureColorMod(SDL_Renderer * renderer, SDL_Texture * texture)
|
||||
{
|
||||
SDL_Surface *surface = (SDL_Surface *) texture->driverdata;
|
||||
/* If the color mod is ever enabled (non-white), permanently disable RLE (which doesn't support
|
||||
* color mod) to avoid potentially frequent RLE encoding/decoding.
|
||||
*/
|
||||
if ((texture->r & texture->g & texture->b) != 255) {
|
||||
SDL_SetSurfaceRLE(surface, 0);
|
||||
}
|
||||
return SDL_SetSurfaceColorMod(surface, texture->r, texture->g,
|
||||
texture->b);
|
||||
}
|
||||
|
|
@ -260,6 +267,12 @@ static int
|
|||
SW_SetTextureAlphaMod(SDL_Renderer * renderer, SDL_Texture * texture)
|
||||
{
|
||||
SDL_Surface *surface = (SDL_Surface *) texture->driverdata;
|
||||
/* If the texture ever has multiple alpha values (surface alpha plus alpha channel), permanently
|
||||
* disable RLE (which doesn't support this) to avoid potentially frequent RLE encoding/decoding.
|
||||
*/
|
||||
if (texture->a != 255 && surface->format->Amask) {
|
||||
SDL_SetSurfaceRLE(surface, 0);
|
||||
}
|
||||
return SDL_SetSurfaceAlphaMod(surface, texture->a);
|
||||
}
|
||||
|
||||
|
|
@ -267,6 +280,12 @@ static int
|
|||
SW_SetTextureBlendMode(SDL_Renderer * renderer, SDL_Texture * texture)
|
||||
{
|
||||
SDL_Surface *surface = (SDL_Surface *) texture->driverdata;
|
||||
/* If add or mod blending are ever enabled, permanently disable RLE (which doesn't support
|
||||
* them) to avoid potentially frequent RLE encoding/decoding.
|
||||
*/
|
||||
if ((texture->blendMode == SDL_BLENDMODE_ADD || texture->blendMode == SDL_BLENDMODE_MOD)) {
|
||||
SDL_SetSurfaceRLE(surface, 0);
|
||||
}
|
||||
return SDL_SetSurfaceBlendMode(surface, texture->blendMode);
|
||||
}
|
||||
|
||||
|
|
@ -347,11 +366,9 @@ SW_UpdateClipRect(SDL_Renderer * renderer)
|
|||
{
|
||||
SW_RenderData *data = (SW_RenderData *) renderer->driverdata;
|
||||
SDL_Surface *surface = data->surface;
|
||||
const SDL_Rect *rect = &renderer->clip_rect;
|
||||
|
||||
if (surface) {
|
||||
if (!SDL_RectEmpty(rect)) {
|
||||
SDL_SetClipRect(surface, rect);
|
||||
if (renderer->clipping_enabled) {
|
||||
SDL_SetClipRect(surface, &renderer->clip_rect);
|
||||
} else {
|
||||
SDL_SetClipRect(surface, NULL);
|
||||
}
|
||||
|
|
@ -554,6 +571,10 @@ SW_RenderCopy(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
if ( srcrect->w == final_rect.w && srcrect->h == final_rect.h ) {
|
||||
return SDL_BlitSurface(src, srcrect, surface, &final_rect);
|
||||
} else {
|
||||
/* If scaling is ever done, permanently disable RLE (which doesn't support scaling)
|
||||
* to avoid potentially frequent RLE encoding/decoding.
|
||||
*/
|
||||
SDL_SetSurfaceRLE(surface, 0);
|
||||
return SDL_BlitScaled(src, srcrect, surface, &final_rect);
|
||||
}
|
||||
}
|
||||
|
|
@ -579,7 +600,6 @@ SW_RenderCopyEx(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
SDL_Surface *src = (SDL_Surface *) texture->driverdata;
|
||||
SDL_Rect final_rect, tmp_rect;
|
||||
SDL_Surface *surface_rotated, *surface_scaled;
|
||||
Uint32 colorkey;
|
||||
int retval, dstwidth, dstheight, abscenterx, abscentery;
|
||||
double cangle, sangle, px, py, p1x, p1y, p2x, p2y, p3x, p3y, p4x, p4y;
|
||||
|
||||
|
|
@ -597,66 +617,113 @@ SW_RenderCopyEx(SDL_Renderer * renderer, SDL_Texture * texture,
|
|||
final_rect.w = (int)dstrect->w;
|
||||
final_rect.h = (int)dstrect->h;
|
||||
|
||||
surface_scaled = SDL_CreateRGBSurface(SDL_SWSURFACE, final_rect.w, final_rect.h, src->format->BitsPerPixel,
|
||||
src->format->Rmask, src->format->Gmask,
|
||||
src->format->Bmask, src->format->Amask );
|
||||
if (surface_scaled) {
|
||||
SDL_GetColorKey(src, &colorkey);
|
||||
SDL_SetColorKey(surface_scaled, SDL_TRUE, colorkey);
|
||||
tmp_rect = final_rect;
|
||||
tmp_rect.x = 0;
|
||||
tmp_rect.y = 0;
|
||||
/* SDLgfx_rotateSurface doesn't accept a source rectangle, so crop and scale if we need to */
|
||||
tmp_rect = final_rect;
|
||||
tmp_rect.x = 0;
|
||||
tmp_rect.y = 0;
|
||||
if (srcrect->w == final_rect.w && srcrect->h == final_rect.h && srcrect->x == 0 && srcrect->y == 0) {
|
||||
surface_scaled = src; /* but if we don't need to, just use the original */
|
||||
retval = 0;
|
||||
} else {
|
||||
SDL_Surface *blit_src = src;
|
||||
Uint32 colorkey;
|
||||
SDL_BlendMode blendMode;
|
||||
Uint8 alphaMod, r, g, b;
|
||||
SDL_bool cloneSource = SDL_FALSE;
|
||||
|
||||
retval = SDL_BlitScaled(src, srcrect, surface_scaled, &tmp_rect);
|
||||
if (!retval) {
|
||||
SDLgfx_rotozoomSurfaceSizeTrig(tmp_rect.w, tmp_rect.h, -angle, &dstwidth, &dstheight, &cangle, &sangle);
|
||||
surface_rotated = SDLgfx_rotateSurface(surface_scaled, -angle, dstwidth/2, dstheight/2, GetScaleQuality(), flip & SDL_FLIP_HORIZONTAL, flip & SDL_FLIP_VERTICAL, dstwidth, dstheight, cangle, sangle);
|
||||
if(surface_rotated) {
|
||||
/* Find out where the new origin is by rotating the four final_rect points around the center and then taking the extremes */
|
||||
abscenterx = final_rect.x + (int)center->x;
|
||||
abscentery = final_rect.y + (int)center->y;
|
||||
/* Compensate the angle inversion to match the behaviour of the other backends */
|
||||
sangle = -sangle;
|
||||
|
||||
/* Top Left */
|
||||
px = final_rect.x - abscenterx;
|
||||
py = final_rect.y - abscentery;
|
||||
p1x = px * cangle - py * sangle + abscenterx;
|
||||
p1y = px * sangle + py * cangle + abscentery;
|
||||
|
||||
/* Top Right */
|
||||
px = final_rect.x + final_rect.w - abscenterx;
|
||||
py = final_rect.y - abscentery;
|
||||
p2x = px * cangle - py * sangle + abscenterx;
|
||||
p2y = px * sangle + py * cangle + abscentery;
|
||||
|
||||
/* Bottom Left */
|
||||
px = final_rect.x - abscenterx;
|
||||
py = final_rect.y + final_rect.h - abscentery;
|
||||
p3x = px * cangle - py * sangle + abscenterx;
|
||||
p3y = px * sangle + py * cangle + abscentery;
|
||||
|
||||
/* Bottom Right */
|
||||
px = final_rect.x + final_rect.w - abscenterx;
|
||||
py = final_rect.y + final_rect.h - abscentery;
|
||||
p4x = px * cangle - py * sangle + abscenterx;
|
||||
p4y = px * sangle + py * cangle + abscentery;
|
||||
|
||||
tmp_rect.x = (int)MIN(MIN(p1x, p2x), MIN(p3x, p4x));
|
||||
tmp_rect.y = (int)MIN(MIN(p1y, p2y), MIN(p3y, p4y));
|
||||
tmp_rect.w = dstwidth;
|
||||
tmp_rect.h = dstheight;
|
||||
|
||||
retval = SDL_BlitSurface(surface_rotated, NULL, surface, &tmp_rect);
|
||||
SDL_FreeSurface(surface_scaled);
|
||||
SDL_FreeSurface(surface_rotated);
|
||||
return retval;
|
||||
}
|
||||
surface_scaled = SDL_CreateRGBSurface(SDL_SWSURFACE, final_rect.w, final_rect.h, src->format->BitsPerPixel,
|
||||
src->format->Rmask, src->format->Gmask,
|
||||
src->format->Bmask, src->format->Amask );
|
||||
if (!surface_scaled) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* copy the color key, alpha mod, blend mode, and color mod so the scaled surface behaves like the source */
|
||||
if (SDL_GetColorKey(src, &colorkey) == 0) {
|
||||
SDL_SetColorKey(surface_scaled, SDL_TRUE, colorkey);
|
||||
cloneSource = SDL_TRUE;
|
||||
}
|
||||
SDL_GetSurfaceAlphaMod(src, &alphaMod); /* these will be copied to surface_scaled below if necessary */
|
||||
SDL_GetSurfaceBlendMode(src, &blendMode);
|
||||
SDL_GetSurfaceColorMod(src, &r, &g, &b);
|
||||
|
||||
/* now we need to blit the src into surface_scaled. since we want to copy the colors from the source to
|
||||
* surface_scaled rather than blend them, etc. we'll need to disable the blend mode, alpha mod, etc.
|
||||
* but we don't want to modify src (in case it's being used on other threads), so we'll need to clone it
|
||||
* before changing the blend options
|
||||
*/
|
||||
cloneSource |= blendMode != SDL_BLENDMODE_NONE || (alphaMod & r & g & b) != 255;
|
||||
if (cloneSource) {
|
||||
blit_src = SDL_ConvertSurface(src, src->format, src->flags); /* clone src */
|
||||
if (!blit_src) {
|
||||
SDL_FreeSurface(surface_scaled);
|
||||
return -1;
|
||||
}
|
||||
SDL_SetSurfaceAlphaMod(blit_src, 255); /* disable all blending options in blit_src */
|
||||
SDL_SetSurfaceBlendMode(blit_src, SDL_BLENDMODE_NONE);
|
||||
SDL_SetColorKey(blit_src, 0, 0);
|
||||
SDL_SetSurfaceColorMod(blit_src, 255, 255, 255);
|
||||
SDL_SetSurfaceRLE(blit_src, 0); /* don't RLE encode a surface we'll only use once */
|
||||
|
||||
SDL_SetSurfaceAlphaMod(surface_scaled, alphaMod); /* copy blending options to surface_scaled */
|
||||
SDL_SetSurfaceBlendMode(surface_scaled, blendMode);
|
||||
SDL_SetSurfaceColorMod(surface_scaled, r, g, b);
|
||||
}
|
||||
|
||||
retval = SDL_BlitScaled(blit_src, srcrect, surface_scaled, &tmp_rect);
|
||||
if (blit_src != src) {
|
||||
SDL_FreeSurface(blit_src);
|
||||
}
|
||||
return retval;
|
||||
}
|
||||
|
||||
return -1;
|
||||
if (!retval) {
|
||||
SDLgfx_rotozoomSurfaceSizeTrig(tmp_rect.w, tmp_rect.h, -angle, &dstwidth, &dstheight, &cangle, &sangle);
|
||||
surface_rotated = SDLgfx_rotateSurface(surface_scaled, -angle, dstwidth/2, dstheight/2, GetScaleQuality(), flip & SDL_FLIP_HORIZONTAL, flip & SDL_FLIP_VERTICAL, dstwidth, dstheight, cangle, sangle);
|
||||
if(surface_rotated) {
|
||||
/* Find out where the new origin is by rotating the four final_rect points around the center and then taking the extremes */
|
||||
abscenterx = final_rect.x + (int)center->x;
|
||||
abscentery = final_rect.y + (int)center->y;
|
||||
/* Compensate the angle inversion to match the behaviour of the other backends */
|
||||
sangle = -sangle;
|
||||
|
||||
/* Top Left */
|
||||
px = final_rect.x - abscenterx;
|
||||
py = final_rect.y - abscentery;
|
||||
p1x = px * cangle - py * sangle + abscenterx;
|
||||
p1y = px * sangle + py * cangle + abscentery;
|
||||
|
||||
/* Top Right */
|
||||
px = final_rect.x + final_rect.w - abscenterx;
|
||||
py = final_rect.y - abscentery;
|
||||
p2x = px * cangle - py * sangle + abscenterx;
|
||||
p2y = px * sangle + py * cangle + abscentery;
|
||||
|
||||
/* Bottom Left */
|
||||
px = final_rect.x - abscenterx;
|
||||
py = final_rect.y + final_rect.h - abscentery;
|
||||
p3x = px * cangle - py * sangle + abscenterx;
|
||||
p3y = px * sangle + py * cangle + abscentery;
|
||||
|
||||
/* Bottom Right */
|
||||
px = final_rect.x + final_rect.w - abscenterx;
|
||||
py = final_rect.y + final_rect.h - abscentery;
|
||||
p4x = px * cangle - py * sangle + abscenterx;
|
||||
p4y = px * sangle + py * cangle + abscentery;
|
||||
|
||||
tmp_rect.x = (int)MIN(MIN(p1x, p2x), MIN(p3x, p4x));
|
||||
tmp_rect.y = (int)MIN(MIN(p1y, p2y), MIN(p3y, p4y));
|
||||
tmp_rect.w = dstwidth;
|
||||
tmp_rect.h = dstheight;
|
||||
|
||||
retval = SDL_BlitSurface(surface_rotated, NULL, surface, &tmp_rect);
|
||||
SDL_FreeSurface(surface_rotated);
|
||||
}
|
||||
}
|
||||
|
||||
if (surface_scaled != src) {
|
||||
SDL_FreeSurface(surface_scaled);
|
||||
}
|
||||
return retval;
|
||||
}
|
||||
|
||||
static int
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
|
|||
|
|
@ -188,10 +188,8 @@ _transformSurfaceRGBA(SDL_Surface * src, SDL_Surface * dst, int cx, int cy, int
|
|||
dy = (sdy >> 16);
|
||||
if (flipx) dx = sw - dx;
|
||||
if (flipy) dy = sh - dy;
|
||||
if ((dx > -1) && (dy > -1) && (dx < (src->w-1)) && (dy < (src->h-1))) {
|
||||
sp = (tColorRGBA *)src->pixels;;
|
||||
sp += ((src->pitch/4) * dy);
|
||||
sp += dx;
|
||||
if ((unsigned)dx < (unsigned)sw && (unsigned)dy < (unsigned)sh) {
|
||||
sp = (tColorRGBA *) ((Uint8 *) src->pixels + src->pitch * dy) + dx;
|
||||
c00 = *sp;
|
||||
sp += 1;
|
||||
c01 = *sp;
|
||||
|
|
@ -237,14 +235,12 @@ _transformSurfaceRGBA(SDL_Surface * src, SDL_Surface * dst, int cx, int cy, int
|
|||
sdx = (ax + (isin * dy)) + xd;
|
||||
sdy = (ay - (icos * dy)) + yd;
|
||||
for (x = 0; x < dst->w; x++) {
|
||||
dx = (short) (sdx >> 16);
|
||||
dy = (short) (sdy >> 16);
|
||||
if (flipx) dx = (src->w-1)-dx;
|
||||
if (flipy) dy = (src->h-1)-dy;
|
||||
if ((dx >= 0) && (dy >= 0) && (dx < src->w) && (dy < src->h)) {
|
||||
sp = (tColorRGBA *) ((Uint8 *) src->pixels + src->pitch * dy);
|
||||
sp += dx;
|
||||
*pc = *sp;
|
||||
dx = (sdx >> 16);
|
||||
dy = (sdy >> 16);
|
||||
if ((unsigned)dx < (unsigned)src->w && (unsigned)dy < (unsigned)src->h) {
|
||||
if(flipx) dx = sw - dx;
|
||||
if(flipy) dy = sh - dy;
|
||||
*pc = *((tColorRGBA *)((Uint8 *)src->pixels + src->pitch * dy) + dx);
|
||||
}
|
||||
sdx += icos;
|
||||
sdy += isin;
|
||||
|
|
@ -277,7 +273,7 @@ static void
|
|||
transformSurfaceY(SDL_Surface * src, SDL_Surface * dst, int cx, int cy, int isin, int icos, int flipx, int flipy)
|
||||
{
|
||||
int x, y, dx, dy, xd, yd, sdx, sdy, ax, ay;
|
||||
tColorY *pc, *sp;
|
||||
tColorY *pc;
|
||||
int gap;
|
||||
|
||||
/*
|
||||
|
|
@ -301,14 +297,12 @@ transformSurfaceY(SDL_Surface * src, SDL_Surface * dst, int cx, int cy, int isin
|
|||
sdx = (ax + (isin * dy)) + xd;
|
||||
sdy = (ay - (icos * dy)) + yd;
|
||||
for (x = 0; x < dst->w; x++) {
|
||||
dx = (short) (sdx >> 16);
|
||||
dy = (short) (sdy >> 16);
|
||||
if (flipx) dx = (src->w-1)-dx;
|
||||
if (flipy) dy = (src->h-1)-dy;
|
||||
if ((dx >= 0) && (dy >= 0) && (dx < src->w) && (dy < src->h)) {
|
||||
sp = (tColorY *) (src->pixels);
|
||||
sp += (src->pitch * dy + dx);
|
||||
*pc = *sp;
|
||||
dx = (sdx >> 16);
|
||||
dy = (sdy >> 16);
|
||||
if ((unsigned)dx < (unsigned)src->w && (unsigned)dy < (unsigned)src->h) {
|
||||
if (flipx) dx = (src->w-1)-dx;
|
||||
if (flipy) dy = (src->h-1)-dy;
|
||||
*pc = *((tColorY *)src->pixels + src->pitch * dy + dx);
|
||||
}
|
||||
sdx += icos;
|
||||
sdy += isin;
|
||||
|
|
@ -348,7 +342,7 @@ SDLgfx_rotateSurface(SDL_Surface * src, double angle, int centerx, int centery,
|
|||
SDL_Surface *rz_src;
|
||||
SDL_Surface *rz_dst;
|
||||
int is32bit;
|
||||
int i, src_converted;
|
||||
int i;
|
||||
Uint8 r,g,b;
|
||||
Uint32 colorkey = 0;
|
||||
int colorKeyAvailable = 0;
|
||||
|
|
@ -375,27 +369,15 @@ SDLgfx_rotateSurface(SDL_Surface * src, double angle, int centerx, int centery,
|
|||
* Use source surface 'as is'
|
||||
*/
|
||||
rz_src = src;
|
||||
src_converted = 0;
|
||||
} else {
|
||||
/*
|
||||
* New source surface is 32bit with a defined RGBA ordering
|
||||
*/
|
||||
rz_src =
|
||||
SDL_CreateRGBSurface(SDL_SWSURFACE, src->w, src->h, 32,
|
||||
Uint32 format = SDL_MasksToPixelFormatEnum(32,
|
||||
#if SDL_BYTEORDER == SDL_LIL_ENDIAN
|
||||
0x000000ff, 0x0000ff00, 0x00ff0000, 0xff000000
|
||||
#else
|
||||
0xff000000, 0x00ff0000, 0x0000ff00, 0x000000ff
|
||||
#endif
|
||||
);
|
||||
if(colorKeyAvailable)
|
||||
SDL_SetColorKey(src, 0, 0);
|
||||
|
||||
SDL_BlitSurface(src, NULL, rz_src, NULL);
|
||||
|
||||
if(colorKeyAvailable)
|
||||
SDL_SetColorKey(src, SDL_TRUE /* SDL_SRCCOLORKEY */, colorkey);
|
||||
src_converted = 1;
|
||||
);
|
||||
rz_src = SDL_ConvertSurfaceFormat(src, format, src->flags);
|
||||
is32bit = 1;
|
||||
}
|
||||
|
||||
|
|
@ -480,6 +462,19 @@ SDLgfx_rotateSurface(SDL_Surface * src, double angle, int centerx, int centery,
|
|||
flipx, flipy);
|
||||
SDL_SetColorKey(rz_dst, /* SDL_SRCCOLORKEY */ SDL_TRUE | SDL_RLEACCEL, _colorkey(rz_src));
|
||||
}
|
||||
|
||||
/* copy alpha mod, color mod, and blend mode */
|
||||
{
|
||||
SDL_BlendMode blendMode;
|
||||
Uint8 alphaMod, cr, cg, cb;
|
||||
SDL_GetSurfaceAlphaMod(src, &alphaMod);
|
||||
SDL_GetSurfaceBlendMode(src, &blendMode);
|
||||
SDL_GetSurfaceColorMod(src, &cr, &cg, &cb);
|
||||
SDL_SetSurfaceAlphaMod(rz_dst, alphaMod);
|
||||
SDL_SetSurfaceBlendMode(rz_dst, blendMode);
|
||||
SDL_SetSurfaceColorMod(rz_dst, cr, cg, cb);
|
||||
}
|
||||
|
||||
/*
|
||||
* Unlock source surface
|
||||
*/
|
||||
|
|
@ -490,7 +485,7 @@ SDLgfx_rotateSurface(SDL_Surface * src, double angle, int centerx, int centery,
|
|||
/*
|
||||
* Cleanup temp surface
|
||||
*/
|
||||
if (src_converted) {
|
||||
if (rz_src != src) {
|
||||
SDL_FreeSurface(rz_src);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Simple DirectMedia Layer
|
||||
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
|
||||
Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any damages
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue