Merge branch 'next' into feat-popup-menu
This commit is contained in:
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@layui/layui-vue",
|
||||
"version": "1.2.3",
|
||||
"version": "1.2.5",
|
||||
"author": "就眠儀式",
|
||||
"license": "MIT",
|
||||
"description": "a component library for Vue 3 base on layui-vue",
|
||||
|
||||
@@ -18,12 +18,12 @@ export interface LayAiffxProps {
|
||||
}
|
||||
const props = withDefaults(defineProps<LayAiffxProps>(), {
|
||||
offset: 0,
|
||||
position: 'top',
|
||||
position: "top",
|
||||
target: () => {
|
||||
return document.body;
|
||||
},
|
||||
});
|
||||
const emit = defineEmits(['scroll'])
|
||||
const emit = defineEmits(["scroll"]);
|
||||
const outWindow = ref(false);
|
||||
const dom = ref();
|
||||
|
||||
@@ -43,7 +43,7 @@ const getStyle = computed(() => {
|
||||
bottom: "unset",
|
||||
left: orginOffsetLeft - marginLeft + "px",
|
||||
};
|
||||
if (props.position === 'top') {
|
||||
if (props.position === "top") {
|
||||
style.top = fixedOffset - marginTop + "px";
|
||||
} else {
|
||||
style.bottom = fixedOffset - marginBottom + "px";
|
||||
@@ -56,7 +56,7 @@ const checkInWindow = () => {
|
||||
if (dom.value) {
|
||||
let offsetTop = dom.value.offsetTop;
|
||||
let scrollTop = props.target?.scrollTop;
|
||||
if (props.position === 'top') {
|
||||
if (props.position === "top") {
|
||||
//top检查 当前元素与容器顶部距离-减去滚动条的高度+容器offsetTop
|
||||
let result = offsetTop - scrollTop + props.target.offsetTop;
|
||||
if (result < fixedOffset) {
|
||||
@@ -82,15 +82,15 @@ const checkInWindow = () => {
|
||||
}
|
||||
} else {
|
||||
if (result < fixedOffset) {
|
||||
changeScrollTop = scrollTop - result + props.offset
|
||||
changeScrollTop = scrollTop - result + props.offset;
|
||||
outWindow.value = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
emit('scroll', {
|
||||
emit("scroll", {
|
||||
targetScroll: scrollTop,
|
||||
affixed: outWindow.value,
|
||||
offset: !outWindow.value ? 0 : Math.abs(scrollTop - changeScrollTop)
|
||||
offset: !outWindow.value ? 0 : Math.abs(scrollTop - changeScrollTop),
|
||||
});
|
||||
}
|
||||
};
|
||||
@@ -106,14 +106,14 @@ const getDomStyle = (dom: any, attr: string) => {
|
||||
|
||||
onMounted(() => {
|
||||
nextTick(() => {
|
||||
orginOffsetTop = dom.value.offsetTop - props.target.offsetTop
|
||||
orginOffsetLeft = dom.value.getBoundingClientRect().left
|
||||
marginLeft = parseFloat(getDomStyle(dom.value, 'marginLeft'))
|
||||
marginTop = parseFloat(getDomStyle(dom.value, 'marginTop'))
|
||||
marginBottom = parseFloat(getDomStyle(dom.value, 'marginBottom'))
|
||||
fixedOffset = props.offset + props.target.offsetTop
|
||||
if (props.position === 'bottom') {
|
||||
fixedOffset = props.offset
|
||||
orginOffsetTop = dom.value.offsetTop - props.target.offsetTop;
|
||||
orginOffsetLeft = dom.value.getBoundingClientRect().left;
|
||||
marginLeft = parseFloat(getDomStyle(dom.value, "marginLeft"));
|
||||
marginTop = parseFloat(getDomStyle(dom.value, "marginTop"));
|
||||
marginBottom = parseFloat(getDomStyle(dom.value, "marginBottom"));
|
||||
fixedOffset = props.offset + props.target.offsetTop;
|
||||
if (props.position === "bottom") {
|
||||
fixedOffset = props.offset;
|
||||
}
|
||||
props.target.addEventListener("scroll", checkInWindow, true);
|
||||
checkInWindow();
|
||||
|
||||
@@ -174,7 +174,7 @@ function findData(orginData: any, level: number) {
|
||||
const dataContainer = ref<any>([]);
|
||||
const selectBar = (item: any, selectIndex: number, parentIndex: number) => {
|
||||
treeData.value[parentIndex].selectIndex = selectIndex;
|
||||
if (item.children) {
|
||||
if (item.children && item.children.length > 0) {
|
||||
treeData.value[parentIndex + 1].selectIndex = null;
|
||||
treeData.value[parentIndex + 1].data = findData(item.children, 1);
|
||||
}
|
||||
|
||||
@@ -72,11 +72,9 @@ watch([red, green, blue], (newValue) => {
|
||||
rgba2hex(red.value, green.value, blue.value, alpha.value)
|
||||
);
|
||||
let { h, s, v } = rgb2hsv(red.value, green.value, blue.value);
|
||||
hue.value = h;
|
||||
saturation.value = s;
|
||||
value.value = v;
|
||||
pointStyle.value = `top: ${100 - v * 100}%;left: ${s * 100}%;`;
|
||||
hueSliderStyle.value = `left: ${(hue.value / 360) * 100}%;`;
|
||||
});
|
||||
|
||||
watch(alpha, () => {
|
||||
|
||||
@@ -1,10 +1,12 @@
|
||||
<template>
|
||||
<div>
|
||||
<lay-dropdown ref="dropdownRef" :disabled="props.disabled">
|
||||
<lay-input :name="name" :value="dateValue || modelValue" readonly>
|
||||
<template #prefix>
|
||||
<lay-icon type="layui-icon-date"></lay-icon>
|
||||
</template>
|
||||
<lay-input
|
||||
readonly
|
||||
:name="name"
|
||||
:value="dateValue || modelValue"
|
||||
prefix-icon="layui-icon-date"
|
||||
>
|
||||
</lay-input>
|
||||
<template #content>
|
||||
<!-- 日期选择 -->
|
||||
|
||||
@@ -34,6 +34,7 @@
|
||||
|
||||
.layui-dropdown .layui-menu li {
|
||||
position: relative;
|
||||
display: flex;
|
||||
line-height: 26px;
|
||||
color: rgba(0, 0, 0, 0.8);
|
||||
font-size: 14px;
|
||||
@@ -46,7 +47,19 @@
|
||||
}
|
||||
|
||||
.layui-dropdown .layui-menu-body-title {
|
||||
position: relative;
|
||||
white-space: nowrap;
|
||||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
}
|
||||
|
||||
.layui-dropdown-menu-prefix{
|
||||
margin-right: 8px;
|
||||
}
|
||||
.layui-dropdown-menu-suffix{
|
||||
margin-left: 15px;
|
||||
}
|
||||
|
||||
.layui-dropdown .layui-line-horizontal{
|
||||
margin: 0px;
|
||||
border-color: #EEEEEE;
|
||||
}
|
||||
@@ -387,11 +387,15 @@ const handleClick = () => {
|
||||
}
|
||||
};
|
||||
|
||||
const handleContextMenuClick = () => {
|
||||
const handleContextMenuClick = (e: Event) => {
|
||||
if (props.disabled || (openState.value && !props.clickToClose)) {
|
||||
return;
|
||||
}
|
||||
if (triggerMethods.value.includes("contextMenu")) {
|
||||
e.preventDefault();
|
||||
if (props.alignPoint) {
|
||||
hide();
|
||||
}
|
||||
toggle();
|
||||
}
|
||||
};
|
||||
@@ -511,7 +515,7 @@ defineExpose({ open, hide, toggle });
|
||||
@focusout="handleFocusout()"
|
||||
:class="{ 'layui-dropdown-up': openState }"
|
||||
>
|
||||
<div @click="handleClick()" @contextmenu.prevent="handleContextMenuClick()">
|
||||
<div @click="handleClick()" @contextmenu="handleContextMenuClick">
|
||||
<slot></slot>
|
||||
</div>
|
||||
<dl
|
||||
|
||||
@@ -15,9 +15,18 @@ const handleClick = () => {
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<li>
|
||||
<div class="layui-menu-body-title" @click="handleClick">
|
||||
<slot></slot>
|
||||
</div>
|
||||
<li
|
||||
@click="handleClick"
|
||||
:style="$slots.suffix ? `justify-content: space-between;` : ''"
|
||||
>
|
||||
<span class="layui-menu-body-title">
|
||||
<span v-if="$slots.prefix" class="layui-dropdown-menu-prefix">
|
||||
<slot name="prefix" />
|
||||
</span>
|
||||
<slot />
|
||||
</span>
|
||||
<span v-if="$slots.suffix" class="layui-dropdown-menu-suffix">
|
||||
<slot name="suffix" />
|
||||
</span>
|
||||
</li>
|
||||
</template>
|
||||
|
||||
5
package/component/src/component/dropdownSubMenu/index.ts
Normal file
5
package/component/src/component/dropdownSubMenu/index.ts
Normal file
@@ -0,0 +1,5 @@
|
||||
import { withInstall, WithInstallType } from "../../utils";
|
||||
import Component from "./index.vue";
|
||||
|
||||
const component: WithInstallType<typeof Component> = withInstall(Component);
|
||||
export default component;
|
||||
58
package/component/src/component/dropdownSubMenu/index.vue
Normal file
58
package/component/src/component/dropdownSubMenu/index.vue
Normal file
@@ -0,0 +1,58 @@
|
||||
<script lang="ts">
|
||||
export default {
|
||||
name: "LayDropdownSubMenu",
|
||||
};
|
||||
</script>
|
||||
|
||||
<script setup lang="ts">
|
||||
import { inject, Ref } from "vue";
|
||||
import LayDropdown from "../dropdown/index.vue";
|
||||
import LayDropdownMenu from "../dropdownMenu/index.vue";
|
||||
import LayDropdownMenuItem from "../dropdownMenuItem/index.vue";
|
||||
import { LayIcon } from "@layui/icons-vue";
|
||||
import { DropdownPlacement } from "../dropdown/interface";
|
||||
|
||||
export type DropdownTrigger = "click" | "hover" | "focus" | "contextMenu";
|
||||
|
||||
export interface LayDropdownProps {
|
||||
trigger?: DropdownTrigger | DropdownTrigger[];
|
||||
placement?: DropdownPlacement;
|
||||
disabled?: boolean;
|
||||
contentOffset?: number;
|
||||
}
|
||||
|
||||
const props = withDefaults(defineProps<LayDropdownProps>(), {
|
||||
trigger: "hover",
|
||||
disabled: false,
|
||||
placement: "right-top",
|
||||
contentOffset: 2,
|
||||
});
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<lay-dropdown
|
||||
:trigger="trigger"
|
||||
:placement="placement"
|
||||
:auto-fit-min-width="false"
|
||||
:contentOffset="contentOffset"
|
||||
>
|
||||
<lay-dropdown-menu-item>
|
||||
<template v-if="$slots.prefix" #prefix>
|
||||
<slot name="prefix" />
|
||||
</template>
|
||||
<template v-if="$slots.default" #default>
|
||||
<slot />
|
||||
</template>
|
||||
<template #suffix>
|
||||
<slot name="suffix">
|
||||
<lay-icon type="layui-icon-right" size="14px"></lay-icon>
|
||||
</slot>
|
||||
</template>
|
||||
</lay-dropdown-menu-item>
|
||||
<template #content>
|
||||
<lay-dropdown-menu>
|
||||
<slot name="content" />
|
||||
</lay-dropdown-menu>
|
||||
</template>
|
||||
</lay-dropdown>
|
||||
</template>
|
||||
@@ -25,8 +25,9 @@
|
||||
border-radius: var(--input-border-radius);
|
||||
}
|
||||
|
||||
.layui-input-wrapper:hover,
|
||||
.layui-input-wrapper:focus-within {
|
||||
border-color: var(--global-checked-color);
|
||||
border-color: #d2d2d2 !important;
|
||||
}
|
||||
|
||||
.layui-input-prefix {
|
||||
@@ -55,14 +56,6 @@
|
||||
color: rgba(0, 0, 0, 0.45);
|
||||
}
|
||||
|
||||
.layui-input:hover {
|
||||
border-color: #eee !important;
|
||||
}
|
||||
|
||||
.layui-input:focus {
|
||||
border-color: #d2d2d2 !important;
|
||||
}
|
||||
|
||||
.layui-input::-webkit-input-placeholder {
|
||||
line-height: 1.3;
|
||||
}
|
||||
|
||||
@@ -20,6 +20,7 @@ import {
|
||||
shallowRef,
|
||||
} from "vue";
|
||||
import LayBadge from "../badge/index.vue";
|
||||
import LayInput from "../input/index.vue";
|
||||
import LayScroll from "../scroll/index.vue";
|
||||
import { onClickOutside } from "@vueuse/core";
|
||||
import { SelectItem } from "../../types";
|
||||
|
||||
28
package/component/src/component/tab/RenderTitle.vue
Normal file
28
package/component/src/component/tab/RenderTitle.vue
Normal file
@@ -0,0 +1,28 @@
|
||||
<script lang="ts">
|
||||
import { h, PropType, defineComponent } from "vue";
|
||||
import { TabData } from "./interface";
|
||||
|
||||
export default defineComponent({
|
||||
name: "RenderTitle",
|
||||
props: {
|
||||
tag: {
|
||||
type: String,
|
||||
required: false,
|
||||
default: "span",
|
||||
},
|
||||
tabItemData: {
|
||||
type: Object as PropType<TabData>,
|
||||
required: false,
|
||||
},
|
||||
},
|
||||
setup(props) {
|
||||
return props.tabItemData?.slots?.title
|
||||
? () =>
|
||||
h(
|
||||
props.tag,
|
||||
props.tabItemData?.slots?.title && props.tabItemData?.slots.title()
|
||||
)
|
||||
: () => props.tabItemData?.title;
|
||||
},
|
||||
});
|
||||
</script>
|
||||
@@ -8,6 +8,7 @@ export default {
|
||||
import "./index.less";
|
||||
import { LayIcon } from "@layui/icons-vue";
|
||||
import tabItem from "../tabItem/index.vue";
|
||||
import RenderTitle from "./renderTitle.vue";
|
||||
import {
|
||||
Component,
|
||||
computed,
|
||||
@@ -21,8 +22,10 @@ import {
|
||||
onMounted,
|
||||
nextTick,
|
||||
CSSProperties,
|
||||
reactive,
|
||||
} from "vue";
|
||||
import { useResizeObserver } from "@vueuse/core";
|
||||
import { TabData, TabInjectKey } from "./interface";
|
||||
|
||||
export type tabPositionType = "top" | "bottom" | "left" | "right";
|
||||
|
||||
@@ -40,6 +43,7 @@ const slot = useSlots();
|
||||
const slots = slot.default && slot.default();
|
||||
const childrens: Ref<VNode[]> = ref([]);
|
||||
const slotsChange = ref(true);
|
||||
const tabMap = reactive(new Map<number, TabData>());
|
||||
|
||||
const setItemInstanceBySlot = function (nodeList: VNode[]) {
|
||||
nodeList?.map((item) => {
|
||||
@@ -67,6 +71,32 @@ const active = computed({
|
||||
},
|
||||
});
|
||||
|
||||
const tabItems = computed(() => {
|
||||
const tabData: TabData[] = [];
|
||||
childrens.value.forEach((item) => {
|
||||
const tab = tabMap.get(item.props?.id);
|
||||
if (tab) tabData.push(tab);
|
||||
});
|
||||
return tabData;
|
||||
});
|
||||
|
||||
const addItem = (id: number, data: any) => {
|
||||
tabMap.set(id, data);
|
||||
};
|
||||
|
||||
const removeItem = (id: number) => {
|
||||
tabMap.delete(id);
|
||||
};
|
||||
|
||||
provide(
|
||||
TabInjectKey,
|
||||
reactive({
|
||||
active: active,
|
||||
addItem,
|
||||
removeItem,
|
||||
})
|
||||
);
|
||||
|
||||
const change = function (id: any) {
|
||||
if (props.beforeLeave && props.beforeLeave(id) === false) {
|
||||
return;
|
||||
@@ -294,16 +324,16 @@ provide("slotsChange", slotsChange);
|
||||
:style="tabBarStyle"
|
||||
></div>
|
||||
<li
|
||||
v-for="(children, index) in childrens"
|
||||
:key="children.props?.id"
|
||||
:class="[children.props?.id === active ? 'layui-this' : '']"
|
||||
@click.stop="change(children.props?.id)"
|
||||
v-for="(children, index) in tabItems"
|
||||
:key="children.id"
|
||||
:class="[children.id === active ? 'layui-this' : '']"
|
||||
@click.stop="change(children.id)"
|
||||
>
|
||||
{{ children.props?.title }}
|
||||
<RenderTitle :tabItemData="children"></RenderTitle>
|
||||
<i
|
||||
v-if="allowClose && children.props?.closable != false"
|
||||
v-if="allowClose && children.closable != false"
|
||||
class="layui-icon layui-icon-close layui-unselect layui-tab-close"
|
||||
@click.stop="close(index, children.props?.id)"
|
||||
@click.stop="close(index, children.id)"
|
||||
></i>
|
||||
</li>
|
||||
</ul>
|
||||
|
||||
16
package/component/src/component/tab/interface.ts
Normal file
16
package/component/src/component/tab/interface.ts
Normal file
@@ -0,0 +1,16 @@
|
||||
import { Slots } from "vue";
|
||||
|
||||
export const TabInjectKey = Symbol("layuiTab");
|
||||
|
||||
export interface TabData {
|
||||
id: string;
|
||||
title?: string;
|
||||
closable?: string | boolean;
|
||||
slots: Slots;
|
||||
}
|
||||
|
||||
export interface TabsContext {
|
||||
active: string;
|
||||
addItem: (id: string, data: TabData) => void;
|
||||
removeItem: (id: string) => void;
|
||||
}
|
||||
@@ -5,7 +5,18 @@ export default {
|
||||
</script>
|
||||
|
||||
<script setup lang="ts">
|
||||
import { withDefaults, inject, Ref } from "vue";
|
||||
import {
|
||||
withDefaults,
|
||||
inject,
|
||||
Ref,
|
||||
useSlots,
|
||||
getCurrentInstance,
|
||||
computed,
|
||||
reactive,
|
||||
onBeforeUnmount,
|
||||
toRefs,
|
||||
} from "vue";
|
||||
import { TabInjectKey, TabsContext } from "../tab/interface";
|
||||
|
||||
export interface LayTabItemProps {
|
||||
id: string;
|
||||
@@ -17,9 +28,29 @@ const props = withDefaults(defineProps<LayTabItemProps>(), {
|
||||
closable: true,
|
||||
});
|
||||
|
||||
const instance = getCurrentInstance();
|
||||
const slots = useSlots();
|
||||
const active = inject("active");
|
||||
const slotsChange: Ref<boolean> = inject("slotsChange") as Ref<boolean>;
|
||||
slotsChange.value = !slotsChange.value;
|
||||
const tabsCtx = inject<Partial<TabsContext>>(TabInjectKey, {});
|
||||
|
||||
const data = reactive({
|
||||
id: props.id,
|
||||
title: props.title,
|
||||
closable: props.closable,
|
||||
slots: slots,
|
||||
});
|
||||
|
||||
if (instance?.uid) {
|
||||
tabsCtx.addItem?.(props.id, data);
|
||||
}
|
||||
|
||||
onBeforeUnmount(() => {
|
||||
if (instance?.uid) {
|
||||
tabsCtx.removeItem?.(props.id);
|
||||
}
|
||||
});
|
||||
</script>
|
||||
|
||||
<template>
|
||||
|
||||
@@ -10,8 +10,10 @@ import { computed, ref, useSlots, WritableComputedRef } from "vue";
|
||||
import LayCheckbox from "../checkbox/index.vue";
|
||||
import LayDropdown from "../dropdown/index.vue";
|
||||
import LayTooltip from "../tooltip/index.vue";
|
||||
import { LayIcon } from "@layui/icons-vue";
|
||||
|
||||
export interface LayTableRowProps {
|
||||
index: number;
|
||||
indentSize: number;
|
||||
currentIndentSize: number;
|
||||
expandSpace: boolean;
|
||||
@@ -20,6 +22,10 @@ export interface LayTableRowProps {
|
||||
childrenColumnName?: string;
|
||||
columns: Recordable[];
|
||||
checkbox?: boolean;
|
||||
cellClassName: string | Function;
|
||||
cellStyle: string | Function;
|
||||
rowClassName: string | Function;
|
||||
rowStyle: string | Function;
|
||||
id: string;
|
||||
data: any;
|
||||
}
|
||||
@@ -35,6 +41,8 @@ const emit = defineEmits([
|
||||
const props = withDefaults(defineProps<LayTableRowProps>(), {
|
||||
checkbox: false,
|
||||
childrenColumnName: "children",
|
||||
cellStyle: "",
|
||||
cellClassName: "",
|
||||
});
|
||||
|
||||
const tableSelectedKeys: WritableComputedRef<Recordable[]> = computed({
|
||||
@@ -75,11 +83,51 @@ const handleExpand = () => {
|
||||
isExpand.value = !isExpand.value;
|
||||
};
|
||||
|
||||
const renderCellStyle = (
|
||||
row: any,
|
||||
column: any,
|
||||
rowIndex: number,
|
||||
columnIndex: number
|
||||
) => {
|
||||
if (typeof props.cellStyle === "string") {
|
||||
return props.cellStyle;
|
||||
}
|
||||
return props.cellStyle(row, column, rowIndex, columnIndex);
|
||||
};
|
||||
|
||||
const renderCellClassName = (
|
||||
row: any,
|
||||
column: any,
|
||||
rowIndex: number,
|
||||
columnIndex: number
|
||||
) => {
|
||||
if (typeof props.cellClassName === "string") {
|
||||
return props.cellClassName;
|
||||
}
|
||||
return props.cellClassName(row, column, rowIndex, columnIndex);
|
||||
};
|
||||
|
||||
const renderRowStyle = (data: any, index: number) => {
|
||||
if (typeof props.rowStyle === "string") {
|
||||
return props.rowStyle;
|
||||
}
|
||||
return props.rowStyle(data, index);
|
||||
};
|
||||
|
||||
const renderRowClassName = (data: any, index: number) => {
|
||||
if (typeof props.rowClassName === "string") {
|
||||
return props.rowClassName;
|
||||
}
|
||||
return props.rowClassName(data, index);
|
||||
};
|
||||
|
||||
const childrenIndentSize = props.currentIndentSize + props.indentSize;
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<tr
|
||||
:style="[renderRowStyle(data, index)]"
|
||||
:class="[renderRowClassName(data, index)]"
|
||||
@click.stop="rowClick(data, $event)"
|
||||
@dblclick.stop="rowDoubleClick(data, $event)"
|
||||
@contextmenu.stop="contextmenu(data, $event)"
|
||||
@@ -96,21 +144,25 @@ const childrenIndentSize = props.currentIndentSize + props.indentSize;
|
||||
</td>
|
||||
|
||||
<!-- 数据列 -->
|
||||
<template v-for="(column, index) in columns" :key="column">
|
||||
<template v-for="(column, columnIndex) in columns" :key="columnIndex">
|
||||
<!-- 展示否 -->
|
||||
<template v-if="tableColumnKeys.includes(column.key)">
|
||||
<!-- 插槽列 -->
|
||||
<template v-if="column.customSlot">
|
||||
<td
|
||||
class="layui-table-cell"
|
||||
:style="{
|
||||
textAlign: column.align,
|
||||
whiteSpace: column.ellipsisTooltip ? 'nowrap' : 'normal',
|
||||
}"
|
||||
:style="[
|
||||
{
|
||||
textAlign: column.align,
|
||||
whiteSpace: column.ellipsisTooltip ? 'nowrap' : 'normal',
|
||||
},
|
||||
renderCellStyle(data, column, index, columnIndex),
|
||||
]"
|
||||
:class="[renderCellClassName(data, column, index, columnIndex)]"
|
||||
>
|
||||
<!-- 树表占位与缩进 -->
|
||||
<span
|
||||
v-if="expandSpace && index === 0"
|
||||
v-if="expandSpace && columnIndex === 0"
|
||||
:style="{ 'margin-right': currentIndentSize + 'px' }"
|
||||
></span>
|
||||
|
||||
@@ -119,13 +171,15 @@ const childrenIndentSize = props.currentIndentSize + props.indentSize;
|
||||
expandSpace &&
|
||||
!data[childrenColumnName] &&
|
||||
!slot.expand &&
|
||||
index === 0
|
||||
columnIndex === 0
|
||||
"
|
||||
class="layui-table-cell-expand-icon-spaced"
|
||||
></span>
|
||||
|
||||
<lay-icon
|
||||
v-if="(slot.expand || data[childrenColumnName]) && index === 0"
|
||||
v-if="
|
||||
(slot.expand || data[childrenColumnName]) && columnIndex === 0
|
||||
"
|
||||
class="layui-table-cell-expand-icon"
|
||||
:type="expandIconType"
|
||||
@click="handleExpand"
|
||||
@@ -147,14 +201,18 @@ const childrenIndentSize = props.currentIndentSize + props.indentSize;
|
||||
<template v-if="column.key in data">
|
||||
<td
|
||||
class="layui-table-cell"
|
||||
:style="{
|
||||
textAlign: column.align,
|
||||
whiteSpace: column.ellipsisTooltip ? 'nowrap' : 'normal',
|
||||
}"
|
||||
:style="[
|
||||
{
|
||||
textAlign: column.align,
|
||||
whiteSpace: column.ellipsisTooltip ? 'nowrap' : 'normal',
|
||||
},
|
||||
renderCellStyle(data, column, index, columnIndex),
|
||||
]"
|
||||
:class="[renderCellClassName(data, column, index, columnIndex)]"
|
||||
>
|
||||
<!-- 树表占位与缩进 -->
|
||||
<span
|
||||
v-if="expandSpace && index === 0"
|
||||
v-if="expandSpace && columnIndex === 0"
|
||||
:style="{ 'margin-right': currentIndentSize + 'px' }"
|
||||
></span>
|
||||
|
||||
@@ -163,13 +221,15 @@ const childrenIndentSize = props.currentIndentSize + props.indentSize;
|
||||
expandSpace &&
|
||||
!data[childrenColumnName] &&
|
||||
!slot.expand &&
|
||||
index === 0
|
||||
columnIndex === 0
|
||||
"
|
||||
class="layui-table-cell-expand-icon-spaced"
|
||||
></span>
|
||||
|
||||
<lay-icon
|
||||
v-if="(slot.expand || data[childrenColumnName]) && index === 0"
|
||||
v-if="
|
||||
(slot.expand || data[childrenColumnName]) && columnIndex === 0
|
||||
"
|
||||
class="layui-table-cell-expand-icon"
|
||||
:type="expandIconType"
|
||||
@click="handleExpand"
|
||||
@@ -198,11 +258,12 @@ const childrenIndentSize = props.currentIndentSize + props.indentSize;
|
||||
<!-- 树形结构 -->
|
||||
<template v-if="data[childrenColumnName] && isExpand">
|
||||
<template
|
||||
v-for="(children, index) in data[childrenColumnName]"
|
||||
:key="index"
|
||||
v-for="(children, childrenIndex) in data[childrenColumnName]"
|
||||
:key="childrenIndex"
|
||||
>
|
||||
<table-row
|
||||
:id="id"
|
||||
:index="childrenIndex"
|
||||
:data="children"
|
||||
:columns="columns"
|
||||
:indent-size="indentSize"
|
||||
@@ -210,6 +271,10 @@ const childrenIndentSize = props.currentIndentSize + props.indentSize;
|
||||
:checkbox="checkbox"
|
||||
:tableColumnKeys="tableColumnKeys"
|
||||
:expandSpace="expandSpace"
|
||||
:cellStyle="cellStyle"
|
||||
:cellClassName="cellClassName"
|
||||
:rowStyle="rowStyle"
|
||||
:rowClassName="rowClassName"
|
||||
@row="rowClick"
|
||||
@row-double="rowDoubleClick"
|
||||
@contextmenu="contextmenu"
|
||||
|
||||
@@ -30,6 +30,10 @@ export interface LayTableProps {
|
||||
height?: number;
|
||||
maxHeight?: string;
|
||||
even?: boolean;
|
||||
rowClassName?: string | Function;
|
||||
cellClassName?: string | Function;
|
||||
rowStyle?: string | Function;
|
||||
cellStyle?: string | Function;
|
||||
}
|
||||
|
||||
const props = withDefaults(defineProps<LayTableProps>(), {
|
||||
@@ -41,6 +45,10 @@ const props = withDefaults(defineProps<LayTableProps>(), {
|
||||
selectedKeys: () => [],
|
||||
maxHeight: "auto",
|
||||
even: false,
|
||||
rowClassName: "",
|
||||
cellClassName: "",
|
||||
rowStyle: "",
|
||||
cellStyle: "",
|
||||
});
|
||||
|
||||
const tableId = uuidv4();
|
||||
@@ -384,9 +392,10 @@ props.dataSource.map((value: any) => {
|
||||
</colgroup>
|
||||
<tbody>
|
||||
<!-- 渲染 -->
|
||||
<template v-for="data in tableDataSource" :key="data">
|
||||
<template v-for="(data, index) in tableDataSource" :key="data">
|
||||
<table-row
|
||||
:id="id"
|
||||
:index="index"
|
||||
:data="data"
|
||||
:columns="columns"
|
||||
:checkbox="checkbox"
|
||||
@@ -394,6 +403,10 @@ props.dataSource.map((value: any) => {
|
||||
:currentIndentSize="currentIndentSize"
|
||||
:tableColumnKeys="tableColumnKeys"
|
||||
:expandSpace="childrenExpandSpace"
|
||||
:cellStyle="cellStyle"
|
||||
:cellClassName="cellClassName"
|
||||
:rowStyle="rowStyle"
|
||||
:rowClassName="rowClassName"
|
||||
@row="rowClick"
|
||||
@row-double="rowDoubleClick"
|
||||
@contextmenu="contextmenu"
|
||||
|
||||
@@ -12,6 +12,7 @@
|
||||
import "./index.less";
|
||||
import LayPopper from "../popper/index.vue";
|
||||
import { defineComponent, ref } from "vue";
|
||||
import { useEventListener } from "@vueuse/core";
|
||||
export default defineComponent({
|
||||
name: "LayTooltip",
|
||||
components: {
|
||||
@@ -45,7 +46,7 @@ export default defineComponent({
|
||||
},
|
||||
setup() {
|
||||
const isMounted = ref(false);
|
||||
const refTooltip = ref(null);
|
||||
const refTooltip = ref<any>(null);
|
||||
return {
|
||||
isMounted,
|
||||
refTooltip,
|
||||
@@ -57,11 +58,20 @@ export default defineComponent({
|
||||
},
|
||||
},
|
||||
mounted() {
|
||||
if (this.isAutoShow) {
|
||||
useEventListener("resize", () => {
|
||||
this.setEllipsis();
|
||||
});
|
||||
}
|
||||
this.$nextTick(() => {
|
||||
this.setEllipsis();
|
||||
});
|
||||
},
|
||||
methods: {
|
||||
setEllipsis() {
|
||||
if (this.refTooltip) {
|
||||
if (
|
||||
this.refTooltip.offsetWidth >= this.refTooltip.firstChild.offsetWidth
|
||||
) {
|
||||
let tooltipHtml = this.refTooltip;
|
||||
if (tooltipHtml.offsetWidth >= tooltipHtml.firstChild.offsetWidth) {
|
||||
this.isMounted = false;
|
||||
} else {
|
||||
this.isMounted = true;
|
||||
@@ -69,7 +79,7 @@ export default defineComponent({
|
||||
} else {
|
||||
this.isMounted = true;
|
||||
}
|
||||
});
|
||||
},
|
||||
},
|
||||
});
|
||||
</script>
|
||||
|
||||
@@ -57,6 +57,7 @@ import LayRate from "./component/rate/index";
|
||||
import LayDropdown from "./component/dropdown/index";
|
||||
import LayDropdownMenu from "./component/dropdownMenu/index";
|
||||
import LayDropdownMenuItem from "./component/dropdownMenuItem/index";
|
||||
import LayDropdownSubMenu from "./component/dropdownSubMenu/index";
|
||||
import LayTab from "./component/tab/index";
|
||||
import LayTabItem from "./component/tabItem/index";
|
||||
import LayTree from "./component/tree/index";
|
||||
@@ -140,6 +141,7 @@ const components: Record<string, Plugin> = {
|
||||
LayDropdown,
|
||||
LayDropdownMenu,
|
||||
LayDropdownMenuItem,
|
||||
LayDropdownSubMenu,
|
||||
LayTab,
|
||||
LayTabItem,
|
||||
LayIconPicker,
|
||||
@@ -232,6 +234,7 @@ export {
|
||||
LayDropdown,
|
||||
LayDropdownMenu,
|
||||
LayDropdownMenuItem,
|
||||
LayDropdownSubMenu,
|
||||
LayTab,
|
||||
LayTabItem,
|
||||
LayIconPicker,
|
||||
|
||||
@@ -13,6 +13,7 @@ import {
|
||||
enable as enableDarkMode,
|
||||
disable as disableDarkMode,
|
||||
auto as followSystemColorScheme,
|
||||
setFetchMethod,
|
||||
} from "@umijs/ssr-darkreader";
|
||||
|
||||
export interface LayConfigProviderProps {
|
||||
@@ -71,6 +72,9 @@ const changeTheme = (theme: string) => {
|
||||
};
|
||||
Object.assign(defaultPartial, props.darkPartial);
|
||||
if (theme === "dark") {
|
||||
if (window) {
|
||||
setFetchMethod(window.fetch);
|
||||
}
|
||||
enableDarkMode(defaultPartial, defaultFixes);
|
||||
} else if (theme === "light") {
|
||||
disableDarkMode();
|
||||
|
||||
Reference in New Issue
Block a user