2017-03-28 4 views
0

나는 자른 비트 맵이 있습니다CroppedBitmap을 투명하게 만드는 방법은 무엇입니까?

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

을 나는 투명 흰색 설정해야합니다.

crop.MakeTransparent(Colors.White); 

누구가 어떤 아이디어/제안이 : 불행하게도,이 (CroppedBitmap는 'MakeTransparent'에 대한 정의가 포함되어 있지 않습니다) 작동하지 않는 이유는 무엇입니까?

미리 감사드립니다.

~~~~~~~~~~~~~~~이 코드 How can I make all white (FFFFFFFF) pixel in an image(ImageBrush) to be transparent

을 발견하지만 구현할 때

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()); 
    } 

그것은 WHITE가되지 않습니다

투명한; 그것은 BLACK과 WHITE를 대체 Solution to transparency problem

답변

1

한 가지 가능한 :

enter image description here


편집 솔루션이 솔루션은 여기입니다

(문제는 WPF와 투명성과 관련이있다) 변형은 CroppedBitmap에서 쓰기 가능한 비트 맵을 만드는 것입니다 :

WriteableBitmap writeable = new WriteableBitmap(cropped); 

그러면 비트 맵의 ​​각 픽셀을 분석하여 흰색 픽셀을 투명하게 변경할 수 있습니다. 가장 빠른 방법은 Lock 메서드를 사용하여 픽셀 버퍼를 가져온 다음 안전하지 않은 코드를 사용하여 BackBuffer을 반복하는 것입니다. 더 간단하지만 느린 방법은 CopyPixelsWritePixels 방법을 사용하는 것입니다.

+0

이 어떻게 안전하지 않은 코드를 사용하여 백 버퍼를 통해 잠금 방법 다음 루프를 사용하여 픽셀 버퍼를 얻을 보여줍니다 링크를 알고 계십니까? – zetar

+0

MSDN에 샘플이 있습니다. https://msdn.microsoft.com/en-us/library/system.windows.media.imaging.writeablebitmap(v=vs.110).aspx (예제의 DrawPixel 메서드 참조) 페이지 하단). IntPtr을 int로 변환하기 때문에 완벽하지는 않습니다. 따라서 64 비트 플랫폼에서는 IntPtr이 실패 할 수 있습니다. 대신 byte *로 할 수 있고 포인터로 직접 작업 할 수 있습니다. 단일 잠금 호출 후에 모든 바이트를 처리 한 다음 마지막에 잠금 해제를 호출 할 수 있습니다. – Pavel