繁体   English   中英

使用 MagickImage 和 C# 调整图像大小并添加黑色背景

[英]Resizing an image and adding black background using MagickImage and C#

我必须使用Magick Image涵盖四种可能的场景:

  1. 如果上传的图像的宽度或高度小于 150,则将图像居中并将背景中的所有内容绘制为黑色

  2. 宽度 > 150 和纵横比不同的 1:1 从两侧裁剪图像以覆盖 150px

  3. 高度 > 150 且纵横比不同于 1:1 裁剪图像从两侧覆盖 150 像素

  4. 在所有其他情况下调整为 150x150

我很难找到文档或任何关于它的信息。 我正在使用试错法。

我首先绘制了所有案例的草图,然后我想将其实现到 C# 代码中

    public async Task<IActionResult> SetImageFroUser([FromRoute] string userId, [FromForm] byte[] avatar)
    {
        if (string.IsNullOrEmpty(userId) || avatar == null || avatar.Length == 0) return BadRequest();

        var user = await userManagerWrapper.FindByIdAsync(userId);

        if (user == null) return NotFound();

        // if (User == null || !User.IsInRole("Administrator")) return Forbid();
        if ((User == null || !User.IsInRole("Administrator")) && !user.Id.Equals(userId)) return Forbid();

        try
        {
            avatarManager.SetAvatar(user, new MemoryStream(avatar));
        }
        catch (MagickException)
        {
            return BadRequest("Invalid image format");
        }

        return NoContent();
    }

    public void SetAvatar(IntentUser user, Stream avatar)
    {
        using (var ms = new MemoryStream())
        {
            avatar.CopyTo(ms);
            ms.Seek(0, SeekOrigin.Begin);

            using MagickImage image = new MagickImage(ms);
            ms.Seek(0, SeekOrigin.Begin);
            ProcessImage(image.Width, image.Height, image);
            image.Write(ms, MagickFormat.Jpeg);

            var dbUser = database.Users.FirstOrDefault(u => u.Id == user.Id);
            if (dbUser == null)
            {
                throw new NotFoundException();
            }

            dbUser.Avatar = ms.ToArray();
            user.Avatar = dbUser.Avatar;
            database.SaveChanges();
        }
    }


    private void ProcessImage(int width, int height, MagickImage image)
    {
        double startPosition, endPosition;

    if (width < 150 && height < 150)
    {
        startPosition = 150 - width;
        endPosition = 150 - height;
        //center image
        image.Draw(new DrawableRectangle(startPosition / 2, endPosition / 2, startPosition / 2 + width, endPosition / 2 + height));

        image.Draw(new DrawableFillColor(MagickColors.Black));

        //rest of background is black
    }

    else if (width < 150 && height > 150)
    {
        startPosition = 150 - width;
        endPosition = height - 150;

        image.Draw(new DrawableRectangle(startPosition / 2, endPosition / 2, startPosition / 2 + width, endPosition / 2 + height));
        image.Draw(new DrawableFillColor(MagickColors.Black));
    }

    else if (width > 150 && height > 150 && width != height)
    {
        startPosition = width - 150;
        endPosition = height - 150;

        image.Draw(new DrawableRectangle(startPosition / 2, endPosition / 2, startPosition / 2 + width, endPosition / 2 + height));
        image.Draw(new DrawableFillColor(MagickColors.Black));
    }

    else if (width > 150 && height < 150)
    {
        startPosition = width - 150;
        endPosition = 150 - height;

        image.Draw(new DrawableRectangle(startPosition / 2, endPosition / 2, startPosition / 2 + width, endPosition / 2 + height));
        image.Draw(new DrawableFillColor(MagickColors.Black));
    }
    else
    {
        image.Resize(150, 150);

    }
    image.Strip();
    image.Quality = 75;
    }

输出图像 48x10px

这是原始图像:

在此处输入图片说明

非常简单的解决方案。

我还添加了一个检查以保留图像的外观,因此它不会被挤压:

var aspect_ratio = (decimal)image.Width / (decimal)image.Height;

    if (aspect_ratio > 1)
    {
         var newWidth = (int) Math.Round((decimal) (aspect_ratio * 150));
         image.Resize(newWidth, 150);
         // cut width and new width is multiply 150 by aspect ratio
    }

   else if (aspect_ratio < 1) 
   {
         //cut height and new height is multiply 150 by aspect ratio
         var newHeight = (int)Math.Round((decimal)((decimal)image.Height / (decimal)image.Width * 150));
         image.Resize(150, newHeight);
   }

   private void ProcessImage(MagickImage image, MemoryStream ms)
    {
        using var finalImage = new MagickImage(new MagickColor("#000000"), 150, 150);

        finalImage.Composite(image, Gravity.Center, CompositeOperator.Over);

        finalImage.Write(ms, MagickFormat.Jpg);

        image.Strip();
        image.Quality = 75;
    }

对于 ImageMagick 文档,请参阅他们的 github: https : //github.com/dlemstra/Magick.NET

如果您下载项目并打开文档,您可以看到一个文档 - 描述方法的注释,然后是方法中的逻辑。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM