00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020 #include "glapplet.h"
00021
00022 #include <QtOpenGL/QGLPixelBuffer>
00023 #include <QtGui/QPainter>
00024 #include <QtGui/QImage>
00025
00026 namespace Plasma {
00027
00028 class GLAppletPrivate
00029 {
00030 public:
00031 GLAppletPrivate()
00032 {
00033 init();
00034 }
00035 ~GLAppletPrivate()
00036 {
00037 delete pbuf;
00038 delete dummy;
00039 }
00040 void init()
00041 {
00042 dummy = new QGLWidget((QWidget *) 0);
00043 QGLFormat format = QGLFormat::defaultFormat();
00044 format.setSampleBuffers(true);
00045 format.setAlphaBufferSize(8);
00046
00047 pbuf = new QGLPixelBuffer(300, 300, format, dummy);
00048 if (pbuf->isValid()) {
00049 pbuf->makeCurrent();
00050 }
00051 }
00052 void updateGlSize(const QSize &size)
00053 {
00054 if (size.width() > pbuf->width() ||
00055 size.height() > pbuf->height()) {
00056 QGLFormat format = pbuf->format();
00057 delete pbuf;
00058 pbuf = new QGLPixelBuffer(size, format, dummy);
00059 }
00060 }
00061
00062 public:
00063 QGLPixelBuffer *pbuf;
00064 QGLWidget *dummy;
00065 };
00066
00067 GLApplet::GLApplet(QGraphicsItem *parent,
00068 const QString &serviceId,
00069 int appletId)
00070 : Applet(parent, serviceId, appletId),
00071 d(new GLAppletPrivate)
00072 {
00073 if (!d->dummy->isValid() ||
00074 !QGLPixelBuffer::hasOpenGLPbuffers() ||
00075 !d->pbuf->isValid()) {
00076 setFailedToLaunch(true, i18n("This system does not support OpenGL widgets."));
00077 }
00078 }
00079
00080 GLApplet::GLApplet(QObject *parent, const QVariantList &args)
00081 : Applet(parent, args),
00082 d(new GLAppletPrivate)
00083 {
00084 if (!d->dummy->isValid() ||
00085 !QGLPixelBuffer::hasOpenGLPbuffers() ||
00086 !d->pbuf->isValid()) {
00087 setFailedToLaunch(true, i18n("This system does not support OpenGL widgets."));
00088 }
00089 }
00090
00091 GLApplet::~GLApplet()
00092 {
00093 delete d;
00094 }
00095
00096 GLuint GLApplet::bindTexture(const QImage &image, GLenum target)
00097 {
00098 Q_ASSERT(d->pbuf);
00099 if (!d->dummy->isValid()) {
00100 return 0;
00101 }
00102 return d->dummy->bindTexture(image, target);
00103 }
00104
00105 void GLApplet::deleteTexture(GLuint textureId)
00106 {
00107 Q_ASSERT(d->pbuf);
00108 d->dummy->deleteTexture(textureId);
00109 }
00110
00111 void GLApplet::paintGLInterface(QPainter *painter,
00112 const QStyleOptionGraphicsItem *option)
00113 {
00114 Q_UNUSED(painter)
00115 Q_UNUSED(option)
00116 }
00117
00118 static inline QPainterPath headerPath(const QRectF &r, int roundness,
00119 int headerHeight=10)
00120 {
00121 QPainterPath path;
00122 int xRnd = roundness;
00123 int yRnd = roundness;
00124 if (r.width() > r.height()) {
00125 xRnd = int(roundness * r.height() / r.width());
00126 } else {
00127 yRnd = int(roundness * r.width() / r.height());
00128 }
00129
00130 if(xRnd >= 100) {
00131 xRnd = 99;
00132 }
00133 if(yRnd >= 100) {
00134 yRnd = 99;
00135 }
00136 if(xRnd <= 0 || yRnd <= 0) {
00137 path.addRect(r);
00138 return path;
00139 }
00140
00141 QRectF rect = r.normalized();
00142
00143 if (rect.isNull()) {
00144 return path;
00145 }
00146
00147 qreal x = rect.x();
00148 qreal y = rect.y();
00149 qreal w = rect.width();
00150 qreal h = rect.height();
00151 qreal rxx = w * xRnd / 200;
00152 qreal ryy = h * yRnd / 200;
00153
00154 if (rxx < 0) {
00155 rxx = w / 200 * xRnd;
00156 }
00157 if (ryy < 0) {
00158 ryy = h / 200 * yRnd;
00159 }
00160 qreal rxx2 = 2 * rxx;
00161 qreal ryy2 = 2 * ryy;
00162
00163 path.arcMoveTo(x, y, rxx2, ryy2, 90);
00164 path.arcTo(x, y, rxx2, ryy2, 90, 90);
00165 QPointF pt = path.currentPosition();
00166 path.lineTo(x, pt.y() + headerHeight);
00167 path.lineTo(x + w, pt.y() + headerHeight);
00168 path.lineTo(x + w, pt.y());
00169 path.arcTo(x + w - rxx2, y, rxx2, ryy2, 0, 90);
00170 path.closeSubpath();
00171
00172 return path;
00173 }
00174
00175 void GLApplet::paintInterface(QPainter *painter,
00176 const QStyleOptionGraphicsItem *option,
00177 const QRect &contentsRect)
00178 {
00179 Q_UNUSED(contentsRect)
00180 Q_ASSERT(d->pbuf);
00181 if ((!d->dummy->isValid() ||
00182 !d->pbuf->isValid())) {
00183 if (!hasFailedToLaunch()) {
00184 setFailedToLaunch(true, i18n("Your machine does not support OpenGL widgets."));
00185 }
00186
00187 return;
00188 }
00189 d->pbuf->makeCurrent();
00190
00191
00192 glClearColor(0, 0, 0, 0);
00193 glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
00194
00195 QMatrix m = painter->worldMatrix();
00196 QRect deviceRect = m.mapRect(QRect(QPoint(23, 25), boundingRect().size().toSize()));
00197 d->updateGlSize(deviceRect.size());
00198
00199
00200 QPainter p(d->pbuf);
00201 paintGLInterface(&p, option);
00202
00203
00204 QImage image = d->pbuf->toImage();
00205 painter->drawImage(0, 0, image);
00206 }
00207
00208 void GLApplet::makeCurrent()
00209 {
00210 if (!d->dummy->isValid() || !d->pbuf->isValid()) {
00211 d->dummy->makeCurrent();
00212 }
00213 }
00214
00215 }
00216
00217 #include "glapplet.moc"