Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(162)

Unified Diff: src/core/SkRemote.cpp

Issue 1412223002: SkRemote: add xfermodes (Closed) Base URL: https://skia.googlesource.com/skia.git@master
Patch Set: rebase Created 5 years, 2 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « src/core/SkRemote.h ('k') | src/core/SkRemote_protocol.h » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: src/core/SkRemote.cpp
diff --git a/src/core/SkRemote.cpp b/src/core/SkRemote.cpp
index 3966aaccc0318afba694f8775f00fdb6617d4eb4..8efeb8b8451f766dacc295c0d487e427fad741ea 100644
--- a/src/core/SkRemote.cpp
+++ b/src/core/SkRemote.cpp
@@ -97,15 +97,16 @@ namespace SkRemote {
Cache* Cache::CreateNeverCache() {
struct NeverCache final : public Cache {
NeverCache()
- : fNextMatrix(Type::kMatrix)
- , fNextMisc (Type::kMisc)
- , fNextPath (Type::kPath)
- , fNextStroke(Type::kStroke)
+ : fNextMatrix (Type::kMatrix)
+ , fNextMisc (Type::kMisc)
+ , fNextPath (Type::kPath)
+ , fNextStroke (Type::kStroke)
+ , fNextXfermode(Type::kXfermode)
{}
void cleanup(Encoder*) override {}
static bool Helper(ID* next, ID* id, LookupScope* ls) {
- *id = (*next)++;
+ *id = ++(*next);
ls->undefineWhenDone(*id);
return false;
}
@@ -122,65 +123,120 @@ namespace SkRemote {
bool lookup(const Stroke&, ID* id, LookupScope* ls) override {
return Helper(&fNextStroke, id, ls);
}
+ bool lookup(const SkXfermode* xfermode, ID* id, LookupScope* ls) override {
+ if (!xfermode) {
+ *id = ID(Type::kXfermode);
+ return true; // Null IDs are always defined.
+ }
+ return Helper(&fNextXfermode, id, ls);
+ }
ID fNextMatrix,
fNextMisc,
fNextPath,
- fNextStroke;
+ fNextStroke,
+ fNextXfermode;
};
return new NeverCache;
}
- // Can't be declared locally inside AlwaysCache because of the templating. :(
- template <typename T, typename Map>
- static bool always_cache_helper(const T& val, Map* map, ID* next, ID* id) {
- if (ID* found = map->find(val)) {
- *id = *found;
- return true;
+ // These can't be declared locally inside AlwaysCache because of the templating. :(
+ namespace {
+ template <typename T, typename Map>
+ static bool always_cache_lookup(const T& val, Map* map, ID* next, ID* id) {
+ if (const ID* found = map->find(val)) {
+ *id = *found;
+ return true;
+ }
+ *id = ++(*next);
+ map->set(val, *id);
+ return false;
}
- *id = (*next)++;
- map->set(val, *id);
- return false;
- }
+
+ struct Undefiner {
+ Encoder* fEncoder;
+
+ template <typename T>
+ void operator()(const T&, ID* id) const { fEncoder->undefine(*id); }
+ };
+
+ // Maps const T* -> ID, and refs the key. nullptr always maps to ID(kType).
+ template <typename T, Type kType>
+ class RefKeyMap {
+ public:
+ RefKeyMap() {}
+ ~RefKeyMap() { fMap.foreach([](const T* key, ID*) { key->unref(); }); }
+
+ void set(const T* key, const ID& id) {
+ SkASSERT(key && id.type() == kType);
+ fMap.set(SkRef(key), id);
+ }
+
+ void remove(const T* key) {
+ SkASSERT(key);
+ fMap.remove(key);
+ key->unref();
+ }
+
+ const ID* find(const T* key) const {
+ static const ID nullID(kType);
+ return key ? fMap.find(key) : &nullID;
+ }
+
+ template <typename Fn>
+ void foreach(const Fn& fn) { fMap.foreach(fn); }
+ private:
+ SkTHashMap<const T*, ID> fMap;
+ };
+ } // namespace
Cache* Cache::CreateAlwaysCache() {
struct AlwaysCache final : public Cache {
AlwaysCache()
- : fNextMatrix(Type::kMatrix)
- , fNextMisc (Type::kMisc)
- , fNextPath (Type::kPath)
- , fNextStroke(Type::kStroke)
+ : fNextMatrix (Type::kMatrix)
+ , fNextMisc (Type::kMisc)
+ , fNextPath (Type::kPath)
+ , fNextStroke (Type::kStroke)
+ , fNextXfermode(Type::kXfermode)
{}
void cleanup(Encoder* encoder) override {
- fMatrix.foreach([=](const SkMatrix&, ID* id) { encoder->undefine(*id); });
- fMisc .foreach([=](const Misc&, ID* id) { encoder->undefine(*id); });
- fPath .foreach([=](const SkPath&, ID* id) { encoder->undefine(*id); });
- fStroke.foreach([=](const Stroke&, ID* id) { encoder->undefine(*id); });
+ Undefiner undef{encoder};
+ fMatrix .foreach(undef);
+ fMisc .foreach(undef);
+ fPath .foreach(undef);
+ fStroke .foreach(undef);
+ fXfermode.foreach(undef);
}
bool lookup(const SkMatrix& matrix, ID* id, LookupScope*) override {
- return always_cache_helper(matrix, &fMatrix, &fNextMatrix, id);
+ return always_cache_lookup(matrix, &fMatrix, &fNextMatrix, id);
}
bool lookup(const Misc& misc, ID* id, LookupScope*) override {
- return always_cache_helper(misc, &fMisc, &fNextMisc, id);
+ return always_cache_lookup(misc, &fMisc, &fNextMisc, id);
}
bool lookup(const SkPath& path, ID* id, LookupScope*) override {
- return always_cache_helper(path, &fPath, &fNextPath, id);
+ return always_cache_lookup(path, &fPath, &fNextPath, id);
}
bool lookup(const Stroke& stroke, ID* id, LookupScope*) override {
- return always_cache_helper(stroke, &fStroke, &fNextStroke, id);
+ return always_cache_lookup(stroke, &fStroke, &fNextStroke, id);
}
+ bool lookup(const SkXfermode* xfermode, ID* id, LookupScope*) override {
+ return always_cache_lookup(xfermode, &fXfermode, &fNextXfermode, id);
+ }
+
+ SkTHashMap<SkMatrix, ID> fMatrix;
+ SkTHashMap<Misc, ID, MiscHash> fMisc;
+ SkTHashMap<SkPath, ID> fPath;
+ SkTHashMap<Stroke, ID> fStroke;
+ RefKeyMap<SkXfermode, Type::kXfermode> fXfermode;
- SkTHashMap<SkMatrix, ID> fMatrix;
- SkTHashMap<Misc, ID, MiscHash> fMisc;
- SkTHashMap<SkPath, ID> fPath;
- SkTHashMap<Stroke, ID> fStroke;
ID fNextMatrix,
fNextMisc,
fNextPath,
- fNextStroke;
+ fNextStroke,
+ fNextXfermode;
};
return new AlwaysCache;
}
@@ -236,13 +292,14 @@ namespace SkRemote {
void Client::onDrawPath(const SkPath& path, const SkPaint& paint) {
LookupScope ls(fCache, fEncoder);
ID p = ls.lookup(path),
- m = ls.lookup(Misc::CreateFrom(paint));
+ m = ls.lookup(Misc::CreateFrom(paint)),
+ x = ls.lookup(paint.getXfermode());
if (paint.getStyle() == SkPaint::kFill_Style) {
- fEncoder->fillPath(p, m);
+ fEncoder->fillPath(p, m, x);
} else {
// TODO: handle kStrokeAndFill_Style
- fEncoder->strokePath(p, m, ls.lookup(Stroke::CreateFrom(paint)));
+ fEncoder->strokePath(p, m, x, ls.lookup(Stroke::CreateFrom(paint)));
}
}
@@ -302,17 +359,19 @@ namespace SkRemote {
Server::Server(SkCanvas* canvas) : fCanvas(canvas) {}
- void Server::define(ID id, const SkMatrix& v) { fMatrix.set(id, v); }
- void Server::define(ID id, const Misc& v) { fMisc .set(id, v); }
- void Server::define(ID id, const SkPath& v) { fPath .set(id, v); }
- void Server::define(ID id, const Stroke& v) { fStroke.set(id, v); }
+ void Server::define(ID id, const SkMatrix& v) { fMatrix .set(id, v); }
+ void Server::define(ID id, const Misc& v) { fMisc .set(id, v); }
+ void Server::define(ID id, const SkPath& v) { fPath .set(id, v); }
+ void Server::define(ID id, const Stroke& v) { fStroke .set(id, v); }
+ void Server::define(ID id, SkXfermode* v) { fXfermode.set(id, v); }
void Server::undefine(ID id) {
switch(id.type()) {
- case Type::kMatrix: return fMatrix.remove(id);
- case Type::kMisc: return fMisc .remove(id);
- case Type::kPath: return fPath .remove(id);
- case Type::kStroke: return fStroke.remove(id);
+ case Type::kMatrix: return fMatrix .remove(id);
+ case Type::kMisc: return fMisc .remove(id);
+ case Type::kPath: return fPath .remove(id);
+ case Type::kStroke: return fStroke .remove(id);
+ case Type::kXfermode: return fXfermode.remove(id);
case Type::kNone: SkASSERT(false);
};
@@ -326,17 +385,19 @@ namespace SkRemote {
void Server::clipPath(ID path, SkRegion::Op op, bool aa) {
fCanvas->clipPath(fPath.find(path), op, aa);
}
- void Server::fillPath(ID path, ID misc) {
+ void Server::fillPath(ID path, ID misc, ID xfermode) {
SkPaint paint;
paint.setStyle(SkPaint::kFill_Style);
fMisc.find(misc).applyTo(&paint);
+ paint.setXfermode(fXfermode.find(xfermode));
fCanvas->drawPath(fPath.find(path), paint);
}
- void Server::strokePath(ID path, ID misc, ID stroke) {
+ void Server::strokePath(ID path, ID misc, ID xfermode, ID stroke) {
SkPaint paint;
paint.setStyle(SkPaint::kStroke_Style);
fMisc .find(misc ).applyTo(&paint);
fStroke.find(stroke).applyTo(&paint);
+ paint.setXfermode(fXfermode.find(xfermode));
fCanvas->drawPath(fPath.find(path), paint);
}
« no previous file with comments | « src/core/SkRemote.h ('k') | src/core/SkRemote_protocol.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698