2012-01-06 12 views
7

ガウスぼかしを試してみましたが、stackoverflowのすべての質問をチェックアウトしましたが、私のクラッシュ問題を解決した人はいませんでした。ガウスぼかしアルゴリズム以外の画像をぼかす方法はありますか?私の画像サイズは768x1024であり、ループは2 * 1024 * 768回繰り返され、これは実行可能ではありません。スライダーの変更時にUIImageをぼかしてください

CGContextRef NYXImageCreateARGBBitmapContext(const size_t width, const size_t height, const size_t bytesPerRow) 
{ 
/// Use the generic RGB color space 
/// We avoid the NULL check because CGColorSpaceRelease() NULL check the value anyway, and worst case scenario = fail to create context 
CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB(); 

/// Create the bitmap context, we want pre-multiplied ARGB, 8-bits per component 
CGContextRef bmContext = CGBitmapContextCreate(NULL, width, height, 8/*Bits per component*/, bytesPerRow, colorSpace, kCGBitmapByteOrderDefault | kCGImageAlphaPremultipliedFirst); 

CGColorSpaceRelease(colorSpace); 

return bmContext; 
} 



-(UIImage*)blurredImageUsingGaussFactor:(NSUInteger)gaussFactor andPixelRadius:(NSUInteger)pixelRadius 
{ 
CGImageRef cgImage = self.CGImage; 
const size_t originalWidth = CGImageGetWidth(cgImage); 
const size_t originalHeight = CGImageGetHeight(cgImage); 
const size_t bytesPerRow = originalWidth * 4; 
CGContextRef context = NYXImageCreateARGBBitmapContext(originalWidth, originalHeight, bytesPerRow); 
if (!context) 
    return nil; 

unsigned char *srcData, *destData, *finalData; 

size_t width = CGBitmapContextGetWidth(context); 
size_t height = CGBitmapContextGetHeight(context); 
size_t bpr = CGBitmapContextGetBytesPerRow(context); 
size_t bpp = CGBitmapContextGetBitsPerPixel(context)/8; 
CGRect rect = {{0.0f, 0.0f}, {width, height}}; 

CGContextDrawImage(context, rect, cgImage); 

// Now we can get a pointer to the image data associated with the bitmap 
// context. 
srcData = (unsigned char*)CGBitmapContextGetData(context); 
if (srcData != NULL) 
{ 
    size_t dataSize = bpr * height; 
    finalData = malloc(dataSize); 
    destData = malloc(dataSize); 
    memcpy(finalData, srcData, dataSize); 
    memcpy(destData, srcData, dataSize); 

    int sums[gaussFactor]; 
    size_t i, /*x, y,*/ k; 
    int gauss_sum = 0; 
    size_t radius = pixelRadius * 2 + 1; 
    int *gauss_fact = malloc(radius * sizeof(int)); 

    for (i = 0; i < pixelRadius; i++) 
    { 
     gauss_fact[i] = 1 + (gaussFactor * i); 
     gauss_fact[radius - (i + 1)] = 1 + (gaussFactor * i); 
     gauss_sum += (gauss_fact[i] + gauss_fact[radius - (i + 1)]); 
    } 
    gauss_fact[(radius - 1)/2] = 1 + (gaussFactor*pixelRadius); 
    gauss_sum += gauss_fact[(radius - 1)/2]; 

    unsigned char *p1, *p2, *p3; 

    for (size_t y = 0; y < height; y++) 
    { 
     for (size_t x = 0; x < width; x++) 
     { 
      p1 = srcData + bpp * (y * width + x); 
      p2 = destData + bpp * (y * width + x); 

      for (i = 0; i < gaussFactor; i++) 
       sums[i] = 0; 

      for (k = 0; k < radius ; k++) 
      { 
       if ((y - ((radius - 1) >> 1) + k) < height) 
        p1 = srcData + bpp * ((y - ((radius - 1) >> 1) + k) * width + x); 
       else 
        p1 = srcData + bpp * (y * width + x); 

       for (i = 0; i < bpp; i++) 
        sums[i] += p1[i] * gauss_fact[k]; 

      } 
      for (i = 0; i < bpp; i++) 
       p2[i] = sums[i]/gauss_sum; 
     } 
    } 
    for (size_t y = 0; y < height; y++) 
    { 
     for (size_t x = 0; x < width; x++) 
     { 
      p2 = destData + bpp * (y * width + x); 
      p3 = finalData + bpp * (y * width + x); 

      for (i = 0; i < gaussFactor; i++) 
       sums[i] = 0; 

      for(k = 0; k < radius ; k++) 
      { 
       if ((x - ((radius - 1) >> 1) + k) < width) 
        p1 = srcData + bpp * (y * width + (x - ((radius - 1) >> 1) + k)); 
       else 
        p1 = srcData + bpp * (y * width + x); 

       for (i = 0; i < bpp; i++) 
        sums[i] += p2[i] * gauss_fact[k]; 

      } 
      for (i = 0; i < bpp; i++) 
      { 
       p3[i] = sums[i]/gauss_sum; 
      } 
     } 
    } 
} 

size_t bitmapByteCount = bpr * height; 

///////Here was the problem.. you had given srcData instead of destData.. Rest all 
//were perfect... 
CGDataProviderRef dataProvider = CGDataProviderCreateWithData(NULL, destData, bitmapByteCount, NULL); 

CGImageRef blurredImageRef = CGImageCreate(width, height, CGBitmapContextGetBitsPerComponent(context), CGBitmapContextGetBitsPerPixel(context), CGBitmapContextGetBytesPerRow(context), CGBitmapContextGetColorSpace(context), CGBitmapContextGetBitmapInfo(context), dataProvider, NULL, true, kCGRenderingIntentDefault); 

CGDataProviderRelease(dataProvider); 
CGContextRelease(context); 
if (destData) 
    free(destData); 
if (finalData) 
    free(finalData); 

UIImage* retUIImage = [UIImage imageWithCGImage:blurredImageRef]; 

CGImageRelease(blurredImageRef); 

return retUIImage; 
} 
+0

