0

So I am trying to save a png of a UserControl to use as a tile. The code that i am using is

SquareTile sq = new SquareTile();
sq.Measure(new Size(336,336));
sq.Arrange(new Rect(0,0,336,336));
RenderExtensions.SaveToFile(sq);

And the RenderExtension Class looks like this

public static class RenderExtensions
{
    public static bool SaveToFile(this UIElement visualTreeElement)
    {
        WriteableBitmap wb = new WriteableBitmap(336, 336);
        wb.Render(visualTreeElement, null);
        wb.Invalidate();
        return wb.SaveToFile();
    }

    public static bool SaveToFile(this WriteableBitmap renderTargetBitmap)
    {
        try
        {
            string fname = "Shared/ShellContent/SquareTile.png";

            //StorageFile liveTileImageFile = localFolder.CreateFile("/Shared/ShellContent/SquareTile.png", CreationCollisionOption.ReplaceExisting);

            ExtendedImage ei = new ExtendedImage();
            byte[] result = new byte[renderTargetBitmap.Pixels.Length * sizeof(int)];
            Buffer.BlockCopy(renderTargetBitmap.Pixels, 0, result, 0, result.Length);
            ei.SetPixels(336,336,result);

            if (ei != null)
            {
                IsolatedStorageFile isf = IsolatedStorageFile.GetUserStoreForApplication();
                using (isf)
                {
                    if (!isf.DirectoryExists("Shared")) { isf.CreateDirectory("Shared"); }
                    if (!isf.DirectoryExists("Shared/ShellContent")) { isf.CreateDirectory("Shared/ShellContent"); }
                    if (isf.FileExists(fname)) { isf.DeleteFile(fname); }

                    using (var stream = new IsolatedStorageFileStream(fname, System.IO.FileMode.OpenOrCreate, FileAccess.ReadWrite, FileShare.ReadWrite, isf))
                    {
                        ei.WriteToStream(stream, fname);
                        stream.Close();
                    }
                }
            }
            return true;
        }
        catch (Exception ex)
        {
            return false;
        }
    }

}

Now the tile looks like this (Note background color has some transparency) enter image description here

And if I add the same UserControl in a grid, it actually looks like this enter image description here

here is the original image that this usercontrol is showing

enter image description here

You can see how red has turned blue even though the image is not transparent there. Why is this happening?

Update: I also tried a different image with only three colors red blue and yellow. turns out only red and blue are getting switched.

Rishabh876
  • 3,010
  • 2
  • 20
  • 37

2 Answers2

0

It sounds like WriteableBitmap and ExtendedImage expect their bytes to be in different formats. Probably BRGA (for WriteableBitmap) vs. RGBA (for ExtendedImage).

Unless you can specify the order on the ExtendedImage to match the WriteableBitmap you'll need to swizzle the bytes rather than just copying them straight over so that the colours line up properly.

Rob Caplan - MSFT
  • 21,714
  • 3
  • 32
  • 54
0

Ok I have managed to swap the red and blue using this function

private static byte[] convertArray(int[] array)
    {
        byte[] newarray = new byte[array.Length * 4];

        for (int i = 0; i < array.Length; i++)
        {

            newarray[i * 4] = (byte)(array[i] >> 16); 
            newarray[i * 4 + 1] = (byte)(array[i] >> 8); 
            newarray[i * 4 + 2] = (byte)(array[i]); 
            newarray[i * 4 + 3] = (byte)(array[i] >> 24); 

        }
        return newarray;
    }

so now I am not using

Buffer.BlockCopy(renderTargetBitmap.Pixels, 0, result, 0, result.Length);

to convert int[] of WriteableBitmap.Pixels to byte[] required by ExtendedImage

Rishabh876
  • 3,010
  • 2
  • 20
  • 37
  • 1
    How about using [`BitmapEncoder`](https://msdn.microsoft.com/en-us/library/windows/apps/xaml/windows.graphics.imaging.bitmapencoder.aspx)? You wouldn't need a third party library, nor doing this conversion, and it's faster, I think. It wasn't available before 8.1, but I see the question is marked with wp8.1 tag, so you might want to give it a try. – yasen Mar 18 '15 at 10:14
  • Is that available in silverlight or runtime – Rishabh876 Mar 18 '15 at 11:26
  • It's available in both – yasen Mar 18 '15 at 14:36