图片 13

自定义标签在IE6,最近学习JS的感悟

自定义标签在IE6-8的窘况

2015/07/20 · HTML5 ·
IE,
自定义标签

原稿出处:
司徒正美   

想必以后前端组件化之路都以自定义标签,但那东西早在20年前,JSTL已在搞了。现在Web
Component还只有webkit扶持。但叁个零器件库,还索要三个特种的标记它们是一块的。可是那个XML已经帮大家化解了,使用scopeName,如”<xxx:dialog>”。在本人继续往下想如何管理怎么着为这么些标签绑定数据,与任何构件通讯,处理生命周期,等等大事此前,小编还大概有三个只可以面临的问题,便是怎么着宽容IE6-8!

比方以下二个页面:

图片 1

在chrome, firefox, IE11, IE11的IE6宽容形式分别如下:

图片 2
图片 3
图片 4
图片 5

咱俩会意识IE6下实际是多出累累标签,它是把闭标签也化为叁个独门的要秋天点

图片 6

其豆蔻梢头AA:DIV标签被开膛破肚,里面子节点全部暴出来,成为其兄弟节点了。因而想宽容它,就要费点劲。有个五个情景要求思索,1是客户已经将它写在页面上,情状同上;2是顾客是将它座落字符串模版中,这些用正则消除。可是正则若是碰上复杂的属性名,依然会晕掉。因而作者照旧希图接收原生的HTML
parser。换言之,字符串,小编要么会将它成为节点。这么办吧?!笔者想了无数措施,后来依然使用VML的命名空间法消除!

大家将方面包车型大巴页面改复杂点,再看看效果!

图片 7
图片 8

能够看出其套嵌关系今后完全准确,並且标具名不会大写化,也不会变卦多余节点!

好了,大家再判断一下是或不是为自定义标签,也许纯粹地说,那一个节点是或不是大家组件库中定义的自定义标签。有个别情状下,二个页面能够存在多套组件库,满含avalon的,ploymer的,也许是直接用Web
Component写的。

avalon的组件库将动用命名空间,那样就好界别开。在IE6-9中,推断element.scopeName是或不是为aa(那是组件库的命名空间,你能够改个更庞大上的名字),在此外浏览器判别此因素的localName是或不是以aa:起先就能够了!

JavaScript

function isWidget(el, uiName){ return el.scopeName ? el.scopeName ===
uiName: el.localName.indexOf(uiName+”:”) === 0 }

1
2
3
function isWidget(el, uiName){
  return   el.scopeName ? el.scopeName === uiName: el.localName.indexOf(uiName+":") === 0
}

以此难点消灭后,我们就足以开龙阳之癖于自定义标签的UI库了!

1 赞 1 收藏
评论

图片 9

     
 还记得笔者大二的时候以前接触JS,这个时候从体育场地借了N多的书籍,然后面看边用editplus写,然后遭逢标题,各样DEBUG,在做项指标时候,种种宽容性难题,真是忧伤啊。由于连串须求赶紧写完,所以就起来接触了jquery,依然从体育场合抱了几本书,然后下载了jquery源码,然前边看书籍边写代码,看了几章之后,感到貌似简单,然后就从英特网下载了jquery的文书档案,对照着文书档案,对其调用搞获得底相比较清楚了。

本文由 埃姆杰 翻译。未经许可,幸免转发! 波兰语出处:Future Insights。

       
未来综上说述,作者认为学习jquery反而使自身走了弯路,用jquery是相比较平价,也无须思索宽容性难题了,並且调用特别轻便高贵,然而,反而作者对原生js以为越发面生了,也诱致了后面以为完全离不开jquery了,想去写叁个XXX组件,想了一下,思路有了,然后写的时候遭受各个难点,然后就又回来jquery了。

内容提要

使用过多独门组件创设应用程序的主张并不特殊。Web
Component的面世,是再度纪念基于组件的应用程序开荒格局的好机缘。大家能够从那个进程中收益,精晓什么行使现存技巧成功目的,何况在以往做出自身的前端Web应用。

       
 从2018年暑假的时候,小编决定离开jquery了,jquery是风流罗曼蒂克把双刃剑,开荒的时候是有益,不过,作为贰个初大方,笔者觉着那是特别不利于的。

