SDL  2.0
SDL_RLEaccel_c.h File Reference
#include "../SDL_internal.h"
+ Include dependency graph for SDL_RLEaccel_c.h:
+ This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Functions

int SDL_RLESurface (SDL_Surface *surface)
 
int SDL_RLEBlit (SDL_Surface *src, SDL_Rect *srcrect, SDL_Surface *dst, SDL_Rect *dstrect)
 
int SDL_RLEAlphaBlit (SDL_Surface *src, SDL_Rect *srcrect, SDL_Surface *dst, SDL_Rect *dstrect)
 
void SDL_UnRLESurface (SDL_Surface *surface, int recode)
 

Function Documentation

◆ SDL_RLEAlphaBlit()

int SDL_RLEAlphaBlit ( SDL_Surface src,
SDL_Rect srcrect,
SDL_Surface dst,
SDL_Rect dstrect 
)

Definition at line 730 of file SDL_RLEaccel.c.

References BLIT_TRANSL_555, BLIT_TRANSL_565, BLIT_TRANSL_888, SDL_PixelFormat::Bmask, SDL_PixelFormat::BytesPerPixel, SDL_BlitMap::data, done, SDL_Surface::format, SDL_PixelFormat::Gmask, SDL_Surface::map, SDL_Surface::pitch, SDL_Surface::pixels, RLEALPHABLIT, RLEAlphaClipBlit(), SDL_PixelFormat::Rmask, SDL_LockSurface, SDL_MUSTLOCK, SDL_UnlockSurface, SDL_Rect::w, SDL_Surface::w, SDL_Rect::x, and SDL_Rect::y.

Referenced by SDL_RLESurface().

