style: slogan区域移动端样式

This commit is contained in:
2026-03-18 10:22:24 +08:00
parent f2c265e4e7
commit ec4ba64030

View File

@@ -1,9 +1,5 @@
<template>
<div
class="blocks-list flex"
ref="root"
:class="{ 'in-view': inView }"
>
<div class="blocks-list flex" ref="root" :class="{ 'in-view': inView }">
<div
class="block-item flex flex-col flex-center"
v-for="(item, idx) in blocksList"
@@ -18,12 +14,12 @@
</template>
<script setup lang="ts">
import { computed, ref, onMounted, onUnmounted } from 'vue'
import { useI18n } from 'vue-i18n'
import { computed, ref, onMounted, onUnmounted } from 'vue'
import { useI18n } from 'vue-i18n'
const { t } = useI18n()
const { t } = useI18n()
const blocksList = ref([
const blocksList = ref([
{
number: 'AwardsPage.totalCashPrizes',
label: 'AwardsPage.totalCashPrizesLabel'
@@ -40,14 +36,14 @@
number: 'AwardsPage.awardCeremonyHongKong',
label: 'AwardsPage.awardCeremonyLabel'
}
])
const root = ref<HTMLElement | null>(null)
const inView = ref(false)
let io: IntersectionObserver | null = null
])
const root = ref<HTMLElement | null>(null)
const inView = ref(false)
let io: IntersectionObserver | null = null
onMounted(() => {
onMounted(() => {
io = new IntersectionObserver(
entries => {
(entries) => {
for (const entry of entries) {
if (entry.isIntersecting) {
// 延迟 0.5s 后触发动画并断开观察
@@ -65,15 +61,15 @@
if (root.value) {
io.observe(root.value)
}
})
})
onUnmounted(() => {
onUnmounted(() => {
io?.disconnect()
})
})
</script>
<style lang="less" scoped>
.blocks-list {
.blocks-list {
height: 31.4rem;
background: linear-gradient(98.55deg, #232323 18.22%, #898989 101.1%);
@@ -115,26 +111,26 @@
will-change: height;
}
}
}
}
/* 当组件进入视口并且等待 0.5s 后,.in-view 会加入根节点,下面规则触发动画 */
.in-view .block-item .number {
/* 当组件进入视口并且等待 0.5s 后,.in-view 会加入根节点,下面规则触发动画 */
.in-view .block-item .number {
animation: scaleIn 0.48s cubic-bezier(0.2, 0.9, 0.2, 1) forwards;
animation-delay: var(--delay);
}
}
.in-view .block-item .label {
.in-view .block-item .label {
animation: scaleIn 0.48s cubic-bezier(0.2, 0.9, 0.2, 1) forwards;
animation-delay: calc(var(--delay) + 0.12s);
}
}
.in-view .block-item .line {
.in-view .block-item .line {
animation: growLine 0.7s cubic-bezier(0.2, 0.9, 0.2, 1) forwards;
animation-delay: calc(var(--delay) + 0.18s);
}
}
/* keyframes */
@keyframes scaleIn {
/* keyframes */
@keyframes scaleIn {
from {
transform: scale(0);
opacity: 0;
@@ -143,14 +139,142 @@
transform: scale(1);
opacity: 1;
}
}
}
@keyframes growLine {
@keyframes growLine {
from {
height: 0;
}
to {
height: 27.4rem;
}
}
/* 移动端 <= 1200px 四宫格布局 */
@media (max-width: 1200px) {
.blocks-list {
height: auto;
flex-wrap: wrap;
padding: 2rem 1.5rem;
column-gap: 0;
row-gap: 0;
.block-item {
flex: none;
width: 50%;
height: 18rem;
padding: 2rem 1rem;
box-sizing: border-box;
.number {
font-size: 2.8rem;
}
.label {
font-size: 1.8rem;
}
.line {
display: none;
}
&:nth-child(1)::after,
&:nth-child(2)::after,
&:nth-child(3)::after {
content: '';
position: absolute;
background-color: #8d8d8d;
}
/* 第一行的两个item底部需要分隔线 */
&:nth-child(1)::after,
&:nth-child(2)::after {
bottom: 0;
left: 0;
width: 100%;
height: 0.1rem;
}
/* 第一个item右侧需要分隔线 */
&:nth-child(1)::before {
content: '';
position: absolute;
right: 0;
top: 0;
height: 100%;
width: 0.1rem;
background-color: #8d8d8d;
}
&:nth-child(4)::before {
content: '';
position: absolute;
bottom: 0;
left: 0;
width: 0.1rem;
height: 100%;
background-color: #8d8d8d;
transform: translateX(-100%);
}
}
}
.in-view {
.block-item {
&:nth-child(1)::before {
transform-origin: bottom;
transform: scaleY(0);
animation: growUp 2s cubic-bezier(0.4, 0, 0.2, 1) forwards;
animation-delay: calc(var(--delay) + 0.5s);
}
&:nth-child(1)::after {
transform-origin: right;
transform: scaleX(0);
animation: growRight 2s cubic-bezier(0.4, 0, 0.2, 1) forwards;
animation-delay: calc(var(--delay) + 0.5s);
}
&:nth-child(2)::after {
transform-origin: left;
transform: scaleX(0);
animation: growLeft 2s cubic-bezier(0.4, 0, 0.2, 1) forwards;
animation-delay: calc(var(--delay) + 0.5s);
}
&:nth-child(4)::before {
transform: translateX(-100%) scaleY(0);
transform-origin: top;
animation: growDown 2s cubic-bezier(0.4, 0, 0.2, 1) forwards;
animation-delay: calc(var(--delay) + 0.5s);
}
}
}
@keyframes growUp {
0% {
transform: scaleY(0);
}
100% {
transform: scaleY(1);
}
}
@keyframes growDown {
0% {
transform: translateX(-100%) scaleY(0);
}
100% {
transform: translateX(-100%) scaleY(1);
}
}
@keyframes growLeft {
0% {
transform: scaleX(0);
}
100% {
transform: scaleX(1);
}
}
@keyframes growRight {
0% {
transform: scaleX(0);
}
100% {
transform: scaleX(1);
}
}
}
</style>