summaryrefslogtreecommitdiff
path: root/src/monmon.cc
diff options
context:
space:
mode:
Diffstat (limited to 'src/monmon.cc')
-rw-r--r--src/monmon.cc47
1 files changed, 34 insertions, 13 deletions
diff --git a/src/monmon.cc b/src/monmon.cc
index ef341df..2c359e4 100644
--- a/src/monmon.cc
+++ b/src/monmon.cc
@@ -22,7 +22,7 @@ MonMon::MonMon(std::shared_ptr<PollLooper> const& looper)
: looper_(looper), animator_(Animator::create(looper)),
depth_(0), black_pixel_(0), screen_(nullptr), x_(0), y_(0), w_(0), h_(0),
rootpmap_(XCB_ATOM_NONE), desktop_window_(XCB_NONE),
- desktop_pixmap_(XCB_NONE) {
+ desktop_pixmap_(XCB_NONE), draw_requested_(false) {
pipe_.open();
looper_->add(pipe_.read(), Looper::EV_READ,
std::bind(&MonMon::pipe, this, std::placeholders::_1,
@@ -185,6 +185,7 @@ void MonMon::configure(int16_t x, int16_t y, uint16_t w, uint16_t h) {
y_ = y;
if (desktop_surface_) {
draw = true;
+ mark_all_dirty();
io::write(pipe_, "d", 1);
}
}
@@ -366,6 +367,7 @@ void MonMon::update_desktop_pixmap() {
desktop_pixmap_ = pixmap;
if (desktop_pixmap_ == XCB_NONE) desktop_surface_.reset();
+ mark_all_dirty();
io::write(pipe_, "d", 1);
}
@@ -375,11 +377,35 @@ void MonMon::close_pipe() {
pipe_.reset();
}
+pango::unique_layout MonMon::make_layout() const {
+ return pango::unique_layout(pango_layout_copy(layout_.get()));
+}
+
+void MonMon::fill_background(cairo_t* cairo, xcb_rectangle_t const& r) {
+ cairo_save(cairo);
+ cairo_rectangle(cairo, r.x, r.y, r.width, r.height);
+ cairo_clip(cairo);
+ if (!desktop_surface_) {
+ cairo_set_source_rgb(cairo, 0, 0, 0);
+ } else {
+ cairo_set_source_surface(cairo, desktop_surface_.get(), -x_, -y_);
+ }
+ cairo_paint(cairo);
+ cairo_restore(cairo);
+}
+
+void MonMon::request_draw() {
+ if (draw_requested_ || !pipe_) return;
+ draw_requested_ = true;
+ io::write(pipe_, "d", 1);
+}
+
void MonMon::pipe(Looper*, int, uint8_t event) {
if (event & Looper::EV_READ) {
char tmp;
if (io::read(pipe_, &tmp, 1)) {
if (tmp == 'd') {
+ draw_requested_ = false;
force_draw();
return;
}
@@ -424,19 +450,14 @@ void MonMon::rounded_path(cairo_t* cr, double x, double y,
void MonMon::internal_draw() {
std::lock_guard<std::mutex> lock(mutex_);
- if (!desktop_surface_) {
- cairo_set_source_rgb(cairo_.get(), 0, 0, 0);
- } else {
- cairo_set_source_surface(cairo_.get(), desktop_surface_.get(), -x_, -y_);
- }
- cairo_rectangle(cairo_.get(), 0, 0, w_, h_);
- cairo_fill(cairo_.get());
-
- draw_content(cairo_.get(), layout_.get(), w_, h_);
-
+ std::vector<xcb_rectangle_t> dirty;
+ draw_content(cairo_.get(), layout_.get(), w_, h_, dirty);
+ if (dirty.empty()) return;
cairo_surface_flush(surface_.get());
- xcb_copy_area(wnd_.conn(), pixmap_.get(), wnd_.get(), gcontext_.get(),
- 0, 0, 0, 0, w_, h_);
+ for (auto const& r : dirty) {
+ xcb_copy_area(wnd_.conn(), pixmap_.get(), wnd_.get(), gcontext_.get(),
+ r.x, r.y, r.x, r.y, r.width, r.height);
+ }
}
void MonMon::force_draw() {