GithubHelp home page GithubHelp logo

cmui / gearbox Goto Github PK

View Code? Open in Web Editor NEW
16.0 4.0 2.0 125 KB

Lightweight JavaScript utilities for web development, based on `_` and `$`.

License: MIT License

JavaScript 93.10% HTML 6.90%
library utility javascript lightweight-javascript-utilities ua string template mobile-web event cmui

gearbox's Introduction

CMUI

CMUI is a UI framework for mobile web. It provides rich widgets and simple interfaces out-of-the-box, which helps developers get rid of details of styling and troubles of compatibility, and focus on building their own applications.

CMUI 是一个专攻移动网页的 UI 框架,它提供了丰富的组件和简洁的接口,开箱即用。CMUI 帮助开发者摆脱样式细节和兼容性困扰,从而腾出更多精力投入到业务开发中。

兼容性

浏览器支持

  • 支持以下移动平台的主流浏览器:

    • iOS 10+
    • Android 4.4+
  • 同样支持以下桌面浏览器:

    • Firefox (Latest)
    • Chrome (Latest)
    • Safari (Latest)

(更多细节参见 CMUI 的浏览器分级支持策略。)

外部依赖

  • Underscore 1.8+
  • Zepto 1.1+
  • Gearbox 0.7+

安装与使用

传统方式

  1. 通过 npm 3 安装:

    $ npm install cmui
  2. 在页面中加载 CMUI 的样式文件、脚本文件及必要的依赖:

    <!DOCTYPE html>
    <html>
    <head>
    	...
    	<link rel="stylesheet" href="node_modules/cmui/dist/cmui.css">
    </head>
    <body>
    	...
    	<script src="node_modules/underscore/underscore-min.js"></script>
    	<script src="node_modules/zepto.js/dist/zepto.min.js"></script>
    	<script src="node_modules/cmui-gearbox/dist/gearbox.min.js"></script>
    	<script src="node_modules/cmui/dist/cmui.js"></script>
    </body>
    </html>

通过 Stylus 加载

如果你的项目以 Stylus 作为 CSS 预处理器语言,则可以在你的源码中直接引入 CMUI 的样式入口文件:

@import './node_modules/cmui/src/css/theme/baixing/index'

在这种方式下,你可以在源码中使用 CMUI 提供的高级 API

  • 变量
  • Mixin

演示与文档

建议使用 iOS/Android 设备访问:CMUI Demo

cmui-demo

谁在用?

以下网站基于 CMUI 构建(请使用 iOS/Android 设备访问):


参与开发

功能模块

CMUI 的部分模块已经分离出去,成为独立项目。这些模块以开发依赖的方式引入,并打包到发布文件中。因此,参与这些独立项目的开发即可修改这些模块。

构建

  1. 把本项目的代码 fork 并 clone 到本地。
  2. 在项目根目录执行 npm install,安装必要的依赖。
  3. 在项目根目录执行 npm run dist,运行构建脚本。
  4. 构建生成的发布文件将存放在 /dist 目录下。

单元测试

  1. 把本项目的代码 fork 并 clone 到本地。
  2. 在项目根目录执行 npm install,安装必要的依赖。
  3. 在浏览器中打开以下文件即可运行单元测试:
    • test/test-dev.html - 测试源码(用于开发阶段的测试)

Thanks

CMUI is based on these open source projects:

CMUI team is using JetBrains IDE (WebStorm) with Open Source License:

  • WebStorm Logo

License

MIT License

gearbox's People

Contributors

cssmagic avatar lyt9304 avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar

gearbox's Issues

适配新的手机号段 199、198、166

2017 新增手机号段的详细信息参见:
https://www.sohu.com/a/164234860_782282


号段汇总:

