您的位置:首页 > 理论基础 > 计算机网络

使用HttpHandler为图片添加水印

2011-07-19 10:42 351 查看
需求:1、为所有的大图添加水印2、不要直接在图片上生成水印,要保持图片的原汁原味3、要求可配置,配置的选项包括是否启用水印,水印图片可以更换,水印的位置可以更换解决方案: 在我们的图片管理系统中,用户上传的图片都通过一个二级域名进行管理,如 images.photocms.com所以就只需在这个应用中,拦截所有的图片请求交由asp.net处理,在asp.net程序中处理原图和水印图片,将结果输出给用户即可。 具体步骤如下: 1、配置IIS,将jpg后缀名的请求用aspnet_isapi.dll来接收处理。 2、配置Web.config ,添加.jpg处理程序对应的具体asp.net类 <add verb="*" path="*.jpg" type="PhotoCms.Common.WaterMark,PhotoCms.Common" />具体技术实现: 其中具体的 HttpHandler 程序

public class WaterMark : IHttpHandler

{
public void ProcessRequest(HttpContext context)
{
HttpResponse Response = context.Response;
HttpRequest Request = context.Request;

Response.ContentType = "image/jpeg";
string filePath = Request.FilePath;
string physicalPath = context.Server.MapPath(filePath);

if (!File.Exists(physicalPath))
return;

string waterImagePath = context.Server.MapPath("/watermark.png");
IList<string> ruleList=new List<string>();
string isOpen=string.Empty;
int padding = 10;

watermarkConfig objWaterConfig = watermarkConfig.GetInstance();
if (objWaterConfig != null)
{
isOpen=objWaterConfig.isOpen;
waterImagePath = context.Server.MapPath(objWaterConfig.filePath);
ruleList = objWaterConfig.rules;
padding = objWaterConfig.padding;
}

bool doWaterMark=false;
foreach(string _rule in ruleList)
{
if(filePath.Contains(_rule))
{
doWaterMark=true;
continue;
}
}

if(isOpen.Equals("1") && doWaterMark)
{
physicalPath = context.Server.MapPath(filePath);
ImageHelper obj = new ImageHelper(physicalPath);
obj.InsertImage(waterImagePath, Common.WathermarkPosition.BottomRight,padding);
obj.GetImage().Save(Response.OutputStream, System.Drawing.Imaging.ImageFormat.Jpeg);
obj.Dispose();
}
else
{
physicalPath = context.Server.MapPath(filePath);
byte[] buffer = new Byte[10000];
int length;
long dataToRead;
System.IO.Stream iStream = null;

iStream = new System.IO.FileStream(physicalPath, System.IO.FileMode.Open, System.IO.FileAccess.Read, System.IO.FileShare.Read);
dataToRead = iStream.Length;

Response.Buffer = false;
while (dataToRead > 0)
{
if (Response.IsClientConnected)
{
length = iStream.Read(buffer, 0, 10000);
Response.OutputStream.Write(buffer, 0, length);
Response.Flush();

buffer = new Byte[10000];
dataToRead = dataToRead - length;
}
else
{
dataToRead = -1;
}
}
iStream.Close();

}

}

public bool IsReusable
{
get
{
return false;
}
}

}

public class watermarkConfig
{
public string isOpen = string.Empty;
public string filePath = string.Empty;
public int padding = 0;
public IList<string> rules=new List<string>();

private static watermarkConfig instance;
private watermarkConfig()
{
loadConfigFile();
}

public static watermarkConfig GetInstance()
{
if (instance == null)
{
instance = new watermarkConfig();
}
return instance;
}

private void loadConfigFile()
{
string configFile = HttpContext.Current.Request.ApplicationPath + "/config/photo/photo.config";
XmlDocument xml = new XmlDocument();
xml.Load(HttpContext.Current.Server.MapPath(configFile));

XmlNode waterroot = xml.SelectSingleNode("picture/watermark");
this.isOpen = waterroot.Attributes["isOpen"].Value;
this.filePath = waterroot.Attributes["filePath"].Value;
this.padding = Convert.ToInt32(waterroot.Attributes["padding"].Value);
foreach(XmlNode rule in waterroot.ChildNodes)
{
if (rule.NodeType != XmlNodeType.Comment)
{
if (rule.Name.ToLower().Equals("rule"))
{
rules.Add(rule.Attributes["urlfrom"].Value);
}
}

}
}
}

/config/photo/photo.config 的内容

<!--水印设置,isOpen 1开启水印 其他值关闭,filePath 水印图片的物理路径, rule 包含哪些字符串的图片需要加水印--> <watermark isOpen="1" filePath="~/watermark.png" padding="100"> <rule urlfrom="/photo/e0"></rule> <rule urlfrom="/photo/f0"></rule> <rule urlfrom="/photo/a0"></rule> </watermark>
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: