简体   繁体   English

如何使CroppedBitmap透明?

[英]How to make a CroppedBitmap transparent?

I have a cropped bitmap: 我有一个裁剪的位图:

 CroppedBitmap crop = new CroppedBitmap(rtb, new Int32Rect(MapOffset, MapOffset, BOARD_WIDTH - 1 - MapOffset, BOARD_HEIGHT - 1 - MapOffset));

and I need to set white to transparent. 我需要将白色设置为透明。 Unfortunately, this does not work (CroppedBitmap does not contain a definition for 'MakeTransparent'): 不幸的是,这不起作用(CroppedBitmap不包含“ MakeTransparent”的定义):

crop.MakeTransparent(Colors.White);

Anybody have any ideas / suggestions? 有人有什么想法/建议吗?

Thanks in advance. 提前致谢。

~~~~~~~~~~~~~~~ ~~~~~~~~~~~~~~~

I found this code How can I make all white (FFFFFFFF) pixel in an image(ImageBrush) to be transparent 我发现此代码如何使图像(ImageBrush)中的所有白色(FFFFFFFF)像素透明

But when I implement it 但是当我实现它时

    public void SaveMainCanvas2BMP(string filename)
    {

        // Write BMP
        VisualBrush sourceBrush = new VisualBrush(MainCanvas);
        DrawingVisual drawingVisual = new DrawingVisual();
        DrawingContext drawingContext = drawingVisual.RenderOpen();
        using (drawingContext)
        {
            drawingContext.DrawRectangle(sourceBrush, null, new Rect(new Point(- MapOffset, - MapOffset), new Point(BOARD_WIDTH - 1 + MapOffset, BOARD_HEIGHT - 1 + MapOffset)));
        }

        RenderTargetBitmap rtb = new RenderTargetBitmap(BOARD_WIDTH - 1, BOARD_HEIGHT - 1, 96, 96, PixelFormats.Default);
        rtb.Render(drawingVisual);

        //crops  rectangle at position (0,0).
        CroppedBitmap crop = new CroppedBitmap(rtb, new Int32Rect(0, 0, BOARD_WIDTH - 1, BOARD_HEIGHT - 1));

        WriteableBitmap writeable = new WriteableBitmap(crop);

        // Code to turn WHITE pixels TRANSPARENT
        int pixelWidth = (int)writeable.Width;
        int pixelHeight = (int)writeable.Height;
        int Stride = pixelWidth * 4;

        BitmapSource imgSource = (BitmapSource)writeable;
        byte[] pixels = new byte[pixelHeight * Stride];
        imgSource.CopyPixels(pixels, Stride, 0);
        byte TransparentByte = byte.Parse("0");
        byte Byte255 = byte.Parse("255");
        int N = pixelWidth * pixelHeight;
        //Operate the pixels directly
        for (int i = 0; i < N; i++)
        {
            byte a = pixels[i * 4];
            byte b = pixels[i * 4 + 1];
            byte c = pixels[i * 4 + 2];
            byte d = pixels[i * 4 + 3];
            if (a == Byte255 && b == Byte255 && c == Byte255 && d == Byte255)
            {
                pixels[i * 4] = TransparentByte;
                pixels[i * 4 + 1] = TransparentByte;
                pixels[i * 4 + 2] = TransparentByte;
                pixels[i * 4 + 3] = TransparentByte;
            }
        }
        WriteableBitmap writeableBitmap = new WriteableBitmap(pixelWidth, pixelHeight, 96, 96,
            PixelFormats.Pbgra32, BitmapPalettes.Halftone256Transparent);
        writeableBitmap.WritePixels(new Int32Rect(0, 0, pixelWidth, pixelHeight), pixels, Stride, 0);



        //encode as BMP
        BitmapEncoder bmpEncoder = new BmpBitmapEncoder();

        bmpEncoder.Frames.Add(BitmapFrame.Create(writeableBitmap));

        //save to memory stream
        System.IO.MemoryStream ms = new System.IO.MemoryStream();
        bmpEncoder.Save(ms);
        ms.Close();
        System.IO.File.WriteAllBytes(filename, ms.ToArray());
    }

It doesn't make WHITE transparent; 它不会使WHITE透明。 it replaces WHITE with BLACK: 它将WHITE替换为BLACK:

在此处输入图片说明


EDIT SOLUTION 编辑解决方案

The solution is over here (the problem has to do with WPF and transparency): Solution to transparency problem 解决方案就在这里(问题与WPF和透明度有关): 透明度问题的解决方案

One possible variant is to create a writable bitmap from your CroppedBitmap: 一种可能的变体是从您的CroppedBitmap创建可写位图:

WriteableBitmap writeable = new WriteableBitmap(cropped);

Then you can analyze each pixel of your bitmap and change white pixels to transparent ones. 然后,您可以分析位图的每个像素,并将白色像素更改为透明像素。 The fastest way to do it is to get the pixel buffer using the Lock method and then loop through the BackBuffer using unsafe code. 最快的方法是使用Lock方法获取像素缓冲区,然后使用不安全的代码循环遍历BackBuffer The simpler but slower way is to use CopyPixels and WritePixels methods. 比较简单但较慢的方法是使用CopyPixelsWritePixels方法。

The problem was with the way WPF handles transparency (BMPs are not the way to go, PNGs are). 问题在于WPF处理透明度的方式(不是BMP,而PNG是)。

Solution here: Solution to transparency problem 这里的解决方案: 透明度问题的解决方案

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

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