号段 运营商 用途 需要匹配
134(0~8)
135139
**移动 公众移动通信
150152 **移动 公众移动通信
157 **移动 公众移动通信(TD)
158159 **移动 公众移动通信
182184
187188
**移动 公众移动通信
178 **移动 公众移动通信
1705 **移动 公众移动通信(虚拟运营商)
147 **移动 公众移动通信(数据卡)
130132 **联通 公众移动通信
155156 **联通 公众移动通信
176 **联通 公众移动通信
185186 **联通 公众移动通信
1709 **联通 公众移动通信(虚拟运营商)
145 **联通 公众移动通信(数据卡)
133 **电信 公众移动通信
153 **电信 公众移动通信
177 **电信 公众移动通信
180181
189
**电信 公众移动通信
1349 **电信 卫通
1700 **电信 公众移动通信(虚拟运营商)
198 **移动 公众移动通信
199 **电信 公众移动通信
166 **联通 公众移动通信

API 文档 - `str` 模块

API 文档 - str 模块

JavaScript 变量  

以下预定义的变量在业务层可以直接使用。

.RE_EMAIL  

校验电子邮箱的正则表达式。

示例

gearbox.str.RE_EMAIL.test('[email protected]')  // => true
gearbox.str.RE_EMAIL.test('foo@bar')  // => false
gearbox.str.RE_EMAIL.test('foo.bar.cn')  // => false

.RE_MOBILE  

校验手机号的正则表达式。

手机号必须是**大陆的手机号,11 位数字,不可包含空格、横杠等特殊字符。

示例

gearbox.str.RE_MOBILE.test('13355668899')  // => true
gearbox.str.RE_MOBILE.test('021-55668899')  // => false
gearbox.str.RE_MOBILE.test('10086')  // => false

.RE_POSTCODE  

校验邮政编码的正则表达式。

邮政编码必须是**大陆的邮政编码,6 位数字,不可包含空格、横杠等特殊字符。

示例

gearbox.str.RE_POSTCODE.test('200030')  // => true
gearbox.str.RE_POSTCODE.test('4008517517')  // => false
gearbox.str.RE_POSTCODE.test('1234')  // => false

.CNY  

别名.RMB

人民币符号 ¥

.FULL_WIDTH_CNY  

别名.FULL_WIDTH_RMB

全角的人民币符号

示例

// 将所有全角的人民币符号替换为半角
var text = '¥1000 - ¥2000'
text.split(gearbox.str.FULL_WIDTH_CNY).join(gearbox.str.CNY)  // => '¥1000 - ¥2000'

JavaScript 接口  

.isHash(string)  

判断是否为 hash 字符串。

Hash 字符串以 # 开头,比如 #foo 就是一个 hash 字符串。这种字符串通常出现于链接锚点(<a href="#anchor">bar</a>)、ID 选择符($('#id'))、Twitter 标签或 location.hash 的值等等。

字符串开头的空白符将被忽略,不影响判断结果。

参数

  • string -- 字符串。需要判断的字符串。

返回值

布尔值。判断结果。

示例

gearbox.str.isHash('#foo')  // => true
gearbox.str.isHash('bar')  // => false
gearbox.str.isHash('  #foo-bar')  // => true

.stripHash(string)  

去除 hash 字符串开头的 # 字符。

字符串头尾的空白符也将被去除。

参数

  • string -- 字符串(非字符串会被强制转换为字符串)。需要处理的字符串。

返回值

字符串。处理结果。

示例

gearbox.str.stripHash('#foo')  // => 'foo'
gearbox.str.stripHash('bar')  // => 'bar'
gearbox.str.stripHash('  #foo-bar')  // => 'foo-bar'

.toFloat(string)  

转换为浮点数。

可以视为 parseFloat() 的别名。

参数

  • string -- 字符串。

返回值

数字。转换结果。

示例

gearbox.str.toFloat('0')  // => 0
gearbox.str.toFloat('1.77')  // => 1.77
gearbox.str.toFloat('2.3.6')  // => 2.3
gearbox.str.toFloat('2e3')  // => 2000
gearbox.str.toFloat('1.23foo')  // => 1.23
gearbox.str.toFloat('foo123')  // => NaN

.toInt(string)  

转换为整数。

可以视为 parseInt(string, 10) 的别名。直接取整,不做舍入。

参数

  • string -- 字符串。

