From 60632013f38669ff5ff140fef67d73b910c1a350 Mon Sep 17 00:00:00 2001 From: luojiahao Date: Tue, 11 Oct 2022 11:27:08 +0800 Subject: [PATCH] =?UTF-8?q?TASK:=20#115114=20-=20=E6=B7=BB=E5=8A=A0?= =?UTF-8?q?=E5=88=86=E9=A1=B5=E7=AE=A1=E7=90=86=E5=8A=9F=E8=83=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- CHANGELOG.md | 1 + src/components/grid-container/container.ts | 37 +++++++- .../grid-container/gaia-container-child.ts | 2 +- .../grid-container/gaia-container-page.ts | 87 ++++++++++++++----- .../panels/container/homescreen-container.ts | 2 + 5 files changed, 102 insertions(+), 27 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 4bb1205..fcaabc5 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -27,3 +27,4 @@ - add gauss blur component - change container's gesture function - fix bugs of multiple fingers in container +- add pagination controller of container diff --git a/src/components/grid-container/container.ts b/src/components/grid-container/container.ts index f210539..8551376 100644 --- a/src/components/grid-container/container.ts +++ b/src/components/grid-container/container.ts @@ -325,6 +325,7 @@ class GaiaContainer extends StarBaseElement { set status(value) { if (value !== this._status) { + this._status = value this.dispatchEvent( new CustomEvent('statuschange', { detail: { @@ -335,7 +336,6 @@ class GaiaContainer extends StarBaseElement { composed: true, }) ) - this._status = value } } @@ -371,7 +371,7 @@ class GaiaContainer extends StarBaseElement { } // 同时触发划动时,不同触发原因的优先级顺序,越后越优先 - typeIndex = ['reset', 'swipe', 'mouseup', 'touchend', 'holdend', 'panend'] + typeIndex = ['', 'swipe', 'mouseup', 'touchend', 'holdend', 'panend', 'reset'] // 划动计时器 timer: Function | undefined = undefined // 触发划动的原因类型 @@ -493,11 +493,13 @@ class GaiaContainer extends StarBaseElement { this.status |= STATUS.SORT // @ts-ignore this.gestureDetector.setOption('holdThreshold', 100) + this.firstUpdated().then(this.addTailPage) } else { this._dnd.delay = DEFAULT_DND_TIMEOUT this.status &= ~STATUS.SORT // @ts-ignore this.gestureDetector.setOption('holdThreshold', DEFAULT_DND_TIMEOUT) + this.removeTailPage() } this._sortMode = value } @@ -949,8 +951,8 @@ class GaiaContainer extends StarBaseElement { throw 'removeChild called on unknown child' } - addPage() { - const {page, shadowPage} = this.pages.addPage() + addPage(pages?: {page: HTMLElement; shadowPage: HTMLElement}) { + const {page, shadowPage} = pages ?? this.pages.addPage() HTMLElement.prototype.appendChild.call(this, page) HTMLElement.prototype.appendChild.call(this, shadowPage) @@ -963,6 +965,24 @@ class GaiaContainer extends StarBaseElement { return page } + addTailPage() { + if (this._status & STATUS.DRAG || this._status & STATUS.SORT) { + // 仅仅在拖动状态和编辑状态时,允许添加空白尾页 + if (this.pages[this.pagination] == this.pages._tail) { + // 当当前页为尾页时,再行添加尾页前,需要去掉当前页面的尾页标记 + this.pages._tail = undefined + } + + this.pages.addTail() + } + } + + removeTailPage() { + if (!(this._status & STATUS.SORT) && !(this._status & STATUS.DRAG)) { + this.pages.removeTail() + } + } + /** * Reorders the given element to appear before referenceElement. */ @@ -1220,6 +1240,9 @@ class GaiaContainer extends StarBaseElement { gridId, this._dnd.child ).recommended + if (!this.childCoordinate[this.pagination]) { + this.childCoordinate[this.pagination] = {} + } children = this.childCoordinate[this.pagination] child = children[gridId]! element = child?.element ?? this.pages[this.pagination] @@ -1276,6 +1299,11 @@ class GaiaContainer extends StarBaseElement { this._dnd.lastDropChild = null } + // 进行拖拽的手指未松开之前,即使其他手指松开也不会添加空白尾页 + if (!(this._status & STATUS.DRAG)) { + this.addTailPage() + } + this.removeTailPage() this._dnd.child = null this._dnd.isSpanning = false this.status &= ~STATUS.DRAG @@ -1285,6 +1313,7 @@ class GaiaContainer extends StarBaseElement { startDrag() { this.status |= STATUS.DRAG + this.addTailPage() const child = this._dnd.child this._staticElements = [child.element] this._dnd.start.translateX = child.master.offsetLeft diff --git a/src/components/grid-container/gaia-container-child.ts b/src/components/grid-container/gaia-container-child.ts index 5a424b7..6cd9030 100644 --- a/src/components/grid-container/gaia-container-child.ts +++ b/src/components/grid-container/gaia-container-child.ts @@ -70,7 +70,7 @@ export default class GaiaContainerChild { this.priority = row * column this.manager = manager this._isStatic = false - this.anchorCoordinate = anchorCoordinate ?? defaultCoordinate // 两种屏幕方向的锚固坐标 + this.anchorCoordinate = anchorCoordinate ?? {...defaultCoordinate} // 两种屏幕方向的锚固坐标 this.markDirty() } diff --git a/src/components/grid-container/gaia-container-page.ts b/src/components/grid-container/gaia-container-page.ts index c53abaf..5e14fae 100644 --- a/src/components/grid-container/gaia-container-page.ts +++ b/src/components/grid-container/gaia-container-page.ts @@ -1,19 +1,32 @@ import GaiaContainer from './container' +import {STATUS} from './contianer-interface' class GaiaContainerPage { _pages: HTMLElement[] = [] // 存储所有添加进 gaia-container 的页面 // 等待被移除的页面,仅在编辑、拖拽时出现,若结束前两种状态时仍然没有子节点,则删除 - _suspending: HTMLElement | null = null + _suspending: HTMLElement[] = [] _manager: GaiaContainer _shadowPagesMap: WeakMap = new WeakMap() + + _tail: HTMLElement | undefined + _shadowTail: HTMLElement | undefined observerCallback: MutationCallback constructor(manager: GaiaContainer) { this._manager = manager this._manager.addEventListener('statuschange', () => { // gaia-container 退出拖拽模式,且有待删除页面 - if (!(this._manager._status & 2) && this._suspending) { - this.deletePage(this._suspending) + if ( + !(this._manager._status & STATUS.DRAG) && + !(this._manager._status & STATUS.SORT) && + this._suspending.length + ) { + while (this._suspending.length) { + const page = this._suspending.shift() + this.deletePage(page) + } + this.removeTail() + this._manager.turnPre('reset') } }) @@ -26,7 +39,6 @@ class GaiaContainerPage { const page = mutation.target as HTMLElement const container = page.parentElement as any - page.classList.add('removed') const callback = () => { if (!container || !page.dataset.page) return if ( @@ -37,7 +49,8 @@ class GaiaContainerPage { } if (this.editMode) { - this._suspending = page + // 处于编辑状态时,空白页不被删除 + this._suspending.push(page) } else { this.deletePage(page) } @@ -90,8 +103,26 @@ class GaiaContainerPage { } } + addTail = () => { + if (!this._tail || !this._shadowTail || this._tail.children.length) { + const pages = this.addPage() + this._tail = pages.page + this._shadowTail = pages.shadowPage + this._manager.addPage({page: this._tail, shadowPage: this._shadowTail}) + } + } + + removeTail = () => { + if (!this._tail) return + this.deletePage(this._tail) + this._tail = undefined + this._shadowTail = undefined + } + get editMode() { - return this._manager._status & 2 || this._manager._status & 8 + return ( + this._manager._status & STATUS.DRAG || this._manager._status & STATUS.SORT + ) } observe = (page: HTMLElement) => { @@ -102,43 +133,55 @@ class GaiaContainerPage { }) } - deletePage = (page: HTMLElement) => { - if (page.children.length) return + deletePage = (page?: HTMLElement) => { + if (!page || page.children.length) return let index = this._pages.indexOf(page) if (this.editMode && index == this.length - 1) { // 处于拖拽状态时,尾页不被删除 - this._suspending = page + this._suspending.push(page) return } if (this._pages.length < 2) { // 页面数量少于1 return } - delete this._pages[index] - this._manager.dispatchEvent( - new CustomEvent('page-change', { - detail: { - deleteIndex: index, - }, - composed: true, - }) - ) + if (index > -1) { page?.remove?.() + this._shadowPagesMap.get(page)?.remove?.() + delete this._pages[index] let flag = false let coordinates: GaiaContainer['childCoordinate'] = [] + // @ts-ignore this._pages = this._pages.filter((page, i) => { - if (flag) { - ;(page.dataset.page as any) = --i - page.style.setProperty('--pagination', String(i)) - } if (i == index) flag = true coordinates[i] = this._manager.childCoordinate[i - +flag] return i !== index }) this._manager.childCoordinate = coordinates + this.sortPagination() + + this._manager.dispatchEvent( + new CustomEvent('page-change', { + detail: { + deleteIndex: index, + }, + composed: true, + }) + ) } + this._manager.synchronise() + } + + sortPagination() { + this._pages.forEach((page, i) => { + page.dataset.page = String(i) + page.style.setProperty('--pagination', String(i)) + this._shadowPagesMap + .get(page) + ?.style.setProperty('--pagination', String(i)) + }) } get length() { diff --git a/src/test/panels/container/homescreen-container.ts b/src/test/panels/container/homescreen-container.ts index c1e273d..5e45ff4 100644 --- a/src/test/panels/container/homescreen-container.ts +++ b/src/test/panels/container/homescreen-container.ts @@ -75,6 +75,7 @@ export class PanelContainer extends LitElement { // 存储全局变量 ;(window as any).dock = this.dock ;(window as any).container = this.container + ;(window as any).pageIndicator = this.pageIndicator ;(window as any).home = this // container 相关事件 @@ -128,6 +129,7 @@ export class PanelContainer extends LitElement { }) } else { this.addAppIcon(1, 1) + this.container.changeLayout() let promise = new Promise((res) => { res(undefined) })