Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
475 views
in Technique[技术] by (71.8m points)

c# - Wrap ImageSource for Base64 image serialization

I have a WPF control that contains panels with images. I'm trying to serialize this so that it can be loaded standalone without having to have images in a local folder.

I know that I can store the images as a Base64 string and then possibly load that back up, but what I would like to do is wrap the ImageSource class to accept a Base64 string as the source.

I looked into the ImageSource class a bit, and I believe I just don't know enough about how it works. When I implement ImageSource in my custom wrapper class I get 2 methods that I'm unclear on:

  1. Metadata

  2. CreateInstanceCore

I was wondering if anyone could shed some light on these methods, or point me in a direction that doesn't lead me back to MSDN documentation.

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

This class wraps a BitmapImage which is initialized from a base64 string property:

public class Base64BitmapImage : BitmapSource
{
    private BitmapImage bitmap;
    private string base64Source;

    public string Base64Source
    {
        get { return base64Source; }
        set
        {
            base64Source = value;
            bitmap = new BitmapImage();

            if (DecodeFailed != null)
            {
                bitmap.DecodeFailed += DecodeFailed;
            }

            using (var stream = new MemoryStream(Convert.FromBase64String(base64Source)))
            {
                bitmap.BeginInit();
                bitmap.CacheOption = BitmapCacheOption.OnLoad;
                bitmap.StreamSource = stream;
                bitmap.EndInit();
            }

            if (DecodeFailed != null)
            {
                bitmap.DecodeFailed -= DecodeFailed;
            }

            bitmap.Freeze();
        }
    }

    public override event EventHandler<ExceptionEventArgs> DecodeFailed;

    public override bool IsDownloading
    {
        get { return false; }
    }

    public override PixelFormat Format
    {
        get { return bitmap != null ? bitmap.Format : base.Format; }
    }

    public override double DpiX
    {
        get { return bitmap != null ? bitmap.DpiX : base.DpiX; }
    }

    public override double DpiY
    {
        get { return bitmap != null ? bitmap.DpiY : base.DpiY; }
    }

    public override double Width
    {
        get { return bitmap != null ? bitmap.Width : base.Width; }
    }

    public override double Height
    {
        get { return bitmap != null ? bitmap.Height : base.Height; }
    }

    public override int PixelWidth
    {
        get { return bitmap != null ? bitmap.PixelWidth : base.PixelWidth; }
    }

    public override int PixelHeight
    {
        get { return bitmap != null ? bitmap.PixelHeight : base.PixelHeight; }
    }

    public override ImageMetadata Metadata
    {
        get { return bitmap != null ? bitmap.Metadata : base.Metadata; }
    }

    public override void CopyPixels(Array pixels, int stride, int offset)
    {
        if (bitmap != null)
        {
            bitmap.CopyPixels(pixels, stride, offset);
        }
    }

    public override void CopyPixels(Int32Rect sourceRect, Array pixels, int stride, int offset)
    {
        if (bitmap != null)
        {
            bitmap.CopyPixels(sourceRect, pixels, stride, offset);
        }
    }

    public override void CopyPixels(Int32Rect sourceRect, IntPtr buffer, int bufferSize, int stride)
    {
        if (bitmap != null)
        {
            bitmap.CopyPixels(sourceRect, buffer, bufferSize, stride);
        }
    }

    protected override Freezable CreateInstanceCore()
    {
        var instance = new Base64BitmapImage();
        instance.bitmap = bitmap;
        instance.base64Source = base64Source;
        return instance;
    }
}

It may be used like this:

<Image>
    <Image.Source>
        <local:Base64BitmapImage Base64Source="..."/>
    </Image.Source>
</Image>

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...