Display the UIColor from func RGB of an image

I have a func to retrieve the RGB of an image.

import Foundation

func findColors(_ image: UIImage) -> [UIColor] {
  let pixelsWide = Int(image.size.width)
  let pixelsHigh = Int(image.size.height)

  guard let pixelData = image.cgImage?.dataProvider?.data else { return [] }
  let data: UnsafePointer<UInt8> = CFDataGetBytePtr(pixelData)

  var imageColors: [UIColor] = []
  for x in 0..<1 {
    for y in 0..<1 {
      let point = CGPoint(x: x, y: y)
      let pixelInfo: Int = ((pixelsWide * Int(point.y)) + Int(point.x)) * 4
      let color = UIColor(red: CGFloat(data[pixelInfo]) / 255.0,
                green: CGFloat(data[pixelInfo + 1]) / 255.0,
                blue: CGFloat(data[pixelInfo + 2]) / 255.0,
                alpha: CGFloat(data[pixelInfo + 3]) / 255.0)
      imageColors.append(color)
    }
  }
  return imageColors
}

I'm trying to display that RGB as an actual color in the UI. I tried the below code, but giving me error. Could you please suggest how to call the func findColors properly?


let image = UIImage(named: "Fish.jpg")!


struct ContentView: View {

  var body: some View {
      Color(findColors(image))
        .frame(width:10, height: 10)
        .position(x: 40, y: 40)
  }
}

struct ContentView_Previews: PreviewProvider {
  static var previews: some View {
    ContentView()
  }
}
Accepted Answer

You're returning an array of colors from your findColors function, and there's no SwiftUI Color view that accepts an array as parameter.

It's unclear why you're returning an array here, since your code only extracts color from one pixel. It seems like what you really want is an optional color returned from the function. In that case, you'd need additional code in your ContentView to handle the two cases: one where a color is returned, and the other where no color is returned.

hi Polyphonic,

Thanks for looking into this. I'd like to read every pixel of the image then store in a json file first. After that, I will retrieve a certain color to display on the screen. As you suggested, I couldn't figure how to return another color in my func. Could you please update directly to my func and ContentView to show the pixel RGB?

Thanks, Huy

I'm not sure I can update your code in any meaningful way, because I don't understand completely what you're trying to achieve. It sounds like you have 2 parts to this:

  1. Write an array of colors to backing storage.

  2. Retrieve one of those colors to display in the UI.

You can't really combine those into a single step, so I suggest that you revise your code to reflect these two different parts more directly. Once you've done that, it should be clearer to you what code you should write.

I want to do the option 2 first to retrieve on of those colors to display in the UI. As I do in the playground, the line 'return imageColors' shows the value as array [r 0.0 g 0.459 b 0.761 a 1.0] for example. Please teach me how to retrieve the RGB from this array in the ContentView.

import Foundation

let image = UIImage(named: "Fish.jpg")!

func findColors(_ image: UIImage) -> [UIColor] {
  let pixelsWide = Int(image.size.width)
  let pixelsHigh = Int(image.size.height)

  guard let pixelData = image.cgImage?.dataProvider?.data else { return [] }
  let data: UnsafePointer<UInt8> = CFDataGetBytePtr(pixelData)

  var imageColors: [UIColor] = []

  for x in 0..<1 {
    for y in 0..<1 {
      let point = CGPoint(x: x, y: y)
      let pixelInfo: Int = ((pixelsWide * Int(point.y)) + Int(point.x)) * 4
      let color = UIColor(red: CGFloat(data[pixelInfo]) / 255.0,
                green: CGFloat(data[pixelInfo + 1]) / 255.0,
                blue: CGFloat(data[pixelInfo + 2]) / 255.0,
                alpha: CGFloat(data[pixelInfo + 3]) / 255.0)
      imageColors.append(color)
    }
  }
  return imageColors
}

 print(findColors(image))
Display the UIColor from func RGB of an image
 
 
Q