怎么样是组件?

软件开垦是三个语义丰硕(术语平日持续一个野趣卡塔 尔(阿拉伯语:قطر‎的天地。很醒目,这里的“组件”是八个很泛的可以称作,所以有重中之重指明大家想要表明的,在前端Web应用的语言景况中的意思。

前面一个Web应用中的组件,是指部分两全为通用性的,用来创设不小型应用程序的软件,这个构件有三种表现方式。它能够是有UI(客户分界面卡塔尔的,也得以是作为
“服务”的纯逻辑代码。

因为有视觉上的表现格局,UI组件更易于领会。UI组件简单的例子满含按键、输入框和文本域。无论是埃及开罗包状的美食做法开关(无论你是不是喜欢卡塔尔国、标签页、日历、选项菜单或然所见即所得的富文本编辑器则是有的更高等的例证。

提供服务类型的组件恐怕会令人为难掌握,那体系型的例子蕴涵跨浏览器的AJAX扶持,日志记录可能提供某种数据悠久化的效率。

依附组件开辟,最关键的正是组件能够用来组成任何零器件,而富文本编辑器正是个很好的例子。它是由按键、下拉菜单和局地可视化组件等组成。另一个例证是HTML5上的video成分。它同样含有开关,也还要包涵二个能从录像数据流渲染内容的要素。

       
 然后就起来下载JS的E-BOOK,大概是友善相比较急躁吧,看书真心看不步入,我也许喜欢边看边写代码这种。写了意气风发段时间,稳步的感到最先始的以为慢慢回来了,当然,也遇上了N多的主题素材。

何以要创设组件?

既然现在早就驾驭组件的情趣,就看看使用组件的措施营造前端选拔的平价。

       
到寒假的时候,决定自个儿的毕设不应用以往成熟的JS库,反而自个儿来写三个不完善的库,那样学习的越来越多,当然,也相比费时间。

模块

你或然听新闻说过 “组件是原始模块”的说法。好呢,感激它,咱们又要表明这里的术语!

你恐怕会感觉“组件”的传教更为相符用来陈述UI,而“模块”更切合描述提供服务的功能逻辑。而对此自己的话,模块和组件意思周边,都提供组织、集中和包裹,是与某些效用单位相关的。

       
开首写的感到真是优伤啊,什么都不懂,所以就去看了看tangram的源码,为何看tangram呢,其实原因相比较滑稽,当时校招的时候作者面试百度前端,被刷掉了,这时候面试官让本身看看它们百度选拔的JS库tangram,笔者就想看看它们极度库到底有啥了不起的。。。

高内聚

又是三个软件工程的高频词! 咱俩将相关的片段效果与利益团体在协作,把整个封装起来,而在组件的例证中,就恐怕是连锁的法力逻辑和静态财富:JavaScript、HTML、CSS以至图像等。那便是大家所说的内聚。

这种做法将让组件更易于保险,并且这么做之后,组件的可信赖性也将加强。同一时候,它也能让组件的功力分明,增大组件重用的大概。

       
写这么些库,首先使用了命名空间,笔者相比较欣赏toper,所以作者先是定义了三个变量:

可重用

您见到的亲自过问组件,尤其是Web
Component,更关爱可选拔的难题。作用断定,完成清晰,API易于通晓。自然就能够推动组件复用。通过营造可选取组件,大家不光保持了 D悍马H2Y(不要再一次造轮子卡塔 尔(英语:State of Qatar)标准,还获得了相应的功利。

此处要升迁: 不要过度尝试构建可选拔组件。你更应有关爱应用程序上所急需的这么些特定部分。假若以往相应必要应时而生,大概构件的确到了可选取的境界,就花一点外加时间让组件重用。事实上,开垦者都爱好去创设可选拔功效块(库、组件、模块、插件等卡塔尔国,做得太早将会让您后来难熬不堪。所以,吸收基于组件开垦的别的利润,而且采取不是装有组件都能重用的实际。

var tp = tp || {};

可互换

叁个效果与利益肯定好组件的API能令人私自地改成其内部的功用完成。若是程序内部的构件是松耦合的,这其实能够用三个零件轻便地更换另三个构件,只要依据相仿的 API/接口/约定。

假如你使用GoInstant提供的实时间效果与利益益服务组件,那她们上周关闭服务那样的信息会影响到你。不过,只要提供了相像的多寡同步API,你也足以自行创设利用三个 FirebaseComponent 组件可能 PubNubComponent 组件。

       
这种方法也是借鉴了tangram的写法,采用对象字面量的方式。那样具备toper定义的点子都投身了tp那个私有空间内了,比方对DOM的操作就位于tp.dom中。

可组合

事先也研讨过,基于组件的架构让组件组合成新组件尤其便于。那样的计划让组件更小心,也让任何零件中塑造和暴光的功力更加好利用。

无论是给程序增添效果,依然用来制作完整的次第,越发深根固柢的法力也能萧规曹随。那正是这种艺术的要害收益。

是还是不是有要求把装有的事物调换到组件,事实上决议于你自身。未有任何理由让你的程序由 你自己 的零器件组合成你最惊叹的功能 ,乃至 最花哨的功能。而那么些构件又扭曲构成任何零零件。借让你从那几个主意中赢得了获益,就想尽地去坚持不渝它。然则要专心的是,不要用同风流倜傥的点子把事情变得复杂,你并无需过分关切怎么样让组件重用。而是要关切呈现程序的效用。

     
 由于那么些库完全部是为毕设做的,所以这里面包车型客车洋洋文件都感到促成毕设的少数职能而写的。

到现在就起来营造组件

在 Caplin
Systems 创设基于组件的自有应用程序时,作者利用了几条准绳和举行。那个准则由 BladeRunnerJS(BRJS) 开源工具集支撑。它被称作”BladeRunnerJS”
是因为大家将次第成效都封装在称作 Blades 的东西中。Blade是能够在有些应用中收音和录音的效应特色,可是无法在程序间重用。当成效真的
变得进一层通用的时候,大家将相应的定义移到库文件中,供各种程序间接选举拔。特定应用中的组件(blade)和大家前后相继间的通用组件能够应用,大家只要找到最棒满意要求的任何库和框架。

那么,今后如何库和框架可以扶植大家塑造组件呢?

在调整营造利用时应选用何种能力时,只必要探视流行的 TodoMVC 网址就能够看看多量可供选用的前端库和框架。你或者会感到任何豆蔻年华种方案都能用来创设基于组件的应用程序。可是,他们之中的局地方案内置了对组件的支持。个中相比知名的是AngularJS、Ember
和 React。

     
笔者使用的协会是core+组件的措施,tp.core.js(压缩后为tp.core-min.js卡塔 尔(阿拉伯语:قطر‎,而任何的零器件每个组件叁个文本,而组件之间大概存在依据关系,这种依靠关系就透过英特尔解决。

组件间是何许通讯的?

在深切示例在此之前有非常重要简单地提到组件间通讯的难点。假使组件之间是“独立”、“模块化”的,他们又是怎么相互通讯的吗?

最令人瞩指标答案正是让组件间相互影响援用并由此她们之间的API交互作用。那样做的标题就在于,这种做法会让组件互相信任。长期内恐怕幸好,风流倜傥段时间今后,你在校勘程序的时候程序会失控,修正贰个组件就可以对另叁个组件发生宏大的震慑。决定移除贰个无法推动预期价值组件恐怕会让您的应用程序结束事业,因为它背后会有数个构件正视于它。

此刻,解决方案是提供松耦合的,让组件之间比很少依旧大约不通晓相互的方案。组件并不直接创建其余构件,在她们须求通讯的时候,他们经过“接口/约定”恐怕通过 “服务”。大家在创设B奥迪Q5JS程序时思谋了累累这么些方面包车型大巴事物,并且接受 ServiceRegistry 访问用于组件间通信的服务仍是Web
API如此那般的能源。Angular和Ember接收了服务和依据注入化解那类难题。

     
在一向不写这么些库此前,就算是笔者利用jquery,每二个JS文件作者都以直接在HTML文件中使用script标签写进去的,而前天急需运用这种异步模块加载的秘籍,假若要动用非焦点模块,那么必要:

演示组件my-avatar

为了体现我们怎么样用那几个库和框架营造最中央的零件,大家创造了四个暗含UI,用于取回和出示客户头像的差相当少示例。在或者的图景下,该零器件会有 my-avatar 标签,会从以下多少个属性中赢得头像:

  • service 允许设置二个服务。比如 twitter 或者 facebook
  • username 用于取回该客商名相对应的头像
tp.use(["tp.a","tp.b"],function(a,b) {

})

AngularJS

AngularJS 可能是明天用来创设程序最风靡的前端应用方案了。作为创笔者的Google,重新思索HTML,思考怎么重新发明,满意方今Web开拓的内需。

Angular中得以应用自定义指令概念组件。之后,你能够行使 HTML
标志评释自定义组件。

查阅代码演示: 

以此例子显示了应用Angular指令的简练程度。值scope 定义了从
 my-avatar 成分中拿走,况且之后用来营造相应的img标签和渲染成客户头像的性质。

     
使用use情势,它会活动去下载tp.a.js和tp.b.js,下载达成今后,实施回调函数。

Ember

框架与库的争辩旷日漫长,总来讲之框架是挟持你按某种方式做作业,所以它是阴毒的。很醒目,Angular是个框架,而Ember的作者,Yehuda
Katz和汤姆Dale也很乐意把Ember看作框架。

Ember 有对它称为组件的内建扶持。Ember
Components背后的眼光是竭尽的向Web
Components看齐,当浏览器协助允许时,就足以很方便地迁移到Web
Components中。

查阅代码演示: 

下边包车型地铁事例中选取了 handlebars 做模板,所以成分的定义不是同等种语法。

      同样,在tp.a.js中,也不可能利用普通的JS的写法了,而要使用:

React

React 固然是个新人,不过却大器晚成度有不菲的维护者。它由推特(TWTR.US)开辟,况且已经完美用于Facebook的UI和一些Twitter的UI。

使用React塑造组件的推荐模式是采用叫做 JSX 的东西来定义它们。那是风华正茂种“推荐在React上运用的JavaScript语法转变”。请不要因此分心。他们风流浪漫度在文书档案中建议,这几个主张就是用来扶植您在JavaScript中写出HTML标志的。

本身不是说你并不得以一贯在HTML中增添标签,而必需运用JSX创制和煦的机件。可是,只要您定义了一个组件,你就能够利用那个组件创设其余零器件。

查看代码演示: 

由此,组件使用的申明语法须求相应的HTML成分和对 React.RenderComponent 的调用。

 

未来:Web Component和其他

Web
Component才是前途!正如名字所表示的那么,他们承诺将拉动能够将成效封装成组件的浏览器原生扶助。

本身将不难展现Web
Component而且演示我们未来得以什么运用它。更深切的原委请参见本文末尾的 “外界财富” 一节。

她们提供的作用包蕴:

define("tp.a",["tp.c","tp.d"],function(c,d) {
   tp.modules.add("tp.a",function() {

    });
});

自定义元素

咱们在地点关怀的是用Angular、Ember和React营造 my-avatar 的事例。恐怕的处境下,那样的章程将以页面上恐怕模板上加上的自定义成分表示。Web
Component包含透过自定义成分获取的原生帮助– 相对是Web Component标准的骨干组成都部队分。

概念新成分,满含拜谒成分生命周期的片段事件比方曾几何时创设(createdCallback卡塔 尔(阿拉伯语:قطر‎、什么日期增加在DOM树上(attachedCallback卡塔 尔(阿拉伯语:قطر‎、曾几何时从DOM树上分离(detachedCallback),何时成分属性改动(attributeChangedCallback(attrName, oldVal, newVal))。

自定义成分的二个首要的有个别就是有力量从原本成分扩展,因此得到原有成分相应的成效。示例中大家增加了 <img>元素 。

末尾,大家所写的代码中,自定义成分正在而且趋势去做的正是将复杂的东西抽象化,让顾客关切于单个组件发生的价值,进而用来营造越发助长的效应。

   
 define的率先个参数是该器件的名字(须求唯生龙活虎,所以自身恐怕遵照命名空间的点子写的卡塔尔,第2个参数是其意气风发组件所信任的零器件,第几个参数是回调函数,也等于当重视的组件下载完毕以往,回调施行,而tp.modules.add就足以将以此模块加载到方方面面库中,那样的话本事选择tp.use调用。

Shadow DOM

还记得iframe们吧?大家还在动用它们,是因为他俩能保障组件和控件的JavaScript和CSS不会潜濡默化页面。 Shadow
DOM 也能提供这么的掩护,並且未有iframe带给的承担。正式的传教是:

Shadow
DOM的宏图是在shadow根下掩盖DOM子树进而提供包装机制。它提供了创造和维持DOM树之间的作用界限,甚至给那些树提供互相的效应,进而在DOM树上提供了越来越好的效果与利益封装。

     
这种措施本身在tangram中绝非看出,小编是看了天猫商城的KISSY之后求学到的,也正是所谓的AMD(异步模块定义卡塔尔。

HTML导入

大家长日子早先就能够导入JavaScript和CSS了。 HTML导入成效提供了从任何HTML文书档案中程导弹入和选定HTML文书档案的才干。这种简单性同期表示能够很方便地用部分构件创设另生龙活虎对组件。

最后,这样的格式很了不起,符合可选拔组件,况且可以用你最欢悦的包管理应用方案发布(比如: bower、 npm 或者 Component)。

     
临时英特尔的完毕格局是通过setInterval,可是将在被重构图片 10

模板

我们中的许多少人已经应用像handlebars、mustache恐怕underscore.js中的模板那样的缓慢解决方案(就好像大家在地点的Ember示例中用的同样卡塔尔。Web
Component通过 template元素 提供了模版的原生扶持。

原生模板令你能够注脚分类为“掩瞒DOM”不过拆解剖判成HTML的标志片段。他们在页面加载时不曾用场,不过能够在运转时实例化。他们得以
被搜寻到 ,不过在插入活动的DOM树前不会加载任何有关能源。

     
笔者早先写了生龙活虎篇日记来落到实处英特尔,当然,效用低下,反正我们看看就能够了

Platform.js

不过,好似每便提到新特色同样,大家不能够显著浏览器是还是不是扶持这几个特点。

图片 11

以致二零一四年5月十二日,Web Component 的浏览器扶助情形

同等,大家也能透过某个神奇的相称代码,伊始接收一些Web
Component所提供的功用。

图片 12

有了宽容库的Web Component帮助情形

好消息是几个最早进的浏览器厂商谷歌和Mozilla正在全力完善宽容库
,帮忙大家选拔Web Component。

以下示例显示使用platform.js后大家得以什么定义作为img元素扩大的my-avatar成分。最好的是它能用到原生img成分的富有机能。

翻看代码演示: 

点击 HTML5 Rocks Custom Elements
tutorial 以查看创造自定义成分的越来越多新闻。

注:即使您对platform.js感兴趣,也得以看看 bosonic。

原生技艺的支撑目标便是给大家提供相应的创设底工。所以Web
Component并非库和框架的前期功率信号。

     
然后就是事件了,事件是一个比较恼火的作业,东西相当多,笔者把它坐落了tp.event这几个空间中。

Polymer

Polymer 是演示构建基于原生Web
Component功能的顶尖示例。它提供了增选的机制用来成立自定义的Polymer元素,何况提供了多数基本的UI组件,让您能够创制协调的应用程序。

图片 13

下边你能够观望 my-avatar 成分的归纳创设进程,同期大家也博得了想要的标记。

翻开代码演示: 

谷歌正在大力拉动Polymer。请查看 Polymer getting started
guide 查看更加多示例。

     
首先是增加和移除事件监听器,由于IE和非IE选拔的措施分化样,IE选用attachEvent和detechEvent,非IE采纳addEventListener和removeEventListener,况兼IE只协理冒泡(从近期因素冒泡到根成分卡塔尔,而非IE扶植冒泡和破获(从根成分捕获到日前元素卡塔 尔(阿拉伯语:قطر‎。最开端自己是如此做的:

X-Tag和Brick

Mozilla开垦了和煦的自定义元素包容库,叫做 X-Tag。X-Tag是一个为启用Web
Component举办多项包容的库,并将在提供对Web Component的完好扶持。

以下正是行使X-Tag的 my-avatar 自定义组件,与正规文书档案超近乎:

翻看代码演示:

Mozilla同有时间还成立了一个叫 Brick 的库,个中囊括X-Tag,提供“生机勃勃组用来方便连忙营造Web应用程序的UI组件”,使用与谷歌的Polymer相像的主意。

tp.event.on = function(element,event,fn) {
        if (window.attachEvent) {
            //IE
            //第三个参数_realFn是为了修正this
            var realFn = function(e{fn.call(element,e);};
            _realEventCallbackFns[fn] = realFn;
            element.attachEvent("on" + event,realFn);
        } else if (window.addEventListener) {
            element.addEventListener(event, fn,false);
        } else {
            element["on" + event] = fn;
        }
};

总结

利用基于组件的架构创设应用程序有为数不少益处,你能从现成的框架中学到,也能在营造前端Web应用程序时从引进的Web
Component中上学到。

这场组件化Web帝国的旅程,让我们在面前遭受框架和工具的选用时沉吟未决不决。可是,Web
Component会是终极的点灯!

Web
Component会提供创设应用程序的原生统风度翩翩的艺术
。现存的框架很有相当的大可能率会转而选择Web
Component也许评释什么与它二头使用。Ember的政策是让迁移到Web
Component尤其便利,而推特(TWTR.US)的React则是身体力行整合的好例子,已经有贰个 ReactiveElements 演示它了。因为Angular和Polymer都以谷歌的类型,他们很有异常的大希望会走到一块儿。

   
 也正是在一个函数内部去决断是不是是IE,然后相应的进行相应的函数,然而如此,若是加上的事件监听器超多,每一回都if什么的,小编个人认为十分不佳,所以作者背后增加了二个扶助函数:

外界财富(拉脱维亚语卡塔尔国

  • Eric Bidelman – Google I/O 2014 – Polymer and Web Components change
    everything you know about Web
    development
  • Ryan Seddon – Web Directions – Web Components, The Future of Web
    Development
  • Addy Osmani – LXJS – Componentize The Web: Back To The
    Browser!
  • WebComponents.org a place to discuss and evolve web component
    best-practices
var _listeners = {},
        _addEventListener,
        _removeEventListener;
    if (window.attachEvent) {

        var _realEventCallbackFns = {};
        _addEventListener = function(element,event,fn) {
            //第三个参数_realFn是为了修正this
            var realFn = function(e) {fn.call(element,e);};
            _realEventCallbackFns[fn] = realFn;
            element.attachEvent("on" + event,realFn);
        };
        _removeEventListener = function(element,event,fn) {
            element.detachEvent("on" + event,_realEventCallbackFns[fn]);
        };
    } else if (window.addEventListener) {
        _addEventListener = function(element,event,fn,capture) {
            element.addEventListener(event, fn,capture);
        };
        _removeEventListener = function (element,event,fn,capture) {
            element.removeEventListener(event,fn,capture);
        };
    } else {
        _addEventListener = function(element,event,fn) {
            element["on" + event] = fn;
        };
        _removeEventListener = function(element,event) {
            delete element["on" + event];
        };
    }

         
 那样,整个推断只必要实行二次,前边调用的时候只必要动用_add伊夫ntListener就能够,当然,由于应用了闭包,tp.event命名空间之外是不足访谈那多少个函数的。

           那那样,tp.event.on就变得特别轻松了:

tp.event.on = function(element,event,fn) {
        _addEventListener(element,event,fn,false);
         };

         
何况这样还恐怕有一个好处,在此之前的不二秘技只可以利用冒泡情势,但今后,能够运用捕获,当然,只好非IE才干选取,那样在末端使用事件代理一些非冒泡的轩然大波的时候特别有用,举例blur和focus事件。

         
 除了事件监听器,还亟需事件风浪的拉长,删除等,也正是add,fire,remove等,这里就背着了。

         
在利用事件代理的时候,大家日常要博取到事件的对象成分,而IE和非IE又是不等同的,所以必要独自写一个函数:

tp.event.getTarget = function(event) {
        return event.target || event.srcElement;
    };

         
常用的效率自然如故阻止事件冒泡以至阻碍暗中认可事件的发出,很可惜,IE和非IE管理格局依旧不等同的,比如阻止冒泡IE采纳的是cancelBubble,而别的浏览器接收的是stopPropagation,所以依然须求写:

tp.event.preventDefault = function(event) {
        if(event.preventDefault) {
            event.preventDefault();
        } else {
            event.returnValue = false;
        }
    };
    tp.event.stopPropagation = function(event) {
        if(event.stopPropagation) {
            event.stopPropagation();
        } else {
            event.cancelBubble = true;
        }
    };

       
 事件那大器晚成道实际作者做了N多东西,不过出于讲不完,所以偶尔不说了。

        注意一下啊,由于JS变量作用域未有block,所以请不要选取上边这种:

var arr = new Array();
if(xxx) {
   for(var i = 0,len = arr.length ; i < len; i++) {

   }
} else {
   for(var i = 0,len = arr.length ; i < len; i++) {

   }
}

      那样使用变量i已经被重新定义了,所以必要把变量i定义在if早前,即:

var arr = new Array(),
    i;

          事件之后,当然就是DOM了,认为每一种库在此个上面都做了成都百货上千干活。

       
 首先是ready的论断,关于这几个能够看本人其它大器晚成篇日记:

       
 这里作者入眼讲一下tp.dom.query,也正是查询咋办的,首先拜候常用的询问有:#aa,.aa,input。

       
 #aa这种比较容易,因为JS提供了API,也等于document.getElementById;input这种也正如好搞,因为JS有document.getElementsByTagName;可是.aa这种办法就相比较郁结了,因为JS未有提供API,幸而,在部分浏览器中也许提供了API:document.getElementsByClassName,而那贰个从没提供这几个API的就相比正剧了,只好遍历全体节点,也等于使用document.getElementsByTagName(*):

          我那时写了一个协理函数:

var _getElementsByClassName = null;
        if(document.getElementsByClassName) {
                _getElementsByClassName = function(str) {
                    var fetchedEles = document.getElementsByClassName(str),
                        eles = [];

                    for(var i = 0, len = fetchedEles.length; i < len; i++) {
                        eles.push(fetchedEles[i]);
                    }
                    return eles;
                };
        } else {
            _getElementsByClassName = function(str,openClassScan) {
                var eles = [],
                    allElements = document.getElementsByTagName("*"),
                    i;
                if(openClassScan) {
                    for (i = 0; i< allElements.length; i++ ) {
                        if (tp.dom.containClass(allElements[i],str)) {
                            eles.push(allElements[i]);
                        }
                    }
                } else {
                    for (i = 0; i< allElements.length; i++ ) {
                        if (str === allElements[i].className) {
                            eles.push(allElements[i]);
                        }
                    }
                }
                return eles;
            };
        }

           
笔者此刻写了一个openClassScan参数,解释一下,那么些参数是为了减轻肖似于<div
class = “a
b”></div>这种,因为如果要协助通过API查询如class:a,那么必要各类节点都认清是或不是contain那个class,比较费时间,而自身感到非常多时候不需求,所以私下认可本身关闭了。

           
PS:使用了原生的document.getElementsByClassName的任天由命不受那个影响的。

           小编把每贰个询问如:tp.dom.query(“#aa
input”)分为三种,生龙活虎种为简易询问(也正是如查询:#aaa卡塔尔国,别的一种是参差不齐查询,每种复杂查询都以由大多简便询问构成的,比方#aaa
input,就足以切成:#aaa和input。

           所以,在种种查询的最最早,必要将传递的询问格式化,举例#aa
>input这种格式化为:#aa >
input,多个空格变为1个空格,>两侧必需有七个空格等。

         
 之后写叁个帮忙函数,判别是还是不是是复杂查询,假设是,那么切开查询字符串,切成数组。

           我认为:#aa
input这种实际上正是经过document.getElementById查询以往然后查询它的子孙节点中的全体满意tagName为input的要素;而#aaa
>
input这种就是查询它的孩子节点中是不是有这种满足条件的因素。将来任何流程比较轻松了,对于一个参差不齐查询,首先进行多个简单易行询问,然后依照查询的结果集合,举办叁回遍历,对每一种节点查询它的男女节点或子孙节点,将有所满意条件的放入到此外八个数组,假如该数组为空,那么直接重回空数组,不然,继继续展览开下贰遍询问(依然查询孩子节点或子孙节点卡塔 尔(阿拉伯语:قطر‎。

         
 笔者觉着,如同此三个效应比较容易的query就够了,不须要达成相像于jquery里面包车型地铁那样复杂的查询,如若要动用它,其实也超级粗略,因为jquery的询问引擎sizzle已经开源,完全能够将它到场到那一个库,而现行toper也是这么做的,要调用sizzle就利用:

tp.use("tp.dom.sizzle",function(sizzle) {});

         
感到JS的包容性真心很头痛啊,就举例在DOM这一块儿,为了协作,作者都做了十分短日子。当然,DOM这一头必定将不仅如此一点剧情,权且也不写了。

          除了DOM,对变量类型的剖断和浏览器的检查实验也是很关键的。

       
 首先,类型判断,由于JS是弱类型语言,而不常候是内需推断它的花色的,当然也得以选拔typeof
去看清,权且作者是那般做的:

  

tp.type = tp.type || {};
tp.type.isArray = function(ele) {
    return "[object Array]" === Object.prototype.toString.call(ele);
};
tp.type.isFunction = function(ele) {
    return "[object Function]" === Object.prototype.toString.call(ele);
};
tp.type.isObject = function(ele) {
    return ("function" === typeof ele) || !!(ele && "object" === typeof ele);
};
tp.type.isString = function(ele) {
    return "[object String]" === Object.prototype.toString.call(ele);
};
tp.type.isNumber = function(ele) {
    return "[object Number]" === Object.prototype.toString.call(ele) && isFinite(ele);
};
tp.type.isBoolean = function(ele) {
    return "boolean" === typeof ele;
};
tp.type.isElement = function(ele) {
    return ele && ele.nodeType == 1;
};
tp.type.isUndefined = function(ele) {
    return "undefined" === typeof ele;
};

       
我看了风流倜傥晃,不相同的库的判别格局分歧等,我那个时候使用的是tangram的推断方式。

        然后正是浏览器判断,笔者是这么写的:

(function() {
    var ua = navigator.userAgent;
    tp.browser.isIe = ua.hasString("MSIE") && !ua.hasString("Opera");
    tp.browser.isFirefox = ua.hasString("Firefox");
    tp.browser.isChrome = ua.hasString("Chrome");
    tp.browser.isWebKit = ua.hasString("WebKit");
    tp.browser.isGecko = ua.hasString("Gecko") && !ua.hasString("like Gecko");
    tp.browser.isOpera = ua.hasString("Opera");
    tp.browser.isSafari = ua.hasString("Safari") && !ua.hasString('Chrome');
    tp.browser.isStrict = ("CSS1Compat" === document.compatMode);
})();

     
 当然,还应该有浏览器版本的剖断,一时半刻就不贴出来了。这里基本思路正是推断navigator.useAgent重回的字符串中,各个浏览器里面包车型地铁这么些字符串是不相近的,当然,那么些进度比较恶心,並且有不小大概前面某三个浏览器会改造它的userAgent,招致整个判断失效,比方IE,听外人说前面新IE要把userAgent搞成firefox,真心搞不懂,那是要逆天啊?

     
 除了这种判别方式,还足以经过推断是还是不是有某一个函数或某四个变量来判别,这种决断方式本身记不清叫什么名字了,反正以前这种叫浏览器嗅探。

     
 除了代码之外,工具也很着重,另生龙活虎篇日记介绍JS工具的:

       
对动漫片有野趣的童鞋,可以看看作者的方今求学JS的醒悟-2,关于动画的。

     
 好呢,貌似又超时了,先就这么吧,认为每回写这种日志都会损耗数不胜数时日。

发表评论

电子邮件地址不会被公开。 必填项已用*标注