Javascript/JQuery五步入门——正则&DOM&事件

1.正则表达式检测是否为URL——总结正则表达式相关知识

正则表达式测试工具 http://tool.chinaz.com/regex/ 通过这个可以检测我们的正则表达式是否匹配了希望的内容。

下面用十点简要总结正则表达式的一些基本用法。

一,创建一个正则表达式

var reg = /pattern/;
或 var reg = new RegExp('pattern');

二,正则表达式方法

reg.exec(str); 或 str.match(reg); 都是返回数组,exec只返回第一个匹配即只有一个元素的正则信息数组while(match=reg.exec(str))console.log(match[1])遍历输出匹配到的字符串,而match是在指定全局g时返回每一个匹配。
reg.test(str); 返回布尔值以表示是否成功
str.replace(reg,'c'); 将str字符串中匹配reg的部分用’’代替,结果作为返回值被返回
str.search(reg); 返回正则表达式第一次匹配的位置
str.split(reg); 返回分割后的数组

三,限制匹配个数的语法规则 

1. c{n} 

{1}表示一个的意思。/c{1}/只能匹配一个c。 /c{n}/则会匹配n个连续的c。
reg = /c{1}/;
str='cainiao';
execReg(reg,str);
返回结果c
reg = /c{2}/;
str='cainiao';
execReg(reg,str);
返回结果null,表示没有匹配成功。

2. c{m,n}

c{3,4}的意思是,连续的3个c或者4个c。
reg = /c{3,4}/;
str='ccccTest';
execReg(reg,str);
结果返回cccc,这表明正则会尽量多品牌,可3可4的时候它会选择多匹配一个。

3. c{n,}

c{1,}表示1个以上的c。例如:
reg = /c{1,}/;
str='cccccTest';
execReg(reg,str);
返回ccccc,再次说明了正则表达式会尽量多地匹配。
reg = /c{2,}/;
str='cainiao';
execReg(reg,str);
结果返回null,c{2,}表示2个以上的c,而cainiao中只有1个c。

4. *  +  ? 与转意\* \+ \?

* 表示0次或者多次,可有可无,等同于{0,},即c* 和 c{0,} 是一个意思。
+ 表示一次或者多次,必须出现,等同于{1,},即c+ 和 c{1,} 是一个意思。
? 表示0次或者1次,可无可有一次,等同于{0,1},即c? 和 c{0,1} 是一个意思。
如果我们真的想匹配’c*’这个字符串的时候,就要将*转义
reg = /c\*/;
str='c*';
execReg(reg,str);
返回匹配的字符串:c*。
同理,要匹配其他元字符,只要在前面加上一个“\”就可以了。

5. 贪心模式与非贪心模式

只要在合法的情况下,正则会尽量多去匹配字符,叫做贪心模式。
如果我们希望正则尽量少地匹配字符,那么就可以在表示数字的符号后面加上一个?变成非贪心模式。
{n,}?, *?, +?, ??, {m,n}?

reg = /c{1,}?/;
str='ccccc';
execReg(reg,str);
返回的结果只有1个c,尽管有5个c可以匹配,但是由于正则表达式是非贪心模式,所以只会匹配一个。

四,边界\b 非边界\B /^开头  $/结尾匹配

\b表示的边界的意思,也就是说,只有字符串的开头和结尾才算数。例如/\bc/就表示字符串开始的c或者是结尾的c。看下面的例子:
reg = /\bc/;
str='cainiao';
execReg(reg,str);
返回结果c。匹配到了左边界的c字符。
reg = /\bc/;
str='维生素c';
execReg(reg,str);
仍然返回c,不过这次返回的是右侧边界的c。
reg = /\bc/;
str='bcb';
execReg(reg,str);
这次匹配失败,因为bcb字符串中的c被夹在中间,既不在左边界也不再右边界。

与\b对应\B表示非边界。例如:
reg = /\Bc/;
str='bcb';
execReg(reg,str);
这次会成功地匹配到bcb中的c,而
reg = /\Bc/;
str='cainiao';
execReg(reg,str);
则会返回null。因为\B告诉正则,只匹配非边界的c。
^表示只匹配字符串的开头。看下面的例子: reg = /^c/; str='维生素c'; execReg(reg,str); 结果为null,因为字符串‘维生素c’的开头并不是c,所以匹配失败。 reg = /^c/; str='cainiao'; execReg(reg,str); 这次则返回c,匹配成功,因为cainiao恰恰是以c开头的。 与^相反,$则只匹配字符串结尾的字符: reg = /c$/; str='维生素c'; execReg(reg,str); 这次返回的结果是c,表明匹配成功。

五,代表任意非\n的点’.’ 

reg = /./;
str='cao';
execReg(reg,str);
结果显示,正则匹配到了字符c。
reg = /.+/;
str='blue——经典  好_。';
execReg(reg,str);
结果是所有的字符都被匹配掉了,包括一个空格,一个下滑线,和一个破折号。
reg = /^./;
str='\ncaao';
execReg(reg,str);
结果是null,终于失败了,正则要求字符串的第一个字符不是换行,但是恰恰字符是以\n开始的。

六,正则表达式中的或,“|“

