   Draw wide texture between two points
  Hi all. Trying to implement effect of lazer shooting using 2D sprite in OpenGl withgluOrtho2D(0, width, height, 0).What i want to have: draw wide texture (128x26) between points A and B within 1 sec,the coordinates of the points A and B are changed during this seccond. The texture must be dynamically scaled by weight(depends on the distance between A and B), but height must be constant(in my case 16 pixels)The main purpose is to keep algorithm as simple as possible:for example i want to avoid to use glRotatef function, because i have to calculate angle between A and B within game loop. I believe that exist some simple resolution of my problem. What i want is to draw wide texture between two points.My last approach is following:x, y - coordinate of point Axt, yt - coordinate of point Bh - desired texture heightdef draw_tex_inRect((x, y), (xt, yt), h, tex):    glBindTexture(GL_TEXTURE_2D, tex)    # Send four vertices to draw a quad    glBegin(GL_QUADS)    glTexCoord2f(0, 0); glVertex2f(x - h/2, y - h/2)    glTexCoord2f(1, 0); glVertex2f(xt + h/2, yt - h/2)    glTexCoord2f(1, 1); glVertex2f(xt + h/2, yt + h/2)    glTexCoord2f(0, 1); glVertex2f(x - h/2, y + h/2)    glEnd()But disadvantage of this method is: when angle between A and B is aimed to 90 or 270 then texture height is aimed to 0. This problem is illustrated on the picture belowGood variant:http://i47.tinypic.com/1z7w1z.jpgAs u may see here angle is aimed to 0Bad variant:http://i46.tinypic.com/21cwmb.jpgAs u may see here angle is aimed to 90(270), and that is why texture height is decreasing(effect that i want to avoid)def resize(width, height):    glViewport(0,0,width, height)    glMatrixMode(GL_PROJECTION)    glLoadIdentity()    gluOrtho2D(0, width, height, 0)    glDisable(GL_DEPTH_TEST)    glMatrixMode(GL_MODELVIEW)    glLoadIdentity()Maybe someone have any idea how to implement this correctly? Many thanks in advance[Edited by - diverlin on July 6, 2010 12:53:54 PM]
  Right I see.You have to rotate the lazer beam quad, either by applying a rotational matrix or by doing the math yourself.Im going now work now, Ill post some example code on the second option in a bit :)   ;  Hi empirical2Quote:Original post by empirical2You have to rotate the lazer beam quad, either by applying a rotational matrix or by doing the math yourself.Yes, indeed. Sorry for my "many words", it's hard to generate strict question if you are beginner in graphic and + u English is not native language. Anyway, thanks for diving into my problem and "my" not brilliant English :D Quote:Im going now work now, Ill post some example code on the second option in a bit :)Looking forward for u help/advices/ideas.;  The easiest would be something like this (C++) off the top of my head....I have not tested this and a suck at math so if its at the wrong angles try switching x-xt to xt-x (same with y-yt)float XL=x-xt,YL=y-ytfloat Angle=atan2(XL,YL);float Len=sqrt((XL*XL)+(YL*YL));glPushMatrix();glRotate(Angle,0,0,1.0f);glTranslate(x,y,0);glBegin(GL_QUADS)glTexCoord2f(0, 0); glVertex2f(- h/2,0);glTexCoord2f(1, 0); glVertex2f(h/2, Len);glTexCoord2f(1, 1); glVertex2f(h/2, Len);glTexCoord2f(0, 1); glVertex2f(- h/2, 0);glEnd();glPopMatrix();This is for if you want to do the math in your own application. Now this one I have just tested (with lines) so should work//Get the distance between the points on each axisfloat LX=x-xt;float LY=yt-y;//Calculate the length the quad needs to be and the sine & cosine values required for calculate the rotation of each pointfloat Len=sqrt((LX*LX)+(LY*LY));float TheSin=LX/Len;float TheCos=LY/Len;float h=5;//Matrix math is hard :( float X1=(-h*TheCos) - (0*TheSin)+x,Y1=(-h*TheSin) + (0*TheCos)+y;float X2=( h*TheCos) - (0*TheSin)+x,Y2=( h*TheSin) + (0*TheCos)+y;float X3=( h*TheCos) - (Len*TheSin)+x,Y3=( h*TheSin) + (Len*TheCos)+y;float X4=(-h*TheCos) - (Len*TheSin)+x,Y4=(-h*TheSin) + (Len*TheCos)+y;//Draw the quad!glBegin(GL_QUADS)glTexCoord2f(0, 0); glVertex2f(X1,Y1,0);glTexCoord2f(0, 0); glVertex2f(X2,Y2,0);glTexCoord2f(0, 0); glVertex2f(X3,Y3,0);glTexCoord2f(0, 0); glVertex2f(X4,Y4,0);glEnd(GL_QUADS)HTH;Quote:for example i want to avoid to use glRotatef function, because i have to calculate angle between A and B within game loop.Why do you want to avoid calculating the angle within the game loop?There are other ways you could do it though, if need be. One would be to construct a basis from the vectors A and B, and then compute the corners of the quad manually from this basis. (Ask if you need further details.)   ;  You don't even need trigonometry: since angles are 90 degrees, all you have to do is swap the x,y coordinates to rotate.rotate 90 deg CW: x,y -> y,-xrotate 90 deg CCW: x,y ->-y,xSo you calculate the direction vector, you normalize it, then you rotate it in both directions and multiply it with the height/thickness of the beam. You add the two vectors to both ends of the beam, and you have your quad.   ;Quote:Original post by szecsYou don't even need trigonometry: since angles are 90 degrees, all you have to do is swap the x,y coordinates to rotate.Where did the OP say the angles were multiples of 90? (I can't find it anywhere in his posts...)   ;Quote:Original post by jykQuote:Original post by szecsYou don't even need trigonometry: since angles are 90 degrees, all you have to do is swap the x,y coordinates to rotate.Where did the OP say the angles were multiples of 90? (I can't find it anywhere in his posts...)The OP is speaking about a rotated rectangle no? And for some reason, the OP doesn't want to use rotation to make the quad.;  Oh, I see. (I thought you meant that the beams themselves were only oriented at 90-degree intervals.)   ;  empirical2 it works! Thanks a lotQuote:Original post by empirical2The easiest would be something like this (C++) off the top of my head....I have not tested this and a suck at math so if its at the wrong angles try switching x-xt to xt-x (same with y-yt)I was used the first variant of you code and adapt it to my program.I didn't check the second method because it has many of mathematic (python don't like this)So adapted code is following:def draw_tex_inRect((x, y), (xt, yt), h, tex):    XL= xt - x    YL= yt - y    Angle=atan2(YL,XL) * 57.295779    Len=sqrt((XL*XL)+(YL*YL))    glBindTexture(GL_TEXTURE_2D, tex)    glPushMatrix()    glTranslatef(x,y,0)    glRotatef(Angle,0,0,1.0)    glBegin(GL_QUADS)    glTexCoord2f(0, 0); glVertex2f(0,  -h/2 )    glTexCoord2f(1, 0); glVertex2f(Len,-h/2 )    glTexCoord2f(1, 1); glVertex2f(Len, h/2)    glTexCoord2f(0, 1); glVertex2f(0,  h/2)    glEnd()    glPopMatrix()And i also changed from gluOrtho2D(0, width, height, 0) to gluOrtho2D(0, width, 0, height)def resize(width, height):    glMatrixMode(GL_PROJECTION)    glLoadIdentity()    gluOrtho2D(0, width, 0, height)    glDisable(GL_DEPTH_TEST)    glMatrixMode(GL_MODELVIEW)    glLoadIdentity()Quote:Why do you want to avoid calculating the angle within the game loop?In my game i hope to use this effect very frequently(for example fire up to 100 space ships). I am using python as the  programming language. As known this language is slow in mathematic(for my game it's OK, because for most objects move i use pre-calculated lists of coordinates). So i wanted to think about optimization. My thought was that exist the easiest way to draw rotated texture without angle calculation, for example using coordinates of two points A and B (the texture_width will me in Vector AB, and texture_height all time is constant and perpendicular to Vector AB). But recently i got new point(i will be able to perform length and angle re-freshing not for each frame, let's say once per 5-7 frames. This should not kill perfomance and still provide good looking :). Quote:There are other ways you could do it though, if need be. One would be to construct a basis from the vectors A and B, and then compute the corners of the quad manually from this basis. (Ask if you need further details.)I may have wrong understanding but is this the same code as empirical2 provides?If it's not may you explain a little bit more about this?Cheers***Thank all for you support!   