Creating framework for drawShadowedPicture
GOLD_TRYBOT_URL= https://gold.skia.org/search?issue=2146073003
Committed: https://skia.googlesource.com/skia/+/0ae097d116f4332be02a135ffc99c162473dee6a
Review-Url: https://codereview.chromium.org/2146073003
diff --git a/src/core/SkCanvas.cpp b/src/core/SkCanvas.cpp
index 050253f..2cfe8ae 100644
--- a/src/core/SkCanvas.cpp
+++ b/src/core/SkCanvas.cpp
@@ -663,6 +663,9 @@
fDeviceCMDirty = true;
fSaveCount = 1;
fMetaData = nullptr;
+#ifdef SK_EXPERIMENTAL_SHADOWING
+ fLights = nullptr;
+#endif
fClipStack.reset(new SkClipStack);
@@ -1519,6 +1522,7 @@
this->setMatrix(SkMatrix::I());
}
+#ifdef SK_EXPERIMENTAL_SHADOWING
void SkCanvas::translateZ(SkScalar z) {
this->checkForDeferredSave();
this->fMCRec->fCurDrawDepth += z;
@@ -1529,6 +1533,15 @@
return this->fMCRec->fCurDrawDepth;
}
+void SkCanvas::setLights(sk_sp<SkLights> lights) {
+ this->fLights = lights;
+}
+
+sk_sp<SkLights> SkCanvas::getLights() const {
+ return this->fLights;
+}
+#endif
+
//////////////////////////////////////////////////////////////////////////////
void SkCanvas::clipRect(const SkRect& rect, SkRegion::Op op, bool doAA) {
@@ -3000,6 +3013,24 @@
picture->playback(this);
}
+#ifdef SK_EXPERIMENTAL_SHADOWING
+void SkCanvas::drawShadowedPicture(const SkPicture* picture,
+ const SkMatrix* matrix,
+ const SkPaint* paint) {
+ RETURN_ON_NULL(picture);
+
+ TRACE_EVENT0("disabled-by-default-skia", "SkCanvas::drawShadowedPicture()");
+
+ this->onDrawShadowedPicture(picture, matrix, paint);
+}
+
+void SkCanvas::onDrawShadowedPicture(const SkPicture* picture,
+ const SkMatrix* matrix,
+ const SkPaint* paint) {
+ this->onDrawPicture(picture, matrix, paint);
+}
+#endif
+
///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
diff --git a/src/core/SkLightingShader.cpp b/src/core/SkLightingShader.cpp
index 92f41ad..b6b5496 100644
--- a/src/core/SkLightingShader.cpp
+++ b/src/core/SkLightingShader.cpp
@@ -45,7 +45,7 @@
*/
SkLightingShaderImpl(sk_sp<SkShader> diffuseShader,
sk_sp<SkNormalSource> normalSource,
- const sk_sp<SkLights> lights)
+ sk_sp<SkLights> lights)
: fDiffuseShader(std::move(diffuseShader))
, fNormalSource(std::move(normalSource))
, fLights(std::move(lights)) {}
@@ -134,6 +134,7 @@
// TODO: handle more than one of these
fLightColor = lights->light(i).color();
fLightDir = lights->light(i).dir();
+ // TODO get the handle to the shadow map if there is one
}
}
@@ -176,6 +177,9 @@
this->emitChild(0, nullptr, &dstNormalName, args);
fragBuilder->codeAppendf("vec3 normal = %s.xyz;", dstNormalName.c_str());
+
+ // TODO: make this a loop and modulate the contribution from each light
+ // based on the shadow map
fragBuilder->codeAppendf("float NdotL = clamp(dot(normal, %s), 0.0, 1.0);",
lightDirUniName);
// diffuse light
diff --git a/src/core/SkPictureFlat.h b/src/core/SkPictureFlat.h
index 125d4e9..17b7681 100644
--- a/src/core/SkPictureFlat.h
+++ b/src/core/SkPictureFlat.h
@@ -17,6 +17,13 @@
#include "SkPtrRecorder.h"
#include "SkTDynamicHash.h"
+/*
+ * Note: While adding new DrawTypes, it is necessary to add to the end of this list
+ * and update LAST_DRAWTYPE_ENUM to avoid having the code read older skps wrong.
+ * (which can cause segfaults)
+ *
+ * Reordering can be done during version updates.
+ */
enum DrawType {
UNUSED,
CLIP_PATH,
@@ -83,7 +90,9 @@
TRANSLATE_Z,
- LAST_DRAWTYPE_ENUM = TRANSLATE_Z
+ DRAW_SHADOWED_PICTURE_LIGHTS,
+
+ LAST_DRAWTYPE_ENUM = DRAW_SHADOWED_PICTURE_LIGHTS
};
// In the 'match' method, this constant will match any flavor of DRAW_BITMAP*
diff --git a/src/core/SkPicturePlayback.cpp b/src/core/SkPicturePlayback.cpp
index 60c4fe8..0bce09c 100644
--- a/src/core/SkPicturePlayback.cpp
+++ b/src/core/SkPicturePlayback.cpp
@@ -617,9 +617,11 @@
canvas->translate(dx, dy);
} break;
case TRANSLATE_Z: {
+#ifdef SK_EXPERIMENTAL_SHADOWING
SkScalar dz = reader->readScalar();
canvas->translateZ(dz);
- }
+#endif
+ } break;
default:
SkASSERTF(false, "Unknown draw type: %d", op);
}
diff --git a/src/core/SkPictureRecord.cpp b/src/core/SkPictureRecord.cpp
index f2a0fd8..562f056 100644
--- a/src/core/SkPictureRecord.cpp
+++ b/src/core/SkPictureRecord.cpp
@@ -219,6 +219,7 @@
}
void SkPictureRecord::didTranslateZ(SkScalar z) {
+#ifdef SK_EXPERIMENTAL_SHADOWING
this->validate(fWriter.bytesWritten(), 0);
// op + scalar
size_t size = 1 * kUInt32Size + 1 * sizeof(SkScalar);
@@ -226,6 +227,7 @@
this->addScalar(z);
this->validate(initialOffset, size);
this->INHERITED::didTranslateZ(z);
+#endif
}
static bool regionOpExpands(SkRegion::Op op) {
@@ -672,6 +674,27 @@
this->validate(initialOffset, size);
}
+void SkPictureRecord::onDrawShadowedPicture(const SkPicture* picture,
+ const SkMatrix* matrix,
+ const SkPaint* paint) {
+ // op + picture index
+ size_t size = 2 * kUInt32Size;
+ size_t initialOffset;
+
+ if (nullptr == matrix && nullptr == paint) {
+ initialOffset = this->addDraw(DRAW_PICTURE, &size);
+ this->addPicture(picture);
+ } else {
+ const SkMatrix& m = matrix ? *matrix : SkMatrix::I();
+ size += m.writeToMemory(nullptr) + kUInt32Size; // matrix + paint
+ initialOffset = this->addDraw(DRAW_PICTURE_MATRIX_PAINT, &size);
+ this->addPaintPtr(paint);
+ this->addMatrix(m);
+ this->addPicture(picture);
+ }
+ this->validate(initialOffset, size);
+}
+
void SkPictureRecord::onDrawDrawable(SkDrawable* drawable, const SkMatrix* matrix) {
// op + drawable index
size_t size = 2 * kUInt32Size;
diff --git a/src/core/SkPictureRecord.h b/src/core/SkPictureRecord.h
index 276dd3e..5f51a0e 100644
--- a/src/core/SkPictureRecord.h
+++ b/src/core/SkPictureRecord.h
@@ -159,7 +159,11 @@
void didConcat(const SkMatrix&) override;
void didSetMatrix(const SkMatrix&) override;
+#ifdef SK_EXPERIMENTAL_SHADOWING
void didTranslateZ(SkScalar) override;
+#endif
+ void didTranslateZ(SkScalar);
+#endif
void onDrawDRRect(const SkRRect&, const SkRRect&, const SkPaint&) override;
@@ -208,6 +212,17 @@
void onClipRegion(const SkRegion&, SkRegion::Op) override;
void onDrawPicture(const SkPicture*, const SkMatrix*, const SkPaint*) override;
+
+#ifdef SK_EXPERIMENTAL_SHADOWING
+ void onDrawShadowedPicture(const SkPicture*,
+ const SkMatrix*,
+ const SkPaint*) override;
+#else
+ void onDrawShadowedPicture(const SkPicture*,
+ const SkMatrix*,
+ const SkPaint*);
+#endif
+
void onDrawDrawable(SkDrawable*, const SkMatrix*) override;
void onDrawAnnotation(const SkRect&, const char[], SkData*) override;
@@ -253,5 +268,3 @@
typedef SkCanvas INHERITED;
};
-
-#endif
diff --git a/src/core/SkRecordDraw.cpp b/src/core/SkRecordDraw.cpp
index 02d07d5..cdfce66 100644
--- a/src/core/SkRecordDraw.cpp
+++ b/src/core/SkRecordDraw.cpp
@@ -86,7 +86,11 @@
DRAW(ClipRect, clipRect(r.rect, r.opAA.op, r.opAA.aa));
DRAW(ClipRegion, clipRegion(r.region, r.op));
+#ifdef SK_EXPERIMENTAL_SHADOWING
DRAW(TranslateZ, SkCanvas::translateZ(r.z));
+#else
+template <> void Draw::draw(const TranslateZ& r) { }
+#endif
DRAW(DrawBitmap, drawBitmap(r.bitmap.shallowCopy(), r.left, r.top, r.paint));
DRAW(DrawBitmapNine, drawBitmapNine(r.bitmap.shallowCopy(), r.center, r.dst, r.paint));
@@ -107,6 +111,13 @@
DRAW(DrawPath, drawPath(r.path, r.paint));
DRAW(DrawPatch, drawPatch(r.cubics, r.colors, r.texCoords, r.xmode, r.paint));
DRAW(DrawPicture, drawPicture(r.picture, &r.matrix, r.paint));
+
+#ifdef SK_EXPERIMENTAL_SHADOWING
+DRAW(DrawShadowedPicture, drawShadowedPicture(r.picture, &r.matrix, r.paint));
+#else
+template <> void Draw::draw(const DrawShadowedPicture& r) { }
+#endif
+
DRAW(DrawPoints, drawPoints(r.mode, r.count, r.pts, r.paint));
DRAW(DrawPosText, drawPosText(r.text, r.byteLength, r.pos, r.paint));
DRAW(DrawPosTextH, drawPosTextH(r.text, r.byteLength, r.xpos, r.y, r.paint));
@@ -472,6 +483,12 @@
return this->adjustAndMap(dst, op.paint);
}
+ Bounds bounds(const DrawShadowedPicture& op) const {
+ SkRect dst = op.picture->cullRect();
+ op.matrix.mapRect(&dst);
+ return this->adjustAndMap(dst, op.paint);
+ }
+
Bounds bounds(const DrawPosText& op) const {
const int N = op.paint.countText(op.text, op.byteLength);
if (N == 0) {
diff --git a/src/core/SkRecorder.cpp b/src/core/SkRecorder.cpp
index c7869bb..76fd3b8 100644
--- a/src/core/SkRecorder.cpp
+++ b/src/core/SkRecorder.cpp
@@ -305,6 +305,20 @@
}
}
+void SkRecorder::onDrawShadowedPicture(const SkPicture* pic,
+ const SkMatrix* matrix,
+ const SkPaint* paint) {
+ if (fDrawPictureMode == Record_DrawPictureMode) {
+ fApproxBytesUsedBySubPictures += SkPictureUtils::ApproximateBytesUsed(pic);
+ APPEND(DrawShadowedPicture, this->copy(paint), pic, matrix ? *matrix : SkMatrix::I());
+ } else {
+ SkASSERT(fDrawPictureMode == Playback_DrawPictureMode);
+ SkAutoCanvasMatrixPaint acmp(this, matrix, paint, pic->cullRect());
+ pic->playback(this);
+ }
+}
+
+
void SkRecorder::onDrawVertices(VertexMode vmode,
int vertexCount, const SkPoint vertices[],
const SkPoint texs[], const SkColor colors[],
@@ -369,8 +383,10 @@
APPEND(SetMatrix, matrix);
}
-void SkRecorder::didTranslateZ(SkScalar z) {
+void SkRecorder::didTranslateZ(SkScalar z) {
+#ifdef SK_EXPERIMENTAL_SHADOWING
APPEND(TranslateZ, z);
+#endif
}
void SkRecorder::onClipRect(const SkRect& rect, SkRegion::Op op, ClipEdgeStyle edgeStyle) {
diff --git a/src/core/SkRecorder.h b/src/core/SkRecorder.h
index 66a0067..5282740 100644
--- a/src/core/SkRecorder.h
+++ b/src/core/SkRecorder.h
@@ -60,7 +60,12 @@
void didConcat(const SkMatrix&) override;
void didSetMatrix(const SkMatrix&) override;
+
+#ifdef SK_EXPERIMENTAL_SHADOWING
void didTranslateZ(SkScalar) override;
+#else
+ void didTranslateZ(SkScalar);
+#endif
void onDrawDRRect(const SkRRect&, const SkRRect&, const SkPaint&) override;
void onDrawDrawable(SkDrawable*, const SkMatrix*) override;
@@ -126,6 +131,17 @@
void onClipRegion(const SkRegion& deviceRgn, SkRegion::Op op) override;
void onDrawPicture(const SkPicture*, const SkMatrix*, const SkPaint*) override;
+
+#ifdef SK_EXPERIMENTAL_SHADOWING
+ void onDrawShadowedPicture(const SkPicture*,
+ const SkMatrix*,
+ const SkPaint*) override;
+#else
+ void onDrawShadowedPicture(const SkPicture*,
+ const SkMatrix*,
+ const SkPaint*);
+#endif
+
void onDrawAnnotation(const SkRect&, const char[], SkData*) override;
sk_sp<SkSurface> onNewSurface(const SkImageInfo&, const SkSurfaceProps&) override;