import { Prop, Vue } from 'vue-property-decorator'; import { CreateElement, VNode } from 'vue'; import { indexOf, mergeDeepRight } from 'ramda'; import { IDesignContext, IMaterialItem } from '../../interface'; import sortable from 'sortablejs'; import './design-material-panel-base.less'; /** * 拖拽面板 * * @export * @class DesignMaterialPanelBase * @extends {Vue} */ export class DesignMaterialPanelBase extends Vue { /** * 设计上下文 * * @type {IDesignContext} * @memberof DesignMaterialPanelBase */ @Prop() ctx!: IDesignContext; /** * 容器面板DOM实例 * * @type {HTMLDivElement} * @memberof DesignMaterialPanelBase */ el!: HTMLDivElement; /** * 数据 * * @type {IMaterialItem[]} * @memberof DesignMaterialPanelBase */ list: IMaterialItem[] = []; /** * 过滤参数 * * @memberof DesignMaterialPanelBase */ @Prop() searchValue = ''; /** * 拖拽参数 * * @private * @type {sortable.Options} * @memberof DesignMaterialPanelBase */ public options: sortable.Options = { group: { name: this.ctx.tag, pull: 'clone', put: false, }, sort: false, }; private created(): void { this.componentCreated(); } /** * 组件创建完毕 * * @memberof DesignMaterialPanelBase */ componentCreated(): void {} private mounted(): void { this.el = this.$refs.panel as any; this.options = mergeDeepRight(this.options, this.generateOption()) as any; this.componentMounted(); } /** * 组件加载完毕 * * @memberof DesignMaterialPanelBase */ componentMounted(): void {} private destroyed(): void { this.componentDestroyed(); } /** * 组件销毁 * * @memberof DesignMaterialPanelBase */ componentDestroyed(): void {} /** * 生成拖拽面板参数 * * @return {*} {sortable.Options} * @memberof DesignMaterialPanelBase */ generateOption(): sortable.Options { return {}; } /** * 容器样式名称 * * @return {*} * @memberof DesignMaterialPanelBase */ getClass() { return { 'ibz-design-material-panel': true, 'ant-row': true, }; } /** * 容器样式 * * @return {*} * @memberof DesignMaterialPanelBase */ getStyle() { return {}; } getFilterList(list?: any[]): IMaterialItem[] { const items = list || this.list; if(!this.searchValue && Object.is(this.searchValue, '')) { return items; } const regExp = this.searchValue .trimStart() .trimEnd() .toLowerCase(); return items.filter((item: any) => { const text = item.text.toLowerCase(); if (text.indexOf(regExp) >= 0) { return true; } else { return false; } }); } /** * 监听素材项双击 * * @author zhanghengfeng * @date 2023-05-18 14:05:54 * @param {MouseEvent} e * @param {IMaterialItem} _item */ onItemDblClick(e: MouseEvent, _item: IMaterialItem): void { e.stopPropagation(); } /** * 绘制内容 * * @param {CreateElement} _h * @return {*} {VNode[]} * @memberof DesignMaterialPanelBase */ renderContentList(_h: CreateElement): VNode | VNode[] { const isSearch = this.searchValue && !Object.is(this.searchValue, ''); const regExp = this.searchValue .trimStart() .trimEnd() .toLowerCase(); const items: any[] = isSearch ? this.getFilterList() : this.list; return items.length > 0 ? ( items.map((item: IMaterialItem, index: number) => { let iconVNode = null; if (item.icon) { if (item.icon.endsWith('.svg')) { iconVNode = ; } else if (item.icon.endsWith('')) { const svg = URL.createObjectURL(new Blob([item.icon], {type:"image/svg+xml;charset=utf-8"})); iconVNode = ; } else { iconVNode = ; } } else if (item.iconcls) { iconVNode =
; } return (
this.onItemDblClick(e, item)}> {iconVNode}
{item.text}
); }) ) : (
暂无数据
); } render(h: CreateElement) { return ( item.data)} > {this.renderContentList(h)} ); } }