I have seen in the raphael document that translate is depreciated and suggested to use transform instead. But my requirement is when i move an object i need the x, y or cx, cy need to updated to the server with latest value. This can be done easily using translate. But if i use transform it stores as Tx,y. How to get the modified x and y when using transform?
example
console.dir(page1);
var c1 = paper.circle(50,50,3);
c1.transform("T100,100");
here the cx and cy is still 50,50 but i need the value as 100,100
transform() will change the coordinate system. If you only need to "move" a shape, then you can just change its position attribute that can be cx, cy, x, y depending on the shape. The following is a raphael extension that adds methods nt_translate() and nt_scale() to shapes and sets and also adds two custom attributes translateNT and scaleNT to shapes. So if you do aCircle.nt_translate(10,10) the circle's cx and cy attributes will change and it will be translated without transform(). Hope that helps!
Related
I am try to create a bivariate map but I adjusted my projection incorrectly and can't figure out how to set it back. I used:
geo2xy _Y _X, proj(Mercator) replace
and now the map is zoomed out beyond where it should be. What is the best way to set it back to normal?
I have the next problem. I am trying to rotate a 3D model around all 3 axis at the same time. Meaning i want to rotate the model around the X axis, then the Y axis, then again the X and so forth by pressing the buttons on the keyboard. The problem is when i use XMMatrixRotationX, XMMatrixRotationY or XMMatrixRotationZ like this:
void Rotate(float radians_x, float radians_y, float radians_z)
{
DirectX::XMStoreFloat4x4(&_transfer.world, DirectX::XMMatrixTranspose(DirectX::XMMatrixRotationZ(radians_z)));
DirectX::XMStoreFloat4x4(&_transfer.world, DirectX::XMMatrixTranspose(DirectX::XMMatrixRotationY(radians_y)));
DirectX::XMStoreFloat4x4(&_transfer.world, DirectX::XMMatrixTranspose(DirectX::XMMatrixRotationX(radians_x)));
}
only the last rotation gets done. I want to be able to rotate the object around each of the axis by a specific angle (actually, radians), as you can see in the code. I have found out that the XMMatrixRotationAxis method does this, but it only takes one angle parameter, and i want to use a different one for each axis. Can anyone help me about how can this be done?
Also, i don't know what to send as a first parameter to the XMMatrixRotationAxis, it just says a vector of axis. I don't understand how do i access those, the methods i used in the code posted don't need to be sent any axis. I dont understand why is this necessary, or how to do it, in case this is the right solution.
Any help would be much appreciated.
I have found the answer here:
http://books.google.hr/books?id=7ZkLAAAAQBAJ&pg=PA251&lpg=PA251&dq=XMMatrixRotationQuaternion&source=bl&ots=xveQhsj-x_&sig=Ny6IdK1JNFBF99LyC_HY8b-y4tI&hl=hr&sa=X&ei=dtkQVOmmA8aXatfugZgL&ved=0CHEQ6AEwCA#v=onepage&q=XMMatrixRotationQuaternion&f=false
I have to use the XMMatrixRotationRollPitchYaw. The code now looks:
void Rotate(float radians_x, float radians_y, float radians_z)
{
DirectX::XMStoreFloat4x4(&_transfer.world, DirectX::XMMatrixTranspose(DirectX::XMMatrixRotationRollPitchYaw(radians_x, radians_y, radians_z)));
}
Works like a charm :)
1. Goal
My colleague and I have been trying to render rotated ellipsoids in Qt. The typical solution approach, as we understand it, consists of shifting the center of the ellipsoids to the origin of the coordinate system, doing the rotation there, and shifting back:
http://qt-project.org/doc/qt-4.8/qml-rotation.html
2. Sample Code
Based on the solution outlined in the link above, we came up with the following sample code:
// Constructs and destructors
RIEllipse(QRect rect, RIShape* parent, bool isFilled = false)
: RIShape(parent, isFilled), _rect(rect), _angle(30)
{}
// Main functionality
virtual Status draw(QPainter& painter)
{
const QPen& prevPen = painter.pen();
painter.setPen(getContColor());
const QBrush& prevBrush = painter.brush();
painter.setBrush(getFillBrush(Qt::SolidPattern));
// Get rectangle center
QPoint center = _rect.center();
// Center the ellipse at the origin (0,0)
painter.translate(-center.x(), -center.y());
// Rotate the ellipse around its center
painter.rotate(_angle);
// Move the rotated ellipse back to its initial location
painter.translate(center.x(), center.y());
// Draw the ellipse rotated around its center
painter.drawEllipse(_rect);
painter.setBrush(prevBrush);
painter.setPen(prevPen);
return IL_SUCCESS;
}
As you can see, we have hard coded the rotation angle to 30 degrees in this test sample.
3. Observations
The ellipses come out at wrong positions, oftentimes outside the canvas area.
4. Question
What is wrong about the sample code above?
Best regards,
Baldur
P.S. Thanks in advance for any constructive response?
P.P.S. Prior to posting this message, we searched around quite a bit on stackoverflow.com.
Qt image move/rotation seemed to reflect a solution approach similar to the link above.
In painter.translate(center.x(), center.y()); you shift your object by the amount of current coordinate which makes (2*center.x(), 2*center.y()) as a result. You may need:
painter.translate(- center.x(), - center.y());
The theory of moving an object back to its origin, rotating and then replacing the object's position is correct. However, the code you've presented is not translating and rotating the object at all, but translating and rotating the painter. In the example question that you've referred to, they're wanting to rotate the whole image about an object, which is why they move the painter to the object's centre before rotating.
The easiest way to do rotations about a GraphicsItem is to initially define the item with its centre in the centre of the object, rather than in its top left corner. That way, any rotation will automatically be about the objects centre, without any need to translate the object.
To do this, you'd define the item with a bounding rect for x,y,width,height with (-width/2, -height/2, width, height).
Alternatively, assuming your item is inherited from QGraphicsItem or QGraphicsObject, you can use the function setTransformOriginPoint before any rotation.
I am using QT and try to plot a graph with QGraphicsView and QGraphicsScene..i dont want any additional dependencies, thats why i dont use QWT. When i plot my data, at the moment i use
scene->drawLine(x1,y1,x2,y2,pen);
then this draws a line between the 2 points in the QGraphicScene. But this uses a top left x=0 y=0 system... i would like to use my own system like in the picture below. Another problem is that i have double values from -3 to +3..has anyone some experience with QGraphicScene and QGraphicsView and can tell me how i can accomplish this?
Try looking into QGraphicsView::setTransform. This matrix defines how "scene coordinates" are translated to "view coordinates", it's a common concept in graphics programming.
There are also convenience functions scale(), rotate(), translate() and shear() which modify the view's current transformation matrix.
So you could do something like this:
scale(1.0, -1.0); // invert Y axis
// translate to account for fact that Y coordinates start at -3
translate(0.0, 3.0);
// scale Y coordinates to height of widget
scale(1.0, (qreal)viewport()->size().height()/6.0);
And since this is dependent on the size of the widget, you'd also want to catch any resize events and reset the transformation matrix again there. Assuming you want "3" to represent the top of the viewport and "-3" the bottom.
I have a scene which contains objects located anywhere in space and I'm making a trackball-like interface.
I'd like to make it so that I can move 2 separate sliders to rotate it in x and y axes respectively:
glRotatef(drawRotateY,0.0,1.0f,0);
glRotatef(drawRotateX,1.0f,0.0,0.0);
//draw stuff in space
However, the above code won't work because X rotation will then be dependent on the Y rotation.
How can I achieve this without using gluLookAt()?
Edit:
I'd like to say that my implementation is even simpler than a trackball interface. Basically, if the x slider value is 80 and y slider is 60, rotate vertically 80 degrees and horizontally 60 degrees. I just need to make them independent of each other!
This code should get you started: http://www.cse.ohio-state.edu/~crawfis/Graphics/VirtualTrackball.html
It explains how to implement a virtual trackball using the current mouse position in the GL window.
You could probably use something like this:
Vector v = new Vector(drawRotateX, drawRotateY, 0);
float length = v.length();
v.normalize();
glRotatef(length, v.x, v.y, v.z);
When you say rotate vertically and horizontally, do you mean like an anti-aircraft gun - rotate around the vertical Z axis, to face in a particular compass heading (yaw) and then rotate to a particular elevation (pitch)?
If this is the case, then you just need to do your two rotations in the right order, and all will be well. In this example, you must do the 'pitch' rotation first, and then the 'yaw' rotation. All will work out fine.
If you mean something more complicated (eg. like the 'Cobra' spaceship in Elite) then you will need a more fiddly solution.