SDL 1.3: Beyond scaling

Still thinking about ways to bridge the gap between Direct3D and
OpenGL (and software rendering) without making a complete mess of the
API and/or the backend implementations.

Considering the semantics of SDL_BlitSurface() and SDL_RenderCopy(),
it seems logical to handle quads pretty much like OpenGL, with
explicit texture coordinates. That is, you specify four source
vertices (“texcoords”) and four destination coordinates;

int SDL_RenderCopyQuad(
	SDL_TextureID textureID,
	int srcX0, int srcY0,
	int srcX1, int srcY1,
	int srcX2, int srcY2,
	int srcX3, int srcY3,
	int dstX0, int dstY0,
	int dstX1, int dstY1,
	int dstX2, int dstY2,
	int dstX3, int dstY3,
	int blendMode, int scaleMode);

(Eww… Too many arguments for my taste - but you get the idea.) This
preserves the current logic that you can blit from an area inside a
texture; not just the entire texture. I also think this is the most
useful way of doing it.

A simpler alternative would be the basic “stretch the texture so it’s
corners meet the respective vertices”. That is, texture coordinates
are implicitly fixed to the corners of the texture. All src*n
arguments removed from the prototype above, that is.

However, I think this limits the usefullness of this feature too much,
in relation to the extra work of doing it “properly”. (I know there
are issues with explicit texture coords - more on that below.)

Anyone here who have tried doing serious stuff using an API where you
cannot specify texture coordinates explicitly? Wasn’t the old Flash
2D stuff like that…? (People have made 3D games with that.) How
severe is this restriction in real life applications?

Anyway, with implicit texture coordinates, one does not have to worry
about what happens if you run off the edge of the texture, because
that will never happen! With explicit texture coordinates, it’s
perfectly possible to end up with a final rendering area with eight
sides. (Or worse, if coordinates are allowed to be twisted, ie
butterflies instead of quads.)

Simple solution: Just don’t allow off-texture texcoords, and don’t
allow “twisted” (butterfly shaped, non-convex) quads in texture
space. Clamp, fail or whatever if the application tries these things.
That way, implementations can make the assumptions that the
destination vertices define a zone of pixels that should all be
affected, and that there is valid texture data for every pixel
rendered.

Next problem; implementation: Rendering polygons (even triangles) is
not quite as straightforward as rendering non rotated rectangles. No
rocket science though, and it’s been done countless times before. And
of course, OpenGL and Direct3D will do this automatically - probably
even in hardware.

However, what happens when blit plugins (as suggested by the 1.3 TODO)
are thrown in the mix? Does every blit plugin have to implement this
logic? Does every blit plugin have to implement both this and the
plain rectangular blit call?

How about a call that renders into a trapezoid shaped destination
area? (That is, an SDL_Rect + bottom left and bottom right offsets,
or something like that.) Not much harder to handle than a plain
rectangle, but it’s sufficient for rendering anything from triangles
through complex polygons.

Oh, and this also makes it more reasonable to support off-texture
texcoords and/or non-convex quads if desired, because we only need
one central polygon splitter implementation to deal with such things.
(One might have to use this with OpenGL and Direct3D as well, for
concistent behavior across backends.)

//David Olofson - Programmer, Composer, Open Source Advocate

.------- http://olofson.net - Games, SDL examples -------.
| http://zeespace.net - 2.5D rendering engine |
| http://audiality.org - Music/audio engine |
| http://eel.olofson.net - Real time scripting |
’-- http://www.reologica.se - Rheology instrumentation --’

Still thinking about ways to bridge the gap between Direct3D and
OpenGL (and software rendering) without making a complete mess of the
API and/or the backend implementations.

Considering the semantics of SDL_BlitSurface() and SDL_RenderCopy(),
it seems logical to handle quads pretty much like OpenGL, with
explicit texture coordinates. That is, you specify four source
vertices (“texcoords”) and four destination coordinates;

Naw, OpenGL got that part right. Just use a subset of the existing
OpenGL API for rendering primitive. Use begin() and end() and coord(x,
y) and textCoord(u, v) and so on. It is easy to implement, handles all
primitives nicely and most people are already familiar with it.

I buried a little renderer that works that way in
http://gameprogrammer.com/polyfonts/polyfonts.html I called is something
like sgl. If you are rendering into an OpenGL buffer it just calls the
OpenGL functions, and if you are not then it does the operation in
software. Right now it only supports solid colors but adding texture
support wouldn’t take that long. The whole thing is only 7 function
calls but it supports all (or at least most) of the OpenGL graphic
primitives as well as a clear buffer and swap buffer function. Take a
look at it.

	Bob PendletonOn Sat, 2006-08-19 at 22:06 +0200, David Olofson wrote:

int SDL_RenderCopyQuad(
SDL_TextureID textureID,
int srcX0, int srcY0,
int srcX1, int srcY1,
int srcX2, int srcY2,
int srcX3, int srcY3,
int dstX0, int dstY0,
int dstX1, int dstY1,
int dstX2, int dstY2,
int dstX3, int dstY3,
int blendMode, int scaleMode);

