如何从 .net 核心上的 SVG 生成 System.Drawing.Image?

tor*_*dil 3 c# svg asp.net-core

我在 C# 框架中找到了许多读取 SVG 并将其转换为 System.Drawing.Image 或 png 的库,但在 .net core 中找不到任何方法。

如果我使用 Image.FromFile,我会得到一个 OutOfMemoryException(据说是因为 SVG 不是光栅化格式)。

关于如何使用 Image 读取 SVG 或任何在 .net core 中工作的开源库的任何提示?

itm*_*nus 5

  1. Xamarin 团队的Skiasharp似乎是一个不错的选择。docs.microsoft.com上已经有 API 文档。有关更多详细信息,请参阅Mono/SkiaSharpMono/mono/SkiaSharp.Extended

  2. 您可以通过以下方式在nuget上安装官方 svg 扩展dotnet add package SkiaSharp.Svg

    <PackageReference Include="SkiaSharp.Svg" Version="1.60.0" />
    
    Run Code Online (Sandbox Code Playgroud)
  3. 演示:

        var svgSrc=Path.Combine(Directory.GetCurrentDirectory(),"img.svg");
        string svgSaveAs = "xyz.png";
        var quality = 100;
    
        var svg = new SkiaSharp.Extended.Svg.SKSvg();
        var pict = svg.Load(svgSrc);
        var dimen = new SkiaSharp.SKSizeI(
            (int) Math.Ceiling(pict.CullRect.Width),
            (int) Math.Ceiling(pict.CullRect.Height)
        );
        var matrix = SKMatrix.MakeScale(1,1);
        var img = SKImage.FromPicture(pict,dimen,matrix);
    
        // convert to PNG
        var skdata = img.Encode(SkiaSharp.SKEncodedImageFormat.Png,quality);
        using(var stream = File.OpenWrite(svgSaveAs)){
            skdata.SaveTo(stream);
        }
    
    Run Code Online (Sandbox Code Playgroud)

截屏:

在此处输入图片说明


小智 5

您可以使用 ImageMagick 将 svg 转换为任何格式。

<PackageReference Include="Magick.NET-Q16-AnyCPU" Version="7.14.0" />
Run Code Online (Sandbox Code Playgroud)

下面的方法将 svg base64 字符串转换为其他格式。

public static string Base64ToImageStream(string base64String)
    {
        byte[] imageBytes = Convert.FromBase64String(base64String);
        using (MemoryStream ms = new MemoryStream(imageBytes, 0, imageBytes.Length))
        {
            using (var msOut = new MemoryStream())
            {
                MagickReadSettings readSettings = new MagickReadSettings()
                {
                    Format = MagickFormat.Svg,
                    Width = 60,
                    Height = 40,
                    BackgroundColor = MagickColors.Transparent
                };

                using (MagickImage image = new MagickImage(imageBytes, readSettings))
                {
                    image.Format = MagickFormat.Png; // Specify the format you need
                    image.Write(msOut);
                    byte[] data = image.ToByteArray();
                    return Convert.ToBase64String(data);

                    // In case if you want the output in stream
                    // byte[] imgByte = Convert.FromBase64String(pngBase64);
                    // var pngStream = new MemoryStream(imgByte, 0, imgByte.Length);
                    // return pngStream;
                }
            }
        }            
    }
Run Code Online (Sandbox Code Playgroud)