返回值

数字。转换结果。

示例

gearbox.str.toInt('0')  // => 0
gearbox.str.toInt('1.77')  // => 1
gearbox.str.toInt('2.3.6')  // => 2
gearbox.str.toInt('2e3')  // => 2000
gearbox.str.toInt('1.23foo')  // => 1
gearbox.str.toInt('foo123')  // => NaN

.toFixed(string, [i])  

转换为固定位数的小数。会做舍入。

Number.prototype.toFixed() 的功能类似,但此接口接收字符串,输出数字。

参数

  • string -- 字符串。
  • i -- 可选。整数。保留的位数。默认值为 0

返回值

数字。转换结果。

示例

gearbox.str.toFixed('0')  // => 0
gearbox.str.toFixed('0', 2)  // => 0
gearbox.str.toFixed('1.77')  // => 2
gearbox.str.toFixed('1.77', 1)  // => 1.8
gearbox.str.toFixed('2.3.6', 2)  // => 2.3
gearbox.str.toFixed('2e3', 3)  // => 2000
gearbox.str.toFixed('1.23foo', 1)  // => 1.2
gearbox.str.toFixed('foo123')  // => NaN

Underscore.string 同名接口  

str 模块提供的部分接口与 Underscore.string 类库的同名接口完全一致。这些接口的源码均引用了 Underscore.string 的实现,并存放在 src/str-backup.js 文件中。

字符串裁剪

  • .trim(string, [characters])  

    请参考 Underscore.string 的文档: trim

  • .ltrim(string, [characters])  

    请参考 Underscore.string 的文档: ltrim

  • .rtrim(string, [characters])  

    请参考 Underscore.string 的文档: rtrim

字符串包含关系

  • .includes(string, substring)  

    别名.contains()

    请参考 Underscore.string 的文档: include

    注意:从 Gearbox v0.6 开始,.include() 已弃用,已改名为 .includes()

  • .startsWith(string, starts, [position])  

    请参考 Underscore.string 的文档: startsWith

  • .endsWith(string, ends, [position])  

    请参考 Underscore.string 的文档: endsWith

废除 `.isPlainObject()` API

背景

由于启用独立命名空间,把 jQuery/Zepto 的同名 API 复制过来没有意义。

鼓励用户在业务代码中使用 $.isPlainObject(),与本库无关。

需要做的

  • 更新源码,废除 .isPlainObject() API。
  • 对本库的源码以及依赖本库的项目(CMUI、Haojing)做一下清查,最终只保留上述两个 API。
  • 更新文档。

`str` 模块中的 `str.include()` 需要改名为 `str.includes()`

背景

  • 在 ES6 的最终版当中,String#contains() 已经更名为 String#includes()
  • 本库启用独立的命名空间,不再需要兼容 Underscore.string 的 API。
  • Underscore 中有 _.includes(),是 _.contains() 的别名。

最终打算

  • 废除 str.include(),把 str.includes() 作为标准 API,并把 str.contains() 作为其别名。
  • 对本库的源码以及依赖本库的项目(CMUI、Haojing)做一下清查,最终只保留上述两个 API。
  • 更新文档。

API 文档 - `action` 模块

API 文档 - action 模块

本项目的 action 模块由 Action 类库实现,详细功能说明请参见该类库的 API 文档wiki

需要注意的是,所有 JavaScript API 均挂接在 gearbox.action 命名空间下。比如:

  • action.add()gearbox.action.add()
  • action.trigger()gearbox.action.trigger()
  • ...

Gearbox测试代码在IE8下适配总结

Gearbox测试代码在IE8下适配总结

整体步骤

  1. mocha支持IE8,但是chai不支持,所以需要找到代替的断言库,也就是expect.js
  2. 换成expect.js后,对应的测试语句语法需要修改,有些没有的需要自己重写,比如deepEqual
  3. 测试页面跑起来之后,看看所有代码中有哪些不能跑的代码,一一修改
    • history.replaceState不支持
    • Date.now不支持
    • Action中的Dom Binding有谜之bug
    • Template中有谜之bug