(Eww… Too many arguments for my taste - but you get the idea.) This
preserves the current logic that you can blit from an area inside a
texture; not just the entire texture. I also think this is the most
useful way of doing it.

A simpler alternative would be the basic “stretch the texture so it’s
corners meet the respective vertices”. That is, texture coordinates
are implicitly fixed to the corners of the texture. All src*n
arguments removed from the prototype above, that is.

However, I think this limits the usefullness of this feature too much,
in relation to the extra work of doing it “properly”. (I know there
are issues with explicit texture coords - more on that below.)

Anyone here who have tried doing serious stuff using an API where you
cannot specify texture coordinates explicitly? Wasn’t the old Flash
2D stuff like that…? (People have made 3D games with that.) How
severe is this restriction in real life applications?

Anyway, with implicit texture coordinates, one does not have to worry
about what happens if you run off the edge of the texture, because
that will never happen! With explicit texture coordinates, it’s
perfectly possible to end up with a final rendering area with eight
sides. (Or worse, if coordinates are allowed to be twisted, ie
butterflies instead of quads.)

Simple solution: Just don’t allow off-texture texcoords, and don’t
allow “twisted” (butterfly shaped, non-convex) quads in texture
space. Clamp, fail or whatever if the application tries these things.
That way, implementations can make the assumptions that the
destination vertices define a zone of pixels that should all be
affected, and that there is valid texture data for every pixel
rendered.

Next problem; implementation: Rendering polygons (even triangles) is
not quite as straightforward as rendering non rotated rectangles. No
rocket science though, and it’s been done countless times before. And
of course, OpenGL and Direct3D will do this automatically - probably
even in hardware.

However, what happens when blit plugins (as suggested by the 1.3 TODO)
are thrown in the mix? Does every blit plugin have to implement this
logic? Does every blit plugin have to implement both this and the
plain rectangular blit call?

How about a call that renders into a trapezoid shaped destination
area? (That is, an SDL_Rect + bottom left and bottom right offsets,
or something like that.) Not much harder to handle than a plain
rectangle, but it’s sufficient for rendering anything from triangles
through complex polygons.

Oh, and this also makes it more reasonable to support off-texture
texcoords and/or non-convex quads if desired, because we only need
one central polygon splitter implementation to deal with such things.
(One might have to use this with OpenGL and Direct3D as well, for
concistent behavior across backends.)

//David Olofson - Programmer, Composer, Open Source Advocate

.------- http://olofson.net - Games, SDL examples -------.
| http://zeespace.net - 2.5D rendering engine |
| http://audiality.org - Music/audio engine |
| http://eel.olofson.net - Real time scripting |
’-- http://www.reologica.se - Rheology instrumentation --’


SDL mailing list
SDL at libsdl.org
http://www.libsdl.org/mailman/listinfo/sdl


±-------------------------------------+

I did have a look at sgl some time ago, and looked a bit closer now. A
lot of functionality in some 1500 lines, including specialized inner
loops for different pixel formats. :slight_smile:

Now, assuming we have implementation of this + texture support in SDL
sorted (people to do the software implementation and wiring of the
API to OpenGL and Direct3D), how does this impact the rest of SDL?
Can this “beyond scaled rectangular blits” stuff be a separate
subsystem, or does it have to be integrated with blit plugins and
stuff to make sense?

Plugins could perhaps be hooked in on the edge list or span level, to
avoid reimplementing the higher levels… A minimalistic yet complete
plugin could get away with supporting only this interface, as it
can handle straight and scaled blits just fine.

Or, do we implement an add-on library that provides a software
implementation, along with OpenGL and Direct3D implementations? What
are the real disadvantages with this approach?

//David Olofson - Programmer, Composer, Open Source Advocate

.------- http://olofson.net - Games, SDL examples -------.
| http://zeespace.net - 2.5D rendering engine |
| http://audiality.org - Music/audio engine |
| http://eel.olofson.net - Real time scripting |
’-- http://www.reologica.se - Rheology instrumentation --'On Sunday 20 August 2006 04:18, Bob Pendleton wrote:

On Sat, 2006-08-19 at 22:06 +0200, David Olofson wrote:

Still thinking about ways to bridge the gap between Direct3D and
OpenGL (and software rendering) without making a complete mess of
the API and/or the backend implementations.

Considering the semantics of SDL_BlitSurface() and
SDL_RenderCopy(),
it seems logical to handle quads pretty much like OpenGL, with
explicit texture coordinates. That is, you specify four source
vertices (“texcoords”) and four destination coordinates;

Naw, OpenGL got that part right. Just use a subset of the existing
OpenGL API for rendering primitive. Use begin() and end() and
coord(x, y) and textCoord(u, v) and so on. It is easy to implement,
handles all primitives nicely and most people are already familiar
with it.

