在 C# 中使用 imagick 将 .HEIC 转换为 JPEG

问题描述 投票:0回答:5

我在将 heic 文件转换为 jpeg 时遇到问题

我已经尝试过在线搜索它,我可以找到如何写入文件夹,但不知道如何获取转换后的文件的字节[]以便我可以保存它

       byte[] file = null;
        file = Convert.FromBase64String(dto.File);

        //Convert HEIC/HEIF to JPF
        if (extension == "HEIC" || extension == "HEIF")
        {
          try
          {
           using (MagickImageCollection images = new MagickImageCollection())
            {
              images.Read(file);
              using (IMagickImage vertical = images.AppendVertically())
              {
                var imgname = filename + ".jpeg";
                vertical.Format = MagickFormat.Jpeg;
                vertical.Density = new Density(300);
                vertical.Write(imgname);
                extension = "jpeg";
            }
            }
          }
          catch (Exception ex)
          {
            Elmah.ErrorSignal.FromCurrentContext().Raise(ex);
          }
        }
            documentId = Service.AddSupportingDocument(file, extension , userName);

我无法获取输出文件,它只是一个字符串

c# imagick imagemagick.net
5个回答
14
投票

其他解决方案。

适用于 dotnet 6Nuget 软件包 Magick.NET-Q16-AnyCPU

using ImageMagick;

string[] allfiles = Directory.GetFiles(@"__PATH__", "*.heic", SearchOption.AllDirectories);

foreach (var file in allfiles)
{
    FileInfo info = new FileInfo(file);
    using (MagickImage image = new MagickImage(info.FullName))
    {
        // Save frame as jpg
        image.Write(@$"__OUTPATH__{info.Name}.jpg");
    }
}

7
投票

根据文档,就像 @SLaks 建议的那样,您需要通过 MemoryStream 来完成此操作。直接从文档中检查这个示例

// Read first frame of gif image
using (MagickImage image = new MagickImage("Snakeware.gif"))
{
    // Save frame as jpg
    image.Write("Snakeware.jpg");
}

// Write to stream
MagickReadSettings settings = new MagickReadSettings();
// Tells the xc: reader the image to create should be 800x600
settings.Width = 800;
settings.Height = 600;

using (MemoryStream memStream = new MemoryStream())
{
    // Create image that is completely purple and 800x600
    using (MagickImage image = new MagickImage("xc:purple", settings))
    {
        // Sets the output format to png
        image.Format = MagickFormat.Png;
        // Write the image to the memorystream
        image.Write(memStream);
    }
}

// Read image from file
using (MagickImage image = new MagickImage("Snakeware.png"))
{
    // Sets the output format to jpeg
    image.Format = MagickFormat.Jpeg;
    // Create byte array that contains a jpeg file
    byte[] data = image.ToByteArray();
}

0
投票

您需要创建一个

MemoryStream
,调用
.Write()
将图像写入内存流,然后在流上调用
.ToArray()
以获取其写入的字节。


0
投票

这对我使用 dotnet 6Nuget Package Magick.NET-Q16-AnyCPU

有效
using (MagickImage image = new MagickImage(filePath))
{
    image.Format = MagickFormat.Jpeg;
    // Save frame as jpg
    image.Write(filePath2);
}

0
投票

补充 @Sios 的答案,我使用任务测试了代码,对于许多图像,代码使用 100% 的 PC 资源(它始终取决于您的硬件)将它们的转换速度提高了 4 倍。 这是更新后的代码:

using ImageMagick;
using System.Diagnostics;

Stopwatch stopWatch = new Stopwatch();
stopWatch.Start();

var inputPath = "D:\\Wallpapers";
var outputPath = "D:\\Wallpapers\\PNG_Test2";
string[] allfiles = Directory.GetFiles(inputPath, "*.heic", SearchOption.AllDirectories);

var tasks = new List<Task>();


foreach (var file in allfiles)
{

    tasks.Add(Task.Run(() =>
    {
        FileInfo info = new FileInfo(file);
        using (MagickImage image = new MagickImage(info.FullName))
        {
            Console.WriteLine("Processing: " + info.FullName);
            image.Format = MagickFormat.Jpg;
            image.Write(Path.Join(outputPath, info.Name + ".Jpg"));
            Console.WriteLine("Processed: " + info.FullName);
        }
    }));
}

Task.WaitAll(tasks.ToArray());

TimeSpan ts = stopWatch.Elapsed;
string elapsedTime = String.Format("{0:00}:{1:00}:{2:00}.{3:00}",
    ts.Hours, ts.Minutes, ts.Seconds,
    ts.Milliseconds / 10);

Console.WriteLine(elapsedTime);
Console.WriteLine("Done");
© www.soinside.com 2019 - 2024. All rights reserved.