Project

General

Profile

« Previous | Next » 

Revision 0d81d0fb

Added by Leszek Koltunski almost 8 years ago

Separable Box blur (almost) works.

View differences:

src/main/java/org/distorted/library/EffectQueuePostprocess.java
42 42

  
43 43
class EffectQueuePostprocess extends EffectQueue
44 44
  {
45
  private static final int MAX_BLUR = 50;
46

  
45 47
  private static final int POSITION_DATA_SIZE= 2; // Post Program: size of the position data in elements
46 48
  private static final int TEX_DATA_SIZE     = 2; // Post Program: size of the texture coordinate data in elements.
47 49

  
......
49 51
  private static final int NUM_CACHE    = 0;
50 52
  private static final int INDEX = EffectTypes.POSTPROCESS.ordinal();
51 53

  
52
  private static int mRadiusH;
53
  private static int mOneOverH;
54
  private static int mObjDH;
55
  private static int mMVPMatrixH;
56

  
57
  private static final FloatBuffer mQuadPositions, mQuadTexture;
58
  private static DistortedProgram mBlurProgram;
54
  private static final FloatBuffer mQuadPositions, mQuadTexture1, mQuadTexture2;
59 55

  
60 56
  static
61 57
    {
......
63 59
    int bytes_per_float = 4;
64 60

  
65 61
    float[] positionData= { -0.5f, -0.5f,  -0.5f, 0.5f,  0.5f,-0.5f,  0.5f, 0.5f };
66
    float[] textureData = {  0.0f,  0.0f,   0.0f, 1.0f,  1.0f, 0.0f,  1.0f, 1.0f };
62
    float[] textureData1= {  0.0f,  0.0f,   0.0f, 1.0f,  1.0f, 0.0f,  1.0f, 1.0f };
63
    float[] textureData2= {  0.0f,  0.0f,   1.0f, 0.0f,  0.0f, 1.0f,  1.0f, 1.0f };
67 64

  
68 65
    mQuadPositions = ByteBuffer.allocateDirect(POSITION_DATA_SIZE*dataLength*bytes_per_float).order(ByteOrder.nativeOrder()).asFloatBuffer();
69 66
    mQuadPositions.put(positionData).position(0);
70
    mQuadTexture   = ByteBuffer.allocateDirect(TEX_DATA_SIZE     *dataLength*bytes_per_float).order(ByteOrder.nativeOrder()).asFloatBuffer();
71
    mQuadTexture.put(textureData).position(0);
67
    mQuadTexture1  = ByteBuffer.allocateDirect(TEX_DATA_SIZE     *dataLength*bytes_per_float).order(ByteOrder.nativeOrder()).asFloatBuffer();
68
    mQuadTexture1.put(textureData1).position(0);
69
    mQuadTexture2  = ByteBuffer.allocateDirect(TEX_DATA_SIZE     *dataLength*bytes_per_float).order(ByteOrder.nativeOrder()).asFloatBuffer();
70
    mQuadTexture2.put(textureData2).position(0);
72 71
    }
73 72

  
73
  private static DistortedFramebuffer mBufferFBO = new DistortedFramebuffer(1,1);
74

  
75
  // BLUR effect
76
  private static DistortedProgram mBlurProgram;
77
  private static int mRadiusH,mStepH,mWeightsH,mObjDH,mMVPMatrixH;
78
  private float[] mWeights = new float[MAX_BLUR];
79

  
80
  // another effect ....
81

  
74 82
///////////////////////////////////////////////////////////////////////////////////////////////////
75 83

  
76 84
  EffectQueuePostprocess(long id)
......
86 94
    final InputStream postVertexStream   = resources.openRawResource(R.raw.blur_vertex_shader);
87 95
    final InputStream postFragmentStream = resources.openRawResource(R.raw.blur_fragment_shader);
88 96

  
89
    mBlurProgram = new DistortedProgram(postVertexStream,postFragmentStream, "", "");
97
    mBlurProgram = new DistortedProgram(postVertexStream,postFragmentStream,
98
                                        "#version 100\n",
99
                                        "#version 100\n#define MAX_BLUR "+MAX_BLUR);
90 100

  
91 101
    int blurProgramH = mBlurProgram.getProgramHandle();
92 102
    mRadiusH    = GLES30.glGetUniformLocation( blurProgramH, "u_Radius");
93
    mOneOverH   = GLES30.glGetUniformLocation( blurProgramH, "one_over_objD");
103
    mStepH      = GLES30.glGetUniformLocation( blurProgramH, "u_Step");
104
    mWeightsH   = GLES30.glGetUniformLocation( blurProgramH, "u_Weights");
94 105
    mObjDH      = GLES30.glGetUniformLocation( blurProgramH, "u_objD");
95 106
    mMVPMatrixH = GLES30.glGetUniformLocation( blurProgramH, "u_MVPMatrix");
96 107
    }
