blob: 9bf91fc59527b377625f9894c579813fb64ccfa7 [file] [log] [blame]
junov@google.comf93e7172011-03-31 21:26:24 +00001/*
epoger@google.comec3ed6a2011-07-28 14:26:00 +00002 * Copyright 2011 Google Inc.
3 *
4 * Use of this source code is governed by a BSD-style license that can be
5 * found in the LICENSE file.
junov@google.comf93e7172011-03-31 21:26:24 +00006 */
joshualitt23e280d2014-09-18 12:26:38 -07007
junov@google.comf93e7172011-03-31 21:26:24 +00008#include "GrGLProgram.h"
9
tomhudson@google.comd8f856c2012-05-10 12:13:36 +000010#include "GrAllocator.h"
joshualittb0a8a372014-09-23 09:50:21 -070011#include "GrProcessor.h"
bsalomon@google.com77af6802013-10-02 13:04:56 +000012#include "GrCoordTransform.h"
joshualitta5305a12014-10-10 17:47:00 -070013#include "GrGLGeometryProcessor.h"
joshualittb0a8a372014-09-23 09:50:21 -070014#include "GrGLProcessor.h"
egdanielc2304142014-12-11 13:15:13 -080015#include "GrGLXferProcessor.h"
bsalomon@google.com34cccde2013-01-04 18:34:30 +000016#include "GrGpuGL.h"
kkinnunenec56e452014-08-25 22:21:16 -070017#include "GrGLPathRendering.h"
bsalomon@google.com4fa66942011-09-20 19:06:12 +000018#include "GrGLShaderVar.h"
bsalomon@google.com018f1792013-04-18 19:36:09 +000019#include "GrGLSL.h"
egdaniel170f90b2014-09-16 12:54:40 -070020#include "GrOptDrawState.h"
egdanielc2304142014-12-11 13:15:13 -080021#include "GrXferProcessor.h"
Scroggo97c88c22011-05-11 14:05:25 +000022#include "SkXfermode.h"
23
commit-bot@chromium.org9188a152013-09-05 18:28:24 +000024#define GL_CALL(X) GR_GL_CALL(fGpu->glInterface(), X)
25#define GL_CALL_RET(R, X) GR_GL_CALL_RET(fGpu->glInterface(), R, X)
bsalomon@google.comecb60aa2012-07-18 13:20:29 +000026
joshualitt47bb3822014-10-07 16:43:25 -070027/**
28 * Retrieves the final matrix that a transform needs to apply to its source coords.
29 */
joshualitt290c09b2014-12-19 13:45:20 -080030static SkMatrix get_transform_matrix(const GrPendingFragmentStage& stage,
31 int transformIdx,
32 const SkMatrix& localMatrix) {
bsalomonae59b772014-11-19 08:23:49 -080033 const GrCoordTransform& coordTransform = stage.getProcessor()->coordTransform(transformIdx);
joshualitt47bb3822014-10-07 16:43:25 -070034 SkMatrix combined;
35
36 if (kLocal_GrCoordSet == coordTransform.sourceCoords()) {
joshualitt16b27892014-12-18 07:47:16 -080037 // If we have explicit local coords or are in device coords then we shouldn't need a coord
38 // change.
joshualitt290c09b2014-12-19 13:45:20 -080039 // TODO shortly we will get rid of coord change matrices entirely, and the PrimProc will
40 // always have a local matrix, often Identity, which can be used to transform coord
41 // transforms. Until we actually do this, we need some way for a PrimProc to say 'use my
42 // matrix' instead of the coord change mechanism. Temporarily, we have overloaded
43 // The identity matrix to be this value, ie if a primproc has an identity matrix for a
44 // local matrix then use the coord change matrix, otherwise use the matrix on the primproc
45 if (localMatrix.isIdentity()) {
46 const SkMatrix& ccm = stage.getCoordChangeMatrix();
47 combined.setConcat(coordTransform.getMatrix(), ccm);
48 } else {
49 combined.setConcat(coordTransform.getMatrix(), localMatrix);
50 }
kkinnunenec56e452014-08-25 22:21:16 -070051 } else {
joshualitt47bb3822014-10-07 16:43:25 -070052 combined = coordTransform.getMatrix();
kkinnunendddc18a2014-08-03 23:19:46 -070053 }
joshualitt47bb3822014-10-07 16:43:25 -070054 if (coordTransform.reverseY()) {
55 // combined.postScale(1,-1);
56 // combined.postTranslate(0,1);
57 combined.set(SkMatrix::kMSkewY,
58 combined[SkMatrix::kMPersp0] - combined[SkMatrix::kMSkewY]);
59 combined.set(SkMatrix::kMScaleY,
60 combined[SkMatrix::kMPersp1] - combined[SkMatrix::kMScaleY]);
61 combined.set(SkMatrix::kMTransY,
62 combined[SkMatrix::kMPersp2] - combined[SkMatrix::kMTransY]);
bsalomon@google.comecb60aa2012-07-18 13:20:29 +000063 }
joshualitt47bb3822014-10-07 16:43:25 -070064 return combined;
bsalomon@google.comecb60aa2012-07-18 13:20:29 +000065}
66
joshualitt47bb3822014-10-07 16:43:25 -070067///////////////////////////////////////////////////////////////////////////////////////////////////
68
bsalomon861e1032014-12-16 07:33:49 -080069GrGLProgram::GrGLProgram(GrGLGpu* gpu,
joshualitt79f8fae2014-10-28 17:59:26 -070070 const GrProgramDesc& desc,
joshualitt47bb3822014-10-07 16:43:25 -070071 const BuiltinUniformHandles& builtinUniforms,
72 GrGLuint programID,
73 const UniformInfoArray& uniforms,
joshualitta5305a12014-10-10 17:47:00 -070074 GrGLInstalledGeoProc* geometryProcessor,
egdanielc2304142014-12-11 13:15:13 -080075 GrGLInstalledXferProc* xferProcessor,
joshualitta5305a12014-10-10 17:47:00 -070076 GrGLInstalledFragProcs* fragmentProcessors)
commit-bot@chromium.orga05fa062014-05-30 18:55:03 +000077 : fColor(GrColor_ILLEGAL)
egdaniel37b4d862014-11-03 10:07:07 -080078 , fCoverage(0)
commit-bot@chromium.org6eac42e2014-05-29 21:29:51 +000079 , fDstCopyTexUnit(-1)
joshualitt47bb3822014-10-07 16:43:25 -070080 , fBuiltinUniformHandles(builtinUniforms)
81 , fProgramID(programID)
joshualitta5305a12014-10-10 17:47:00 -070082 , fGeometryProcessor(geometryProcessor)
egdanielc2304142014-12-11 13:15:13 -080083 , fXferProcessor(xferProcessor)
joshualitta5305a12014-10-10 17:47:00 -070084 , fFragmentProcessors(SkRef(fragmentProcessors))
commit-bot@chromium.org6eac42e2014-05-29 21:29:51 +000085 , fDesc(desc)
86 , fGpu(gpu)
joshualitt47bb3822014-10-07 16:43:25 -070087 , fProgramDataManager(gpu, uniforms) {
commit-bot@chromium.org6eac42e2014-05-29 21:29:51 +000088 this->initSamplerUniforms();
junov@google.comf93e7172011-03-31 21:26:24 +000089}
90
91GrGLProgram::~GrGLProgram() {
kkinnunendddc18a2014-08-03 23:19:46 -070092 if (fProgramID) {
93 GL_CALL(DeleteProgram(fProgramID));
bsalomon@google.comecb60aa2012-07-18 13:20:29 +000094 }
junov@google.comf93e7172011-03-31 21:26:24 +000095}
96
bsalomon@google.comecb60aa2012-07-18 13:20:29 +000097void GrGLProgram::abandon() {
kkinnunendddc18a2014-08-03 23:19:46 -070098 fProgramID = 0;
bsalomon@google.comecb60aa2012-07-18 13:20:29 +000099}
100
bsalomon@google.comdbbc4e22012-07-25 17:48:39 +0000101void GrGLProgram::initSamplerUniforms() {
kkinnunendddc18a2014-08-03 23:19:46 -0700102 GL_CALL(UseProgram(fProgramID));
bsalomon@google.com34cccde2013-01-04 18:34:30 +0000103 GrGLint texUnitIdx = 0;
kkinnunendddc18a2014-08-03 23:19:46 -0700104 if (fBuiltinUniformHandles.fDstCopySamplerUni.isValid()) {
105 fProgramDataManager.setSampler(fBuiltinUniformHandles.fDstCopySamplerUni, texUnitIdx);
bsalomon@google.com804e9942013-06-06 18:04:38 +0000106 fDstCopyTexUnit = texUnitIdx++;
bsalomon@google.com26e18b52013-03-29 19:22:36 +0000107 }
bsalomon49f085d2014-09-05 13:34:00 -0700108 if (fGeometryProcessor.get()) {
joshualitt47bb3822014-10-07 16:43:25 -0700109 this->initSamplers(fGeometryProcessor.get(), &texUnitIdx);
joshualittbd769d02014-09-04 08:56:46 -0700110 }
egdanielc2304142014-12-11 13:15:13 -0800111 if (fXferProcessor.get()) {
112 this->initSamplers(fXferProcessor.get(), &texUnitIdx);
113 }
joshualitta5305a12014-10-10 17:47:00 -0700114 int numProcs = fFragmentProcessors->fProcs.count();
115 for (int i = 0; i < numProcs; i++) {
116 this->initSamplers(fFragmentProcessors->fProcs[i], &texUnitIdx);
joshualitt47bb3822014-10-07 16:43:25 -0700117 }
118}
119
joshualitta5305a12014-10-10 17:47:00 -0700120void GrGLProgram::initSamplers(GrGLInstalledProc* ip, int* texUnitIdx) {
121 SkTArray<GrGLInstalledProc::Sampler, true>& samplers = ip->fSamplers;
122 int numSamplers = samplers.count();
123 for (int s = 0; s < numSamplers; ++s) {
124 SkASSERT(samplers[s].fUniform.isValid());
125 fProgramDataManager.setSampler(samplers[s].fUniform, *texUnitIdx);
126 samplers[s].fTextureUnit = (*texUnitIdx)++;
127 }
128}
129
130void GrGLProgram::bindTextures(const GrGLInstalledProc* ip, const GrProcessor& processor) {
131 const SkTArray<GrGLInstalledProc::Sampler, true>& samplers = ip->fSamplers;
joshualitt47bb3822014-10-07 16:43:25 -0700132 int numSamplers = samplers.count();
133 SkASSERT(numSamplers == processor.numTextures());
134 for (int s = 0; s < numSamplers; ++s) {
135 SkASSERT(samplers[s].fTextureUnit >= 0);
136 const GrTextureAccess& textureAccess = processor.textureAccess(s);
137 fGpu->bindTexture(samplers[s].fTextureUnit,
138 textureAccess.getParams(),
139 static_cast<GrGLTexture*>(textureAccess.getTexture()));
140 }
141}
142
143
bsalomon@google.comeb715c82012-07-11 15:03:31 +0000144///////////////////////////////////////////////////////////////////////////////
junov@google.comf93e7172011-03-31 21:26:24 +0000145
joshualittdafa4d02014-12-04 08:59:10 -0800146void GrGLProgram::setData(const GrOptDrawState& optState) {
joshualittdafa4d02014-12-04 08:59:10 -0800147 this->setMatrixAndRenderTargetHeight(optState);
bsalomon@google.com91207482013-02-12 21:45:24 +0000148
joshualitt9176e2c2014-11-20 07:28:52 -0800149 const GrDeviceCoordTexture* dstCopy = optState.getDstCopy();
bsalomon49f085d2014-09-05 13:34:00 -0700150 if (dstCopy) {
kkinnunendddc18a2014-08-03 23:19:46 -0700151 if (fBuiltinUniformHandles.fDstCopyTopLeftUni.isValid()) {
152 fProgramDataManager.set2f(fBuiltinUniformHandles.fDstCopyTopLeftUni,
kkinnunen7510b222014-07-30 00:04:16 -0700153 static_cast<GrGLfloat>(dstCopy->offset().fX),
154 static_cast<GrGLfloat>(dstCopy->offset().fY));
kkinnunendddc18a2014-08-03 23:19:46 -0700155 fProgramDataManager.set2f(fBuiltinUniformHandles.fDstCopyScaleUni,
kkinnunen7510b222014-07-30 00:04:16 -0700156 1.f / dstCopy->texture()->width(),
157 1.f / dstCopy->texture()->height());
bsalomon@google.com26e18b52013-03-29 19:22:36 +0000158 GrGLTexture* texture = static_cast<GrGLTexture*>(dstCopy->texture());
159 static GrTextureParams kParams; // the default is clamp, nearest filtering.
commit-bot@chromium.org9188a152013-09-05 18:28:24 +0000160 fGpu->bindTexture(fDstCopyTexUnit, kParams, texture);
bsalomon@google.com26e18b52013-03-29 19:22:36 +0000161 } else {
kkinnunendddc18a2014-08-03 23:19:46 -0700162 SkASSERT(!fBuiltinUniformHandles.fDstCopyScaleUni.isValid());
163 SkASSERT(!fBuiltinUniformHandles.fDstCopySamplerUni.isValid());
bsalomon@google.com26e18b52013-03-29 19:22:36 +0000164 }
165 } else {
kkinnunendddc18a2014-08-03 23:19:46 -0700166 SkASSERT(!fBuiltinUniformHandles.fDstCopyTopLeftUni.isValid());
167 SkASSERT(!fBuiltinUniformHandles.fDstCopyScaleUni.isValid());
168 SkASSERT(!fBuiltinUniformHandles.fDstCopySamplerUni.isValid());
bsalomon@google.com26e18b52013-03-29 19:22:36 +0000169 }
bsalomon@google.comc7818882013-03-20 19:19:53 +0000170
joshualitt47bb3822014-10-07 16:43:25 -0700171 // we set the textures, and uniforms for installed processors in a generic way, but subclasses
172 // of GLProgram determine how to set coord transforms
joshualitt9b989322014-12-15 14:16:27 -0800173 const GrPrimitiveProcessor& primProc = *optState.getPrimitiveProcessor();
174 const GrBatchTracker& bt = optState.getBatchTracker();
175 fGeometryProcessor->fGLProc->setData(fProgramDataManager, primProc, bt);
176 this->bindTextures(fGeometryProcessor, primProc);
177
egdanielc2304142014-12-11 13:15:13 -0800178 if (fXferProcessor.get()) {
179 const GrXferProcessor& xp = *optState.getXferProcessor();
180 fXferProcessor->fGLProc->setData(fProgramDataManager, xp);
181 this->bindTextures(fXferProcessor, xp);
182 }
joshualitta5305a12014-10-10 17:47:00 -0700183 this->setFragmentData(optState);
commit-bot@chromium.org20807222013-11-01 11:54:54 +0000184
joshualitt47bb3822014-10-07 16:43:25 -0700185 // Some of GrGLProgram subclasses need to update state here
joshualittdafa4d02014-12-04 08:59:10 -0800186 this->didSetData(optState.drawType());
joshualitt47bb3822014-10-07 16:43:25 -0700187}
188
joshualitta5305a12014-10-10 17:47:00 -0700189void GrGLProgram::setFragmentData(const GrOptDrawState& optState) {
190 int numProcessors = fFragmentProcessors->fProcs.count();
191 for (int e = 0; e < numProcessors; ++e) {
bsalomonae59b772014-11-19 08:23:49 -0800192 const GrPendingFragmentStage& stage = optState.getFragmentStage(e);
joshualitta5305a12014-10-10 17:47:00 -0700193 const GrProcessor& processor = *stage.getProcessor();
194 fFragmentProcessors->fProcs[e]->fGLProc->setData(fProgramDataManager, processor);
joshualitt290c09b2014-12-19 13:45:20 -0800195 const SkMatrix& localMatrix = optState.getPrimitiveProcessor()->localMatrix();
196 this->setTransformData(stage, localMatrix, fFragmentProcessors->fProcs[e]);
joshualitta5305a12014-10-10 17:47:00 -0700197 this->bindTextures(fFragmentProcessors->fProcs[e], processor);
198 }
199}
bsalomonae59b772014-11-19 08:23:49 -0800200void GrGLProgram::setTransformData(const GrPendingFragmentStage& processor,
joshualitt290c09b2014-12-19 13:45:20 -0800201 const SkMatrix& localMatrix,
bsalomonae59b772014-11-19 08:23:49 -0800202 GrGLInstalledFragProc* ip) {
joshualitta5305a12014-10-10 17:47:00 -0700203 SkTArray<GrGLInstalledFragProc::Transform, true>& transforms = ip->fTransforms;
joshualitt47bb3822014-10-07 16:43:25 -0700204 int numTransforms = transforms.count();
205 SkASSERT(numTransforms == processor.getProcessor()->numTransforms());
206 for (int t = 0; t < numTransforms; ++t) {
207 SkASSERT(transforms[t].fHandle.isValid());
joshualitt290c09b2014-12-19 13:45:20 -0800208 const SkMatrix& matrix = get_transform_matrix(processor, t, localMatrix);
joshualitt47bb3822014-10-07 16:43:25 -0700209 if (!transforms[t].fCurrentValue.cheapEqualTo(matrix)) {
210 fProgramDataManager.setSkMatrix(transforms[t].fHandle.convertToUniformHandle(), matrix);
211 transforms[t].fCurrentValue = matrix;
212 }
commit-bot@chromium.org6b30e452013-10-04 20:02:53 +0000213 }
skia.committer@gmail.com8ae714b2013-01-05 02:02:05 +0000214}
bsalomon@google.com91207482013-02-12 21:45:24 +0000215
joshualitt47bb3822014-10-07 16:43:25 -0700216void GrGLProgram::didSetData(GrGpu::DrawType drawType) {
217 SkASSERT(!GrGpu::IsPathRenderingDrawType(drawType));
218}
219
joshualittdafa4d02014-12-04 08:59:10 -0800220void GrGLProgram::setMatrixAndRenderTargetHeight(const GrOptDrawState& optState) {
joshualitt47bb3822014-10-07 16:43:25 -0700221 // Load the RT height uniform if it is needed to y-flip gl_FragCoord.
222 if (fBuiltinUniformHandles.fRTHeightUni.isValid() &&
223 fMatrixState.fRenderTargetSize.fHeight != optState.getRenderTarget()->height()) {
224 fProgramDataManager.set1f(fBuiltinUniformHandles.fRTHeightUni,
225 SkIntToScalar(optState.getRenderTarget()->height()));
226 }
227
228 // call subclasses to set the actual view matrix
joshualittdafa4d02014-12-04 08:59:10 -0800229 this->onSetMatrixAndRenderTargetHeight(optState);
joshualitt47bb3822014-10-07 16:43:25 -0700230}
231
joshualittdafa4d02014-12-04 08:59:10 -0800232void GrGLProgram::onSetMatrixAndRenderTargetHeight(const GrOptDrawState& optState) {
egdaniel170f90b2014-09-16 12:54:40 -0700233 const GrRenderTarget* rt = optState.getRenderTarget();
bsalomon@google.com6a51dcb2013-02-13 16:03:51 +0000234 SkISize size;
235 size.set(rt->width(), rt->height());
joshualitt47bb3822014-10-07 16:43:25 -0700236 if (fMatrixState.fRenderTargetOrigin != rt->origin() ||
237 fMatrixState.fRenderTargetSize != size ||
238 !fMatrixState.fViewMatrix.cheapEqualTo(optState.getViewMatrix())) {
kkinnunendddc18a2014-08-03 23:19:46 -0700239 SkASSERT(fBuiltinUniformHandles.fViewMatrixUni.isValid());
bsalomon@google.com6a51dcb2013-02-13 16:03:51 +0000240
egdaniel170f90b2014-09-16 12:54:40 -0700241 fMatrixState.fViewMatrix = optState.getViewMatrix();
bsalomon@google.com6a51dcb2013-02-13 16:03:51 +0000242 fMatrixState.fRenderTargetSize = size;
243 fMatrixState.fRenderTargetOrigin = rt->origin();
commit-bot@chromium.org215a6822013-09-05 18:28:42 +0000244
245 GrGLfloat viewMatrix[3 * 3];
246 fMatrixState.getGLMatrix<3>(viewMatrix);
kkinnunendddc18a2014-08-03 23:19:46 -0700247 fProgramDataManager.setMatrix3f(fBuiltinUniformHandles.fViewMatrixUni, viewMatrix);
commit-bot@chromium.org47c66dd2014-05-29 01:12:10 +0000248
249 GrGLfloat rtAdjustmentVec[4];
250 fMatrixState.getRTAdjustmentVec(rtAdjustmentVec);
kkinnunendddc18a2014-08-03 23:19:46 -0700251 fProgramDataManager.set4fv(fBuiltinUniformHandles.fRTAdjustmentUni, 1, rtAdjustmentVec);
bsalomon@google.com6a51dcb2013-02-13 16:03:51 +0000252 }
253}
joshualitt47bb3822014-10-07 16:43:25 -0700254
255/////////////////////////////////////////////////////////////////////////////////////////
256
bsalomon861e1032014-12-16 07:33:49 -0800257GrGLNvprProgramBase::GrGLNvprProgramBase(GrGLGpu* gpu,
joshualitt79f8fae2014-10-28 17:59:26 -0700258 const GrProgramDesc& desc,
joshualitt47bb3822014-10-07 16:43:25 -0700259 const BuiltinUniformHandles& builtinUniforms,
260 GrGLuint programID,
261 const UniformInfoArray& uniforms,
joshualitt9b989322014-12-15 14:16:27 -0800262 GrGLInstalledGeoProc* primProc,
egdanielc2304142014-12-11 13:15:13 -0800263 GrGLInstalledXferProc* xferProcessor,
joshualitta5305a12014-10-10 17:47:00 -0700264 GrGLInstalledFragProcs* fragmentProcessors)
joshualitt9b989322014-12-15 14:16:27 -0800265 : INHERITED(gpu, desc, builtinUniforms, programID, uniforms, primProc,
egdanielc2304142014-12-11 13:15:13 -0800266 xferProcessor, fragmentProcessors) {
joshualitt47bb3822014-10-07 16:43:25 -0700267}
268
joshualittdafa4d02014-12-04 08:59:10 -0800269void GrGLNvprProgramBase::onSetMatrixAndRenderTargetHeight(const GrOptDrawState& optState) {
270 SkASSERT(GrGpu::IsPathRenderingDrawType(optState.drawType()));
joshualitt47bb3822014-10-07 16:43:25 -0700271 const GrRenderTarget* rt = optState.getRenderTarget();
272 SkISize size;
273 size.set(rt->width(), rt->height());
274 fGpu->glPathRendering()->setProjectionMatrix(optState.getViewMatrix(), size, rt->origin());
275}
276
277/////////////////////////////////////////////////////////////////////////////////////////
278
bsalomon861e1032014-12-16 07:33:49 -0800279GrGLNvprProgram::GrGLNvprProgram(GrGLGpu* gpu,
joshualitt79f8fae2014-10-28 17:59:26 -0700280 const GrProgramDesc& desc,
joshualitt47bb3822014-10-07 16:43:25 -0700281 const BuiltinUniformHandles& builtinUniforms,
282 GrGLuint programID,
283 const UniformInfoArray& uniforms,
joshualitt9b989322014-12-15 14:16:27 -0800284 GrGLInstalledGeoProc* primProc,
egdanielc2304142014-12-11 13:15:13 -0800285 GrGLInstalledXferProc* xferProcessor,
joshualitta5305a12014-10-10 17:47:00 -0700286 GrGLInstalledFragProcs* fragmentProcessors,
joshualitt47bb3822014-10-07 16:43:25 -0700287 const SeparableVaryingInfoArray& separableVaryings)
joshualitt9b989322014-12-15 14:16:27 -0800288 : INHERITED(gpu, desc, builtinUniforms, programID, uniforms, primProc,
egdanielc2304142014-12-11 13:15:13 -0800289 xferProcessor, fragmentProcessors) {
joshualitt47bb3822014-10-07 16:43:25 -0700290 int count = separableVaryings.count();
291 fVaryings.push_back_n(count);
292 for (int i = 0; i < count; i++) {
293 Varying& varying = fVaryings[i];
294 const SeparableVaryingInfo& builderVarying = separableVaryings[i];
295 SkASSERT(GrGLShaderVar::kNonArray == builderVarying.fVariable.getArrayCount());
296 SkDEBUGCODE(
297 varying.fType = builderVarying.fVariable.getType();
298 );
299 varying.fLocation = builderVarying.fLocation;
300 }
301}
302
303void GrGLNvprProgram::didSetData(GrGpu::DrawType drawType) {
304 SkASSERT(GrGpu::IsPathRenderingDrawType(drawType));
305}
306
bsalomonae59b772014-11-19 08:23:49 -0800307void GrGLNvprProgram::setTransformData(const GrPendingFragmentStage& proc,
joshualitt290c09b2014-12-19 13:45:20 -0800308 const SkMatrix& localMatrix,
bsalomonae59b772014-11-19 08:23:49 -0800309 GrGLInstalledFragProc* ip) {
joshualitta5305a12014-10-10 17:47:00 -0700310 SkTArray<GrGLInstalledFragProc::Transform, true>& transforms = ip->fTransforms;
joshualitt47bb3822014-10-07 16:43:25 -0700311 int numTransforms = transforms.count();
joshualitta5305a12014-10-10 17:47:00 -0700312 SkASSERT(numTransforms == proc.getProcessor()->numTransforms());
joshualitt47bb3822014-10-07 16:43:25 -0700313 for (int t = 0; t < numTransforms; ++t) {
314 SkASSERT(transforms[t].fHandle.isValid());
joshualitt290c09b2014-12-19 13:45:20 -0800315 const SkMatrix& transform = get_transform_matrix(proc, t, localMatrix);
joshualitt47bb3822014-10-07 16:43:25 -0700316 if (transforms[t].fCurrentValue.cheapEqualTo(transform)) {
317 continue;
318 }
319 transforms[t].fCurrentValue = transform;
320 const Varying& fragmentInput = fVaryings[transforms[t].fHandle.handle()];
321 SkASSERT(transforms[t].fType == kVec2f_GrSLType || transforms[t].fType == kVec3f_GrSLType);
322 unsigned components = transforms[t].fType == kVec2f_GrSLType ? 2 : 3;
323 fGpu->glPathRendering()->setProgramPathFragmentInputTransform(fProgramID,
324 fragmentInput.fLocation,
325 GR_GL_OBJECT_LINEAR,
326 components,
327 transform);
328 }
329}
330
331//////////////////////////////////////////////////////////////////////////////////////
332
bsalomon861e1032014-12-16 07:33:49 -0800333GrGLLegacyNvprProgram::GrGLLegacyNvprProgram(GrGLGpu* gpu,
joshualitt79f8fae2014-10-28 17:59:26 -0700334 const GrProgramDesc& desc,
joshualitta5305a12014-10-10 17:47:00 -0700335 const BuiltinUniformHandles& builtinUniforms,
336 GrGLuint programID,
337 const UniformInfoArray& uniforms,
joshualitt9b989322014-12-15 14:16:27 -0800338 GrGLInstalledGeoProc* primProc,
egdanielc2304142014-12-11 13:15:13 -0800339 GrGLInstalledXferProc* xp,
joshualitta5305a12014-10-10 17:47:00 -0700340 GrGLInstalledFragProcs* fps,
341 int texCoordSetCnt)
joshualitt9b989322014-12-15 14:16:27 -0800342 : INHERITED(gpu, desc, builtinUniforms, programID, uniforms, primProc, xp, fps)
joshualitt47bb3822014-10-07 16:43:25 -0700343 , fTexCoordSetCnt(texCoordSetCnt) {
344}
345
346void GrGLLegacyNvprProgram::didSetData(GrGpu::DrawType drawType) {
347 SkASSERT(GrGpu::IsPathRenderingDrawType(drawType));
348 fGpu->glPathRendering()->flushPathTexGenSettings(fTexCoordSetCnt);
349}
350
joshualitta5305a12014-10-10 17:47:00 -0700351void
bsalomonae59b772014-11-19 08:23:49 -0800352GrGLLegacyNvprProgram::setTransformData(const GrPendingFragmentStage& proc,
joshualitt290c09b2014-12-19 13:45:20 -0800353 const SkMatrix& localMatrix,
bsalomonae59b772014-11-19 08:23:49 -0800354 GrGLInstalledFragProc* ip) {
joshualitt47bb3822014-10-07 16:43:25 -0700355 // We've hidden the texcoord index in the first entry of the transforms array for each effect
joshualitta5305a12014-10-10 17:47:00 -0700356 int texCoordIndex = ip->fTransforms[0].fHandle.handle();
357 int numTransforms = proc.getProcessor()->numTransforms();
joshualitt47bb3822014-10-07 16:43:25 -0700358 for (int t = 0; t < numTransforms; ++t) {
joshualitt290c09b2014-12-19 13:45:20 -0800359 const SkMatrix& transform = get_transform_matrix(proc, t, localMatrix);
joshualitt47bb3822014-10-07 16:43:25 -0700360 GrGLPathRendering::PathTexGenComponents components =
361 GrGLPathRendering::kST_PathTexGenComponents;
bsalomonae59b772014-11-19 08:23:49 -0800362 if (proc.isPerspectiveCoordTransform(t)) {
joshualitt47bb3822014-10-07 16:43:25 -0700363 components = GrGLPathRendering::kSTR_PathTexGenComponents;
364 }
365 fGpu->glPathRendering()->enablePathTexGen(texCoordIndex++, components, transform);
366 }
367}