14cead8034aab0e20e402baee87cbe9129db00192Stephen Hinespackage com.android.rs.refocus.f32;
2de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
3de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
44cead8034aab0e20e402baee87cbe9129db00192Stephen Hinesimport com.android.rs.refocus.BlurStack;
54cead8034aab0e20e402baee87cbe9129db00192Stephen Hinesimport com.android.rs.refocus.KernelDataForRenderScript;
64cead8034aab0e20e402baee87cbe9129db00192Stephen Hinesimport com.android.rs.refocus.LayerInfo;
74cead8034aab0e20e402baee87cbe9129db00192Stephen Hinesimport com.android.rs.refocus.MediaStoreSaver;
84cead8034aab0e20e402baee87cbe9129db00192Stephen Hinesimport com.android.rs.refocus.R;
94cead8034aab0e20e402baee87cbe9129db00192Stephen Hinesimport com.android.rs.refocus.RefocusFilter;
104cead8034aab0e20e402baee87cbe9129db00192Stephen Hinesimport com.android.rs.refocus.renderscript.ScriptC_layered_filter_fast_f32;
11de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
12de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wangimport android.graphics.Bitmap;
13de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wangimport android.support.v8.renderscript.Allocation;
14de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wangimport android.support.v8.renderscript.RenderScript;
15de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wangimport android.support.v8.renderscript.Script;
16de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wangimport android.util.Log;
17de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang/**
18de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang * An accelerated implementation of RefocusFilter using float32 as pixel
19de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang * representation. The corresponding RenderScript class is
20de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang * ScriptC_layered_filter_f32. Integral image is used for the speedup.
21de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang *
22de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang * Example Usage:
23de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang *
24de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang * {@code RenderScript renderScript = RenderScript.create(context);}
25de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang * {@code RefocusFilterF32 rfFilter = new RefocusFilterF32(renderScript);}
26de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang * {@code ProgressCallback progress;}
27de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang * {@code Bitmap result = rfFilter.compute(rgbdImage, blurStack, progress);}
28de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang *
29de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang * @author zhl@google.com (Li Zhang)
30de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang */
31de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wangpublic class RefocusFilterF32 extends
32de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    RefocusFilter<ScriptC_layered_filter_fast_f32> {
33de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  private static final String myTAG = "RefocusFilterF32";
34de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  private static final boolean ENABLE_FAST_FILTER = true;
35de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  private static final float MIN_DISC_RADIUS_FOR_FAST_FILTER = 3;
36de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  boolean useFastFilterForCurrentLayer = false;
37de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  ImageBuffersForRenderScriptF32 buffers;
38de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
39de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  public RefocusFilterF32(RenderScript rs) {
40de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    super(rs);
41de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  }
42de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
43de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  @Override
44de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  protected void initializeScriptAndBuffers(Bitmap inputImage,
45de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang      LayerInfo focalLayer) {
46de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    scriptC = new ScriptC_layered_filter_fast_f32(renderScript);
47de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
48de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    // Allocates, binds, and initializes buffers that interface between Java
49de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    // and Render Script.
50de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    // + 1 is for the boundary case of using integral image.
51de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    KernelDataForRenderScript.setUseNewRS(false);
52de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    int margin = KernelDataForRenderScript.getMaxKernelRadius() + 1;
53de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    buffers = new ImageBuffersForRenderScriptF32(inputImage, margin,
54de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang        renderScript, scriptC);
55de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    buffers.initializeRenderScript(focalLayer, scriptC);
56de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  }
57de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
58de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  @Override
59de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  protected Bitmap extractResultImage() {
60de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    // Extracts the result from .rs file to {@code buffers.outputImage} in Java.
61de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    long startnow;
62de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    long endnow;
63de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    startnow = System.nanoTime();
64de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    scriptC.forEach_PackOutputImage(buffers.outAllocation);
65de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    endnow = System.nanoTime();
66de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    Log.d(myTAG, "PackOutputImage: "+(endnow - startnow)+ " ns" );
67de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
68de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    buffers.outAllocation.copyTo(buffers.outputImage);
69de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    return buffers.outputImage;
70de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  }
71de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
72de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  /*
73de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang   * Utility Method to extract intermediatory result
74de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang   */
75de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  private  void extractSharpImage(String name) {
76de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
77de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    Bitmap mBitmap = Bitmap.createBitmap(buffers.inputImage.getWidth(),
78de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang            buffers.inputImage.getHeight(), Bitmap.Config.ARGB_8888);
79de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    Allocation mAllocation = Allocation.createFromBitmap(renderScript, mBitmap);
80de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    scriptC.forEach_PackSharpImage(mAllocation);
81de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
82de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    mAllocation.copyTo(mBitmap);
83de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    MediaStoreSaver.savePNG(mBitmap, "sharpF32", name, renderScript.getApplicationContext());
84de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  }
85de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  /*
86de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang   * Utility Method to extract intermediatory result
87de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang   */
88de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  private  void extractFuzzyImage(String name) {
89de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
90de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    Bitmap mBitmap = Bitmap.createBitmap(buffers.inputImage.getWidth(),
91de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang            buffers.inputImage.getHeight(), Bitmap.Config.ARGB_8888);
92de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    Allocation mAllocation = Allocation.createFromBitmap(renderScript, mBitmap);
93de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    scriptC.forEach_PackFuzzyImage(mAllocation);
94de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
95de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    mAllocation.copyTo(mBitmap);
96de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    MediaStoreSaver.savePNG(mBitmap, "fuzzyF32", name, renderScript.getApplicationContext());
97de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  }
98de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
99de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  @Override
100de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  protected void setTargetLayer(LayerInfo layerInfo) {
101de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    scriptC.invoke_SetTargetLayer(layerInfo.frontDepth, layerInfo.backDepth);
102de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  }
103de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
104de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  @Override
105de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  protected void setBlendInfo(int dilationRadius) {
106de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    scriptC.invoke_SetBlendInfo(dilationRadius);
107de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  }
108de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
109de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  @Override
110de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  protected void setKernelData(int targetLayer, BlurStack blurStack) {
111de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    KernelDataForRenderScriptF32 kernelData =
112de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang        new KernelDataForRenderScriptF32(targetLayer, blurStack, renderScript);
113de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
114de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    if (ENABLE_FAST_FILTER
115de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang        && kernelData.minDiskRadius > MIN_DISC_RADIUS_FOR_FAST_FILTER) {
116de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang      useFastFilterForCurrentLayer = true;
117de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    } else {
118de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang      useFastFilterForCurrentLayer = false;
119de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    }
120de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
121de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    scriptC.bind_g_kernel_info(kernelData.getKernelInfo());
122de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    scriptC.bind_g_kernel_stack(kernelData.stackAllocation);
123de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  }
124de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
125de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  @Override
126de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  protected void computeLayerMatteBehindFocalDepth() {
127de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    // Marks active pixels (pixels that are on this target layer);
128de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    // Marks adjacent pixels that are close enough to active pixels;
129de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    long startnow;
130de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    long endnow;
131de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    startnow = System.nanoTime();
132de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    scriptC.forEach_MarkLayerMask(buffers.inAllocation);
133de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    endnow = System.nanoTime();
134de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    Log.d(myTAG, "MarkLayerMask: "+(endnow - startnow)+ " ns" );
135de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
136de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    startnow = System.nanoTime();
137de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    scriptC.forEach_ComputeLayerMatteBehindFocalDepth(buffers.inAllocation);
138de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    endnow = System.nanoTime();
139de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    Log.d(myTAG, "ComputeLayerMatteBehindFocalDepth: "+(endnow - startnow)+ " ns" );
140de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  }
141de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
142de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  @Override
143de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  protected void filterLayerBehindFocalDepth() {
144de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    // Filters the target layer and saves the result to {@code g_accum_map} in
145de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    // .rs file.
146de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    long startnow;
147de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    long endnow;
148de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    if (useFastFilterForCurrentLayer) {
149de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang      scriptC.invoke_SetUseIntegralImage(1);
150de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang      Script.LaunchOptions launchOptions = new Script.LaunchOptions();
151de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang      launchOptions.setX(0, 1);
152de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang      launchOptions.setY(0, buffers.inputImage.getHeight());
153de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
154de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang      startnow = System.nanoTime();
155de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang      scriptC.forEach_ComputeIntegralImageForLayerBehindFocalDepth(
156de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang          buffers.inAllocation, launchOptions);
157de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang      endnow = System.nanoTime();
158de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang      Log.d(myTAG, "ComputeIntegralImageForLayerBehindFocalDepth: "+(endnow - startnow)+ " ns" );
159de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    } else {
160de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang      scriptC.invoke_SetUseIntegralImage(0);
161de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    }
162de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
163de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    startnow = System.nanoTime();
164de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    scriptC.forEach_FilterLayerBehindFocalDepth(buffers.inAllocation);
165de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    endnow = System.nanoTime();
166de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    Log.d(myTAG, "FilterLayerBehindFocalDepth: "+(endnow - startnow)+ " ns" );
167de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
168de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    //extractFuzzyImage("fuzzy_behind");
169de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    //extractSharpImage("sharp_behind");
170de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  }
171de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
172de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  @Override
173de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  protected void updateSharpImageUsingFuzzyImage() {
174de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang		// Log the kernel execution time
175de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    long startnow;
176de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    long endnow;
177de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    startnow = System.nanoTime();
178de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    scriptC.forEach_UpdateSharpImageUsingFuzzyImage(buffers.inAllocation);
179de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    endnow = System.nanoTime();
180de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    Log.d(myTAG, "UpdateSharpImageUsingFuzzyImage: "+(endnow - startnow)+ " ns" );
181de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
182de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    //extractSharpImage("sharp_update");
183de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  }
184de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
185de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  @Override
186de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  protected void computeLayerMatteInFrontOfFocalDepth() {
187de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    // Marks active pixels (pixels that are on this target layer);
188de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    // Marks adjacent pixels that are close enough to active pixels;
189de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    long startnow;
190de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    long endnow;
191de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    startnow = System.nanoTime();
192de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    scriptC.forEach_MarkLayerMask(buffers.inAllocation);
193de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    endnow = System.nanoTime();
194de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    Log.d(myTAG, "MarkLayerMask: "+(endnow - startnow)+ " ns" );
195de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
196de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    startnow = System.nanoTime();
197de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    scriptC.forEach_ComputeLayerMatteInFrontOfFocalDepth(buffers.inAllocation);
198de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    endnow = System.nanoTime();
199de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    Log.d(myTAG, "ComputeLayerMatteInFrontOfFocalDepth: "+(endnow - startnow)+ " ns" );
200de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  }
201de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
202de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  @Override
203de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  protected void filterLayerInFrontOfFocalDepth() {
204de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    // Filters the target layer and accumulates the result to {@code
205de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    // g_accum_map} in .rs file.
206de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    long startnow;
207de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    long endnow;
208de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    if (useFastFilterForCurrentLayer) {
209de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang      scriptC.invoke_SetUseIntegralImage(1);
210de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang      Script.LaunchOptions launchOptions = new Script.LaunchOptions();
211de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang      launchOptions.setX(0, 1);
212de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang      launchOptions.setY(0, buffers.inputImage.getHeight());
213de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
214de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang      startnow = System.nanoTime();
215de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang      scriptC.forEach_ComputeIntegralImageForLayerInFrontOfFocalDepth(
216de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang          buffers.inAllocation, launchOptions);
217de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang      endnow = System.nanoTime();
218de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang      Log.d(myTAG, "ComputeIntegralImageForLayerInFrontOfFocalDepth: "+(endnow - startnow)+ " ns" );
219de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    } else {
220de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang      scriptC.invoke_SetUseIntegralImage(0);
221de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    }
222de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    startnow = System.nanoTime();
223de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    scriptC.forEach_FilterLayerInFrontOfFocalDepth(buffers.inAllocation);
224de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    endnow = System.nanoTime();
225de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    Log.d(myTAG, "FilterLayerInFrontOfFocalDepth: "+(endnow - startnow)+ " ns" );
226de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
227de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    //extractFuzzyImage("fuzzy_front");
228de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    //extractSharpImage("sharp_front");
229de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  }
230de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang
231de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  @Override
232de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  protected void finalizeFuzzyImageUsingSharpImage() {
233de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    // Blends {@code g_accum_map} and {@code g_focus_map} in .rs file.
234de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    // Saves the result in {@code g_accum_map}.
235de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    long startnow;
236de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    long endnow;
237de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    startnow = System.nanoTime();
238de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    scriptC.forEach_FinalizeFuzzyImageUsingSharpImage(buffers.inAllocation);
239de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    endnow = System.nanoTime();
240de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang    Log.d(myTAG, "FinalizeFuzzyImageUsingSharpImage: "+(endnow - startnow)+ " ns" );
241de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang  }
242de2f182fdb522689e05280e449a39ec2c1b53e1fCindy Wang}
243