732 {
733  int x, y;
734  int w = surf_src->w;
735  Uint8 *srcbuf, *dstbuf;
736  SDL_PixelFormat *df = surf_dst->format;
737 
738  /* Lock the destination if necessary */
739  if (SDL_MUSTLOCK(surf_dst)) {
740  if (SDL_LockSurface(surf_dst) < 0) {
741  return -1;
742  }
743  }
744 
745  x = dstrect->x;
746  y = dstrect->y;
747  dstbuf = (Uint8 *) surf_dst->pixels + y * surf_dst->pitch + x * df->BytesPerPixel;
748  srcbuf = (Uint8 *) surf_src->map->data + sizeof(RLEDestFormat);
749 
750  {
751  /* skip lines at the top if necessary */
752  int vskip = srcrect->y;
753  if (vskip) {
754  int ofs;
755  if (df->BytesPerPixel == 2) {
756  /* the 16/32 interleaved format */
757  do {
758  /* skip opaque line */
759  ofs = 0;
760  do {
761  int run;
762  ofs += srcbuf[0];
763  run = srcbuf[1];
764  srcbuf += 2;
765  if (run) {
766  srcbuf += 2 * run;
767  ofs += run;
768  } else if (!ofs)
769  goto done;
770  } while (ofs < w);
771 
772  /* skip padding */
773  srcbuf += (uintptr_t) srcbuf & 2;
774 
775  /* skip translucent line */
776  ofs = 0;
777  do {
778  int run;
779  ofs += ((Uint16 *) srcbuf)[0];
780  run = ((Uint16 *) srcbuf)[1];
781  srcbuf += 4 * (run + 1);
782  ofs += run;
783  } while (ofs < w);
784  } while (--vskip);
785  } else {
786  /* the 32/32 interleaved format */
787  vskip <<= 1; /* opaque and translucent have same format */
788  do {
789  ofs = 0;
790  do {
791  int run;
792  ofs += ((Uint16 *) srcbuf)[0];
793  run = ((Uint16 *) srcbuf)[1];
794  srcbuf += 4;
795  if (run) {
796  srcbuf += 4 * run;
797  ofs += run;
798  } else if (!ofs)
799  goto done;
800  } while (ofs < w);
801  } while (--vskip);
802  }
803  }
804  }
805 
806  /* if left or right edge clipping needed, call clip blit */
807  if (srcrect->x || srcrect->w != surf_src->w) {
808  RLEAlphaClipBlit(w, srcbuf, surf_dst, dstbuf, srcrect);
809  } else {
810 
811  /*
812  * non-clipped blitter. Ptype is the destination pixel type,
813  * Ctype the translucent count type, and do_blend the
814  * macro to blend one pixel.
815  */
816 #define RLEALPHABLIT(Ptype, Ctype, do_blend) \
817  do { \
818  int linecount = srcrect->h; \
819  do { \
820  int ofs = 0; \
821  /* blit opaque pixels on one line */ \
822  do { \
823  unsigned run; \
824  ofs += ((Ctype *)srcbuf)[0]; \
825  run = ((Ctype *)srcbuf)[1]; \
826  srcbuf += 2 * sizeof(Ctype); \
827  if(run) { \
828  PIXEL_COPY(dstbuf + ofs * sizeof(Ptype), srcbuf, \
829  run, sizeof(Ptype)); \
830  srcbuf += run * sizeof(Ptype); \
831  ofs += run; \
832  } else if(!ofs) \
833  goto done; \
834  } while(ofs < w); \
835  /* skip padding if necessary */ \
836  if(sizeof(Ptype) == 2) \
837  srcbuf += (uintptr_t)srcbuf & 2; \
838  /* blit translucent pixels on the same line */ \
839  ofs = 0; \
840  do { \
841  unsigned run; \
842  ofs += ((Uint16 *)srcbuf)[0]; \
843  run = ((Uint16 *)srcbuf)[1]; \
844  srcbuf += 4; \
845  if(run) { \
846  Ptype *dst = (Ptype *)dstbuf + ofs; \
847  unsigned i; \
848  for(i = 0; i < run; i++) { \
849  Uint32 src = *(Uint32 *)srcbuf; \
850  do_blend(src, *dst); \
851  srcbuf += 4; \
852  dst++; \
853  } \
854  ofs += run; \
855  } \
856  } while(ofs < w); \
857  dstbuf += surf_dst->pitch; \
858  } while(--linecount); \
859  } while(0)
860 
861  switch (df->BytesPerPixel) {
862  case 2:
863  if (df->Gmask == 0x07e0 || df->Rmask == 0x07e0
864  || df->Bmask == 0x07e0)
866  else
868  break;
869  case 4:
871  break;
872  }
873  }
874 
875  done:
876  /* Unlock the destination if necessary */
877  if (SDL_MUSTLOCK(surf_dst)) {
878  SDL_UnlockSurface(surf_dst);
879  }
880  return 0;
881 }
#define SDL_UnlockSurface
#define BLIT_TRANSL_555(src, dst)
Definition: SDL_RLEaccel.c:604
GLint GLint GLint GLint GLint x
Definition: SDL_opengl.h:1567
Uint8 BytesPerPixel
Definition: SDL_pixels.h:318
uint32_t Uint32
An unsigned 32-bit integer type.
Definition: SDL_stdinc.h:161
static void RLEAlphaClipBlit(int w, Uint8 *srcbuf, SDL_Surface *surf_dst, Uint8 *dstbuf, SDL_Rect *srcrect)
Definition: SDL_RLEaccel.c:638
GLint GLint GLint GLint GLint GLint y
Definition: SDL_opengl.h:1567
uint8_t Uint8
An unsigned 8-bit integer type.
Definition: SDL_stdinc.h:143
int done
Definition: checkkeys.c:28
unsigned int uintptr_t
int x
Definition: SDL_rect.h:66
int w
Definition: SDL_rect.h:67
#define SDL_LockSurface
#define RLEALPHABLIT(Ptype, Ctype, do_blend)
#define SDL_MUSTLOCK(S)
Definition: SDL_surface.h:61
#define BLIT_TRANSL_565(src, dst)
Definition: SDL_RLEaccel.c:592
#define BLIT_TRANSL_888(src, dst)
Definition: SDL_RLEaccel.c:574
uint16_t Uint16
An unsigned 16-bit integer type.
Definition: SDL_stdinc.h:151
GLubyte GLubyte GLubyte GLubyte w
int y
Definition: SDL_rect.h:66

◆ SDL_RLEBlit()

int SDL_RLEBlit ( SDL_Surface src,
SDL_Rect srcrect,
SDL_Surface dst,
SDL_Rect dstrect 
)

Definition at line 452 of file SDL_RLEaccel.c.

References SDL_BlitInfo::a, SDL_PixelFormat::BytesPerPixel, CHOOSE_BLIT, SDL_BlitMap::data, done, SDL_Surface::format, SDL_BlitMap::info, SDL_Surface::map, SDL_Surface::pitch, SDL_Surface::pixels, RLEBLIT, RLEClipBlit(), RLESKIP, SDL_LockSurface, SDL_MUSTLOCK, SDL_UnlockSurface, SDL_Rect::w, SDL_Surface::w, SDL_Rect::x, and SDL_Rect::y.

Referenced by SDL_RLESurface(), and SDL_UnRLESurface().

