blob: e28d646f5f1c812defd9b6dfb8da50a1b519d08c [file] [log] [blame]
Rahul Ravikumar05336002019-10-14 15:04:32 -07001/*
2 * Copyright (C) 2008 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17package android.renderscript;
18
19
20import java.io.IOException;
21import java.io.InputStream;
22import java.io.UnsupportedEncodingException;
23
24import android.annotation.UnsupportedAppUsage;
25import android.content.res.Resources;
26import android.util.Log;
27
28
29/**
30 * @hide
31 *
32 * Program is a base class for all the objects that modify
33 * various stages of the graphics pipeline
34 *
35 **/
36public class Program extends BaseObj {
37 static final int MAX_INPUT = 8;
38 static final int MAX_OUTPUT = 8;
39 static final int MAX_CONSTANT = 8;
40 static final int MAX_TEXTURE = 8;
41
42 /**
43 *
44 * TextureType specifies what textures are attached to Program
45 * objects
46 *
47 **/
48 public enum TextureType {
49 @UnsupportedAppUsage
50 TEXTURE_2D (0),
51 TEXTURE_CUBE (1);
52
53 int mID;
54 TextureType(int id) {
55 mID = id;
56 }
57 }
58
59 enum ProgramParam {
60 INPUT (0),
61 OUTPUT (1),
62 CONSTANT (2),
63 TEXTURE_TYPE (3);
64
65 int mID;
66 ProgramParam(int id) {
67 mID = id;
68 }
69 };
70
71 Element mInputs[];
72 Element mOutputs[];
73 Type mConstants[];
74 TextureType mTextures[];
75 String mTextureNames[];
76 int mTextureCount;
77 String mShader;
78
79 Program(long id, RenderScript rs) {
80 super(id, rs);
81 guard.open("destroy");
82 }
83
84 /**
85 * Program object can have zero or more constant allocations
86 * associated with it. This method returns the total count.
87 * @return number of constant input types
88 */
89 public int getConstantCount() {
90 return mConstants != null ? mConstants.length : 0;
91 }
92
93 /**
94 * Returns the type of the constant buffer used in the program
95 * object. It could be used to query internal elements or create
96 * an allocation to store constant data.
97 * @param slot index of the constant input type to return
98 * @return constant input type
99 */
100 public Type getConstant(int slot) {
101 if (slot < 0 || slot >= mConstants.length) {
102 throw new IllegalArgumentException("Slot ID out of range.");
103 }
104 return mConstants[slot];
105 }
106
107 /**
108 * Returns the number of textures used in this program object
109 * @return number of texture inputs
110 */
111 public int getTextureCount() {
112 return mTextureCount;
113 }
114
115 /**
116 * Returns the type of texture at a given slot. e.g. 2D or Cube
117 * @param slot index of the texture input
118 * @return texture input type
119 */
120 public TextureType getTextureType(int slot) {
121 if ((slot < 0) || (slot >= mTextureCount)) {
122 throw new IllegalArgumentException("Slot ID out of range.");
123 }
124 return mTextures[slot];
125 }
126
127 /**
128 * Returns the name of the texture input at a given slot. e.g.
129 * tex0, diffuse, spec
130 * @param slot index of the texture input
131 * @return texture input name
132 */
133 public String getTextureName(int slot) {
134 if ((slot < 0) || (slot >= mTextureCount)) {
135 throw new IllegalArgumentException("Slot ID out of range.");
136 }
137 return mTextureNames[slot];
138 }
139
140 /**
141 * Binds a constant buffer to be used as uniform inputs to the
142 * program
143 *
144 * @param a allocation containing uniform data
145 * @param slot index within the program's list of constant
146 * buffer allocations
147 */
148 public void bindConstants(Allocation a, int slot) {
149 if (slot < 0 || slot >= mConstants.length) {
150 throw new IllegalArgumentException("Slot ID out of range.");
151 }
152 if (a != null &&
153 a.getType().getID(mRS) != mConstants[slot].getID(mRS)) {
154 throw new IllegalArgumentException("Allocation type does not match slot type.");
155 }
156 long id = a != null ? a.getID(mRS) : 0;
157 mRS.nProgramBindConstants(getID(mRS), slot, id);
158 }
159
160 /**
161 * Binds a texture to be used in the program
162 *
163 * @param va allocation containing texture data
164 * @param slot index within the program's list of textures
165 *
166 */
167 public void bindTexture(Allocation va, int slot)
168 throws IllegalArgumentException {
169 mRS.validate();
170 if ((slot < 0) || (slot >= mTextureCount)) {
171 throw new IllegalArgumentException("Slot ID out of range.");
172 }
173 if (va != null && va.getType().hasFaces() &&
174 mTextures[slot] != TextureType.TEXTURE_CUBE) {
175 throw new IllegalArgumentException("Cannot bind cubemap to 2d texture slot");
176 }
177
178 long id = va != null ? va.getID(mRS) : 0;
179 mRS.nProgramBindTexture(getID(mRS), slot, id);
180 }
181
182 /**
183 * Binds an object that describes how a texture at the
184 * corresponding location is sampled
185 *
186 * @param vs sampler for a corresponding texture
187 * @param slot index within the program's list of textures to
188 * use the sampler on
189 *
190 */
191 public void bindSampler(Sampler vs, int slot)
192 throws IllegalArgumentException {
193 mRS.validate();
194 if ((slot < 0) || (slot >= mTextureCount)) {
195 throw new IllegalArgumentException("Slot ID out of range.");
196 }
197
198 long id = vs != null ? vs.getID(mRS) : 0;
199 mRS.nProgramBindSampler(getID(mRS), slot, id);
200 }
201
202
203 public static class BaseProgramBuilder {
204 @UnsupportedAppUsage
205 RenderScript mRS;
206 @UnsupportedAppUsage
207 Element mInputs[];
208 @UnsupportedAppUsage
209 Element mOutputs[];
210 @UnsupportedAppUsage
211 Type mConstants[];
212 Type mTextures[];
213 TextureType mTextureTypes[];
214 String mTextureNames[];
215 @UnsupportedAppUsage
216 int mInputCount;
217 @UnsupportedAppUsage
218 int mOutputCount;
219 @UnsupportedAppUsage
220 int mConstantCount;
221 @UnsupportedAppUsage
222 int mTextureCount;
223 @UnsupportedAppUsage
224 String mShader;
225
226
227 @UnsupportedAppUsage
228 protected BaseProgramBuilder(RenderScript rs) {
229 mRS = rs;
230 mInputs = new Element[MAX_INPUT];
231 mOutputs = new Element[MAX_OUTPUT];
232 mConstants = new Type[MAX_CONSTANT];
233 mInputCount = 0;
234 mOutputCount = 0;
235 mConstantCount = 0;
236 mTextureCount = 0;
237 mTextureTypes = new TextureType[MAX_TEXTURE];
238 mTextureNames = new String[MAX_TEXTURE];
239 }
240
241 /**
242 * Sets the GLSL shader code to be used in the program
243 *
244 * @param s GLSL shader string
245 * @return self
246 */
247 public BaseProgramBuilder setShader(String s) {
248 mShader = s;
249 return this;
250 }
251
252 /**
253 * Sets the GLSL shader code to be used in the program
254 *
255 * @param resources application resources
256 * @param resourceID id of the file containing GLSL shader code
257 *
258 * @return self
259 */
260 public BaseProgramBuilder setShader(Resources resources, int resourceID) {
261 byte[] str;
262 int strLength;
263 InputStream is = resources.openRawResource(resourceID);
264 try {
265 try {
266 str = new byte[1024];
267 strLength = 0;
268 while(true) {
269 int bytesLeft = str.length - strLength;
270 if (bytesLeft == 0) {
271 byte[] buf2 = new byte[str.length * 2];
272 System.arraycopy(str, 0, buf2, 0, str.length);
273 str = buf2;
274 bytesLeft = str.length - strLength;
275 }
276 int bytesRead = is.read(str, strLength, bytesLeft);
277 if (bytesRead <= 0) {
278 break;
279 }
280 strLength += bytesRead;
281 }
282 } finally {
283 is.close();
284 }
285 } catch(IOException e) {
286 throw new Resources.NotFoundException();
287 }
288
289 try {
290 mShader = new String(str, 0, strLength, "UTF-8");
291 } catch (UnsupportedEncodingException e) {
292 Log.e("RenderScript shader creation", "Could not decode shader string");
293 }
294
295 return this;
296 }
297
298 /**
299 * Queries the index of the last added constant buffer type
300 *
301 */
302 public int getCurrentConstantIndex() {
303 return mConstantCount - 1;
304 }
305
306 /**
307 * Queries the index of the last added texture type
308 *
309 */
310 public int getCurrentTextureIndex() {
311 return mTextureCount - 1;
312 }
313
314 /**
315 * Adds constant (uniform) inputs to the program
316 *
317 * @param t Type that describes the layout of the Allocation
318 * object to be used as constant inputs to the Program
319 * @return self
320 */
321 public BaseProgramBuilder addConstant(Type t) throws IllegalStateException {
322 // Should check for consistant and non-conflicting names...
323 if(mConstantCount >= MAX_CONSTANT) {
324 throw new RSIllegalArgumentException("Max input count exceeded.");
325 }
326 if (t.getElement().isComplex()) {
327 throw new RSIllegalArgumentException("Complex elements not allowed.");
328 }
329 mConstants[mConstantCount] = t;
330 mConstantCount++;
331 return this;
332 }
333
334 /**
335 * Adds a texture input to the Program
336 *
337 * @param texType describes that the texture to append it (2D,
338 * Cubemap, etc.)
339 * @return self
340 */
341 public BaseProgramBuilder addTexture(TextureType texType) throws IllegalArgumentException {
342 addTexture(texType, "Tex" + mTextureCount);
343 return this;
344 }
345
346 /**
347 * Adds a texture input to the Program
348 *
349 * @param texType describes that the texture to append it (2D,
350 * Cubemap, etc.)
351 * @param texName what the texture should be called in the
352 * shader
353 * @return self
354 */
355 public BaseProgramBuilder addTexture(TextureType texType, String texName)
356 throws IllegalArgumentException {
357 if(mTextureCount >= MAX_TEXTURE) {
358 throw new IllegalArgumentException("Max texture count exceeded.");
359 }
360 mTextureTypes[mTextureCount] = texType;
361 mTextureNames[mTextureCount] = texName;
362 mTextureCount ++;
363 return this;
364 }
365
366 protected void initProgram(Program p) {
367 p.mInputs = new Element[mInputCount];
368 System.arraycopy(mInputs, 0, p.mInputs, 0, mInputCount);
369 p.mOutputs = new Element[mOutputCount];
370 System.arraycopy(mOutputs, 0, p.mOutputs, 0, mOutputCount);
371 p.mConstants = new Type[mConstantCount];
372 System.arraycopy(mConstants, 0, p.mConstants, 0, mConstantCount);
373 p.mTextureCount = mTextureCount;
374 p.mTextures = new TextureType[mTextureCount];
375 System.arraycopy(mTextureTypes, 0, p.mTextures, 0, mTextureCount);
376 p.mTextureNames = new String[mTextureCount];
377 System.arraycopy(mTextureNames, 0, p.mTextureNames, 0, mTextureCount);
378 }
379 }
380
381}
382
383