6

I have create a method where I want to take an image mask and apply it to another image. If you have a look at this post, you will see a frame image. The frame image in that post is the maskingImage and the background image is the imageToMask. The masking image is really an image with a hot pink center. This is the process the method goes through:

  1. The masking image is a PNG and the image to mask is a JPG.
  2. The method traces the masking image and draws the image to mask over it. This helps keep the outer transparency intact.
  3. The output form that is then drawn underneath the masking image and we make the hot pink color transparent.

The line var bitsimageToMask = imageToMask.LockBits... is where I get my error. If the width or height of the image to mask is smaller than the masking image, I get the "Parameter is not valid" error. I am a newbie when it comes to working with bitmaps.

public Bitmap RenderMaskedImage(Bitmap maksingImage, Bitmap imageToMask, Point imageToMaskOffset, ImageFormat imageFormat)
{
    using (var newImageToMaskGraphic = Graphics.FromImage(imageToMask))
    {
    newImageToMaskGraphic.DrawImage(imageToMask, imageToMaskOffset);
    }

    var output = new Bitmap(maksingImage.Width, maksingImage.Height, PixelFormat.Format32bppArgb);
    var rect = new Rectangle(0, 0, maksingImage.Width, maksingImage.Height);
    var bitsMask = maksingImage.LockBits(rect, ImageLockMode.ReadOnly, PixelFormat.Format32bppArgb);
    var bitsimageToMask = imageToMask.LockBits(rect, ImageLockMode.ReadOnly, PixelFormat.Format32bppArgb);
    var bitsOutput = output.LockBits(rect, ImageLockMode.WriteOnly, PixelFormat.Format32bppArgb);

    unsafe
    {
        for (int y = 0; y < maksingImage.Height; y++)
        {
            var ptrMask = (byte*)bitsMask.Scan0 + y * bitsMask.Stride;
            var ptrimageToMask = (byte*)bitsimageToMask.Scan0 + y * bitsimageToMask.Stride;
            var ptrOutput = (byte*)bitsOutput.Scan0 + y * bitsOutput.Stride;
            for (int x = 0; x < maksingImage.Width; x++)
            {
                ptrOutput[4 * x] = ptrimageToMask[4 * x];           // blue
                ptrOutput[4 * x + 1] = ptrimageToMask[4 * x + 1];   // green
                ptrOutput[4 * x + 2] = ptrimageToMask[4 * x + 2];   // red
                ptrOutput[4 * x + 3] = ptrMask[4 * x + 3];        // alpha 
            }
        }
    }

    maksingImage.UnlockBits(bitsMask);
    imageToMask.UnlockBits(bitsimageToMask);
    output.UnlockBits(bitsOutput);

    using (var outputGraphic = Graphics.FromImage(output))
    {
        outputGraphic.DrawImage(maksingImage.ToTransparentColor(255,0,192), 0, 0);
    }

    return output;
}

1 Answer 1

8

The reason is the rect you are using on the imageToMask is bigger then the bitmap itself.

var rect = new Rectangle(0, 0, maksingImage.Width, maksingImage.Height);
var bitsimageToMask = imageToMask.LockBits(rect, ImageLockMode.ReadOnly, PixelFormat.Format32bppArgb);

The rect is used to specify the area of the bitmap which needs to be locked. This rect can be the same size or smaller than the bitmap but can not be bigger. In your case because you use the rect based on your maskingImage the rect becomes bigger than the bitmap you are using it on which gives you that error.

Sign up to request clarification or add additional context in comments.

2 Comments

Exactly, what would be a solution to fix this?
A solution would to make a seperate rectangle for each bitmap (maskImage, imageToMask and for the output). For example I would first check if the maskImage width and height are smaller than imageToMask width and height. If yes than use the width of the maskingImage for the output, if no than use the width/height of the imageToMask for the output image and than create 3 rectangles based on the 3 bitmaps.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.