郵便番号を「正常化」のために、ちょうどそのReadMeファイルの「正規化」があります - あなたはそれを修正するための助けを得ることができます。 –

+0

私はちょうど私のコードを投稿します。 – Leena

+0

この質問をチェック:http://stackoverflow.com/questions/1356250/iphone-blur-uiimage –

答えて

15

私はUIImageに小さなStackBlur拡張を作成しました。 StackBlurはGaussianBlurの近くですが、はるかに高速です。

がでそれを確認してください:https://github.com/tomsoft1/StackBluriOS


小さなノート ...タイプミスはあなたのガウスぼかしの実装に

+0

本当にうまく動作してくれてありがとうございました。 – Leena

+0

これは私に役立ちました。たくさんありがとうございます – Meet

+1

透明性を扱うiOS上のStackBlurの実装について知っていますか? – mmc

2

画像をぼかしする方法についてはわかりません。 これは、blur an UIImageView or any viewにしてもらいたい場合に役立ちます。

UIView *myView = self.theImageView; 
    CALayer *layer = [myView layer]; 
    [layer setRasterizationScale:0.25]; 
    [layer setShouldRasterize:YES]; 

あなたは1

[layer setRasterizationScale:1.0]; 

UPDATEに戻ってラスタライズスケールを設定することで、それを元に戻すことができます。

ザ・アップル以下のサンプルコードは、ぼかし/シャープ効果を含んでいます。 (Open GLを使用) 役立つかどうかを確認するhttp://developer.apple.com/library/ios/#samplecode/GLImageProcessing/Introduction/Intro.html

+0

私はぼやけた画像を保存したい。 – Leena

+0

kは、サンプルコードのリンクを追加しました。それがあなたに役立つかどうかを見てください。 – sElanthiraiyan

+0

私もそれを試してみましたが、そのガウスのぼかしほど良くはありません – Leena

1

おそらく、ボックスブラーアルゴリズムが必要です。ガウスのぼかしより約10倍高速で、素晴らしい結果が得られます。 Android上でコードを実行していますが、まだiOSに移植していません。ここにはsourceがあります。

iOSに移植するのに約10分かかります。関数はそのまま動作します(上のソースコードで行っているように)画像バイトにアクセスし、それらを関数に渡すだけです。

+0

私はそれを試してみてください、助けてくれてありがとう。 – Leena

+0

Box BlurはCore Imageの一部として利用できます。 – Abizern

+1

ボックスボケはMacのみで利用可能です。このリンクを確認してください:-http://developer.apple.com/library/mac/#documentation/GraphicsImaging/Reference/CoreImageFilterReference/Reference/reference.html#//apple_ref/doc/uid/ TP30000136-SW69 – Leena

関連する問題