Click here to Skip to main content
15,896,606 members
Articles / Web Development / ASP.NET

Control to Display Binary Images in ASP.NET

Rate me:
Please Sign up or sign in to vote.
4.60/5 (12 votes)
31 Mar 2009CPOL1 min read 80.5K   1.9K   25  
The RbmBinaryImage control will help you display images directly from your database. You could bind the Image field directly to the ImageContent property, and also specify whether you want the display to be as a thumbnail and provide the thumbnail size.
/*
************************************************************************************************************************************
***                                                                                                                              ***
*** By Ramy Mostafa -							                                                                                 ***
*** http://www.ramymostafa.com                                                                                                   ***
*** 31/03/2009                                                                                                                   ***
*** Last Modified March 31 2009                                                                                               ***
************************************************************************************************************************************
*/
using System;
using System.Collections.Generic;
using System.Text;
using System.Web.UI.WebControls;
using System.Web.Caching;
using System.Web.Security;
using System.IO;
using System.Drawing;
using System.ComponentModel;
using System.Web.UI;
using System.Web;
using System.Drawing.Drawing2D;
using System.Drawing.Imaging;

[assembly: TagPrefix("RbmControls","Rbm")]
namespace RbmControls
{
    /// <summary>
    /// RbmBinaryImage Control allows you to bind image database field directly to the control ImageContent also it allows you
    /// to create thumbnails from those images and display them
    /// </summary>
    [ToolboxData("<{0}:RbmBinaryImage runat=\"server\" />")]
    public class RbmBinaryImage : System.Web.UI.WebControls.Image
    {
        #region Properties
        private static int ImageControlCount = 1;
        private StateBag sbViewState;
        ///// <summary>
        ///// Here I Create my own statebag object of ViewState to use in the control so that each control maintain it's own viewstate.
        ///// </summary>
        //[Browsable(false)]
        //public StateBag ViewState
        //{
        //    get
        //    {
        //        if (sbViewState == null)
        //            sbViewState = new StateBag();
        //        return sbViewState;
        //    }
        //}

        /// <summary>
        /// In case the ImageContent and ImageUrl are empty then the image inside the empty image url will be
        /// displayed
        /// </summary>
        [
            Browsable(true),
            Description("Set or Get a Url When ImageContent Is Null for the image control"),
        ]
        public string EmptyImageUrl
        {
            get
            {
                string imageUrl = ViewState["EmptyImageUrl"] as string;
                return (imageUrl == null) ? "" : imageUrl;
            }
            set
            {
                ViewState["EmptyImageUrl"] = value;
            }
        }

        /// <summary>
        /// The CacheKey The control uses to display the images
        /// </summary>
        private string CacheKey
        {
            get
            {
                string cacheKey = ViewState["CacheKey"] as string;
                return (cacheKey == null) ? "" : cacheKey;
            }
            set
            {
                ViewState["CacheKey"] = value;
            }
        }

        /// <summary>
        /// The byte content of the image
        /// </summary>
        [
            Browsable(true),
            Description("Set or Get Content Data for the image control")
        ]
        public byte[] ImageContent
        {
            get
            {
                byte[] imageBytes = ViewState["ImageContent"] as byte[];
                if (!DisplayThumbnail)
                    return (imageBytes == null) ? null : imageBytes;
                else if (imageBytes != null)
                {
                    byte[] bytes = CreateThumb();
                    return bytes;
                }
                else
                    return null;
            }
            set
            {
                ViewState["ImageContent"] = value;
            }
        }
        /// <summary>
        /// The Thumbmail required size this field is only used in case the DisplayThumbnail Property is true
        /// </summary>
        [
            Browsable(true), Category("Properties"), DefaultValue("150"),
            Description("Set or Get the Size of the thumbnail created from the original image, if SizeIsHeight is set to true then its used as height else used as width")
        ]
        public int ThumbnailSize
        {
            get
            {
                object o = ViewState["ThumbnailSize"];
                return (o == null) ? 150 : (int)o;
            }
            set { ViewState["ThumbnailSize"] = value; }
        }
        /// <summary>
        /// This field is used while generating the thumbnail, it basically says that the thumbnail size is value of the height not 
        /// the width.
        /// </summary>
        [
            Browsable(true), Category("Properties"), DefaultValue("false"),
            Description("Set or Get the SizeIsHeight value if it is set to true then ThumbnailSize is used for height, else it is used for width")
        ]
        public bool SizeIsHeight
        {
            get
            {
                object o = ViewState["SizeIsHeight"];
                return (o == null) ? false : (bool)o;
            }
            set { ViewState["SizeIsHeight"] = value; }

        }
        /// <summary>
        /// When this property is set to true the Image will be displayed as a thumbnail
        /// </summary>
        [
            Browsable(true), Category("Properties"), DefaultValue("false"),
            Description("Set or Get DisplayThumbnail value, used to check if the image will be displayed as thumbnail")
        ]
        public bool DisplayThumbnail
        {
            get
            {
                object o = ViewState["DisplayThumbnail"];
                return (o == null) ? false : (bool)o;
            }
            set { ViewState["DisplayThumbnail"] = value; }

        }
        /// <summary>
        /// The mimetype of the image
        /// </summary>
        [
            Browsable(true), DefaultValue("image/jpeg"),
            Description("Mime type (e.g., image/jpeg)")
        ]
        public string MimeType
        {
            get
            {
                object o = ViewState["MimeType"];
                return (o == null) ? "image/jpeg" : (string)o;
            }
            set { ViewState["MimeType"] = value; ; }
        }
        #endregion

