1/* eslint-disable */ 2 3import { def, Log } from '../../utils/index.ts'; 4 5const arrayProto = Array.prototype; 6export const arrayMethods = Object.create(arrayProto); 7 8/* 9 * Intercept mutating methods and emit events 10 */ 11 12;[ 13 'push', 14 'pop', 15 'shift', 16 'unshift', 17 'splice', 18 'sort', 19 'reverse' 20] 21.forEach(function (method) { 22 // cache original method 23 const original = arrayProto[method]; 24 def(arrayMethods, method, function mutator() { 25 // avoid leaking arguments: 26 // http://jsperf.com/closure-with-arguments 27 let i = arguments.length; 28 const args = new Array(i); 29 while (i--) { 30 args[i] = arguments[i]; 31 } 32 const result = original.apply(this, args); 33 const ob = this.__ob__; 34 let inserted; 35 switch (method) { 36 case 'push': 37 inserted = args; 38 break; 39 case 'unshift': 40 inserted = args; 41 break; 42 case 'splice': 43 inserted = args.slice(2); 44 break; 45 } 46 if (inserted) { 47 ob.observeArray(inserted); 48 } 49 // Notify change. 50 ob.dep.notify(); 51 return result; 52 }) 53}) 54 55/** 56 * Swap the element at the given index with a new value and emits corresponding event. 57 * @param {Number} index 58 * @param {*} val 59 * @return {*} - replaced element 60 */ 61 62def( 63 arrayProto, 64 '$set', 65 function $set (index, val) { 66 Log.warn(`"Array.prototype.$set" is not a standard API, ` 67 + `it will be removed in the next version.`); 68 if (index >= this.length) { 69 this.length = index + 1; 70 } 71 return this.splice(index, 1, val)[0]; 72 } 73) 74 75/** 76 * Convenience method to remove the element at given index. 77 * @param {Number} index 78 * @param {*} val 79 */ 80 81def( 82 arrayProto, 83 '$remove', 84 function $remove (index) { 85 Log.warn(`"Array.prototype.$remove" is not a standard API,` 86 + ` it will be removed in the next version.`); 87 if (!this.length) { 88 return; 89 } 90 if (typeof index !== 'number') { 91 index = this.indexOf(index); 92 } 93 if (index > -1) { 94 this.splice(index, 1); 95 } 96 } 97) 98 99/** 100 * Support includes for panda. 101 * @param {Number} index 102 * @param {*} val 103 * @return {Boolean} 104 */ 105 106def( 107 arrayProto, 108 'includes', 109 function includes(param, start = 0) { 110 if (start >= this.length) return false 111 if (start < 0) { 112 start = start + this.length < 0 ? 0 : start + this.length; 113 } 114 if (Number.isNaN(param)) { 115 for (let i = start; i < this.length; i++) { 116 if (Number.isNaN(this[i])) return true; 117 } 118 } else { 119 for (let i = start; i < this.length; i++) { 120 if (this[i] === param) return true; 121 } 122 } 123 return false 124 } 125) 126