eric lardon
eric lardon

Reputation: 359

How can l colorize an RGB image with blue color?

I have the following image that l would like to colorize with blue color.

Image input :
inputs

Expected output :
Expected_output

Is there any skimage or opencv tool that allows to do this kind of operation ?

Thank you

Upvotes: 1

Views: 1335

Answers (5)

filippo
filippo

Reputation: 5294

Pure numpy solution

import numpy as np
import skimage.io

def blend(a, b, alpha):
    return (alpha * a + (1 - alpha) * b).astype(np.uint8)

def luma(img):
    rgb_to_luma = np.array([0.2126, 0.7152, 0.0722]) # BT.709
    return np.repeat((img * rgb_to_luma).sum(axis=-1).astype(np.uint8), 3).reshape(img.shape)

BGCOLOR = np.array([1, 174, 242])

img = skimage.io.imread('city.jpg')
bg = np.ones_like(img) * BGCOLOR

skimage.io.imsave('blue.png', blend(luma(img), bg, 0.2))

enter image description here

Upvotes: 0

Jeru Luke
Jeru Luke

Reputation: 21203

You can obtain the desired effect by applying a transparent overlay. I roughly figured out the color (sky blue) by trial-and-error. It can be changed to any color possible.

In OpenCV you can use the cv2..addWeighted() for this purpose

Code:

import numpy as np
import cv2

image = 'C:/Users/Desktop/city.jpg'
im = cv2.imread(path, 1)

blue = np.zeros_like(im)
blue[:] = (255, 200, 0)     #<--- Change here
cv2.imshow('blue.jpg', blue)

enter image description here

val = 0.75
fin = cv2.addWeighted(blue, val, im, 1 - val, 0)
cv2.imshow('Transparent_image', fin)

enter image description here

As mentioned by @vasia setting the red and green pixels to 0 does not produce the desired effect. This is what I get as a result:

enter image description here

UPDATE

@MarkSetchell's comment got me thinking and this is the result of that:

enter image description here

So what did I do?

I merged three channels:

  1. An array of values 255 in the blue channel
  2. Grayscale of the original image in the green channel
  3. An array of values 0 in the red channel

Thanks Mark!!

Upvotes: 4

Tim Bradley
Tim Bradley

Reputation: 183

To answer your question exactly, you can just set the other channels to 0. You might want to set them a bit higher than that or things end up a bit dark, but here you go:

img = cv2.imread(your_image)
img[:, :, 1] = 0  # (or 20)
img[:, :, 2] = 0

cv2.namedWindow("test")

while True:
    cv2.imshow("test", a)
    ch = cv2.waitKey & 0xFF
    if ch == ord('q'):
    break

cv2.destroyAllWindows()

Here's an example:

Original Image Blue Cage

Upvotes: 1

vasia
vasia

Reputation: 1172

A typical bitmap image is a two-dimensional grid of pixels, where each pixel is a group of three integers ranging from 0 to 255, representing red, green, and blue. If you want to view only the blue channel of an image, you could create a new image from the pixels in your original image, and set the red and green pixel values to 0 for each pixel, leaving only blue.

Upvotes: 0

GPPK
GPPK

Reputation: 6666

You could do this by blending two images together, create one that is just your blue image, and blend it together with an alpha of your choosing:

here is the OpenCV tutorial on how to do that.

You can see how this can affect your images in more detail on this blog post

Upvotes: 0

Related Questions