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

Unified Diff: src/gpu/GrLayerAtlas.cpp

Issue 1412243013: Clean up GrAtlas and rename it GrLayerAtlas (Closed) Base URL: https://skia.googlesource.com/skia.git@master
Patch Set: clean up Created 5 years, 1 month 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/gpu/GrLayerAtlas.h ('k') | src/gpu/GrLayerCache.h » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: src/gpu/GrLayerAtlas.cpp
diff --git a/src/gpu/GrLayerAtlas.cpp b/src/gpu/GrLayerAtlas.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..3b30607c8cfc72cea328bbea9eb3023b89842098
--- /dev/null
+++ b/src/gpu/GrLayerAtlas.cpp
@@ -0,0 +1,145 @@
+
+/*
+ * Copyright 2010 Google Inc.
+ *
+ * Use of this source code is governed by a BSD-style license that can be
+ * found in the LICENSE file.
+ */
+
+#include "GrLayerAtlas.h"
+#include "GrRectanizer.h"
+#include "GrTextureProvider.h"
+
+///////////////////////////////////////////////////////////////////////////////
+GrLayerAtlas::Plot::Plot()
+ : fID(-1)
+ , fRects(nullptr) {
+ fOffset.set(0, 0);
+}
+
+GrLayerAtlas::Plot::~Plot() {
+ delete fRects;
+}
+
+void GrLayerAtlas::Plot::init(int id, int offX, int offY, int width, int height) {
+ fID = id;
+ fRects = GrRectanizer::Factory(width, height);
+ fOffset.set(offX * width, offY * height);
+}
+
+bool GrLayerAtlas::Plot::allocateRect(int width, int height, SkIPoint16* loc) {
+ if (!fRects->addRect(width, height, loc)) {
+ return false;
+ }
+
+ loc->fX += fOffset.fX;
+ loc->fY += fOffset.fY;
+ return true;
+}
+
+void GrLayerAtlas::Plot::reset() {
+ SkASSERT(fRects);
+ fRects->reset();
+}
+
+///////////////////////////////////////////////////////////////////////////////
+
+GrLayerAtlas::GrLayerAtlas(GrTextureProvider* texProvider, GrPixelConfig config,
+ GrSurfaceFlags flags,
+ const SkISize& backingTextureSize,
+ int numPlotsX, int numPlotsY) {
+ fTexProvider = texProvider;
+ fPixelConfig = config;
+ fFlags = flags;
+ fBackingTextureSize = backingTextureSize;
+ fTexture = nullptr;
+
+ int textureWidth = fBackingTextureSize.width();
+ int textureHeight = fBackingTextureSize.height();
+
+ int plotWidth = textureWidth / numPlotsX;
+ int plotHeight = textureHeight / numPlotsY;
+
+ SkASSERT(plotWidth * numPlotsX == textureWidth);
+ SkASSERT(plotHeight * numPlotsY == textureHeight);
+
+ // We currently do not support compressed atlases...
+ SkASSERT(!GrPixelConfigIsCompressed(config));
+
+ // set up allocated plots
+ fPlotArray = new Plot[numPlotsX * numPlotsY];
+
+ Plot* currPlot = fPlotArray;
+ for (int y = numPlotsY-1; y >= 0; --y) {
+ for (int x = numPlotsX-1; x >= 0; --x) {
+ currPlot->init(y*numPlotsX+x, x, y, plotWidth, plotHeight);
+
+ // build LRU list
+ fPlotList.addToHead(currPlot);
+ ++currPlot;
+ }
+ }
+}
+
+GrLayerAtlas::~GrLayerAtlas() {
+ SkSafeUnref(fTexture);
+ delete[] fPlotArray;
+}
+
+void GrLayerAtlas::makeMRU(Plot* plot) {
+ if (fPlotList.head() == plot) {
+ return;
+ }
+
+ fPlotList.remove(plot);
+ fPlotList.addToHead(plot);
+};
+
+GrLayerAtlas::Plot* GrLayerAtlas::addToAtlas(ClientPlotUsage* usage,
+ int width, int height, SkIPoint16* loc) {
+ // Iterate through the plots currently being used by this client and see if we can find a hole.
+ // The last one was most recently added and probably most empty.
+ // We want to consolidate the uses from individual clients to the same plot(s) so that
+ // when a specific client goes away they are more likely to completely empty a plot.
+ for (int i = usage->numPlots()-1; i >= 0; --i) {
+ Plot* plot = usage->plot(i);
+ if (plot->allocateRect(width, height, loc)) {
+ this->makeMRU(plot);
+ return plot;
+ }
+ }
+
+ // before we get a new plot, make sure we have a backing texture
+ if (nullptr == fTexture) {
+ // TODO: Update this to use the cache rather than directly creating a texture.
+ GrSurfaceDesc desc;
+ desc.fFlags = fFlags;
+ desc.fWidth = fBackingTextureSize.width();
+ desc.fHeight = fBackingTextureSize.height();
+ desc.fConfig = fPixelConfig;
+
+ fTexture = fTexProvider->createTexture(desc, true, nullptr, 0);
+ if (nullptr == fTexture) {
+ return nullptr;
+ }
+ }
+
+ // Now look through all allocated plots for one we can share, in MRU order
+ // TODO: its seems like traversing from emptiest to fullest would make more sense
+ PlotList::Iter plotIter;
+ plotIter.init(fPlotList, PlotList::Iter::kHead_IterStart);
+ Plot* plot;
+ while ((plot = plotIter.get())) {
+ if (plot->allocateRect(width, height, loc)) {
+ this->makeMRU(plot);
+ // new plot for atlas, put at end of array
+ usage->appendPlot(plot);
+ return plot;
+ }
+ plotIter.next();
+ }
+
+ // If the above fails, then the current plot list has no room
+ return nullptr;
+}
+
« no previous file with comments | « src/gpu/GrLayerAtlas.h ('k') | src/gpu/GrLayerCache.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698