《锋利的JS》之 超链接提示
这是《锋利的JQ》第三章里的案例,主要实现的功能就是当鼠标划过链接时,用特定的提示代替a标签默认的title提示。
效果如图所示:
结构如下 :
<style type="text/css"> body{ margin:0; padding:40px; background:#fff; font:80% Arial; color:#555; line-height:180%;} p{ clear:both; margin:0; padding:.5em 0;} #tooltip{position:absolute; border:1px solid #333; background:#f7f5d1; padding:1px; color:#333; display:none;} </style> </head> <body> <p><a href="#" class="tooltip" title="这是我的超链接提示1.">提示1.</a></p> <p><a href="#" class="tooltip" title="这是我的超链接提示2.">提示2.</a></p> <p><a href="#" title="这是自带的提示1.">自带提示1.</a></p> <p><a href="#" title="这是自带的提示2.">自带提示2.</a></p> </body>
建立了四个a标签,后两个默认不作处理以进行对比,CSS中定义了一个id为tooltip的样式,留作弹出提示用。
下面是它的JQ代码:
$(function(){ var x = 10; var y = 20; $("a.tooltip").mouseover(function(e){ this.myTitle = this.title; this.title = ''; var tooltip = "<div id='tooltip'>" + this.myTitle + "</div>"; $("body").append(tooltip); $("#tooltip").css({ top : (e.pageY + y) + "px", left : (e.pageX + x) + "px" }).show("fast"); }).mouseout(function(){ this.title = this.myTitle; $("#tooltip").remove(); }).mousemove(function(e){ $("#tooltip").css({ "top" : (e.pageY + y) + "px", "left" : (e.pageX + x) + "px" }) }) })
虽然说JQ的实现思想可能跟我们JS的实现思想不同,但从这一个例子来说,个人觉得是一样的,所以,可以从JQ里总结出实现这效果的思路:
1.当然是先获取所要的两个a标签,添加鼠标onmouseover和onmouseout事件,由于html结构里有直接给了两个class,所以,我们可以直接通过class来获取到这两个a标签。
2.显示出提示效果。在这里,可以通过创建一个id为tooltip的div,并将a的title属性作为这个div的内容,最后添加到body上,并通过鼠标事件进行定位。
大概思路就是如此,我们还是直接用代码来解释吧。如下:
window.onload = function(){ var aList = getElementsByClassName("tooltip"); //获取a元素 var x = 10,y = 20; //定位用 var tooltip; for(var i = 0,l = aList.length; i < l; i++){ aList[i].onmouseover = function(evt){ evt = fixEvt(evt); //事件的兼容处理 this.myTitle = this.title; //如果有title属性的话,默认的提示效果还是会弹出来,所以,要将默认的取消 this.title = ''; var div = document.createElement("div"); //创建提示内容 div.setAttribute("id","tooltip"); var text = document.createTextNode(this.myTitle); div.appendChild(text); tooltip = document.body.appendChild(div); tooltip.style.top = (evt.pageY + y) + "px"; //提示内容的定位 tooltip.style.left = (evt.pageX + x) + "px"; tooltip.style.display = "block"; } aList[i].onmouseout = function(){ this.title = this.myTitle; //将title内容还给title属性,如若不然,下次就获取不到title内容鸟 document.body.removeChild(tooltip); //移除div } aList[i].onmousemove = function(evt){ //鼠标移动时也进行定位 evt = fixEvt(evt); tooltip.style.top = (evt.pageY + y) + "px"; tooltip.style.left = (evt.pageX + x) + "px"; } } } function getElementsByClassName(className,node){ //通过类名获取元素,返回一个元素数组 node = node || document; if(node.getElementsByClassName){ return node.getElementsByClassName(className); } var eles = node.getElementsByTagName('*'); var reg = []; for(var i = 0,l = eles.length; i < l; i++){ if(hasClass(className,eles[i])){ reg.push(eles[i]); } } return reg; } function hasClass(className,node){ //判断是否含有某类名 var eles = node.className.split(/\s+/); for(var i = 0,l = eles.length; i < l; i++){ if(eles[i] == className){ return true; } } return false; } function fixEvt(evt){ //处理事件的兼容性 evt = evt || window.event; if(!evt.pageX){ evt.pageX = evt.clientX + document.documentElement.scrollLeft - 2; evt.pageY = evt.clientY + document.documentElement.scrollTop - 2; } return evt; }
我在实现这个JS代码的过程中,主要收获是处理pageX的兼容性上,在这之前我没接触过,通过google后,才了解,在IE中并不兼容此属性,并找了相关解决方案。才知道IE下想实现pageX的效果是要通过cliendX加上滚动条的滚动距离再减去默认的滚动条2个边框像素。所以才有了fixEvt函数。
/**************************华丽的分界线***************************************/
经高手点拨,说不要通过固定的x=10; y=20;这样定位置,而应该根据所划过元素的宽高进行定位,可以通过offsetWidth和offsetHeigth获取到元素自身的绝对宽高。还有,最好就是通过控制显示隐藏来达到效果,而不是每次都创建而移除提示信息,因为这样会影响效率。最后,有必要的话,就给封装成函数。但这里只是访写,实现即可,具体的自己学习到了,将来应用到了,再应用。