分步总结

搭建环境,阅读代码

  1. IE8的测试机不能跑,所以只能用vmware跑modernie来搭建测试环境。
  2. bower install && npm install
  3. 阅读gearbox的src代码以及action的代码,熟悉underscore库的语法

找寻代替的断言库

  1. 查找后发现expect.js可以支持IE8,所以就写了简单的测试套件,放在IE8下运行后通过
  2. 分别查看chai的api和expect的api,发现测试所用到的基本断言都是可以代替的,并且expect的eql接口和deepEqual其实原理是差不多的,只不过递归判断的时候需要全等,所以改写是相对比较容易得。

改写测试代码,重写deepEqual

  1. 断言库改变了之后有一些chai的语法要修改到expect去,如下:
    • .to.be.true=>.to.equal(true)
    • .to.be.false=>.to.equal(false)
    • .to.be.undefined=>.to.equal(undefined)
    • .to.deep.equal()=>.to.deepEqual()
  2. 实现deepEqual
    • 首先想了比较多的情况,写了chai版本和expect版本的两个测试集,只要最后改的deepEqual能够将这个测试集完全通过,就可以说基本模拟了chai的deep.equal的接口
    • 分析了deepEqual所可能的情况
    • 阅读expect.js的源代码,了解他的构造,然后在内部添加所需要的deepEqual方法
    • 可以看到eql方法其实思路和deep equal的思路是一样的,只不过expect.js的eql方法对于类型没有卡死,只要==满足就可以了,这和我们需要的是不一样的,所以其实只要以eql的代码为基础修改一下某一些情况下的判断就可以了。
    • 通过deepeql测试集

修改测试代码适配到IE8

  1. Date.now不支持

    now方法IE8不支持,所以加入polyfill

    if (!Date.now) {
          Date.now = function now() {
            return new Date().getTime();
          };
        }
  2. Action中的Dom Binding有谜之bug

    • 这里的bug不是很容易发现,一步步调试过来之后发现,不知道为什么在action模块的getActionName方法调用后,actionName并没有被取出来,是个空字符串。最后定位到了action模块中的.data()这个接口上。
    • 这个bug在使用zepto的时候没有发生,但是在jquery下就发生了。
    • 阅读jquery的data接口的相关代码,发现了jquery在调用dataapi的时候回经过缓存cache对象。
    • 最后发现在赋值data-action的时候,使用的是attr("data-action",value)这个接口,但是取的时候使用的是data接口
    • 也就是说存的时候调用attr,但是没有将新的data值存到缓存池中,但是在取的时候用data接口,却是从缓存池里拿出来的,所以这个值就丢掉了。
    • 所以这个问题通过统一存取的接口就可以fix了。
    • 最后结论:统一使用attr去存取
  3. Template中有谜之bug

    • 这个bug是因为script标签创造出来后,调用jquery的text的方法,最后就会调用原生的createTextNode,然后这个方法如果实在script标签下调用的话,IE8下面会有bug
    • 用原生的方法去添加一个script标签
    var body= document.getElementsByTagName('body')[0]; 
    var script1= document.createElement('script'); 
    script1.type= SCRIPT_TYPE; 
    script1.id=PREFIX + TEMPLATE_ELEM_ID_1;
    script1.text= templateCode1; 
    body.appendChild(script1); 
  4. history.replaceState不支持

    • 先尝试用了polyfill的方式,找到了history.js,尝试之后由于是通过改变hash值来完成的,所以最后url会变得很乱,就无法测试函数功能了,这条路就是走不通的。

    • 乱七八糟想了很多

    • 在鹏哥的提示下尝试了用iframe的方式,其实已经想到了,但是没有往这个方面多考虑一下,而是一直再想怎么自己造一个window来欺骗action

    • iframe的主要思路是:

      • 在测试页面插一个iframe,然后所有的跳转都在iframe中进行
      • 每次要跳转页面的时候,自动分配一个testID,并和url一起加到iframe的url中,进行跳转
      • 将回调函数以testID为key注册到regesteredTests中
      • 将需要测试的param通过window.name赋给iframe,这样就可以在iframe的脚本中拿到需要测试的数据
      • 在测试页面注册对应onMessage操作,当收到iframe发来的结果后,根据testID去执行相应的回调函数
      • 在iframe中执行_.url.getParam的操作后,将记录下来的结果以及本次分配的testID,通过postMessage的方式传回给原来的测试页面
      • 触发测试页面的回调函数,将测试结果与预期结果进行比较
    • 坑:global leak

      这个坑是因为,通过jquery创造iframe的时候,jquery创造了一个全局变量就是这个iframe的id,然后指向iframe这个dom元素,但是这个在mocha中不被允许,他怕你在写代码中无意创造了全局变量,为了提醒你,所以会报global leak的错,所以在一开始的时候就设定好sandbox是我刻意创造出的全局变量就可以了

      $(function(){
          mocha
              .globals(['sandbox'])
              .run()
      })
    • 坑:JSON格式中不能够使某个key对应的value为undefined

      由于这个原因从iframe传参数回来的时候回导致value未undefine的key会丢失,但是由于IE8下的postMessage接口只能传递字符串,所以说没有很好的方法解决,只能暂时通过数组记录undefined的那些key,然后传回测试页面的方法来还原测试结果