454 {
455  Uint8 *dstbuf;
456  Uint8 *srcbuf;
457  int x, y;
458  int w = surf_src->w;
459  unsigned alpha;
460 
461  /* Lock the destination if necessary */
462  if (SDL_MUSTLOCK(surf_dst)) {
463  if (SDL_LockSurface(surf_dst) < 0) {
464  return (-1);
465  }
466  }
467 
468  /* Set up the source and destination pointers */
469  x = dstrect->x;
470  y = dstrect->y;
471  dstbuf = (Uint8 *) surf_dst->pixels
472  + y * surf_dst->pitch + x * surf_src->format->BytesPerPixel;
473  srcbuf = (Uint8 *) surf_src->map->data;
474 
475  {
476  /* skip lines at the top if necessary */
477  int vskip = srcrect->y;
478  int ofs = 0;
479  if (vskip) {
480 
481 #define RLESKIP(bpp, Type) \
482  for(;;) { \
483  int run; \
484  ofs += *(Type *)srcbuf; \
485  run = ((Type *)srcbuf)[1]; \
486  srcbuf += sizeof(Type) * 2; \
487  if(run) { \
488  srcbuf += run * bpp; \
489  ofs += run; \
490  } else if(!ofs) \
491  goto done; \
492  if(ofs == w) { \
493  ofs = 0; \
494  if(!--vskip) \
495  break; \
496  } \
497  }
498 
499  switch (surf_src->format->BytesPerPixel) {
500  case 1:
501  RLESKIP(1, Uint8);
502  break;
503  case 2:
504  RLESKIP(2, Uint8);
505  break;
506  case 3:
507  RLESKIP(3, Uint8);
508  break;
509  case 4:
510  RLESKIP(4, Uint16);
511  break;
512  }
513 
514 #undef RLESKIP
515 
516  }
517  }
518 
519  alpha = surf_src->map->info.a;
520  /* if left or right edge clipping needed, call clip blit */
521  if (srcrect->x || srcrect->w != surf_src->w) {
522  RLEClipBlit(w, srcbuf, surf_dst, dstbuf, srcrect, alpha);
523  } else {
524  SDL_PixelFormat *fmt = surf_src->format;
525 
526 #define RLEBLIT(bpp, Type, do_blit) \
527  do { \
528  int linecount = srcrect->h; \
529  int ofs = 0; \
530  for(;;) { \
531  unsigned run; \
532  ofs += *(Type *)srcbuf; \
533  run = ((Type *)srcbuf)[1]; \
534  srcbuf += 2 * sizeof(Type); \
535  if(run) { \
536  do_blit(dstbuf + ofs * bpp, srcbuf, run, bpp, alpha); \
537  srcbuf += run * bpp; \
538  ofs += run; \
539  } else if(!ofs) \
540  break; \
541  if(ofs == w) { \
542  ofs = 0; \
543  dstbuf += surf_dst->pitch; \
544  if(!--linecount) \
545  break; \
546  } \
547  } \
548  } while(0)
549 
550  CHOOSE_BLIT(RLEBLIT, alpha, fmt);
551 
552 #undef RLEBLIT
553  }
554 
555  done:
556  /* Unlock the destination if necessary */
557  if (SDL_MUSTLOCK(surf_dst)) {
558  SDL_UnlockSurface(surf_dst);
559  }
560  return (0);
561 }
#define CHOOSE_BLIT(blitter, alpha, fmt)
Definition: SDL_RLEaccel.c:306
#define SDL_UnlockSurface
GLint GLint GLint GLint GLint x
Definition: SDL_opengl.h:1567
GLfloat GLfloat GLfloat alpha
GLint GLint GLint GLint GLint GLint y
Definition: SDL_opengl.h:1567
uint8_t Uint8
An unsigned 8-bit integer type.
Definition: SDL_stdinc.h:143
int done
Definition: checkkeys.c:28
#define RLESKIP(bpp, Type)
int x
Definition: SDL_rect.h:66
static void RLEClipBlit(int w, Uint8 *srcbuf, SDL_Surface *surf_dst, Uint8 *dstbuf, SDL_Rect *srcrect, unsigned alpha)
Definition: SDL_RLEaccel.c:393
int w
Definition: SDL_rect.h:67
#define SDL_LockSurface
#define SDL_MUSTLOCK(S)
Definition: SDL_surface.h:61
uint16_t Uint16
An unsigned 16-bit integer type.
Definition: SDL_stdinc.h:151
GLubyte GLubyte GLubyte GLubyte w
int y
Definition: SDL_rect.h:66
#define RLEBLIT(bpp, Type, do_blit)

