您现在的位置是:首页 >技术交流 >C# - 图片抠像 - PP.MODNET.HRNET - 含模型 - 完整可运行网站首页技术交流
C# - 图片抠像 - PP.MODNET.HRNET - 含模型 - 完整可运行
简介C# - 图片抠像 - PP.MODNET.HRNET - 含模型 - 完整可运行
环境
.NET Framework 4.7.2 , X64 , VS2022
依赖
OpenCvSharp.dll,OpenCvSharp.Extensions.dll,Sdcb.PaddleInference.dll, YamlDotNet.dll, modnet-hrnet_w18
效果
页面
主逻辑代码
public partial class Form1 : Form
{
private string imgFile = "";
private string model_path = string.Empty;
private int modelSize = 512;
private PaddleSeger seger;
public Form1()
{
InitializeComponent();
}
private void button1_Click(object sender, EventArgs e)
{
using (OpenFileDialog ofd = new OpenFileDialog())
{
ofd.Filter = "图像文件|*.jpg;*.png;";
if (ofd.ShowDialog() == DialogResult.OK)
{
imgFile = ofd.FileName;
}
}
if (string.IsNullOrEmpty(imgFile))
{
return;
}
do_rec();
}
private async void do_rec()
{
var imgBs = File.ReadAllBytes(imgFile);
var imgInit = Image.FromStream(new MemoryStream(imgBs)) as Bitmap;
pb_init.Image = imgInit;
Application.DoEvents();
if (seger == null)
{
load_removebg();
}
var imgRst = await Task.Run(() =>
removebg(imgBs)
);
pb_rst.Image = imgRst;
Application.DoEvents();
}
private void load_removebg()
{
this.seger = new PaddleSeger(Application.StartupPath + "\model");
}
private Bitmap removebg(byte[] imgbs)
{
var image = Cv2.ImDecode(imgbs, ImreadModes.Color);
int oldwidth = image.Cols;
int oldheight = image.Rows;
int maxEdge = Math.Max(image.Rows, image.Cols);
float ratio = 1f * (float)this.modelSize / (float)maxEdge;
int newHeight = (int)((float)image.Rows * ratio);
int newWidth = (int)((float)image.Cols * ratio);
var mat = image.Resize(new OpenCvSharp.Size(newWidth, newHeight), 0.0, 0.0, InterpolationFlags.Linear);
int width = mat.Cols;
int height = mat.Rows;
bool flag3 = width != this.modelSize || height != this.modelSize;
if (flag3)
{
mat = mat.CopyMakeBorder(0, this.modelSize - newHeight, 0, this.modelSize - newWidth, BorderTypes.Constant, new Scalar?(new Scalar(0.0, 0.0, 0.0)));
}
var mask = this.seger.Run(mat);
bool flag4 = width != this.modelSize || height != this.modelSize;
if (flag4)
{
Rect rect = new Rect(0, 0, width, height);
mask = mask.Clone(rect);
}
#region 图像合并 和 尺寸恢复
var m1 = image;
var m2 = mask;
m1 = m1.Resize(new OpenCvSharp.Size(oldwidth, oldheight));
m2 = m2.Resize(new OpenCvSharp.Size(oldwidth, oldheight));
using (var result = new Mat())
{
try
{
using (var grayMat = new Mat())
using (var normalizedMat = new Mat())
{
if (m2.Channels() == 3)
{
Cv2.CvtColor(m2, grayMat, ColorConversionCodes.BGR2GRAY);
}
else
{
m2.CopyTo(grayMat);
}
if (grayMat.Type() == MatType.CV_32F || grayMat.Type() == MatType.CV_32FC3)
{
Cv2.Normalize(grayMat, normalizedMat, 0, 255, NormTypes.MinMax);
normalizedMat.ConvertTo(grayMat, MatType.CV_8UC1);
}
using (var rgbMat = new Mat())
{
Cv2.CvtColor(m1, rgbMat, ColorConversionCodes.BGR2RGB);
var channels = rgbMat.Split();
var allChannels = new List<Mat>();
allChannels.Add(channels[2]);
allChannels.Add(channels[1]);
allChannels.Add(channels[0]);
allChannels.Add(grayMat.Clone()); // Alpha
Cv2.Merge(allChannels.ToArray(), result);
foreach (var channel in channels)
{
channel.Dispose();
}
foreach (var channel in allChannels)
{
channel.Dispose();
}
return OpenCvSharp.Extensions.BitmapConverter.ToBitmap(result);
}
}
}
catch (Exception ex)
{
MessageBox.Show($"处理图像时出错: {ex.Message}
调试信息:
{ex.StackTrace}");
return null;
}
}
#endregion
}
}
Demo 下载地址:
风语者!平时喜欢研究各种技术,目前在从事后端开发工作,热爱生活、热爱工作。