Jquery基本功能

jQuery 是一个高效、精简并且功能丰富的 JavaScript 工具库。它提供的 API 易于使用且兼容众多浏览器,这让诸如 HTML 文档遍历和操作、事件处理、动画和 Ajax 操作更加简单。Jquery提供的诸多API详见 jQuery API 中文文档

这篇博客参考:jQuery设计思想 - 阮一峰的网络日志 ,记录下 jquery 如何获取/创建/移动元素、如何修改元素属性,以及jQuery 链式操作的实现原理。尤其是链式操作,是jQuery最令人称道、最方便的特点。

1、jQuery 如何获取元素

jQuery的基本设计思想和主要用法,就是"选择某个网页元素,然后对其进行某种操作"。这是它区别于其他Javascript库的根本特点。

  • 获取网页元素:

jquery(selector) 或者 $(selector) 。 jquery可以简写为 $ ,selector为选择表达式

选择表达式可以是CSS选择器:

$('div.myClass')   // 选择class为myClass的div元素
$('input[name=first]')   // 选择name属性等于first的input元素

也可以是jQuery特有的表达式

$('a:first')   //选择网页中第一个a元素
$('tr:odd')  //选择表格的奇数行
$('#myForm :input')   // 选择表单中的input元素
$('div:visible')   //选择可见的div元素
$('div:gt(2)')   // 选择所有的div元素,除了前三个
$('div:animated')   // 选择当前处于动画状态的div元素

$(':header')   // 获取所有的标题元素:<h1> ~ <h6>
$(':animated')   // 获取所有的动画元素
$('p:contains(Hello)')   // 获取所有包含文本为Hello的<p>元素,中间的文本区分大小写
$(':hidden')   // 获取所有的隐藏元素:width和height为0、display:none、type=hidden、
$('[href]')   // 属性选择器:获取所有含有属性为href的元素
$('div + p')   // 每个div相邻的下一个<p>元素
$('div ~ p')   // 获取跟div同级的所有的<p>元素

!!!但要注意:jquery(selector) 操作返回的是一个 API ,包含处理 selector 的方法,这是为了方便进行链式操作

  • 对获取的网页元素进一步筛选:

$('div').has('p');   // 选择包含p元素的div元素
$('div').not('.myClass');   //选择class不等于myClass的div元素
$('div').filter('.myClass');   //选择class等于myClass的div元素
$('div').eq(0);   //选择第1个div元素

2、链式操作

这是jQuery最令人称道、最方便的特点。它的原理在于每一步的jQuery操作,返回的都是一个jQuery对象,所以不同操作可以连在一起。

(1)链式调用的代码

$('div').find('h3').eq(2).html('Hello');

分解开来,就是下面这样:

$('div')     //找到div元素
 .find('h3')   //选择其中的h3元素
 .eq(2)     //选择第3个h3元素
 .html('Hello');   //将它的内容改为Hello

jQuery还提供了.end()方法,使得结果集可以后退一步(相对于find() ):

$('div')
 .find('h3').eq(2).html('Hello')
 .end()   //退回到选中所有的h3元素的那一步

(2)原理

链式调用的实现离不开this和elements这两个外部变量,也就是说利用了js闭包。

  • 链式调用addClass()是通过return this的形式来实现的

通过对象上的方法最后加上return this,把对象再返回回来,对象就可以继续调用方法,实现链式操作。

const 对象 = {
        方法名:function(){
        // …
        return this; // 实现链式编程的核心this,this的关键字,表示当前对象。
    }
 }

比如为了能链式调用 addClass() 方法:

window.jQuery=function(selector){
  const elements=documents.querySelectorAll(selector)
  const api={
    addClass(className){
        for(let i=0;i<elements.length;i++){
          elements[i].classList.add(className)
        }
    return api    // addClass()里返回一个可以调用addClass()的api,这样就能链式调用 addClass()
    }//addclass    
  }//api
  return api    // 也返回api,但只是为了jQuery()返回值能调用addClass()
}//window.jQuery

addClass()里返回一个可以调用addClass()的api,这样就能链式调用 addClass()
上述代码等同于:

window.jQuery=function(selector){
  const elements=documents.querySelectorAll(selector)
  return{
    addClass(className){
        for(let i=0;i<elements.length;i++){
          elements[i].classList.add(className)
        }
        return this 
    }//addclass   
  }//return
}//window.jQuery

调用方式

jQuery('.test').addClass('red').addClass('blue')

可以看出,对于jQuery函数return的结果来说,this和elements都是外部变量
其中,谁调用addClass(),this就指向谁