API 文档 - `url` 模块

API 文档 - url 模块

术语  

Query String

举例来说,http://domain.com/path/file?foo&bar=2 中的 foo&bar=2 部分即为 query string。

Query String 的本质是对一些名值对进行编码和序列化之后的结果。而 query string 的解析就是一个反序列化和解码的过程。

URL 参数

Query String 所保存的这些名值对即称作 “URL 参数”。

JavaScript 接口  

.parseQuery(queryString)  

把 query string 解析为以对象的方式保存的名值对。

参数

  • queryString -- 字符串。需要解析的 query string。

返回值

对象。解析结果,以名值对的方式保存。

示例

gearbox.url.parseQuery('foo=1&bar=2')  // => {foo: '1', bar: '2'}
gearbox.url.parseQuery('foo=&bar=2')  // => {foo: '', bar: '2'}
gearbox.url.parseQuery('foo&bar=2')  // => {foo: '', bar: '2'}
gearbox.url.parseQuery('')  // => {}

注意事项

  • 传入不合法的参数,则一律返回空对象({})。
  • Query string 中的所有 key 都会被转换为小写。
  • Query string 的格式为 foo=1&bar=true,不包含问号。如果此接口接收的参数以问号开头,则会被视为第一个 URL 参数的一部分,因为 ?foo 是一个合法的 URL 参数名。
  • Query string 中多个连续的 & 字符会被视为一个。
  • 解析结果中的值如果为 truefalsenullundefined 或数字时,总是以字符串的方式保存,不会自动转换数据类型。
  • 当 query string 中出现某个 key 但没有对应的值时(比如 foo&bar=2foo=&bar=2 中的 foo),其值将解析为空字符串。

已知问题

  • 重复出现的 key 将只解析最后一次出现的值,不会把所有值加入到一个数组中。
  • 不处理复杂模式的 key,比如 foo[]foo[bar] 都不会被视为特殊含义,只会视为普通的 key。

.getParam(key)  

获取当前页面 URL 的某个 URL 参数的值。

参数

  • key -- 字符串。需要获取的 URL 参数名,忽略大小写。

返回值

字符串或 undefined。对应 URL 参数的值。

示例

假设当前页面的 URL 为 http://domain.com/path/file?foo&bar=2,此时:

gearbox.url.getParam('foo')  // => ''
gearbox.url.getParam('bar')  // => '2'
gearbox.url.getParam('absentKey')  // => undefined

注意事项

  • Query string 的解析方式参见 .parseQuery() 方法。
  • 当页面 URL 发生变化时(比如调用 history.pushState() 等方法时),返回结果总是当前的。

.appendParam(url, param)  

为给定的 URL 附加新的参数。

