Anforderungen  |   Konzepte  |   Entwurf  |   Entwicklung  |   Qualitätssicherung  |   Lebenszyklus  |   Steuerung
 
 
 
 


Quelle  SkCanvasStack.cpp   Sprache: C

 
/*
 * Copyright 2013 Google Inc.
 *
 * Use of this source code is governed by a BSD-style license that can be
 * found in the LICENSE file.
 */


#include "src/utils/SkCanvasStack.h"

#include "include/core/SkRect.h"
#include "include/core/SkScalar.h"
#include "include/core/SkShader.h"
#include "include/private/base/SkTDArray.h"
#include <utility>

class SkPath;
class SkRRect;

SkCanvasStack::SkCanvasStack(int width, int height)
        : INHERITED(width, height) {}

SkCanvasStack::~SkCanvasStack() {
    this->removeAll();
}

void SkCanvasStack::pushCanvas(std::unique_ptr<SkCanvas> canvas, const SkIPoint& origin) {
    if (canvas) {
        // compute the bounds of this canvas
        const SkIRect canvasBounds = SkIRect::MakeSize(canvas->getBaseLayerSize());

        // push the canvas onto the stack
        this->INHERITED::addCanvas(canvas.get());

        // push the canvas data onto the stack
        CanvasData* data = &fCanvasData.push_back();
        data->origin = origin;
        data->requiredClip.setRect(canvasBounds);
        data->ownedCanvas = std::move(canvas);

        // subtract this region from the canvas objects already on the stack.
        // This ensures they do not draw into the space occupied by the layers
        // above them.
        for (int i = fList.size() - 1; i > 0; --i) {
            SkIRect localBounds = canvasBounds;
            localBounds.offset(origin - fCanvasData[i-1].origin);

            fCanvasData[i-1].requiredClip.op(localBounds, SkRegion::kDifference_Op);
            fList[i-1]->clipRegion(fCanvasData[i-1].requiredClip);
        }
    }
    SkASSERT(fList.size() == fCanvasData.size());
}

void SkCanvasStack::removeAll() {
    this->INHERITED::removeAll();   // call the baseclass *before* we actually delete the canvases
    fCanvasData.clear();
}

/**
 * Traverse all canvases (e.g. layers) the stack and ensure that they are clipped
 * to their bounds and that the area covered by any canvas higher in the stack is
 * also clipped out.
 */

void SkCanvasStack::clipToZOrderedBounds() {
    SkASSERT(fList.size() == fCanvasData.size());
    for (int i = 0; i < fList.size(); ++i) {
        fList[i]->clipRegion(fCanvasData[i].requiredClip);
    }
}

////////////////////////////////////////////////////////////////////////////////

/**
 * We need to handle setMatrix specially as it overwrites the matrix in each
 * canvas unlike all other matrix operations (i.e. translate, scale, etc) which
 * just pre-concatenate with the existing matrix.
 */

void SkCanvasStack::didSetM44(const SkM44& mx) {
    SkASSERT(fList.size() == fCanvasData.size());
    for (int i = 0; i < fList.size(); ++i) {
        fList[i]->setMatrix(SkM44::Translate(SkIntToScalar(-fCanvasData[i].origin.x()),
                                             SkIntToScalar(-fCanvasData[i].origin.y())) * mx);
    }
    this->SkCanvas::didSetM44(mx);
}

void SkCanvasStack::onClipRect(const SkRect& r, SkClipOp op, ClipEdgeStyle edgeStyle) {
    this->INHERITED::onClipRect(r, op, edgeStyle);
    this->clipToZOrderedBounds();
}

void SkCanvasStack::onClipRRect(const SkRRect& rr, SkClipOp op, ClipEdgeStyle edgeStyle) {
    this->INHERITED::onClipRRect(rr, op, edgeStyle);
    this->clipToZOrderedBounds();
}

void SkCanvasStack::onClipPath(const SkPath& p, SkClipOp op, ClipEdgeStyle edgeStyle) {
    this->INHERITED::onClipPath(p, op, edgeStyle);
    this->clipToZOrderedBounds();
}

void SkCanvasStack::onClipShader(sk_sp<SkShader> cs, SkClipOp op) {
    this->INHERITED::onClipShader(std::move(cs), op);
    // we don't change the "bounds" of the clip, so we don't need to update zorder
}

void SkCanvasStack::onClipRegion(const SkRegion& deviceRgn, SkClipOp op) {
    SkASSERT(fList.size() == fCanvasData.size());
    for (int i = 0; i < fList.size(); ++i) {
        SkRegion tempRegion;
        deviceRgn.translate(-fCanvasData[i].origin.x(),
                            -fCanvasData[i].origin.y(), &tempRegion);
        tempRegion.op(fCanvasData[i].requiredClip, SkRegion::kIntersect_Op);
        fList[i]->clipRegion(tempRegion, op);
    }
    this->SkCanvas::onClipRegion(deviceRgn, op);
}

Messung V0.5
C=90 H=73 G=81

¤ Dauer der Verarbeitung: 0.12 Sekunden  (vorverarbeitet)  ¤

*© Formatika GbR, Deutschland






Wurzel

Suchen

Beweissystem der NASA

Beweissystem Isabelle

NIST Cobol Testsuite

Cephes Mathematical Library

Wiener Entwicklungsmethode

Haftungshinweis

Die Informationen auf dieser Webseite wurden nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit, noch Qualität der bereit gestellten Informationen zugesichert.

Bemerkung:

Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.






                                                                                                                                                                                                                                                                                                                                                                                                     


Neuigkeiten

     Aktuelles
     Motto des Tages

Software

     Produkte
     Quellcodebibliothek

Aktivitäten

     Artikel über Sicherheit
     Anleitung zur Aktivierung von SSL

Muße

     Gedichte
     Musik
     Bilder

Jenseits des Üblichen ....

Besucherstatistik

Besucherstatistik

Monitoring

Montastic status badge