adui
Version:
<div> <img src="https://wxa.wxs.qq.com/mpweb/delivery/legacy/wxadtouch/upload/t1/od834zef_52939fc6.png" style="margin:40px 0 0 -8px; background-color: #fcfcfc; box-shadow: none;" /> </div>
144 lines (125 loc) • 3.81 kB
text/typescript
import React from "react"
interface IBaseObject {
[key: string]: any
}
export default class ColumnManager {
public cached: any = {}
public columns: IBaseObject[]
constructor(elements: IBaseObject[]) {
this.columns = this.normalize(elements)
}
public isAnyColumnsFixed = () =>
this.cache("isAnyColumnsFixed", () =>
this.columns.some((column: IBaseObject) => !!column.fixed)
)
public isAnyColumnsLeftFixed = () =>
this.cache("isAnyColumnsLeftFixed", () =>
this.columns.some(
(column: IBaseObject) =>
column.fixed === "left" || column.fixed === true
)
)
public isAnyColumnsRightFixed = () =>
this.cache("isAnyColumnsRightFixed", () =>
this.columns.some((column: IBaseObject) => column.fixed === "right")
)
public getLeftColumns = () =>
this.cache("getLeftColumns", () =>
this.columns.filter(
(column: IBaseObject) =>
column.fixed === "left" || column.fixed === true
)
)
public getMainColumns = () =>
this.cache("getMainColumns", () =>
this.columns.filter((column: IBaseObject) => !column.fixed)
)
public getRightColumns = () =>
this.cache("getRightColumns", () =>
this.columns.filter((column: IBaseObject) => column.fixed === "right")
)
public getColumns = () => [
...this.getLeftColumns(),
...this.getMainColumns(),
...this.getRightColumns(),
]
public getLeftColumnsWidth = () =>
this.cache("getLeftColumnsWidth", () =>
this.getColumnsWidthBase(this.getLeftColumns())
)
public getRightColumnsWidth = () =>
this.cache("getRightColumnsWidth", () =>
this.getColumnsWidthBase(this.getRightColumns())
)
public getGroupColumnsDepth = () =>
this.cache("getGroupColumnsDepth", () => {
let depth = 1
const children = this.columns.filter(
(column: IBaseObject) => !!column.children
)
if (children.length) {
depth = 2
children.forEach((child) => {
const grands = child.children.some(
(grand: IBaseObject) => !!grand.children
)
if (grands) {
depth = 3
}
})
}
return depth
})
public getColumnsWidthBase = (columns: IBaseObject[]) => {
let sum = "calc("
columns.forEach((column: IBaseObject) => {
const { width } = column
if (typeof width === "number") {
sum += `${width}px + `
} else {
sum += `${width} + `
}
})
return `${sum.slice(0, -2)})`
}
public normalize = (elementsParam: IBaseObject[]) => {
const columns: IBaseObject[] = []
const elements = Array.isArray(elementsParam)
? elementsParam
: [elementsParam]
if (elements.find((o) => React.isValidElement(o))) {
React.Children.forEach(elements, (element) => {
/**
* Column 名存实亡,实际上是从 children 获取每一列的 props
* 因此需要判断 children isValidElement,再从 children 遍历 prop
*/
if (!React.isValidElement(element)) {
return
}
const column: any = { ...(element.props as {}) }
let { children } = column
if (children) {
children = Array.isArray(children) ? children : [children]
column.children = this.normalize(children)
}
columns.push(column)
})
} else {
elements.forEach((o) => {
columns.push(o)
})
}
return columns
}
public reset = (elements: IBaseObject[]) => {
this.columns = this.normalize(elements)
this.cached = {}
}
public cache = (name: string, fn: () => void) => {
if (name in this.cached) {
return this.cached[name]
}
this.cached[name] = fn()
return this.cached[name]
}
}