        #region Caching
        /// <summary>
        /// States whether or not the control should enable caching.
        /// </summary>
        [
            Browsable(true), Category("Caching"), DefaultValue("false"),
            Description("Specifies whether image should be cached in memory")
        ]
        public bool EnableCachinge
        {
            get
            {
                
                object o = ViewState["EnableCaching"];
                return (o == null) ? false : (bool)o;
            }
            set { ViewState["EnableCaching"] = value; }

        }
        [
            Browsable(true), Category("Caching"), DefaultValue(""),
            Description("Cached duration in seconds")
        ]

        #endregion

        #region Rendering
        ///<summary>
        /// Override the OnPreRender Method to state the ImageUrl correctly based on the properties set
        /// The first case is if the ImageContent has data then it's set the Url to the RbmImageHandler
        /// Then check if the ImageUrl is empty it sets the ImageUrl to the EmptyImageUrl
        ///</summary>
        protected override void OnPreRender(EventArgs e)
        {
            base.OnPreRender(e);
            if (DesignMode)
                return;
            if (ImageContent != null)
            {
                if (string.IsNullOrEmpty(CacheKey))
                {
                    CacheKey = "Rbm" + System.DateTime.Now.Ticks + ImageControlCount;
                    ImageControlCount++;
                }
                ImageUrl = String.Format("~/__RbmImageHandler.rbm?MimeType={0}&EnableCaching={1}&ImageContent={2}",
                    MimeType, EnableCachinge ? "1" : "0", CacheKey);
                if(this.Context.Cache[CacheKey] == null)
                    this.Context.Cache[CacheKey] = ImageContent;
            }
            else if (ImageUrl == "" || ImageUrl == null)
            {
                ImageUrl = EmptyImageUrl;
            }
        }
        #endregion

        #region Methods
        /// <summary>
        /// Get the Image Format based on the MimeType
        /// </summary>
        /// <returns></returns>
        private ImageFormat GetFormat()
        {
            ImageFormat result = ImageFormat.Jpeg;
            switch (MimeType)
            {
                case "image/gif":
                    result = ImageFormat.Gif;
                    break;
                case "image/png":
                    result = ImageFormat.Png;
                    break;
                case "image/bmp":
                    result = ImageFormat.Bmp;
                    break;
                case "image/tiff":
                    result = ImageFormat.Tiff;
                    break;
                case "image/x-icon":
                    result = ImageFormat.Icon;
                    break;
                default:
                    result = ImageFormat.Jpeg;
                    break;
            }
            return result;
        }
        /// <summary>
        /// Create thumb from the original ImageContent
        /// </summary>
        /// <returns></returns>
        private byte[] CreateThumb()
        {
            try
            {
                byte[] imageBytes = ViewState["ImageContent"] as byte[];
                if (imageBytes == null)
                    return null;
                MemoryStream stream = new MemoryStream(imageBytes);
                Bitmap tempImage = new Bitmap(stream);
                int dw = tempImage.Width; ;
                int dh = tempImage.Height;
                int compareSize = dw;
                if (dw > ThumbnailSize || dh > ThumbnailSize)
                {
                    int tw = ThumbnailSize;
                    int th = ThumbnailSize;
                    double zw = (tw / (double)dw);
                    double zh = (th / (double)dh);

                    double z = SizeIsHeight ? zh : zw;
                    dw = (int)(dw * z);
                    dh = (int)(dh * z);
                }



                Bitmap m_Image = new Bitmap(dw, dh);
                Graphics g = Graphics.FromImage(m_Image);
                g.InterpolationMode = InterpolationMode.HighQualityBicubic;
                g.DrawImage(tempImage, 0, 0, dw, dh);
                g.Dispose();
                tempImage.Dispose();
                stream = new MemoryStream();
                m_Image.Save(stream, GetFormat());
                return stream.GetBuffer();
            }
            catch (Exception ex)
            {

            }
            return null;
        }
        #endregion
    }

    /// <summary>
    /// The Image Handler handles the ProcessRequest comming from the RbmBinaryImage to display the image in the browser
    /// </summary>
    public class RbmImageHandler : IHttpHandler
    {

        #region IHttpHandler Members

        public bool IsReusable
        {
            get { return true; }
        }
        /// <summary>
        /// The ProcessRequest Method is used to write the image to the response
        /// </summary>
        /// <param name="context"></param>
        public void ProcessRequest(HttpContext context)
        {

            #region Caching Properties
            string cacheKey = context.Request["ImageContent"];
            if (String.IsNullOrEmpty(cacheKey))
                return;
            bool enableCaching = false;
            if (!String.IsNullOrEmpty(context.Request["EnableCaching"]))
                Boolean.TryParse(context.Request["EnableCaching"], out enableCaching);
            #endregion
            
            #region Image Properties
            string mimeType = context.Request["MimeType"];
            if (string.IsNullOrEmpty(mimeType))
                mimeType = "image/jpeg";
            byte []imageData = context.Cache[cacheKey] as byte[];
            #endregion

            if (!enableCaching)
                context.Cache.Remove(cacheKey);
            context.Response.ContentType = mimeType;
            context.Response.OutputStream.Write(imageData, 0, imageData.Length);
        }

        #endregion
    }
}

By viewing downloads associated with this article you agree to the Terms of Service and the article's licence.

If a file you wish to view isn't highlighted, and is a text file (not binary), please let us know and we'll add colourisation support for it.

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)


Written By
Software Developer (Senior)
Egypt Egypt
Fun Coder Smile | :) My Job is my Hobby Smile | :)

Comments and Discussions