chore: prepare notice bar component refactoring

This commit is contained in:
就眠儀式
2022-04-15 10:13:49 +08:00
parent 8ad11a94e4
commit cd0e46d37e
8 changed files with 278 additions and 764 deletions

View File

@@ -1,8 +0,0 @@
import type { App } from "vue";
import Component from "./index.vue";
Component.install = (app: App) => {
app.component(Component.name, Component);
};
export default Component;

View File

@@ -1,253 +0,0 @@
<template>
<div
class="notice-bar"
:style="{ background, height: `${height}px` }"
v-show="!isMode"
>
<div class="notice-bar-warp" :style="{ color, fontSize: `${size}px` }">
<lay-icon
v-if="leftIcon"
class="notice-bar-warp-left-icon"
:type="leftIcon"
></lay-icon>
<div class="notice-bar-warp-text-box" ref="noticeBarWarpRef">
<div
class="notice-bar-warp-text"
ref="noticeBarTextRef"
v-if="!scrollable"
>
{{ text }}
</div>
<div class="notice-bar-warp-slot" v-else>
<lay-carousel
v-model="active4"
:interval="3000"
:autoplay="true"
anim="updown"
indicator="none"
arrow="none"
style="height: 40px"
>
<lay-carousel-item :id="ind" v-for="(item, ind) in arrays">
<div>{{ item }}</div>
</lay-carousel-item>
</lay-carousel>
<!-- <slot /> -->
</div>
</div>
<lay-icon
:type="rightIcon"
v-if="rightIcon"
class="notice-bar-warp-right-icon"
@click="onRightIconClick"
></lay-icon>
</div>
</div>
</template>
<script lang="ts">
import {
toRefs,
reactive,
defineComponent,
ref,
onMounted,
nextTick,
} from "vue";
import LayCarousel from "../carousel/index.vue";
import LayCarouselItem from "../carouselItem/index.vue";
export default defineComponent({
name: "LayNoticeBar",
components: {
LayCarousel,
LayCarouselItem,
},
props: {
mode: {
type: String,
default: () => "",
},
text: {
type: String,
default: () => "",
},
textlist: {
type: Array,
default: [],
},
// 通知文本颜色
color: {
type: String,
default: () => "var(--color-warning)",
},
// 通知背景色
background: {
type: String,
default: () => "var(--color-warning-light-9)",
},
// 字体大小单位px
size: {
type: [Number, String],
default: () => 14,
},
// 通知栏高度单位px
height: {
type: Number,
default: () => 40,
},
// 动画延迟时间 (s)
delay: {
type: Number,
default: () => 1,
},
// 滚动速率 (px/s)
speed: {
type: Number,
default: () => 100,
},
// 是否开启垂直滚动
scrollable: {
type: Boolean,
default: () => false,
},
// 自定义左侧图标
leftIcon: {
type: String,
default: () => "",
},
// 自定义右侧图标
rightIcon: {
type: String,
default: () => "",
},
},
setup(props, { emit }) {
const noticeBarWarpRef = ref();
const noticeBarTextRef = ref();
const state = reactive({
order: 1,
oneTime: 0,
twoTime: 0,
warpOWidth: 0,
textOWidth: 0,
isMode: false,
});
// 初始化 animation 各项参数
const initAnimation = () => {
nextTick(() => {
state.warpOWidth = noticeBarWarpRef.value.offsetWidth;
state.textOWidth = noticeBarTextRef.value.offsetWidth;
document.styleSheets[0].insertRule(
`@keyframes oneAnimation {0% {left: 0px;} 100% {left: -${state.textOWidth}px;}}`
);
document.styleSheets[0].insertRule(
`@keyframes twoAnimation {0% {left: ${state.warpOWidth}px;} 100% {left: -${state.textOWidth}px;}}`
);
computeAnimationTime();
setTimeout(() => {
changeAnimation();
}, props.delay * 1000);
});
};
// 计算 animation 滚动时长
const computeAnimationTime = () => {
state.oneTime = state.textOWidth / props.speed;
state.twoTime = (state.textOWidth + state.warpOWidth) / props.speed;
};
// 改变 animation 动画调用
const changeAnimation = () => {
if (state.order === 1) {
noticeBarTextRef.value.style.cssText = `animation: oneAnimation ${state.oneTime}s linear; opactity: 1;}`;
state.order = 2;
} else {
noticeBarTextRef.value.style.cssText = `animation: twoAnimation ${state.twoTime}s linear infinite; opacity: 1;`;
}
};
// 监听 animation 动画的结束
const listenerAnimationend = () => {
noticeBarTextRef.value.addEventListener(
"animationend",
() => {
changeAnimation();
},
false
);
};
// 右侧 icon 图标点击
const onRightIconClick = () => {
if (!props.mode) return false;
if (props.mode === "closeable") {
state.isMode = true;
emit("close");
} else if (props.mode === "link") {
emit("link");
}
};
// 页面加载时
onMounted(() => {
if (props.scrollable) return false;
initAnimation();
listenerAnimationend();
});
return {
noticeBarWarpRef,
noticeBarTextRef,
onRightIconClick,
...toRefs(state),
};
},
});
</script>
<style>
.notice-bar {
padding: 0 15px;
width: 100%;
border-radius: 4px;
}
.notice-bar .notice-bar-warp {
display: flex;
align-items: center;
width: 100%;
height: inherit;
}
.notice-bar .notice-bar-warp .notice-bar-warp-text-box {
flex: 1;
height: inherit;
display: flex;
align-items: center;
overflow: hidden;
position: relative;
}
.notice-bar .notice-bar-warp .notice-bar-warp-text-box .notice-bar-warp-text {
white-space: nowrap;
position: absolute;
left: 0;
}
.notice-bar .notice-bar-warp .notice-bar-warp-text-box .notice-bar-warp-slot {
width: 100%;
white-space: nowrap;
}
.notice-bar
.notice-bar-warp
.notice-bar-warp-text-box
.notice-bar-warp-slot
.layui-carousel
> [carousel-item]
* {
display: flex;
align-items: center;
}
.notice-bar .notice-bar-warp .notice-bar-warp-left-icon {
width: 24px;
font-size: inherit !important;
}
.notice-bar .notice-bar-warp .notice-bar-warp-right-icon {
width: 24px;
text-align: right;
font-size: inherit !important;
}
.notice-bar .notice-bar-warp .notice-bar-warp-right-icon:hover {
cursor: pointer;
}
</style>

