diff options
Diffstat (limited to 'gpu/src/GrDrawTarget.cpp')
-rw-r--r-- | gpu/src/GrDrawTarget.cpp | 679 |
1 files changed, 0 insertions, 679 deletions
diff --git a/gpu/src/GrDrawTarget.cpp b/gpu/src/GrDrawTarget.cpp deleted file mode 100644 index 2848999..0000000 --- a/gpu/src/GrDrawTarget.cpp +++ /dev/null @@ -1,679 +0,0 @@ -/* - Copyright 2010 Google Inc. - - Licensed under the Apache License, Version 2.0 (the "License"); - you may not use this file except in compliance with the License. - You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. - */ - - -#include "GrDrawTarget.h" -#include "GrGpuVertex.h" -#include "GrTexture.h" - -namespace { - -// recursive helper for creating mask with all the tex coord bits set for -// one stage -template <int N> -int stage_mask_recur(int stage) { - return GrDrawTarget::StageTexCoordVertexLayoutBit(stage, N) | - stage_mask_recur<N+1>(stage); -} -template<> -int stage_mask_recur<GrDrawTarget::kNumStages>(int) { return 0; } - -// mask of all tex coord indices for one stage -int stage_tex_coord_mask(int stage) { - return stage_mask_recur<0>(stage); -} - -// mask of all bits relevant to one stage -int stage_mask(int stage) { - return stage_tex_coord_mask(stage) | - GrDrawTarget::StagePosAsTexCoordVertexLayoutBit(stage); -} - -// recursive helper for creating mask of with all bits set relevant to one -// texture coordinate index -template <int N> -int tex_coord_mask_recur(int texCoordIdx) { - return GrDrawTarget::StageTexCoordVertexLayoutBit(N, texCoordIdx) | - tex_coord_mask_recur<N+1>(texCoordIdx); -} -template<> -int tex_coord_mask_recur<GrDrawTarget::kMaxTexCoords>(int) { return 0; } - -// mask of all bits relevant to one texture coordinate index -int tex_coord_idx_mask(int texCoordIdx) { - return tex_coord_mask_recur<0>(texCoordIdx); -} - -bool check_layout(GrVertexLayout layout) { - // can only have 1 or 0 bits set for each stage. - for (int s = 0; s < GrDrawTarget::kNumStages; ++s) { - int stageBits = layout & stage_mask(s); - if (stageBits && !GrIsPow2(stageBits)) { - return false; - } - } - return true; -} - -} //unnamed namespace - -size_t GrDrawTarget::VertexSize(GrVertexLayout vertexLayout) { - GrAssert(check_layout(vertexLayout)); - - size_t vecSize = (vertexLayout & kTextFormat_VertexLayoutBit) ? - sizeof(GrGpuTextVertex) : - sizeof(GrPoint); - - size_t size = vecSize; // position - for (int t = 0; t < kMaxTexCoords; ++t) { - if (tex_coord_idx_mask(t) & vertexLayout) { - size += vecSize; - } - } - if (vertexLayout & kColor_VertexLayoutBit) { - size += sizeof(GrColor); - } - return size; -} - -int GrDrawTarget::VertexStageCoordOffset(int stage, GrVertexLayout vertexLayout) { - GrAssert(check_layout(vertexLayout)); - if (StagePosAsTexCoordVertexLayoutBit(stage) & vertexLayout) { - return 0; - } - int tcIdx = VertexTexCoordsForStage(stage, vertexLayout); - if (tcIdx >= 0) { - - int vecSize = (vertexLayout & kTextFormat_VertexLayoutBit) ? - sizeof(GrGpuTextVertex) : - sizeof(GrPoint); - int offset = vecSize; // position - // figure out how many tex coordinates are present and precede this one. - for (int t = 0; t < tcIdx; ++t) { - if (tex_coord_idx_mask(t) & vertexLayout) { - offset += vecSize; - } - } - return offset; - } - - return -1; -} - -int GrDrawTarget::VertexColorOffset(GrVertexLayout vertexLayout) { - GrAssert(check_layout(vertexLayout)); - - if (vertexLayout & kColor_VertexLayoutBit) { - int vecSize = (vertexLayout & kTextFormat_VertexLayoutBit) ? - sizeof(GrGpuTextVertex) : - sizeof(GrPoint); - int offset = vecSize; // position - // figure out how many tex coordinates are present and precede this one. - for (int t = 0; t < kMaxTexCoords; ++t) { - if (tex_coord_idx_mask(t) & vertexLayout) { - offset += vecSize; - } - } - return offset; - } - return -1; -} - -int GrDrawTarget::VertexSizeAndOffsetsByIdx(GrVertexLayout vertexLayout, - int texCoordOffsetsByIdx[kMaxTexCoords], - int* colorOffset) { - GrAssert(check_layout(vertexLayout)); - - GrAssert(NULL != texCoordOffsetsByIdx); - GrAssert(NULL != colorOffset); - - int vecSize = (vertexLayout & kTextFormat_VertexLayoutBit) ? - sizeof(GrGpuTextVertex) : - sizeof(GrPoint); - int size = vecSize; // position - - for (int t = 0; t < kMaxTexCoords; ++t) { - if (tex_coord_idx_mask(t) & vertexLayout) { - texCoordOffsetsByIdx[t] = size; - size += vecSize; - } else { - texCoordOffsetsByIdx[t] = -1; - } - } - if (kColor_VertexLayoutBit & vertexLayout) { - *colorOffset = size; - size += sizeof(GrColor); - } else { - *colorOffset = -1; - } - return size; -} - -int GrDrawTarget::VertexSizeAndOffsetsByStage(GrVertexLayout vertexLayout, - int texCoordOffsetsByStage[kNumStages], - int* colorOffset) { - GrAssert(check_layout(vertexLayout)); - - GrAssert(NULL != texCoordOffsetsByStage); - GrAssert(NULL != colorOffset); - - int texCoordOffsetsByIdx[kMaxTexCoords]; - int size = VertexSizeAndOffsetsByIdx(vertexLayout, - texCoordOffsetsByIdx, - colorOffset); - for (int s = 0; s < kNumStages; ++s) { - int tcIdx; - if (StagePosAsTexCoordVertexLayoutBit(s) & vertexLayout) { - texCoordOffsetsByStage[s] = 0; - } else if ((tcIdx = VertexTexCoordsForStage(s, vertexLayout)) >= 0) { - texCoordOffsetsByStage[s] = texCoordOffsetsByIdx[tcIdx]; - } else { - texCoordOffsetsByStage[s] = -1; - } - } - return size; -} - -bool GrDrawTarget::VertexUsesStage(int stage, GrVertexLayout vertexLayout) { - GrAssert(stage < kNumStages); - GrAssert(check_layout(vertexLayout)); - return !!(stage_mask(stage) & vertexLayout); -} - -bool GrDrawTarget::VertexUsesTexCoordIdx(int coordIndex, - GrVertexLayout vertexLayout) { - GrAssert(coordIndex < kMaxTexCoords); - GrAssert(check_layout(vertexLayout)); - return !!(tex_coord_idx_mask(coordIndex) & vertexLayout); -} - -int GrDrawTarget::VertexTexCoordsForStage(int stage, GrVertexLayout vertexLayout) { - GrAssert(stage < kNumStages); - GrAssert(check_layout(vertexLayout)); - int bit = vertexLayout & stage_tex_coord_mask(stage); - if (bit) { - // figure out which set of texture coordates is used - // bits are ordered T0S0, T0S1, T0S2, ..., T1S0, T1S1, ... - // and start at bit 0. - GR_STATIC_ASSERT(sizeof(GrVertexLayout) <= sizeof(uint32_t)); - return (32 - Gr_clz(bit) - 1) / kNumStages; - } - return -1; -} - -void GrDrawTarget::VertexLayoutUnitTest() { - // not necessarily exhaustive - static bool run; - if (!run) { - run = true; - for (int s = 0; s < kNumStages; ++s) { - - GrAssert(!VertexUsesStage(s, 0)); - GrAssert(-1 == VertexStageCoordOffset(s, 0)); - GrVertexLayout stageMask = 0; - for (int t = 0; t < kMaxTexCoords; ++t) { - stageMask |= StageTexCoordVertexLayoutBit(s,t); - } - GrAssert(1 == kMaxTexCoords || !check_layout(stageMask)); - GrAssert(stage_tex_coord_mask(s) == stageMask); - stageMask |= StagePosAsTexCoordVertexLayoutBit(s); - GrAssert(stage_mask(s) == stageMask); - GrAssert(!check_layout(stageMask)); - } - for (int t = 0; t < kMaxTexCoords; ++t) { - GrVertexLayout tcMask = 0; - GrAssert(!VertexUsesTexCoordIdx(t, 0)); - for (int s = 0; s < kNumStages; ++s) { - tcMask |= StageTexCoordVertexLayoutBit(s,t); - GrAssert(VertexUsesStage(s, tcMask)); - GrAssert(sizeof(GrPoint) == VertexStageCoordOffset(s, tcMask)); - GrAssert(VertexUsesTexCoordIdx(t, tcMask)); - GrAssert(2*sizeof(GrPoint) == VertexSize(tcMask)); - GrAssert(t == VertexTexCoordsForStage(s, tcMask)); - for (int s2 = s + 1; s2 < kNumStages; ++s2) { - GrAssert(-1 == VertexStageCoordOffset(s2, tcMask)); - GrAssert(!VertexUsesStage(s2, tcMask)); - GrAssert(-1 == VertexTexCoordsForStage(s2, tcMask)); - - #if GR_DEBUG - GrVertexLayout posAsTex = tcMask | StagePosAsTexCoordVertexLayoutBit(s2); - #endif - GrAssert(0 == VertexStageCoordOffset(s2, posAsTex)); - GrAssert(VertexUsesStage(s2, posAsTex)); - GrAssert(2*sizeof(GrPoint) == VertexSize(posAsTex)); - GrAssert(-1 == VertexTexCoordsForStage(s2, posAsTex)); - } - #if GR_DEBUG - GrVertexLayout withColor = tcMask | kColor_VertexLayoutBit; - #endif - GrAssert(2*sizeof(GrPoint) == VertexColorOffset(withColor)); - GrAssert(2*sizeof(GrPoint) + sizeof(GrColor) == VertexSize(withColor)); - } - GrAssert(tex_coord_idx_mask(t) == tcMask); - GrAssert(check_layout(tcMask)); - - int stageOffsets[kNumStages]; - int colorOffset; - int size; - size = VertexSizeAndOffsetsByStage(tcMask, stageOffsets, &colorOffset); - GrAssert(2*sizeof(GrPoint) == size); - GrAssert(-1 == colorOffset); - for (int s = 0; s < kNumStages; ++s) { - GrAssert(VertexUsesStage(s, tcMask)); - GrAssert(sizeof(GrPoint) == stageOffsets[s]); - GrAssert(sizeof(GrPoint) == VertexStageCoordOffset(s, tcMask)); - } - } - } -} - -//////////////////////////////////////////////////////////////////////////////// - -GrDrawTarget::GrDrawTarget() { -#if GR_DEBUG - VertexLayoutUnitTest(); -#endif - fReservedGeometry.fLocked = false; -#if GR_DEBUG - fReservedGeometry.fVertexCount = ~0; - fReservedGeometry.fIndexCount = ~0; -#endif - fGeometrySrc.fVertexSrc = kReserved_GeometrySrcType; - fGeometrySrc.fIndexSrc = kReserved_GeometrySrcType; -} - -void GrDrawTarget::setClip(const GrClip& clip) { - clipWillBeSet(clip); - fClip = clip; -} - -const GrClip& GrDrawTarget::getClip() const { - return fClip; -} - -void GrDrawTarget::setTexture(int stage, GrTexture* tex) { - GrAssert(stage >= 0 && stage < kNumStages); - fCurrDrawState.fTextures[stage] = tex; -} - -const GrTexture* GrDrawTarget::getTexture(int stage) const { - GrAssert(stage >= 0 && stage < kNumStages); - return fCurrDrawState.fTextures[stage]; -} - -GrTexture* GrDrawTarget::getTexture(int stage) { - GrAssert(stage >= 0 && stage < kNumStages); - return fCurrDrawState.fTextures[stage]; -} - -void GrDrawTarget::setRenderTarget(GrRenderTarget* target) { - fCurrDrawState.fRenderTarget = target; -} - -const GrRenderTarget* GrDrawTarget::getRenderTarget() const { - return fCurrDrawState.fRenderTarget; -} - -GrRenderTarget* GrDrawTarget::getRenderTarget() { - return fCurrDrawState.fRenderTarget; -} - -void GrDrawTarget::setViewMatrix(const GrMatrix& m) { - fCurrDrawState.fViewMatrix = m; -} - -void GrDrawTarget::preConcatViewMatrix(const GrMatrix& matrix) { - fCurrDrawState.fViewMatrix.preConcat(matrix); -} - -void GrDrawTarget::postConcatViewMatrix(const GrMatrix& matrix) { - fCurrDrawState.fViewMatrix.postConcat(matrix); -} - -const GrMatrix& GrDrawTarget::getViewMatrix() const { - return fCurrDrawState.fViewMatrix; -} - -bool GrDrawTarget::getViewInverse(GrMatrix* matrix) const { - // Mike: Can we cache this somewhere? - // Brian: Sure, do we use it often? - - GrMatrix inverse; - if (fCurrDrawState.fViewMatrix.invert(&inverse)) { - if (matrix) { - *matrix = inverse; - } - return true; - } - return false; -} - -void GrDrawTarget::setSamplerState(int stage, const GrSamplerState& state) { - GrAssert(stage >= 0 && stage < kNumStages); - fCurrDrawState.fSamplerStates[stage] = state; -} - -void GrDrawTarget::enableState(uint32_t bits) { - fCurrDrawState.fFlagBits |= bits; -} - -void GrDrawTarget::disableState(uint32_t bits) { - fCurrDrawState.fFlagBits &= ~(bits); -} - -void GrDrawTarget::setBlendFunc(GrBlendCoeff srcCoeff, - GrBlendCoeff dstCoeff) { - fCurrDrawState.fSrcBlend = srcCoeff; - fCurrDrawState.fDstBlend = dstCoeff; -#if GR_DEBUG - switch (dstCoeff) { - case kDC_BlendCoeff: - case kIDC_BlendCoeff: - case kDA_BlendCoeff: - case kIDA_BlendCoeff: - GrPrintf("Unexpected dst blend coeff. Won't work correctly with" - "coverage stages.\n"); - break; - default: - break; - } - switch (srcCoeff) { - case kSC_BlendCoeff: - case kISC_BlendCoeff: - case kSA_BlendCoeff: - case kISA_BlendCoeff: - GrPrintf("Unexpected src blend coeff. Won't work correctly with" - "coverage stages.\n"); - break; - default: - break; - } -#endif -} - -void GrDrawTarget::setColor(GrColor c) { - fCurrDrawState.fColor = c; -} - -void GrDrawTarget::setColorFilter(GrColor c, SkXfermode::Mode mode) { - fCurrDrawState.fColorFilterColor = c; - fCurrDrawState.fColorFilterXfermode = mode; -} - -void GrDrawTarget::setAlpha(uint8_t a) { - this->setColor((a << 24) | (a << 16) | (a << 8) | a); -} - -void GrDrawTarget::saveCurrentDrawState(SavedDrawState* state) const { - state->fState = fCurrDrawState; -} - -void GrDrawTarget::restoreDrawState(const SavedDrawState& state) { - fCurrDrawState = state.fState; -} - -void GrDrawTarget::copyDrawState(const GrDrawTarget& srcTarget) { - fCurrDrawState = srcTarget.fCurrDrawState; -} - - -bool GrDrawTarget::reserveAndLockGeometry(GrVertexLayout vertexLayout, - uint32_t vertexCount, - uint32_t indexCount, - void** vertices, - void** indices) { - GrAssert(!fReservedGeometry.fLocked); - fReservedGeometry.fVertexCount = vertexCount; - fReservedGeometry.fIndexCount = indexCount; - - fReservedGeometry.fLocked = this->onAcquireGeometry(vertexLayout, - vertices, - indices); - if (fReservedGeometry.fLocked) { - if (vertexCount) { - fGeometrySrc.fVertexSrc = kReserved_GeometrySrcType; - fGeometrySrc.fVertexLayout = vertexLayout; - } else if (NULL != vertices) { - *vertices = NULL; - } - if (indexCount) { - fGeometrySrc.fIndexSrc = kReserved_GeometrySrcType; - } else if (NULL != indices) { - *indices = NULL; - } - } - return fReservedGeometry.fLocked; -} - -bool GrDrawTarget::geometryHints(GrVertexLayout vertexLayout, - int32_t* vertexCount, - int32_t* indexCount) const { - GrAssert(!fReservedGeometry.fLocked); - if (NULL != vertexCount) { - *vertexCount = -1; - } - if (NULL != indexCount) { - *indexCount = -1; - } - return false; -} - -void GrDrawTarget::releaseReservedGeometry() { - GrAssert(fReservedGeometry.fLocked); - this->onReleaseGeometry(); - fReservedGeometry.fLocked = false; -} - -void GrDrawTarget::setVertexSourceToArray(GrVertexLayout vertexLayout, - const void* vertexArray, - int vertexCount) { - fGeometrySrc.fVertexSrc = kArray_GeometrySrcType; - fGeometrySrc.fVertexLayout = vertexLayout; - this->onSetVertexSourceToArray(vertexArray, vertexCount); -} - -void GrDrawTarget::setIndexSourceToArray(const void* indexArray, - int indexCount) { - fGeometrySrc.fIndexSrc = kArray_GeometrySrcType; - this->onSetIndexSourceToArray(indexArray, indexCount); -} - -void GrDrawTarget::setVertexSourceToBuffer(GrVertexLayout vertexLayout, - const GrVertexBuffer* buffer) { - fGeometrySrc.fVertexSrc = kBuffer_GeometrySrcType; - fGeometrySrc.fVertexBuffer = buffer; - fGeometrySrc.fVertexLayout = vertexLayout; -} - -void GrDrawTarget::setIndexSourceToBuffer(const GrIndexBuffer* buffer) { - fGeometrySrc.fIndexSrc = kBuffer_GeometrySrcType; - fGeometrySrc.fIndexBuffer = buffer; -} - -/////////////////////////////////////////////////////////////////////////////// - -bool GrDrawTarget::canDisableBlend() const { - // If we compute a coverage value (using edge AA or a coverage stage) then - // we can't force blending off. - if (fCurrDrawState.fEdgeAANumEdges > 0) { - return false; - } - for (int s = fCurrDrawState.fFirstCoverageStage; s < kNumStages; ++s) { - if (this->isStageEnabled(s)) { - return false; - } - } - - if ((kOne_BlendCoeff == fCurrDrawState.fSrcBlend) && - (kZero_BlendCoeff == fCurrDrawState.fDstBlend)) { - return true; - } - - // If we have vertex color without alpha then we can't force blend off - if ((fGeometrySrc.fVertexLayout & kColor_VertexLayoutBit) || - 0xff != GrColorUnpackA(fCurrDrawState.fColor)) { - return false; - } - - // If the src coef will always be 1... - if (kSA_BlendCoeff != fCurrDrawState.fSrcBlend && - kOne_BlendCoeff != fCurrDrawState.fSrcBlend) { - return false; - } - - // ...and the dst coef is always 0... - if (kISA_BlendCoeff != fCurrDrawState.fDstBlend && - kZero_BlendCoeff != fCurrDrawState.fDstBlend) { - return false; - } - - // ...and there isn't a texture stage with an alpha channel... - for (int s = 0; s < fCurrDrawState.fFirstCoverageStage; ++s) { - if (this->isStageEnabled(s)) { - GrAssert(NULL != fCurrDrawState.fTextures[s]); - - GrPixelConfig config = fCurrDrawState.fTextures[s]->config(); - - if (!GrPixelConfigIsOpaque(config)) { - return false; - } - } - } - - // ...and there isn't an interesting color filter... - // TODO: Consider being more aggressive with regards to disabling - // blending when a color filter is used. - if (SkXfermode::kDst_Mode != fCurrDrawState.fColorFilterXfermode) { - return false; - } - - // ...then we disable blend. - return true; -} - -/////////////////////////////////////////////////////////////////////////////// -void GrDrawTarget::setEdgeAAData(const Edge* edges, int numEdges) { - GrAssert(numEdges <= kMaxEdges); - memcpy(fCurrDrawState.fEdgeAAEdges, edges, numEdges * sizeof(Edge)); - fCurrDrawState.fEdgeAANumEdges = numEdges; -} - - -/////////////////////////////////////////////////////////////////////////////// -void GrDrawTarget::drawRect(const GrRect& rect, - const GrMatrix* matrix, - StageBitfield stageEnableBitfield, - const GrRect* srcRects[], - const GrMatrix* srcMatrices[]) { - GrVertexLayout layout = GetRectVertexLayout(stageEnableBitfield, srcRects); - - AutoReleaseGeometry geo(this, layout, 4, 0); - - SetRectVertices(rect, matrix, srcRects, - srcMatrices, layout, geo.vertices()); - - drawNonIndexed(kTriangleFan_PrimitiveType, 0, 4); -} - -GrVertexLayout GrDrawTarget::GetRectVertexLayout(StageBitfield stageEnableBitfield, - const GrRect* srcRects[]) { - GrVertexLayout layout = 0; - - for (int i = 0; i < kNumStages; ++i) { - int numTC = 0; - if (stageEnableBitfield & (1 << i)) { - if (NULL != srcRects && NULL != srcRects[i]) { - layout |= StageTexCoordVertexLayoutBit(i, numTC); - ++numTC; - } else { - layout |= StagePosAsTexCoordVertexLayoutBit(i); - } - } - } - return layout; -} -void GrDrawTarget::SetRectVertices(const GrRect& rect, - const GrMatrix* matrix, - const GrRect* srcRects[], - const GrMatrix* srcMatrices[], - GrVertexLayout layout, - void* vertices) { -#if GR_DEBUG - // check that the layout and srcRects agree - for (int i = 0; i < kNumStages; ++i) { - if (VertexTexCoordsForStage(i, layout) >= 0) { - GR_DEBUGASSERT(NULL != srcRects && NULL != srcRects[i]); - } else { - GR_DEBUGASSERT(NULL == srcRects || NULL == srcRects[i]); - } - } -#endif - - int stageOffsets[kNumStages]; - int colorOffset; - int vsize = VertexSizeAndOffsetsByStage(layout, stageOffsets, &colorOffset); - GrAssert(-1 == colorOffset); - - GrTCast<GrPoint*>(vertices)->setRectFan(rect.fLeft, rect.fTop, - rect.fRight, rect.fBottom, - vsize); - if (NULL != matrix) { - matrix->mapPointsWithStride(GrTCast<GrPoint*>(vertices), vsize, 4); - } - - for (int i = 0; i < kNumStages; ++i) { - if (stageOffsets[i] > 0) { - GrPoint* coords = GrTCast<GrPoint*>(GrTCast<intptr_t>(vertices) + - stageOffsets[i]); - coords->setRectFan(srcRects[i]->fLeft, srcRects[i]->fTop, - srcRects[i]->fRight, srcRects[i]->fBottom, - vsize); - if (NULL != srcMatrices && NULL != srcMatrices[i]) { - srcMatrices[i]->mapPointsWithStride(coords, vsize, 4); - } - } - } -} - -/////////////////////////////////////////////////////////////////////////////// -GrDrawTarget::AutoStateRestore::AutoStateRestore() { - fDrawTarget = NULL; -} - -GrDrawTarget::AutoStateRestore::AutoStateRestore(GrDrawTarget* target) { - fDrawTarget = target; - if (NULL != fDrawTarget) { - fDrawTarget->saveCurrentDrawState(&fDrawState); - } -} - -GrDrawTarget::AutoStateRestore::~AutoStateRestore() { - if (NULL != fDrawTarget) { - fDrawTarget->restoreDrawState(fDrawState); - } -} - -void GrDrawTarget::AutoStateRestore::set(GrDrawTarget* target) { - if (target != fDrawTarget) { - if (NULL != fDrawTarget) { - fDrawTarget->restoreDrawState(fDrawState); - } - if (NULL != target) { - fDrawTarget->saveCurrentDrawState(&fDrawState); - } - fDrawTarget = target; - } -} |