◆ SDL_RLESurface()

int SDL_RLESurface ( SDL_Surface surface)

Definition at line 1403 of file SDL_RLEaccel.c.

References SDL_PixelFormat::Amask, SDL_PixelFormat::BitsPerPixel, SDL_BlitMap::blit, SDL_BlitInfo::flags, SDL_Surface::flags, SDL_Surface::format, SDL_BlitMap::identity, SDL_BlitMap::info, SDL_Surface::map, SDL_Surface::pixels, RLEAlphaSurface(), RLEColorkeySurface(), SDL_COPY_ADD, SDL_COPY_BLEND, SDL_COPY_COLORKEY, SDL_COPY_MOD, SDL_COPY_MODULATE_ALPHA, SDL_COPY_MODULATE_COLOR, SDL_COPY_NEAREST, SDL_COPY_RLE_ALPHAKEY, SDL_COPY_RLE_COLORKEY, SDL_RLEACCEL, SDL_RLEAlphaBlit(), SDL_RLEBlit(), and SDL_UnRLESurface().

Referenced by SDL_CalculateBlit(), and SDL_UnlockSurface().

1404 {
1405  int flags;
1406 
1407  /* Clear any previous RLE conversion */
1408  if ((surface->flags & SDL_RLEACCEL) == SDL_RLEACCEL) {
1409  SDL_UnRLESurface(surface, 1);
1410  }
1411 
1412  /* We don't support RLE encoding of bitmaps */
1413  if (surface->format->BitsPerPixel < 8) {
1414  return -1;
1415  }
1416 
1417  /* Make sure the pixels are available */
1418  if (!surface->pixels) {
1419  return -1;
1420  }
1421 
1422  /* If we don't have colorkey or blending, nothing to do... */
1423  flags = surface->map->info.flags;
1424  if (!(flags & (SDL_COPY_COLORKEY | SDL_COPY_BLEND))) {
1425  return -1;
1426  }
1427 
1428  /* Pass on combinations not supported */
1429  if ((flags & SDL_COPY_MODULATE_COLOR) ||
1430  ((flags & SDL_COPY_MODULATE_ALPHA) && surface->format->Amask) ||
1431  (flags & (SDL_COPY_ADD | SDL_COPY_MOD)) ||
1432  (flags & SDL_COPY_NEAREST)) {
1433  return -1;
1434  }
1435 
1436  /* Encode and set up the blit */
1437  if (!surface->format->Amask || !(flags & SDL_COPY_BLEND)) {
1438  if (!surface->map->identity) {
1439  return -1;
1440  }
1441  if (RLEColorkeySurface(surface) < 0) {
1442  return -1;
1443  }
1444  surface->map->blit = SDL_RLEBlit;
1445  surface->map->info.flags |= SDL_COPY_RLE_COLORKEY;
1446  } else {
1447  if (RLEAlphaSurface(surface) < 0) {
1448  return -1;
1449  }
1450  surface->map->blit = SDL_RLEAlphaBlit;
1451  surface->map->info.flags |= SDL_COPY_RLE_ALPHAKEY;
1452  }
1453 
1454  /* The surface is now accelerated */
1455  surface->flags |= SDL_RLEACCEL;
1456 
1457  return (0);
1458 }
#define SDL_COPY_MODULATE_COLOR
Definition: SDL_blit.h:34
#define SDL_COPY_COLORKEY
Definition: SDL_blit.h:39
SDL_blit blit
Definition: SDL_blit.h:89
#define SDL_COPY_MOD
Definition: SDL_blit.h:38
void SDL_UnRLESurface(SDL_Surface *surface, int recode)
#define SDL_COPY_RLE_COLORKEY
Definition: SDL_blit.h:42
int SDL_RLEBlit(SDL_Surface *surf_src, SDL_Rect *srcrect, SDL_Surface *surf_dst, SDL_Rect *dstrect)
Definition: SDL_RLEaccel.c:452
#define SDL_COPY_ADD
Definition: SDL_blit.h:37
Uint32 flags
Definition: SDL_surface.h:71
#define SDL_COPY_NEAREST
Definition: SDL_blit.h:40
struct SDL_BlitMap * map
Definition: SDL_surface.h:88
void * pixels
Definition: SDL_surface.h:75
Uint8 BitsPerPixel
Definition: SDL_pixels.h:317
int SDL_RLEAlphaBlit(SDL_Surface *surf_src, SDL_Rect *srcrect, SDL_Surface *surf_dst, SDL_Rect *dstrect)
Definition: SDL_RLEaccel.c:730
static int RLEColorkeySurface(SDL_Surface *surface)
SDL_PixelFormat * format
Definition: SDL_surface.h:72
#define SDL_COPY_MODULATE_ALPHA
Definition: SDL_blit.h:35
#define SDL_COPY_RLE_ALPHAKEY
Definition: SDL_blit.h:43
static int RLEAlphaSurface(SDL_Surface *surface)
GLbitfield flags
int identity
Definition: SDL_blit.h:88
#define SDL_COPY_BLEND
Definition: SDL_blit.h:36
SDL_BlitInfo info
Definition: SDL_blit.h:91
#define SDL_RLEACCEL
Definition: SDL_surface.h:54

