-
Notifications
You must be signed in to change notification settings - Fork 693
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
0f5c55c
commit 3d96229
Showing
27 changed files
with
1,790 additions
and
78 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,193 @@ | ||
<template> | ||
<el-dialog | ||
ref="dialogRef" | ||
v-bind="getBindValue" | ||
:fullscreen="fullscreen" | ||
destroy-on-close | ||
lock-scroll | ||
:close-on-click-modal="false" | ||
top="10vh" | ||
> | ||
<template #title> | ||
<slot name="title"> | ||
{{ title }} | ||
</slot> | ||
<svg-icon | ||
v-if="showFullscreen" | ||
:icon-class="fullscreen ? 'exit-fullscreen' : 'fullscreen'" | ||
class-name="dialog__icon" | ||
@click="toggleFull" | ||
/> | ||
</template> | ||
|
||
<!-- 弹窗内容 --> | ||
<el-scrollbar | ||
:class=" | ||
fullscreen && slots.footer | ||
? 'com-dialog__content--footer' | ||
: fullscreen && !slots.footer | ||
? 'com-dialog__content--fullscreen' | ||
: 'com-dialog__content' | ||
" | ||
> | ||
<div class="content__wrap"> | ||
<slot></slot> | ||
</div> | ||
</el-scrollbar> | ||
|
||
<template v-if="slots.footer" #footer> | ||
<slot name="footer"></slot> | ||
</template> | ||
</el-dialog> | ||
</template> | ||
|
||
<script setup lang="ts" name="Dialog"> | ||
import { ref, computed, PropType, nextTick, unref, useAttrs, useSlots } from 'vue' | ||
import SvgIcon from '@/components/SvgIcon/index.vue' | ||
const slots = useSlots() | ||
const props = defineProps({ | ||
title: { | ||
type: String as PropType<string>, | ||
default: '' | ||
}, | ||
// 是否显示全屏按钮 | ||
showFullscreen: { | ||
type: Boolean as PropType<boolean>, | ||
default: true | ||
}, | ||
// 是否可以拖拽 | ||
draggable: { | ||
type: Boolean as PropType<boolean>, | ||
default: true | ||
} | ||
}) | ||
const dialogRef = ref<HTMLElement | null>(null) | ||
const fullscreen = ref<boolean>(false) | ||
const getBindValue = computed((): any => { | ||
const delArr: string[] = ['showFullscreen', 'draggable'] | ||
const attrs = useAttrs() | ||
const obj = { ...attrs, ...props } | ||
for (const key in obj) { | ||
if (delArr.indexOf(key) !== -1) { | ||
delete obj[key] | ||
} | ||
} | ||
return obj | ||
}) | ||
function toggleFull(): void { | ||
fullscreen.value = !fullscreen.value | ||
// 全屏的时候需要重新定义left top | ||
if (fullscreen.value && props.draggable) { | ||
const dragDom = unref(dialogRef as any).$refs.dialogRef | ||
dragDom.style.cssText += `;left:0px;top:0px;` | ||
} | ||
} | ||
function initDraggable() { | ||
nextTick(() => { | ||
const dragDom = unref(dialogRef as any).$refs.dialogRef | ||
const dialogHeaderEl = dragDom.querySelector('.el-dialog__header') as HTMLElement | ||
dragDom.style.cssText += ';top:0px;' | ||
dialogHeaderEl.style.cssText += ';cursor:move;user-select:none;' | ||
dialogHeaderEl.onmousedown = (e) => { | ||
const disX = e.clientX - dialogHeaderEl.offsetLeft | ||
const disY = e.clientY - dialogHeaderEl.offsetTop | ||
const dragDomWidth = dragDom.offsetWidth | ||
const dragDomHeight = dragDom.offsetHeight | ||
const screenWidth = document.body.clientWidth | ||
const screenHeight = document.body.clientHeight | ||
const minDragDomLeft = dragDom.offsetLeft | ||
const maxDragDomLeft = screenWidth - dragDom.offsetLeft - dragDomWidth | ||
const minDragDomTop = dragDom.offsetTop | ||
const maxDragDomTop = screenHeight - dragDom.offsetTop - dragDomHeight | ||
const styleLeftStr = getComputedStyle(dragDom).left | ||
const styleTopStr = getComputedStyle(dragDom).top | ||
if (!styleLeftStr || !styleTopStr) return | ||
let styleLeft: number | ||
let styleTop: number | ||
// Format may be "##%" or "##px" | ||
if (styleLeftStr.includes('%')) { | ||
styleLeft = +document.body.clientWidth * (+styleLeftStr.replace(/%/g, '') / 100) | ||
styleTop = +document.body.clientHeight * (+styleTopStr.replace(/%/g, '') / 100) | ||
} else { | ||
styleLeft = +styleLeftStr.replace(/px/g, '') | ||
styleTop = +styleTopStr.replace(/px/g, '') | ||
} | ||
document.onmousemove = (e) => { | ||
let left = e.clientX - disX | ||
let top = e.clientY - disY | ||
// Handle edge cases | ||
if (-left > minDragDomLeft) { | ||
left = -minDragDomLeft | ||
} else if (left > maxDragDomLeft) { | ||
left = maxDragDomLeft | ||
} | ||
if (-top > minDragDomTop) { | ||
top = -minDragDomTop | ||
} else if (top > maxDragDomTop) { | ||
top = maxDragDomTop | ||
} | ||
// Move current element | ||
dragDom.style.cssText += `;left:${left + styleLeft}px;top:${top + styleTop}px;` | ||
} | ||
document.onmouseup = () => { | ||
document.onmousemove = null | ||
document.onmouseup = null | ||
} | ||
} | ||
}) | ||
} | ||
if (props.draggable) { | ||
initDraggable() | ||
} | ||
</script> | ||
|
||
<style lang="less" scoped> | ||
.dialog__icon { | ||
position: absolute; | ||
top: 22px; | ||
right: 45px; | ||
font-size: 12px; | ||
color: #909399; | ||
cursor: pointer; | ||
transition: color 0.2s; | ||
&:hover { | ||
color: #409eff; | ||
} | ||
} | ||
.com-dialog__content { | ||
.content__wrap { | ||
padding-right: 10px; | ||
} | ||
:deep(.el-scrollbar__wrap) { | ||
max-height: 600px; // 最大高度 | ||
overflow-x: hidden; // 隐藏横向滚动栏 | ||
} | ||
} | ||
.com-dialog__content--fullscreen { | ||
:deep(.el-scrollbar__wrap) { | ||
height: calc(~'100vh - 46px - 60px'); // 最大高度 | ||
} | ||
} | ||
.com-dialog__content--footer { | ||
:deep(.el-scrollbar__wrap) { | ||
max-height: calc(~'100vh - 46px - 60px - 70px'); // 最大高度 | ||
} | ||
} | ||
</style> |
Oops, something went wrong.