Andrei
Andrei

Reputation: 4617

Cairo and Qt integration

I want to use Cairo graphics library whith Qt, but I can't find any documenattion. I just want to make the GUI whith Qt and use Cairo for drawing graphics in a Qt window.

Thanks.

Upvotes: 16

Views: 12118

Answers (5)

user1095108
user1095108

Reputation: 14603

Here is an example of how it might be done:

class CairoWidget: public QWidget
{
public:
  using QWidget::QWidget;

private:
  void paintEvent(QPaintEvent*)
  {
    auto const w(width()), h(height());
    QImage image(w, h, QImage::Format_RGB32);

    auto const surf(cairo_image_surface_create_for_data(image.bits(),
      CAIRO_FORMAT_RGB24, w, h, image.bytesPerLine()));
    auto const cr(cairo_create(surf));
    cairo_surface_destroy(surf);

    //
    cairo_set_source_rgb(cr, 1, 1, 1);
    cairo_paint(cr);
    cairo_scale(cr, w, h);

    //
    cairo_set_source_rgb(cr, 0, 0, 0);
    cairo_move_to(cr, 0, 0);
    cairo_line_to(cr, 1, 1);
    cairo_move_to(cr, 1, 0);
    cairo_line_to(cr, 0, 1);
    cairo_set_line_width(cr, .2);
    cairo_stroke(cr);

    cairo_rectangle(cr, 0, 0, .5, .5);
    cairo_set_source_rgba(cr, 1, 0, 0, .80);
    cairo_fill(cr);

    cairo_rectangle(cr, 0, .5, .5, .5);
    cairo_set_source_rgba(cr, 0, 1, 0, .60);
    cairo_fill(cr);

    cairo_rectangle(cr, .5, 0, .5, .5);
    cairo_set_source_rgba(cr, 0, 0, 1, .40);
    cairo_fill(cr);

    cairo_destroy(cr);

    //
    QPainter p(this);
    p.drawImage(0, 0, image);
  }
};

int main(int argc, char* argv[])
{
  QApplication app(argc, argv);

  CairoWidget w;
  w.show();

  return app.exec();
}

There are other hacks you might try to attempt, such as drawing directly into the backing store or you can also initialize QImage from your own buffer, which would be preferable for a custom cairo QWidget:

QImage::QImage(const uchar *data, int width, int height, int bytesPerLine, QImage::Format format, QImageCleanupFunction cleanupFunction = nullptr, void *cleanupInfo = nullptr)

Upvotes: 1

ntd
ntd

Reputation: 7434

Starting from cairo 1.17.8, the Qt support will be removed upstream.

Old answer

Recent version of cairo supports Qt by allowing to draw to a surface created with cairo_qt_surface_create(QPainter *painter): you can inspect the relevant header file here. There's no documentation because this feature is still experimental and disabled by default (you should compile cairo yourself explicitely enabling the Qt support with configure --enable-qt.

Upvotes: 13

jiandingzhe
jiandingzhe

Reputation: 2121

It can be achieved by this dirty way:

  1. Create an cairo image surface, draw on that surface.
  2. Call cairo_image_surface_get_data() to get the pixels.
  3. Copy the image to a Qt widget.

Upvotes: 1

andref
andref

Reputation: 4492

Qt's Paint System is a very good drawing library and is vector based. And it's already there. If you pick Qt as your GUI toolkit, it can't get any easier.

Upvotes: 8

dirkgently
dirkgently

Reputation: 111150

Caveat: This is not going to be the answer you are looking for.

Are you sure you want this? To what end? Is this about writing a QPaintDevice based on Cairo? Qt has its own graphics primitives implemented and so does Cairo. The only reason I can see is that you don't want the a heavy layer of Qt interfere with your system (embedded?). It's like you are trying to use the DirectFB backend of Cairo -- but then there's stuff like Qt-on-DirectFB. However, note such an implementation is costly and not free without its own set of quarks such as library-interop issues, printing from this Cairo based context etc. I'd suggest you do a regular search on Google to figure if such efforts are/ever were underway and weigh the pros and cons very heavily before even attempting the same.

Upvotes: 4

Related Questions