◆ SDL_UnRLESurface()

void SDL_UnRLESurface ( SDL_Surface surface,
int  recode 
)

Definition at line 1540 of file SDL_RLEaccel.c.

References SDL_BlitInfo::colorkey, SDL_BlitMap::data, SDL_BlitInfo::flags, SDL_Surface::flags, SDL_Rect::h, SDL_Surface::h, SDL_BlitMap::info, SDL_Surface::map, NULL, SDL_Surface::pitch, SDL_Surface::pixels, SDL_COPY_RLE_ALPHAKEY, SDL_COPY_RLE_COLORKEY, SDL_FillRect, SDL_free(), SDL_malloc, SDL_PREALLOC, SDL_RLEACCEL, SDL_RLEBlit(), UnRLEAlpha(), SDL_Rect::w, SDL_Surface::w, SDL_Rect::x, and SDL_Rect::y.

Referenced by SDL_CalculateBlit(), SDL_FreeSurface(), SDL_LockSurface(), SDL_MapSurface(), and SDL_RLESurface().

1541 {
1542  if (surface->flags & SDL_RLEACCEL) {
1543  surface->flags &= ~SDL_RLEACCEL;
1544 
1545  if (recode && !(surface->flags & SDL_PREALLOC)) {
1546  if (surface->map->info.flags & SDL_COPY_RLE_COLORKEY) {
1547  SDL_Rect full;
1548 
1549  /* re-create the original surface */
1550  surface->pixels = SDL_malloc(surface->h * surface->pitch);
1551  if (!surface->pixels) {
1552  /* Oh crap... */
1553  surface->flags |= SDL_RLEACCEL;
1554  return;
1555  }
1556 
1557  /* fill it with the background color */
1558  SDL_FillRect(surface, NULL, surface->map->info.colorkey);
1559 
1560  /* now render the encoded surface */
1561  full.x = full.y = 0;
1562  full.w = surface->w;
1563  full.h = surface->h;
1564  SDL_RLEBlit(surface, &full, surface, &full);
1565  } else {
1566  if (!UnRLEAlpha(surface)) {
1567  /* Oh crap... */
1568  surface->flags |= SDL_RLEACCEL;
1569  return;
1570  }
1571  }
1572  }
1573  surface->map->info.flags &=
1575 
1576  SDL_free(surface->map->data);
1577  surface->map->data = NULL;
1578  }
1579 }
#define SDL_COPY_RLE_COLORKEY
Definition: SDL_blit.h:42
int SDL_RLEBlit(SDL_Surface *surf_src, SDL_Rect *srcrect, SDL_Surface *surf_dst, SDL_Rect *dstrect)
Definition: SDL_RLEaccel.c:452
Uint32 colorkey
Definition: SDL_blit.h:69
Uint32 flags
Definition: SDL_surface.h:71
struct SDL_BlitMap * map
Definition: SDL_surface.h:88
void * pixels
Definition: SDL_surface.h:75
void SDL_free(void *mem)
int x
Definition: SDL_rect.h:66
int w
Definition: SDL_rect.h:67
#define NULL
Definition: begin_code.h:143
static SDL_bool UnRLEAlpha(SDL_Surface *surface)
int h
Definition: SDL_rect.h:67
#define SDL_COPY_RLE_ALPHAKEY
Definition: SDL_blit.h:43
#define SDL_FillRect
void * data
Definition: SDL_blit.h:90
#define SDL_malloc
int y
Definition: SDL_rect.h:66
SDL_BlitInfo info
Definition: SDL_blit.h:91
#define SDL_PREALLOC
Definition: SDL_surface.h:53
A rectangle, with the origin at the upper left.
Definition: SDL_rect.h:64
#define SDL_RLEACCEL
Definition: SDL_surface.h:54