外观模式(Facade)为子系统中的一组接口提供了一个一致的界面,此模块定义了一个高层接口,这个接口值得这一子系统更加容易使用。
外观模式在JS中经常用于解决浏览器兼容性问题。html
外观模式不只简化类中的接口,并且对接口与调用者也进行了解耦。外观模式常常被认为开发者必备,它能够将一些复杂操做封装起来,并建立一个简单的接口用于调用。
外观模式常常被用于JavaScript类库里,经过它封装一些接口用于兼容多浏览器,外观模式可让咱们间接调用子系统,从而避免因直接访问子系统而产生没必要要的错误。前端
外观模式的优点是易于使用,并且自己也比较轻量级。但也有缺点 外观模式被开发者连续使用时会产生必定的性能问题,由于在每次调用时都要检测功能的可用性。
下面是一段未优化过的代码,咱们使用了外观模式经过检测浏览器特性的方式来建立一个跨浏览器的使用方法。segmentfault
好比对document
对象添加click
事件的时候:设计模式
function addEvent(dom, type, fn) { if (dom.addEventListener) { // 支持DOM2级事件处理方法的浏览器 dom.addEventListener(type, fn, false) } else if (dom.attachEvent) { // 不支持DOM2级但支持attachEvent dom.attachEvent('on' + type, fn) } else { dom['on' + type] = fn // 都不支持的浏览器 } } const myInput = document.getElementById('myinput') addEvent(myInput, 'click', function() {console.log('绑定 click 事件')})
还能够用来解决一些其余的浏览器兼容性问题:浏览器
const getEvent = function(event) { // 获取事件对象 return event || window.event // IE下window.event } const getTarget = function(event) { // 获取事件元素 const event = getEvent(event) return event.target || event.srcElement // IE下event.srcElement } const preventDefault = function(event) { // 阻止默认事件 const event = getEvent(event) if (event.preventDefault) {event.preventDefault()} else {event.returnValue = false} // IE下 } const cancelBubble = function(event) { const event = getEvent(event) if (event.stopPropagation) {event.stopPropagation()} else {event.cancelBubble = true} // IE下 } document.onclick = function(e) { preventDefault(e) if (getTarget(e) !== document.getElementById('myinput')) {console.log('呵呵')} }
那么什么时候使用外观模式呢?通常来讲分三个阶段:缓存
Facade
也是很是合适的,为系统开发一个外观Facade
类,为设计粗糙和高度复杂的遗留代码提供比较清晰的接口,让新系统和Facade
对象交互,Facade
与遗留代码交互全部的复杂工做。本文是系列文章,能够相互参考印证,共同进步~微信
网上的帖子大多深浅不一,甚至有些先后矛盾,在下的文章都是学习过程当中的总结,若是发现错误,欢迎留言指出~dom
参考:
设计模式以外观模式
《Javascript 设计模式》 - 张荣铭
PS:欢迎你们关注个人公众号【前端下午茶】,一块儿加油吧~函数
另外能够加入「前端下午茶交流群」微信群,长按识别下面二维码便可加我好友,备注加群,我拉你入群~性能