FragmentShader.java revision 0c9523357f48a26c8214ccff0b0d95c6927ac0d3
14fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk/*
24fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk * Copyright (C) 2011 The Android Open Source Project
34fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk *
44fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk * Licensed under the Apache License, Version 2.0 (the "License");
54fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk * you may not use this file except in compliance with the License.
64fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk * You may obtain a copy of the License at
74fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk *
84fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk *      http://www.apache.org/licenses/LICENSE-2.0
94fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk *
104fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk * Unless required by applicable law or agreed to in writing, software
114fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk * distributed under the License is distributed on an "AS IS" BASIS,
124fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
134fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk * See the License for the specific language governing permissions and
144fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk * limitations under the License.
154fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk */
164fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk
174fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchoukpackage com.android.scenegraph;
184fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk
194fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchoukimport java.lang.Math;
204fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchoukimport java.util.ArrayList;
214fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk
225de922962a2fa06267f3ad26f75e3a8083af906cAlex Sakhartchoukimport com.android.scenegraph.TextureBase;
235de922962a2fa06267f3ad26f75e3a8083af906cAlex Sakhartchouk
244fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchoukimport android.content.res.Resources;
254fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchoukimport android.renderscript.*;
264fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchoukimport android.renderscript.ProgramFragment.Builder;
274fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchoukimport android.util.Log;
284fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk
294fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk/**
304fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk * @hide
314fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk */
324fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchoukpublic class FragmentShader extends Shader {
334fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk    ProgramFragment mProgram;
344fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk    ScriptField_FragmentShader_s mField;
354fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk
364fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk    public static class Builder {
374fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk
384fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk        FragmentShader mShader;
394fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk        ProgramFragment.Builder mBuilder;
404fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk
414fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk        public Builder(RenderScriptGL rs) {
424fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk            mShader = new FragmentShader();
434fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk            mBuilder = new ProgramFragment.Builder(rs);
444fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk        }
454fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk
464fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk        public Builder setShader(Resources resources, int resourceID) {
474fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk            mBuilder.setShader(resources, resourceID);
484fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk            return this;
494fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk        }
504fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk
514fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk        public Builder setObjectConst(Type type) {
524fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk            mShader.mPerObjConstants = type;
534fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk            return this;
544fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk        }
554fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk
564fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk        public Builder setShaderConst(Type type) {
574fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk            mShader.mPerShaderConstants = type;
584fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk            return this;
594fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk        }
604fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk
6199b93819f12f18b8559f702d7a303c31fe05205aAlex Sakhartchouk        public Builder addShaderTexture(Program.TextureType texType, String name) {
6299b93819f12f18b8559f702d7a303c31fe05205aAlex Sakhartchouk            mShader.mShaderTextureNames.add(name);
6399b93819f12f18b8559f702d7a303c31fe05205aAlex Sakhartchouk            mShader.mShaderTextureTypes.add(texType);
6499b93819f12f18b8559f702d7a303c31fe05205aAlex Sakhartchouk            return this;
6599b93819f12f18b8559f702d7a303c31fe05205aAlex Sakhartchouk        }
6699b93819f12f18b8559f702d7a303c31fe05205aAlex Sakhartchouk
674fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk        public Builder addTexture(Program.TextureType texType, String name) {
684fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk            mShader.mTextureNames.add(name);
6999b93819f12f18b8559f702d7a303c31fe05205aAlex Sakhartchouk            mShader.mTextureTypes.add(texType);
704fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk            return this;
714fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk        }
724fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk
73d4cb9c587c23e3c24d928b0ac1a4de5679846f93Alex Sakhartchouk        public FragmentShader create() {
744fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk            if (mShader.mPerShaderConstants != null) {
754fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk                mBuilder.addConstant(mShader.mPerShaderConstants);
764fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk            }
774fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk            if (mShader.mPerObjConstants != null) {
784fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk                mBuilder.addConstant(mShader.mPerObjConstants);
794fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk            }
8099b93819f12f18b8559f702d7a303c31fe05205aAlex Sakhartchouk            for (int i = 0; i < mShader.mTextureTypes.size(); i ++) {
8199b93819f12f18b8559f702d7a303c31fe05205aAlex Sakhartchouk                mBuilder.addTexture(mShader.mTextureTypes.get(i));
8299b93819f12f18b8559f702d7a303c31fe05205aAlex Sakhartchouk            }
8399b93819f12f18b8559f702d7a303c31fe05205aAlex Sakhartchouk            for (int i = 0; i < mShader.mShaderTextureTypes.size(); i ++) {
8499b93819f12f18b8559f702d7a303c31fe05205aAlex Sakhartchouk                mBuilder.addTexture(mShader.mShaderTextureTypes.get(i));
8599b93819f12f18b8559f702d7a303c31fe05205aAlex Sakhartchouk            }
8699b93819f12f18b8559f702d7a303c31fe05205aAlex Sakhartchouk
874fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk            mShader.mProgram = mBuilder.create();
884fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk            return mShader;
894fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk        }
904fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk    }
914fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk
92d4cb9c587c23e3c24d928b0ac1a4de5679846f93Alex Sakhartchouk    public ProgramFragment getProgram() {
93d4cb9c587c23e3c24d928b0ac1a4de5679846f93Alex Sakhartchouk        return mProgram;
94d4cb9c587c23e3c24d928b0ac1a4de5679846f93Alex Sakhartchouk    }
95d4cb9c587c23e3c24d928b0ac1a4de5679846f93Alex Sakhartchouk
96e93db17a143ff560f92d94b68ce1e76f79db7902Alex Sakhartchouk    public void updateTextures() {
97e93db17a143ff560f92d94b68ce1e76f79db7902Alex Sakhartchouk        RenderScriptGL rs = SceneManager.getRS();
98e93db17a143ff560f92d94b68ce1e76f79db7902Alex Sakhartchouk        Resources res = SceneManager.getRes();
99e93db17a143ff560f92d94b68ce1e76f79db7902Alex Sakhartchouk        if (rs == null || res == null) {
100e93db17a143ff560f92d94b68ce1e76f79db7902Alex Sakhartchouk            return;
101e93db17a143ff560f92d94b68ce1e76f79db7902Alex Sakhartchouk        }
10299b93819f12f18b8559f702d7a303c31fe05205aAlex Sakhartchouk        int shaderTextureStart = mTextureTypes.size();
10399b93819f12f18b8559f702d7a303c31fe05205aAlex Sakhartchouk        for (int i = 0; i < mShaderTextureNames.size(); i ++) {
10499b93819f12f18b8559f702d7a303c31fe05205aAlex Sakhartchouk            ShaderParam sp = mSourceParams.get(mShaderTextureNames.get(i));
10599b93819f12f18b8559f702d7a303c31fe05205aAlex Sakhartchouk            if (sp != null && sp instanceof TextureParam) {
10699b93819f12f18b8559f702d7a303c31fe05205aAlex Sakhartchouk                TextureParam p = (TextureParam)sp;
1075de922962a2fa06267f3ad26f75e3a8083af906cAlex Sakhartchouk                TextureBase tex = p.getTexture();
1085de922962a2fa06267f3ad26f75e3a8083af906cAlex Sakhartchouk                if (tex != null) {
1095de922962a2fa06267f3ad26f75e3a8083af906cAlex Sakhartchouk                    mProgram.bindTexture(tex.getRsData(), shaderTextureStart + i);
1105de922962a2fa06267f3ad26f75e3a8083af906cAlex Sakhartchouk                }
11199b93819f12f18b8559f702d7a303c31fe05205aAlex Sakhartchouk            }
11299b93819f12f18b8559f702d7a303c31fe05205aAlex Sakhartchouk        }
11399b93819f12f18b8559f702d7a303c31fe05205aAlex Sakhartchouk    }
11499b93819f12f18b8559f702d7a303c31fe05205aAlex Sakhartchouk
115e93db17a143ff560f92d94b68ce1e76f79db7902Alex Sakhartchouk    ScriptField_FragmentShader_s getRSData() {
1164fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk        if (mField != null) {
1174fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk            return mField;
1184fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk        }
1194fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk
120e93db17a143ff560f92d94b68ce1e76f79db7902Alex Sakhartchouk        RenderScriptGL rs = SceneManager.getRS();
121e93db17a143ff560f92d94b68ce1e76f79db7902Alex Sakhartchouk        Resources res = SceneManager.getRes();
122e93db17a143ff560f92d94b68ce1e76f79db7902Alex Sakhartchouk        if (rs == null || res == null) {
123e93db17a143ff560f92d94b68ce1e76f79db7902Alex Sakhartchouk            return null;
124e93db17a143ff560f92d94b68ce1e76f79db7902Alex Sakhartchouk        }
125e93db17a143ff560f92d94b68ce1e76f79db7902Alex Sakhartchouk
1264fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk        ScriptField_FragmentShader_s.Item item = new ScriptField_FragmentShader_s.Item();
1274fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk        item.program = mProgram;
1284fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk
129e93db17a143ff560f92d94b68ce1e76f79db7902Alex Sakhartchouk        linkConstants(rs);
1304fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk        if (mPerShaderConstants != null) {
1314fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk            item.shaderConst = mConstantBuffer;
1320c9523357f48a26c8214ccff0b0d95c6927ac0d3Alex Sakhartchouk            item.shaderConstParams = mConstantBufferParams.getAllocation();
1334fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk            mProgram.bindConstants(item.shaderConst, 0);
1344fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk        }
1354fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk
1364fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk        item.objectConstIndex = -1;
1374fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk        if (mPerObjConstants != null) {
1384fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk            item.objectConstIndex = mPerShaderConstants != null ? 1 : 0;
1394fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk        }
1404fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk
1414fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk        mField = new ScriptField_FragmentShader_s(rs, 1);
1424fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk        mField.set(item, 0, true);
1434fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk        return mField;
1444fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk    }
1454fd35d8f49dbed174828da60b70c37e7a77a0d13Alex Sakhartchouk}
146