Rotating a quad(?)
Blitz3D Forums/Blitz3D Programming/Rotating a quad(?)
| ||
Anybody got a quick/simple routine which can rotate a quad (set of 4 verts) in the same way as RotateImage works? This example code creates a bunch of quads in a single-surface container. You can move one of the quads around with the mouse. Press [W] to toggle wireframe view. This is how the quads are contructed and displayed on screen: The quad verts are located at 2d pixel coordinates. Each quad has a custom type holding the quads surface (container), vertex index number (top/left), and size (in pixels). I'm sure there was a function posted which rotated a set of quads using Sin()/Cos() NB: See the RotateQuad function ; Quad - Rotate? Const sw=640,sh=480 Graphics3D sw,sh,0,2 SetBuffer BackBuffer() HidePointer Type quadtype Field container ; conainter holding quad (surface) Field vert ; quads first vertex in container Field w,h ; quads width and height (in 2d pixels) End Type ; init 3d display (camera + quads pivot) spritecamera=CreateCamera() pivot2d=CreatePivot(spritecamera) aspect#=Float(GraphicsHeight())/Float(GraphicsWidth()) scale#=2.0/GraphicsWidth() PositionEntity pivot2d,-1,aspect,1.0001 ScaleEntity pivot2d,scale,scale,scale ; create a quad containter (surface) quadsurf=CreateQuadContainer(pivot2d) ; add random quads to container For num=1 To 50 NewQuad quadsurf,Rand(sw),Rand(sh),Rand(64),Rand(64),Rand(100),Rand(100),Rand(100) Next ; add quad to container (pos=0,0 size=90x80 color=green) quad1=NewQuad(quadsurf , 0,0 , 90,80 , $04,$f2,$07) MoveMouse 320,240 ; MAIN LOOP Repeat If KeyHit(17) ; [W] w=Not w WireFrame w EndIf If KeyHit(57) ; [SPACE] RotateQuad quad1, Rand(360) EndIf mx=MouseX() : my=MouseY() PositionQuad quad1,mx,my,0 RenderWorld Text 20,40,"[MOUSE] = move large green quad" Text 20,60,"[W] = Wireframe" Text 20,80,"[SPACE] = Rotate quad" Line mx,my+8,mx,my-8 Line mx+8,my,mx-8,my Flip Until KeyHit(1) End ; create a container (surface) for holding quads Function CreateQuadContainer(pivot) Local quadmesh=CreateMesh(pivot) Local surf=CreateSurface(quadmesh) EntityFX quadmesh,1+2 ScaleEntity quadmesh,1,-1,1 PositionEntity quadmesh,-0.5,0.5,0 Return surf End Function ; adds a new quad to an existing container Function NewQuad(surf,x,y,w,h,r=255,g=255,b=255) Local q.quadtype=New quadtype q\container=surf q\w=w : q\h=h q\vert=AddVertex(surf,x,y,0) AddVertex surf,x+w,y,0 AddVertex surf,x,y+h,0 AddVertex surf,x+w,y+h,0 AddTriangle surf,q\vert+0,q\vert+1,q\vert+2 AddTriangle surf,q\vert+3,q\vert+2,q\vert+1 For o=0 To 3 VertexColor surf,q\vert+o,r,g,b Next Return Handle(q) End Function ; position a quad at 2d pixel coordinates Function PositionQuad(qindex,x,y,z#=1.0001) Local q.quadtype=Object.quadtype(qindex) Local s=q\container , v=q\vert dx#=x-VertexX(s,v) : dy#=y-VertexY(s,v) : dz#=z-VertexZ(s,v) For o=0 To 3 VertexCoords s,v+o,VertexX(s,v+o)+dx,VertexY(s,v+o)+dy,VertexZ(s,v+o)+dz Next End Function ; rotate a quad set Function RotateQuad(qindex,ang) Local q.quadtype=Object.quadtype(qindex) Local s=q\container , v=q\vert ; not sure how to do this part ????????????? For o=0 To 3 ;; dx#=? : dy#=? VertexCoords s,v+o,VertexX(s,v+o)+dx,VertexY(s,v+o)+dy,VertexZ(s,v+o) Next End Function |
| ||
for each vertex: new_x = x * cos(angle) - y * sin(angle) new_y = x * sin(angle) + y * cos(angle) don't remember the z ... oh and this rotates around a center point so x and y values are distances from the quad center. So store these values and add your quads location to them after a rotate. |
| ||
Is this what you need ..; rotate a quad set Function RotateQuad(qindex,ang) Local q.quadtype=Object.quadtype(qindex) Local s=q\container , v=q\vert ; not sure how to do this part ????????????? For o=0 To 3 dx# = VertexX(s,v+o)*Cos(ang)-VertexY(s,v+o)*Sin(ang) dy# = VertexY(s,v+o)*Cos(ang)+VertexX(s,v+o)*Sin(ang) VertexCoords s,v+o,dx,dy,VertexZ( s,v+o) Next End Function |
| ||
I took the route of using a pivot point. I rotate the pivot point to where I want it to be and then transform the verts of the quad into the pivots coordinate space. Works pretty well. The variable names won't make sense to you guys, but basically:RotateEntity( GRendererVars\Pivot, 0, 0, InAngle# ) TFormPoint( X0#, Y0#, 0, GRendererVars\Pivot, 0 ) : X0# = TFormedX() : Y0# = TFormedY() TFormPoint( X1#, Y1#, 0, GRendererVars\Pivot, 0 ) : X1# = TFormedX() : Y1# = TFormedY() TFormPoint( X2#, Y2#, 0, GRendererVars\Pivot, 0 ) : X2# = TFormedX() : Y2# = TFormedY() TFormPoint( X3#, Y3#, 0, GRendererVars\Pivot, 0 ) : X3# = TFormedX() : Y3# = TFormedY() |
| ||
Brilliant help! Epic, I previously used a similar approach to yours but maybe not as elegant. I used a dumming quad, rotated it with RotateMesh, then copied the vert positions to the real quad to be rotated. |