......
146 157
  synchronized void render(float w, float h, float[] mvp, DistortedFramebuffer df)
147 158
    {
148 159
    mBlurProgram.useProgram();
149
    df.setAsOutput();
150 160

  
151
    GLES30.glUniform1f( mRadiusH, mUniforms[0]);
152
    GLES30.glUniform2f( mOneOverH, 1/w,1/h);
161
    int radius = (int)mUniforms[0];
162
    if( radius>=MAX_BLUR ) radius = MAX_BLUR-1;
163

  
164
    for(int i=0; i<=radius; i++)
165
      {
166
      mWeights[i] = 1.0f / (2.0f*radius+1.0f);
167
      }
168

  
169
    GLES30.glUniform1fv( mWeightsH, radius+1, mWeights,0);
170
    GLES30.glUniform1i( mRadiusH, radius);
153 171
    GLES30.glUniform2f( mObjDH , w, h );
154 172
    GLES30.glUniformMatrix4fv(mMVPMatrixH, 1, false, mvp , 0);
155 173

  
174
    mBufferFBO.resizeFast(df.mWidth, df.mHeight);
175
    mBufferFBO.setAsOutput();
176

  
177
    // horizontal blur
178
    GLES30.glUniform1f( mStepH , 1/h );
179
    GLES30.glVertexAttribPointer(mBlurProgram.mAttribute[0], POSITION_DATA_SIZE, GLES30.GL_FLOAT, false, 0, mQuadPositions);
180
    GLES30.glVertexAttribPointer(mBlurProgram.mAttribute[1], TEX_DATA_SIZE     , GLES30.GL_FLOAT, false, 0, mQuadTexture2);
181
    GLES30.glDrawArrays(GLES30.GL_TRIANGLE_STRIP, 0, 4);
182

  
183
    mBufferFBO.setAsInput();
184
    df.setAsOutput();
185

  
186
    // vertical blur
187
    GLES30.glUniform1f( mStepH , 1/w );
156 188
    GLES30.glVertexAttribPointer(mBlurProgram.mAttribute[0], POSITION_DATA_SIZE, GLES30.GL_FLOAT, false, 0, mQuadPositions);
157
    GLES30.glVertexAttribPointer(mBlurProgram.mAttribute[1], TEX_DATA_SIZE     , GLES30.GL_FLOAT, false, 0, mQuadTexture);
189
    GLES30.glVertexAttribPointer(mBlurProgram.mAttribute[1], TEX_DATA_SIZE     , GLES30.GL_FLOAT, false, 0, mQuadTexture2);
158 190
    GLES30.glDrawArrays(GLES30.GL_TRIANGLE_STRIP, 0, 4);
159 191
    }
160 192

  
src/main/res/raw/blur_fragment_shader.glsl
21 21

  
22 22
varying vec2 v_TexCoordinate;
23 23
uniform sampler2D u_Texture;
24
uniform vec2 one_over_objD;
25
uniform float u_Radius;
24
uniform float u_Step;
25
uniform float u_Weights[MAX_BLUR];
26
uniform int u_Radius;
26 27

  
27 28
//////////////////////////////////////////////////////////////////////////////////////////////
28 29

  
29 30
void main()
30 31
  {
31
  vec2 tex;
32
  vec4 pixel = vec4(0.0);
33
  float denom = 1.0 / ((2.0*u_Radius+1.0)*(2.0*u_Radius+1.0));
32
  float lCoord = v_TexCoordinate.x;
33
  float rCoord = lCoord;
34
  float yCoord = v_TexCoordinate.y;
34 35

  
35
  for (float x = -u_Radius; x <= u_Radius; x+=1.0)
36
    for (float y = -u_Radius; y <= u_Radius; y+=1.0)
37
      {
38
      tex = vec2(v_TexCoordinate.x + x*one_over_objD.x, v_TexCoordinate.y + y*one_over_objD.y);
39
      pixel += texture2D(u_Texture,tex)*denom;
40
      }
36
  vec4  pixel  = texture2D(u_Texture,vec2(lCoord,yCoord)) * u_Weights[0];
37

  
38
  for (int x = 1; x <= u_Radius; x+=1)
39
    {
40
    rCoord+= u_Step;
41
    lCoord-= u_Step;
42
    pixel += ( texture2D(u_Texture,vec2(rCoord,yCoord)) +
43
               texture2D(u_Texture,vec2(lCoord,yCoord)) ) * u_Weights[x];
44
    }
41 45

  
42 46
  gl_FragColor = pixel;
43 47
  }

Also available in: Unified diff