Results 1 to 19 of 19

Thread: Artifacts with custom QGraphicsItem

  1. #1
    Join Date
    Feb 2015
    Posts
    12
    Qt products
    Qt4 Qt5
    Platforms
    Unix/X11 Windows

    Default Artifacts with custom QGraphicsItem

    Hi,
    when using my custom QGraphicsItemi get artifacts in the GraphicsView.
    The artifacts appear when i "zoom out" by caling graphicsView->scale(0.2,0,2). Without scaling i don't see the artifacts.

    I have a 5x5 grid of my GraphicsItem objects, and the upper left is the parent of the other ones.
    I draw the bounding rects and they look good.


    Here is my paint method:
    Qt Code:
    1. void Tile::paint(QPainter *painter, const QStyleOptionGraphicsItem *option, QWidget *widget) {
    2. Q_UNUSED(widget);
    3.  
    4. painter->save();
    5.  
    6. if(!pixels.isNull()) {
    7.  
    8. painter->drawPixmap(QRect(0,0,w,h), pixels, pixels.rect());
    9.  
    10. }
    11.  
    12. painter->drawRect(boundingRect());
    13.  
    14. painter->restore();
    15. }
    To copy to clipboard, switch view to plain text mode 

    and my bounding rect method:

    Qt Code:
    1. QRectF Tile::boundingRect() const {
    2.  
    3. if(childItems().empty()) {
    4. return QRectF(-50,-50,w+100,h+100);
    5. } else {
    6. return QRectF(-100,-100,5*w+200,5*h+200);
    7. }
    8. }
    To copy to clipboard, switch view to plain text mode 


    I searched this forum and the web for solutions, but i couldn't solve it yet. Any ideads?

    Any idea?

    Cheers,
    Thomas

  2. #2
    Join Date
    Jan 2006
    Location
    Warsaw, Poland
    Posts
    33,359
    Thanks
    3
    Thanked 5,015 Times in 4,792 Posts
    Qt products
    Qt3 Qt4 Qt5 Qt/Embedded
    Platforms
    Unix/X11 Windows Android Maemo/MeeGo
    Wiki edits
    10

    Default Re: Artifacts with custom QGraphicsItem

    Where are you calling prepareGeometryChange()?
    Your biological and technological distinctiveness will be added to our own. Resistance is futile.

    Please ask Qt related questions on the forum and not using private messages or visitor messages.


  3. #3
    Join Date
    Feb 2015
    Posts
    12
    Qt products
    Qt4 Qt5
    Platforms
    Unix/X11 Windows

    Default Re: Artifacts with custom QGraphicsItem

    i called prepareGeometryChange() in the constructor of my QGraphicsItemSubclass, but i removed since it didn't change anything.
    Is it neccessary to call prepareGeometryChange() even if the bounding rect never changes?

    Now i call prepareGeometryChange() in the beginning of my paint() method, and the artifacts disappeared. Is this a suitable place to call prepareGeometryChange() or sould it be called only once and from somewhere else?

    Thanks!

  4. #4
    Join Date
    Jan 2006
    Location
    Warsaw, Poland
    Posts
    33,359
    Thanks
    3
    Thanked 5,015 Times in 4,792 Posts
    Qt products
    Qt3 Qt4 Qt5 Qt/Embedded
    Platforms
    Unix/X11 Windows Android Maemo/MeeGo
    Wiki edits
    10

    Default Re: Artifacts with custom QGraphicsItem

    Quote Originally Posted by ThomasS0 View Post
    i called prepareGeometryChange() in the constructor of my QGraphicsItemSubclass,
    That doesn't make sense.

    Is it neccessary to call prepareGeometryChange() even if the bounding rect never changes?
    Your boundingRect does change depending on whether your item has children or not.

    Is this a suitable place to call prepareGeometryChange()
    No. You should call it when boundingRect() changes.
    Your biological and technological distinctiveness will be added to our own. Resistance is futile.

    Please ask Qt related questions on the forum and not using private messages or visitor messages.


  5. #5
    Join Date
    Feb 2015
    Posts
    12
    Qt products
    Qt4 Qt5
    Platforms
    Unix/X11 Windows

    Default Re: Artifacts with custom QGraphicsItem

    thanks for you explanations.

    This is what i added now:
    Qt Code:
    1. QVariant Tile::itemChange(GraphicsItemChange change, const QVariant &value) {
    2.  
    3. //if(change == ItemChildAddedChange) {
    4. prepareGeometryChange();
    5. //}
    6.  
    7. return QGraphicsItem::itemChange(change, value);
    8. }
    To copy to clipboard, switch view to plain text mode 

    prepareGeometryChange() gets called this way, but the artifacts still appear.

    The only way to get rid of the artifacts that i found yet is to call prepareGeometryChange() in paint(), which leads to repeated redrawing and high cpu usage.
    The Tile class does not add its children itself, they are added from outside the class.
    Is my assumption right, that the boundingRect also needs to include the items children?

  6. #6
    Join Date
    Jan 2006
    Location
    Warsaw, Poland
    Posts
    33,359
    Thanks
    3
    Thanked 5,015 Times in 4,792 Posts
    Qt products
    Qt3 Qt4 Qt5 Qt/Embedded
    Platforms
    Unix/X11 Windows Android Maemo/MeeGo
    Wiki edits
    10

    Default Re: Artifacts with custom QGraphicsItem

    Maybe you should just state what you are trying to achieve?
    Your biological and technological distinctiveness will be added to our own. Resistance is futile.

    Please ask Qt related questions on the forum and not using private messages or visitor messages.


  7. #7
    Join Date
    Feb 2015
    Posts
    12
    Qt products
    Qt4 Qt5
    Platforms
    Unix/X11 Windows

    Default Re: Artifacts with custom QGraphicsItem

    I want to draw different QPixmaps to a GraphicsScene, depending on the zoom level. I use option->levelOfDetailFromTransform(painter->worldTransform()) in paint() to get the level of detail, and then draw the right pixmap.
    This is why i don't use QGraphicsPixmapItem insteat of my Tile class.
    For debugging, i removed the level of detail code, and the problem still appears.

    When creating the QGraphicsScene, all Tile objects are created. There is one parent Tile and multiple child Tiles.
    The number of children per Tile does not change at a later time. The parent Tile is added to the QGraphicsScene only after all children have been set.

    I drawed my boundingRects, and they look good.

    Now if i never call prepareGeometryChange() i get artifacts. I was able to get rid of the artifacts by calling prepareGeometryChange() at the beginning of the paint method, but this is not a good solution because it leads to an endlessly repeated painting().

  8. #8
    Join Date
    Jan 2008
    Location
    Alameda, CA, USA
    Posts
    5,230
    Thanks
    302
    Thanked 864 Times in 851 Posts
    Qt products
    Qt5
    Platforms
    Windows

    Default Re: Artifacts with custom QGraphicsItem

    What are these "artifacts"?

  9. #9
    Join Date
    Jan 2006
    Location
    Warsaw, Poland
    Posts
    33,359
    Thanks
    3
    Thanked 5,015 Times in 4,792 Posts
    Qt products
    Qt3 Qt4 Qt5 Qt/Embedded
    Platforms
    Unix/X11 Windows Android Maemo/MeeGo
    Wiki edits
    10

    Default Re: Artifacts with custom QGraphicsItem

    Quote Originally Posted by ThomasS0 View Post
    I want to draw different QPixmaps to a GraphicsScene, depending on the zoom level. I use option->levelOfDetailFromTransform(painter->worldTransform()) in paint() to get the level of detail, and then draw the right pixmap.
    This is why i don't use QGraphicsPixmapItem insteat of my Tile class.
    For debugging, i removed the level of detail code, and the problem still appears.
    This doesn't explain why the bounding rect of the item depends on whether it has children or not.

    When creating the QGraphicsScene, all Tile objects are created. There is one parent Tile and multiple child Tiles.
    The number of children per Tile does not change at a later time. The parent Tile is added to the QGraphicsScene only after all children have been set.
    This still doesn't explain why bounding rect depends on whether the item has children or not.

    I drawed my boundingRects, and they look good.
    Because you are calling the boundingRect() function. Graphics View is not (until you call prepareGeometryChange), that's the issue.

    Now if i never call prepareGeometryChange() i get artifacts. I was able to get rid of the artifacts by calling prepareGeometryChange() at the beginning of the paint method, but this is not a good solution because it leads to an endlessly repeated painting().
    I think the problem is that you are trying to paint something "on behalf of your children" which you shouldn't be doing.
    Your biological and technological distinctiveness will be added to our own. Resistance is futile.

    Please ask Qt related questions on the forum and not using private messages or visitor messages.


  10. #10
    Join Date
    Feb 2015
    Posts
    12
    Qt products
    Qt4 Qt5
    Platforms
    Unix/X11 Windows

    Default Re: Artifacts with custom QGraphicsItem

    d_stranz, i attached a picture. left is what i want, right are the "artifacts". artifacts.png

    Quote Originally Posted by wysota View Post
    This still doesn't explain why bounding rect depends on whether the item has children or not.
    As stated above, i assumed that the bounding rect should include all children. Am i wrong?
    Nevertheless, i set the bounding rect to a fixed size now, independently of the children, and it didn't change anything.

    Qt Code:
    1. QRectF Tile::boundingRect() const {
    2. return QRectF(-50,-50,w+100,h+100);
    3. }
    To copy to clipboard, switch view to plain text mode 
    w and h are const.

    Quote Originally Posted by wysota View Post
    Because you are calling the boundingRect() function. Graphics View is not (until you call prepareGeometryChange), that's the issue.
    Yes, i see. But what i don't know is why i have to call prepareGeometryChange(), even if the bounding rect is fixed, and where whould be a better place to call prepareGeometryChange() instead of in paint()?

    Quote Originally Posted by wysota View Post
    I think the problem is that you are trying to paint something "on behalf of your children" which you shouldn't be doing.
    Now every Tile has a fixed bounding rect, and draws only its own pixmap and its own bounding rect. The problem remains.

  11. #11
    Join Date
    Jan 2006
    Location
    Warsaw, Poland
    Posts
    33,359
    Thanks
    3
    Thanked 5,015 Times in 4,792 Posts
    Qt products
    Qt3 Qt4 Qt5 Qt/Embedded
    Platforms
    Unix/X11 Windows Android Maemo/MeeGo
    Wiki edits
    10

    Default Re: Artifacts with custom QGraphicsItem

    The item should never care about is children, it reports is own size. PrepareGeometryChange is only required if you modify the bounding rect. The artifacts on the picture are in my opinion related to incorrectly drawing the pixmap. Does calling prepareGeometryChange still help for it? What if you call update() instead?
    Your biological and technological distinctiveness will be added to our own. Resistance is futile.

    Please ask Qt related questions on the forum and not using private messages or visitor messages.


  12. #12
    Join Date
    Feb 2015
    Posts
    12
    Qt products
    Qt4 Qt5
    Platforms
    Unix/X11 Windows

    Default Re: Artifacts with custom QGraphicsItem

    Quote Originally Posted by wysota View Post
    Does calling prepareGeometryChange still help for it? What if you call update() instead?
    update() and prepareGeometryChange() in the beginning of paint() each solve the drawing problem, but both lead to endlessly repeated paint() calls.

  13. #13
    Join Date
    Jan 2006
    Location
    Warsaw, Poland
    Posts
    33,359
    Thanks
    3
    Thanked 5,015 Times in 4,792 Posts
    Qt products
    Qt3 Qt4 Qt5 Qt/Embedded
    Platforms
    Unix/X11 Windows Android Maemo/MeeGo
    Wiki edits
    10

    Default Re: Artifacts with custom QGraphicsItem

    If update() solves the problem then it has nothing to do with the bounding rect. prepareGeometryChange() calls update(), that's why it helps. I would take a closer look at your drawPixmap call, make sure it is valid.
    Your biological and technological distinctiveness will be added to our own. Resistance is futile.

    Please ask Qt related questions on the forum and not using private messages or visitor messages.


  14. #14
    Join Date
    Feb 2015
    Posts
    12
    Qt products
    Qt4 Qt5
    Platforms
    Unix/X11 Windows

    Default Re: Artifacts with custom QGraphicsItem

    I have created a minumal example reproducing the problem, attached.
    The drawing happens in src/Tile.cpp.


    My image is quite big, 8192x8192 pixels. If i use a smaller picture, everything looks good.
    The problem is: when i zoom out several times, it does not display the images correctly.

    I would be happy if you could take a look.
    test.zip



    Thanks,
    Thomas
    Last edited by ThomasS0; 27th February 2015 at 10:30.

  15. #15
    Join Date
    Jan 2006
    Location
    Warsaw, Poland
    Posts
    33,359
    Thanks
    3
    Thanked 5,015 Times in 4,792 Posts
    Qt products
    Qt3 Qt4 Qt5 Qt/Embedded
    Platforms
    Unix/X11 Windows Android Maemo/MeeGo
    Wiki edits
    10

    Default Re: Artifacts with custom QGraphicsItem

    I'm not sure what effect exactly you wanted to achieve. The loop where you create tiles seems a bit strange.
    Your biological and technological distinctiveness will be added to our own. Resistance is futile.

    Please ask Qt related questions on the forum and not using private messages or visitor messages.


  16. #16
    Join Date
    Feb 2015
    Posts
    12
    Qt products
    Qt4 Qt5
    Platforms
    Unix/X11 Windows

    Default Re: Artifacts with custom QGraphicsItem

    Hey wysota, thanks for your time.

    I attached a more simplified example, the problem still occures: test.zip.

    I want to display a Pixmap, using my own QGraphicsItem subclass.

    When i scale the scene to zoom out, the drawing of the pixmap goes wront, as you can see on the attached screenshots:

    1.png2.png3.png4.png
    Last edited by ThomasS0; 2nd March 2015 at 12:15.

  17. #17
    Join Date
    Jan 2006
    Location
    Warsaw, Poland
    Posts
    33,359
    Thanks
    3
    Thanked 5,015 Times in 4,792 Posts
    Qt products
    Qt3 Qt4 Qt5 Qt/Embedded
    Platforms
    Unix/X11 Windows Android Maemo/MeeGo
    Wiki edits
    10

    Default Re: Artifacts with custom QGraphicsItem

    I still think what I wrote a couple of posts ago, that your drawPixmap call is wrong.

    Qt Code:
    1. painter->drawPixmap(QRect(0,0,w,h), pixels, pixels.rect());
    To copy to clipboard, switch view to plain text mode 
    Your biological and technological distinctiveness will be added to our own. Resistance is futile.

    Please ask Qt related questions on the forum and not using private messages or visitor messages.


  18. #18
    Join Date
    Feb 2015
    Posts
    12
    Qt products
    Qt4 Qt5
    Platforms
    Unix/X11 Windows

    Default Re: Artifacts with custom QGraphicsItem

    Quote Originally Posted by wysota View Post
    I still think what I wrote a couple of posts ago, that your drawPixmap call is wrong.

    Qt Code:
    1. painter->drawPixmap(QRect(0,0,w,h), pixels, pixels.rect());
    To copy to clipboard, switch view to plain text mode 
    I checked the documentation again and i don't see the problem. Please explain whats wrong with this line.
    What i am trying to is to draw the complete pixmap at position (0,0), scaled to size (w.h).

  19. #19
    Join Date
    Jan 2006
    Location
    Warsaw, Poland
    Posts
    33,359
    Thanks
    3
    Thanked 5,015 Times in 4,792 Posts
    Qt products
    Qt3 Qt4 Qt5 Qt/Embedded
    Platforms
    Unix/X11 Windows Android Maemo/MeeGo
    Wiki edits
    10

    Default Re: Artifacts with custom QGraphicsItem

    I think the effect you observe comes from rounding errors and effectively the pixmap gets "pulled" to one side of the item. I don't understand why you have a tile of size 1900 and draw a pixmap of size 8192 onto it.
    Your biological and technological distinctiveness will be added to our own. Resistance is futile.

    Please ask Qt related questions on the forum and not using private messages or visitor messages.


Similar Threads

  1. Replies: 4
    Last Post: 21st November 2012, 14:05
  2. QSlider handle drawing artifacts
    By TheClassic in forum Newbie
    Replies: 3
    Last Post: 27th June 2011, 11:48
  3. QGraphicsScene artifacts
    By psih128 in forum Qt Programming
    Replies: 7
    Last Post: 17th February 2011, 13:19
  4. Custom QGraphicsItem
    By Lis in forum Qt Programming
    Replies: 1
    Last Post: 12th April 2010, 03:47
  5. Rubber band artifacts?
    By mooreaa in forum Qt Programming
    Replies: 1
    Last Post: 25th June 2008, 18:19

Bookmarks

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  
Digia, Qt and their respective logos are trademarks of Digia Plc in Finland and/or other countries worldwide.