b|c表示,匹配b或者c。
reg = /b|c/;
str='blue';
execReg(reg,str);
结果是b。
reg = /^b|c.+/;
str='caao';
execReg(reg,str);
匹配开头的b或者是c.+,c开头则匹配掉整个caao。

七,子正则表达式的括号与其多义

reg = /^(b|c).+/;
str='bbs.blueidea.com';
execReg(reg,str);
这次的结果是整个串bbs.blueidea.com,加上上面的括号这后,正则表示,如果字符串的开头是b或者c,那么匹配开头的b或者c以及其后的所有的非换行字符。

 

 

捕获

 

 

(exp)

匹配exp,并捕获文本到自动命名的组里

(?<name>exp)

匹配exp,并捕获文本到名称为name的组里,也可以写成(?’name’exp)

(?:exp)

匹配exp,不捕获匹配文本,也不给分组分配组号

 

 

 断言

 

 

 

(?=exp)

匹配exp前面位置,但是不匹配exp

(?<exp)

匹配exp后面位置,但是不匹配exp

(?!exp)

匹配后面的不是exp的位置,但是不匹配exp

(?<!exp)

匹配前面不是exp的位置,但是不匹配exp

小括号的多义,分组捕获。

var reg1 = /(\d{3}) (\d{3})/
var str = '111 222'
str.replace(reg1, '$2 $1') // => '222 111' , 注意这里的$2,$1,存放了匹配的字符串
 
var reg2 = /(\d{3})(\d{4})(\d{4})/
var mobile = '13522722724'
reg2.test(mobile)
RegExp.$1 // => 135
RegExp.$2 // => 2272
RegExp.$3 // => 2724
 
var reg3 = /(\d{3})(\d{4})(\d{4})/
var mobile = '13522722724'
mobile.replace(reg3, '$1 $2 $3') // => '135 2272 2724'

较长的正则表达式中,反向引用会降低匹配速度,性能降低,不需要反向引用时应使用分组不捕获,括号前加?:。 

另外正则有一个限制相邻信息而不实际匹配的语法,括号前加?=。最适合的例子就是将12个数字分拆成3组4个数字,.replace(/(\d{4})(?=\d)/g,"$1 ")。 

在/g全局匹配基础上,逐4个替换成$1+空格,当第三组不满足后面为数字的相邻限制,不做替换,最后没有冗余空格。

var reg = /(John) (?=Resig)/
reg.test('John') // => false
reg.test('John Backus') // => false
reg.test('John Reisg') // => true
RegExp.$1 // => 'John',注意这里不是 "John Resig"

参考: http://www.cnblogs.com/dwlsxj/p/Regex.html 

 

另外,正则表达式\+数字n表示匹配的第n个group

捕获组可以通过从左到右计算其开括号来编号。例如,在表达式 ((A)(B(C))) 中,存在四个这样的组: 

1     ((A)(B(C))) 
2     \A 
3     (B(C)) 
4     (C) 

组零始终代表整个表达式。 

之所以这样命名捕获组是因为在匹配中,保存了与这些组匹配的输入序列的每个子序列。捕获的子序列稍后可以通过 Back 引用在表达式中使用,也可以在匹配操作完成后从匹配器检索。 

/^(11+?)\1+$/ 解释:以11开头的非贪婪模式匹配至少2个连续的1,作为组1被匹配1次或多次(被用来检测1的个数是否为素数)。

(\w)((?=\1\1\1)(\1))+ 解释:重复4次或以上的字母匹配除最后两位之前的部分

Java中Matcher.group(n) 和 s.substring(m.start(n), m.end(n)) 是等效的

 

八,一个字符[abc] 反[^abc]

[abc]表示a或者b或者c中的任意一个字符,[^abc]就表示不能是a,b或者c中的任何一个。
^在正则表达式开始部分的时候表示开头的意思,例如/^c/表示开头是c;但是在字符集和中,它表示的是类似“非“的意思。

reg = /^[abc]/;
str='bbs';
execReg(reg,str);
返回结果是b。
reg = /[^abc]/;
str='blue';
execReg(reg,str);
返回的结果是l,因为它是第一个非abc的字符(即第一个b没有匹配)。

在字字符集合中可以使用如下的表示方式:[a-z],[A-Z],[0-9],分别表示小写字母,大写字母,数字。例如:
reg =  /^[a-zA-Z][a-zA-Z0-9_]+/;
str='test';
execReg(reg,str);
结果是整个test,正则的意思是开头必须是英文字母,后面可以是英文字母或者数字以及下划线。

九,数字\d 非数字\D 英文字符\w

\d表示数字的意思,相反,\D表示非数字。例如:
reg = /\d/;
str='cao8';
execReg(reg,str);
返回的匹配结果为8,因为它是第一个数字字符。

reg = /\D/;
str='cao8';
execReg(reg,str);
返回c,第一个非数字字符。

\w表示英文字符,等同于字符集合[a-zA-Z0-9_]。例如:
reg = /\w+/;
str='blue';
execReg(reg,str);
返回完整的blue字符串,因为所有字符都是单词字符。
reg = /\w+/;
str='.className';
execReg(reg,str);
结果显示匹配了字符串中的className。

