Files
MuditaOS/module-gui/gui/core/BoundingBox.cpp
Adam Wulkiewicz 49bbaf51a0 [MOS-550] Improve refresh of the display
1. Implement partial refresh.
2. Implement refresh canceling mechanism.
3. Refactor some parts of the gui and display code.

ad 1.
- Detect parts of the screen changed since last update and merge them
  into bigger regions. These regions defines parts of the context sent
  to the display.
- Refresh the region covering all of the parts since this is the most
  time consuming part and the size of the refreshed region doesn't
  change the time much.
- Refresh the whole screen if deep refresh is requested and previously
  fast refresh was used. This is needed to prevent unwanted artifacts
  in some cases.

ad 2.
- Separate display update and refresh logic.
- Divide image display message handling into two handlers, one updating
  and other one refreshing the screen.
- Add cancel refresh message and use it to cancel refresh during update.
- Store sum of refresh regions gathered during updates to refresh them
  all at once at the end.
2022-10-11 20:00:33 +02:00

125 lines
2.7 KiB
C++

// Copyright (c) 2017-2022, Mudita Sp. z.o.o. All rights reserved.
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
#include "BoundingBox.hpp"
#include <limits>
#include <sstream>
#include <limits>
#include <module-gui/gui/Common.hpp>
namespace gui
{
BoundingBox::BoundingBox(Position x, Position y, Length w, Length h)
{
this->x = x;
this->y = y;
this->w = w;
this->h = h;
}
bool BoundingBox::intersect(const BoundingBox &box1, const BoundingBox &box2, BoundingBox &result)
{
const BoundingBox *l;
const BoundingBox *r;
if (box1.x < box2.x) {
l = &box1;
r = &box2;
}
else {
l = &box2;
r = &box1;
}
int w = l->x + l->w - r->x;
if (w <= 0) {
result.clear();
return false;
}
// most left bbox overlap right box entirely
if ((l->x + l->w) >= (r->x + r->w)) {
w = r->w;
}
result.w = w;
result.x = r->x;
// vertical check
// select bbox that is higher
const BoundingBox *u;
if (box1.y < box2.y) {
l = &box1;
u = &box2;
}
else {
l = &box2;
u = &box1;
}
int h = l->y + l->h - u->y;
if (h <= 0) {
result.clear();
return false;
}
// most lower bbox overlap upper box entirely
if ((l->y + l->h) >= (u->y + u->h)) {
h = u->h;
}
result.y = u->y;
result.h = h;
return true;
}
void BoundingBox::clear()
{
x = zero_position;
y = zero_position;
w = zero_size;
h = zero_size;
}
Length BoundingBox::size(gui::Axis axis) const
{
if (axis == Axis::X)
return w;
else
return h;
}
Position BoundingBox::pos(gui::Axis axis) const
{
if (axis == Axis::X)
return x;
else
return y;
}
std::string BoundingBox::str() const
{
std::stringstream ss;
ss << "{";
ss << "x: " << x << ", y: " << y << ", w: " << w << ", h: " << h;
ss << "}";
return ss.str();
}
void BoundingBox::expandSize(const BoundingBox &box)
{
w = box.w > w ? box.w : w;
h = box.h > h ? box.h : h;
}
bool BoundingBox::operator==(const BoundingBox &box) const
{
return !(x != box.x || y != box.y || w != box.w || h != box.h);
}
bool BoundingBox::operator!=(const BoundingBox &box) const
{
return (x != box.x || y != box.y || w != box.w || h != box.h);
}
} /* namespace gui */