diff --git a/packages/@qymh/q-select/src/index.ts b/packages/@qymh/q-select/src/index.ts index c6e15e3..18991f3 100644 --- a/packages/@qymh/q-select/src/index.ts +++ b/packages/@qymh/q-select/src/index.ts @@ -76,12 +76,17 @@ class QSelect extends Layer { ? column[column.length - 1] + 1 : column + 1; const min = Array.isArray(column) ? column[0] : column; - this.normalizeData(realData as NotGangedData, column); - this.dataTrans = this.dataTrans.slice(0, max).filter(v => v.length); - this.dynamicIndex = this.dynamicIndex.slice(0, max); - this.diff(preTrans, this.dataTrans, min, true, true, true); - this.realData = deepClone(this.dynamicData); - resolve(this.getChangeCallData()); + const validateData = Array.isArray(column) ? realData : [realData]; + if (this.validateData(validateData as any, false)) { + this.normalizeData(realData as NotGangedData, column); + this.dataTrans = this.dataTrans.slice(0, max).filter(v => v.length); + this.normalizeIndex(this.dataTrans); + this.diff(preTrans, this.dataTrans, min, true, true, true); + this.realData = deepClone(this.dynamicData); + resolve(this.getChangeCallData()); + } else { + reject(); + } } catch (error) { reject(error); } @@ -162,22 +167,8 @@ class QSelect extends Layer { } else { const dataTransLater = this.genGangedData( this.data as GangedData[], - index + this.dynamicIndex ); - this.dynamicIndex.map((v, i) => { - if (v < 0) { - this.dynamicIndex[i] = 0; - this.realIndex[i] = 0; - } - const len = ( - dataTransLater[i] || dataTransLater[dataTransLater.length - 1] - ).length; - if (v > len - 1) { - this.dynamicIndex[i] = len - 1; - this.realIndex[i] = len - 1; - } - return v; - }); this.diff( preDataTrans || this.dataTrans, dataTransLater, diff --git a/packages/@qymh/q-select/src/layer.ts b/packages/@qymh/q-select/src/layer.ts index 6f4a698..b4a75cf 100644 --- a/packages/@qymh/q-select/src/layer.ts +++ b/packages/@qymh/q-select/src/layer.ts @@ -139,7 +139,7 @@ class Layer { * 验证data规范 * @param forceData 需要覆盖验证的data */ - validateData(forceData?: Data): boolean { + validateData(forceData?: Data, forceType?: boolean): boolean { let data = forceData || this.$options.data; if ( !data || @@ -150,7 +150,10 @@ class Layer { this.data = data = [['']]; } - this.isGanged = data.every((v: any) => isPlainObj(v)); + this.isGanged = + forceType !== undefined + ? forceType + : data.every((v: any) => isPlainObj(v)); /** * 递归验证联动下的data @@ -202,10 +205,17 @@ class Layer { } return v.every((p: NotGangedDataObj | string | number) => { if (isPlainObj(p)) { - return assert( - (p as NotGangedDataObj).value !== undefined, - 'value is required if NotGangedData is an object' - ); + if ((p as any).children && (p as any).children.length) { + return assert( + false, + 'notGangedData can not has prop which is children' + ); + } else { + return assert( + (p as NotGangedDataObj).value !== undefined, + 'value is required if NotGangedData is an object' + ); + } } else if (typeof p !== 'string' && typeof p !== 'number') { return assert( false, @@ -863,7 +873,7 @@ class Layer { genGangedData(data: GangedData[], preciseIndex?: number[]): DataTrans[][] { let index = 0; const dataTrans: DataTrans[][] = []; - function genGangedDataChildren(child: GangedData[]) { + function genGangedDataChildren(this: Layer, child: GangedData[]) { dataTrans[index] = []; for (const item of child) { dataTrans[index].push({ @@ -873,11 +883,15 @@ class Layer { } const curIndex = (preciseIndex || [])[index] || 0; index++; - if (child[curIndex] && child[curIndex].children.length) { - genGangedDataChildren(child[curIndex].children); + if (child[curIndex]) { + if (child[curIndex].children.length) { + genGangedDataChildren.call(this, child[curIndex].children); + } + } else if (child[0] && child[0].children.length) { + genGangedDataChildren.call(this, child[0].children); } } - genGangedDataChildren(data); + genGangedDataChildren.call(this, data); this.completeDynamicIndex(dataTrans); return dataTrans; } @@ -887,9 +901,18 @@ class Layer { * @param data data优化值 */ completeDynamicIndex(data: DataTrans[][]) { + for (let i = 0; i < this.dynamicIndex.length; i++) { + if (data[i] && this.dynamicIndex[i] > data[i].length - 1) { + this.dynamicIndex[i] = data[i].length - 1; + } + if (this.dynamicIndex[i] < 0) { + this.dynamicIndex[i] = 0; + } + } for (let i = this.dynamicIndex.length; i < data.length; i++) { this.dynamicIndex[i] = 0; } + this.dynamicIndex = this.dynamicIndex.slice(0, data.length); } /** diff --git a/tests/q-select/index.spec.js b/tests/q-select/index.spec.js index 9add0ad..89d8f40 100644 --- a/tests/q-select/index.spec.js +++ b/tests/q-select/index.spec.js @@ -459,6 +459,19 @@ describe('instance', () => { }); expect(s.setIndex()).rejects.toBe(undefined); }); + + it('wrong index', () => { + const s = new QSelect({ + data: [ + { value: 1, children: [1, 2, 3] }, + { value: 2, children: [4, 5, 6] } + ] + }); + s.setIndex([-1, -1]); + expect(s.getIndex()).toStrictEqual([0, 0]); + s.setIndex([10, 10]); + expect(s.getIndex()).toStrictEqual([1, 2]); + }); }); describe('setValue', () => { @@ -549,33 +562,130 @@ describe('instance', () => { }); }); - it('show and close', done => { + it('show and close', () => { const s = new QSelect({ data: [[1, 2, 3]] }); s.show(); - expect(document.querySelector('.q-select-bk').style.display).toBe('block'); setTimeout(() => { s.close(); - expect(document.querySelector('.q-select-bk').style.display).toBe('none'); - done(); }, 300); }); - it('setLoading and cancelLoading ', done => { + it('setLoading and cancelLoading ', () => { const s = new QSelect({ data: [[1, 2, 3]] }); s.setLoading(); - expect( - document.querySelector(`.q-select-loading--${s.id}`).style.display - ).toBe('flex'); - setTimeout(() => { - s.cancelLoading(); - expect( - document.querySelector(`.q-select-loading--${s.id}`).style.display - ).toBe('none'); - done(); - }, 300); + s.cancelLoading(); + }); + + describe('scrollTo', () => { + it('notGangedData', () => { + const s = new QSelect({ + data: [[1, 2, 3]] + }); + s.scrollTo(0, 2); + expect(s.getIndex()).toStrictEqual([2]); + expect(s.getKey()).toStrictEqual([3]); + expect(s.getValue()).toStrictEqual([3]); + expect(s.getData()).toStrictEqual([ + [3], + [3], + [{ index: 2, key: 3, value: 3 }] + ]); + }); + + it('gangedData', () => { + const s = new QSelect({ + data: [ + { value: 1, children: [1, 2, 3] }, + { value: 2, children: [4, 5, 6] } + ] + }); + s.scrollTo(1, 10); + expect(s.getIndex()).toStrictEqual([0, 2]); + expect(s.getKey()).toStrictEqual([1, 3]); + expect(s.getValue()).toStrictEqual([1, 3]); + expect(s.getData()).toStrictEqual([ + [1, 3], + [1, 3], + [{ index: 0, key: 1, value: 1 }, { index: 2, key: 3, value: 3 }] + ]); + }); + + it('no params', () => { + const s = new QSelect({ + data: [ + { value: 1, children: [1, 2, 3] }, + { value: 2, children: [4, 5, 6] } + ] + }); + s.scrollTo(); + expect(s.getIndex()).toStrictEqual([0, 0]); + }); + }); + + describe('setColumnData', () => { + it('one Data', () => { + const s = new QSelect({ + data: [[1, 2, 3]] + }); + s.setColumnData(1, [4, 5, 6]); + + expect(s.getIndex()).toStrictEqual([0, 0]); + expect(s.getKey()).toStrictEqual([1, 4]); + expect(s.getValue()).toStrictEqual([1, 4]); + expect(s.getData()).toStrictEqual([ + [1, 4], + [1, 4], + [{ index: 0, key: 1, value: 1 }, { index: 0, key: 4, value: 4 }] + ]); + }); + + it('double Data', () => { + const s = new QSelect({ + data: [[1, 2, 3]] + }); + s.setColumnData([1, 2], [[4, 5, 6], [7, 8, 9]]); + + expect(s.getIndex()).toStrictEqual([0, 0, 0]); + expect(s.getKey()).toStrictEqual([1, 4, 7]); + expect(s.getValue()).toStrictEqual([1, 4, 7]); + expect(s.getData()).toStrictEqual([ + [1, 4, 7], + [1, 4, 7], + [ + { index: 0, key: 1, value: 1 }, + { index: 0, key: 4, value: 4 }, + { index: 0, key: 7, value: 7 } + ] + ]); + }); + + it('wrong params', () => { + const s = new QSelect({ + data: [[1, 2, 3]] + }); + expect(s.setColumnData()).rejects.toBe(''); + }); + + it('wrong data', () => { + const s = new QSelect({ + data: [[1, 2, 3]] + }); + s.setColumnData(1, [{ value: 1, children: [4, 5, 6] }]); + expect(s.getIndex()).toStrictEqual([0]); + }); + }); + + describe('destroy', () => { + it('destroy', () => { + const s = new QSelect({ + data: [[1, 2, 3]] + }); + s.destroy(); + expect(document.querySelector(`.q-select--${s.id}`)).toBeNull(); + }); }); });