I buried a little renderer that works that way in
http://gameprogrammer.com/polyfonts/polyfonts.html I called is
something like sgl. If you are rendering into an OpenGL buffer it
just calls the OpenGL functions, and if you are not then it does the
operation in software. Right now it only supports solid colors but
adding texture support wouldn’t take that long. The whole thing is
only 7 function calls but it supports all (or at least most) of the
OpenGL graphic primitives as well as a clear buffer and swap buffer
function. Take a look at it.

[…]

Plugins could perhaps be hooked in on the edge list or span level,
to avoid reimplementing the higher levels… A minimalistic yet
complete plugin could get away with supporting only this
interface, as it can handle straight and scaled blits just fine.
[…]

BTW, maybe blit plugins don’t really mix with hardware accelerated
backends anyway? Indeed, it can be done, but actually accelerating it
is a bit harder…

Are blit plugins supposed to be implemented as pixel shaders when
running over OpenGL or Direct3D, or in the idea that blit plugins are
for software blits only, regardless of backend?

//David Olofson - Programmer, Composer, Open Source Advocate

.------- http://olofson.net - Games, SDL examples -------.
| http://zeespace.net - 2.5D rendering engine |
| http://audiality.org - Music/audio engine |
| http://eel.olofson.net - Real time scripting |
’-- http://www.reologica.se - Rheology instrumentation --'On Sunday 20 August 2006 16:08, David Olofson wrote:

Still thinking about ways to bridge the gap between Direct3D and
OpenGL (and software rendering) without making a complete mess of
the API and/or the backend implementations.

Considering the semantics of SDL_BlitSurface() and
SDL_RenderCopy(),
it seems logical to handle quads pretty much like OpenGL, with
explicit texture coordinates. That is, you specify four source
vertices (“texcoords”) and four destination coordinates;

Naw, OpenGL got that part right. Just use a subset of the existing
OpenGL API for rendering primitive. Use begin() and end() and
coord(x, y) and textCoord(u, v) and so on. It is easy to implement,
handles all primitives nicely and most people are already familiar
with it.

I buried a little renderer that works that way in
http://gameprogrammer.com/polyfonts/polyfonts.html I called is
something like sgl. If you are rendering into an OpenGL buffer it
just calls the OpenGL functions, and if you are not then it does the
operation in software. Right now it only supports solid colors but
adding texture support wouldn’t take that long. The whole thing is
only 7 function calls but it supports all (or at least most) of the
OpenGL graphic primitives as well as a clear buffer and swap buffer
function. Take a look at it.

I did have a look at sgl some time ago, and looked a bit closer now. A
lot of functionality in some 1500 lines, including specialized inner
loops for different pixel formats. :slight_smile:

Thank you!

Now, assuming we have implementation of this + texture support in SDL
sorted (people to do the software implementation and wiring of the
API to OpenGL and Direct3D), how does this impact the rest of SDL?
Can this “beyond scaled rectangular blits” stuff be a separate
subsystem, or does it have to be integrated with blit plugins and
stuff to make sense?

The way sgl works is that it identifies the type of the buffer it is
being asked to work on and then based on the type it either calls OpenGL
or it does the job in software. I can do that in a library because
support for OpenGL is already in SDL. OTOH, it won’t work for DirectX
(or anything else) because (AFAIK) you can not use DirectX inside an SDL
program. But, if you are using the DirectX back end for SDL you can make
DirectX calls from inside of SDL. It looks like this code would have to
be built into SDL.

Plugins could perhaps be hooked in on the edge list or span level, to
avoid reimplementing the higher levels… A minimalistic yet complete
plugin could get away with supporting only this interface, as it
can handle straight and scaled blits just fine.

Plugins could be handled that way, but it is likely that an accelerated
backend will provide the higher level primitives and so we should allow
them to provide those operations as well.

Or, do we implement an add-on library that provides a software
implementation, along with OpenGL and Direct3D implementations? What
are the real disadvantages with this approach?

I’m not sure you can provide a DirectX add on library for SDL. It would
need access to internal SDL state information. I think the key is to
move all graphic operations out of the huge SDL context and move them to
per-buffer contexts. Then each buffer can be identified and a graphics
context constructed for that buffer. That context can provide pointers
to primitive level operations and/or scan line operations and we can
have a nice layered approach to implementing graphics operations on a
per buffer basis.

	Bob Pendleton

	Bob PendletonOn Sun, 2006-08-20 at 16:08 +0200, David Olofson wrote:

On Sunday 20 August 2006 04:18, Bob Pendleton wrote:

On Sat, 2006-08-19 at 22:06 +0200, David Olofson wrote:

//David Olofson - Programmer, Composer, Open Source Advocate

.------- http://olofson.net - Games, SDL examples -------.
| http://zeespace.net - 2.5D rendering engine |
| http://audiality.org - Music/audio engine |
| http://eel.olofson.net - Real time scripting |
’-- http://www.reologica.se - Rheology instrumentation --’


SDL mailing list
SDL at libsdl.org
http://www.libsdl.org/mailman/listinfo/sdl


±-------------------------------------+