参数

  • url -- 字符串。待处理的 URL。
  • param -- 对象。需要附加的 URL 参数(名值对)。

返回值

字符串。已附加 URL 参数的新的 URL。

示例

var url = 'http://domain.com/path/file'

url = gearbox.url.appendParam(url, {foo: 'bar'})
    // => 'http://domain.com/path/file?foo=bar'

url = gearbox.url.appendParam(url, {test: 1})
    // => 'http://domain.com/path/file?foo=bar&test=1'

注意事项

  • param 参数中的 key 并不会覆盖 url 参数中已有的同名 key,只是追加一个同名参数。

.removeHashFromUrl(url)  

把 URL 中的 hash 部分去除。

参数

  • url -- 字符串。待处理的 URL,可以是完整的 URL,也可以是相对路径。若传入其它类型的数值,将被转换为字符串。

返回值

字符串。去除 hash 之后的 URL。若未传入参数则返回空字符串。

示例

var url = 'http://domain.com/foo#bar'
gearbox.url.removeHashFromUrl(url)  // => 'http://domain.com/foo'

.getHashFromUrl(url)  

获取 URL 中的 hash 部分。获取结果包含开头的 # 字符。

如果需要得到当前页面 URL 的 hash 部分,直接使用 location.hash 即可。

参数

  • url -- 字符串。待处理的 URL,可以是完整的 URL,也可以是相对路径。若传入其它类型的数值,将被转换为字符串。

返回值

字符串。若传入的 URL 不包含 hash 部分则返回空字符串;若未传入参数则返回空字符串。

示例

var url = 'http://domain.com/foo#bar'
gearbox.url.getHashFromUrl(url)  // => '#bar'

别名  

.isHash()  

gearbox.str.isHash() 的别名。

.stripHash()  

gearbox.str.stripHash() 的别名。



暂未实现的接口 ⚠️

.parse(url)  

别名.parseUrl()

此接口的行为与 Node.js 内置的 url 模块.parse() 接口的功能保持基本一致,但仍然有细微差异,详见 “注意事项” 部分。

解析 URL 的各个要素,解析结果以对象的方式输出。举例来说,当传入以下 URL 时:

'http://user:[email protected]:8080/path/file?query=string#hash'