现在结合this再分析下上面调用方式里2次链式调用的具体过程
1、jQuery('.test')返回的对象可以调用addClass('red')
2、因为谁调用addClass(),this就指向谁,故:jQuery('.test').addClass('red') 返回的this指向jQuery('.test')。而结合第1条,jQuery('.test')返回的对象可以调用addClass('red')。因此可以继续调用addClass('blue'),依次类推,链式调用。
最终在 .test 标签上添加 red 类和 blue 类。

  • find()链式调用addClass(),除了借助this以外,还用到了elements这个外部变量
window.jQuery = function(selector) {
  const elements=documents.querySelectorAll(selector)
  return{
    addClass(){},
    find(selector) {
      let array = [];
      for (let i = 0; i < this.elements.length; i++) {
        const elements2 = Array.from(this.elements[i].querySelectorAll(selector));
        array = array.concat(elements2);
       }
      array.oldApi = this; // this 就是 旧 api,目的是为了给end()使用
      return jQuery(array);
    }//find
  }//return
}//window.jQuery

调用方式:

jQuery('.test').find('.child').addClass('red').addClass('blue')

1、jQuery('.test')返回的是一个可以处理elements的 api 对象(elements是一个伪数组,装满了被 .test 选中的div)。
2、find('.child') 返回的是一个能在后面链式调用addClass()的api
3、array作参数是为了改变elements,而find()、addClass()均瑶访问elements(闭包:访问函数外部变量),且elements变成了array(array里装的又是.child选中的所有div),故addClass里面的elements也变成了array
因此,可以在每一个.child标签里添加'red'类和'blue'类

parent()也是类似原理。

3、创建元素

createElement() 是来自核心 JavaScript 的用于创建 HTML 元素的方法。在 jQuery 中,有一些方法可以执行类似的操作:

  • append():所选元素的末尾添加元素。
  • prepend() :在所选元素的开头添加元素。
  • after() :在选定元素之后添加元素。
  • before() :在所选元素之前添加元素。

4、插入元素

假定我们选中了一个div元素,需要把它移动到p元素后面。
第一种方法是使用.insertAfter(),把div元素移动p元素后面:

$('div').insertAfter($('p'));

第二种方法是使用.after(),把p元素加到div元素前面:

$('p').after($('div'));

但是两种方法返回的API显然不一样,前者返回处理p标签的API,后者返回处理div标签的API。
插入操作有以下四对:

.insertAfter().after():在现存元素的外部,从后面插入元素
.insertBefore().before():在现存元素的外部,从前面插入元素
.appendTo().append():在现存元素的内部,从后面插入元素
.prependTo().prepend():在现存元素的内部,从前面插入元素

5、复制/删除操作

复制元素使用.clone()
删除元素使用.remove().detach()。前者不保留被删除元素的事件,后者保留,有利于重新插入文档时使用。
清空元素内容(但是不删除该元素)使用.empty()

6、修改元素属性

jQuery使用同一个函数,来完成取值和赋值,具体取值还是赋值,取决于函数的参数,比如

$("div").text()  //表示获取div的内容
$("div").text('新的内容')  //设置div的内容

需要注意的是,如果结果集包含多个元素,那么赋值的时候,将对其中所有的元素赋值;取值的时候,则是只取出第一个元素的值(.text()例外,它取出所有元素的text内容)。

使用attr()可以修改元素属性:

$('div').attr('class','red')  // 有则改 无则加 class为red

removeAttr()可以删除属性

$('div').removeAttr('name')  // 删除name属性

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容

  • 1.jQuery如何获取元素 jQuery的基本设计思想,就是获取某个网页元素,然后对其进行某种操作(通过返回jQ...
    Prayx阅读 411评论 0 0
  • 1. 选择网页元素 通过CSS选择器 通过jQuery特有的表达式 2. 改变结果集 通过过滤器 在DOM树上游走...
    WebbTang阅读 491评论 0 0
  • 1、jQuery 如何获取元素 jQuery的基本设计思想和主要用法,就是"选择某个网页元素,然后对其进行某种操作...
    siyuetian阅读 154评论 0 0
  • 选择网页元素 jQuery的基本设计思想和主要用法,就是"选择某个网页元素,然后对其进行某种操作"。这是它区别于其...
    奇异果victory阅读 167评论 0 0
  • jQuery 功能简介 jQuery 的基本思想是选取元素再对其操作,操作时特点是可以进行链式操作。 通过设置别名...
    一轮鱼丸阅读 273评论 0 0