Skip to content

Commit 5acd3a5

Browse files
committed
more changes to marginally improve performance + now using less memory per destination (20bytes -> 16)
1 parent 0325472 commit 5acd3a5

File tree

3 files changed

+28
-26
lines changed

3 files changed

+28
-26
lines changed

src_c/alphablit.c

+9-8
Original file line numberDiff line numberDiff line change
@@ -590,23 +590,24 @@ SoftBlitPyGame(SDL_Surface *src, SDL_Rect *srcrect, SDL_Surface *dst,
590590
}
591591

592592
void
593-
pg_multi_blitcopy(SDL_Surface *src, SDL_Surface *dst,
594-
BlitSequence *destinations)
593+
pg_multi_blitcopy(SDL_Surface *restrict src, SDL_Surface *restrict dst,
594+
BlitSequence *restrict destinations)
595595
{
596596
Py_ssize_t i;
597597
const int src_skip = src->pitch / 4;
598598
const int dst_skip = dst->pitch / 4;
599599

600+
Uint32 *const src_start = (Uint32 *)src->pixels;
601+
600602
for (i = 0; i < destinations->size; i++) {
601603
BlitDestination *item = &destinations->sequence[i];
602-
603-
const int src_pitch = item->w * sizeof(Uint32);
604-
605-
Uint32 *srcp32 = (Uint32 *)src->pixels + item->x + item->y * src_skip;
606604
Uint32 *dstp32 = item->pixels;
605+
int h = item->rows;
606+
const int copy_w = item->copy_w;
607+
Uint32 *srcp32 = src_start + item->src_offset;
607608

608-
while (item->h--) {
609-
memcpy(dstp32, srcp32, src_pitch);
609+
while (h--) {
610+
memcpy(dstp32, srcp32, copy_w);
610611
srcp32 += src_skip;
611612
dstp32 += dst_skip;
612613
}

src_c/surface.c

+16-15
Original file line numberDiff line numberDiff line change
@@ -2162,14 +2162,13 @@ surf_blits(pgSurfaceObject *self, PyObject *args, PyObject *keywds)
21622162
#define FBLITS_ERR_INVALID_SEQUENCE 21
21632163

21642164
int
2165-
_surf_fblits_item_check_and_blit(PyObject *src_surf, SDL_Surface *src,
2165+
_surf_fblits_item_check_and_blit(pgSurfaceObject *src_surf, SDL_Surface *src,
21662166
pgSurfaceObject *dest, int x, int y,
21672167
int blend_flags)
21682168
{
21692169
SDL_Rect dest_rect = {x, y, src->w, src->h};
21702170

2171-
if (pgSurface_Blit(dest, (pgSurfaceObject *)src_surf, &dest_rect, NULL,
2172-
blend_flags))
2171+
if (pgSurface_Blit(dest, src_surf, &dest_rect, NULL, blend_flags))
21732172
return BLITS_ERR_BLIT_FAIL;
21742173

21752174
return 0;
@@ -2257,6 +2256,7 @@ _surf_fblits_multiblit_item_check_and_blit(PyObject *src_surf,
22572256
Py_ssize_t current_size = 0;
22582257
SDL_Rect src_dest = {0, 0, src->w, src->h};
22592258
SDL_Rect temp, *argrect;
2259+
const SDL_Rect *clip_rect = &dst->clip_rect;
22602260
for (i = 0; i < destinations->size; i++) {
22612261
PyObject *item = seq_items[i];
22622262

@@ -2273,7 +2273,6 @@ _surf_fblits_multiblit_item_check_and_blit(PyObject *src_surf,
22732273
src_dest.x += suboffsetx;
22742274
src_dest.y += suboffsety;
22752275

2276-
SDL_Rect *clip_rect = &dst->clip_rect;
22772276
SDL_Rect clipped;
22782277
if (!SDL_IntersectRect(clip_rect, &src_dest, &clipped))
22792278
continue; /* Skip out of bounds destinations */
@@ -2282,12 +2281,12 @@ _surf_fblits_multiblit_item_check_and_blit(PyObject *src_surf,
22822281

22832282
d_item->pixels =
22842283
(Uint32 *)dst->pixels + clipped.y * dst->pitch / 4 + clipped.x;
2285-
2286-
d_item->w = clipped.w;
2287-
d_item->h = clipped.h;
2288-
2289-
d_item->x = src_dest.x < clip_rect->x ? clip_rect->x - src_dest.x : 0;
2290-
d_item->y = src_dest.y < clip_rect->y ? clip_rect->y - src_dest.y : 0;
2284+
d_item->copy_w = clipped.w * 4;
2285+
d_item->rows = clipped.h;
2286+
d_item->src_offset =
2287+
(src_dest.x < clip_rect->x ? clip_rect->x - src_dest.x : 0) +
2288+
(src_dest.y < clip_rect->y ? clip_rect->y - src_dest.y : 0) *
2289+
src->pitch / 4;
22912290
}
22922291

22932292
if (!(destinations->size = current_size)) {
@@ -2348,14 +2347,17 @@ _surf_fblits_blit(pgSurfaceObject *self, PyObject *item, int blend_flags,
23482347
return;
23492348
}
23502349

2350+
if (!src->w || !src->h)
2351+
return;
2352+
23512353
if (pg_TwoIntsFromObj(pos_or_seq, &x, &y) ||
23522354
(argrect = pgRect_FromObject(pos_or_seq, &temp))) {
23532355
if (argrect) {
23542356
x = argrect->x;
23552357
y = argrect->y;
23562358
}
2357-
*error = _surf_fblits_item_check_and_blit(src_surf, src, self, x, y,
2358-
blend_flags);
2359+
*error = _surf_fblits_item_check_and_blit(
2360+
(pgSurfaceObject *)src_surf, src, self, x, y, blend_flags);
23592361
return;
23602362
}
23612363

@@ -2403,9 +2405,8 @@ surf_fblits(pgSurfaceObject *self, PyObject *const *args, Py_ssize_t nargs)
24032405
Py_ssize_t i;
24042406
PyObject **sequence_items = PySequence_Fast_ITEMS(blit_sequence);
24052407
for (i = 0; i < PySequence_Fast_GET_SIZE(blit_sequence); i++) {
2406-
item = sequence_items[i];
2407-
2408-
_surf_fblits_blit(self, item, blend_flags, &destinations, &error);
2408+
_surf_fblits_blit(self, sequence_items[i], blend_flags,
2409+
&destinations, &error);
24092410

24102411
if (error)
24112412
goto on_error;

src_c/surface.h

+3-3
Original file line numberDiff line numberDiff line change
@@ -339,7 +339,7 @@
339339

340340
typedef struct {
341341
Uint32 *pixels;
342-
int w, h, x, y;
342+
int copy_w, rows, src_offset;
343343
} BlitDestination;
344344

345345
typedef struct {
@@ -368,8 +368,8 @@ SoftMultiBlitPyGame(SDL_Surface *src, SDL_Surface *dst, int blend_flags,
368368
BlitSequence *destinations);
369369

370370
void
371-
pg_multi_blitcopy(SDL_Surface *src, SDL_Surface *dst,
372-
BlitSequence *destinations);
371+
pg_multi_blitcopy(SDL_Surface *restrict src, SDL_Surface *restrict dst,
372+
BlitSequence *restrict destinations);
373373

374374
int
375375
premul_surf_color_by_alpha(SDL_Surface *src, SDL_Surface *dst);

0 commit comments

Comments
 (0)