mirror of
https://invent.kde.org/graphics/okular
synced 2024-10-02 14:14:10 +00:00
Don't paint a partial pixmap over a fully rendered pixmap, even if dirty
This preserves fully rendered areas when zooming in or out instead of replacing them with partially rendered pixmaps.
This commit is contained in:
parent
aa0386dccd
commit
a1cf3f9e5e
|
@ -226,6 +226,10 @@ void TilesManager::Private::setPixmap(const QPixmap *pixmap, const NormalizedRec
|
||||||
if (!tile.rect.intersects(rect)) {
|
if (!tile.rect.intersects(rect)) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
// Avoid painting partial pixmaps over tiles that already have a fully rendered pixmap, even if dirty
|
||||||
|
if (isPartialPixmap && tile.pixmap != nullptr && !tile.partial) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
// if the tile is not entirely within the viewport (the tile intersects an
|
// if the tile is not entirely within the viewport (the tile intersects an
|
||||||
// edged of the viewport), attempt to set the pixmap in the children tiles
|
// edged of the viewport), attempt to set the pixmap in the children tiles
|
||||||
|
@ -239,13 +243,17 @@ void TilesManager::Private::setPixmap(const QPixmap *pixmap, const NormalizedRec
|
||||||
delete tile.pixmap;
|
delete tile.pixmap;
|
||||||
tile.pixmap = nullptr;
|
tile.pixmap = nullptr;
|
||||||
}
|
}
|
||||||
|
// We could paint the pixmap over part of the tile here, but
|
||||||
|
// there is little reason to as it will usually be offscreen
|
||||||
|
// and it will be overwritten later if more tiles enter the screen,
|
||||||
|
// as we only track the dirty state of whole tiles, not rects.
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// the tile lies entirely within the viewport
|
// the tile lies entirely within the viewport
|
||||||
if (tile.nTiles == 0) {
|
if (tile.nTiles == 0) {
|
||||||
tile.dirty = isPartialPixmap;
|
tile.dirty = isPartialPixmap;
|
||||||
|
tile.partial = isPartialPixmap;
|
||||||
|
|
||||||
// check whether the tile size is big and split it if necessary
|
// check whether the tile size is big and split it if necessary
|
||||||
if (!splitBigTiles(tile, rect)) {
|
if (!splitBigTiles(tile, rect)) {
|
||||||
|
@ -276,8 +284,11 @@ void TilesManager::Private::setPixmap(const QPixmap *pixmap, const NormalizedRec
|
||||||
QRect tileRect = tile.rect.geometry(width, height);
|
QRect tileRect = tile.rect.geometry(width, height);
|
||||||
// sets the pixmap of the children tiles. if the tile's size is too
|
// sets the pixmap of the children tiles. if the tile's size is too
|
||||||
// small, discards the children tiles and use the current one
|
// small, discards the children tiles and use the current one
|
||||||
if (tileRect.width() * tileRect.height() >= TILES_MAXSIZE) {
|
// Never join small tiles during a partial update in order to
|
||||||
|
// not lose existing image data
|
||||||
|
if (tileRect.width() * tileRect.height() >= TILES_MAXSIZE || isPartialPixmap) {
|
||||||
tile.dirty = isPartialPixmap;
|
tile.dirty = isPartialPixmap;
|
||||||
|
tile.partial = isPartialPixmap;
|
||||||
if (tile.pixmap) {
|
if (tile.pixmap) {
|
||||||
totalPixels -= tile.pixmap->width() * tile.pixmap->height();
|
totalPixels -= tile.pixmap->width() * tile.pixmap->height();
|
||||||
delete tile.pixmap;
|
delete tile.pixmap;
|
||||||
|
@ -312,6 +323,7 @@ void TilesManager::Private::setPixmap(const QPixmap *pixmap, const NormalizedRec
|
||||||
tile.pixmap = nullptr;
|
tile.pixmap = nullptr;
|
||||||
}
|
}
|
||||||
tile.dirty = isPartialPixmap;
|
tile.dirty = isPartialPixmap;
|
||||||
|
tile.partial = isPartialPixmap;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -471,6 +483,8 @@ void TilesManager::cleanupPixmapMemory(qulonglong numberOfBytes, const Normalize
|
||||||
delete tile->pixmap;
|
delete tile->pixmap;
|
||||||
tile->pixmap = nullptr;
|
tile->pixmap = nullptr;
|
||||||
|
|
||||||
|
tile->partial = true;
|
||||||
|
|
||||||
d->markParentDirty(*tile);
|
d->markParentDirty(*tile);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -625,6 +639,7 @@ TileNode::TileNode()
|
||||||
: pixmap(nullptr)
|
: pixmap(nullptr)
|
||||||
, rotation(Rotation0)
|
, rotation(Rotation0)
|
||||||
, dirty(true)
|
, dirty(true)
|
||||||
|
, partial(true)
|
||||||
, distance(-1)
|
, distance(-1)
|
||||||
, tiles(nullptr)
|
, tiles(nullptr)
|
||||||
, nTiles(0)
|
, nTiles(0)
|
||||||
|
|
|
@ -66,6 +66,13 @@ public:
|
||||||
*/
|
*/
|
||||||
bool dirty;
|
bool dirty;
|
||||||
|
|
||||||
|
/**
|
||||||
|
Whether the tile contains a partially rendered pixmap.
|
||||||
|
Some backends, such as PDF, can send partial updates that contain
|
||||||
|
only some of the page's elements (e.g. only a background image) drawn.
|
||||||
|
*/
|
||||||
|
bool partial;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Distance between the tile and the viewport.
|
* Distance between the tile and the viewport.
|
||||||
* This is used by the evicting algorithm.
|
* This is used by the evicting algorithm.
|
||||||
|
|
Loading…
Reference in a new issue