/* * SDL Graphics Extension * Drawing primitives * * Started 990815 (split from sge_draw 010611) * * License: LGPL v2+ (see the file LICENSE) * (c)1999-2001 Anders Lindström */ /********************************************************************* * This library is free software; you can redistribute it and/or * * modify it under the terms of the GNU Library General Public * * License as published by the Free Software Foundation; either * * version 2 of the License, or (at your option) any later version. * *********************************************************************/ /* * Some of this code is taken from the "Introduction to SDL" and * John Garrison's PowerPak */ #include "SDL.h" #include #include #include #include "sge_primitives.h" #include "sge_surface.h" /* Globals used for sge_Update/sge_Lock (defined in sge_surface) */ extern Uint8 _sge_update; extern Uint8 _sge_lock; /**********************************************************************************/ /** Line functions **/ /**********************************************************************************/ //================================================================================== // Internal draw horizontal line //================================================================================== void _HLine(SDL_Surface *Surface, Sint16 x1, Sint16 x2, Sint16 y, Uint32 Color) { if(x1>x2){Sint16 tmp=x1; x1=x2; x2=tmp;} //Do the clipping #if SDL_VERSIONNUM(SDL_MAJOR_VERSION, SDL_MINOR_VERSION, SDL_PATCHLEVEL) < \ SDL_VERSIONNUM(1, 1, 5) if(yclip_miny || y>Surface->clip_maxy || x1>Surface->clip_maxx || x2clip_minx) return; if(x1clip_minx) x1=Surface->clip_minx; if(x2>Surface->clip_maxx) x2=Surface->clip_maxx; #endif SDL_Rect l; l.x=x1; l.y=y; l.w=x2-x1+1; l.h=1; SDL_FillRect(Surface, &l, Color); } //================================================================================== // Draw horizontal line //================================================================================== void sge_HLine(SDL_Surface *Surface, Sint16 x1, Sint16 x2, Sint16 y, Uint32 Color) { if(x1>x2){Sint16 tmp=x1; x1=x2; x2=tmp;} //Do the clipping #if SDL_VERSIONNUM(SDL_MAJOR_VERSION, SDL_MINOR_VERSION, SDL_PATCHLEVEL) < \ SDL_VERSIONNUM(1, 1, 5) if(yclip_miny || y>Surface->clip_maxy || x1>Surface->clip_maxx || x2clip_minx) return; if(x1clip_minx) x1=Surface->clip_minx; if(x2>Surface->clip_maxx) x2=Surface->clip_maxx; #endif SDL_Rect l; l.x=x1; l.y=y; l.w=x2-x1+1; l.h=1; SDL_FillRect(Surface, &l, Color); sge_UpdateRect(Surface, x1, y, x2-x1+1, 1); } //================================================================================== // Draw horizontal line (RGB) //================================================================================== void sge_HLine(SDL_Surface *Surface, Sint16 x1, Sint16 x2, Sint16 y, Uint8 R, Uint8 G, Uint8 B) { sge_HLine(Surface,x1,x2,y, SDL_MapRGB(Surface->format, R, G, B)); } //================================================================================== // Internal draw horizontal line (alpha) //================================================================================== void _HLineAlpha(SDL_Surface *Surface, Sint16 x1, Sint16 x2, Sint16 y, Uint32 Color, Uint8 alpha) { Uint8 update = _sge_update; Uint8 lock = _sge_lock; _sge_update = 0; _sge_lock = 0; sge_FilledRectAlpha(Surface, x1,y,x2,y, Color, alpha); _sge_update = update; _sge_lock = lock; } //================================================================================== // Draw horizontal line (alpha) //================================================================================== void sge_HLineAlpha(SDL_Surface *Surface, Sint16 x1, Sint16 x2, Sint16 y, Uint32 Color, Uint8 alpha) { sge_FilledRectAlpha(Surface, x1,y,x2,y, Color, alpha); } //================================================================================== // Draw horizontal line (alpha RGB) //================================================================================== void sge_HLineAlpha(SDL_Surface *Surface, Sint16 x1, Sint16 x2, Sint16 y, Uint8 R, Uint8 G, Uint8 B, Uint8 alpha) { sge_HLineAlpha(Surface,x1,x2,y, SDL_MapRGB(Surface->format, R, G, B), alpha); } //================================================================================== // Internal draw vertical line //================================================================================== void _VLine(SDL_Surface *Surface, Sint16 x, Sint16 y1, Sint16 y2, Uint32 Color) { if(y1>y2){Sint16 tmp=y1; y1=y2; y2=tmp;} //Do the clipping #if SDL_VERSIONNUM(SDL_MAJOR_VERSION, SDL_MINOR_VERSION, SDL_PATCHLEVEL) < \ SDL_VERSIONNUM(1, 1, 5) if(xclip_minx || x>Surface->clip_maxx || y1>Surface->clip_maxy || y2clip_miny) return; if(y1clip_miny) y1=Surface->clip_miny; if(y2>Surface->clip_maxy) y2=Surface->clip_maxy; #endif SDL_Rect l; l.x=x; l.y=y1; l.w=1; l.h=y2-y1+1; SDL_FillRect(Surface, &l, Color); } //================================================================================== // Draw vertical line //================================================================================== void sge_VLine(SDL_Surface *Surface, Sint16 x, Sint16 y1, Sint16 y2, Uint32 Color) { if(y1>y2){Sint16 tmp=y1; y1=y2; y2=tmp;} //Do the clipping #if SDL_VERSIONNUM(SDL_MAJOR_VERSION, SDL_MINOR_VERSION, SDL_PATCHLEVEL) < \ SDL_VERSIONNUM(1, 1, 5) if(xclip_minx || x>Surface->clip_maxx || y1>Surface->clip_maxy || y2clip_miny) return; if(y1clip_miny) y1=Surface->clip_miny; if(y2>Surface->clip_maxy) y2=Surface->clip_maxy; #endif SDL_Rect l; l.x=x; l.y=y1; l.w=1; l.h=y2-y1+1; SDL_FillRect(Surface, &l, Color); sge_UpdateRect(Surface, x, y1, 1, y2-y1+1); } //================================================================================== // Draw vertical line (RGB) //================================================================================== void sge_VLine(SDL_Surface *Surface, Sint16 x, Sint16 y1, Sint16 y2, Uint8 R, Uint8 G, Uint8 B) { sge_VLine(Surface,x,y1,y2, SDL_MapRGB(Surface->format, R, G, B)); } //================================================================================== // Internal draw vertical line (alpha - no update) //================================================================================== void _VLineAlpha(SDL_Surface *Surface, Sint16 x, Sint16 y1, Sint16 y2, Uint32 Color, Uint8 alpha) { Uint8 update = _sge_update; Uint8 lock = _sge_lock; _sge_update = 0; _sge_lock = 0; sge_FilledRectAlpha(Surface, x,y1,x,y2, Color, alpha); _sge_update = update; _sge_lock = lock; } //================================================================================== // Draw vertical line (alpha) //================================================================================== void sge_VLineAlpha(SDL_Surface *Surface, Sint16 x, Sint16 y1, Sint16 y2, Uint32 Color, Uint8 alpha) { sge_FilledRectAlpha(Surface, x,y1,x,y2, Color, alpha); } //================================================================================== // Draw vertical line (alpha RGB) //================================================================================== void sge_VLineAlpha(SDL_Surface *Surface, Sint16 x, Sint16 y1, Sint16 y2, Uint8 R, Uint8 G, Uint8 B, Uint8 alpha) { sge_VLineAlpha(Surface,x,y1,y2, SDL_MapRGB(Surface->format, R, G, B), alpha); } //================================================================================== // Performs Callback at each line point. (From PowerPak) //================================================================================== void sge_DoLine(SDL_Surface *Surface, Sint16 x1, Sint16 y1, Sint16 x2, Sint16 y2, Uint32 Color, void Callback(SDL_Surface *Surf, Sint16 X, Sint16 Y, Uint32 Color)) { Sint16 dx, dy, sdx, sdy, x, y, px, py; dx = x2 - x1; dy = y2 - y1; sdx = (dx < 0) ? -1 : 1; sdy = (dy < 0) ? -1 : 1; dx = sdx * dx + 1; dy = sdy * dy + 1; x = y = 0; px = x1; py = y1; if (dx >= dy){ for (x = 0; x < dx; x++){ Callback(Surface, px, py, Color); y += dy; if (y >= dx){ y -= dx; py += sdy; } px += sdx; } } else{ for (y = 0; y < dy; y++){ Callback(Surface, px, py, Color); x += dx; if (x >= dy){ x -= dy; px += sdx; } py += sdy; } } } //================================================================================== // Performs Callback at each line point. (RGB) //================================================================================== void sge_DoLine(SDL_Surface *Surface, Sint16 X1, Sint16 Y1, Sint16 X2, Sint16 Y2, Uint8 R, Uint8 G, Uint8 B, void Callback(SDL_Surface *Surf, Sint16 X, Sint16 Y, Uint32 Color)) { sge_DoLine(Surface,X1,Y1,X2,Y2, SDL_MapRGB(Surface->format, R, G, B),Callback); } //================================================================================== // Draws a line //================================================================================== void _Line(SDL_Surface *surface, Sint16 x1, Sint16 y1, Sint16 x2, Sint16 y2, Uint32 color) { /* Clipping */ if(x2sge_clip_xmax(surface) || y2sge_clip_ymax(surface)) return; if (x1 < sge_clip_xmin(surface)) x1 = sge_clip_xmin(surface); if (x2 > sge_clip_xmax(surface)) x2 = sge_clip_xmax(surface); if (y1 < sge_clip_ymin(surface)) y1 = sge_clip_ymin(surface); if (y2 > sge_clip_ymax(surface)) y2 = sge_clip_ymax(surface); Sint16 dx, dy, sdx, sdy, x, y; dx = x2 - x1; dy = y2 - y1; sdx = (dx < 0) ? -1 : 1; sdy = (dy < 0) ? -1 : 1; dx = sdx * dx + 1; dy = sdy * dy + 1; x = y = 0; Sint16 pixx = surface->format->BytesPerPixel; Sint16 pixy = surface->pitch; Uint8 *pixel = (Uint8*)surface->pixels + y1*pixy + x1*pixx; pixx *= sdx; pixy *= sdy; if (dx < dy) { Sint32 tmp = dx; dx = dy; dy = Sint16(tmp); tmp = pixx; pixx = pixy; pixy = tmp; } switch(surface->format->BytesPerPixel) { case 1: { for(x=0; x < dx; x++) { *pixel = color; y += dy; if (y >= dx) { y -= dx; pixel += pixy; } pixel += pixx; } } break; case 2: { for(x=0; x < dx; x++) { *(Uint16*)pixel = color; y += dy; if (y >= dx) { y -= dx; pixel += pixy; } pixel += pixx; } } break; case 3: { Uint8 rshift8 = surface->format->Rshift/8; Uint8 gshift8 = surface->format->Gshift/8; Uint8 bshift8 = surface->format->Bshift/8; Uint8 ashift8 = surface->format->Ashift/8; Uint8 R = (color>>surface->format->Rshift)&0xff; Uint8 G = (color>>surface->format->Gshift)&0xff; Uint8 B = (color>>surface->format->Bshift)&0xff; Uint8 A = (color>>surface->format->Ashift)&0xff; for(x=0; x < dx; x++) { *(pixel+rshift8) = R; *(pixel+gshift8) = G; *(pixel+bshift8) = B; *(pixel+ashift8) = A; y += dy; if (y >= dx) { y -= dx; pixel += pixy; } pixel += pixx; } } break; case 4: { for(x=0; x < dx; x++) { *(Uint32*)pixel = color; y += dy; if (y >= dx) { y -= dx; pixel += pixy; } pixel += pixx; } } break; } } void sge_Line(SDL_Surface *Surface, Sint16 x1, Sint16 y1, Sint16 x2, Sint16 y2, Uint32 Color) { if (SDL_MUSTLOCK(Surface) && _sge_lock) { if (SDL_LockSurface(Surface) < 0) return; } /* Draw the line */ _Line(Surface, x1,y1, x2,y2, Color); /* unlock the display */ if (SDL_MUSTLOCK(Surface) && _sge_lock) { SDL_UnlockSurface(Surface); } sge_UpdateRect(Surface, (x1 < x2)? x1 : x2, (y1 < y2)? y1 : y2, ((x2-x1)<0)? (x1-x2+1) : (x2-x1+1), ((y2-y1)<0)? (y1-y2+1) : (y2-y1+1)); } //================================================================================== // Draws a line (RGB) //================================================================================== void sge_Line(SDL_Surface *Surface, Sint16 x1, Sint16 y1, Sint16 x2, Sint16 y2, Uint8 R, Uint8 G, Uint8 B) { sge_Line(Surface,x1,y1,x2,y2, SDL_MapRGB(Surface->format, R, G, B)); } //================================================================================== // A quick hack to get alpha working with callbacks //================================================================================== Uint8 _sge_alpha_hack = 0; void callback_alpha_hack(SDL_Surface *surf, Sint16 x, Sint16 y, Uint32 color) { _PutPixelAlpha(surf,x,y,color,_sge_alpha_hack); } //================================================================================== // Draws a line (alpha) //================================================================================== void sge_LineAlpha(SDL_Surface *Surface, Sint16 x1, Sint16 y1, Sint16 x2, Sint16 y2, Uint32 Color, Uint8 alpha) { if (SDL_MUSTLOCK(Surface) && _sge_lock) if (SDL_LockSurface(Surface) < 0) return; _sge_alpha_hack = alpha; /* Draw the line */ sge_DoLine(Surface, x1, y1, x2, y2, Color, callback_alpha_hack); /* unlock the display */ if (SDL_MUSTLOCK(Surface) && _sge_lock) { SDL_UnlockSurface(Surface); } sge_UpdateRect(Surface, (x1 < x2)? x1 : x2, (y1 < y2)? y1 : y2, ((x2-x1)<0)? (x1-x2+1) : (x2-x1+1), ((y2-y1)<0)? (y1-y2+1) : (y2-y1+1)); } //================================================================================== // Draws a line (alpha - RGB) //================================================================================== void sge_LineAlpha(SDL_Surface *Surface, Sint16 x1, Sint16 y1, Sint16 x2, Sint16 y2, Uint8 R, Uint8 G, Uint8 B, Uint8 alpha) { sge_LineAlpha(Surface,x1,y1,x2,y2, SDL_MapRGB(Surface->format, R, G, B), alpha); } //================================================================================== // Anti-aliased line // From SDL_gfxPrimitives written by A. Schiffler (aschiffler@home.com) //================================================================================== #define AAbits 8 #define AAlevels 256 /* 2^AAbits */ void sge_AALineAlpha(SDL_Surface *dst, Sint16 x1, Sint16 y1, Sint16 x2, Sint16 y2, Uint32 color, Uint8 alpha) { Sint32 xx0,yy0,xx1,yy1; Uint32 intshift, erracc=0, erradj; Uint32 erracctmp, wgt, wgtcompmask; Sint16 dx, dy, tmp, xdir, y0p1, x0pxdir; /* Keep on working with 32bit numbers */ xx0=x1; yy0=y1; xx1=x2; yy1=y2; /* Reorder points if required */ if (yy0 > yy1) { tmp = yy0; yy0 = yy1; yy1 = tmp; tmp = xx0; xx0 = xx1; xx1 = tmp; } /* Calculate distance */ dx = xx1 - xx0; dy = yy1 - yy0; /* Adjust for negative dx and set xdir */ if (dx >= 0) { xdir=1; } else { xdir=-1; dx=(-dx); } /* Check for special cases */ if (dx==0) { /* Vertical line */ sge_VLineAlpha(dst, x1,y1,y2,color,alpha); return; } else if (dy==0) { /* Horizontal line */ sge_HLineAlpha(dst, x1,x2,y1,color,alpha); return; } else if (dx==dy) { /* Diagonal line */ if(alpha==255) sge_Line(dst,x1,y1,x2,y2,color); else sge_LineAlpha(dst,x1,y1,x2,y2,color,alpha); return; } Uint8 a = 255-alpha; /* Lock surface */ if ( SDL_MUSTLOCK(dst) && _sge_lock ) if ( SDL_LockSurface(dst) < 0 ) return; intshift = 32 - AAbits; /* # of bits by which to shift erracc to get intensity level */ wgtcompmask = AAlevels - 1; /* Mask used to flip all bits in an intensity weighting */ if(alpha==255) _PutPixel(dst,x1,y1, color); /* Draw the initial pixel in the foreground color */ else _PutPixelAlpha(dst,x1,y1, color, alpha); /* x-major or y-major? */ if (dy > dx) { /* y-major. Calculate 16-bit fixed point fractional part of a pixel that X advances every time Y advances 1 pixel, truncating the result so that we won't overrun the endpoint along the X axis */ erradj = ((dx << 16) / dy)<<16; /* draw all pixels other than the first and last */ x0pxdir=xx0+xdir; while (--dy) { erracctmp = erracc; erracc += erradj; if (erracc <= erracctmp) { /* rollover in error accumulator, x coord advances */ xx0=x0pxdir; x0pxdir += xdir; } yy0++; /* y-major so always advance Y */ /* the AAbits most significant bits of erracc give us the intensity weighting for this pixel, and the complement of the weighting for the paired pixel. */ wgt = (erracc >> intshift) & 255; tmp = 255-wgt-a; if(tmp<0) tmp=0; _PutPixelAlpha(dst,xx0,yy0,color,Uint8(tmp)); tmp = wgt-a; if(tmp<0) tmp=0; _PutPixelAlpha(dst,x0pxdir,yy0,color,Uint8(tmp)); } } else { /* x-major line. Calculate 16-bit fixed-point fractional part of a pixel that Y advances each time X advances 1 pixel, truncating the result so that we won't overrun the endpoint along the X axis. */ erradj = ((dy << 16) / dx)<<16; /* draw all pixels other than the first and last */ y0p1=yy0+1; while (--dx) { erracctmp = erracc; erracc += erradj; if (erracc <= erracctmp) { /* Accumulator turned over, advance y */ yy0=y0p1; y0p1++; } xx0 += xdir; /* x-major so always advance X */ /* the AAbits most significant bits of erracc give us the intensity weighting for this pixel, and the complement of the weighting for the paired pixel. */ wgt = (erracc >> intshift) & 255; tmp = 255-wgt-a; if(tmp<0) tmp=0; _PutPixelAlpha(dst,xx0,yy0,color,tmp); tmp = wgt-a; if(tmp<0) tmp=0; _PutPixelAlpha(dst,xx0,y0p1,color,tmp); } } /* Draw final pixel, always exactly intersected by the line and doesn't need to be weighted. */ if(alpha==255) _PutPixel(dst,x2,y2, color); else _PutPixelAlpha(dst,x2,y2, color, alpha); /* unlock the display */ if (SDL_MUSTLOCK(dst) && _sge_lock) { SDL_UnlockSurface(dst); } sge_UpdateRect(dst, (x1 < x2)? x1 : x2, (y1 < y2)? y1 : y2, ((x2-x1)<0)? (x1-x2+1) : (x2-x1+1), ((y2-y1)<0)? (y1-y2+1) : (y2-y1+1)); } void sge_AALineAlpha(SDL_Surface *dst, Sint16 x1, Sint16 y1, Sint16 x2, Sint16 y2, Uint8 r, Uint8 g, Uint8 b, Uint8 alpha) { sge_AALineAlpha(dst,x1,y1,x2,y2,SDL_MapRGB(dst->format, r, g, b),alpha); } void sge_AALine(SDL_Surface *dst, Sint16 x1, Sint16 y1, Sint16 x2, Sint16 y2, Uint32 color) { sge_AALineAlpha(dst, x1,y1, x2,y2, color, 255); } void sge_AALine(SDL_Surface *dst, Sint16 x1, Sint16 y1, Sint16 x2, Sint16 y2, Uint8 r, Uint8 g, Uint8 b) { sge_AALineAlpha(dst,x1,y1,x2,y2,SDL_MapRGB(dst->format, r, g, b),255); } /**********************************************************************************/ /** Figure functions **/ /**********************************************************************************/ //================================================================================== // Draws a rectangle //================================================================================== void sge_Rect(SDL_Surface *Surface, Sint16 x1, Sint16 y1, Sint16 x2, Sint16 y2, Uint32 color) { _HLine(Surface,x1,x2,y1,color); _HLine(Surface,x1,x2,y2,color); _VLine(Surface,x1,y1,y2,color); _VLine(Surface,x2,y1,y2,color); sge_UpdateRect(Surface, x1, y1, x2-x1, 1); sge_UpdateRect(Surface, x1, y2, x2-x1+1, 1); /* Hmm? */ sge_UpdateRect(Surface, x1, y1, 1, y2-y1); sge_UpdateRect(Surface, x2, y1, 1, y2-y1); } //================================================================================== // Draws a rectangle (RGB) //================================================================================== void sge_Rect(SDL_Surface *Surface, Sint16 x1, Sint16 y1, Sint16 x2, Sint16 y2, Uint8 R, Uint8 G, Uint8 B) { sge_Rect(Surface,x1,y1,x2,y2, SDL_MapRGB(Surface->format, R, G, B)); } //================================================================================== // Draws a rectangle (alpha) //================================================================================== void sge_RectAlpha(SDL_Surface *Surface, Sint16 x1, Sint16 y1, Sint16 x2, Sint16 y2, Uint32 color, Uint8 alpha) { if (SDL_MUSTLOCK(Surface) && _sge_lock) if (SDL_LockSurface(Surface) < 0) return; _HLineAlpha(Surface,x1,x2,y1,color,alpha); _HLineAlpha(Surface,x1,x2,y2,color,alpha); _VLineAlpha(Surface,x1,y1,y2,color,alpha); _VLineAlpha(Surface,x2,y1,y2,color,alpha); if (SDL_MUSTLOCK(Surface) && _sge_lock) { SDL_UnlockSurface(Surface); } sge_UpdateRect(Surface, x1, y1, x2-x1, 1); sge_UpdateRect(Surface, x1, y2, x2-x1+1, 1); /* Hmm? */ sge_UpdateRect(Surface, x1, y1, 1, y2-y1); sge_UpdateRect(Surface, x2, y1, 1, y2-y1); } //================================================================================== // Draws a rectangle (RGB) //================================================================================== void sge_RectAlpha(SDL_Surface *Surface, Sint16 x1, Sint16 y1, Sint16 x2, Sint16 y2, Uint8 R, Uint8 G, Uint8 B, Uint8 alpha) { sge_RectAlpha(Surface,x1,y1,x2,y2, SDL_MapRGB(Surface->format, R, G, B), alpha); } //================================================================================== // Draws a filled rectangle //================================================================================== void sge_FilledRect(SDL_Surface *Surface, Sint16 x1, Sint16 y1, Sint16 x2, Sint16 y2, Uint32 color) { Sint16 tmp; if(x1>x2){ tmp=x1; x1=x2; x2=tmp; } if(y1>y2){ tmp=y1; y1=y2; y2=tmp; } #if SDL_VERSIONNUM(SDL_MAJOR_VERSION, SDL_MINOR_VERSION, SDL_PATCHLEVEL) < \ SDL_VERSIONNUM(1, 1, 5) if(x2clip_minx || x1>Surface->clip_maxx || y2clip_miny || y1>Surface->clip_maxy) return; if (x1 < Surface->clip_minx) x1=Surface->clip_minx; if (x2 > Surface->clip_maxx) x2=Surface->clip_maxx; if (y1 < Surface->clip_miny) y1=Surface->clip_miny; if (y2 > Surface->clip_maxy) y2=Surface->clip_maxy; #endif SDL_Rect area; area.x=x1; area.y=y1; area.w=x2-x1+1; area.h=y2-y1+1; SDL_FillRect(Surface,&area,color); sge_UpdateRect(Surface, x1, y1, x2-x1+1, y2-y1+1); } //================================================================================== // Draws a filled rectangle (RGB) //================================================================================== void sge_FilledRect(SDL_Surface *Surface, Sint16 x1, Sint16 y1, Sint16 x2, Sint16 y2, Uint8 R, Uint8 G, Uint8 B) { sge_FilledRect(Surface,x1,y1,x2,y2, SDL_MapRGB(Surface->format, R, G, B)); } //================================================================================== // Draws a filled rectangle (alpha) //================================================================================== void sge_FilledRectAlpha(SDL_Surface *surface, Sint16 x1, Sint16 y1, Sint16 x2, Sint16 y2, Uint32 color, Uint8 alpha) { /*if( alpha == 255 ){ sge_FilledRect(surface,x1,y1,x2,y2,color); return; }*/ /* Fix coords */ Sint16 tmp; if(x1>x2){ tmp=x1; x1=x2; x2=tmp; } if(y1>y2){ tmp=y1; y1=y2; y2=tmp; } /* Clipping */ if(x2sge_clip_xmax(surface) || y2sge_clip_ymax(surface)) return; if (x1 < sge_clip_xmin(surface)) x1 = sge_clip_xmin(surface); if (x2 > sge_clip_xmax(surface)) x2 = sge_clip_xmax(surface); if (y1 < sge_clip_ymin(surface)) y1 = sge_clip_ymin(surface); if (y2 > sge_clip_ymax(surface)) y2 = sge_clip_ymax(surface); Uint32 Rmask = surface->format->Rmask, Gmask = surface->format->Gmask, Bmask = surface->format->Bmask, Amask = surface->format->Amask; Uint32 R,G,B,A=0; Sint16 x,y; if (SDL_MUSTLOCK(surface) && _sge_lock) if (SDL_LockSurface(surface) < 0) return; switch (surface->format->BytesPerPixel) { case 1: { /* Assuming 8-bpp */ Uint8 *row, *pixel; Uint8 dR, dG, dB; Uint8 sR = surface->format->palette->colors[color].r; Uint8 sG = surface->format->palette->colors[color].g; Uint8 sB = surface->format->palette->colors[color].b; for(y = y1; y<=y2; y++){ row = (Uint8 *)surface->pixels + y*surface->pitch; for(x = x1; x <= x2; x++){ pixel = row + x; dR = surface->format->palette->colors[*pixel].r; dG = surface->format->palette->colors[*pixel].g; dB = surface->format->palette->colors[*pixel].b; dR = dR + ((sR-dR)*alpha >> 8); dG = dG + ((sG-dG)*alpha >> 8); dB = dB + ((sB-dB)*alpha >> 8); *pixel = SDL_MapRGB(surface->format, dR, dG, dB); } } } break; case 2: { /* Probably 15-bpp or 16-bpp */ Uint16 *row, *pixel; Uint32 dR=(color & Rmask),dG=(color & Gmask),dB=(color & Bmask),dA=(color & Amask); for(y = y1; y<=y2; y++){ row = (Uint16 *)surface->pixels + y*surface->pitch/2; for(x = x1; x <= x2; x++){ pixel = row + x; R = ((*pixel & Rmask) + (( dR - (*pixel & Rmask) ) * alpha >> 8)) & Rmask; G = ((*pixel & Gmask) + (( dG - (*pixel & Gmask) ) * alpha >> 8)) & Gmask; B = ((*pixel & Bmask) + (( dB - (*pixel & Bmask) ) * alpha >> 8)) & Bmask; if( Amask ) A = ((*pixel & Amask) + (( dA - (*pixel & Amask) ) * alpha >> 8)) & Amask; *pixel= R | G | B | A; } } } break; case 3: { /* Slow 24-bpp mode, usually not used */ Uint8 *row,*pix; Uint8 dR, dG, dB, dA; Uint8 rshift8=surface->format->Rshift/8; Uint8 gshift8=surface->format->Gshift/8; Uint8 bshift8=surface->format->Bshift/8; Uint8 ashift8=surface->format->Ashift/8; Uint8 sR = (color>>surface->format->Rshift)&0xff; Uint8 sG = (color>>surface->format->Gshift)&0xff; Uint8 sB = (color>>surface->format->Bshift)&0xff; Uint8 sA = (color>>surface->format->Ashift)&0xff; for(y = y1; y<=y2; y++){ row = (Uint8 *)surface->pixels + y * surface->pitch; for(x = x1; x <= x2; x++){ pix = row + x*3; dR = *((pix)+rshift8); dG = *((pix)+gshift8); dB = *((pix)+bshift8); dA = *((pix)+ashift8); dR = dR + ((sR-dR)*alpha >> 8); dG = dG + ((sG-dG)*alpha >> 8); dB = dB + ((sB-dB)*alpha >> 8); dA = dA + ((sA-dA)*alpha >> 8); *((pix)+rshift8) = dR; *((pix)+gshift8) = dG; *((pix)+bshift8) = dB; *((pix)+ashift8) = dA; } } } break; case 4: { /* Probably 32-bpp */ Uint32 *row, *pixel; Uint32 dR=(color & Rmask),dG=(color & Gmask),dB=(color & Bmask),dA=(color & Amask); for(y = y1; y<=y2; y++){ row = (Uint32 *)surface->pixels + y*surface->pitch/4; for(x = x1; x <= x2; x++){ pixel = row + x; R = ((*pixel & Rmask) + (( dR - (*pixel & Rmask) ) * alpha >> 8)) & Rmask; G = ((*pixel & Gmask) + (( dG - (*pixel & Gmask) ) * alpha >> 8)) & Gmask; B = ((*pixel & Bmask) + (( dB - (*pixel & Bmask) ) * alpha >> 8)) & Bmask; if( Amask ) A = ((*pixel & Amask) + (( dA - (*pixel & Amask) ) * alpha >> 8)) & Amask; *pixel= R | G | B | A; } } } break; } if (SDL_MUSTLOCK(surface) && _sge_lock) { SDL_UnlockSurface(surface); } sge_UpdateRect(surface, x1, y1, x2-x1+1, y2-y1+1); } void sge_FilledRectAlpha(SDL_Surface *Surface, Sint16 x1, Sint16 y1, Sint16 x2, Sint16 y2, Uint8 R, Uint8 G, Uint8 B, Uint8 alpha) { sge_FilledRectAlpha(Surface,x1,y1,x2,y2, SDL_MapRGB(Surface->format, R, G, B), alpha); } //================================================================================== // Performs Callback at each ellipse point. // (from Allegro) //================================================================================== void sge_DoEllipse(SDL_Surface *Surface, Sint16 x, Sint16 y, Sint16 rx, Sint16 ry, Uint32 color, void Callback(SDL_Surface *Surf, Sint16 X, Sint16 Y, Uint32 Color) ) { int ix, iy; int h, i, j, k; int oh, oi, oj, ok; if (rx < 1) rx = 1; if (ry < 1) ry = 1; h = i = j = k = 0xFFFF; if (rx > ry) { ix = 0; iy = rx * 64; do { oh = h; oi = i; oj = j; ok = k; h = (ix + 32) >> 6; i = (iy + 32) >> 6; j = (h * ry) / rx; k = (i * ry) / rx; if (((h != oh) || (k != ok)) && (h < oi)) { Callback(Surface, x+h, y+k, color); if (h) Callback(Surface, x-h, y+k, color); if (k) { Callback(Surface, x+h, y-k, color); if (h) Callback(Surface, x-h, y-k, color); } } if (((i != oi) || (j != oj)) && (h < i)) { Callback(Surface, x+i, y+j, color); if (i) Callback(Surface, x-i, y+j, color); if (j) { Callback(Surface, x+i, y-j, color); if (i) Callback(Surface, x-i, y-j, color); } } ix = ix + iy / rx; iy = iy - ix / rx; } while (i > h); } else { ix = 0; iy = ry * 64; do { oh = h; oi = i; oj = j; ok = k; h = (ix + 32) >> 6; i = (iy + 32) >> 6; j = (h * rx) / ry; k = (i * rx) / ry; if (((j != oj) || (i != oi)) && (h < i)) { Callback(Surface, x+j, y+i, color); if (j) Callback(Surface, x-j, y+i, color); if (i) { Callback(Surface, x+j, y-i, color); if (j) Callback(Surface, x-j, y-i, color); } } if (((k != ok) || (h != oh)) && (h < oi)) { Callback(Surface, x+k, y+h, color); if (k) Callback(Surface, x-k, y+h, color); if (h) { Callback(Surface, x+k, y-h, color); if (k) Callback(Surface, x-k, y-h, color); } } ix = ix + iy / ry; iy = iy - ix / ry; } while(i > h); } } //================================================================================== // Performs Callback at each ellipse point. (RGB) //================================================================================== void sge_DoEllipse(SDL_Surface *Surface, Sint16 x, Sint16 y, Sint16 rx, Sint16 ry, Uint8 R, Uint8 G, Uint8 B, void Callback(SDL_Surface *Surf, Sint16 X, Sint16 Y, Uint32 Color) ) { sge_DoEllipse(Surface,x,y,rx,ry,SDL_MapRGB(Surface->format, R, G, B),Callback); } //================================================================================== // Draws an ellipse //================================================================================== void sge_Ellipse(SDL_Surface *Surface, Sint16 x, Sint16 y, Sint16 rx, Sint16 ry, Uint32 color) { if (SDL_MUSTLOCK(Surface) && _sge_lock) { if (SDL_LockSurface(Surface) < 0) return; } sge_DoEllipse(Surface, x, y, rx, ry, color, _PutPixel); if (SDL_MUSTLOCK(Surface) && _sge_lock) { SDL_UnlockSurface(Surface); } sge_UpdateRect(Surface, x-rx, y-ry, 2*rx+1, 2*ry+1); } //================================================================================== // Draws an ellipse (RGB) //================================================================================== void sge_Ellipse(SDL_Surface *Surface, Sint16 x, Sint16 y, Sint16 rx, Sint16 ry, Uint8 R, Uint8 G, Uint8 B) { sge_Ellipse(Surface,x,y,rx,ry,SDL_MapRGB(Surface->format, R, G, B)); } //================================================================================== // Draws an ellipse (alpha) //================================================================================== void sge_EllipseAlpha(SDL_Surface *Surface, Sint16 x, Sint16 y, Sint16 rx, Sint16 ry, Uint32 color, Uint8 alpha) { if (SDL_MUSTLOCK(Surface) && _sge_lock) if (SDL_LockSurface(Surface) < 0) return; _sge_alpha_hack = alpha; sge_DoEllipse(Surface, x, y, rx, ry, color, callback_alpha_hack); if (SDL_MUSTLOCK(Surface) && _sge_lock) { SDL_UnlockSurface(Surface); } sge_UpdateRect(Surface, x-rx, y-ry, 2*rx+1, 2*ry+1); } //================================================================================== // Draws an ellipse (alpha - RGB) //================================================================================== void sge_EllipseAlpha(SDL_Surface *Surface, Sint16 x, Sint16 y, Sint16 rx, Sint16 ry, Uint8 R, Uint8 G, Uint8 B, Uint8 alpha) { sge_EllipseAlpha(Surface,x,y,rx,ry,SDL_MapRGB(Surface->format, R, G, B),alpha); } //================================================================================== // Draws a filled ellipse //================================================================================== void sge_FilledEllipse(SDL_Surface *Surface, Sint16 x, Sint16 y, Sint16 rx, Sint16 ry, Uint32 color) { int ix, iy; int h, i, j, k; int oh, oi, oj, ok; if (rx < 1) rx = 1; if (ry < 1) ry = 1; oh = oi = oj = ok = 0xFFFF; if (rx > ry) { ix = 0; iy = rx * 64; do { h = (ix + 32) >> 6; i = (iy + 32) >> 6; j = (h * ry) / rx; k = (i * ry) / rx; if ((k!=ok) && (k!=oj)) { if (k){ _HLine(Surface,x-h,x+h,y-k,color); _HLine(Surface,x-h,x+h,y+k,color); }else _HLine(Surface,x-h,x+h,y,color); ok=k; } if ((j!=oj) && (j!=ok) && (k!=j)) { if (j){ _HLine(Surface,x-i,x+i,y-j,color); _HLine(Surface,x-i,x+i,y+j,color); }else _HLine(Surface,x-i,x+i,y,color); oj=j; } ix = ix + iy / rx; iy = iy - ix / rx; } while (i > h); } else { ix = 0; iy = ry * 64; do { h = (ix + 32) >> 6; i = (iy + 32) >> 6; j = (h * rx) / ry; k = (i * rx) / ry; if ((i!=oi) && (i!=oh)) { if (i){ _HLine(Surface,x-j,x+j,y-i,color); _HLine(Surface,x-j,x+j,y+i,color); }else _HLine(Surface,x-j,x+j,y,color); oi=i; } if ((h!=oh) && (h!=oi) && (i!=h)) { if (h){ _HLine(Surface,x-k,x+k,y-h,color); _HLine(Surface,x-k,x+k,y+h,color); }else _HLine(Surface,x-k,x+k,y,color); oh=h; } ix = ix + iy / ry; iy = iy - ix / ry; } while(i > h); } } //================================================================================== // Draws a filled ellipse (RGB) //================================================================================== void sge_FilledEllipse(SDL_Surface *Surface, Sint16 x, Sint16 y, Sint16 rx, Sint16 ry, Uint8 R, Uint8 G, Uint8 B) { sge_FilledEllipse(Surface,x,y,rx,ry,SDL_MapRGB(Surface->format, R, G, B)); } //================================================================================== // Draws a filled ellipse (alpha) //================================================================================== void sge_FilledEllipseAlpha(SDL_Surface *Surface, Sint16 x, Sint16 y, Sint16 rx, Sint16 ry, Uint32 color, Uint8 alpha) { int ix, iy; int h, i, j, k; int oh, oi, oj, ok; if (SDL_MUSTLOCK(Surface) && _sge_lock) if (SDL_LockSurface(Surface) < 0) return; if (rx < 1) rx = 1; if (ry < 1) ry = 1; oh = oi = oj = ok = 0xFFFF; if (rx > ry) { ix = 0; iy = rx * 64; do { h = (ix + 32) >> 6; i = (iy + 32) >> 6; j = (h * ry) / rx; k = (i * ry) / rx; if ((k!=ok) && (k!=oj)) { if (k){ _HLineAlpha(Surface,x-h,x+h,y-k,color,alpha); _HLineAlpha(Surface,x-h,x+h,y+k,color,alpha); }else _HLineAlpha(Surface,x-h,x+h,y,color,alpha); ok=k; } if ((j!=oj) && (j!=ok) && (k!=j)) { if (j){ _HLineAlpha(Surface,x-i,x+i,y-j,color,alpha); _HLineAlpha(Surface,x-i,x+i,y+j,color,alpha); }else _HLineAlpha(Surface,x-i,x+i,y,color,alpha); oj=j; } ix = ix + iy / rx; iy = iy - ix / rx; } while (i > h); } else { ix = 0; iy = ry * 64; do { h = (ix + 32) >> 6; i = (iy + 32) >> 6; j = (h * rx) / ry; k = (i * rx) / ry; if ((i!=oi) && (i!=oh)) { if (i){ _HLineAlpha(Surface,x-j,x+j,y-i,color,alpha); _HLineAlpha(Surface,x-j,x+j,y+i,color,alpha); }else _HLineAlpha(Surface,x-j,x+j,y,color,alpha); oi=i; } if ((h!=oh) && (h!=oi) && (i!=h)) { if (h){ _HLineAlpha(Surface,x-k,x+k,y-h,color,alpha); _HLineAlpha(Surface,x-k,x+k,y+h,color,alpha); }else _HLineAlpha(Surface,x-k,x+k,y,color,alpha); oh=h; } ix = ix + iy / ry; iy = iy - ix / ry; } while(i > h); } if (SDL_MUSTLOCK(Surface) && _sge_lock) { SDL_UnlockSurface(Surface); } } //================================================================================== // Draws a filled ellipse (alpha - RGB) //================================================================================== void sge_FilledEllipseAlpha(SDL_Surface *Surface, Sint16 x, Sint16 y, Sint16 rx, Sint16 ry, Uint8 R, Uint8 G, Uint8 B, Uint8 alpha) { sge_FilledEllipseAlpha(Surface,x,y,rx,ry,SDL_MapRGB(Surface->format, R, G, B),alpha); } //================================================================================== // Performs Callback at each circle point. //================================================================================== void sge_DoCircle(SDL_Surface *Surface, Sint16 x, Sint16 y, Sint16 r, Uint32 color, void Callback(SDL_Surface *Surf, Sint16 X, Sint16 Y, Uint32 Color)) { Sint16 cx = 0; Sint16 cy = r; Sint16 df = 1 - r; Sint16 d_e = 3; Sint16 d_se = -2 * r + 5; do { Callback(Surface, x+cx, y+cy, color); Callback(Surface, x-cx, y+cy, color); Callback(Surface, x+cx, y-cy, color); Callback(Surface, x-cx, y-cy, color); Callback(Surface, x+cy, y+cx, color); Callback(Surface, x+cy, y-cx, color); Callback(Surface, x-cy, y+cx, color); Callback(Surface, x-cy, y-cx, color); if (df < 0) { df += d_e; d_e += 2; d_se += 2; } else { df += d_se; d_e += 2; d_se += 4; cy--; } cx++; }while(cx <= cy); } //================================================================================== // Performs Callback at each circle point. (RGB) //================================================================================== void sge_DoCircle(SDL_Surface *Surface, Sint16 x, Sint16 y, Sint16 r, Uint8 R, Uint8 G, Uint8 B, void Callback(SDL_Surface *Surf, Sint16 X, Sint16 Y, Uint32 Color)) { sge_DoCircle(Surface,x,y,r,SDL_MapRGB(Surface->format, R, G, B),Callback); } //================================================================================== // Draws a circle //================================================================================== void sge_Circle(SDL_Surface *Surface, Sint16 x, Sint16 y, Sint16 r, Uint32 color) { if (SDL_MUSTLOCK(Surface) && _sge_lock) { if (SDL_LockSurface(Surface) < 0) return; } sge_DoCircle(Surface, x, y, r, color, _PutPixel); if (SDL_MUSTLOCK(Surface) && _sge_lock) { SDL_UnlockSurface(Surface); } sge_UpdateRect(Surface, x-r, y-r, 2*r+1, 2*r+1); } //================================================================================== // Draws a circle (RGB) //================================================================================== void sge_Circle(SDL_Surface *Surface, Sint16 x, Sint16 y, Sint16 r, Uint8 R, Uint8 G, Uint8 B) { sge_Circle(Surface,x,y,r,SDL_MapRGB(Surface->format, R, G, B)); } //================================================================================== // Draws a circle (alpha) //================================================================================== void sge_CircleAlpha(SDL_Surface *Surface, Sint16 x, Sint16 y, Sint16 r, Uint32 color, Uint8 alpha) { if (SDL_MUSTLOCK(Surface) && _sge_lock) if (SDL_LockSurface(Surface) < 0) return; _sge_alpha_hack = alpha; sge_DoCircle(Surface, x, y, r, color, callback_alpha_hack); if (SDL_MUSTLOCK(Surface) && _sge_lock) { SDL_UnlockSurface(Surface); } sge_UpdateRect(Surface, x-r, y-r, 2*r+1, 2*r+1); } //================================================================================== // Draws a circle (alpha - RGB) //================================================================================== void sge_CircleAlpha(SDL_Surface *Surface, Sint16 x, Sint16 y, Sint16 r, Uint8 R, Uint8 G, Uint8 B, Uint8 alpha) { sge_CircleAlpha(Surface,x,y,r,SDL_MapRGB(Surface->format, R, G, B),alpha); } //================================================================================== // Draws a filled circle //================================================================================== void sge_FilledCircle(SDL_Surface *Surface, Sint16 x, Sint16 y, Sint16 r, Uint32 color) { Sint16 cx = 0; Sint16 cy = r; bool draw=true; Sint16 df = 1 - r; Sint16 d_e = 3; Sint16 d_se = -2 * r + 5; do { if(draw){ _HLine(Surface,x-cx,x+cx,y+cy,color); _HLine(Surface,x-cx,x+cx,y-cy,color); draw=false; } if(cx!=cy){ if(cx){ _HLine(Surface,x-cy,x+cy,y-cx,color); _HLine(Surface,x-cy,x+cy,y+cx,color); }else _HLine(Surface,x-cy,x+cy,y,color); } if (df < 0) { df += d_e; d_e += 2; d_se += 2; } else { df += d_se; d_e += 2; d_se += 4; cy--; draw=true; } cx++; }while(cx <= cy); sge_UpdateRect(Surface, x-r, y-r, 2*r+1, 2*r+1); } //================================================================================== // Draws a filled circle (RGB) //================================================================================== void sge_FilledCircle(SDL_Surface *Surface, Sint16 x, Sint16 y, Sint16 r, Uint8 R, Uint8 G, Uint8 B) { sge_FilledCircle(Surface,x,y,r,SDL_MapRGB(Surface->format, R, G, B)); } //================================================================================== // Draws a filled circle (alpha) //================================================================================== void sge_FilledCircleAlpha(SDL_Surface *Surface, Sint16 x, Sint16 y, Sint16 r, Uint32 color, Uint8 alpha) { Sint16 cx = 0; Sint16 cy = r; bool draw=true; Sint16 df = 1 - r; Sint16 d_e = 3; Sint16 d_se = -2 * r + 5; if (SDL_MUSTLOCK(Surface) && _sge_lock) if (SDL_LockSurface(Surface) < 0) return; do { if(draw){ _HLineAlpha(Surface,x-cx,x+cx,y+cy,color,alpha); _HLineAlpha(Surface,x-cx,x+cx,y-cy,color,alpha); draw=false; } if(cx!=cy){ if(cx){ _HLineAlpha(Surface,x-cy,x+cy,y-cx,color,alpha); _HLineAlpha(Surface,x-cy,x+cy,y+cx,color,alpha); }else _HLineAlpha(Surface,x-cy,x+cy,y,color,alpha); } if (df < 0) { df += d_e; d_e += 2; d_se += 2; } else { df += d_se; d_e += 2; d_se += 4; cy--; draw=true; } cx++; }while(cx <= cy); if (SDL_MUSTLOCK(Surface) && _sge_lock) { SDL_UnlockSurface(Surface); } sge_UpdateRect(Surface, x-r, y-r, 2*r+1, 2*r+1); } //================================================================================== // Draws a filled circle (alpha - RGB) //================================================================================== void sge_FilledCircleAlpha(SDL_Surface *Surface, Sint16 x, Sint16 y, Sint16 r, Uint8 R, Uint8 G, Uint8 B, Uint8 alpha) { sge_FilledCircleAlpha(Surface,x,y,r,SDL_MapRGB(Surface->format, R, G, B),alpha); } //================================================================================== // Draws a bezier line //================================================================================== /* Macro to do the line... 'function' is the line drawing routine */ #define DO_BEZIER(function)\ /* * Note: I don't think there is any great performance win in translating this to fixed-point integer math, * most of the time is spent in the line drawing routine. */\ float x = float(x1), y = float(y1);\ float xp = x, yp = y;\ float delta;\ float dx, d2x, d3x;\ float dy, d2y, d3y;\ float a, b, c;\ int i;\ int n = 1;\ Sint16 xmax=x1, ymax=y1, xmin=x1, ymin=y1;\ \ /* compute number of iterations */\ if(level < 1)\ level=1;\ if(level >= 15)\ level=15; \ while (level-- > 0)\ n*= 2;\ delta = 1.0 / float(n);\ \ /* compute finite differences */\ /* a, b, c are the coefficient of the polynom in t defining the parametric curve */\ /* The computation is done independently for x and y */\ a = float(-x1 + 3*x2 - 3*x3 + x4);\ b = float(3*x1 - 6*x2 + 3*x3);\ c = float(-3*x1 + 3*x2);\ \ d3x = 6 * a * delta*delta*delta;\ d2x = d3x + 2 * b * delta*delta;\ dx = a * delta*delta*delta + b * delta*delta + c * delta;\ \ a = float(-y1 + 3*y2 - 3*y3 + y4);\ b = float(3*y1 - 6*y2 + 3*y3);\ c = float(-3*y1 + 3*y2);\ \ d3y = 6 * a * delta*delta*delta;\ d2y = d3y + 2 * b * delta*delta;\ dy = a * delta*delta*delta + b * delta*delta + c * delta;\ \ if (SDL_MUSTLOCK(surface) && _sge_lock) {\ if (SDL_LockSurface(surface) < 0)\ return;\ }\ \ /* iterate */\ for (i = 0; i < n; i++) {\ x += dx; dx += d2x; d2x += d3x;\ y += dy; dy += d2y; d2y += d3y;\ if(Sint16(xp) != Sint16(x) || Sint16(yp) != Sint16(y)){\ function;\ if(_sge_update==1){\ xmax= (xmax>Sint16(xp))? xmax : Sint16(xp); ymax= (ymax>Sint16(yp))? ymax : Sint16(yp);\ xmin= (xminSint16(x))? xmax : Sint16(x); ymax= (ymax>Sint16(y))? ymax : Sint16(y);\ xmin= (xminformat,R,G,B)); } //================================================================================== // Draws a bezier line (alpha) //================================================================================== void sge_BezierAlpha(SDL_Surface *surface, Sint16 x1, Sint16 y1, Sint16 x2, Sint16 y2,Sint16 x3, Sint16 y3, Sint16 x4, Sint16 y4, int level, Uint32 color, Uint8 alpha) { _sge_alpha_hack = alpha; DO_BEZIER(sge_DoLine(surface, Sint16(xp),Sint16(yp), Sint16(x),Sint16(y), color, callback_alpha_hack)); } //================================================================================== // Draws a bezier line (alpha - RGB) //================================================================================== void sge_BezierAlpha(SDL_Surface *surface, Sint16 x1, Sint16 y1, Sint16 x2, Sint16 y2,Sint16 x3, Sint16 y3, Sint16 x4, Sint16 y4, int level, Uint8 R, Uint8 G, Uint8 B, Uint8 alpha) { sge_BezierAlpha(surface,x1,y1,x2,y2,x3,y3,x4,y4,level, SDL_MapRGB(surface->format,R,G,B),alpha); } //================================================================================== // Draws an AA bezier line (alpha) //================================================================================== void sge_AABezierAlpha(SDL_Surface *surface, Sint16 x1, Sint16 y1, Sint16 x2, Sint16 y2,Sint16 x3, Sint16 y3, Sint16 x4, Sint16 y4, int level, Uint32 color, Uint8 alpha) { Uint8 update = _sge_update; Uint8 lock = _sge_lock; _sge_update = 0; _sge_lock = 0; if (SDL_MUSTLOCK(surface) && lock) if (SDL_LockSurface(surface) < 0) return; DO_BEZIER(sge_AALineAlpha(surface, Sint16(xp),Sint16(yp), Sint16(x),Sint16(y), color, alpha)); if (SDL_MUSTLOCK(surface) && lock) { SDL_UnlockSurface(surface); } _sge_update = update; _sge_lock = lock; sge_UpdateRect(surface, xmin, ymin, xmax-xmin+1, ymax-ymin+1); } //================================================================================== // Draws an AA bezier line (alpha - RGB) //================================================================================== void sge_AABezierAlpha(SDL_Surface *surface, Sint16 x1, Sint16 y1, Sint16 x2, Sint16 y2,Sint16 x3, Sint16 y3, Sint16 x4, Sint16 y4, int level, Uint8 R, Uint8 G, Uint8 B, Uint8 alpha) { sge_AABezierAlpha(surface,x1,y1,x2,y2,x3,y3,x4,y4,level, SDL_MapRGB(surface->format,R,G,B),alpha); } //================================================================================== // Draws an AA bezier line //================================================================================== void sge_AABezier(SDL_Surface *surface, Sint16 x1, Sint16 y1, Sint16 x2, Sint16 y2,Sint16 x3, Sint16 y3, Sint16 x4, Sint16 y4, int level, Uint32 color) { sge_AABezierAlpha(surface, x1,y1, x2,y2, x3,y3, x4,y4, level, color, 255); } //================================================================================== // Draws an AA bezier line (RGB) //================================================================================== void sge_AABezier(SDL_Surface *surface, Sint16 x1, Sint16 y1, Sint16 x2, Sint16 y2,Sint16 x3, Sint16 y3, Sint16 x4, Sint16 y4, int level, Uint8 R, Uint8 G, Uint8 B) { sge_AABezierAlpha(surface,x1,y1,x2,y2,x3,y3,x4,y4,level, SDL_MapRGB(surface->format,R,G,B),255); }