如何设置一个获取灰度图像并输出 ARGB 的图层,使其中一种灰度颜色透明?
Posted
技术标签:
【中文标题】如何设置一个获取灰度图像并输出 ARGB 的图层,使其中一种灰度颜色透明?【英文标题】:How to setup a layer that takes grayscale image and ouputs ARGB making one of the grayscale color transparent? 【发布时间】:2020-12-28 21:03:57 【问题描述】:我从输出 2D 多阵列(分段)的 DeepLabV3+ mlmodel 开始。成功添加了一个将其作为输入并输出 GRAYSCALE 图像的层。
现在,我想将此灰度图像作为输入和输出 ARGB,我想让其中一种颜色透明。
如何设置这样的层?
我的python代码:
import coremltools
import coremltools.proto.FeatureTypes_pb2 as ft
coreml_model = coremltools.models.MLModel('DeepLabKP.mlmodel')
spec = coreml_model.get_spec()
spec_layers = getattr(spec,spec.WhichOneof("Type")).layers
# find the current output layer and save it for later reference
last_layer = spec_layers[-1]
# add the post-processing layer
new_layer = spec_layers.add()
new_layer.name = 'image_gray_to_RGB'
# Configure it as an activation layer
new_layer.activation.linear.alpha = 255
new_layer.activation.linear.beta = 0
# Use the original model's output as input to this layer
new_layer.input.append(last_layer.output[0])
# Name the output for later reference when saving the model
new_layer.output.append('image_gray_to_RGB')
# Find the original model's output description
output_description = next(x for x in spec.description.output if x.name==last_layer.output[0])
# Update it to use the new layer as output
output_description.name = new_layer.name
# Function to mark the layer as output
# https://forums.developer.apple.com/thread/81571#241998
def convert_grayscale_image_to_RGB(spec, feature_name, is_bgr=False):
"""
Convert an output multiarray to be represented as an image
This will modify the Model_pb spec passed in.
Example:
model = coremltools.models.MLModel('MyNeuralNetwork.mlmodel')
spec = model.get_spec()
convert_multiarray_output_to_image(spec,'imageOutput',is_bgr=False)
newModel = coremltools.models.MLModel(spec)
newModel.save('MyNeuralNetworkWithImageOutput.mlmodel')
Parameters
----------
spec: Model_pb
The specification containing the output feature to convert
feature_name: str
The name of the multiarray output feature you want to convert
is_bgr: boolean
If multiarray has 3 channels, set to True for RGB pixel order or false for BGR
"""
for output in spec.description.output:
if output.name != feature_name:
continue
if output.type.WhichOneof('Type') != 'imageType':
raise ValueError("%s is not a image type" % output.name)
output.type.imageType.colorSpace = ft.ImageFeatureType.ColorSpace.Value('RGB')
# Mark the new layer as image
convert_grayscale_image_to_RGB(spec, output_description.name, is_bgr=False)
updated_model = coremltools.models.MLModel(spec)
updated_model.author = 'Saran'
updated_model.license = 'MIT'
updated_model.short_description = 'Inherits DeepLab V3+ and adds a layer to turn scores into an image'
updated_model.input_description['image'] = 'Input Image'
updated_model.output_description[output_description.name] = 'RGB Image'
model_file_name = 'DeepLabKP-G2R.mlmodel'
updated_model.save(model_file_name)
虽然模型成功保存没有任何错误,但预测错误如下
result = model.predict('image': img)
File "/Users/saran/Library/Python/2.7/lib/python/site-packages/coremltools/models/model.py", line 336, in predict
return self.__proxy__.predict(data, useCPUOnly)
RuntimeError:
NSLocalizedDescription = "Failed to convert output image_gray_to_RGB to image";
NSUnderlyingError = "Error Domain=com.apple.CoreML Code=0 \"Invalid array shape (\n 1,\n 513,\n 513\n) for converting to gray image\" UserInfo=NSLocalizedDescription=Invalid array shape (\n 1,\n 513,\n 513\n) for converting to gray image";
我觉得这与在这一层中如何设置激活有关。但是找不到任何可以尝试不同的方法。
非常感谢任何帮助。
我添加的图层生成的灰度图像
【问题讨论】:
【参考方案1】:看起来您的输出具有形状 (1, 513, 513)。第一个数字 1 是通道数。由于这是 1,Core ML 只能将输出变成灰度图像。一张彩色图片需要 3 个通道,或者是 (3, 513, 513) 的形状。
由于这是 DeepLab,我假设您的灰度图像中并没有真正的“颜色”,而是类的索引(换句话说,您已将 ARGMAX 用于预测)。在我看来,将这个灰度“图像”(实际上是分割蒙版)转换为彩色图像的最简单方法是在 Swift 或 Metal 中执行此操作。
这是一个源代码示例:https://github.com/hollance/SemanticSegmentationMetalDemo
【讨论】:
附加的灰度图像输出,我从我添加到上述问题的上一层获得。如果我没有恢复原来的颜色,我很好。只要我可以通过变成 3 通道来使分段部分透明,即使使用一些默认值,我也会很高兴。我将把它用作与原始图像合成的蒙版。谢谢你的链接,我也去看看。以上是关于如何设置一个获取灰度图像并输出 ARGB 的图层,使其中一种灰度颜色透明?的主要内容,如果未能解决你的问题,请参考以下文章