-
Notifications
You must be signed in to change notification settings - Fork 103
Description
Yes, I know that I'm like 10 years late :) but I have found out an interesting problem while porting an older game (still using SDL 1.2). The game explicitly asks for SDL_SWSURFACE in SDL_SetVideoMode. And since its wish is granted, its author didn't need to worry about surface locking:
Lines 572 to 574 in 2a0b742
| * pixel format of the surface will not change. In particular, if the | |
| * SDL_HWSURFACE flag is not given when calling SDL_SetVideoMode(), you | |
| * will not need to lock the display surface before accessing it. |
Therefore the game doesn't lock surfaces neither checks SDL_MUSTLOCK. Now, this all works nice if the returned surface is the same dimension as requested. However what if isn't?
Then there's a big problem: SDL_UpdateRects tries to do the right thing and take the offset into consideration:
Lines 1096 to 1106 in 2a0b742
| if ( screen->offset ) { | |
| for ( i=0; i<numrects; ++i ) { | |
| rects[i].x += video->offset_x; | |
| rects[i].y += video->offset_y; | |
| } | |
| video->UpdateRects(this, numrects, rects); | |
| for ( i=0; i<numrects; ++i ) { | |
| rects[i].x -= video->offset_x; | |
| rects[i].y -= video->offset_y; | |
| } | |
| } else { |
However the game author doesn't care / know anything about offsets, he just accesses pixels and rightfully so as documentation explicitly discourages him to use MUSTLOCK / SDL_LockSurface. Outcome is clear, the game fills first 200 lines of the software surface while SDL_UpdateRects offers pixels to backends from an offset, leading to a shifted display.
So my question is ... if we were in 2010, what would have been your recommendation as fix?
- documentation update, i.e. encourage developers to always call
SDL_MUSTLOCKand tell the author to suck it up and fix his code? - when requesting software surfaces, always return the requested dimensions and do the offsetting in the backend?
- this would imply that
SDL_LockSurfaceandSDL_UpdateRectswouldn't need to worry about offsets for software surfaces in general
- this would imply that
- use the internal
SDL_ShadowSurfaceif dimensions do not match ? (this looks like the cleanest solution to me as it is very similar to the situation when we request a software surface and get a hardware one however currently we take dimensions fromSDL_VideoSurfacewhich is the one with "bad" dimensions) - ?
Of course, I'm at the liberty to choose any approach as both the game and SDL are open source but still, I'd appreciate some input and reasoning behind the current state.