View File

@@ -46,8 +46,11 @@ const onActive = function (event: Event) {
// 跟随鼠标点击
if (props.type === "inset" && !props.spreadSize && !props.center) {
const el = event.currentTarget;
// @ts-ignore
const rect = el.getBoundingClientRect();
// @ts-ignore
const rippleOffsetLeft = event.clientX - rect.left;
// @ts-ignore
const rippleOffsetTop = event.clientY - rect.top;
const sizeX = Math.max(rippleOffsetLeft, rect.width - rippleOffsetLeft);
const sizeY = Math.max(rippleOffsetTop, rect.height - rippleOffsetTop);

View File

@@ -79,7 +79,6 @@ import LayException from "./component/exception/index";
import LayResult from "./component/result/index";
import LayFullscreen from "./component/fullscreen/index";
import LayDatePicker from "./component/datePicker/index";
import LayNoticeBar from "./component/noticeBar/index";
import LayTransition from "./component/transition/index";
import LayUpload from "./component/upload/index";
import LayRipple from "./component/ripple/index";
@@ -160,7 +159,6 @@ const components: Record<string, Component> = {
LayFullscreen,
LayConfigProvider,
LayDatePicker,
LayNoticeBar,
LayTransition,
LayUpload,
LayRipple,
@@ -249,7 +247,6 @@ export {
LayFullscreen,
LayConfigProvider,
LayDatePicker,
LayNoticeBar,
LayTransition,
LayUpload,
LayRipple,