| OLD | NEW |
| 1 /* | 1 /* |
| 2 * Copyright 2012 Google Inc. | 2 * Copyright 2012 Google Inc. |
| 3 * | 3 * |
| 4 * Use of this source code is governed by a BSD-style license that can be | 4 * Use of this source code is governed by a BSD-style license that can be |
| 5 * found in the LICENSE file. | 5 * found in the LICENSE file. |
| 6 */ | 6 */ |
| 7 | 7 |
| 8 #include "GrDrawState.h" | 8 #include "GrDrawState.h" |
| 9 | 9 |
| 10 #include "GrBlend.h" | 10 #include "GrBlend.h" |
| (...skipping 10 matching lines...) Expand all Loading... |
| 21 } | 21 } |
| 22 | 22 |
| 23 if (this->getRenderTarget() != that.getRenderTarget() || | 23 if (this->getRenderTarget() != that.getRenderTarget() || |
| 24 this->fColorStages.count() != that.fColorStages.count() || | 24 this->fColorStages.count() != that.fColorStages.count() || |
| 25 this->fCoverageStages.count() != that.fCoverageStages.count() || | 25 this->fCoverageStages.count() != that.fCoverageStages.count() || |
| 26 !this->fViewMatrix.cheapEqualTo(that.fViewMatrix) || | 26 !this->fViewMatrix.cheapEqualTo(that.fViewMatrix) || |
| 27 this->fSrcBlend != that.fSrcBlend || | 27 this->fSrcBlend != that.fSrcBlend || |
| 28 this->fDstBlend != that.fDstBlend || | 28 this->fDstBlend != that.fDstBlend || |
| 29 this->fBlendConstant != that.fBlendConstant || | 29 this->fBlendConstant != that.fBlendConstant || |
| 30 this->fFlagBits != that.fFlagBits || | 30 this->fFlagBits != that.fFlagBits || |
| 31 this->fVACount != that.fVACount || | |
| 32 this->fVAStride != that.fVAStride || | |
| 33 memcmp(this->fVAPtr, that.fVAPtr, this->fVACount * sizeof(GrVertexAttrib
)) || | |
| 34 this->fStencilSettings != that.fStencilSettings || | 31 this->fStencilSettings != that.fStencilSettings || |
| 35 this->fDrawFace != that.fDrawFace) { | 32 this->fDrawFace != that.fDrawFace) { |
| 36 return false; | 33 return false; |
| 37 } | 34 } |
| 38 | 35 |
| 39 bool usingVertexCoverage = this->hasCoverageVertexAttribute(); | 36 bool usingVertexCoverage = this->hasCoverageVertexAttribute(); |
| 40 if (!usingVertexCoverage && this->fCoverage != that.fCoverage) { | 37 if (!usingVertexCoverage && this->fCoverage != that.fCoverage) { |
| 41 return false; | 38 return false; |
| 42 } | 39 } |
| 43 | 40 |
| (...skipping 14 matching lines...) Expand all Loading... |
| 58 return false; | 55 return false; |
| 59 } | 56 } |
| 60 } | 57 } |
| 61 for (int i = 0; i < this->numCoverageStages(); i++) { | 58 for (int i = 0; i < this->numCoverageStages(); i++) { |
| 62 if (!GrFragmentStage::AreCompatible(this->getCoverageStage(i), that.getC
overageStage(i), | 59 if (!GrFragmentStage::AreCompatible(this->getCoverageStage(i), that.getC
overageStage(i), |
| 63 explicitLocalCoords)) { | 60 explicitLocalCoords)) { |
| 64 return false; | 61 return false; |
| 65 } | 62 } |
| 66 } | 63 } |
| 67 | 64 |
| 68 SkASSERT(0 == memcmp(this->fFixedFunctionVertexAttribIndices, | |
| 69 that.fFixedFunctionVertexAttribIndices, | |
| 70 sizeof(this->fFixedFunctionVertexAttribIndices))); | |
| 71 | |
| 72 return true; | 65 return true; |
| 73 } | 66 } |
| 74 | 67 |
| 75 //////////////////////////////////////////////////////////////////////////////s | 68 //////////////////////////////////////////////////////////////////////////////s |
| 76 | 69 |
| 77 GrDrawState::GrDrawState(const GrDrawState& state, const SkMatrix& preConcatMatr
ix) { | 70 GrDrawState::GrDrawState(const GrDrawState& state, const SkMatrix& preConcatMatr
ix) { |
| 78 SkDEBUGCODE(fBlockEffectRemovalCnt = 0;) | 71 SkDEBUGCODE(fBlockEffectRemovalCnt = 0;) |
| 79 *this = state; | 72 *this = state; |
| 80 if (!preConcatMatrix.isIdentity()) { | 73 if (!preConcatMatrix.isIdentity()) { |
| 81 for (int i = 0; i < this->numColorStages(); ++i) { | 74 for (int i = 0; i < this->numColorStages(); ++i) { |
| 82 fColorStages[i].localCoordChange(preConcatMatrix); | 75 fColorStages[i].localCoordChange(preConcatMatrix); |
| 83 } | 76 } |
| 84 for (int i = 0; i < this->numCoverageStages(); ++i) { | 77 for (int i = 0; i < this->numCoverageStages(); ++i) { |
| 85 fCoverageStages[i].localCoordChange(preConcatMatrix); | 78 fCoverageStages[i].localCoordChange(preConcatMatrix); |
| 86 } | 79 } |
| 87 } | 80 } |
| 88 } | 81 } |
| 89 | 82 |
| 90 GrDrawState& GrDrawState::operator=(const GrDrawState& that) { | 83 GrDrawState& GrDrawState::operator=(const GrDrawState& that) { |
| 91 fRenderTarget.reset(SkSafeRef(that.fRenderTarget.get())); | 84 fRenderTarget.reset(SkSafeRef(that.fRenderTarget.get())); |
| 92 fColor = that.fColor; | 85 fColor = that.fColor; |
| 93 fViewMatrix = that.fViewMatrix; | 86 fViewMatrix = that.fViewMatrix; |
| 94 fSrcBlend = that.fSrcBlend; | 87 fSrcBlend = that.fSrcBlend; |
| 95 fDstBlend = that.fDstBlend; | 88 fDstBlend = that.fDstBlend; |
| 96 fBlendConstant = that.fBlendConstant; | 89 fBlendConstant = that.fBlendConstant; |
| 97 fFlagBits = that.fFlagBits; | 90 fFlagBits = that.fFlagBits; |
| 98 fVACount = that.fVACount; | |
| 99 fVAPtr = that.fVAPtr; | |
| 100 fVAStride = that.fVAStride; | |
| 101 fStencilSettings = that.fStencilSettings; | 91 fStencilSettings = that.fStencilSettings; |
| 102 fCoverage = that.fCoverage; | 92 fCoverage = that.fCoverage; |
| 103 fDrawFace = that.fDrawFace; | 93 fDrawFace = that.fDrawFace; |
| 104 fGeometryProcessor.reset(SkSafeRef(that.fGeometryProcessor.get())); | 94 fGeometryProcessor.reset(SkSafeRef(that.fGeometryProcessor.get())); |
| 105 fColorStages = that.fColorStages; | 95 fColorStages = that.fColorStages; |
| 106 fCoverageStages = that.fCoverageStages; | 96 fCoverageStages = that.fCoverageStages; |
| 107 | 97 |
| 108 fHints = that.fHints; | 98 fHints = that.fHints; |
| 109 | 99 |
| 110 fColorProcInfoValid = that.fColorProcInfoValid; | 100 fColorProcInfoValid = that.fColorProcInfoValid; |
| 111 fCoverageProcInfoValid = that.fCoverageProcInfoValid; | 101 fCoverageProcInfoValid = that.fCoverageProcInfoValid; |
| 112 if (fColorProcInfoValid) { | 102 if (fColorProcInfoValid) { |
| 113 fColorProcInfo = that.fColorProcInfo; | 103 fColorProcInfo = that.fColorProcInfo; |
| 114 } | 104 } |
| 115 if (fCoverageProcInfoValid) { | 105 if (fCoverageProcInfoValid) { |
| 116 fCoverageProcInfo = that.fCoverageProcInfo; | 106 fCoverageProcInfo = that.fCoverageProcInfo; |
| 117 } | 107 } |
| 118 | |
| 119 memcpy(fFixedFunctionVertexAttribIndices, | |
| 120 that.fFixedFunctionVertexAttribIndices, | |
| 121 sizeof(fFixedFunctionVertexAttribIndices)); | |
| 122 return *this; | 108 return *this; |
| 123 } | 109 } |
| 124 | 110 |
| 125 void GrDrawState::onReset(const SkMatrix* initialViewMatrix) { | 111 void GrDrawState::onReset(const SkMatrix* initialViewMatrix) { |
| 126 SkASSERT(0 == fBlockEffectRemovalCnt || 0 == this->numTotalStages()); | 112 SkASSERT(0 == fBlockEffectRemovalCnt || 0 == this->numTotalStages()); |
| 127 fRenderTarget.reset(NULL); | 113 fRenderTarget.reset(NULL); |
| 128 | 114 |
| 129 fGeometryProcessor.reset(NULL); | 115 fGeometryProcessor.reset(NULL); |
| 130 fColorStages.reset(); | 116 fColorStages.reset(); |
| 131 fCoverageStages.reset(); | 117 fCoverageStages.reset(); |
| 132 | 118 |
| 133 | |
| 134 this->setDefaultVertexAttribs(); | |
| 135 | |
| 136 fColor = 0xffffffff; | 119 fColor = 0xffffffff; |
| 137 if (NULL == initialViewMatrix) { | 120 if (NULL == initialViewMatrix) { |
| 138 fViewMatrix.reset(); | 121 fViewMatrix.reset(); |
| 139 } else { | 122 } else { |
| 140 fViewMatrix = *initialViewMatrix; | 123 fViewMatrix = *initialViewMatrix; |
| 141 } | 124 } |
| 142 fSrcBlend = kOne_GrBlendCoeff; | 125 fSrcBlend = kOne_GrBlendCoeff; |
| 143 fDstBlend = kZero_GrBlendCoeff; | 126 fDstBlend = kZero_GrBlendCoeff; |
| 144 fBlendConstant = 0x0; | 127 fBlendConstant = 0x0; |
| 145 fFlagBits = 0x0; | 128 fFlagBits = 0x0; |
| (...skipping 59 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 205 this->setState(GrDrawState::kHWAntialias_StateBit, paint.isAntiAlias()); | 188 this->setState(GrDrawState::kHWAntialias_StateBit, paint.isAntiAlias()); |
| 206 | 189 |
| 207 this->setBlendFunc(paint.getSrcBlendCoeff(), paint.getDstBlendCoeff()); | 190 this->setBlendFunc(paint.getSrcBlendCoeff(), paint.getDstBlendCoeff()); |
| 208 this->setCoverage(0xFF); | 191 this->setCoverage(0xFF); |
| 209 fColorProcInfoValid = false; | 192 fColorProcInfoValid = false; |
| 210 fCoverageProcInfoValid = false; | 193 fCoverageProcInfoValid = false; |
| 211 } | 194 } |
| 212 | 195 |
| 213 //////////////////////////////////////////////////////////////////////////////// | 196 //////////////////////////////////////////////////////////////////////////////// |
| 214 | 197 |
| 215 bool GrDrawState::validateVertexAttribs() const { | |
| 216 // check consistency of effects and attributes | |
| 217 GrSLType slTypes[kMaxVertexAttribCnt]; | |
| 218 for (int i = 0; i < kMaxVertexAttribCnt; ++i) { | |
| 219 slTypes[i] = static_cast<GrSLType>(-1); | |
| 220 } | |
| 221 | |
| 222 if (this->hasGeometryProcessor()) { | |
| 223 const GrGeometryProcessor* gp = this->getGeometryProcessor(); | |
| 224 // make sure that any attribute indices have the correct binding type, t
hat the attrib | |
| 225 // type and effect's shader lang type are compatible, and that attribute
s shared by | |
| 226 // multiple effects use the same shader lang type. | |
| 227 const GrGeometryProcessor::VertexAttribArray& s = gp->getVertexAttribs()
; | |
| 228 | |
| 229 int effectIndex = 0; | |
| 230 for (int index = 0; index < fVACount; index++) { | |
| 231 if (kGeometryProcessor_GrVertexAttribBinding != fVAPtr[index].fBindi
ng) { | |
| 232 // we only care about effect bindings | |
| 233 continue; | |
| 234 } | |
| 235 SkASSERT(effectIndex < s.count()); | |
| 236 GrSLType effectSLType = s[effectIndex].getType(); | |
| 237 GrVertexAttribType attribType = fVAPtr[index].fType; | |
| 238 int slVecCount = GrSLTypeVectorCount(effectSLType); | |
| 239 int attribVecCount = GrVertexAttribTypeVectorCount(attribType); | |
| 240 if (slVecCount != attribVecCount || | |
| 241 (static_cast<GrSLType>(-1) != slTypes[index] && slTypes[index] !
= effectSLType)) { | |
| 242 return false; | |
| 243 } | |
| 244 slTypes[index] = effectSLType; | |
| 245 effectIndex++; | |
| 246 } | |
| 247 // Make sure all attributes are consumed and we were able to find everyt
hing | |
| 248 SkASSERT(s.count() == effectIndex); | |
| 249 } | |
| 250 | |
| 251 return true; | |
| 252 } | |
| 253 | |
| 254 //////////////////////////////////////////////////////////////////////////////// | |
| 255 | |
| 256 static void validate_vertex_attribs(const GrVertexAttrib* attribs, int count, si
ze_t stride) { | |
| 257 // this works as long as we're 4 byte-aligned | |
| 258 #ifdef SK_DEBUG | |
| 259 uint32_t overlapCheck = 0; | |
| 260 SkASSERT(count <= GrDrawState::kMaxVertexAttribCnt); | |
| 261 for (int index = 0; index < count; ++index) { | |
| 262 size_t attribSize = GrVertexAttribTypeSize(attribs[index].fType); | |
| 263 size_t attribOffset = attribs[index].fOffset; | |
| 264 SkASSERT(attribOffset + attribSize <= stride); | |
| 265 size_t dwordCount = attribSize >> 2; | |
| 266 uint32_t mask = (1 << dwordCount)-1; | |
| 267 size_t offsetShift = attribOffset >> 2; | |
| 268 SkASSERT(!(overlapCheck & (mask << offsetShift))); | |
| 269 overlapCheck |= (mask << offsetShift); | |
| 270 } | |
| 271 #endif | |
| 272 } | |
| 273 | |
| 274 //////////////////////////////////////////////////////////////////////////////// | |
| 275 | |
| 276 void GrDrawState::internalSetVertexAttribs(const GrVertexAttrib* attribs, int co
unt, | |
| 277 size_t stride) { | |
| 278 SkASSERT(count <= kMaxVertexAttribCnt); | |
| 279 | |
| 280 fVAPtr = attribs; | |
| 281 fVACount = count; | |
| 282 fVAStride = stride; | |
| 283 validate_vertex_attribs(fVAPtr, fVACount, fVAStride); | |
| 284 | |
| 285 // Set all the indices to -1 | |
| 286 memset(fFixedFunctionVertexAttribIndices, | |
| 287 0xff, | |
| 288 sizeof(fFixedFunctionVertexAttribIndices)); | |
| 289 #ifdef SK_DEBUG | |
| 290 uint32_t overlapCheck = 0; | |
| 291 #endif | |
| 292 for (int i = 0; i < count; ++i) { | |
| 293 if (attribs[i].fBinding < kGrFixedFunctionVertexAttribBindingCnt) { | |
| 294 // The fixed function attribs can only be specified once | |
| 295 SkASSERT(-1 == fFixedFunctionVertexAttribIndices[attribs[i].fBinding
]); | |
| 296 SkASSERT(GrFixedFunctionVertexAttribVectorCount(attribs[i].fBinding)
== | |
| 297 GrVertexAttribTypeVectorCount(attribs[i].fType)); | |
| 298 fFixedFunctionVertexAttribIndices[attribs[i].fBinding] = i; | |
| 299 } | |
| 300 #ifdef SK_DEBUG | |
| 301 size_t dwordCount = GrVertexAttribTypeSize(attribs[i].fType) >> 2; | |
| 302 uint32_t mask = (1 << dwordCount)-1; | |
| 303 size_t offsetShift = attribs[i].fOffset >> 2; | |
| 304 SkASSERT(!(overlapCheck & (mask << offsetShift))); | |
| 305 overlapCheck |= (mask << offsetShift); | |
| 306 #endif | |
| 307 } | |
| 308 fColorProcInfoValid = false; | |
| 309 fCoverageProcInfoValid = false; | |
| 310 // Positions must be specified. | |
| 311 SkASSERT(-1 != fFixedFunctionVertexAttribIndices[kPosition_GrVertexAttribBin
ding]); | |
| 312 } | |
| 313 | |
| 314 //////////////////////////////////////////////////////////////////////////////// | |
| 315 | |
| 316 void GrDrawState::setDefaultVertexAttribs() { | |
| 317 static const GrVertexAttrib kPositionAttrib = | |
| 318 {kVec2f_GrVertexAttribType, 0, kPosition_GrVertexAttribBinding}; | |
| 319 | |
| 320 fVAPtr = &kPositionAttrib; | |
| 321 fVACount = 1; | |
| 322 fVAStride = GrVertexAttribTypeSize(kVec2f_GrVertexAttribType); | |
| 323 | |
| 324 // set all the fixed function indices to -1 except position. | |
| 325 memset(fFixedFunctionVertexAttribIndices, | |
| 326 0xff, | |
| 327 sizeof(fFixedFunctionVertexAttribIndices)); | |
| 328 fFixedFunctionVertexAttribIndices[kPosition_GrVertexAttribBinding] = 0; | |
| 329 fColorProcInfoValid = false; | |
| 330 fCoverageProcInfoValid = false; | |
| 331 } | |
| 332 | |
| 333 //////////////////////////////////////////////////////////////////////////////// | |
| 334 | |
| 335 bool GrDrawState::couldApplyCoverage(const GrDrawTargetCaps& caps) const { | 198 bool GrDrawState::couldApplyCoverage(const GrDrawTargetCaps& caps) const { |
| 336 if (caps.dualSourceBlendingSupport()) { | 199 if (caps.dualSourceBlendingSupport()) { |
| 337 return true; | 200 return true; |
| 338 } | 201 } |
| 339 // we can correctly apply coverage if a) we have dual source blending | 202 // we can correctly apply coverage if a) we have dual source blending |
| 340 // or b) one of our blend optimizations applies | 203 // or b) one of our blend optimizations applies |
| 341 // or c) the src, dst blend coeffs are 1,0 and we will read Dst Color | 204 // or c) the src, dst blend coeffs are 1,0 and we will read Dst Color |
| 342 GrBlendCoeff srcCoeff; | 205 GrBlendCoeff srcCoeff; |
| 343 GrBlendCoeff dstCoeff; | 206 GrBlendCoeff dstCoeff; |
| 344 BlendOpt opt = this->getBlendOpt(true, &srcCoeff, &dstCoeff); | 207 BlendOpt opt = this->getBlendOpt(true, &srcCoeff, &dstCoeff); |
| 345 return GrDrawState::kNone_BlendOpt != opt || | 208 return GrDrawState::kNone_BlendOpt != opt || |
| 346 (this->willEffectReadDstColor() && | 209 (this->willEffectReadDstColor() && |
| 347 kOne_GrBlendCoeff == srcCoeff && kZero_GrBlendCoeff == dstCoeff); | 210 kOne_GrBlendCoeff == srcCoeff && kZero_GrBlendCoeff == dstCoeff); |
| 348 } | 211 } |
| 349 | 212 |
| 350 bool GrDrawState::hasSolidCoverage() const { | 213 bool GrDrawState::hasSolidCoverage() const { |
| 351 // If we're drawing coverage directly then coverage is effectively treated a
s color. | 214 // If we're drawing coverage directly then coverage is effectively treated a
s color. |
| 352 if (this->isCoverageDrawing()) { | 215 if (this->isCoverageDrawing()) { |
| 353 return true; | 216 return true; |
| 354 } | 217 } |
| 355 | 218 |
| 356 if (this->numCoverageStages() > 0) { | 219 if (this->numCoverageStages() > 0) { |
| 357 return false; | 220 return false; |
| 358 } | 221 } |
| 359 | 222 |
| 360 this->calcCoverageInvariantOutput(); | 223 this->calcCoverageInvariantOutput(); |
| 361 return fCoverageProcInfo.isSolidWhite(); | 224 return fCoverageProcInfo.isSolidWhite(); |
| 362 } | 225 } |
| 363 | 226 |
| 364 ////////////////////////////////////////////////////////////////////////////// | |
| 365 | |
| 366 GrDrawState::AutoVertexAttribRestore::AutoVertexAttribRestore(GrDrawState* drawS
tate) { | |
| 367 SkASSERT(drawState); | |
| 368 fDrawState = drawState; | |
| 369 fVAPtr = drawState->fVAPtr; | |
| 370 fVACount = drawState->fVACount; | |
| 371 fVAStride = drawState->fVAStride; | |
| 372 fDrawState->setDefaultVertexAttribs(); | |
| 373 } | |
| 374 | |
| 375 //////////////////////////////////////////////////////////////////////////////s | 227 //////////////////////////////////////////////////////////////////////////////s |
| 376 | 228 |
| 377 bool GrDrawState::willEffectReadDstColor() const { | 229 bool GrDrawState::willEffectReadDstColor() const { |
| 378 if (!this->isColorWriteDisabled()) { | 230 if (!this->isColorWriteDisabled()) { |
| 379 this->calcColorInvariantOutput(); | 231 this->calcColorInvariantOutput(); |
| 380 if (fColorProcInfo.readsDst()) { | 232 if (fColorProcInfo.readsDst()) { |
| 381 return true; | 233 return true; |
| 382 } | 234 } |
| 383 } | 235 } |
| 384 this->calcCoverageInvariantOutput(); | 236 this->calcCoverageInvariantOutput(); |
| (...skipping 308 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 693 } else { | 545 } else { |
| 694 flags = kRGBA_GrColorComponentFlags; | 546 flags = kRGBA_GrColorComponentFlags; |
| 695 color = this->getCoverageColor(); | 547 color = this->getCoverageColor(); |
| 696 } | 548 } |
| 697 fCoverageProcInfo.calcWithInitialValues(fCoverageStages.begin(), this->n
umCoverageStages(), | 549 fCoverageProcInfo.calcWithInitialValues(fCoverageStages.begin(), this->n
umCoverageStages(), |
| 698 color, flags, true, fGeometryPro
cessor.get()); | 550 color, flags, true, fGeometryPro
cessor.get()); |
| 699 fCoverageProcInfoValid = true; | 551 fCoverageProcInfoValid = true; |
| 700 } | 552 } |
| 701 } | 553 } |
| 702 | 554 |
| OLD | NEW |