summaryrefslogtreecommitdiff
path: root/libs/hwui/DisplayListCanvas.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'libs/hwui/DisplayListCanvas.cpp')
-rw-r--r--libs/hwui/DisplayListCanvas.cpp187
1 files changed, 88 insertions, 99 deletions
diff --git a/libs/hwui/DisplayListCanvas.cpp b/libs/hwui/DisplayListCanvas.cpp
index 2dd52788074d..f5e57355138c 100644
--- a/libs/hwui/DisplayListCanvas.cpp
+++ b/libs/hwui/DisplayListCanvas.cpp
@@ -31,70 +31,62 @@
namespace android {
namespace uirenderer {
-DisplayListCanvas::DisplayListCanvas()
+DisplayListCanvas::DisplayListCanvas(int width, int height)
: mState(*this)
, mResourceCache(ResourceCache::getInstance())
- , mDisplayListData(nullptr)
+ , mDisplayList(nullptr)
, mTranslateX(0.0f)
, mTranslateY(0.0f)
, mHasDeferredTranslate(false)
, mDeferredBarrierType(kBarrier_None)
, mHighContrastText(false)
, mRestoreSaveCount(-1) {
+ reset(width, height);
}
DisplayListCanvas::~DisplayListCanvas() {
- LOG_ALWAYS_FATAL_IF(mDisplayListData,
+ LOG_ALWAYS_FATAL_IF(mDisplayList,
"Destroyed a DisplayListCanvas during a record!");
}
-///////////////////////////////////////////////////////////////////////////////
-// Operations
-///////////////////////////////////////////////////////////////////////////////
-
-DisplayListData* DisplayListCanvas::finishRecording() {
- mPaintMap.clear();
- mRegionMap.clear();
- mPathMap.clear();
- DisplayListData* data = mDisplayListData;
- mDisplayListData = nullptr;
- mSkiaCanvasProxy.reset(nullptr);
- return data;
-}
-
-void DisplayListCanvas::prepareDirty(float left, float top,
- float right, float bottom) {
-
- LOG_ALWAYS_FATAL_IF(mDisplayListData,
+void DisplayListCanvas::reset(int width, int height) {
+ LOG_ALWAYS_FATAL_IF(mDisplayList,
"prepareDirty called a second time during a recording!");
- mDisplayListData = new DisplayListData();
+ mDisplayList = new DisplayList();
- mState.initializeSaveStack(0, 0, mState.getWidth(), mState.getHeight(), Vector3());
+ mState.initializeSaveStack(width, height,
+ 0, 0, width, height, Vector3());
mDeferredBarrierType = kBarrier_InOrder;
mState.setDirtyClip(false);
mRestoreSaveCount = -1;
}
-bool DisplayListCanvas::finish() {
+
+///////////////////////////////////////////////////////////////////////////////
+// Operations
+///////////////////////////////////////////////////////////////////////////////
+
+DisplayList* DisplayListCanvas::finishRecording() {
flushRestoreToCount();
flushTranslate();
- return false;
-}
-void DisplayListCanvas::interrupt() {
-}
-
-void DisplayListCanvas::resume() {
+ mPaintMap.clear();
+ mRegionMap.clear();
+ mPathMap.clear();
+ DisplayList* displayList = mDisplayList;
+ mDisplayList = nullptr;
+ mSkiaCanvasProxy.reset(nullptr);
+ return displayList;
}
void DisplayListCanvas::callDrawGLFunction(Functor *functor) {
addDrawOp(new (alloc()) DrawFunctorOp(functor));
- mDisplayListData->functors.add(functor);
+ mDisplayList->functors.push_back(functor);
}
SkCanvas* DisplayListCanvas::asSkCanvas() {
- LOG_ALWAYS_FATAL_IF(!mDisplayListData,
+ LOG_ALWAYS_FATAL_IF(!mDisplayList,
"attempting to get an SkCanvas when we are not recording!");
if (!mSkiaCanvasProxy) {
mSkiaCanvasProxy.reset(new SkiaCanvasProxy(this));
@@ -176,11 +168,6 @@ void DisplayListCanvas::setMatrix(const SkMatrix& matrix) {
mState.setMatrix(matrix);
}
-void DisplayListCanvas::setLocalMatrix(const SkMatrix& matrix) {
- addStateOp(new (alloc()) SetLocalMatrixOp(matrix));
- mState.setMatrix(matrix);
-}
-
void DisplayListCanvas::concat(const SkMatrix& matrix) {
addStateOp(new (alloc()) ConcatMatrixOp(matrix));
mState.concatMatrix(matrix);
@@ -229,11 +216,11 @@ void DisplayListCanvas::drawRenderNode(RenderNode* renderNode) {
addRenderNodeOp(op);
}
-void DisplayListCanvas::drawLayer(DeferredLayerUpdater* layerHandle, float x, float y) {
+void DisplayListCanvas::drawLayer(DeferredLayerUpdater* layerHandle) {
// We ref the DeferredLayerUpdater due to its thread-safe ref-counting
// semantics.
- mDisplayListData->ref(layerHandle);
- addDrawOp(new (alloc()) DrawLayerOp(layerHandle->backingLayer(), x, y));
+ mDisplayList->ref(layerHandle);
+ addDrawOp(new (alloc()) DrawLayerOp(layerHandle->backingLayer()));
}
void DisplayListCanvas::drawBitmap(const SkBitmap* bitmap, const SkPaint* paint) {
@@ -330,13 +317,14 @@ void DisplayListCanvas::drawBitmapMesh(const SkBitmap& bitmap, int meshWidth, in
vertices, colors, paint));
}
-void DisplayListCanvas::drawPatch(const SkBitmap& bitmap, const Res_png_9patch* patch,
- float left, float top, float right, float bottom, const SkPaint* paint) {
+void DisplayListCanvas::drawNinePatch(const SkBitmap& bitmap, const Res_png_9patch& patch,
+ float dstLeft, float dstTop, float dstRight, float dstBottom, const SkPaint* paint) {
const SkBitmap* bitmapPtr = refBitmap(bitmap);
- patch = refPatch(patch);
+ const Res_png_9patch* patchPtr = refPatch(&patch);
paint = refPaint(paint);
- addDrawOp(new (alloc()) DrawPatchOp(bitmapPtr, patch, left, top, right, bottom, paint));
+ addDrawOp(new (alloc()) DrawPatchOp(bitmapPtr, patchPtr,
+ dstLeft, dstTop, dstRight, dstBottom, paint));
}
void DisplayListCanvas::drawColor(int color, SkXfermode::Mode mode) {
@@ -366,13 +354,13 @@ void DisplayListCanvas::drawRoundRect(
CanvasPropertyPrimitive* right, CanvasPropertyPrimitive* bottom,
CanvasPropertyPrimitive* rx, CanvasPropertyPrimitive* ry,
CanvasPropertyPaint* paint) {
- mDisplayListData->ref(left);
- mDisplayListData->ref(top);
- mDisplayListData->ref(right);
- mDisplayListData->ref(bottom);
- mDisplayListData->ref(rx);
- mDisplayListData->ref(ry);
- mDisplayListData->ref(paint);
+ mDisplayList->ref(left);
+ mDisplayList->ref(top);
+ mDisplayList->ref(right);
+ mDisplayList->ref(bottom);
+ mDisplayList->ref(rx);
+ mDisplayList->ref(ry);
+ mDisplayList->ref(paint);
refBitmapsInShader(paint->value.getShader());
addDrawOp(new (alloc()) DrawRoundRectPropsOp(&left->value, &top->value,
&right->value, &bottom->value, &rx->value, &ry->value, &paint->value));
@@ -384,10 +372,10 @@ void DisplayListCanvas::drawCircle(float x, float y, float radius, const SkPaint
void DisplayListCanvas::drawCircle(CanvasPropertyPrimitive* x, CanvasPropertyPrimitive* y,
CanvasPropertyPrimitive* radius, CanvasPropertyPaint* paint) {
- mDisplayListData->ref(x);
- mDisplayListData->ref(y);
- mDisplayListData->ref(radius);
- mDisplayListData->ref(paint);
+ mDisplayList->ref(x);
+ mDisplayList->ref(y);
+ mDisplayList->ref(radius);
+ mDisplayList->ref(paint);
refBitmapsInShader(paint->value.getShader());
addDrawOp(new (alloc()) DrawCirclePropsOp(&x->value, &y->value,
&radius->value, &paint->value));
@@ -447,16 +435,6 @@ void DisplayListCanvas::drawPosText(const uint16_t* text, const float* positions
addDrawOp(op);
}
-static void simplifyPaint(int color, SkPaint* paint) {
- paint->setColor(color);
- paint->setShader(nullptr);
- paint->setColorFilter(nullptr);
- paint->setLooper(nullptr);
- paint->setStrokeWidth(4 + 0.04 * paint->getTextSize());
- paint->setStrokeJoin(SkPaint::kRound_Join);
- paint->setLooper(nullptr);
-}
-
void DisplayListCanvas::drawText(const uint16_t* glyphs, const float* positions,
int count, const SkPaint& paint, float x, float y,
float boundsLeft, float boundsTop, float boundsRight, float boundsBottom,
@@ -469,30 +447,34 @@ void DisplayListCanvas::drawText(const uint16_t* glyphs, const float* positions,
positions = refBuffer<float>(positions, count * 2);
Rect bounds(boundsLeft, boundsTop, boundsRight, boundsBottom);
- if (CC_UNLIKELY(mHighContrastText)) {
- // high contrast draw path
- int color = paint.getColor();
- int channelSum = SkColorGetR(color) + SkColorGetG(color) + SkColorGetB(color);
- bool darken = channelSum < (128 * 3);
-
- // outline
- SkPaint* outlinePaint = copyPaint(&paint);
- simplifyPaint(darken ? SK_ColorWHITE : SK_ColorBLACK, outlinePaint);
- outlinePaint->setStyle(SkPaint::kStrokeAndFill_Style);
- addDrawOp(new (alloc()) DrawTextOp(text, bytesCount, count,
- x, y, positions, outlinePaint, totalAdvance, bounds)); // bounds?
-
- // inner
- SkPaint* innerPaint = copyPaint(&paint);
- simplifyPaint(darken ? SK_ColorBLACK : SK_ColorWHITE, innerPaint);
- innerPaint->setStyle(SkPaint::kFill_Style);
- addDrawOp(new (alloc()) DrawTextOp(text, bytesCount, count,
- x, y, positions, innerPaint, totalAdvance, bounds));
+ DrawOp* op = new (alloc()) DrawTextOp(text, bytesCount, count,
+ x, y, positions, refPaint(&paint), totalAdvance, bounds);
+ addDrawOp(op);
+}
+
+void DisplayListCanvas::drawRegion(const SkRegion& region, const SkPaint& paint) {
+ if (paint.getStyle() != SkPaint::kFill_Style ||
+ (paint.isAntiAlias() && !mState.currentTransform()->isSimple())) {
+ SkRegion::Iterator it(region);
+ while (!it.done()) {
+ const SkIRect& r = it.rect();
+ drawRect(r.fLeft, r.fTop, r.fRight, r.fBottom, paint);
+ it.next();
+ }
} else {
- // standard draw path
- DrawOp* op = new (alloc()) DrawTextOp(text, bytesCount, count,
- x, y, positions, refPaint(&paint), totalAdvance, bounds);
- addDrawOp(op);
+ int count = 0;
+ Vector<float> rects;
+ SkRegion::Iterator it(region);
+ while (!it.done()) {
+ const SkIRect& r = it.rect();
+ rects.push(r.fLeft);
+ rects.push(r.fTop);
+ rects.push(r.fRight);
+ rects.push(r.fBottom);
+ count += 4;
+ it.next();
+ }
+ drawRects(rects.array(), count, &paint);
}
}
@@ -532,21 +514,26 @@ void DisplayListCanvas::flushTranslate() {
}
size_t DisplayListCanvas::addOpAndUpdateChunk(DisplayListOp* op) {
- int insertIndex = mDisplayListData->displayListOps.add(op);
+ int insertIndex = mDisplayList->ops.size();
+#if HWUI_NEW_OPS
+ LOG_ALWAYS_FATAL("unsupported");
+#else
+ mDisplayList->ops.push_back(op);
+#endif
if (mDeferredBarrierType != kBarrier_None) {
// op is first in new chunk
- mDisplayListData->chunks.push();
- DisplayListData::Chunk& newChunk = mDisplayListData->chunks.editTop();
+ mDisplayList->chunks.emplace_back();
+ DisplayList::Chunk& newChunk = mDisplayList->chunks.back();
newChunk.beginOpIndex = insertIndex;
newChunk.endOpIndex = insertIndex + 1;
newChunk.reorderChildren = (mDeferredBarrierType == kBarrier_OutOfOrder);
- int nextChildIndex = mDisplayListData->children().size();
+ int nextChildIndex = mDisplayList->children.size();
newChunk.beginChildIndex = newChunk.endChildIndex = nextChildIndex;
mDeferredBarrierType = kBarrier_None;
} else {
// standard case - append to existing chunk
- mDisplayListData->chunks.editTop().endOpIndex = insertIndex + 1;
+ mDisplayList->chunks.back().endOpIndex = insertIndex + 1;
}
return insertIndex;
}
@@ -569,22 +556,24 @@ size_t DisplayListCanvas::addDrawOp(DrawOp* op) {
op->setQuickRejected(rejected);
}
- mDisplayListData->hasDrawOps = true;
+ mDisplayList->hasDrawOps = true;
return flushAndAddOp(op);
}
size_t DisplayListCanvas::addRenderNodeOp(DrawRenderNodeOp* op) {
int opIndex = addDrawOp(op);
- int childIndex = mDisplayListData->addChild(op);
+#if !HWUI_NEW_OPS
+ int childIndex = mDisplayList->addChild(op);
// update the chunk's child indices
- DisplayListData::Chunk& chunk = mDisplayListData->chunks.editTop();
+ DisplayList::Chunk& chunk = mDisplayList->chunks.back();
chunk.endChildIndex = childIndex + 1;
- if (op->renderNode()->stagingProperties().isProjectionReceiver()) {
+ if (op->renderNode->stagingProperties().isProjectionReceiver()) {
// use staging property, since recording on UI thread
- mDisplayListData->projectionReceiveIndex = opIndex;
+ mDisplayList->projectionReceiveIndex = opIndex;
}
+#endif
return opIndex;
}
@@ -595,7 +584,7 @@ void DisplayListCanvas::refBitmapsInShader(const SkShader* shader) {
// it to the bitmap pile
SkBitmap bitmap;
SkShader::TileMode xy[2];
- if (shader->asABitmap(&bitmap, nullptr, xy) == SkShader::kDefault_BitmapType) {
+ if (shader->isABitmap(&bitmap, nullptr, xy)) {
refBitmap(bitmap);
return;
}