实际使用“DXML”:在站点上实现 DHTML 菜单和目录(co.)

发表于:2007-06-30来源:作者:点击数: 标签:
这是有关在 Web 站点上使用可扩展的标记语言 (XML) 和可扩展的样式表语言 (XSL) 的系列文章中的第三篇。在第一篇文章中,我们谈到了使用 XML 文件存储站点的目录 (TOC) 信息,使用 XSL、层叠样式表 (CSS) 和脚本输出 DHTML TOC。在第二篇文章中,我们使用同一
这是有关在 Web 站点上使用可扩展的标记语言 (XML) 和可扩展的样式表语言 (XSL) 的系列文章中的第三篇。在第一篇文章中,我们谈到了使用 XML 文件存储站点的目录 (TOC) 信息,使用 XSL、层叠样式表 (CSS) 和脚本输出 DHTML TOC。在第二篇文章中,我们使用同一 XML 数据生成 DHTML 菜单,而在 microsoft.com 等 Web 站点中就用到了这些菜单。如果您还没有阅读这些文章,我们建议您在阅读这一篇文章之前,先阅读前两篇。

本月,我们将讨论在站点上实现菜单和 TOC 的几种不同方式。我们将解决有关实现过程和架构的几个问题,同时看一看几个案例:

在框架中直接引入 XML
在动态生成的 HTML 中使用 ASP #include
在预先创建的 HTML 中使用 ASP #include
有一点很重要,必须注意:尽管我们能够用任一浏览器查看输出的 DHTML,但是只要进行 XSL 转换,就必须安装 Internet Explorer 5。如果像在第一个案例中,需要将 XML 发送到客户机,则客户机必须是 Internet Explorer 5。如果像在第二个和第三个案例中,要在服务器上转换 XML,则服务器上必须安装 Internet Explorer 5。(注意:在服务器上可以只安装可重分发的 Microsoft XML 分析程序(英文))。

案例 1:在框架中直接引入 XML
如果您处于完全的 Internet Explorer 5 环境中(如 intranet),将输出发送给用户的最简单的方式可能是借助于 Internet Explorer 5 直接浏览 XML(英文) 的功能。Internet Explorer 5 可以使用相关的样式表提交 XML;您不需要进行显式转换。您只需要指定带有处理指南(英文)的 XSL 样式表。

在第一个案例中,我们使用自己的 TOC 作为例子,TOC 框架中将包含一个文件,其 webdev.xml 文件将引用 TOC 样式表,如下所示:

<?xml version="1.0"?>
<?xml-stylesheet type="text/xsl" href="toc.xsl"?>

<TOPICLIST TYPE="Web Dev References">
  .
  .
  .
</TOPICLIST>
TOC 框架自身将包含在框架集中,如下所示:

<FRAMESET COLS="150,*">
  <FRAME NAME="fraToc" SRC="webdev.xml">
  <FRAME NAME="fraContent" SRC="home.htm">
<FRAMESET>
如果您用 Internet Explorer 5 查看这些代码,您可以查看 XML 浏览 TOC 演示。

浏览 XML 除了是一种向用户发送带样式的 XML 的简便方式,它还是一种非常好的调试 XSL 样式表的方式,即使您要在服务器上进行转换,也可以使用这种方式。Internet Explorer 可以在出现错误时为您提供即时的反馈,包括行号和错误类型。

案例 2:在动态生成的 HTML 中使用 ASP #includes
在许多情况下,除了 Internet Explorer 5 之外,您还需要顾及其他浏览器,或者希望只用 XML 构成 HTML 文档的一部分(如顶端的菜单),而不是整篇文档。ASP #include 命令为在较大型文档中插入几个字符的 HTML 和跨多页共享公用代码提供了一个非常好的方式。通过在 #include 文件中进行 XSL 转换,可以非常方便地对 ASP #includes 进行扩展,以便利用 XML。

#include 文件将加载 XML 和 XSL 文件,将其转换为 HTML,然后将 HTML 写入 ASP 文档。如下所示是包含菜单的 ASP 文档:

列表 1:使用“动态” #includes 的通用 HTML 文档模板
<HTML>
<HEAD>
<TITLE>Dynamic ASP #include demo</TITLE>
</HEAD>
<BODY>
<!-- #include file="menus_dyn.inc" -->
<P>此处为常规文档内容...</P>
</BODY>
</HTML>
Include 文件将完成所有繁琐的工作。