\W表示非单词字符,等效于[^a-zA-Z0-9_]
reg = /\W+/;
str='中文如何?';
execReg(reg,str);
返回完整的字符串,因为,无论是中文和“?”都算作是非单词字符。

十,几种空白字符匹配

\f匹配换页符,\n匹配换行符,\r匹配回车,\t匹配制表符,\v匹配垂直制表符。
\s匹配单个空格,等同于[\f\n\r\t\v]。例如:
reg = /\s.+/;
str='This is a test  String.';
execReg(reg,str);
返回“is a test String.”,正则的意思是匹配第一个空格以及其后的所有非换行字符。

同样,\S表示非空格字符。
reg = /\S+/;
str='This is a test  String.';
execReg(reg,str);
匹配结果为This,当遇到第一个空格之后,正则就停止匹配了。

 

实例

用正则表达式写Encode与Decode

    /*1.用浏览器内部转换器实现html转码*/
    htmlEncode:function (html){
        //1.首先动态创建一个容器标签元素,如DIV
        var temp = document.createElement ("div");
        //2.然后将要转换的字符串设置为这个元素的innerText(ie支持)或者textContent(火狐,google支持)
        (temp.textContent != undefined ) ? (temp.textContent = html) : (temp.innerText = html);
        //3.最后返回这个元素的innerHTML,即得到经过HTML编码转换的字符串了
        var output = temp.innerHTML;
        temp = null;
        return output;
    },
    /*2.用浏览器内部转换器实现html解码*/
    htmlDecode:function (text){
        //1.首先动态创建一个容器标签元素,如DIV
        var temp = document.createElement("div");
        //2.然后将要转换的字符串设置为这个元素的innerHTML(ie,火狐,google都支持)
        temp.innerHTML = text;
        //3.最后返回这个元素的innerText(ie支持)或者textContent(火狐,google支持),即得到经过HTML解码的字符串了。
        var output = temp.innerText || temp.textContent;
        temp = null;
        return output;
    },
    /*3.用正则表达式实现html转码*/
    htmlEncodeByRegExp:function (str){  
         var s = "";
         if(str.length == 0) return "";
         s = str.replace(/&/g,"&amp;");
         s = s.replace(/</g,"&lt;");
         s = s.replace(/>/g,"&gt;");
         s = s.replace(/ /g,"&nbsp;");
         s = s.replace(/\'/g,"&#39;");
         s = s.replace(/\"/g,"&quot;");
         return s;  
   },
   /*4.用正则表达式实现html解码*/
   htmlDecodeByRegExp:function (str){  
         var s = "";
         if(str.length == 0) return "";
         s = str.replace(/&amp;/g,"&");
         s = s.replace(/&lt;/g,"<");
         s = s.replace(/&gt;/g,">");
         s = s.replace(/&nbsp;/g," ");
         s = s.replace(/&#39;/g,"\'");
         s = s.replace(/&quot;/g,"\"");
         return s;  
   }

 

综合写出检测一个字符串是否为一个有效URL的JS正则表达式程序

<script type="text/javascript">
function IsURL(urlString)
{
var regExp = /^((https?|ftp|news):\/\/)?([a-z]([a-z0-9\-]*[\.。])+([a-z]{2}|aero|arpa|biz|com|coop|edu|gov|info|int|jobs|mil|museum|name|nato|net|org|pro|travel)|(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5]))(\/[a-z0-9_\-\.~]+)*(\/([a-z0-9_\-\.]*)(\?[a-z0-9+_\-\.%=&]*)?)?(#[a-z][a-z0-9_]*)?$/;
 
     if (regExp.test(urlString) == true){
        document.getElementById('div1').innerHTML="It is a url";
     }
     else {
        document.getElementById('div1').innerHTML="It's not a url";
        }
}
function OC(){
    IsURL(document.getElementById('txt').value);
}
</script>
</head>

<body>
<input id="txt" type="text" />
<input id="btn" type="button" onClick="OC()" value="检查"/>
<label><div>鉴定结果</div><div id=div1></label>
</body>
</html>

http://www.iteye.com/topic/481228

检查邮箱地址格式

n = n.replace(/[。|,|,|、]/g, "."), /^[A-Z_a-z0-9-\.]+@([A-Z_a-z0-9-]+\.)+[a-z0-9A-Z]{2,4}$/.test(n)

IP合法性检测 使用正则分组,四部分都不能大于255

((2[0-4]\d|25[0-5]|[01]?\d\d?)\.){3}(2[0-4]\d|25[0-5]|[01]?\d\d?)

 

 

2.遍历与事件响应,计时器

1:首先页面加载时马上响应JS代码如下运行(不一定要等所有的JS和图片加载完毕,就可以执行方法):

$(document).ready(function(){
});

另一种简单写法:

$(function () {
})

2:当然有些必须要等到所有元素都加载完才可以执行JS方法,可以如下面这种写法:

$(window).load(function() {
});

3:还有一种是DOM元素加载之前执行Jquery代码:

(function() {
        })(jQuery)

 

对body中多个按钮定义onclick事件,用window.event.srcElement得到操作的按钮。

<head>
<meta charset="UTF-8">
<title>HTML</title>

<script type="text/javascript">
function btn() {
    var inputs = document.getElementsByTagName("input");
    for (var i =0; i < inputs.length; i++) {  
        var input = inputs[i];
           input.onclick = btnclick;
    }
}
function btnclick() {
    var inputs = document.getElementsByTagName("input");
    for (var i =0; i < inputs.length; i++) {
        var input = inputs[i];
        if (input == window.event.srcElement) {
            input.value ="Selected"; 
        }
    }
}
</script>

</head>
<body onload="btn()">
<input type="button" value="Botton"/>
<input type="button" value="Botton"/>
<input type="button" value="Botton"/>
</body>


inervalId=setInterval("CountDown()",1000);

clearInterval(inervalId);

时钟实现

<!doctype html>
<html>
<head>
<meta charset="UTF-8">
<title>Untitled Document</title>
<script type="text/javascript">
function check(day)
{
    if(day < 10)
        return '0'+day;
    else
        return ''+day;
}
function show()
{
    var oDate=new Date();
    var str=check(oDate.getHours())+""+check(oDate.getMinutes())+""+check(oDate.getSeconds())+"";
    document.getElementById('txt').value=str;
}
window.onload=function()
{
    var B1=document.getElementById('btn1');
    var B2=document.getElementById('btn2');
    var timer;
    
    B1.onclick=function()
    {
            show();
            timer=setInterval("show()", 1000);
    }
    B2.onclick=function()
    {
            clearInterval(timer);
    }
}
</script>
</head>

<body>
<input id="btn1" type="button" value="Open"/>
<input id="btn2" type="button" value="Close"/>
<div>
<input id="txt" type="text">
</body>
</html>

 

屏幕数值获取与html注入,模拟QQ虚假弹窗

<!doctype html>
<html>
<head>
<meta charset="UTF-8">
<title>Untitled Document</title>
<script>
document.writeln('<div id="qqaddiv" style="position:absolute;\">');
document.writeln('<a href="javascript:;" onclick=closeR()><img src=qq.gif border=0></a>'); 
document.writeln("</div>");
var bodyfrm = document.documentElement;
var AD = document.getElementById("qqaddiv").style;
AD.top = ( bodyfrm.clientHeight - 184) + "px";
AD.left = ( bodyfrm.clientWidth - 257 ) + "px";
function init() {
    //alert(document.body.scrollTop);
    AD.top = ( document.body.scrollTop + bodyfrm.clientHeight - 184) + "px";
    AD.left = ( document.body.scrollLeft + bodyfrm.clientWidth - 257) + "px";
}

var timer;
function closeR(){
    AD.display="none";
    clearInterval(timer);
}

window.onload=function(){
    timer=setInterval("init();", 0);
    var oUl=document.getElementById('ul1');
    var i=0;
    for(i=0;i<100;i++){
        var oLi=document.createElement('li');
        oLi.innerHTML=''+i;
        oUl.appendChild(oLi);
    }
}
</script>
</head>

<body>
<ul id=ul1>
</ul>
</body>
</html>

运用计时器制作淡入淡出的侧边分享栏

<!doctype html>
<html>
<head>
<style>
#div1 {width:100px; height:200px; background:#ccc; position:absolute; left:-100px; opacity:0.3;}
#div1 span {width:20px; height:60px; line-height:20px; text-align:center; left:100px; top:0px; position:absolute; background:yellow;}
</style>
<meta charset="UTF-8">
<title>Untitled Document</title>
<script type="text/javascript">
var timer=null;

function move(speed, end, alpha){
    var oD=document.getElementById('div1');
    var A=0.3;
    if(!timer) {
        timer=setInterval(function(){
        if(oD.offsetLeft==end){
            alert(oD.style.opacity);
            clearInterval(timer);
            timer=null;
        }
        else
            oD.style.left=oD.offsetLeft + speed + 'px';
            A+=alpha;
            oD.style.opacity=A;
        }, 30);
    }
}
window.onload=function(){
    var oD=document.getElementById('div1');
    oD.onmouseover=function(){
        move(10, 0, 0.03);
    }
    oD.onmouseout=function(){
        move(-10, -100, -0.003);
    }
}
</script>
</head>

<body>
<div id="div1">
    <span>分享到</span>
</div>
</body>
</html>

 

3.运动框架

已经封装好的JS运动框架代码,传入Object和JSon,就可以对对象进行style数值运动变化。

注意要将计时器设置在对象上,opacity属性特殊处理。

在Jquery中有.animation({json},'slow',func(){}) 就可以作为我们的运动框架了。

一些特殊效果也有如 fadeIn(500)/fadeOut(500)/fadeTo(0.5, 500) slideUp(500) 灵活使用

function getstyle(obj,name){
    if(obj.currentStyle){
        return obj.currentStyle[name];  
    }else{
          return getComputedStyle(obj,false)[name];
    }
} 
function startMove(obj,json,func){
    clearInterval(obj.timer); 
    obj.timer=setInterval(function(){
        var check=true;
        for(var attr in json){
            var cur=0;
            if(attr=='opacity'){
                cur=parseInt(parseFloat(getstyle(obj,attr))*100);
            } else {
                cur=parseInt(getstyle(obj,attr));
            }
            var speed=(json[attr]-cur)/6;
            speed=speed>0?Math.ceil(speed):Math.floor(speed);
            if(cur!=json[attr]){
                check=false;
                if(attr=='opacity'){
                    obj.style.filter='alpha(opacity:'+(cur+speed)+')';
                    obj.style.opacity=(cur+speed)/100;
                }
                else
                    obj.style[attr]=cur+speed+'px';
            }
        }
        if(check){
            clearInterval(obj.timer);
            if(func)
                func();
        }
    },30);
}

在HTML中调用运动框架JS文件

<!doctype html>
<html>
<head>
<meta charset="UTF-8">
<title>Untitled Document</title>
<style>
#div1 {width:100px; height:100px; background:red;}
</style>
<script src="运动框架.js">
</script>
<script>
window.onload=function(){
    var oD=document.getElementById('div1');
    startMove(oD,{width:400, height:400, opacity:30}, function(){
        document.title='Hello';
    });
}
</script>
</head>

<body>
<div id=div1>
</body>
</html>

 

4.DOM操作

  

HTML代码对应一颗DOM树。对DOM的各种操作事实上都是对这颗DOM树展开的。

1. 查找节点

主要是通过jQuery选择器来完成。结合文章开头的DOM树实例就行说明。        

1 var $li=$("ul li:eq(0)");   //查找ul中第一个<li>
2 alert($li.text());          //打印出第一个节点中的文本内容

2. 创建节点

创建元素节点并不只是单单创建元素节点,还需要将其挂到DOM树上。例如我们创建一个<li>节点然后将其挂在<ul>上,具体代码如下:

var $li_new=$("<li></li>");        //创建一个<li>元素
$("ul").append($li_new);           //将其添加到<ul>下   

3. 插入节点

一种插入节点的方法是通过jQuery中的append()方法,下面通过表1将插入节点的各种方法进行总结。

              表1                                            插入节点的各种方法

方法   描述 示例
append() 向每个匹配元素内部追加节点或是内容 

HTML代码:<p>你好吗?</p>

jQuery代码:$("p").append(“<b>还不错哦.</b>”);

结果:<p>你好吗?<b>还不错哦.</b></p>

appendTo()

$(A).append(B):是将B追加到A上

$(A).appendTo(B):是将A追加到B上

HTML代码:<p>你好吗?</p>

jQuery代码:$("<b>还不错哦.</b>").appendTo(“p”);

结果:<p>你好吗?<b>还不错哦.</b></p>

 prepend()  向每个匹配的元素内部追加内容   

HTML代码:<p>你好吗?</p>

jQuery代码:$("p").prepend(“<b>还不错哦.</b>”);

结果:<p><b>还不错哦.</b>你好吗?</p>

 prependTo()

$(A).prepend(B):是将B追加到A上

$(A).prependTo(B):是将A追加到B上 

 

HTML代码:<p>你好吗?</p>

jQuery代码:$("<b>还不错哦.</b>").aprependTo(“p”);

结果:<p><b>还不错哦.</b>你好吗?</p>

 after() 在每个匹配的元素之后添加内容   

HTML代码:<p>你好吗?</p>

jQuery代码:$("p").after(“<b>还不错哦.</b>”);

结果:<p>你好吗?</p><b>还不错哦.</b>

insertAfter

$(A).after(B):将B插入到A后

$(A).insertAfter(B):将A插入到B后

HTML代码:<p>你好吗?</p>

jQuery代码:$(“<b>还不错哦.</b>”).insertAfter(“p”);

结果:<p>你好吗?</p><b>还不错哦.</b>

before() 在每个匹配元素之前插入内容

HTML代码:<p>你好吗?</p>

jQuery代码:$(“p”).before(“<b>还不错哦.</b>”);

结果:<b>还不错哦.</b><p>你好吗?</p>

insertBefore()

$(A).before(B):将B插入到A前

$(A).insertBefore(B):A插入到B前

HTML代码:<p>你好吗?</p>

jQuery代码:$(“<b>还不错哦.</b>”).insertBefore(“p”);

结果:<b>还不错哦.</b><p>你好吗?</p>

4. 删除节点

jQuery中提供了三种方法删除多余的节点。

remove()方法

$("ul li:eq(0)").remove();     //获取ul下的第一个<li>节点后,删除该节点

值得注意的有两点:1.经remove()方法删除后的节点还可以恢复, 例如上述代码被删除后可以通过以下代码恢复

1 var $li_delete=$("ul li:eq(0)");     //获得ul下第一个li节点
2 $li_delete.remove();                 //将该节点删除
3 $("ul").append($li_delete);          //在将被删除的节点添加到ul上,需要注意的是此时该li节点被放置到ul的最后面

remove()参数,指定某属性的标签删除

1 $("ul li").remove(“li[title=篮球]”);     //在<ul>下,删除属性title为篮球的li的节点

 

detach()方法

具体用法与remove方法基本一样。与remove()方法相同的是该方法在删除元素节点后,也可以恢复元素。与remove()方法不同的是该方法删除所匹配的元素时,并不会删除该元素所绑定的事件、附加的数据,比如说:一个<p>绑定了一个click(function(){ alert("能恢复吗?");});事件,如果用remove()删除之后,再次恢复该元素时候并不会恢复click()事件,而detach()方法则在恢复时,同时也可以恢复其click()事件。

 

empty()方法

准确的说,empty()方法并不是删除节点,而是清空节点,清空元素中的所有后代节点。最后只剩一个空节点(该元素的属性依然存在)。例如我们清空第三个羽毛球的<li>节点。可以用下述代码完成。

1 $("ul li:eq(2)").empty;   //清空该节点

5. 复制节点

通过使用clone()方法,如果只写clone()则表示说明只复制节点,复制节点后,被复制的新元素并不具有任何行为。

如果想复制原节点所绑定的行为(事件),那么写法应该为clone(true).

 

6.替换节点与包裹节点

  两个方法replaceWith()与replaceAll(): $(A).replaceWith(B):用B替换A     

  $(A).replaceAll(B):用A替换B

$("p").wrap(""<b></b>"");   用<b>标签将<p>包裹起来

 

7. 属性操作

1. 获取属性和设置属性

  通过使用attr()获取属性的值,参数可以为多个。执行下述代码就会弹出“你最喜欢的运动”.

var $p=$("p");                  //获取节点<p>
var p_text=$p.attr("title");   //获取节点<p>的属性title的值

 

2. 删除属性

  通过removeAttr();如下例代码。

1 $("p").removeAttr("title");     //删除<p>的title属性

 

8. 样式操作

1.获取样式和设置样式

  我们知道,在HTML中改变样式的方法是通过CSS来完成的,一般都通过在元素中定义id或者class,而id或者class也输入该元素的一个属性,故可以通过attr()方法来获取和设置其属性。例如<p>标签中原始属性是class=start,在CSS中又定义了一个end的样式。这时我们就可以通过以下代码进行设置样式。

1 $("p").attr("class",“end”);  //将<p>标签的样式class从start该为end

2. 追加样式

  通过jQuery中提供的addClass()方法进行追加样式,值得注意的是addClass()是该原先的样式中添加了一种新的样式(多了一种样式,如果以前样式是一种则使用该方法后样式变为两种),而attr()则是该变了元素的初始样式(样式没有增多)。

3. 移除样式

  通过jQuery中的removeClass()方法。如果参数为空,则代表是移除其所有的样式。

4. 切换样式

  通过使用jQuery中的toggle()方法,该方法在jQuery中有着广泛的应用,以后要出一篇blog要把常用的jQuery方法进行总结。这里只说toggle()方法应该如何切换样式。实际上,通过的是tooggleClass()方法进行切换。该方法可以控制样式的重复切换,如果类名存在就删除它,如果类名不存在就添加它。示例代码如下。

1 $("p").tooggleClass("another");              //重复切换类名anohter

5. 判断是否含有某个样式

通过hasClass()方法进行判断,如果有则返回true,没有返回false。

6. 设置样式

.css控制sytle对象的各种样式属性。

1 $("p").css({"color":"red","font-size":"14px"});  //设置<p>的颜色和字体

 

9. 设置和获取HTML、文本、值

1. html()方法

  该方法类似于javascript中的innerHTML属性,获取的是HTML代码。

2.text()方法

  该方法类似于javascript中的innerText属性,获取的是文本内容。

3.val()方法

  该方法类似与javascript中的value属性,获取或者设置元素的值。需要注意的是,如果获取的是多个元素,那么返回值也将是含多个元素值的集合。

 

10. 遍历节点

1.children()方法:节点的子元素,而不考虑后代元素,即DOM树一个节点的直接子节点。

2.next()方法:获得匹配元素后面紧邻的同辈元素

3.prev()方法:获得匹配元素前面紧邻的同辈元素。

4.siblings()方法:取得匹配元素前后所有的同辈元素

 

运用DOM和运动框架制作模仿微博的发布效果。

<!doctype html>
<html>
<head>
<meta charset="UTF-8">
<style>
* { margin:0; padding:0;}
#div2 { width:500px; height:130px;margin:10px auto; text-align:center;}
#ul1 { width:500px; height:600px; border:1px solid black; margin:10px auto;}
#ul1 div { list-style:none; border-bottom:1px dashed #000000; padding:2px; overflow:hidden; opacity:0; filter:alpha(opacity:0);}
</style>
<title>Untitled Document</title>
<script src="../运动框架.js"></script>
<script type="text/javascript">
window.onload=function(){
    var oBtn=document.getElementById('btn1');
    var oTxt=document.getElementById('txt1');
    var oUl=document.getElementById('ul1');
    
    oBtn.onclick=function(){
        var oLi=document.createElement('div');
        oLi.innerHTML=oTxt.value + '<a href="javascript:;">删除</a>';
        var oA=oLi.getElementsByTagName('a');
        oA[0].onclick=function(){
            oUl.removeChild(this.parentNode);
        }
        var aLi=oUl.getElementsByTagName('div');
        if(aLi.length){
            oUl.insertBefore(oLi, aLi[0]);
        } else {
            oUl.appendChild(oLi);
        }
        var tmp=oLi.offsetHeight;
        oLi.style.height=0;
        
        startMove(oLi, {height:tmp}, function(){
            startMove(oLi, {opacity:100});
        });
    }
}
</script>
</head>

<body>
<div id="div2">
<label>微博发布窗</label><br/>
<textarea id="txt1" rows="5" cols="40"></textarea>
<input id="btn1" type="button" value="发布" />
<br/><br>大家都在说<br/>
</div>
<div id="ul1">
</div>
</body>
</html>

 

5.JS的面向对象

通过new构造函数创建一个对象,并给对象定义方法。

通过call继承父对象,通过引用或复制来继承方法。

call和apply,作用都是将函数绑定到另外一个对象上去运行

格式和参数定义:

A.call( B [,arg1,arg2,… ] );       // 参数列表,arg1,arg2,...

将A作为对象B的一个方法运行

辨析:http://blog.csdn.net/ithomer/article/details/6592082 .

下面是一个实例,用来懒加载图片,其中将callback作为对象img的方法运行。

function loadImage(url,callback) {
    var img = new Image();
    img.src = url;
    if(img.complete) {  // 属性判断图片是否已经存在于浏览器缓存
        callback.call(img); 
        return; // 直接返回,不用再处理onload事件
    }
    img.onload = function(){
        img.onload = null;
        callback.call(img);
    }
}

实例2:

style要设置成绝对位置,style位置属性要为字符串px的,可通过offsetLeft等属性获得数值。

注意window.event.clientX只有在鼠标事件中才有效,下面是实现对div拖拽的程序。

本程序将程序封装成对象Drag,注意其中对this属性的分辨和记录。

<!doctype html>
<html>
<head>
<meta charset="UTF-8">
<style>
#div1 { width:100px; height:100px; background:red; position:absolute; z-index:2; opacity:0.8;}
#div2 { width:100px; height:100px; background:green; position:absolute; z-index:1; opacity:0.8;}
</style>
<title>Untitled Document</title>
<script type="text/javascript">
window.onload=function(){
    new LimitDrag('div1');
    new Drag('div2');
}
function Drag(attr) {
    this.disX=0;
    this.disY=0;
    var _this=this;
    this.oD=document.getElementById(attr);
    this.oD.onmousedown=function(){
        _this.mouseDown();
    }
    document.onmouseup=function(){
        document.onmousemove=null;
    }
}
Drag.prototype.mouseDown=function(){
    var _this=this;
    this.disX=window.event.clientX-this.oD.offsetLeft;
    this.disY=window.event.clientY-this.oD.offsetTop;
    //alert(this.disX+' '+this.disY);
    document.onmousemove=function(){
        _this.mouseMove();
    }
}
Drag.prototype.mouseMove=function(){
        this.oD.style.left=window.event.clientX-this.disX+'px';
        this.oD.style.top=window.event.clientY-this.disY+'px';
}

function LimitDrag(id){
    Drag.call(this, id); //继承Drag
}
for(var attr in Drag.prototype){ //复制而非引用Drag的函数
    LimitDrag.prototype[attr]=Drag.prototype[attr];
}
LimitDrag.prototype.mouseMove=function(){ //重定义mouseMove方法,使它被限制在屏幕内
    var tmp1=window.event.clientX-this.disX;
    var tmp2=window.event.clientY-this.disY;
    if(tmp1<0)
        tmp1=0;
    else if(tmp1>document.documentElement.clientWidth-this.oD.offsetWidth)
        tmp1=document.documentElement.clientWidth-this.oD.offsetWidth;
    if(tmp2<0)
        tmp2=0;
    else if(tmp2>document.documentElement.clientHeight-this.oD.offsetHeight)
        tmp2=document.documentElement.clientHeight-this.oD.offsetHeight;
    this.oD.style.left=tmp1+'px';
    this.oD.style.top=tmp2+'px';
}
</script>
</head>

<body>
<div id="div1">aaa</div>
<div id="div2">bbb</div>
</body>
</html>

 

用面向对象的方法写成的电话号码格式化验证功能的JS

$(function() {
    new numConfirm().addEvent();
})
function numConfirm() {
    this.splitType = [3, 4, 4];
}

numConfirm.prototype = {
    _position : function(target) {
        var self = this;
        var elemWidth = $(target).outerWidth(), elemHeight = $(target).outerHeight(), elemParent = $(target).parents('.parentCls'), containerHeight = $('.js-max-input', elemParent).outerHeight();
        $(elemParent).css({
            "position" : 'relative'
        });

        $('.js-max-input', elemParent).css({
            'position' : 'absolute',
            'top' : -elemHeight - containerHeight / 2,
            'left' : 0
        });
    },

    addEvent : function() {
        var self = this;
        $('.inputElem').each(function(index, item) {
            $(this).keyup(function(e) {
                var value = $.trim(e.target.value);
                if (value == '') {
                    $('.js-max-input').hide();
                } else {
                    $('.js-max-input').show();
                }
                var count = 0, output = [];
                for (var i = 0; i < self.splitType.length; i++) {
                    var s = value.substr(count, self.splitType[i]);
                    if (s.length) {
                        output.push(s);
                    }
                    count += self.splitType[i];
                }
                value = output.join('-');
                $('.js-max-input').text(value);
                self._position($(this));
            });
        });
    }
};
View Code

 

6、事件冒泡与阻止冒泡

当事件发生后,这个事件就要开始传播,因为事件源本身并没有处理事件的能力需要委托DOM树父节点。例如我们点击一个按钮时,就会产生一个click事件,但这个按钮本身不能处理这个事件,事件必须从这个按钮传播出去,从而到达能够处理这个事件的代码中(例如我们给按钮的onclick属性赋一个函数的名字,就是让这个函数去处理该按钮的click事件)。 

当事件在传播过程中,找到了一个能够处理它的函数,这时候我们就说这个函数捕捉到了这个事件。 

说到这里,关键的问题来了,那就是一个函数是如何捕捉一个事件的呢?这就涉及到事件的冒泡了。 

为了更好地理解冒泡的概念,现在想象一下你的面前放着一杯水,但这杯水和我们平时看到的有点点不同,它分为数层,每一层又分成一或多个区域,最顶层是我们熟悉的窗口对象(即window对象),下一层分为好几个区域(document对象、history对象等等),而document对象的下一层又分为多个子对象。 

这些对象的层次关系构成了DOM中的对象树。 
事件的传播是有方向的,当点击一个按钮时所产生的事件从这个按钮处开始向上传播(就像一个水泡从杯底冒上来,这就是之所以叫事件冒泡的原因),但这个事件总是寻找特定的属性是否有值。例如按钮的click事件先寻找在按钮上是否有onclick属性的有意义的定义(即该属性指向一个存在的函数或一段可执行的语句),如果有,执行这个函数或语句;然后事件继续向上传播,到达按钮的上一层对象(例如一个form对象或document对象,总之是包含了按钮的父对象),如果该对象也定义了onclick属性,则执行属性的值。 

所以,如果这个按钮上面有3层(form、document、window),且这三层都定义了onclick属性,则当按钮的click事件产生时,将会调用4个(包括按钮本身的一个)函数或执行4段语句。

在火狐Firefox、opera、IE下阻止冒泡事件是不同的代码的,火狐下使用的是event.stopPropagation(),而IE下使用的是cancelBubble,jQuery 可以使用e.stopPropagation()就可以兼容了。

img.onmouseup = function(e){
                e = e || window.event;
                if(e.stopPropagation){
                    e.stopPropagation();
                }else{
                    e.cancelBubble = true;
                }
            }

附百度划词搜索的JS代码

var baidusearch = (function(){
    
    function init(tn){
        addEV(document, 'mouseup', fn);

        function fn(){
            var isStandard = "getSelection" in window;

            var ico_img = document.getElementById('selectsearch-icon');
            if(ico_img){
                ico_img.parentNode.removeChild(ico_img);
            }

            setTimeout(function(){
                selection = isStandard ? window.getSelection() : document.selection.createRange()
                var text = (isStandard ? selection+'' : selection.text).replace(/\n+/g, '');
                if(text && text.length){
                    if(text.length > 76){
                        text = text.substring(0, 76);
                    }
                    show(isStandard, selection, text);
                }
            }, 25);
        }

        function show(isStandard, selection, text){
            var scrollTop = document.body.scrollTop + document.documentElement.scrollTop;
            var scrollLeft = document.body.scrollLeft + document.documentElement.scrollLeft;

            if(isStandard){
                var rangePos = selection.getRangeAt(0).getBoundingClientRect();
                if(rangePos.top==0 && rangePos.right==0)
                    return;
                var tempTop = rangePos.top>35 ? rangePos.top-35+scrollTop : scrollTop;
                var tempLeft = rangePos.right+70>document.documentElement.clientWidth ? document.documentElement.clientWidth-65+scrollLeft : rangePos.right+5+scrollLeft;                
            }else{
                var selectionLeft = selection.boundingLeft+selection.boundingWidth;
                var tempTop = selection.boundingTop>35 ? selection.boundingTop-35+scrollTop : scrollTop;
                var tempLeft = selectionLeft+70>document.documentElement.clientWidth ? document.documentElement.clientWidth-65+scrollLeft : selectionLeft+scrollLeft;
            }

            var text = encodeURI(text);
            var img = document.createElement('img');
            img.src = 'http://img.baidu.com/img/iknow/qb/select-search.png';
            img.alt = '搜索';
            img.style.cssText = "width:65px; height:31px; border:0px none;";

            var link = document.createElement('a');
            link.id = 'selectsearch-icon';
            link.style.cssText = "cursor:pointer; position:absolute;"
            link.href = 'http://www.baidu.com/s?wd='+text+'&tn='+tn+'&hl_tag=flayer';
            link.target = '_blank';

            link.onclick = function(){
                link.parentNode.removeChild(link);
            }

            link.style.left = tempLeft + 'px';
            link.style.top = tempTop + 'px';
            link.appendChild(img);
            document.body.appendChild(link);

            img.onmouseup = function(e){
                e = e || window.event;
                if(e.stopPropagation){
                    e.stopPropagation();
                }else{
                    e.cancelBubble = true;
                }
            }
        }

        function addEV(d,b,a){if(window.attachEvent){d.attachEvent("on"+b,a)}else{if(window.addEventListener){d.addEventListener(b,a,false)}}} 
    };

    return {
        'init' : init
    }
})();    
View Code

 

posted @ 2014-01-24 23:44  匡时@下一站.info  阅读(607)  评论(0编辑  收藏  举报