vue.js学习09之vue2.x实现vue1.x中默认的过滤器
来源:互联网 发布:比较好的淘宝客采集群 编辑:程序博客网 时间:2024/06/06 07:18
最近在学习vue.js,新版本是2.3.0了。在学习过滤器知识时,网上的一些例子是基于vue1.X官方提供的默认的过滤器,但是在vue2.x中全部取消了,都需要自己实现了。但是在vue.js的1.x版本中可以看到默认的过滤器的实现源码。我们可以把想过过滤器的源码复制出来,结合vue2.x过滤器的要求,做一些简单处理就可以使用了。在vue2.x中仍然可以在文本中使用过滤器,比如{{message | capitalize }} ,但是在v-for中就不能直接使用orderby 等过滤器了。
filter.html做测试,vue.js是2.3.0版本的
<!DOCTYPE html><html><head> <meta charset="UTF-8"> <title></title> <link rel="stylesheet" href="bootstrap-3.3.7/dist/css/bootstrap.min.css"> <script src="vue.js"></script> <script src="filter.js"></script></head><body> <div id="app"> <table class='table table-bordered'> <thead> <tr> <th>Name</th> <th>Age</th> <th>Sex</th> <th>Salary</th> </tr> </thead> <tbody> <tr v-for="person in peopleOderBy "> <td>{{ person.name | capitalize }}</td> <td>{{ person.age }}</td> <td>{{ person.sex }}</td> <td>{{ person.salary | currency('¥','0') }}</td> </tr> </tbody> </table> </div></body><script> var vm = new Vue({ el: '#app', data: { people: [{ name: 'jack', age: 30, sex: 'male', salary: '8000' }, { name: 'bill', age: 26, sex: 'male', salary: '7000' }, { name: 'Tracy', age: 22, sex: 'female', salary: '4500' }, { name: 'chris', age: 36, sex: 'male', salary: '9000' }] }, computed: { peopleLimitBy: function() { return limitBy(this.people, 2, 1); }, peopleFilterBy: function() { return filterBy(this.people, 'r', 'in', 'name', 'sex'); }, peopleOderBy: function() { return orderBy(this.people, 'age', 1); } } })</script><style> body { margin: 0 auto; margin-left: 30%; margin-right: 30%; margin-top: 10px; }</style></html>
其中filter.js就是从vue.js 1.x版本中复制出来的一些过滤器的代码
/** * 字符串的第一个字母大写 */Vue.filter('capitalize', function(value) { if (!value && value !== 0) return ''; value = value.toString(); return value.charAt(0).toUpperCase() + value.slice(1);});/** * 将字符串全部转为大写字母 */Vue.filter('uppercase', function(value) { return value || value === 0 ? value.toString().toUpperCase() : '';});/** * 将字符串全部转为小写字母 */Vue.filter('uppercase', function(value) { return value || value === 0 ? value.toString().toLowerCase() : '';});/** * 12345 => $12,345.00 * * @param {String} sign * @param {Number} decimals Decimal places */Vue.filter('currency', function(value, _currency, decimals) { value = parseFloat(value); if (!isFinite(value) || !value && value !== 0) return ''; _currency = _currency != null ? _currency : '$'; decimals = decimals != null ? decimals : 2; var stringified = Math.abs(value).toFixed(decimals); var _int = decimals ? stringified.slice(0, -1 - decimals) : stringified; var i = _int.length % 3; var head = i > 0 ? _int.slice(0, i) + (_int.length > 3 ? ',' : '') : ''; var _float = decimals ? stringified.slice(-1 - decimals) : ''; var sign = value < 0 ? '-' : ''; var digitsRE = /(\d{3})(?=\d)/g; return sign + _currency + head + _int.slice(i).replace(digitsRE, '$1,') + _float;});/** * 'item' => 'items' * * @params * an array of strings corresponding to * the single, double, triple ... forms of the word to * be pluralized. When the number to be pluralized * exceeds the length of the args, it will use the last * entry in the array. * * e.g. ['single', 'double', 'triple', 'multiple'] */Vue.filter('pluralize', function(value) { var args = toArray(arguments, 1); return args.length > 1 ? args[value % 10 - 1] || args[args.length - 1] : args[0] + (value === 1 ? '' : 's');});/** * Limit filter for arrays * * @param {Number} n * @param {Number} offset (Decimal expected) */function limitBy(arr, n, offset) { offset = offset ? parseInt(offset, 10) : 0; n = toNumber(n); return typeof n === 'number' ? arr.slice(offset, offset + n) : arr;}/** * Filter filter for arrays * * @param {String} search * @param {String} [delimiter] * @param {String} ...dataKeys */function filterBy(arr, search, delimiter) { arr = convertArray(arr); if (search == null) { return arr; } if (typeof search === 'function') { return arr.filter(search); } // cast to lowercase string search = ('' + search).toLowerCase(); // allow optional `in` delimiter // because why not var n = delimiter === 'in' ? 3 : 2; // extract and flatten keys var keys = Array.prototype.concat.apply([], toArray(arguments, n)); var res = []; var item, key, val, j; for (var i = 0, l = arr.length; i < l; i++) { item = arr[i]; val = item && item.$value || item; j = keys.length; if (j) { while (j--) { key = keys[j]; if (key === '$key' && contains(item.$key, search) || contains(getPath(val, key), search)) { res.push(item); break; } } } else if (contains(item, search)) { res.push(item); } } return res;};/** * 排序 */function orderBy(arr) { var comparator = null; var sortKeys = undefined; arr = convertArray(arr); // determine order (last argument) var args = toArray(arguments, 1); var order = args[args.length - 1]; if (typeof order === 'number') { order = order < 0 ? -1 : 1; args = args.length > 1 ? args.slice(0, -1) : args; } else { order = 1; } // determine sortKeys & comparator var firstArg = args[0]; if (!firstArg) { return arr; } else if (typeof firstArg === 'function') { // custom comparator comparator = function(a, b) { return firstArg(a, b) * order; }; } else { // string keys. flatten first sortKeys = Array.prototype.concat.apply([], args); comparator = function(a, b, i) { i = i || 0; return i >= sortKeys.length - 1 ? baseCompare(a, b, i) : baseCompare(a, b, i) || comparator(a, b, i + 1); }; } function baseCompare(a, b, sortKeyIndex) { var sortKey = sortKeys[sortKeyIndex]; if (sortKey) { if (sortKey !== '$key') { if (isObject(a) && '$value' in a) a = a.$value; if (isObject(b) && '$value' in b) b = b.$value; } a = isObject(a) ? getPath(a, sortKey) : a; b = isObject(b) ? getPath(b, sortKey) : b; } return a === b ? 0 : a > b ? order : -order; } // sort on a copy to avoid mutating original array return arr.slice().sort(comparator);};/** * Convert an Array-like object to a real Array. */function toArray(list, start) { start = start || 0; var i = list.length - start; var ret = new Array(i); while (i--) { ret[i] = list[i + start]; } return ret}function convertArray(value) { if (Array.isArray(value)) { return value; } else if (isPlainObject(value)) { // convert plain object to array. var keys = Object.keys(value); var i = keys.length; var res = new Array(i); var key; while (i--) { key = keys[i]; res[i] = { $key: key, $value: value[key] }; } return res; } else { if (typeof value === 'number' && !isNaN(value)) { value = range(value); } return value || []; }}/** * String contain helper * * @param {*} val * @param {String} search */function contains(val, search) { var i; if (isPlainObject(val)) { var keys = Object.keys(val); i = keys.length; while (i--) { if (contains(val[keys[i]], search)) { return true; } } } else if (Array.isArray(val)) { i = val.length; while (i--) { if (contains(val[i], search)) { return true; } } } else if (val != null) { return val.toString().toLowerCase().indexOf(search) > -1; }}/** * Quick object check - this is primarily used to tell * Objects from primitive values when we know the value * is a JSON-compliant type. */function isObject(obj) { return obj !== null && typeof obj === 'object'}function isPlainObject(obj) { return Object.prototype.toString.call(obj) === '[object Object]';}/** * Check and convert possible numeric strings to numbers * before setting back to data * * @param {*} value * @return {*|Number} */function toNumber(value) { if (typeof value !== 'string') { return value; } else { var parsed = Number(value); return isNaN(parsed) ? value : parsed; }}function getPath(obj, path) { return parseExpression(path).get(obj);}/** * Parse an expression into re-written getter/setters. * * @param {String} exp * @param {Boolean} needSet * @return {Function} */var expressionCache = new Cache(1000);var pathTestRE = /^[A-Za-z_$][\w$]*(?:\.[A-Za-z_$][\w$]*|\['.*?'\]|\[".*?"\]|\[\d+\]|\[[A-Za-z_$][\w$]*\])*$/;var booleanLiteralRE = /^(?:true|false)$/;function parseExpression(exp, needSet) { exp = exp.trim(); // try cache var hit = expressionCache.get(exp); if (hit) { if (needSet && !hit.set) { hit.set = compileSetter(hit.exp); } return hit; } var res = { exp: exp }; res.get = isSimplePath(exp) && exp.indexOf('[') < 0 // optimized super simple getter ? makeGetterFn('scope.' + exp) // dynamic getter : compileGetter(exp); if (needSet) { res.set = compileSetter(exp); } expressionCache.put(exp, res); return res;}function Cache(limit) { this.size = 0; this.limit = limit; this.head = this.tail = undefined; this._keymap = Object.create(null);}var p = Cache.prototype;/** * Put <value> into the cache associated with <key>. * Returns the entry which was removed to make room for * the new entry. Otherwise undefined is returned. * (i.e. if there was enough room already). * * @param {String} key * @param {*} value * @return {Entry|undefined} */p.put = function(key, value) { var removed; if (this.size === this.limit) { removed = this.shift(); } var entry = this.get(key, true); if (!entry) { entry = { key: key }; this._keymap[key] = entry; if (this.tail) { this.tail.newer = entry; entry.older = this.tail; } else { this.head = entry; } this.tail = entry; this.size++; } entry.value = value; return removed;};/** * Purge the least recently used (oldest) entry from the * cache. Returns the removed entry or undefined if the * cache was empty. */p.shift = function() { var entry = this.head; if (entry) { this.head = this.head.newer; this.head.older = undefined; entry.newer = entry.older = undefined; this._keymap[entry.key] = undefined; this.size--; } return entry;};/** * Get and register recent use of <key>. Returns the value * associated with <key> or undefined if not in cache. * * @param {String} key * @param {Boolean} returnEntry * @return {Entry|*} */p.get = function(key, returnEntry) { var entry = this._keymap[key]; if (entry === undefined) return; if (entry === this.tail) { return returnEntry ? entry : entry.value; } // HEAD--------------TAIL // <.older .newer> // <--- add direction -- // A B C <D> E if (entry.newer) { if (entry === this.head) { this.head = entry.newer; } entry.newer.older = entry.older; // C <-- E. } if (entry.older) { entry.older.newer = entry.newer; // C. --> E } entry.newer = undefined; // D --x entry.older = this.tail; // D. --> E if (this.tail) { this.tail.newer = entry; // E. <-- D } this.tail = entry; return returnEntry ? entry : entry.value;};function isSimplePath(exp) { return pathTestRE.test(exp) && // don't treat true/false as paths !booleanLiteralRE.test(exp) && // Math constants e.g. Math.PI, Math.E etc. exp.slice(0, 5) !== 'Math.';}function makeGetterFn(body) { try { /* eslint-disable no-new-func */ return new Function('scope', 'return ' + body + ';'); /* eslint-enable no-new-func */ } catch (e) { 'development' !== 'production' && warn('Invalid expression. ' + 'Generated function body: ' + body); }}
阅读全文
0 0
- vue.js学习09之vue2.x实现vue1.x中默认的过滤器
- vue 学习笔记二之vue2与vue1的选择
- Vue2.x教程之filter过滤器的使用
- Vue1.x
- vue---vue2.x中如何异步加载路由组件,webpack+vue实现组件懒加载
- Vue1.0中过滤器和Vue2.0中自定义指令的用法
- 使用vue-cli 创建vue2.x项目中使用vue-router 与之前的区别
- vue2.x的初始化
- vue2.x vue-cli webpack 初探
- vue.js之路(4)——vue2.0s中eventBus实现兄弟组件通信
- vue1.0和vue2.0的区别之路由
- vue1和vue2的区别
- Vue.js过滤器学习
- Vue2.x 之 基础API
- vue1x、vue-router 0.7x 迁移到 vue2 vue-router2 vueX的坑
- vue---vue2.x中父组件如何触发子组件事件方法?
- 响应式学习----从VUE1 到 VUE2
- vue.js之filter过滤器
- 浅谈js的深拷贝与浅拷贝
- AOSP Android 源码开源工程镜像获取方法
- java多线程之创建和启动线程
- 解决Mac book pro外接现实器有黑边问题
- 自定义侧边字母导航栏和三阶贝塞尔曲线的轨迹画心
- vue.js学习09之vue2.x实现vue1.x中默认的过滤器
- React 认知 三 组件Component
- 只能输入整数或小数的正则表达式
- Codeforces Round #419 A. Karen and Game
- 基于现有项目的测试环境部署新项目
- layer火狐弹出层显示不完全问题
- 职工有职工号,姓名,年龄.输入n个职工的信息,找出3个年龄最小的职工打印出来
- 使用RTL-SDR和Matlab Simulink玩转软件无线电(五)
- of_iomap