解析结果中各个 key 的含义和值如下:

  • href -- 完整 URL 值。协议名和域名会被转换为全小写。
    值:(同传入的 URL)
  • protocol -- 协议。
    值:'http:'
  • slashes -- 布尔值,此协议是否需要双斜杠。
    值:true
  • host -- 主机(含端口号)。域名会被转换为全小写。
    值:'domain.com:8080'
  • auth -- 身份验证信息。
    值:'user:pass'
  • hostname -- 主机名(不含端口号)。域名会被转换为全小写。
    值:'domain.com'
  • port -- 端口号。它不会被转换为数字。
    值:'8080'
  • pathname -- 路径(含文件名)。
    值:'/path/file'
  • search -- query string 部分(含开头的 ? 字符)。参数名和值不会被解码。
    值:'?query=string'
  • path -- 路径加上 query string 部分。参数名和值不会被解码。
    值:'/path/file?query=string'
  • query -- query string 部分(不含开头的 ? 字符)。
    值:'query=string'
  • hash -- hash 部分(含开头的 # 字符)。
    值:'query=string'

可以看出它们涵盖了 location 对象的各个 key,且含义相同。

参数

  • url -- 字符串。需要解析的 URL。

返回值

对象。整个 URL 的解析结果,URL 的各个要素部分以名值对的方式保存。

当参数不合法时,返回空对象({})。

注意事项

  • 此接口的实现依赖 DOM,无法用于 Worker。
  • 若传入的 URL 不完整,则视为相对路径,以当前页面为基准进行解析。这也意味着 //foo/bar 将会被视为 “foo 主机下的 /bar 路径”。
  • 当 URL 中的某些部分不存在时,解析结果中对应的 key 也将不存在。

.format(parts)  

别名.composeUrl()

此接口的行为与 Node.js 内置的 url 模块的 .format() 接口的功能保持基本一致。

根据提供的 URL 各个要素,构造完整的 URL。URL 各个组成部分的名称及含义同 .parse() 接口的描述。

参数

  • parts -- 对象。URL 的各个要素的名值对。

返回值

字符串。构造出的完整 URL。

当参数不合法时,返回空字符串。

示例

var urlParts = {
    protocol: 'http:',
    host: 'domain.com',
    pathname: '/foo/bar'
}
gearbox.url.format(urlParts)  // => 'http://domain.com/foo/bar'

注意事项

  • 此接口的实现依赖 DOM,无法用于 Worker。
  • href 字段将被忽略。
  • path 字段将被忽略。
  • protocol 字段如果没有用冒号结尾,则会自动补上。对于这些协议(httphttpsftpgopherfile),还会自动补上双斜杠。
  • 可以额外使用 slashes 字段来强制自动补上双斜杠。
  • 如果提供了 auth 字段,则会被使用。
  • 当存在 host 时,将忽略 hostnameport 字段。
  • 当存在 search 时,将忽略 query 字段。
  • pathname 应以 / 开头;不以 / 开头则会自动补上。
  • search 应以 ? 开头;不以 ? 开头则会自动补上。
  • hash 应以 # 开头;不以 # 开头则会自动补上。
  • hosthostnamepathname 中的 ?# 字符会被编码;search 中的 # 字符会被编码。
  • port 值在经过 parseInt(port, 10) 转换后必须为 0 或正整数,否则均视为 0
  • URL 的各个要素并不都是必选的。各字段省略时的行为如下(注意,字段值为空字符串并不表示省略):
    • protocol -- 若省略则取当前页面的 location.protocol
    • auth -- 若省略则不输出。
    • host -- 若省略则取 hostnameport
    • hostname -- 若省略则取当前页面的 location.hostname
    • port -- 若省略则不输出。
    • pathname -- 若省略则取根目录(/)。
    • search -- 若省略则取 query
    • query -- 若省略则不输出。
    • hash -- 若省略则不输出。

新建一个适配文件,便于从 v0.5 升级到 v0.6

背景

因从 v0.5 到 v0.6 的变化较大(主要是命名空间的变化),需要新建一个适配文件,便于平滑升级——基于 Gearbox v0.5 业务代码无需改动就可以升级到 v0.6。

当然长期来看业务代码还是要改的,这个适配文件只不过增加了升级的缓冲期。

注意事项

  • 需要用老版的单元测试来验证它的可靠性。

API 文档 - `dom` 模块

API 文档 - dom 模块

JavaScript 变量  

为减少业务层对常用 DOM 元素的重复获取和包装,dom 模块预先缓存了这些元素的 Zepto 包装对象。在业务层可以直接使用。

.$win  

window 对象的 Zepto 包装对象。

示例

监听 resize 事件:

gearbox.dom.$win.on('resize', function (ev) {
    //...
})

.$root  

document.documentElement 对象(即 <html> 元素)的 Zepto 包装对象。

.$body  

document.body 对象(即 <body> 元素)的 Zepto 包装对象。

注意事项

为确保对 document.body 对象的正确获取,加载 Gearbox 的脚本标签须放置在页面的 <body> 标签内。当然,根据前端性能的最佳实践,所有外链脚本也确实应该放置在页面的最底部:

<html>
<head>...</head>
<body>
    ...
    <script src="gearbox.js"></script>
</body>
</html>

JavaScript 接口  

.is$Element(obj)  

判断是否为 Zepto 包装对象(或 Zepto 集合)。

如果外部环境没有加载 Zepto 但有 jQuery,则理论上此方法也可以判断 jQuery 包装对象(或 jQuery 集合)。

参数

  • obj -- 任意类型。需要判断的对象。

返回值

布尔值。判断结果。

示例

gearbox.dom.is$Element(gearbox.dom.$win)  // => true

API 文档 - `template` 模块

API 文档 - template 模块

本项目的 template 模块由 Underscore-template 类库实现,详细功能说明请参见该类库的 API 文档wiki

需要注意的是,所有 JavaScript API 均挂接在 gearbox.template 命名空间下。比如:

  • template.add()gearbox.template.add()
  • template.render()gearbox.template.render()
  • ...

API 文档 - `ua` 模块

API 文档 - ua 模块

这个模块在加载时会对当前 UA 进行探测(通过特性检测或 UA 字符串分析等方式),并以变量的方式提供探测结果。

这些探测浏览器内核和类型的接口仅用于底层开发或流量统计,不建议在业务层的常规功能中使用。

JavaScript 变量  

.isTouchDevice  

布尔值。当前 UA 是否为触屏设备。Chrome 开启触摸调试之后也将被视为触屏设备。

此探测基于特性检测。


.isSafari  

布尔值。当前 UA 是否为 Safari 浏览器(包括桌面版与移动版)。

此探测基于 UA 信息。

.isChrome  

布尔值。当前 UA 是否为 Chrome 浏览器(包括桌面版与移动版)。

此探测基于 UA 信息。


.isIOS  

布尔值。当前操作系统是否为 iOS 系统。

还有以下对 iOS 设备更细节的探测(值为布尔值或 undefined):

  • .isIPhone -- 当前 UA 是否为 iPhone。
  • .isIPad -- 当前 UA 是否为 iPad。
  • .isIPod -- 当前 UA 是否为 iPod touch。

这些探测均基于 UA 信息。

.isAndroid  

布尔值。当前 UA 是否为 Android 系统。

此探测基于 UA 信息。

.isMobileDevice  

布尔值。当前 UA 是否为移动设备。所有 iOS 和 Android 设备会被识别为移动设备。

此探测基于 UA 信息。


.osVersion  

字符串。当前移动操作系统的版本号,格式为 {主版本号}.{次版本号}。仅可识别 iOS 和 Android 系统的版本号,对于非移动操作系统或不可识别的移动操作系统,其值一律为空字符串。

此探测基于 UA 信息。

示例

  • '7.0' -- 对 iOS 7.0.1 的探测结果。
  • '4.4' -- 对 Android 4.4.4 的探测结果。
  • '' -- 对 Windows、Mac OS、WinPhone 等系统的探测结果。

.browser  

字符串。当前浏览器的名称,可能的值如下:

  • 'chrome' -- Chrome(谷歌浏览器)
  • 'safari' -- Safari(苹果浏览器)
  • 'firefox' -- Firefox(火狐浏览器)
  • 'opera' -- Opera 浏览器
  • 'uc' -- UC 浏览器
  • 'baidu-app' -- 百度客户端
  • 'baidu-browser' -- 百度浏览器
  • 'm-qq-browser' -- 手机 QQ 浏览器
  • 'miui' -- 小米浏览器
  • 'ie-mobile' -- IE 移动版
  • 'edge' -- 微软 Edge 浏览器
  • 'wechat' -- 微信
  • 'weibo' -- 微博
  • 'chrome-webview' -- 采用 Chrome 内核的 WebView

此探测基于 UA 信息。

.engine  

字符串。当前浏览器的引擎(内核)名称,可能的值如下:

  • 'webkit' -- iOS 与新版 Android 浏览器的内核
  • 'chrome' -- Chrome 内核(新版 Android 浏览器与 Opera 的内核)
  • 'gecko' -- Firefox 的内核
  • 'presto' -- 旧版 Opera 的内核
  • 'edge' -- Edge 内核

对于无法识别的引擎,其值一律为空字符串。

此探测基于 UA 信息。

.engineVersion  

字符串。当前浏览器的引擎(内核)版本。对于无法识别的引擎版本,其值一律为空字符串。

此探测基于 UA 信息。

示例

  • '533.1' -- 对 Android 2.2.2 内置浏览器引擎 WebKit 版本的探测结果。
  • '43.0' -- 对 Chrome 43.0.2357.65 引擎版本的探测结果。
  • '' -- 对 Firefox 引擎版本的探测结果。
  • '' -- 对 Edge 引擎版本的探测结果。

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.