1a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk/*
23522f40418fdf877f5a136475dbf75e57a3b7c77Jason Sams * Copyright (C) 2011-2012 The Android Open Source Project
3a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk *
4a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk * Licensed under the Apache License, Version 2.0 (the "License");
5a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk * you may not use this file except in compliance with the License.
6a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk * You may obtain a copy of the License at
7a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk *
8a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk *      http://www.apache.org/licenses/LICENSE-2.0
9a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk *
10a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk * Unless required by applicable law or agreed to in writing, software
11a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk * distributed under the License is distributed on an "AS IS" BASIS,
12a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk * See the License for the specific language governing permissions and
14a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk * limitations under the License.
15a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk */
16a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
17a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk#ifndef ANDROID_RSD_SHADER_H
18a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk#define ANDROID_RSD_SHADER_H
19a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
20a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk#include <utils/String8.h>
21a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
22a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk// ---------------------------------------------------------------------------
23a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouknamespace android {
24a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouknamespace renderscript {
25a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
26a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchoukclass Element;
27a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchoukclass Context;
28a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchoukclass Program;
29a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
30a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk}
31a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk}
32a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
33a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchoukclass RsdShaderCache;
34a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
35a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk#define RS_SHADER_ATTR "ATTRIB_"
36a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk#define RS_SHADER_UNI "UNI_"
37a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
38a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchoukclass RsdShader {
39a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchoukpublic:
40a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
41a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    RsdShader(const android::renderscript::Program *p, uint32_t type,
42e195a3f57ace3b66d313a6ee88c6e93d5c9d87f4Tim Murray              const char * shaderText, size_t shaderLength,
43748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk              const char** textureNames, size_t textureNamesCount,
44748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk              const size_t *textureNamesLength);
45a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    virtual ~RsdShader();
46a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
476d6e114f8bea8db08bf1decb673d3eb9a8f258aeAlex Sakhartchouk    uint32_t getStateBasedShaderID(const android::renderscript::Context *);
48a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
496d6e114f8bea8db08bf1decb673d3eb9a8f258aeAlex Sakhartchouk    // Add ability to get all ID's to clean up the cached program objects
506d6e114f8bea8db08bf1decb673d3eb9a8f258aeAlex Sakhartchouk    uint32_t getStateBasedIDCount() const { return mStateBasedShaders.size(); }
516d6e114f8bea8db08bf1decb673d3eb9a8f258aeAlex Sakhartchouk    uint32_t getStateBasedID(uint32_t index) const {
526d6e114f8bea8db08bf1decb673d3eb9a8f258aeAlex Sakhartchouk        return mStateBasedShaders.itemAt(index)->mShaderID;
536d6e114f8bea8db08bf1decb673d3eb9a8f258aeAlex Sakhartchouk    }
54a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
55a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    uint32_t getAttribCount() const {return mAttribCount;}
56a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    uint32_t getUniformCount() const {return mUniformCount;}
57a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    const android::String8 & getAttribName(uint32_t i) const {return mAttribNames[i];}
58a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    const android::String8 & getUniformName(uint32_t i) const {return mUniformNames[i];}
59a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    uint32_t getUniformArraySize(uint32_t i) const {return mUniformArraySizes[i];}
60a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
61a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    android::String8 getGLSLInputString() const;
62a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
63a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    bool isValid() const {return mIsValid;}
64a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    void forceDirty() const {mDirty = true;}
65a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
66a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    bool loadShader(const android::renderscript::Context *);
67a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    void setup(const android::renderscript::Context *, RsdShaderCache *sc);
68a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
69a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchoukprotected:
70a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
716d6e114f8bea8db08bf1decb673d3eb9a8f258aeAlex Sakhartchouk    class StateBasedKey {
726d6e114f8bea8db08bf1decb673d3eb9a8f258aeAlex Sakhartchouk    public:
736d6e114f8bea8db08bf1decb673d3eb9a8f258aeAlex Sakhartchouk        StateBasedKey(uint32_t texCount) : mShaderID(0) {
746d6e114f8bea8db08bf1decb673d3eb9a8f258aeAlex Sakhartchouk            mTextureTargets = new uint32_t[texCount];
756d6e114f8bea8db08bf1decb673d3eb9a8f258aeAlex Sakhartchouk        }
766d6e114f8bea8db08bf1decb673d3eb9a8f258aeAlex Sakhartchouk        ~StateBasedKey() {
776d6e114f8bea8db08bf1decb673d3eb9a8f258aeAlex Sakhartchouk            delete[] mTextureTargets;
786d6e114f8bea8db08bf1decb673d3eb9a8f258aeAlex Sakhartchouk        }
796d6e114f8bea8db08bf1decb673d3eb9a8f258aeAlex Sakhartchouk        uint32_t mShaderID;
806d6e114f8bea8db08bf1decb673d3eb9a8f258aeAlex Sakhartchouk        uint32_t *mTextureTargets;
816d6e114f8bea8db08bf1decb673d3eb9a8f258aeAlex Sakhartchouk    };
826d6e114f8bea8db08bf1decb673d3eb9a8f258aeAlex Sakhartchouk
836d6e114f8bea8db08bf1decb673d3eb9a8f258aeAlex Sakhartchouk    bool createShader();
846d6e114f8bea8db08bf1decb673d3eb9a8f258aeAlex Sakhartchouk    StateBasedKey *getExistingState();
856d6e114f8bea8db08bf1decb673d3eb9a8f258aeAlex Sakhartchouk
86a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    const android::renderscript::Program *mRSProgram;
87a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    bool mIsValid;
88a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
89a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    // Applies to vertex and fragment shaders only
90a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    void appendUserConstants();
91748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk    void setupUserConstants(const android::renderscript::Context *rsc,
92748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk                            RsdShaderCache *sc, bool isFragment);
93748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk    void initAddUserElement(const android::renderscript::Element *e,
94748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk                            android::String8 *names, uint32_t *arrayLengths,
95748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk                            uint32_t *count, const char *prefix);
96a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    void setupTextures(const android::renderscript::Context *rsc, RsdShaderCache *sc);
97748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk    void setupSampler(const android::renderscript::Context *rsc,
98748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk                      const android::renderscript::Sampler *s,
99748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk                      const android::renderscript::Allocation *tex);
100a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
101a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    void appendAttributes();
102a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    void appendTextures();
103a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
104a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    void initAttribAndUniformArray();
105a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
106a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    mutable bool mDirty;
107a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    android::String8 mShader;
108a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    android::String8 mUserShader;
109a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    uint32_t mType;
110a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
111a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    uint32_t mTextureCount;
1126d6e114f8bea8db08bf1decb673d3eb9a8f258aeAlex Sakhartchouk    StateBasedKey *mCurrentState;
113a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    uint32_t mAttribCount;
114a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    uint32_t mUniformCount;
115a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    android::String8 *mAttribNames;
116a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    android::String8 *mUniformNames;
117a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    uint32_t *mUniformArraySizes;
118a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
1193522f40418fdf877f5a136475dbf75e57a3b7c77Jason Sams    android::Vector<android::String8> mTextureNames;
1203522f40418fdf877f5a136475dbf75e57a3b7c77Jason Sams
1216d6e114f8bea8db08bf1decb673d3eb9a8f258aeAlex Sakhartchouk    android::Vector<StateBasedKey*> mStateBasedShaders;
1226d6e114f8bea8db08bf1decb673d3eb9a8f258aeAlex Sakhartchouk
123a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    int32_t mTextureUniformIndexStart;
124a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
125748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk    void logUniform(const android::renderscript::Element *field,
126748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk                    const float *fd, uint32_t arraySize);
127748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk    void setUniform(const android::renderscript::Context *rsc,
128748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk                    const android::renderscript::Element *field,
129748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk                    const float *fd, int32_t slot, uint32_t arraySize );
130a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk    void initMemberVars();
131748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk    void init(const char** textureNames, size_t textureNamesCount,
132748eb07e805b93c2bf79340d4937963ab739d17cAlex Sakhartchouk              const size_t *textureNamesLength);
133a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk};
134a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
135a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk#endif //ANDROID_RSD_SHADER_H
136a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
137a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
138a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
139a04e30dbb5ab11592b03666bb3d102070759c58eAlex Sakhartchouk
140