列表 2:menus_dyn.inc
<% @LANGUAGE="JScript" %>
<%
  var sXml = "webdev.xml";
  var sXsl = "menus.xsl";
  
  var oXmlDoc = Server.CreateObject("Microsoft.XMLDOM");
  oXmlDoc.async = false;
  oXmlDoc.load(Server.MapPath(sXml));
  
  if (false != oXmlDoc.parseError)
  {
    Response.Write(@#XML parseError on line @# + oXmlDoc.parseError.line);
    Response.End();
  }

  var oXslDoc = Server.CreateObject("Microsoft.XMLDOM");
  oXslDoc.async = false;
  oXslDoc.load(Server.MapPath(sXsl));

  if (false != oXslDoc.parseError)
  {
    Response.Write(@#XSL parseError on line @# + oXslDoc.parseError.line);
    Response.End();
  }

  Response.Write(oXmlDoc.transformNode(oXslDoc));
%>
从上一篇文章开始,我已经将菜单升级为可跨浏览器使用,所以您能够应用任一浏览器查看动态 #include 演示。

案例 3:在预先创建的 HTML 中使用 ASP #include
在服务器负荷较重的情况下,或您无论因何种原因,不希望在每次加载菜单时调用 XML 对象,您可以选择第三种方案:脱机进行转换。在这一情况下所使用的代码与“真正的”include 几乎完全相同。

唯一的区别是:有别于使用 Response.Write 输出所需要的 HMTL,我们可以使用 Scripting.FileSystemObject 对象将已转换的 HTML 保存到一个文件中。

列表 3:makemenus.asp
<% @LANGUAGE="JScript" %>
<%
  var sXml = "webdev.xml";
  var sXsl = "menus.xsl";
  
  var oXmlDoc = Server.CreateObject("Microsoft.XMLDOM");
  oXmlDoc.async = false;
  oXmlDoc.load(Server.MapPath(sXml));
  
  if (false != oXmlDoc.parseError)
  {
    Response.Write(@#XML parseError on line @# + oXmlDoc.parseError.line);
    Response.End();
  }

  var oXslDoc = Server.CreateObject("Microsoft.XMLDOM");
  oXslDoc.async = false;
  oXslDoc.load(Server.MapPath(sXsl));

  if (false != oXslDoc.parseError)
  {
    Response.Write(@#XSL parseError on line @# + oXslDoc.parseError.line);
    Response.End();
  }

  var sOutput = oXmlDoc.transformNode(oXslDoc);
  var sIncFileName = "menus_pre.inc";
  
  var oFS = Server.CreateObject("Scripting.FileSystemObject");
  var oIncFile = oFS.CreateTextFile(Server.MapPath(sIncFileName));
  oIncFile.Write(sOutput);
  oIncFile.Close();
  
  Response.Write(@#The include file <A HREF="@# + sIncFileName + @#">@#
    + sIncFileName + @#</A> was suclearcase/" target="_blank" >ccessfully created.@#);
%>
我们不是写入到 ASP 响应流,而是在服务器上创建了一个“静态”文件,其中包含已转换的 HTML。换句话说,与将 XML 转换代码直接置于 #include 文件不同,所有的转换代码都将位于 “实用程序”ASP 页中,该 ASP 页将生成 include 文件。

如果您需要对 Web 应用程序使用编译过程,您可能会喜欢这种方式。无论任何时候更新 menus.xml 文件,我们只需加载 makemenus.asp ,输出一个更新的 #include 文件。将这一算法用在 Visual Basic 应用程序中能够实现同一目的。

像在案例 2 中一样,我们在所有使用这些菜单的文档中添加这一 #include 文件。

列表 4:使用“预先创建”的 #include 的通用 HTML 文档模板
<HTML>
<HEAD>
<TITLE>Dynamic ASP #include demo</TITLE>
</HEAD>
<BODY>
<!-- #include file="menus_pre.inc" -->
<P>此处为常规文档内容...</P>
</BODY>
</HTML>
当然,对于用户来说输出结果与案例 2 是一样的,但您可以查看各种情况下的静态 #include 演示。

三个案例的代码位于压缩的源代码存档文件中。

George Young 是 Microsoft 的 Windows 站点的开发负责人,以前曾在 Site Builder Network 站点从事开发工作。在他有空时,喜欢用 Windows 媒体播放器收听墨西哥广播电台的节目,也常开着他的宝贝卡迪车往返于新奥尔良和华盛顿之间的 Redmond。

已存档的代码角专栏
1999 年
5 月 24 日    “DXML”Redux:从 XML 创建动态的 HTML 菜单
4 月 26 日    “DXML”:将 TOC 从 XML 带到 DHTML
3 月 30 日    Redirecting Traffic: A Smart Custom 404 Message for IIS 4.0(英文版)










 

原文转自:http://www.ltesting.net