Fix VC7 project. Make rotozoom C++, updated, junk removed, single

zoom function, remove hack that causes image misalignment.
This commit is contained in:
Glenn Maynard
2002-10-28 06:19:23 +00:00
parent 73f7db6b15
commit 195772c720
4 changed files with 318 additions and 16 deletions
+6 -6
View File
@@ -281,13 +281,13 @@ void RageBitmapTexture::Create(
/* If zoomSurface is having problems with some pixel formats, this will
* sanitize it: */
/* if(img->format->BitsPerPixel == 8 || img->format->colorkey) {
if(img->format->BitsPerPixel == 8 || img->format->colorkey) {
int mask = 0;
SDL_Surface *dst = SDL_CreateRGBSurfaceSane(SDL_SWSURFACE, img->w, img->h, PixFmtMasks[target][4],
PixFmtMasks[target][0], PixFmtMasks[target][1], PixFmtMasks[target][2], PixFmtMasks[target][3]);
SDL_FreeSurface(img);
img = dst;
} */
/* resize currently doesn't do paletted */
if(img->format->BytesPerPixel == 1)
ConvertSDLSurface(img, img->w, img->h, PixFmtMasks[mask][4],
PixFmtMasks[mask][0], PixFmtMasks[mask][1], PixFmtMasks[mask][2], PixFmtMasks[mask][3]);
}
SDL_Surface *dst;
dst = zoomSurface(img, float(m_iTextureWidth)/m_iImageWidth,
float(m_iTextureHeight) / m_iImageHeight, SMOOTHING_ON);
+260
View File
@@ -0,0 +1,260 @@
/*
SDL_rotozoom.c - rotozoomer for 32bit or 8bit surfaces
LGPL (c) A. Schiffler
*/
#ifdef WIN32
#include <windows.h>
#endif
#include <stdlib.h>
#include <string.h>
#include "SDL_rotozoom.h"
typedef struct tColorRGBA {
Uint8 r;
Uint8 g;
Uint8 b;
Uint8 a;
} tColorRGBA;
typedef struct tColorY {
Uint8 y;
} tColorY;
#define MAX(a,b) (((a) > (b)) ? (a) : (b))
/*
32bit Zoomer with optional anti-aliasing by bilinear interpolation.
Zoomes 32bit RGBA/ABGR 'src' surface to 'dst' surface.
*/
int zoomSurfaceRGBA(SDL_Surface * src, SDL_Surface * dst, int smooth)
{
int x, y, sx, sy, *sax, *say;
tColorRGBA *c00, *c01, *c10, *c11;
/* Variable setup */
// if (smooth) {
/* For interpolation: assume source dimension is one pixel */
/* smaller to avoid overflow on right and bottom edge. */
/* XXX: no, this misaligns stuff; we need to clamp properly -glenn */
// sx = (int) (65536.0 * (float) (src->w - 1) / (float) dst->w);
// sy = (int) (65536.0 * (float) (src->h - 1) / (float) dst->h);
// } else {
sx = (int) (65536.0 * (float) src->w / (float) dst->w);
sy = (int) (65536.0 * (float) src->h / (float) dst->h);
//}
/*
* Allocate memory for row increments
*/
if ((sax = (int *) malloc((dst->w + 1) * sizeof(Uint32))) == NULL)
return (-1);
if ((say = (int *) malloc((dst->h + 1) * sizeof(Uint32))) == NULL) {
free(sax);
return (-1);
}
/*
* Precalculate row increments
*/
int csx = 0;
int *csax = sax;
for (x = 0; x <= dst->w; x++) {
*csax = csx;
csax++;
csx &= 0xffff;
csx += sx;
}
int csy = 0;
int *csay = say;
for (y = 0; y <= dst->h; y++) {
*csay = csy;
csay++;
csy &= 0xffff;
csy += sy;
}
/*
* Pointer setup
*/
tColorRGBA *sp, *csp, *dp;
sp = csp = (tColorRGBA *) src->pixels;
dp = (tColorRGBA *) dst->pixels;
int sgap = src->pitch - src->w * 4;
int dgap = dst->pitch - dst->w * 4;
/* Switch between interpolating and non-interpolating code */
csay = say;
if (smooth) {
/* Interpolating Zoom */
/* Scan destination */
for (y = 0; y < dst->h; y++) {
/*
* Setup color source pointers
*/
c00 = csp;
c01 = csp;
c01++;
c10 = (tColorRGBA *) ((Uint8 *) csp + src->pitch);
c11 = c10;
c11++;
csax = sax;
for (x = 0; x < dst->w; x++) {
/*
* Interpolate colors
*/
int ex = (*csax & 0xffff);
int ey = (*csay & 0xffff);
int t1, t2;
t1 = ((((c01->r - c00->r) * ex) >> 16) + c00->r) & 0xff;
t2 = ((((c11->r - c10->r) * ex) >> 16) + c10->r) & 0xff;
dp->r = (Uint8)((((t2 - t1) * ey) >> 16) + t1);
t1 = ((((c01->g - c00->g) * ex) >> 16) + c00->g) & 0xff;
t2 = ((((c11->g - c10->g) * ex) >> 16) + c10->g) & 0xff;
dp->g = (Uint8)((((t2 - t1) * ey) >> 16) + t1);
t1 = ((((c01->b - c00->b) * ex) >> 16) + c00->b) & 0xff;
t2 = ((((c11->b - c10->b) * ex) >> 16) + c10->b) & 0xff;
dp->b = (Uint8)((((t2 - t1) * ey) >> 16) + t1);
t1 = ((((c01->a - c00->a) * ex) >> 16) + c00->a) & 0xff;
t2 = ((((c11->a - c10->a) * ex) >> 16) + c10->a) & 0xff;
dp->a = (Uint8)((((t2 - t1) * ey) >> 16) + t1);
/*
* Advance source pointers
*/
csax++;
int sstep = (*csax >> 16);
c00 += sstep;
c01 += sstep;
c10 += sstep;
c11 += sstep;
/*
* Advance destination pointer
*/
dp++;
}
/*
* Advance source pointer
*/
csay++;
csp = (tColorRGBA *) ((Uint8 *) csp + (*csay >> 16) * src->pitch);
/*
* Advance destination pointers
*/
dp = (tColorRGBA *) ((Uint8 *) dp + dgap);
}
} else {
/* Non-Interpolating Zoom */
for (y = 0; y < dst->h; y++) {
sp = csp;
csax = sax;
for (x = 0; x < dst->w; x++) {
/* Draw */
*dp = *sp;
/* Advance source pointers */
csax++;
sp += (*csax >> 16);
/* Advance destination pointer */
dp++;
}
/* Advance source pointer */
csay++;
csp = (tColorRGBA *) ((Uint8 *) csp + (*csay >> 16) * src->pitch);
/* Advance destination pointers */
dp = (tColorRGBA *) ((Uint8 *) dp + dgap);
}
}
/*
* Remove temp arrays
*/
free(sax);
free(say);
return (0);
}
#define VALUE_LIMIT 0.001
/* Local rotozoom-size function with trig result return */
/*
zoomSurface()
Zoomes a 32bit or 8bit 'src' surface to newly created 'dst' surface.
'zoomx' and 'zoomy' are scaling factors for width and height. If 'smooth' is 1
then the destination 32bit surface is anti-aliased. If the surface is not 8bit
or 32bit RGBA/ABGR it will be converted into a 32bit RGBA format on the fly.
*/
void zoomSurfaceSize(int width, int height, double zoomx, double zoomy, int *dstwidth, int *dstheight)
{
/*
* Sanity check zoom factors
*/
if (zoomx < VALUE_LIMIT) zoomx = VALUE_LIMIT;
if (zoomy < VALUE_LIMIT) zoomy = VALUE_LIMIT;
/* Calculate target size */
*dstwidth = (int) ((double) width * zoomx);
*dstheight = (int) ((double) height * zoomy);
if (*dstwidth < 1) *dstwidth = 1;
if (*dstheight < 1) *dstheight = 1;
}
SDL_Surface *zoomSurface(SDL_Surface * src, double zoomx, double zoomy, int smooth)
{
SDL_Surface *rz_dst;
int dstwidth, dstheight;
/*
* Sanity check
*/
if (src == NULL)
return (NULL);
/* Get size if target */
zoomSurfaceSize(src->w, src->h, zoomx, zoomy, &dstwidth, &dstheight);
/* Alloc space to completely contain the zoomed surface */
/* Target surface is 32bit with source RGBA/ABGR ordering */
rz_dst =
SDL_CreateRGBSurface(SDL_SWSURFACE, dstwidth, dstheight, 32,
src->format->Rmask, src->format->Gmask,
src->format->Bmask, src->format->Amask);
/*
* Lock source surface
*/
SDL_LockSurface(src);
/* Call the 32bit transformation routine to do the zooming (using alpha) */
zoomSurfaceRGBA(src, rz_dst, smooth);
/* Turn on source-alpha support */
SDL_SetAlpha(rz_dst, SDL_SRCALPHA, 255);
/* Unlock source surface */
SDL_UnlockSurface(src);
/* Return destination surface */
return (rz_dst);
}
+39 -9
View File
@@ -1,14 +1,27 @@
#ifndef _SDL_rotozoom_h
#define _SDL_rotozoom_h
/*
SDL_rotozoom - rotozoomer
LGPL (c) A. Schiffler
*/
#ifndef SDL_rotozoom_h
#define SDL_rotozoom_h
/* Set up for C function definitions, even when using C++ */
#ifdef __cplusplus
extern "C"
{
extern "C" {
#endif
#include <math.h>
#ifndef M_PI
#define M_PI 3.141592654
#endif
#include "SDL.h"
/* ---- Defines */
#define SMOOTHING_OFF 0
@@ -16,6 +29,16 @@ extern "C"
/* ---- Prototypes */
/* #ifdef WIN32
#ifdef BUILD_DLL
#define DLLINTERFACE __declspec(dllexport)
#else
#define DLLINTERFACE __declspec(dllimport)
#endif
#else */
#define DLLINTERFACE
/* #endif */
/*
rotozoomSurface()
@@ -27,10 +50,14 @@ extern "C"
*/
SDL_Surface *rotozoomSurface (const SDL_Surface * src, double angle, double zoom,
int smooth);
DLLINTERFACE SDL_Surface *rotozoomSurface(SDL_Surface * src, double angle, double zoom, int smooth);
/* Returns the size of the target surface for a rotozoomSurface() call */
DLLINTERFACE void rotozoomSurfaceSize(int width, int height, double angle, double zoom, int *dstwidth,
int *dstheight);
/*
zoomSurface()
@@ -42,8 +69,11 @@ extern "C"
*/
SDL_Surface *zoomSurface (const SDL_Surface * src, double zoomx, double zoomy,
int smooth);
DLLINTERFACE SDL_Surface *zoomSurface(SDL_Surface * src, double zoomx, double zoomy, int smooth);
/* Returns the size of the target surface for a zoomSurface() call */
DLLINTERFACE void zoomSurfaceSize(int width, int height, double zoomx, double zoomy, int *dstwidth, int *dstheight);
/* Ends C function definitions when using C++ */
@@ -51,4 +81,4 @@ extern "C"
};
#endif
#endif /* _SDL_rotozoom_h */
#endif /* _SDL_rotozoom_h */
+13 -1
View File
@@ -271,6 +271,12 @@ cl /Zl /nologo /c verstub.cpp /Fo$(IntDir)\
<File
RelativePath="ScreenMusicScroll.h">
</File>
<File
RelativePath="ScreenNetworkGame.cpp">
</File>
<File
RelativePath="ScreenNetworkGame.h">
</File>
<File
RelativePath="ScreenOptions.cpp">
</File>
@@ -1001,6 +1007,12 @@ cl /Zl /nologo /c verstub.cpp /Fo$(IntDir)\
<File
RelativePath=".\RageMusic.h">
</File>
<File
RelativePath="RageNetwork.cpp">
</File>
<File
RelativePath="RageNetwork.h">
</File>
<File
RelativePath=".\RageSound.cpp">
</File>
@@ -1056,7 +1068,7 @@ cl /Zl /nologo /c verstub.cpp /Fo$(IntDir)\
RelativePath="SDL_dither.h">
</File>
<File
RelativePath="SDL_rotozoom.c">
RelativePath="SDL_rotozoom.cpp">
</File>
<File
RelativePath="SDL_rotozoom.h">