给单帧灰度图添加颜色元素
Add color elements to single-frame greyscale image
我有一张单帧灰度图像。我想修改图像,使某个值的所有像素都变成彩色,比如红色。显然我需要将图像转换为 3 帧图像。
为方便起见,我使用包 EBImage,但仅使用基本包的简单代码会很棒。
mat = round(matrix(runif(100), ncol = 5), digits = 1)
mat
[,1] [,2] [,3] [,4] [,5]
[1,] 0.1 0.2 0.6 0.1 0.8
[2,] 0.1 0.3 0.4 0.5 0.6
[3,] 0.6 0.3 0.8 0.8 0.5
[4,] 0.5 0.9 0.7 0.3 0.2
[5,] 0.7 0.7 0.9 0.3 0.2
[6,] 0.6 1.0 0.4 0.7 0.3
[7,] 0.7 0.6 0.5 0.8 0.5
[8,] 0.4 0.8 0.2 0.2 0.1
[9,] 0.2 0.1 0.4 0.9 0.6
[10,] 0.7 0.3 0.2 0.3 0.8
[11,] 0.8 1.0 0.4 0.8 0.3
[12,] 0.8 1.0 0.5 0.8 0.7
[13,] 0.6 0.5 0.9 0.9 0.1
[14,] 1.0 0.5 0.6 0.0 0.3
[15,] 0.1 0.5 0.6 0.6 0.2
[16,] 0.2 0.8 0.2 0.5 0.2
[17,] 0.9 0.9 0.4 0.7 0.1
[18,] 0.3 0.7 0.9 0.7 0.4
[19,] 1.0 0.0 0.5 0.0 1.0
[20,] 0.2 0.3 0.9 0.3 0.6
matgray = 255*mat
mat_rgb = channel(matgray, 'rgb') ## using EBImage package
dim(mat_rgb)
[1] 20 5 3
mat_red = channel(mat_rgb, 'asred')
# To generate and save gray image from gray matrix
par(mar = c(0,0,0,0))
png(filename = paste("Image.png"), res=1)
image(mat_red, axes = FALSE)
dev.off()
当我继续保存图像时,它显示Missing frame index for an image stack, assuming 'i = 1'
,图像确实没有显示任何红色...谢谢您的帮助!
你几乎答对了。 channel(mat, 'rgb')
或其别名函数 toRGB(mat)
,通过复制红色、绿色和蓝色通道上的像素强度,将单个灰度帧提升为 RGB 图像,从而生成 3D 阵列。默认情况下,EBImage 对 [0:1] 范围内的图像数据进行操作,因此通常您不会将矩阵乘以 255
。您可以使用 display
来可视化数据。
library(EBImage)
set.seed(0) # set random number generator state for reproducibility
mat <- round(matrix(runif(100), ncol = 5), digits = 1)
mat_rgb <- channel(mat, 'rgb') #or: toRGB(mat)
mat_rgb
## Image
## colorMode : Color
## storage.mode : double
## dim : 20 5 3
## frames.total : 3
## frames.render: 1
##
## imageData(object)[1:5,1:5,1]
## [,1] [,2] [,3] [,4] [,5]
## [1,] 0.9 0.8 0.4 0.4 1.0
## [2,] 0.3 0.9 0.8 0.9 0.4
## [3,] 0.4 0.2 0.6 0.3 0.7
## [4,] 0.6 0.7 0.8 0.5 0.4
## [5,] 0.9 0.1 0.6 0.3 0.3
display(mat_rgb)
但是即使图像的 colorMode
是 Color
结果仍然显示为灰色阴影,因为每个像素的颜色强度在 3 个通道中是相同的。 channel(mat_rgb, 'asred')
仅提取通过复制其值从灰度原件生成的红色分量。因此,您最终将拥有与开始时相同的框架。
mat_red <- channel(mat_rgb, 'asred')
mat_red
## Image
## colorMode : Grayscale
## storage.mode : double
## dim : 20 5
## frames.total : 1
## frames.render: 1
##
## imageData(object)[1:5,1:5]
## [,1] [,2] [,3] [,4] [,5]
## [1,] 0.9 0.8 0.4 0.4 1.0
## [2,] 0.3 0.9 0.8 0.9 0.4
## [3,] 0.4 0.2 0.6 0.3 0.7
## [4,] 0.6 0.7 0.8 0.5 0.4
## [5,] 0.9 0.1 0.6 0.3 0.3
identical(imageData(mat_red), mat) #or: identical(as.array(mat_red), mat)
## [1] TRUE
您可以使用灰度矩阵作为 rgbImage
中的 red
通道,将所有像素着色为红色。
mat_red <- rgbImage(red = mat)
display(mat_red)
为了使用固定颜色仅突出显示满足特定条件的像素,同时将图像的其余部分保留为灰度,您需要将原始强度矩阵作为红色、绿色和蓝色通道提供给 rgbImage
但是改变了感兴趣的像素,使它们编码所需的颜色。例如,要将阈值 0.2
以下的所有像素都涂成红色,您可以在红色通道中将它们设置为 1
(最大颜色值),在其他两个通道中设置为 0
。
pts <- which(mat<0.2)
mat_r <- mat_g <- mat_b <- mat
mat_r[pts] <- 1
mat_g[pts] <- 0
mat_b[pts] <- 0
display( rgbImage(mat_r, mat_g, mat_b) )
其他颜色对应的值可以很容易地从col2rgb
.
中得到
col2rgb("orange")/255
## [,1]
## red 1.0000000
## green 0.6470588
## blue 0.0000000
我有一张单帧灰度图像。我想修改图像,使某个值的所有像素都变成彩色,比如红色。显然我需要将图像转换为 3 帧图像。 为方便起见,我使用包 EBImage,但仅使用基本包的简单代码会很棒。
mat = round(matrix(runif(100), ncol = 5), digits = 1)
mat
[,1] [,2] [,3] [,4] [,5]
[1,] 0.1 0.2 0.6 0.1 0.8
[2,] 0.1 0.3 0.4 0.5 0.6
[3,] 0.6 0.3 0.8 0.8 0.5
[4,] 0.5 0.9 0.7 0.3 0.2
[5,] 0.7 0.7 0.9 0.3 0.2
[6,] 0.6 1.0 0.4 0.7 0.3
[7,] 0.7 0.6 0.5 0.8 0.5
[8,] 0.4 0.8 0.2 0.2 0.1
[9,] 0.2 0.1 0.4 0.9 0.6
[10,] 0.7 0.3 0.2 0.3 0.8
[11,] 0.8 1.0 0.4 0.8 0.3
[12,] 0.8 1.0 0.5 0.8 0.7
[13,] 0.6 0.5 0.9 0.9 0.1
[14,] 1.0 0.5 0.6 0.0 0.3
[15,] 0.1 0.5 0.6 0.6 0.2
[16,] 0.2 0.8 0.2 0.5 0.2
[17,] 0.9 0.9 0.4 0.7 0.1
[18,] 0.3 0.7 0.9 0.7 0.4
[19,] 1.0 0.0 0.5 0.0 1.0
[20,] 0.2 0.3 0.9 0.3 0.6
matgray = 255*mat
mat_rgb = channel(matgray, 'rgb') ## using EBImage package
dim(mat_rgb)
[1] 20 5 3
mat_red = channel(mat_rgb, 'asred')
# To generate and save gray image from gray matrix
par(mar = c(0,0,0,0))
png(filename = paste("Image.png"), res=1)
image(mat_red, axes = FALSE)
dev.off()
当我继续保存图像时,它显示Missing frame index for an image stack, assuming 'i = 1'
,图像确实没有显示任何红色...谢谢您的帮助!
你几乎答对了。 channel(mat, 'rgb')
或其别名函数 toRGB(mat)
,通过复制红色、绿色和蓝色通道上的像素强度,将单个灰度帧提升为 RGB 图像,从而生成 3D 阵列。默认情况下,EBImage 对 [0:1] 范围内的图像数据进行操作,因此通常您不会将矩阵乘以 255
。您可以使用 display
来可视化数据。
library(EBImage)
set.seed(0) # set random number generator state for reproducibility
mat <- round(matrix(runif(100), ncol = 5), digits = 1)
mat_rgb <- channel(mat, 'rgb') #or: toRGB(mat)
mat_rgb
## Image
## colorMode : Color
## storage.mode : double
## dim : 20 5 3
## frames.total : 3
## frames.render: 1
##
## imageData(object)[1:5,1:5,1]
## [,1] [,2] [,3] [,4] [,5]
## [1,] 0.9 0.8 0.4 0.4 1.0
## [2,] 0.3 0.9 0.8 0.9 0.4
## [3,] 0.4 0.2 0.6 0.3 0.7
## [4,] 0.6 0.7 0.8 0.5 0.4
## [5,] 0.9 0.1 0.6 0.3 0.3
display(mat_rgb)
但是即使图像的 colorMode
是 Color
结果仍然显示为灰色阴影,因为每个像素的颜色强度在 3 个通道中是相同的。 channel(mat_rgb, 'asred')
仅提取通过复制其值从灰度原件生成的红色分量。因此,您最终将拥有与开始时相同的框架。
mat_red <- channel(mat_rgb, 'asred')
mat_red
## Image
## colorMode : Grayscale
## storage.mode : double
## dim : 20 5
## frames.total : 1
## frames.render: 1
##
## imageData(object)[1:5,1:5]
## [,1] [,2] [,3] [,4] [,5]
## [1,] 0.9 0.8 0.4 0.4 1.0
## [2,] 0.3 0.9 0.8 0.9 0.4
## [3,] 0.4 0.2 0.6 0.3 0.7
## [4,] 0.6 0.7 0.8 0.5 0.4
## [5,] 0.9 0.1 0.6 0.3 0.3
identical(imageData(mat_red), mat) #or: identical(as.array(mat_red), mat)
## [1] TRUE
您可以使用灰度矩阵作为 rgbImage
中的 red
通道,将所有像素着色为红色。
mat_red <- rgbImage(red = mat)
display(mat_red)
为了使用固定颜色仅突出显示满足特定条件的像素,同时将图像的其余部分保留为灰度,您需要将原始强度矩阵作为红色、绿色和蓝色通道提供给 rgbImage
但是改变了感兴趣的像素,使它们编码所需的颜色。例如,要将阈值 0.2
以下的所有像素都涂成红色,您可以在红色通道中将它们设置为 1
(最大颜色值),在其他两个通道中设置为 0
。
pts <- which(mat<0.2)
mat_r <- mat_g <- mat_b <- mat
mat_r[pts] <- 1
mat_g[pts] <- 0
mat_b[pts] <- 0
display( rgbImage(mat_r, mat_g, mat_b) )
其他颜色对应的值可以很容易地从col2rgb
.
col2rgb("orange")/255
## [,1]
## red 1.0000000
## green 0.6470588
## blue 0.0000000