.NET Core如何利用skiasharp文字头像生成方法
创始人
2024-11-27 19:43:02
0次

一、问题背景

目前.NET Core下面针对于图像处理的库微软并没有集成,在.NET FrameWork下我们已经习惯使用System.Drawing类库做简单的图像处理,到了.NET Core下一脸懵逼的我,只能百度+谷歌看看有没啥解决方案,好在网上资料也多,.NET Core下的图像处理还是有些开源库的,我目前使用的其中一个:SkiaSharp,介绍反正大家自己网上找找都有,下面就用该库实现一个文字头像的小功能,话不多说了,来一起看看详细的介绍吧。

二、简单的设计要求

  • 对于输入的名字得解析(中文、英文)

  • 图片背景色随机会换

  • 文字要居中(废话,不居中不是丑爆了)

三、具体实现

1、解析姓名信息

  private String ResolveName(String imageText)
  {
   imageText.Replace("?", "").Replace(":", "").Replace("?", "").Replace("*", "").Replace("<", "").Replace(">", "").Replace(@"/", "").Replace(@"\", "").Replace(@"|", "").Replace("\"", "");//去除路径不支持的信息
   imageText = imageText.Trim(' ');//去除空格信息
   String temp2 = imageText.Substring(0, 1);//根据第一位的数据判断是走英文规则还是中文规则,都不是的话就是取前两位
   if (RegexLib.IsChineseCharacter(temp2))
   {
    //UserName = UserName.Trim(' ');
    if (imageText.Length > 2 & imageText.Length <= 3)
    {
     imageText = imageText.Substring(1, 2);
    }
    else if (imageText.Length >= 3)
    {
     imageText = imageText.Substring(imageText.Length - 2, 2);
    }
   }
   else if (RegexLib.IsEnglishCharacter(temp2))
   {
    String[] temp1 = imageText.Split(' ');
    if (temp1.Length == 2)
    {
     imageText = (temp1[0].Substring(0, 1) + temp1[1].Substring(0, 1)).ToUpper();
    }
    else
    {
     if (imageText.Length > 2)
     {
      imageText = imageText.Substring(0, 2).ToUpper();
     }
    }
   }
   else
   {
    if (imageText.Length > 2)
    {
     imageText = imageText.Substring(0, 2);
    }
   }
   imageName = imageText;
   return imageName;
  }

2、根据文字生成图片

  public byte[] Create()
  {
   String name = imageName + ".jpg";
   SKBitmap bmp = new SKBitmap(128, 128);
   String str = imageName;

   using (SKCanvas canvas = new SKCanvas(bmp))
   {
    Random r = new Random();
    int num = r.Next(0, 9);
    canvas.DrawColor(colors[num]); // colors是图片背景颜色集合,这里代码就不贴出来了,随机找一个
    using (SKPaint sKPaint = new SKPaint())
    {
     sKPaint.Color = SKColors.White;//字体颜色
     sKPaint.TextSize = 39;//字体大小
     sKPaint.IsAntialias = true;//开启抗锯齿
     sKPaint.Typeface = SkiaSharp.SKTypeface.FromFamilyName("微软雅黑", SKTypefaceStyle.Bold);//字体
     SKRect size = new SKRect();
     sKPaint.MeasureText(str, ref size);//计算文字宽度以及高度
     float temp = (128 - size.Size.Width) / 2;
     float temp1 = (128 - size.Size.Height) / 2;
     canvas.DrawText(str, temp, temp1 - size.Top, sKPaint);//画文字
    }
    //保存成图片文件
    using (SKImage img = SKImage.FromBitmap(bmp))
    {
     using (SKData p = img.Encode(SKEncodedImageFormat.Jpeg, 100))
     {
      return p.ToArray();
      //using (var stream = File.Create(Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "photoImage", name)))
      //{
      // stream.Write(p.ToArray(), 0, p.ToArray().Length);
      // return stream;
      //}
     }
    }
   }
  }

我这边只是得到的是byte[]数组,如果需要转成stream或者保存成文件,方法都有,找找肯定都可以找到的,我就不放出来了,

三、docker发布的坑

坑1:IIS下可以,docker下报错的坑爹问题

