四、案例研究:JavaScript图片库

js:

function showPic(whichpic){

//取得链接

var source=whichpic.getAttribute("href");

//取得占位图

var placeholder=document.getElementById("placeholder");

//改变占位图src属性

placeholer.setAttribute("src",source);

//取得文字描述

var text=whichpic.getAttibute("title");

//取得占位文字

var description=document.getElementById("description");

//改变占位文字值

description.firstChild.nodeValue=text;

}

在html中调用:

<a onclick="showPic(this); return false;"></a>

注:

nodeValue属性:node.nodeValue节点的值,通常用这个属性来获取文本值,但要注意的是在<p id="description">text</p>中,description的值是null,它的第一个子节点firstChild的值才是text

nodeType属性:节点的nodeType属性返回的是数字,共有12种值,其中,元素节点是1,属性节点是2,文本节点是3.

childNodes属性:返回的是所有类型的节点,不仅是元素节点。

五、最佳实践

利用元素的class属性,将事件处理函数从html中分离出来。

window.onload=prepareLinks;

function prepareLinks(){

//获取所有链接

var links=document.getElementsByTagName("a");

//遍历所有链接

for(var i=0; i<links.length; i++){

//找出对应类的链接

if(links[i].getAttribute("class")=="popup"){

//为对应类的链接执行事件处理函数

links[i].onclick=function(){

popUp(this.getAttribute("href"));

return false;

}

}

}

}

function popUp(winURL){

//打开一个新窗口显示winURL,窗口名为popup,宽320,高480

window.open(winURL,"popup","width=320,height=480");

}

 注:

平稳退化graceful degradation:让一些不支持javacript的浏览器也能顺利完成基本的操作。比如就算有事件处理函数,在链接中将a href设置成真实的URL。比如搜索机器人searchbot基本都不能理解javascript代码,如果不能平稳退化,搜索排名就会受损。

渐进增强:用一些额外的信息去包裹原始数据,按照渐进增强原则创建的网页几乎都能平稳退化。css代码负责关于表示的信息,javascript代码负责行为的信息,他们都应该表现为额外的指令层。

为什么用window.onload来执行函数,而不是直接执行:不管js代码放在头部还是尾部,都有可能在脚本加载时文档还不完整,有些方法就不能正常工作。而document对象是window对象的一个属性,当window对象触发onload事件时,document对象已经存在。

向后兼容:对象检测object detection如果你不理解这个方法,请离开。if(!document.getElementById) return false;

性能考虑:尽量少访问DOM和尽量减少标记数量;合并和放置脚本,将代码合并到一个js文件中,可以减少加载页面时发送的请求数量。另外,文件如果放在head里会导致浏览器无法并行加载其他文件,一般放在文档末尾body之前可以让页面变得更快;压缩脚本,有很多压缩工具,引用压缩版本,另一个在即添加注释作为副本。

六、案例研究:图片库改进版

将图片库案例的事件处理函数从html中分离出来,并增加了对象检测来保证平稳退化。

function prepareGallery(){

//对象检测

if(!document.getElementsByTagName) return false;

if(!document.getElementById) return false;

if(!document.getElementById("imagegallery")) return false;

//取得图片链接大框架

var gallery=document.getElementById("imagegallery");

//取得图片链接

var links=getElementsByTagName("a");

//遍历链接

for(var i=0; i<links.length; i++){

//对每个链接执行onclick事件,在占位showPic

links[i].onclick=function(){

//showPic执行成功了返回false,阻止默认行为。失败的话返回true,继续执行默认行为,到链接地址

return showPic(this)? false: true;

}

}

}

function showPic(whichpic){

//对象检测

if(!document.getElementById("placeholder")) return false;

//取出链接的href

var source=whichpic.getAttribute("href");

//获得占位图元素

placeholder=document.getElementById("placeholder");

//检测占位元素是否是图片元素

if(placeholder.nodenName!="IMG") return false;

//改变占位图地址为链接图片

placeholder.setAttribute("src",source);

var description=document.getElementById("description");

//有文字描述元素的话继续执行

if(description){

//链接title属性不存在的话赋值为空

var text=whichpic.getAttribute("title")? whichpic.getAttribute("title"): "";

//改变文字表述为链接的title

description.firstChild.nodeValue=text;

}

//函数执行成功的话,返回true

return true;

}

注:

this :是执行事件处理函数onclick时关联的那个元素链接

onload事件:如果只有一个函数的话直接window.onload=function1;这种情况下再加一个函数的话window.onload=function2;只有最后的那个才会被实际执行。所以如果多个的话要整合一个addloadEvent,这样每次要增加函数的话只用增加一条语句:addLoadEvent(func2);即可。

function addLoadEvent(func){

//把现有的处理函数值存入oldonload

var oldonload=window.onload;

//如果还没有绑定任何函数,则把func添加给它

if(!typeof oldonload!="function"){

window.onload=func;

}

//如果已经绑定了函数,则新函数追加到末尾

else{

window.onload=function(){

oldonload();

func();

}

}

}

DOM Core和HTML-DOM:

getElementById getElementsByTagName getAttribute setAttribute都是DOM Core,他们并不专属于javascript ,任何支持DOM的语言都可以使用;另外它们的用途也不仅限于处理网页,可以处理任何一种标记语言编写的文档。

HTML-DOM通常更短,用一个点比如用document.forms来代替document.getElementsByTagName("a"),用placeholder.src=sourc来代替placeholder.setAttribute("src",source)

最新文章

  1. HDOJ 1326. Box of Bricks 纯水题
  2. zabbix centos 6.4 安装
  3. Android Studio Gradle构建脚本
  4. bat完美关机命令
  5. UITableView添加静态背景.
  6. 如何自定义UIPickerView中文本的大小和文本靠左或靠右显示?
  7. 还是把一个课程设计作为第一篇文章吧——学生学籍管理系统(C语言)
  8. 【servlet3.0新特性】Annotation注解配置
  9. Vue下路由History mode导致页面无法渲染的原因
  10. UVA11552:Fewest Flops
  11. Exp3 免杀原理与实践 20164303 景圣
  12. TwinStickShooter的一些问题
  13. windows上redis添加密码
  14. 关于SUID SGID
  15. SSI服务端包含技术
  16. 开闭原则(Open Closed Principle,OCP)
  17. 在ant编译java文件时产生debug信息
  18. 2018-北航-面向对象第三次OO作业分析与小结
  19. 移动端页面使用rem布局
  20. 洛谷 P3302 [SDOI2013]森林 Lebal:主席树 + 启发式合并 + LCA

热门文章

  1. 报错:Caused by: org.hibernate.id.IdentifierGenerationException: ids for this class must be manually assigned before calling save(): cn.itcast.bos.domain.base.SubArea
  2. 解决PCL MLS : error LNK2019; error LNK2001 virtual MovingLeastSquares process performProcessing问题
  3. p2279&amp;bzoj1217 消防局的设立
  4. C++开源库(一) ----log4cpp详解
  5. .Net Core WebApi返回日期格式的问题
  6. webpack@3.6.0(3)-- 优化
  7. CodeForces 116B【二分匹配】
  8. hdu 1847 Good Luck in CET-4 Everybody!(巴什博弈)
  9. PAT天梯赛L3-007 天梯地图
  10. PAT甲级——1093 Count PAT&#39;s (逻辑类型的题目)