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 macextrasgreaterThan(QT_MAJOR_VERSION, 4): QT += widgets
TARGET = nativePainter
TEMPLATE = app
LIBS += -framework CoreGraphicsSOURCES += main.cpp
nativepainter.cppHEADERS +=
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>
#endifnativePainter::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.