OLD | NEW |
1 | 1 |
2 /* | 2 /* |
3 * Copyright 2011 Google Inc. | 3 * Copyright 2011 Google Inc. |
4 * | 4 * |
5 * Use of this source code is governed by a BSD-style license that can be | 5 * Use of this source code is governed by a BSD-style license that can be |
6 * found in the LICENSE file. | 6 * found in the LICENSE file. |
7 */ | 7 */ |
8 | 8 |
9 | 9 |
10 #include "GrContext.h" | 10 #include "GrContext.h" |
(...skipping 1329 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1340 if ((kUnpremul_PixelOpsFlag & flags) || !fGpu->canWriteTexturePixels(texture
, config)) { | 1340 if ((kUnpremul_PixelOpsFlag & flags) || !fGpu->canWriteTexturePixels(texture
, config)) { |
1341 if (texture->asRenderTarget()) { | 1341 if (texture->asRenderTarget()) { |
1342 return this->writeRenderTargetPixels(texture->asRenderTarget(), | 1342 return this->writeRenderTargetPixels(texture->asRenderTarget(), |
1343 left, top, width, height, | 1343 left, top, width, height, |
1344 config, buffer, rowBytes, flags
); | 1344 config, buffer, rowBytes, flags
); |
1345 } else { | 1345 } else { |
1346 return false; | 1346 return false; |
1347 } | 1347 } |
1348 } | 1348 } |
1349 | 1349 |
1350 if (!(kDontFlush_PixelOpsFlag & flags)) { | 1350 if (!(kDontFlush_PixelOpsFlag & flags) && texture->hasPendingIO()) { |
1351 this->flush(); | 1351 this->flush(); |
1352 } | 1352 } |
1353 | 1353 |
1354 return fGpu->writeTexturePixels(texture, left, top, width, height, | 1354 return fGpu->writeTexturePixels(texture, left, top, width, height, |
1355 config, buffer, rowBytes); | 1355 config, buffer, rowBytes); |
1356 } | 1356 } |
1357 | 1357 |
1358 bool GrContext::readTexturePixels(GrTexture* texture, | 1358 bool GrContext::readTexturePixels(GrTexture* texture, |
1359 int left, int top, int width, int height, | 1359 int left, int top, int width, int height, |
1360 GrPixelConfig config, void* buffer, size_t row
Bytes, | 1360 GrPixelConfig config, void* buffer, size_t row
Bytes, |
(...skipping 50 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1411 uint32_t flags) { | 1411 uint32_t flags) { |
1412 ASSERT_OWNED_RESOURCE(target); | 1412 ASSERT_OWNED_RESOURCE(target); |
1413 | 1413 |
1414 if (NULL == target) { | 1414 if (NULL == target) { |
1415 target = fRenderTarget.get(); | 1415 target = fRenderTarget.get(); |
1416 if (NULL == target) { | 1416 if (NULL == target) { |
1417 return false; | 1417 return false; |
1418 } | 1418 } |
1419 } | 1419 } |
1420 | 1420 |
1421 if (!(kDontFlush_PixelOpsFlag & flags)) { | 1421 if (!(kDontFlush_PixelOpsFlag & flags) && target->hasPendingWrite()) { |
1422 this->flush(); | 1422 this->flush(); |
1423 } | 1423 } |
1424 | 1424 |
1425 // Determine which conversions have to be applied: flipY, swapRAnd, and/or u
npremul. | 1425 // Determine which conversions have to be applied: flipY, swapRAnd, and/or u
npremul. |
1426 | 1426 |
1427 // If fGpu->readPixels would incur a y-flip cost then we will read the pixel
s upside down. We'll | 1427 // If fGpu->readPixels would incur a y-flip cost then we will read the pixel
s upside down. We'll |
1428 // either do the flipY by drawing into a scratch with a matrix or on the cpu
after the read. | 1428 // either do the flipY by drawing into a scratch with a matrix or on the cpu
after the read. |
1429 bool flipY = fGpu->readPixelsWillPayForYFlip(target, left, top, | 1429 bool flipY = fGpu->readPixelsWillPayForYFlip(target, left, top, |
1430 width, height, dstConfig, | 1430 width, height, dstConfig, |
1431 rowBytes); | 1431 rowBytes); |
(...skipping 139 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1571 } | 1571 } |
1572 target->discard(renderTarget); | 1572 target->discard(renderTarget); |
1573 } | 1573 } |
1574 | 1574 |
1575 void GrContext::copyTexture(GrTexture* src, GrRenderTarget* dst, const SkIPoint*
topLeft) { | 1575 void GrContext::copyTexture(GrTexture* src, GrRenderTarget* dst, const SkIPoint*
topLeft) { |
1576 if (NULL == src || NULL == dst) { | 1576 if (NULL == src || NULL == dst) { |
1577 return; | 1577 return; |
1578 } | 1578 } |
1579 ASSERT_OWNED_RESOURCE(src); | 1579 ASSERT_OWNED_RESOURCE(src); |
1580 | 1580 |
1581 // Writes pending to the source texture are not tracked, so a flush | 1581 |
1582 // is required to ensure that the copy captures the most recent contents | 1582 if (src->hasPendingWrite() || dst->hasPendingIO()) { |
1583 // of the source texture. See similar behavior in | 1583 this->flush(); |
1584 // GrContext::resolveRenderTarget. | 1584 } |
1585 this->flush(); | |
1586 | 1585 |
1587 GrDrawTarget::AutoStateRestore asr(fGpu, GrDrawTarget::kReset_ASRInit); | 1586 GrDrawTarget::AutoStateRestore asr(fGpu, GrDrawTarget::kReset_ASRInit); |
1588 GrDrawState* drawState = fGpu->drawState(); | 1587 GrDrawState* drawState = fGpu->drawState(); |
1589 drawState->setRenderTarget(dst); | 1588 drawState->setRenderTarget(dst); |
1590 SkMatrix sampleM; | 1589 SkMatrix sampleM; |
1591 sampleM.setIDiv(src->width(), src->height()); | 1590 sampleM.setIDiv(src->width(), src->height()); |
1592 SkIRect srcRect = SkIRect::MakeWH(dst->width(), dst->height()); | 1591 SkIRect srcRect = SkIRect::MakeWH(dst->width(), dst->height()); |
1593 if (topLeft) { | 1592 if (topLeft) { |
1594 srcRect.offset(*topLeft); | 1593 srcRect.offset(*topLeft); |
1595 } | 1594 } |
(...skipping 112 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1708 textureMatrix)); | 1707 textureMatrix)); |
1709 } | 1708 } |
1710 | 1709 |
1711 if (!this->writeTexturePixels(texture, | 1710 if (!this->writeTexturePixels(texture, |
1712 0, 0, width, height, | 1711 0, 0, width, height, |
1713 writeConfig, buffer, rowBytes, | 1712 writeConfig, buffer, rowBytes, |
1714 flags & ~kUnpremul_PixelOpsFlag)) { | 1713 flags & ~kUnpremul_PixelOpsFlag)) { |
1715 return false; | 1714 return false; |
1716 } | 1715 } |
1717 | 1716 |
| 1717 // TODO: Usually this could go to fDrawBuffer but currently |
1718 // writeRenderTargetPixels can be called in the midst of drawing another | 1718 // writeRenderTargetPixels can be called in the midst of drawing another |
1719 // object (e.g., when uploading a SW path rendering to the gpu while | 1719 // object (e.g., when uploading a SW path rendering to the gpu while |
1720 // drawing a rect) so preserve the current geometry. | 1720 // drawing a rect). So we always draw directly to GrGpu and preserve the cur
rent geometry. |
| 1721 // But that means we also have to flush the draw buffer if there is a pendin
g IO operation to |
| 1722 // the render target. |
| 1723 if (!(kDontFlush_PixelOpsFlag & flags) && target->hasPendingIO()) { |
| 1724 this->flush(); |
| 1725 } |
1721 SkMatrix matrix; | 1726 SkMatrix matrix; |
1722 matrix.setTranslate(SkIntToScalar(left), SkIntToScalar(top)); | 1727 matrix.setTranslate(SkIntToScalar(left), SkIntToScalar(top)); |
1723 GrDrawTarget::AutoGeometryAndStatePush agasp(fGpu, GrDrawTarget::kReset_ASRI
nit, &matrix); | 1728 GrDrawTarget::AutoGeometryAndStatePush agasp(fGpu, GrDrawTarget::kReset_ASRI
nit, &matrix); |
1724 GrDrawState* drawState = fGpu->drawState(); | 1729 GrDrawState* drawState = fGpu->drawState(); |
1725 SkASSERT(effect); | 1730 SkASSERT(effect); |
1726 drawState->addColorEffect(effect); | 1731 drawState->addColorEffect(effect); |
1727 | 1732 |
1728 drawState->setRenderTarget(target); | 1733 drawState->setRenderTarget(target); |
1729 | 1734 |
1730 fGpu->drawSimpleRect(SkRect::MakeWH(SkIntToScalar(width), SkIntToScalar(heig
ht))); | 1735 fGpu->drawSimpleRect(SkRect::MakeWH(SkIntToScalar(width), SkIntToScalar(heig
ht))); |
(...skipping 210 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1941 fResourceCache->printStats(); | 1946 fResourceCache->printStats(); |
1942 } | 1947 } |
1943 #endif | 1948 #endif |
1944 | 1949 |
1945 #if GR_GPU_STATS | 1950 #if GR_GPU_STATS |
1946 const GrContext::GPUStats* GrContext::gpuStats() const { | 1951 const GrContext::GPUStats* GrContext::gpuStats() const { |
1947 return fGpu->gpuStats(); | 1952 return fGpu->gpuStats(); |
1948 } | 1953 } |
1949 #endif | 1954 #endif |
1950 | 1955 |
OLD | NEW |