From 96885eb480c5e0526fe2f77d30f6e551f3f3ceab Mon Sep 17 00:00:00 2001 From: Romain Guy Date: Tue, 26 Mar 2013 15:05:58 -0700 Subject: Avoid multiple font cache texture uploads Bug #8378964 This change defers drawing into layers until after the renderer for FBO0 is ready to draw. At that point, all the precaching is done which means all glyphs can be uploaded at once in the font caches. Change-Id: Ie1f7a7ff30f76f06fb3dbc72c7d05e66207d1ecb --- libs/hwui/Layer.cpp | 47 +++++++++++++++++++++++++++++++++++++++++++++-- 1 file changed, 45 insertions(+), 2 deletions(-) (limited to 'libs/hwui/Layer.cpp') diff --git a/libs/hwui/Layer.cpp b/libs/hwui/Layer.cpp index 1899002004c4..2998535c9916 100644 --- a/libs/hwui/Layer.cpp +++ b/libs/hwui/Layer.cpp @@ -18,6 +18,8 @@ #include +#include "DisplayList.h" +#include "DeferredDisplayList.h" #include "Layer.h" #include "LayerRenderer.h" #include "OpenGLRenderer.h" @@ -43,15 +45,18 @@ Layer::Layer(const uint32_t layerWidth, const uint32_t layerHeight) { fbo = 0; stencil = NULL; debugDrawUpdate = false; + deferredList = NULL; Caches::getInstance().resourceCache.incrementRefcount(this); } Layer::~Layer() { - if (mesh) delete mesh; - if (meshIndices) delete meshIndices; if (colorFilter) Caches::getInstance().resourceCache.decrementRefcount(colorFilter); removeFbo(); deleteTexture(); + + delete[] mesh; + delete[] meshIndices; + delete deferredList; } uint32_t Layer::computeIdealWidth(uint32_t layerWidth) { @@ -133,5 +138,43 @@ void Layer::setColorFilter(SkiaColorFilter* filter) { } } +void Layer::defer() { + if (!deferredList) { + deferredList = new DeferredDisplayList; + } + DeferStateStruct deferredState(*deferredList, *renderer, + DisplayList::kReplayFlag_ClipChildren); + + const float width = layer.getWidth(); + const float height = layer.getHeight(); + + if (dirtyRect.isEmpty() || (dirtyRect.left <= 0 && dirtyRect.top <= 0 && + dirtyRect.right >= width && dirtyRect.bottom >= height)) { + dirtyRect.set(0, 0, width, height); + } + + renderer->initViewport(width, height); + renderer->setupFrameState(dirtyRect.left, dirtyRect.top, + dirtyRect.right, dirtyRect.bottom, !isBlend()); + + displayList->defer(deferredState, 0); +} + +void Layer::flush() { + if (deferredList && !deferredList->isEmpty()) { + renderer->setViewport(layer.getWidth(), layer.getHeight()); + renderer->prepareDirty(dirtyRect.left, dirtyRect.top, dirtyRect.right, dirtyRect.bottom, + !isBlend()); + + deferredList->flush(*renderer, dirtyRect); + + renderer->finish(); + renderer = NULL; + + dirtyRect.setEmpty(); + deferredList->clear(); + } +} + }; // namespace uirenderer }; // namespace android -- cgit v1.2.3-59-g8ed1b