/** Unbinds the texture from an OpenGL texturing target. */ public void unbindTextures() { int num = mTextureList.size(); if (mPlugins != null) for (IMaterialPlugin plugin : mPlugins) plugin.unbindTextures(); for (int i = 0; i < num; i++) { ATexture texture = mTextureList.get(i); GLES20.glBindTexture(texture.getGLTextureType(), 0); } GLES20.glBindBuffer(GLES20.GL_ARRAY_BUFFER, 0); }
/** * Binds the textures to an OpenGL texturing target. Called every frame by {@link * RajawaliScene#render(double, rajawali.renderer.RenderTarget)}. Shouldn't be called manually. */ public void bindTextures() { int num = mTextureList.size(); for (int i = 0; i < num; i++) { ATexture texture = mTextureList.get(i); bindTextureByName(texture.getTextureName(), i, texture); GLES20.glActiveTexture(GLES20.GL_TEXTURE0 + i); GLES20.glBindTexture(texture.getGLTextureType(), texture.getTextureId()); GLES20.glUniform1i(GLES20.glGetUniformLocation(mProgramHandle, texture.getTextureName()), i); } if (mPlugins != null) for (IMaterialPlugin plugin : mPlugins) plugin.bindTextures(num); }
/** * Sets the OpenGL texture handles for a newly added texture. * * @param texture */ private void setTextureParameters(ATexture texture) { if (texture.getUniformHandle() > -1) return; int textureHandle = GLES20.glGetUniformLocation(mProgramHandle, texture.getTextureName()); if (textureHandle == -1) { RajLog.d( "Could not get attrib location for " + texture.getTextureName() + ", " + texture.getTextureType()); } texture.setUniformHandle(textureHandle); }
@Override public void main() { super.main(); RVec4 color = (RVec4) getGlobal(DefaultShaderVar.G_COLOR); RVec2 textureCoord = (RVec2) getGlobal(DefaultShaderVar.G_TEXTURE_COORD); RVec4 texColor = new RVec4("texColor"); for (int i = 0; i < mTextures.size(); i++) { ATexture texture = mTextures.get(i); if (texture.offsetEnabled()) textureCoord.assignAdd(getGlobal(DefaultShaderVar.U_OFFSET, i)); if (texture.getWrapType() == WrapType.REPEAT) textureCoord.assignMultiply(getGlobal(DefaultShaderVar.U_REPEAT, i)); if (texture.getTextureType() == TextureType.VIDEO_TEXTURE) texColor.assign(texture2D(muVideoTextures[i], textureCoord)); else texColor.assign(texture2D(muTextures[i], textureCoord)); texColor.assignMultiply(muInfluence[i]); color.assignAdd(texColor); } }
/** * Adds a texture to this material. Throws and error if the maximum number of textures was * reached. * * @param texture * @throws TextureException */ public void addTexture(ATexture texture) throws TextureException { if (mTextureList.indexOf(texture) > -1) return; if (mTextureList.size() + 1 > mMaxTextures) { throw new TextureException( "Maximum number of textures for this material has been reached. Maximum number of textures is " + mMaxTextures + "."); } mTextureList.add(texture); TextureManager.getInstance().addTexture(texture); texture.registerMaterial(this); mIsDirty = true; }
/** * Copies every property from another ATexture object * * @param other another ATexture object to copy from */ public void setFrom(ATexture other) { mTextureId = other.getTextureId(); mUniformHandle = other.getUniformHandle(); mWidth = other.getWidth(); mHeight = other.getHeight(); mBitmapFormat = other.getBitmapFormat(); mMipmap = other.isMipmap(); mShouldRecycle = other.willRecycle(); mTextureName = other.getTextureName(); mTextureType = other.getTextureType(); mWrapType = other.getWrapType(); mFilterType = other.getFilterType(); mBitmapConfig = other.getBitmapConfig(); mCompressedTexture = other.getCompressedTexture(); mGLTextureType = other.getGLTextureType(); }
/** * Removes a texture from this material. * * @param texture */ public void removeTexture(ATexture texture) { mTextureList.remove(texture); texture.unregisterMaterial(this); }
public void bindTextureByName(String name, int index, ATexture texture) { GLES20.glActiveTexture(GLES20.GL_TEXTURE0 + index); GLES20.glBindTexture(texture.getGLTextureType(), texture.getTextureId()); GLES20.glUniform1i(GLES20.glGetUniformLocation(mProgramHandle, name), index); }
/** * Takes all material parameters and creates the vertex shader and fragment shader and then * compiles the program. This method should only be called on initialization or when parameters * have changed. */ private void createShaders() { if (!mIsDirty) return; if (mCustomVertexShader == null && mCustomFragmentShader == null) { // // -- Check textures // List<ATexture> diffuseTextures = null; List<ATexture> normalMapTextures = null; List<ATexture> envMapTextures = null; List<ATexture> skyTextures = null; List<ATexture> specMapTextures = null; List<ATexture> alphaMapTextures = null; boolean hasCubeMaps = false; boolean hasVideoTexture = false; for (int i = 0; i < mTextureList.size(); i++) { ATexture texture = mTextureList.get(i); switch (texture.getTextureType()) { case VIDEO_TEXTURE: hasVideoTexture = true; // no break statement, add the video texture to the diffuse textures case DIFFUSE: case RENDER_TARGET: if (diffuseTextures == null) diffuseTextures = new ArrayList<ATexture>(); diffuseTextures.add(texture); break; case NORMAL: if (normalMapTextures == null) normalMapTextures = new ArrayList<ATexture>(); normalMapTextures.add(texture); break; case CUBE_MAP: hasCubeMaps = true; case SPHERE_MAP: boolean isSkyTexture = false; boolean isEnvironmentTexture = false; if (texture.getClass() == SphereMapTexture.class) { isSkyTexture = ((SphereMapTexture) texture).isSkyTexture(); isEnvironmentTexture = ((SphereMapTexture) texture).isEnvironmentTexture(); } else if (texture.getClass() == CubeMapTexture.class) { isSkyTexture = ((CubeMapTexture) texture).isSkyTexture(); isEnvironmentTexture = ((CubeMapTexture) texture).isEnvironmentTexture(); } if (isSkyTexture) { if (skyTextures == null) skyTextures = new ArrayList<ATexture>(); skyTextures.add(texture); } else if (isEnvironmentTexture) { if (envMapTextures == null) envMapTextures = new ArrayList<ATexture>(); envMapTextures.add(texture); } break; case SPECULAR: if (specMapTextures == null) specMapTextures = new ArrayList<ATexture>(); specMapTextures.add(texture); break; case ALPHA: if (alphaMapTextures == null) alphaMapTextures = new ArrayList<ATexture>(); alphaMapTextures.add(texture); break; default: break; } } mVertexShader = new VertexShader(); mVertexShader.enableTime(mTimeEnabled); mVertexShader.hasCubeMaps(hasCubeMaps); mVertexShader.useVertexColors(mUseVertexColors); mVertexShader.initialize(); mFragmentShader = new FragmentShader(); mFragmentShader.enableTime(mTimeEnabled); mFragmentShader.hasCubeMaps(hasCubeMaps); mFragmentShader.initialize(); if (diffuseTextures != null && diffuseTextures.size() > 0) { DiffuseTextureFragmentShaderFragment fragment = new DiffuseTextureFragmentShaderFragment(diffuseTextures); mFragmentShader.addShaderFragment(fragment); } if (normalMapTextures != null && normalMapTextures.size() > 0) { NormalMapFragmentShaderFragment fragment = new NormalMapFragmentShaderFragment(normalMapTextures); mFragmentShader.addShaderFragment(fragment); } if (envMapTextures != null && envMapTextures.size() > 0) { EnvironmentMapFragmentShaderFragment fragment = new EnvironmentMapFragmentShaderFragment(envMapTextures); mFragmentShader.addShaderFragment(fragment); } if (skyTextures != null && skyTextures.size() > 0) { SkyTextureFragmentShaderFragment fragment = new SkyTextureFragmentShaderFragment(skyTextures); mFragmentShader.addShaderFragment(fragment); } if (hasVideoTexture) mFragmentShader.addPreprocessorDirective("#extension GL_OES_EGL_image_external : require"); checkForPlugins(PluginInsertLocation.PRE_LIGHTING); // // -- Lighting // if (mLightingEnabled && mLights != null && mLights.size() > 0) { mVertexShader.setLights(mLights); mFragmentShader.setLights(mLights); mLightsVertexShaderFragment = new LightsVertexShaderFragment(mLights); mLightsVertexShaderFragment.setAmbientColor(mAmbientColor); mLightsVertexShaderFragment.setAmbientIntensity(mAmbientIntensity); mVertexShader.addShaderFragment(mLightsVertexShaderFragment); mFragmentShader.addShaderFragment(new LightsFragmentShaderFragment(mLights)); checkForPlugins(PluginInsertLocation.PRE_DIFFUSE); // // -- Diffuse method // if (mDiffuseMethod != null) { mDiffuseMethod.setLights(mLights); IShaderFragment fragment = mDiffuseMethod.getVertexShaderFragment(); if (fragment != null) mVertexShader.addShaderFragment(fragment); fragment = mDiffuseMethod.getFragmentShaderFragment(); mFragmentShader.addShaderFragment(fragment); } checkForPlugins(PluginInsertLocation.PRE_SPECULAR); // // -- Specular method // if (mSpecularMethod != null) { mSpecularMethod.setLights(mLights); mSpecularMethod.setTextures(specMapTextures); IShaderFragment fragment = mSpecularMethod.getVertexShaderFragment(); if (fragment != null) mVertexShader.addShaderFragment(fragment); fragment = mSpecularMethod.getFragmentShaderFragment(); if (fragment != null) mFragmentShader.addShaderFragment(fragment); } } checkForPlugins(PluginInsertLocation.PRE_ALPHA); if (alphaMapTextures != null && alphaMapTextures.size() > 0) { AlphaMapFragmentShaderFragment fragment = new AlphaMapFragmentShaderFragment(alphaMapTextures); mFragmentShader.addShaderFragment(fragment); } checkForPlugins(PluginInsertLocation.PRE_TRANSFORM); checkForPlugins(PluginInsertLocation.POST_TRANSFORM); mVertexShader.buildShader(); mFragmentShader.buildShader(); } else { mVertexShader = mCustomVertexShader; mFragmentShader = mCustomFragmentShader; if (mVertexShader.needsBuild()) mVertexShader.initialize(); if (mFragmentShader.needsBuild()) mFragmentShader.initialize(); if (mVertexShader.needsBuild()) mVertexShader.buildShader(); if (mFragmentShader.needsBuild()) mFragmentShader.buildShader(); } if (debug) { RajLog.d("-=-=-=- VERTEX SHADER -=-=-=-"); RajLog.d(mVertexShader.getShaderString()); RajLog.d("-=-=-=- FRAGMENT SHADER -=-=-=-"); RajLog.d(mFragmentShader.getShaderString()); } mProgramHandle = createProgram(mVertexShader.getShaderString(), mFragmentShader.getShaderString()); if (mProgramHandle == 0) { mIsDirty = false; return; } mVertexShader.setLocations(mProgramHandle); mFragmentShader.setLocations(mProgramHandle); for (int i = 0; i < mTextureList.size(); i++) { ATexture texture = mTextureList.get(i); setTextureParameters(texture); } mIsDirty = false; }