diff options
author | Winson Chung <winsonc@google.com> | 2011-09-20 18:29:14 -0700 |
---|---|---|
committer | Winson Chung <winsonc@google.com> | 2011-09-22 16:44:17 -0700 |
commit | 1d1672900d5f7625022d4fcc89b36dc3137dcb62 (patch) | |
tree | a409f2d756eea3b51095bf8ce124c7047f8eecc1 /src | |
parent | a467e16e4ae40c1ebba12a93315adbab4226e29e (diff) | |
download | android_packages_wallpapers_PhaseBeam-1d1672900d5f7625022d4fcc89b36dc3137dcb62.tar.gz android_packages_wallpapers_PhaseBeam-1d1672900d5f7625022d4fcc89b36dc3137dcb62.tar.bz2 android_packages_wallpapers_PhaseBeam-1d1672900d5f7625022d4fcc89b36dc3137dcb62.zip |
Adding PhaseBeam wallpaper.
Change-Id: I253ccb8c8af5cf0d4bc362fc4391af4fd7064c86
Diffstat (limited to 'src')
-rw-r--r-- | src/com/android/phasebeam/PhaseBeam.java | 16 | ||||
-rw-r--r-- | src/com/android/phasebeam/PhaseBeamRS.java | 225 | ||||
-rw-r--r-- | src/com/android/phasebeam/PhaseBeamView.java | 42 | ||||
-rw-r--r-- | src/com/android/phasebeam/PhaseBeamWallpaper.java | 114 | ||||
-rw-r--r-- | src/com/android/phasebeam/phasebeam.rs | 140 |
5 files changed, 537 insertions, 0 deletions
diff --git a/src/com/android/phasebeam/PhaseBeam.java b/src/com/android/phasebeam/PhaseBeam.java new file mode 100644 index 0000000..210eec3 --- /dev/null +++ b/src/com/android/phasebeam/PhaseBeam.java @@ -0,0 +1,16 @@ +package com.android.phasebeam; + +import android.app.Activity; +import android.os.Bundle; + +public class PhaseBeam extends Activity { + + private PhaseBeamView mView; + + @Override + public void onCreate(Bundle savedInstanceState) { + super.onCreate(savedInstanceState); + mView = new PhaseBeamView(this); + setContentView(mView); + } +}
\ No newline at end of file diff --git a/src/com/android/phasebeam/PhaseBeamRS.java b/src/com/android/phasebeam/PhaseBeamRS.java new file mode 100644 index 0000000..0bf126d --- /dev/null +++ b/src/com/android/phasebeam/PhaseBeamRS.java @@ -0,0 +1,225 @@ +package com.android.phasebeam; + +import static android.renderscript.Sampler.Value.NEAREST; +import static android.renderscript.Sampler.Value.WRAP; + +import android.content.res.Resources; +import android.renderscript.Allocation; +import android.renderscript.Matrix4f; +import android.renderscript.Mesh; +import android.renderscript.Program; +import android.renderscript.ProgramFragment; +import android.renderscript.ProgramFragmentFixedFunction; +import android.renderscript.ProgramRaster; +import android.renderscript.ProgramStore; +import android.renderscript.ProgramVertex; +import android.renderscript.ProgramVertexFixedFunction; +import android.renderscript.RenderScriptGL; +import android.renderscript.Sampler; +import android.renderscript.ProgramStore.BlendDstFunc; +import android.renderscript.ProgramStore.BlendSrcFunc; + +public class PhaseBeamRS { + + public static final int DOT_COUNT = 18; + private Resources mRes; + private RenderScriptGL mRS; + private ScriptC_phasebeam mScript; + int mHeight; + int mWidth; + + private ScriptField_VpConsts mPvConsts; + private Allocation dotAllocation; + private Allocation beamAllocation; + private Allocation bgAllocation; + + private ScriptField_Particle dotParticles; + private Mesh dotMesh; + + private ScriptField_Particle beamParticles; + private Mesh beamMesh; + + private int densityDPI; + + boolean inited = false; + + public void init(int dpi, RenderScriptGL rs, Resources res, int width, int height) { + if (!inited) { + densityDPI = dpi; + + mRS = rs; + mRes = res; + + mWidth = width; + mHeight = height; + + dotParticles = new ScriptField_Particle(mRS, DOT_COUNT); + Mesh.AllocationBuilder smb2 = new Mesh.AllocationBuilder(mRS); + smb2.addVertexAllocation(dotParticles.getAllocation()); + smb2.addIndexSetType(Mesh.Primitive.POINT); + dotMesh = smb2.create(); + + beamParticles = new ScriptField_Particle(mRS, DOT_COUNT); + Mesh.AllocationBuilder smb3 = new Mesh.AllocationBuilder(mRS); + smb3.addVertexAllocation(beamParticles.getAllocation()); + smb3.addIndexSetType(Mesh.Primitive.POINT); + beamMesh = smb3.create(); + + mScript = new ScriptC_phasebeam(mRS, mRes, R.raw.phasebeam); + mScript.set_dotMesh(dotMesh); + mScript.set_beamMesh(beamMesh); + mScript.bind_dotParticles(dotParticles); + mScript.bind_beamParticles(beamParticles); + + mPvConsts = new ScriptField_VpConsts(mRS, 1); + + createProgramVertex(); + createProgramRaster(); + createProgramFragmentStore(); + createProgramFragment(); + loadTextures(); + + mScript.set_densityDPI(densityDPI); + + mRS.bindRootScript(mScript); + + mScript.invoke_positionParticles(); + inited = true; + } + } + + private Matrix4f getProjectionNormalized(int w, int h) { + // range -1,1 in the narrow axis at z = 0. + Matrix4f m1 = new Matrix4f(); + Matrix4f m2 = new Matrix4f(); + + if (w > h) { + float aspect = ((float) w) / h; + m1.loadFrustum(-aspect, aspect, -1, 1, 1, 100); + } else { + float aspect = ((float) h) / w; + m1.loadFrustum(-1, 1, -aspect, aspect, 1, 100); + } + + m2.loadRotate(180, 0, 1, 0); + m1.loadMultiply(m1, m2); + + m2.loadScale(-1, 1, 1); + m1.loadMultiply(m1, m2); + + m2.loadTranslate(0, 0, 1); + m1.loadMultiply(m1, m2); + return m1; + } + + private void updateProjectionMatrices() { + Matrix4f projNorm = getProjectionNormalized(mWidth, mHeight); + ScriptField_VpConsts.Item i = new ScriptField_VpConsts.Item(); + i.MVP = projNorm; + i.scaleSize = densityDPI / 240.0f; + mPvConsts.set(i, 0, true); + } + + private Allocation loadTexture(int id) { + final Allocation allocation = Allocation.createFromBitmapResource(mRS, mRes, id); + return allocation; + } + + private void loadTextures() { + dotAllocation = loadTexture(R.drawable.dot); + beamAllocation = loadTexture(R.drawable.beam); + bgAllocation = loadTexture(R.drawable.bg); + mScript.set_textureDot(dotAllocation); + mScript.set_textureBeam(beamAllocation); + mScript.set_textureBg(bgAllocation); + } + + private void createProgramVertex() { + ProgramVertexFixedFunction.Constants mPvOrthoAlloc = + new ProgramVertexFixedFunction.Constants(mRS); + Matrix4f proj = new Matrix4f(); + proj.loadOrthoWindow(mWidth, mHeight); + mPvOrthoAlloc.setProjection(proj); + ProgramVertexFixedFunction.Builder pvb = new ProgramVertexFixedFunction.Builder(mRS); + ProgramVertex pv = pvb.create(); + ((ProgramVertexFixedFunction) pv).bindConstants(mPvOrthoAlloc); + mScript.set_vertBg(pv); + + updateProjectionMatrices(); + + ProgramVertex.Builder builder = new ProgramVertex.Builder(mRS); + builder.setShader(mRes, R.raw.dot_vs); + builder.addConstant(mPvConsts.getType()); + builder.addInput(dotMesh.getVertexAllocation(0).getType().getElement()); + ProgramVertex pvs = builder.create(); + pvs.bindConstants(mPvConsts.getAllocation(), 0); + mRS.bindProgramVertex(pvs); + mScript.set_vertDots(pvs); + + } + + private void createProgramFragment() { + Sampler.Builder samplerBuilder = new Sampler.Builder(mRS); + samplerBuilder.setMinification(NEAREST); + samplerBuilder.setMagnification(NEAREST); + samplerBuilder.setWrapS(WRAP); + samplerBuilder.setWrapT(WRAP); + Sampler sn = samplerBuilder.create(); + ProgramFragmentFixedFunction.Builder builderff = + new ProgramFragmentFixedFunction.Builder(mRS); + builderff = new ProgramFragmentFixedFunction.Builder(mRS); + builderff.setTexture(ProgramFragmentFixedFunction.Builder.EnvMode.REPLACE, + ProgramFragmentFixedFunction.Builder.Format.RGB, 0); + ProgramFragment pfff = builderff.create(); + mScript.set_fragBg(pfff); + pfff.bindSampler(sn, 0); + + ProgramFragment.Builder builder = new ProgramFragment.Builder(mRS); + builder.setShader(mRes, R.raw.dot_fs); + builder.addTexture(Program.TextureType.TEXTURE_2D); + ProgramFragment pf = builder.create(); + pf.bindSampler(Sampler.CLAMP_LINEAR(mRS), 0); + mScript.set_fragDots(pf); + + } + + private void createProgramRaster() { + ProgramRaster.Builder builder = new ProgramRaster.Builder(mRS); + builder.setPointSpriteEnabled(true); + ProgramRaster pr = builder.create(); + mRS.bindProgramRaster(pr); + } + + private void createProgramFragmentStore() { + ProgramStore.Builder builder = new ProgramStore.Builder(mRS); + builder.setBlendFunc(BlendSrcFunc.SRC_ALPHA, BlendDstFunc.ONE); + mRS.bindProgramStore(builder.create()); + } + + public void start() { + mRS.bindRootScript(mScript); + } + + public void stop() { + mRS.bindRootScript(null); + } + + public void setOffset(float xOffset, float yOffset, int xPixels, int yPixels) { + mScript.set_xOffset(xOffset); + } + + public void resize(int w, int h) { + // why do i need to do this again when surface changed for wallpaper, but not when as an app? + ProgramVertexFixedFunction.Constants mPvOrthoAlloc = + new ProgramVertexFixedFunction.Constants(mRS); + Matrix4f proj = new Matrix4f(); + proj.loadOrthoWindow(w, h); + mPvOrthoAlloc.setProjection(proj); + + ProgramVertexFixedFunction.Builder pvb = new ProgramVertexFixedFunction.Builder(mRS); + ProgramVertex pv = pvb.create(); + ((ProgramVertexFixedFunction) pv).bindConstants(mPvOrthoAlloc); + mScript.set_vertBg(pv); + } + +} diff --git a/src/com/android/phasebeam/PhaseBeamView.java b/src/com/android/phasebeam/PhaseBeamView.java new file mode 100644 index 0000000..e88a0b1 --- /dev/null +++ b/src/com/android/phasebeam/PhaseBeamView.java @@ -0,0 +1,42 @@ +package com.android.phasebeam; + +import android.content.Context; +import android.renderscript.RSSurfaceView; +import android.renderscript.RenderScriptGL; +import android.view.SurfaceHolder; + +public class PhaseBeamView extends RSSurfaceView { + + private RenderScriptGL mRS; + private PhaseBeamRS mRender; + + public PhaseBeamView(Context context) { + super(context); + setFocusable(true); + setFocusableInTouchMode(true); + } + + public void surfaceChanged(SurfaceHolder holder, int format, int w, int h) { + super.surfaceChanged(holder, format, w, h); + + if (mRS == null) { + RenderScriptGL.SurfaceConfig sc = new RenderScriptGL.SurfaceConfig(); + mRS = createRenderScriptGL(sc); + mRS.setSurface(holder, w, h); + + mRender = new PhaseBeamRS(); + mRender.init(240, mRS, getResources(), w, h); + } + + } + + @Override + protected void onDetachedFromWindow() { + if (mRS != null) { + mRS.setSurface(null, 0, 0); + mRS = null; + destroyRenderScriptGL(); + } + } + +} diff --git a/src/com/android/phasebeam/PhaseBeamWallpaper.java b/src/com/android/phasebeam/PhaseBeamWallpaper.java new file mode 100644 index 0000000..6b291e7 --- /dev/null +++ b/src/com/android/phasebeam/PhaseBeamWallpaper.java @@ -0,0 +1,114 @@ +package com.android.phasebeam; + +import android.app.Service; +import android.graphics.PixelFormat; +import android.os.Bundle; +import android.renderscript.RenderScript; +import android.renderscript.RenderScriptGL; +import android.service.wallpaper.WallpaperService; +import android.util.DisplayMetrics; +import android.view.SurfaceHolder; +import android.view.WindowManager; + +public class PhaseBeamWallpaper extends WallpaperService { + + @Override + public Engine onCreateEngine() { + return new RenderScriptEngine(); + } + + private class RenderScriptEngine extends Engine { + private RenderScriptGL mRenderScript = null; + private PhaseBeamRS mWallpaperRS = null; + private int densityDPI; + + @Override + public void onCreate(SurfaceHolder surfaceHolder) { + super.onCreate(surfaceHolder); + setTouchEventsEnabled(true); + surfaceHolder.setSizeFromLayout(); + surfaceHolder.setFormat(PixelFormat.RGB_332); + + DisplayMetrics metrics = new DisplayMetrics(); + ((WindowManager) getApplication().getSystemService(Service.WINDOW_SERVICE)) + .getDefaultDisplay().getMetrics(metrics); + densityDPI = metrics.densityDpi; + } + + @Override + public void onDestroy() { + super.onDestroy(); + destroyRenderer(); + } + + public void destroyRenderer() { + if (mWallpaperRS != null) { + mWallpaperRS.stop(); + mWallpaperRS = null; + } + + if (mRenderScript != null) { + mRenderScript.setSurface(null, 0, 0); + mRenderScript.destroy(); + mRenderScript = null; + } + } + + @Override + public void onSurfaceCreated(SurfaceHolder surfaceHolder) { + super.onSurfaceCreated(surfaceHolder); + + RenderScriptGL.SurfaceConfig sc = new RenderScriptGL.SurfaceConfig(); + mRenderScript = new RenderScriptGL(PhaseBeamWallpaper.this, sc); + mRenderScript.setPriority(RenderScript.Priority.NORMAL); + } + + @Override + public void onSurfaceDestroyed(SurfaceHolder surfaceHolder) { + super.onSurfaceDestroyed(surfaceHolder); + destroyRenderer(); + } + + @Override + public void onSurfaceChanged(SurfaceHolder surfaceHolder, int format, int width, + int height) { + super.onSurfaceChanged(surfaceHolder, format, width, height); + + if (mRenderScript != null) { + mRenderScript.setSurface(surfaceHolder, width, height); + } + + if (mWallpaperRS == null) { + mWallpaperRS = new PhaseBeamRS(); + mWallpaperRS.init(densityDPI, mRenderScript, getResources(), width, height); + mWallpaperRS.start(); + } + + mWallpaperRS.resize(width, height); + } + + @Override + public Bundle onCommand(String action, int x, int y, int z, Bundle extras, + boolean resultRequested) { + return null; + } + + @Override + public void onVisibilityChanged(boolean visible) { + super.onVisibilityChanged(visible); + if (mWallpaperRS != null) { + if (visible) { + mWallpaperRS.start(); + } else { + mWallpaperRS.stop(); + } + } + } + + @Override + public void onOffsetsChanged(float xOffset, float yOffset, float xOffsetStep, + float yOffsetStep, int xPixelOffset, int yPixelOffset) { + mWallpaperRS.setOffset(xOffset, yOffset, xPixelOffset, yPixelOffset); + } + } +}
\ No newline at end of file diff --git a/src/com/android/phasebeam/phasebeam.rs b/src/com/android/phasebeam/phasebeam.rs new file mode 100644 index 0000000..c7dd513 --- /dev/null +++ b/src/com/android/phasebeam/phasebeam.rs @@ -0,0 +1,140 @@ +#pragma version(1) + +#pragma rs java_package_name(com.android.phasebeam) + +#include "rs_graphics.rsh" +#pragma stateVertex(parent); +#pragma stateStore(parent); + +rs_allocation textureDot; +rs_allocation textureBeam; +rs_allocation textureBg; + +rs_program_vertex vertBg; +rs_program_fragment fragBg; + +rs_program_vertex vertDots; +rs_program_fragment fragDots; + +int numBeamParticles; +int numDotParticles; + +typedef struct __attribute__((packed, aligned(4))) Particle { + float3 position; + float offsetX; +} Particle_t; + +typedef struct VpConsts { + rs_matrix4x4 MVP; + float scaleSize; +} VpConsts_t; +VpConsts_t *vpConstants; + +Particle_t *dotParticles; +Particle_t *beamParticles; +rs_mesh dotMesh; +rs_mesh beamMesh; + +float densityDPI; +float xOffset = 0.5; + +float screenWidth; +float screenHeight; +float halfScreenWidth; +float quarterScreenWidth; + +float newOffset = 0.5; + +void positionParticles(){ + screenWidth = rsgGetWidth(); + screenHeight = rsgGetHeight(); + halfScreenWidth = screenWidth/2.0f; + quarterScreenWidth = screenWidth/4.0f; + + Particle_t* particle = dotParticles; + numDotParticles = rsAllocationGetDimX(rsGetAllocation(dotParticles)); + for(int i=0; i<numDotParticles; i++){ + particle->position.x = rsRand(0.0f, 3.0f); + particle->position.y = rsRand(-1.25f, 1.25f); + + float z; + if(i < 2){ + z = 14.0f; + } if(i < 3){ + z = 25.0f; + } else if(i < 4){ + z = rsRand(10.f, 20.f); + } else if(i == 5){ + z = 24.0f; + particle->position.x = 1.0; + } else { + z = rsRand(4.0f, 10.0f); + } + particle->position.z = z; + particle->offsetX = 0; + + particle++; + } + + Particle_t* beam = beamParticles; + numBeamParticles = rsAllocationGetDimX(rsGetAllocation(beamParticles)); + for(int i=0; i<numBeamParticles; i++){ + float z; + if(i < 10){ + z = rsRand(4.0f, 10.0f)/2.0f; + } else { + z = rsRand(4.0f, 35.0f)/2.0f; + } + beamParticles->position.x = rsRand(-1.25f, 1.25f); + beamParticles->position.y = rsRand(-1.05f, 1.205f); + + beamParticles->position.z = z; + beamParticles->offsetX = 0; + beamParticles++; + } +} + +int root(){ + + rsgClearColor(0.0f, 0.f, 0.f,1.0f); + + rsgBindProgramVertex(vertBg); + rsgBindProgramFragment(fragBg); + rsgBindTexture(fragBg, 0, textureBg); + rsgDrawRect(-quarterScreenWidth + xOffset*quarterScreenWidth, 0.0f, + screenWidth+halfScreenWidth + xOffset*quarterScreenWidth, screenHeight, 0.0f); + + Particle_t* beam = beamParticles; + Particle_t* particle = dotParticles; + newOffset = xOffset*2; + for(int i=0; i<numDotParticles; i++){ + if(beam->position.y > 1.05){ + beam->position.y = -1.05; + } else { + beam->position.y = beam->position.y + 0.000160*beam->position.z; + } + + beam->offsetX = newOffset; + beam++; + + if(particle->position.y > 1.25){ + particle->position.y = -1.25; + } else { + particle->position.y = particle->position.y + 0.00022*particle->position.z; + } + + particle->offsetX = newOffset; + particle++; + } + + rsgBindProgramVertex(vertDots); + rsgBindProgramFragment(fragDots); + + rsgBindTexture(fragDots, 0, textureBeam); + rsgDrawMesh(beamMesh); + + rsgBindTexture(fragDots, 0, textureDot); + rsgDrawMesh(dotMesh); + + return 45; +} |