Creación de ficheros de imágenes en asp.net
Algunos tipos de aplicaciones pueden requerir la manipulación de imágenes, una galería de fotos, perfiles de un portal corporativo, incluso la creación de iconos o marcas de agua en tiempo de ejecución. Anteriormente en c/c++ requería prácticamente trabajar a nivel de bits para los valores RGB, por suerte en .net está el namespace System.Drawing que nos permite trabajar con la API GDI+ de creación/manipulación de imágenes. Pero en el portal de desarrolladores CodePlex han dado un paso y se han preocupado de crear una librería y control que como en telecentrosgm permite crear iconos personalizados y configurar opciones de cache para las imágenes. Veamos las pocas lineas de código necesarias. El control en cuestión es asp.net Generated Image, así que después de bajarlo e incluir la librería .dll en nuestro proyecto podremos empezar a utilizarlo. Su funcionamiento a través de un httphandler, de manera que invocamos este handler desde la etiqueta img o asp:image, devolviéndonos la imagen. En el caso de la aplicación telecentrosgm queremos un icono
... <table> <tbody> <tr> <td> ImageUrl='<%# string.Format("~/Images/NumberToImageHandlerCS.ashx?number={0}", Container.DisplayIndex + 1) %>' /></td> <td> <%# Eval("Address")%> <%# Eval("City")%>, <%# Eval("Region")%> <%# Eval("PostalCode")%></td> </tr> </tbody> </table> <%# Eval("DistanceFromAddress", "{0:0.00}")%> Kms ...
En cuanto al código del httphandler, debemos de incluir los namespace Microsoft.Web y System.Drawing. La clase base hereda de IHttpHandler por lo que a nosotros nos queda poco más que poner el código para el icono.
<%@ WebHandler Language="C#" Class="NumberToImageHandlerCS" %> using System; using System.Web; using Microsoft.Web; using System.Drawing; using System.Drawing.Imaging; public class NumberToImageHandlerCS : ImageHandler { public NumberToImageHandlerCS() { base.ContentType = ImageFormat.Png; base.EnableClientCache = true; } public override ImageInfo GenerateImage(System.Collections.Specialized.NameValueCollection parameters) { SizeF sz; var numberFont = new Font("Verdana", 12, FontStyle.Bold); using (var dummyBitmap = new Bitmap(1, 1)) { var dummyGraphics = Graphics.FromImage(dummyBitmap); sz = dummyGraphics.MeasureString(parameters["number"], numberFont); } var realWidth = sz.Width + 6; var realHeight = sz.Height + 4; var realBitmap = new Bitmap(Convert.ToInt32(realWidth), Convert.ToInt32(realHeight)); var realGraphics = Graphics.FromImage(realBitmap); realGraphics.Clear(Color.Transparent); realGraphics.FillEllipse(Brushes.Navy, 0, 0, realWidth, realHeight); realGraphics.DrawString(parameters["number"], numberFont, new SolidBrush(Color.White), 3, 2); return new ImageInfo(realBitmap); } }
La opción de cache se configura a través de las propiedades EnableClientCache y EnableServerCache, por defecto están a false, basta con asignarlas a true en el constructor de la clase. En este caso se usa la cache del lado del cliente que añade un response.cache en la cabecera de la respuesta, en el lado del servidor crea un directorio temporal donde se guardan las imágenes creadas.