Thanks jlnr ! I was sure that was the main "issue" there.
I will try to use the "1.0 - " trick. To be able to use a :single_texture flag would of course solve everything, but we would lose your optimizations, and I don't want that. Also, I plan to add some new methods, like you suggest, directly for any Gosu user, as long that he / she uses version >= 0.9 (I don't want to preserve compatibility with the old way of passing Gosu::Window to anything).
I'll try and let you know.
It will be maybe good to reference my new website as a french tutorial one of these days :
http://www.retrorender.netEven if it's still a really really early release :)
EDIT :
that way, it works :
class Gosu::GLTexInfo
def tex_coord_2d(x, y)
tex_x = self.left + x * (self.right - self.left)
tex_y = (self.bottom + y * (self.top - self.bottom))
glTexCoord2d(tex_x, tex_y)
end
def bottom_left; tex_coord_2d(0.0, 0.0); end
def bottom_right; tex_coord_2d(1.0, 0.0); end
def top_left; tex_coord_2d(0.0, 1.0); end
def top_right; tex_coord_2d(1.0, 1.0); end
end
class Gosu::Image
# x, y and z are relative to the center of the image
def draw_3d(x, y, z, options = {})
width, height = self.width, self.height
x, y, w, h = 0.0, 0.0, 1.0, 1.0
if options.has_key?(:rect)
# rect uses the convention [x, y, w, h], expressed in opengl (from 0.0 to 1.0, origin on bottom-left corner)
x, y, w, h = options[:rect][0].to_f, options[:rect][1].to_f, options[:rect][2].to_f, options[:rect][3].to_f
x = 0.0 if x < 0.0 or x > 1.0
y = 0.0 if y < 0.0 or y > 1.0
w = 0.0 if w < 0.0 or w > 1.0
h = 0.0 if h < 0.0 or h > 1.0
width, height = w * self.width, h * self.height
end
glBindTexture(GL_TEXTURE_2D, self.gl_tex_info.tex_name)
glEnable(GL_ALPHA_TEST)
glPushMatrix
glTranslate(x, y, z)
glScale(width, height, 1.0)
if options.has_key?(:rot)
# rot uses the convention [x, y, z], expressed in degrees
glRotate(options[:rot][0], 1, 0, 0)
glRotate(options[:rot][1], 0, 1, 0)
glRotate(options[:rot][2], 0, 0, 1)
end
glBegin(GL_QUADS)
self.gl_tex_info.tex_coord_2d(x, y); glVertex3f(-0.5, -0.5, 0.0)
self.gl_tex_info.tex_coord_2d(x + w, y); glVertex3f(0.5, -0.5, 0.0)
self.gl_tex_info.tex_coord_2d(x + w, y + h); glVertex3f(0.5, 0.5, 0.0)
self.gl_tex_info.tex_coord_2d(x, y + h); glVertex3f(-0.5, 0.5, 0.0)
glEnd
glPopMatrix
glDisable(GL_ALPHA_TEST)
end
end
So I can pass any value from 0.0 to 1.0 to both x and y in the method tex_coord_2d(x, y), or even use the 4 helpers to directly set the coordinate of one corner :)
So I can draw a Sprite in a 3D environnement, with crop and rotation, directly in one method call :)