由于skiasharp在windows跟linux下使用的依赖库是不同的,如果都按照以前的方式部署,在docker里就会出现"The type initializer for 'SkiaSharp.SKImageInfo' threw an exception",原因是linux下skiasharp依赖libSkiaSharp.so,而如果系统中没有libSkiaSharp.so,就会报这个错,目前我最简单的操作就是找到这个文件扔在skiasharp的目录下,然后就可以了

坑2:中文字体不识别

由于docker内部没有中文字体,SO,当要输出中文的时候就狗带了,如下图,所及解决办法那也就是把字体拷贝到docker内部中去

.NET Core如何利用skiasharp文字头像生成方法  

下面提供我自己使用的Dockerfile,具体Dockerfile怎么用,那就只能大家自己百度百度(ps:其实真实原因是我自己这方面也是弱鸡- -,怕误导大家),我的环境是CentOS7.3的环境

#基于 `microsoft/dotnet:latest` 来构建我们的镜像
FROM microsoft/dotnet:latest

#拷贝项目publish文件夹中的所有文件到 docker容器中的publish文件夹中 
COPY . /publish /publish/

#ENV LANG C.UTF-8
#ENV LANGUAGE C.UTF-8
#ENV LC_ALL C.UTF-8
COPY MSYH.TTC /usr/share/fonts/dejavu
COPY MSYHL.TTC /usr/share/fonts/dejavu
COPY MSYHBD.TTC /usr/share/fonts/dejavu

#更换软件源为国内的软件源
RUN mv /etc/apt/sources.list /etc/apt/sources.list.bak && \
 echo "deb http://mirrors.163.com/debian/ jessie main non-free contrib" >/etc/apt/sources.list && \
 echo "deb http://mirrors.163.com/debian/ jessie-proposed-updates main non-free contrib" >>/etc/apt/sources.list && \
 echo "deb-src http://mirrors.163.com/debian/ jessie main non-free contrib" >>/etc/apt/sources.list && \
 echo "deb-src http://mirrors.163.com/debian/ jessie-proposed-updates main non-free contrib" >>/etc/apt/sources.list
#RUN apt-get update && apt-get install -y libfontconfig1 && apt-get install -y fontconfig
RUN apt-get update && apt-get install -y fontconfig

#设置工作目录为 `/publish` 文件夹,即容器启动默认的文件夹
WORKDIR /publish

#设置Docker容器对外暴露5000端口
EXPOSE 5000

#使用`dotnet WebApplication1.dll`来运行应用程序

CMD ["dotnet", "WebApplication1.dll"]

上张成功的图:

.NET Core如何利用skiasharp文字头像生成方法  

相关内容

热门资讯

空调连续工作多久需要停机休息 空调连续工作的时间取决于多个因素,包括空调的型号、功率、使用环境和维护情况等。一般来说,空调可以连续...
空调哪个符号是除湿的 空调除湿功能通常用一个水滴形状的符号表示。不同品牌和型号的空调遥控器可能会有所差异,但一般来说,除湿...
格力空调多长时间加一次氟利昂 1、一般情况下,空调对氟利昂的使用量是非常小的,所以在空调使用了四年左右的时候再考虑加也没问题。2、...
空调用多长时间需要加氟一次 一般情况下是五年。当出现以下这几种情况时,空调才需要加氟。1、空调的室内机和室外机各有两个接口,当接...
格调生活·C标思享荟:卡萨帝在... 9月12日的郑州龙湖金融岛,夜风轻拂,灯光璀璨。“C标时刻共传奇——卡萨帝思享荟暨20周年品牌盛典郑...
品牌价值破千亿、高端份额持续领... 9月12日,“C标时刻共传奇——卡萨帝思享荟暨20周年品牌盛典郑州站”在郑州龙湖金融岛举办。2026...
空调主板坏了修800还是换新的 空调主板坏了是修还是换新,需要考虑多个因素,以下是一些建议:1. 维修成本:如果维修费用较低,比如 ...
空调开多久需要休息多长时间 问题:空调开多久需要休息多长时间回答:1、在使用空调的过程中,一般空调开7~8个小时左右需要休息2~...
中央空调多长时间清洗一次 1、一般空调开机前清洗一次即可,空调开机中间时段再清洗一次,空调关机时清洗一次,这样比较合理。2、空...
中央空调氟利昂多久加一次 看空调制热和制冷程度,很多人的观点认为氟利昂必须一年放一次,其实这个观点是错误的,理解上面有点偏差,...