修剪UIImage的边界 [英] Trim UIImage border

查看:253
本文介绍了修剪UIImage的边界的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

下面是我想裁剪图像的一个例子。我想摆脱图像周围的边框(在这种情况下,顶部和底部有黑条)。

Here's an example of an image I would like to trim. I want to get rid of the borders around the image (in this case the top and bottom black bars).

我发现在Github上库: CKImageAdditions ,但它似乎并没有工作。当我传递一个的UIColor(带RGB色彩),它只是返回相同的图像。

I found a library on Github: CKImageAdditions, however it doesn't seem to work. When I pass in a UIColor (with RGB colours) it just returns the same image.

我可以找到大量的实例和类别类,将修剪一个UIImage与任何透明像素为界,但在这种情况下,我需要修剪黑色。我已采样的颜色在我的图片和它们的颜色值确实是255,但它似乎并没有以匹配上面的库所期待的。

I can find a lot of examples and category classes that would trim a UIImage with any transparent pixels as the border, but in this case I need to trim the black colour. I have sampled the colour in my images and they the colour value is indeed 255, but it doesn't seem to match what the above library is looking for.

有没有人有他们所使用的库或任何见解?我已经搜查,搜查和CKImageAdditions一直是我能找到的唯一的事情是做广告用一种颜色来修剪(不过,遗憾的是没有在我的情况下工作)。

Does anyone have a library they have used or any insight? I've searched and searched and CKImageAdditions has been the only thing I can find that advertises to trim with a colour (although, unfortunately doesn't work in my case).

推荐答案

我结束了从定制的方法的<一个href=\"https://github.com/cmkilger/CKImageAdditions/blob/master/ImageAdditions/CoreGraphicsAdditions.c#L235\">function在假想有这个功能,但我无法得到它的工作CKImageAdditions 。它只是不会修剪的颜色,所以我代替检查像素的RGB值是 \\ 0 (黑色)。在 CKImageAdditions 只是找不到黑色像素,很遗憾。

I ended up customizing a method from a function in CKImageAdditions that had this functionality supposedly but I couldn't get it to work. It just wouldn't trim the colour, so I instead check the pixel's RGB values to be \0 (black). The CKImageAdditions just couldn't find the black pixels, unfortunately.

因为我想有时修剪图像没有超黑条(有时他们不得不用打火机深色或一些流浪像素)我加的 GPUImage 功能的方法,它基本上只是在其创建的图像具有较强的过滤器的黑色和白色版本,所以任何黑暗的颜色变成黑色和任何浅色变成白色,使黑条边框更加突出,并确保更好的结果,当我的方法寻找他们。当然,我在基于从黑/白图像的结果结束裁剪原始图像

Since the images I wanted to trim sometimes didn't have super black bars (sometimes they'd have a stray pixel with a lighter dark colour or something) I added GPUImage functionality to the method, which basically just creates a black and white version of the image with a strong filter on it so any dark colours become black and any light colours become white, making the black bar borders much more prominent and ensuring better results when I look for them in the method. And of course I crop the original image at the end based on the results from the black/white image.

下面是我的code:

typedef struct Pixel { uint8_t r, g, b, a; } Pixel;

+(UIImage*)trimBlack:(UIImage*)originalImage {
    GPUImagePicture *stillImageSource = [[GPUImagePicture alloc] initWithImage:originalImage];
    GPUImageLuminanceThresholdFilter *stillImageFilter = [[GPUImageLuminanceThresholdFilter alloc] init];
    stillImageFilter.threshold = 0.1;
    [stillImageSource addTarget:stillImageFilter];
    [stillImageSource processImage];
    UIImage *imageToProcess = [stillImageFilter imageFromCurrentlyProcessedOutput];

    RMImageTrimmingSides sides = RMImageTrimmingSidesAll;
    CGImageRef image = imageToProcess.CGImage;
    void * bitmapData = NULL;
    CGContextRef context = CKBitmapContextAndDataCreateWithImage(image, &bitmapData);

    Pixel *data = bitmapData;

    size_t width = CGBitmapContextGetWidth(context);
    size_t height = CGBitmapContextGetHeight(context);

    size_t top = 0;
    size_t bottom = height;
    size_t left = 0;
    size_t right = width;

    // Scan the left
    if (sides & RMImageTrimmingSidesLeft) {
        for (size_t x = 0; x < width; x++) {
            for (size_t y = 0; y < height; y++) {
                Pixel pixel = data[y * width + x];
                if (pixel.r != '\0' && pixel.g != '\0' && pixel.b != '\0') {
                    left = x;
                    goto SCAN_TOP;
                }
            }
        }
    }

    // Scan the top
SCAN_TOP:
    if (sides & RMImageTrimmingSidesTop) {
        for (size_t y = 0; y < height; y++) {
            for (size_t x = 0; x < width; x++) {
                Pixel pixel = data[y * width + x];
                if (pixel.r != '\0' && pixel.g != '\0' && pixel.b != '\0') {
                    top = y;
                    goto SCAN_RIGHT;
                }
            }
        }
    }

    // Scan the right
SCAN_RIGHT:
    if (sides & RMImageTrimmingSidesRight) {
        for (size_t x = width-1; x >= left; x--) {
            for (size_t y = 0; y < height; y++) {
                Pixel pixel = data[y * width + x];
                if (pixel.r != '\0' && pixel.g != '\0' && pixel.b != '\0') {
                    right = x;
                    goto SCAN_BOTTOM;
                }
            }
        }
    }

    // Scan the bottom
SCAN_BOTTOM:
    if (sides & RMImageTrimmingSidesBottom) {
        for (size_t y = height-1; y >= top; y--) {
            for (size_t x = 0; x < width; x++) {
                Pixel pixel = data[y * width + x];
                if (pixel.r != '\0' && pixel.g != '\0' && pixel.b != '\0') {
                    bottom = y;
                    goto FINISH;
                }
            }
        }
    }

FINISH:
    CGContextRelease(context);
    free(bitmapData);

    CGRect rect = CGRectMake(left, top, right - left, bottom - top);
    return [originalImage imageCroppedToRect:rect];
}

由于从库中的code上面使用,当然所有归功于他们的开发人员所有的辛勤工作!

Thanks to all the hard work from the developers of the libraries used in the code above and of course all credit goes to them!

这篇关于修剪UIImage的边界的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