UIImage到UIColor像素颜色数组

时间:2016-07-02 19:01:43

标签: swift uiimage uicolor

我很抱歉这样问,但我无法弄清楚如何将UIImage表示为每个像素的UIColor数组。我已经尽力转换UIImagePNG/JPEGRepresentation,但无法获得理想的结果。

3 个答案:

答案 0 :(得分:2)

这只是斯威夫特将Olie's answer翻译成ObjC中的同一个问题。确保你也给他一个upvote。

extension UIImage {
    func colorArray() -> [UIColor] {
        let result = NSMutableArray()

        let img = self.CGImage
        let width = CGImageGetWidth(img)
        let height = CGImageGetHeight(img)
        let colorSpace = CGColorSpaceCreateDeviceRGB()

        var rawData = [UInt8](count: width * height * 4, repeatedValue: 0)
        let bytesPerPixel = 4
        let bytesPerRow = bytesPerPixel * width
        let bytesPerComponent = 8

        let bitmapInfo = CGImageAlphaInfo.PremultipliedLast.rawValue | CGBitmapInfo.ByteOrder32Big.rawValue
        let context = CGBitmapContextCreate(&rawData, width, height, bytesPerComponent, bytesPerRow, colorSpace, bitmapInfo)

        CGContextDrawImage(context, CGRectMake(0, 0, CGFloat(width), CGFloat(height)), img);
        for x in 0..<width {
            for y in 0..<height {
                let byteIndex = (bytesPerRow * x) + y * bytesPerPixel

                let red   = CGFloat(rawData[byteIndex]    ) / 255.0
                let green = CGFloat(rawData[byteIndex + 1]) / 255.0
                let blue  = CGFloat(rawData[byteIndex + 2]) / 255.0
                let alpha = CGFloat(rawData[byteIndex + 3]) / 255.0

                let color = UIColor(red: red, green: green, blue: blue, alpha: alpha)
                result.addObject(color)
            }
        }

        return (result as NSArray) as! [UIColor]
    }
}

请注意,这种运行速度相当慢。模拟器需要35秒才能解码15MP图像,这是四核i7上的。

答案 1 :(得分:2)

这是一个Swiftier版本(Swift 3):

extension UIImage {
    var colors: [UIColor]? {

        var colors = [UIColor]()

        let colorSpace = CGColorSpaceCreateDeviceRGB()

        guard let cgImage = cgImage else {
            return nil
        }

        let width = Int(size.width)
        let height = Int(size.height)

        var rawData = [UInt8](repeating: 0, count: width * height * 4)
        let bytesPerPixel = 4
        let bytesPerRow = bytesPerPixel * width
        let bytesPerComponent = 8

        let bitmapInfo = CGImageAlphaInfo.premultipliedLast.rawValue | CGBitmapInfo.byteOrder32Big.rawValue

        let context = CGContext(data: &rawData,
                                width: width,
                                height: height,
                                bitsPerComponent: bytesPerComponent,
                                bytesPerRow: bytesPerRow,
                                space: colorSpace,
                                bitmapInfo: bitmapInfo)

        let drawingRect = CGRect(origin: .zero, size: CGSize(width: width, height: height))
        context?.draw(cgImage, in: drawingRect)

        for x in 0..<width {
            for y in 0..<height {
                let byteIndex = (bytesPerRow * x) + y * bytesPerPixel

                let red = CGFloat(rawData[byteIndex]) / 255.0
                let green = CGFloat(rawData[byteIndex + 1]) / 255.0
                let blue = CGFloat(rawData[byteIndex + 2]) / 255.0
                let alpha = CGFloat(rawData[byteIndex + 3]) / 255.0

                let color = UIColor(red: red, green: green, blue: blue, alpha: alpha)
                colors.append(color)
            }
        }

        return colors
    }
}

答案 2 :(得分:0)

要获取像素,请尝试

let image = UIImage(named: "pic2.png")
if let cgImage = image?.cgImage, let data = cgImage.dataProvider?.data, let bytes = CFDataGetBytePtr(data){
assert(cgImage.colorSpace?.model == .rgb)
var stringArray = [String]()
let bytesPerPixel = cgImage.bitsPerPixel / cgImage.bitsPerComponent
for y in 0 ..< cgImage.height{
    for x in 0 ..< cgImage.width{
        let offset = (y * cgImage.bytesPerRow) + ( x * bytesPerPixel)
        let components = (r: bytes[offset], g: bytes[offset + 1], b: bytes[offset + 2])
        stringArray.append("[x: \(x), y:\(y)] \(components)")
    }
}
print(stringArray)

}