diff options
author | Pierre Ossman <ossman@cendio.se> | 2017-01-02 19:49:52 +0100 |
---|---|---|
committer | Pierre Ossman <ossman@cendio.se> | 2017-02-10 17:05:20 +0100 |
commit | 3d74d88806d09f3a899be5d8f1df8ec20ed9a14d (patch) | |
tree | a2a86607aa8dda47559c5be82fadad9247844193 /tests | |
parent | 403ac27d2377df4fed8bf5039125f6d89aaa6955 (diff) | |
download | tigervnc-3d74d88806d09f3a899be5d8f1df8ec20ed9a14d.tar.gz tigervnc-3d74d88806d09f3a899be5d8f1df8ec20ed9a14d.zip |
Render on a temporary surface when needed
Some platforms draw directly to the screen, which means that updates
will flicker if we draw multiple layers. Prevent this by first
composing the update on a hidden surface.
Diffstat (limited to 'tests')
-rw-r--r-- | tests/fbperf.cxx | 39 |
1 files changed, 34 insertions, 5 deletions
diff --git a/tests/fbperf.cxx b/tests/fbperf.cxx index 8c71d966..7f1e2c1d 100644 --- a/tests/fbperf.cxx +++ b/tests/fbperf.cxx @@ -72,6 +72,7 @@ public: protected: Surface* overlay; + Surface* offscreen; }; TestWindow::TestWindow() : @@ -202,7 +203,7 @@ void PartialTestWindow::changefb() } OverlayTestWindow::OverlayTestWindow() : - overlay(NULL) + overlay(NULL), offscreen(NULL) { } @@ -212,12 +213,21 @@ void OverlayTestWindow::start(int width, int height) overlay = new Surface(400, 200); overlay->clear(0xff, 0x80, 0x00, 0xcc); + + // X11 needs an off screen buffer for compositing to avoid flicker +#if !defined(WIN32) && !defined(__APPLE__) + offscreen = new Surface(w(), h()); +#else + offscreen = NULL; +#endif } void OverlayTestWindow::stop() { PartialTestWindow::stop(); + delete offscreen; + offscreen = NULL; delete overlay; overlay = NULL; } @@ -227,13 +237,15 @@ void OverlayTestWindow::draw() int ox, oy, ow, oh; int X, Y, W, H; + // We cannot update the damage region from inside the draw function, + // so delegate this to an idle function + Fl::add_idle(timer, this); + // Check what actually needs updating fl_clip_box(0, 0, w(), h(), X, Y, W, H); if ((W == 0) || (H == 0)) return; - PartialTestWindow::draw(); - // We might get a redraw before we are fully ready if (!overlay) return; @@ -243,16 +255,33 @@ void OverlayTestWindow::draw() fl_push_no_clip(); fl_push_clip(X, Y, W, H); + if (offscreen) + fb->draw(offscreen, X, Y, X, Y, W, H); + else + fb->draw(X, Y, X, Y, W, H); + + pixels += W*H; + frames++; + ox = (w() - overlay->width()) / 2; oy = h() / 4 - overlay->height() / 2; ow = overlay->width(); oh = overlay->height(); fl_clip_box(ox, oy, ow, oh, X, Y, W, H); - if ((W != 0) && (H != 0)) - overlay->draw(X - ox, Y - oy, X, Y, W, H); + if ((W != 0) && (H != 0)) { + if (offscreen) + overlay->draw(offscreen, X - ox, Y - oy, X, Y, W, H); + else + overlay->draw(X - ox, Y - oy, X, Y, W, H); + } fl_pop_clip(); fl_pop_clip(); + + if (offscreen) { + fl_clip_box(0, 0, w(), h(), X, Y, W, H); + offscreen->draw(X, Y, X, Y, W, H); + } } static void dosubtest(TestWindow* win, int width, int height, |