setTransformOriginPoint not working as expected - c++

I inherited from the QGraphicsObject and created a new class that has a pixmap and sets its transform origin point to:
setTransformOriginPoint(boundingRect().center());
But when I call setRotation() on the my class (which is added to a QGraphicsView using the scene), the rotation doesn't use the center as the rotation anchor. How can I set the center to be the anchor of the rotation ? Thanks !
More information: calling setRotation() outside of a sceneEvent function it works, but inside a sceneEvent, upon a pinch gesture, the origin point doesn't work.

Draw pixmap at QRect(0, 0, pixmap.width(), pixmap.height(). Use this rectangle for bounding rect also. Use setPos to move the item around the scene. Use setTransformOriginPoint(pixmap.width() / 2, pixmap.height() / 2) to set the origin point. These coordinates are in the item coordinates, so they should point at the pixmap's center regardless of the item's position.

Related

How can I redefine where (0,0) of a QGraphicsItem is?

I've a custom QGraphicsItem which draws nothing but is parent to other QGraphicsItems (like QGraphicsRectItem and so on). My top-level item has (0,0) somewhere "inside" the children Items. This is very inconvenient. I would like to shift the origin to the upper left corner of childrenBoundingRect().
In the picture I've (0,0) of my top-level item somewhere inside of my children items (solid arrow). I would like to shift the origin to the dashed lines. How can I do that?
As result I expect that positioning of the top-level item will be more convenient.
Examples for overriding QGraphicsItem often show the boundingRect() function originating from (0,0). Changing this will change the origin. So, for example, to change it to the centre, where width and height are variables stored internally in the class, you can do this: -
QRectF boundingRect() const
{
return (-width / 2, -height / 2, width, height);
}

Ignore transformation of QGraphicsItem's shape

My reimplemented QGraphicsItem draws a circle. It has flag ItemIgnoresTransformations, so it has always the same size when scaling. Should I set transformations manually for item's shape function to be accurate or there exists easy way? I need shape function for processing mouse events for this circle in QGraphicsScene.

QGraphicsScene image pos pixmap

I am using Qt Graphics Framework for displaying an image. I have opened a raw image in subclassed QGraphicsScene in QGraphicsView using addPixmap(). I have added zoom feature by using scale function and drag mode is set as scroll hand drag. Now, I need to get the pixel coordinates within the scene on mouse hover such that the x and y value show the pixel in the image (drawn by pixmap) the mouse is currently pointing to. I tried using pos() but it didn't work.
Here is the code from Widget.cpp:
img = openImage(dirPath2.toLocal8Bit().data(),
sizeX,sizeY,file_heade,scan_heade,bpp,sign);
QPixmap x = QPixmap(sizeX,sizeY);
x.convertFromImage(img,Qt::AutoColor);
scene->addPixmap(x);
ui->disp_img->setDragMode(QGraphicsView::ScrollHandDrag);
GraphicsScene.h:
class GraphicsScene : public QGraphicsScene {
public:
GraphicsScene(QWidget *parent) : QGraphicsScene(parent){}
};
(preferably the pixmap coordinates but even that doesn't happen and if the values change when zoomed I will use scale factor to get the original values)
I suggest you start by reading about Qt's Graphics Coordinate System.
There are various layers of coordinate systems and you need to think about those with which you dealing with. At the top layer is the screen (or view), which is where the mouse coordinates reside.
The next layer from the view is the graphics scene. Graphics items, such as the QGraphicsPixmapItem which you added with addPixmap, reside here. The graphics scene can be visualised as a world of items, each with there own position and orientation.
Moving to the last coordinate system is an item's local coordinate system. If, for example, we take a rectangle, it may have local coordinates of (-5, -5, 10, 10) for (x, y, w, h). This item is then placed in the scene at some position. If its position is the origin of the scene (0,0), then the item's local coordinates would read the same as its scene coordinates.
However, if we move the rectangle +5 units in x-axis, its local coordinates are the same, but its scene coordinates would now be (0, -5, 10, 10).
Likewise, the view (QGraphicsScene) is a window into the scene and can be looking at the whole scene, or just part of it. As the view's top left coordinate is (0,0), it may map onto (0,0) of the scene, or may not, depending on what area of the scene the view is looking at.
So, by getting a mouse position you're starting in the view's coordinates and need to convert to the scene's coordinate system. Fortunately, Qt provides lots of useful functions for this at every level.
To convert the mouse coordinates from the view to the scene, you can use the view's mapToScene function.
Using the scene coordinates you can then get an item and map that to the local coordinate's of the item with the item's mapFromScene.

QGraphicsView and QGraphicsScene coordinate systems

in Qt 4.8 i have create a QGraphicsView and a DynamicRadarScene(derived from QGraphicsScene):
QGraphicsView* view = new QGraphicsView;
view->setMinimumSize(800, 600);
DynamicRadarScene* _scene = new DynamicRadarScene(mode, channel_types, this);
view->setScene(_scene);
What is the coordinate system of QGraphicsScene? (0,0) is from upper left corner?
How can i draw an item in the upper right corner of the scene (i have set it 800x600: view->setMinimumSize(800, 600);)?
If i resize the widget and so i resize the QGraphicsView, how can move the item i have drawn before to remain in the upper left corner?
Yes, the upper left corner is generally the coordinate of (0,0) in a graphics scene. What you need to consider is that a QGraphicsView is like a window looking into a world (the QGraphicsScene). You set the view to look at an area or the scene, which may be all or just part of the scene.
Once the scene and view are setup, you can then add QGraphicsItems / QGraphicsObjects or instances of classes derived from those by using functions such as QGraphicsScene::addItem. These items are positioned in the scene and draw themselves.
i (sic) resize the widget and so i resize the QGraphicsView
You can change the QGraphicsView position and dimensions, but then the items in the scene will remain in the same place within the scene. Usually you would set up the scene and view and then move / resize the graphics items / objects within the scene, often with the setPos function: QGraphicsItem::setPos(). This sets the position of the item, relative to its parent. If the item has no parent, it sets the position of the item in the scene.
QGraphicsScene has property sceneRect. If it is not set then it is auto adjusted depending on scene content. This can give a filling that origin of coordinating is in some strange place or even that it is mobile.
Set this property. See also this.

Cocos2d-x - Understanding positioning sprites on screen

Can anyone provide some basic pointers on placing CCSprites on screen?
Example:
CCSize s = CCDirector::sharedDirector()->getWinSize();
With s, say I wanted to position a sprite on the very bottom of the screen starting at 0, think something like grass.
if I am running at 1024 x 768, middle is:
setPosition( ccp(s.width/2, s.height/2) );
so starting all the way left and middle would be:
setPosition( ccp(0, s.height/2) );
So how do I get farther down?
setPosition( 0, s.height) );
This puts me starting at the top left and staying along the top of the screen.
Any help would be appreciated.
Position is relative to the sprite's parent, as well as its anchorPoint.
anchorPoint generally ranges from 0 to 1 for each coordinate, with a default of 0.5. I say "generally" because it can really be any value, but ranges outside of 0-1 place you outside of the bounds of the sprite.
For example, an anchorPoint of (0,0) makes positions relative to the bottom left. (1,0) is the bottom right, (0,1) is the top left and (1,1) is the top right. (0.5,0.5) is the very center of the sprite, which is the default.
Basically you just multiple the value by the width to get the relative position.
If you want to place a sprite at the very bottom of the screen (the bottom left corner aligned with the bottom left corner of the screen), you can do it multiple ways, based on the anchorPoint alone.
With the default anchorPoint of (0.5,0.5), the position would be (sprite.contentSize.width/2, sprite.contentSize.height/2).
If you set the anchorPoint to (0,0), the same position is obtained by simply (0,0).
If you wanted to move that sprite to the very center of the screen (the center of the sprite right in the middle), with an anchorpoint of (0.5, 0.5), the position would be (s.width/2, s.height/2).
This is all assuming you are adding a sprite to a parent the size of the screen, which is where the 2nd part of positioning comes in.
Position is also relative to the sprite's parent - which could be any other CCNode (CCLayer, another CCSprite, etc).
The way to think of that is not much different than adding a full screen node - except think in terms of the parent's size and position, not the screen.
Also Just to add something, all buttons start out in the middle of the screen then you can move them from there. if you wanted to button at (0,0):
CCLabelTTF *label1 = [CCLabelTTF labelWithString:#"Press Me!" fontName:#"Marker Felt" fontSize:20];
CCMenuItemLabel *button1 = [CCMenuItemLabel itemWithLabel:label1 block:^(id sender) { NSLog(#"button1 pressed"); }];
button1.position = ccp(-(s.width/2) , -(s.height/2)); // <---