Qt 5.3.2 / OSX cannot use native CGContext drawing in paintEvent / Flickering



  • Hi !
    For the life of me i cannot use native drawing in a paintEvent on Qt 5.

    I created a simple example that should fill the whole Rectangle with a certain color (RGB 240,120,60).
    When started (on Mac of course, i used 10.9) the WIndow flickers some times between white and the desired "orange" color and then stays white.
    Do you have any idea why my drawing is not persistent ?
    A very similar way of drawing in Qt4 is working just fine.

    Here is my sample:

    nativepainter.pro:
    @
    QT += core gui macextras

    greaterThan(QT_MAJOR_VERSION, 4): QT += widgets

    TARGET = nativePainter
    TEMPLATE = app
    LIBS += -framework CoreGraphics

    SOURCES += main.cpp
    nativepainter.cpp

    HEADERS +=
    nativepainter.h
    @

    main.cpp:
    @
    #include <QApplication>
    #include <nativepainter.h>

    int main(int argc, char *argv[])
    {
    QApplication a(argc, argv);
    nativePainter myNP;
    myNP.show();

    return a.exec();
    }
    @

    nativepainter.h:
    @
    #ifndef NATIVEPAINTER_H
    #define NATIVEPAINTER_H

    #include <QApplication>
    #include <QWidget>
    #include <QPaintEvent>
    #include <CoreGraphics/CGColorSpace.h>
    #include <ApplicationServices/ApplicationServices.h>

    class nativePainter : public QWidget
    {
    Q_OBJECT
    public:
    explicit nativePainter(QWidget *parent = 0);
    signals:

    public slots:
    protected:
    void paintEvent(QPaintEvent * event);
    private:
    };

    #endif // NATIVEPAINTER_H
    @

    nativepainter.cpp:
    @
    #include <Qpainter>
    #include <QDebug>
    #include "nativepainter.h"
    #ifdef Q_OS_MACX
    #include <QtMac>
    #endif

    nativePainter::nativePainter(QWidget *parent) :
    QWidget(parent)
    {

    }

    void nativePainter::paintEvent(QPaintEvent* e)
    {
    #ifdef Q_OS_MACX
    //prepare painting
    QPainter painter;
    painter.begin(this);
    painter.beginNativePainting();

    //create pixelbuffer and fill with RGB color (240,120,60)
    int componentCount(4), w(e->rect().width()), h(e->rect().height());
    size_t bufferLength = w * h * componentCount2;
    unsigned char
    pixels = (unsigned char*)malloc(bufferLength);
    for(ulong i=0; i < bufferLength; i+=componentCount)
    {
    pixels[i] = 240;
    pixels[i+1] = 120;
    pixels[i+2] = 60;
    pixels[i+3] = 255;
    }
    CGDataProviderRef provider = CGDataProviderCreateWithData(NULL, pixels, bufferLength, NULL);
    size_t bitsPerComponent = 8;
    size_t bitsPerPixel = bitsPerComponent * componentCount;
    size_t bytesPerRow = componentCount * w;
    CGColorSpaceRef RGBcolorSpaceRef = CGColorSpaceCreateDeviceRGB();
    CGBitmapInfo bitmapInfo = kCGBitmapByteOrderDefault | kCGImageAlphaPremultipliedLast;
    CGColorRenderingIntent renderingIntent = kCGRenderingIntentDefault;

    //create CGImageRef with pixels
    CGImageRef iref = CGImageCreate(
    w,
    h,
    bitsPerComponent,
    bitsPerPixel,
    bytesPerRow,
    RGBcolorSpaceRef,
    bitmapInfo,
    provider, // data provider
    NULL, // decode
    true, // should interpolate
    renderingIntent);

    //draw CGImage to current context
    CGRect cgrect = CGRectMake(e->rect().x(), e->rect().y(), e->rect().x() + e->rect().width(), e->rect().y() + e->rect().height());
    CGContextRef context = QtMac::currentCGContext();
    CGContextDrawImage(context, cgrect, iref);
    CGContextFlush(context);
    CGContextSynchronize(context);
    //end painting
    painter.endNativePainting();
    painter.end();
    #else
    QPainter painter;
    painter.begin(this);
    painter.fillRect(e->rect(), QColor(240, 120, 60));
    painter.end();
    #endif
    }
    @

    May try to compile and see for yourself, do you guys have any idea ?

    Greetings & Thanks,

    Nils



  • Did you ever find a solution to this? I'm having a similar issue. I need to do my own drawing using native CGxxxx APIs and need to get the CGContextRef of the widget, however what I seem to get back is maybe for another object because my drawing never shows up. Prior to Qt5 I was using "qt_mac_cg_context()" to get the CGContextRef which worked fine.


Log in to reply
 

Looks like your connection to Qt Forum was lost, please wait while we try to reconnect.