图片查看器处理程序
为加快处理速度,IIS会直接处理Web应用程序中的某些静态资源,而不会调用ISAPI扩展。这些静态文件包括图像和HTML文件。如果从浏览器直接请求gif或jpg文件,IIS会获取指定的资源,正确设置响应缓冲的内容类型,并将其输出成文件的字节流.
如果浏览器地址指向包含多个图像的虚拟目录呢?在这种情况下,IIS无法识别文件夹的内容,而可能只返回文件的列表。
那么如何实现指向该虚拟目录地址,在浏览器中显示该目录下图片的预览呢?
图片查看器HTTP处理程序的设计
首先,需要确定如何使IIS知道我们的意图?可以通过在文件夹名称后追加一个特定的端点,使IIS将请求传给ASP.NET,由ASP.NET来提供其中图像的预览。换言之,这个思路是,将图片查看器处理程序与一个特定的端点(如folder.axd)绑定。固定端点所指向的不必一定是已经存在的、已部署好的资源,将folder.axd追加到文件夹名之后即可。如下地址所示:
http://www.contoso.com/images/folder.axd
处理程序此时要做的是,提取URL中文件夹名,并选出其中的图片以预览。
在ASP.NET中,axd扩展名通常用于引用特殊服务。用于跟踪的Trace.axd,及用于插入脚本和资源的WebResource.axd,都是使用该扩展名的典型案例。
图片查看器HTTP处理程序的实现
图片查看器处理程序要返回一个包含指定文件夹中所有图像的多列表格。该类的结构如下:
class
PictureViewerInfo
{
public
PictureViewerInfo()
{
DisplayWidth
=
200
;
ColumnCount
=
3
;
}
public
int
DisplayWidth;
public
int
ColumnCount;
public
string
FolderName;
}
public
class
PictureViewerHandler : IHttpHandler
{
public
void
ProcessRequest(HttpContext context)
{
PictureViewerInfo info
=
GetFolderInfo(context);
string
html
=
CreateOutput(info);
//
Output the data
context.Response.Write(
"
<html><head><title>
"
);
context.Response.Write(
"
Picture Web Viewer
"
);
context.Response.Write(
"
</title></head><body>
"
);
context.Response.Write(html);
context.Response.Write(
"
</body></html>
"
);
}
public
bool
IsReusable
{
get
{
return
true
; }
}
...
}
为获取实际的路径,只需从URL中去除“folder.axd”字符串及所有斜杠和反斜杠。随后,我们将文件夹的URL映射到服务器的路径,通过.NET Framework进行处理。
private
ArrayList GetAllImages(
string
path)
{
string
[] fileTypes
=
{
"
*.bmp
"
,
"
*.gif
"
,
"
*.jpg
"
,
"
*.png
"
);
ArrayList Images
=
new
ArrayList();
DiectoryInfo di
=
new
DirectoryInfo(path);
foreach
(
string
ext
in
fileTypes)
{
FileInfo[] files
=
di.GetFiles(ext);
if
(files.Length
>
0
)
images.AddRange(files);
}
return
images;
}
输出图片预览:
string
CreateOutputForFolder(PictureViewerInfo info)
{
ArrayList images
=
GetAllImages(info.FolderName);
Table t
=
new
Table();
int
index
=
0
;
bool
moreImages
=
true
;
while
(moreImages)
{
TableRow row
=
new
TableRow();
t.Rows.Add(row);
for
(
int
i
=
0
; i
<
info.ColumnCount; i
++
)
{
TableCell cell
=
new
TableCell();
row.Cells.Add(cell);
//
Create the image
Image img
=
new
Image();
FileInfo fi
=
(FileInfo)images[index];
img.ImageUrl
=
filName;
img.Width
=
Unit.Pixel(info.DisplayWidth);
//
Wrap the image in an anchor so tha a larger image is
//
shown when the user clicks
HtmlAnchor a
=
new
HtmlAnchor();
a.Href
=
new
HtmlAnchor();
a.Controls.Add(img);
cell.Controls.Add(a);
//
Check whether there are more images to show
index
++
;
moreImages
=
(index
<
images.Count);
if
(
!
moreImage)
break
;
}
}
string html = Utils.RenderControlAsString(t);
return html;
}
我们可使该处理程序接受一些可选的查询字符串参数(如图像宽度和列数)。下面是处理URL查询字符串的过程:
PictureViewerInfo info
=
new
PictureViewInfo();
object
p1
=
context.Request.Params[
"
Width
"
];
object
p1
=
context.Request.Params[
""
];
下面是处理URL查询字符串的过程:
PictureViewerInfo
=
new
PictureViewerINfo();
object
p1
=
context.request.Params[
"
Width
"
];
object
p2
=
context.request.Params[
"
Cols
"
];
if
(p1
!=
null
)
Int32.TryParse((
string
)p1,
out
info.DisplayWidth);
if
(p1
!=
null
)
Int32.TryParse((
string
)p2,
out
info.ColumnCount);
该处理程序的注册非常简单,将以下脚本添加到web.config即可:
<
add verb
=
"
*
"
path
=
"
folder.axd
"
type
=
"
Core35.Components.PictureViewerHandler, Core35Lib
"
/>
将生成的程序集置于GAC中,并将这段脚本插入到全局的web.config中,那么当前计算机中所有的应用程序都可共享该功能了。
使用示例: