2013-03-16 61 views
2

我有两个图像饱和滤波器的实现。一个与Java和一个与Renderscript。其实我的nexus 4设备上的渲染速度比较慢,它怎么可能?Renderscript很慢,可以吗?

Java实现:

public final void Saturation(Bitmap canvas, int saturation, boolean accumulate, int imageNumber) 
{ 
    int height = canvas.getHeight(); 
    int width = canvas.getWidth(); 
    int[] pixels = new int[height*width]; 
    int[] resultPixels = new int[height*width]; 
    canvas.getPixels(pixels, 0, width, 0, 0, width, height); 

    if (!accumulate) 
    { 
     for (int i = 0; i < pixels.length; i ++) 
     { 
      int red = Color.red(pixels[i]); 
      int green = Color.green(pixels[i]); 
      int blue = Color.blue(pixels[i]); 

      double t = (double)red * 0.11 + (double)green * 0.59 + (double)blue * 0.3; 
      red = (int)Math.round(Math.min((double)red + (t - (double)red) * saturation/100.0, 255)); 
      green = (int)Math.round(Math.min((double)green + (t - (double)green) * saturation/100.0, 255)); 
      blue = (int)Math.round(Math.min((double)blue + (t - (double)blue) * saturation/100.0, 255)); 

      resultPixels[i] = Color.argb(Color.alpha(pixels[i]), red, green, blue); 
     } 
    } 

    canvas.setPixels(resultPixels, 0, width, 0, 0, width, height); 
} 

的renderScript实现:

Java的一部分:

public static Bitmap saturate(Bitmap bmIn, float saturation, Context context, Resources resources) 
{ 
    Bitmap bmOut = Bitmap.createBitmap(bmIn.getWidth(), bmIn.getHeight(), 
      bmIn.getConfig()); 
    RenderScript rs = RenderScript.create(context); 
    Allocation allocIn; 
    allocIn = Allocation.createFromBitmap(rs, bmIn, 
      Allocation.MipmapControl.MIPMAP_NONE, 
      Allocation.USAGE_SCRIPT); 
    Allocation allocOut = Allocation.createTyped(rs, allocIn.getType()); 
    ScriptC_saturation script = new ScriptC_saturation(rs, resources, 
      R.raw.saturation); 
    script.set_in(allocIn); 
    script.set_out(allocOut); 
    script.set_script(script); 
    script.set_saturation(saturation); 
    script.invoke_filter(); 
    allocOut.copyTo(bmOut); 
    return bmOut; 
} 

的renderScript脚本:

#pragma version(1) 
#pragma rs java_package_name(ca.tutortutor.embossimage) 

rs_allocation out; 
rs_allocation in; 
rs_script script; 
float saturation; 

void root(const uchar4* v_in, uchar4* v_out, const void* usrData, uint32_t x, 
     uint32_t y) 
{ 
    float4 current = rsUnpackColor8888(*v_in); 

    float t = current.r * 0.11f + current.g * 0.59f + current.b * 0.3f; 
    rsDebug("renderscript t = ", t); 
    rsDebug("renderscript red before = ", current.r); 
    current.r = fmin(current.r + (t - current.r) * saturation/100.0f, 1.f); 
    current.g = fmin(current.g + (t - current.g) * saturation/100.0f, 1.f); 
    current.b = fmin(current.b + (t - current.b) * saturation/100.0f, 1.f); 
    rsDebug("renderscript red after = ", current.r); 

    *v_out = rsPackColorTo8888(current.r, current.g, current.b, current.a); 
} 

void filter() 
{ 
    rsDebug("RS_VERSION = ", RS_VERSION); 
    #if !defined(RS_VERSION) || (RS_VERSION < 14) 
     rsForEach(script, in, out, 0); 
    #else 
     rsForEach(script, in, out); 
    #endif 
} 

我认为的renderScript应该睦h比java快,因为它应该使用cpu和本地代码的所有4个核心,甚至可能是android 4.2.2上的gpu核心。

回答

6

我立即可以看到您的Renderscript代码正在使用rsDebug()打印到日志中,这确保了缓慢。尝试删除您的日志代码并再次测量时间。在这种情况下,Nexus 4应该在4个CPU线程上执行。 Nexus 4目前没有GPU支持。

+3

在RS中写了很多图像处理代码,我保证rsDebug是这里的主要元凶。 – 2013-03-19 00:34:47