fix. useResponsiveBreakpoints, getImageHost 수정

This commit is contained in:
clkim
2025-10-31 12:55:37 +09:00
parent 007d427520
commit 83124d56eb
21 changed files with 106 additions and 106 deletions

View File

@@ -1,6 +1,6 @@
<script setup lang="ts"> <script setup lang="ts">
import { useNuxtApp } from 'nuxt/app' import { useNuxtApp } from 'nuxt/app'
import { getResolvedHost } from '#layers/utils/styleUtil' import { getImageHost } from '#layers/utils/styleUtil'
import type { import type {
GameDataFavicon, GameDataFavicon,
GameDataMetaTag, GameDataMetaTag,
@@ -37,16 +37,16 @@ const setupAllMetaData = (data: GameDataValue) => {
{ {
rel: 'icon', rel: 'icon',
type: 'image/x-icon', type: 'image/x-icon',
href: getResolvedHost(faviconPath[0]), href: getImageHost(faviconPath[0]),
}, },
{ {
rel: 'apple-touch-icon', rel: 'apple-touch-icon',
href: getResolvedHost(faviconPath[1]), href: getImageHost(faviconPath[1]),
}, },
{ {
rel: 'icon', rel: 'icon',
type: 'image/png', type: 'image/png',
href: getResolvedHost(faviconPath[2]), href: getImageHost(faviconPath[2]),
}, },
] ]
@@ -115,7 +115,7 @@ onMounted(() => {
groups.forEach(({ img_name, img_path }) => { groups.forEach(({ img_name, img_path }) => {
document.documentElement.style.setProperty( document.documentElement.style.setProperty(
`--${img_name}`, `--${img_name}`,
`url(${getResolvedHost(img_path?.comm ?? '')})` `url(${getImageHost(img_path?.comm ?? '')})`
) )
}) })
} }

View File

@@ -1,6 +1,6 @@
/* Layout Utility Classes */ /* Layout Utility Classes */
@layer components { @layer components {
.section-container { .section-wrap {
@apply relative h-[640px] md:h-[1000px]; @apply relative h-[640px] md:h-[1000px];
} }

View File

@@ -60,7 +60,7 @@ const inlineStyle = computed<CSSProperties>(() => {
style.color = props.textColor style.color = props.textColor
} }
if (props.type === 'duplication') { if (props.type === 'duplication') {
style.backgroundImage = `url(${getImageHost(DUP_IMAGE_MAP[props.platform])})` style.backgroundImage = `url(${getImageHost(DUP_IMAGE_MAP[props.platform], { imageType: 'common' })})`
} }
return style return style
}) })

View File

@@ -77,7 +77,7 @@ const handleCopy = async () => {
target="_blank" target="_blank"
class="sns-item" class="sns-item"
:style="{ :style="{
backgroundImage: `url(${getImageHost(`/images/common/ic-v2-logo-${key}-fill.svg`)})`, backgroundImage: `url(${getImageHost(`/images/common/ic-v2-logo-${key}-fill.svg`, { imageType: 'common' })})`,
}" }"
> >
<span class="sr-only">{{ key }}</span> <span class="sr-only">{{ key }}</span>
@@ -87,7 +87,7 @@ const handleCopy = async () => {
type="button" type="button"
class="sns-item" class="sns-item"
:style="{ :style="{
backgroundImage: `url(${getImageHost('/images/common/ic-v2-community-link-line.svg')})`, backgroundImage: `url(${getImageHost('/images/common/ic-v2-community-link-line.svg', { imageType: 'common' })})`,
}" }"
@click="handleCopy" @click="handleCopy"
> >

View File

@@ -16,13 +16,13 @@ const isResponsiveMode = computed(() => {
}) })
const imagePaths = computed(() => { const imagePaths = computed(() => {
if (typeof props.src === 'string') { if (typeof props.src === 'string') {
const resolved = getResolvedHost(`${rootPath}${props.src}`) const resolved = getImageHost(`${rootPath}${props.src}`)
return { pc: resolved, mo: '' } return { pc: resolved, mo: '' }
} }
return { return {
pc: props.src.pc ? getResolvedHost(`${rootPath}${props.src.pc}`) : '', pc: props.src.pc ? getImageHost(`${rootPath}${props.src.pc}`) : '',
mo: props.src.mo ? getResolvedHost(`${rootPath}${props.src.mo}`) : '', mo: props.src.mo ? getImageHost(`${rootPath}${props.src.mo}`) : '',
} }
}) })
</script> </script>

View File

@@ -16,7 +16,6 @@ withDefaults(defineProps<Props>(), {
:width="size" :width="size"
:height="size" :height="size"
viewBox="0 0 12 12" viewBox="0 0 12 12"
:fill="color"
> >
<path <path
d="M5.29499 7.715L2.39999 4.875C2.07499 4.555 2.29999 4 2.75999 4L9.23499 4C9.69499 4 9.91999 4.555 9.59499 4.875L6.69999 7.715C6.30999 8.095 5.68999 8.095 5.29999 7.715H5.29499Z" d="M5.29499 7.715L2.39999 4.875C2.07499 4.555 2.29999 4 2.75999 4L9.23499 4C9.69499 4 9.91999 4.555 9.59499 4.875L6.69999 7.715C6.30999 8.095 5.68999 8.095 5.29999 7.715H5.29499Z"

View File

@@ -0,0 +1,27 @@
<script setup lang="ts">
interface Props {
size?: number | string
color?: string
}
withDefaults(defineProps<Props>(), {
size: 20,
color: 'var(--foreground-gray-500)',
})
</script>
<template>
<svg
xmlns="http://www.w3.org/2000/svg"
:width="size"
:height="size"
viewBox="0 0 20 20"
>
<path
fill-rule="evenodd"
clip-rule="evenodd"
d="M6.91073 3.57757C6.5853 3.90301 6.5853 4.43065 6.91073 4.75609L12.1548 10.0002L6.91073 15.2442C6.5853 15.5697 6.5853 16.0973 6.91073 16.4228C7.23617 16.7482 7.76381 16.7482 8.08924 16.4228L13.9226 10.5894C14.248 10.264 14.248 9.73634 13.9226 9.41091L8.08924 3.57757C7.76381 3.25214 7.23617 3.25214 6.91073 3.57757Z"
:fill="color"
/>
</svg>
</template>

View File

@@ -1,26 +0,0 @@
<script setup lang="ts">
interface Props {
size?: number | string
color?: string
}
withDefaults(defineProps<Props>(), {
size: 16,
color: 'var(--foreground-reversal)',
})
</script>
<template>
<svg
xmlns="http://www.w3.org/2000/svg"
:width="size"
:height="size"
viewBox="0 0 16 16"
fill="none"
>
<path
d="M15.7071 1.70711C16.0976 1.31658 16.0976 0.683417 15.7071 0.292893C15.3166 -0.0976311 14.6834 -0.0976311 14.2929 0.292893L8 6.58579L1.70711 0.292893C1.31658 -0.0976311 0.683417 -0.0976311 0.292894 0.292893C-0.0976304 0.683417 -0.0976304 1.31658 0.292894 1.70711L6.58579 8L0.292893 14.2929C-0.0976311 14.6834 -0.0976311 15.3166 0.292893 15.7071C0.683417 16.0976 1.31658 16.0976 1.70711 15.7071L8 9.41421L14.2929 15.7071C14.6834 16.0976 15.3166 16.0976 15.7071 15.7071C16.0976 15.3166 16.0976 14.6834 15.7071 14.2929L9.41421 8L15.7071 1.70711Z"
:fill="color"
/>
</svg>
</template>

View File

@@ -29,7 +29,6 @@ const sanitizedContent = computed(() => {
<template> <template>
<AtomsImg <AtomsImg
v-if="isTypeImage(resourcesData?.resource_type) && imagePaths" v-if="isTypeImage(resourcesData?.resource_type) && imagePaths"
ref="pictureRef"
:src="imagePaths" :src="imagePaths"
:alt="alt || displayText" :alt="alt || displayText"
:class="`w-full h-full object-${objectFit}`" :class="`w-full h-full object-${objectFit}`"

View File

@@ -176,7 +176,7 @@ onBeforeUnmount(() => {
<div class="game-wrapper" :class="{ 'is-fixed': isPassedStoveGnb }"> <div class="game-wrapper" :class="{ 'is-fixed': isPassedStoveGnb }">
<AtomsLocaleLink to="/brand" class="mx-auto md:hidden"> <AtomsLocaleLink to="/brand" class="mx-auto md:hidden">
<img <img
:src="getResolvedHost(gnbData?.bi_path)" :src="getImageHost(gnbData?.bi_path)"
:alt="gameData?.game_name" :alt="gameData?.game_name"
class="h-[30px]" class="h-[30px]"
/> />
@@ -193,7 +193,7 @@ onBeforeUnmount(() => {
<div class="nav-logo"> <div class="nav-logo">
<AtomsLocaleLink to="/brand" @click="handleMenuClose"> <AtomsLocaleLink to="/brand" @click="handleMenuClose">
<img <img
:src="getResolvedHost(gnbData?.bi_path)" :src="getImageHost(gnbData?.bi_path)"
:alt="gameData?.game_name" :alt="gameData?.game_name"
class="h-[30px]" class="h-[30px]"
/> />
@@ -215,13 +215,21 @@ onBeforeUnmount(() => {
<AtomsLocaleLink <AtomsLocaleLink
:to="gnbItem.url_path" :to="gnbItem.url_path"
:target="gnbItem.link_target" :target="gnbItem.link_target"
:class="['nav-1depth', { active: isNavItemActive(gnbItem) }]" :class="[
'nav-1depth',
{ 'has-link': !!gnbItem.url_path },
{ active: isNavItemActive(gnbItem) },
]"
> >
<span>{{ gnbItem.menu_name }}</span> <span>{{ gnbItem.menu_name }}</span>
<AtomsIconsArrowDownFill <AtomsIconsArrowDownFill
v-if="has2depthButton(gnbItem)" v-if="has2depthButton(gnbItem)"
class="hidden md:block" class="hidden md:block"
/> />
<AtomsIconsArrowRightLine
v-if="!has2depthButton(gnbItem)"
class="ml-auto md:hidden"
/>
</AtomsLocaleLink> </AtomsLocaleLink>
<Transition name="fade"> <Transition name="fade">
<div v-if="has2depthButton(gnbItem)" class="nav-2depth"> <div v-if="has2depthButton(gnbItem)" class="nav-2depth">
@@ -322,7 +330,6 @@ onBeforeUnmount(() => {
colorCode: gnb1depthButtonData?.btn_info?.color_code_txt, colorCode: gnb1depthButtonData?.btn_info?.color_code_txt,
}) })
" "
class="nav-1depth"
> >
{{ gnb1depthButtonData?.btn_info?.txt_btn_name }} {{ gnb1depthButtonData?.btn_info?.txt_btn_name }}
</AtomsButtonLauncher> </AtomsButtonLauncher>
@@ -337,7 +344,11 @@ onBeforeUnmount(() => {
</div> </div>
</div> </div>
<button class="btn-close" @click="handleMenuClose"> <button class="btn-close" @click="handleMenuClose">
<AtomsIconsMenuCloseLine class="mx-auto" /> <AtomsIconsCloseLine
size="24"
color="var(--foreground-reversal)"
class="mx-auto"
/>
<span class="sr-only">menu close</span> <span class="sr-only">menu close</span>
</button> </button>
</div> </div>
@@ -426,6 +437,9 @@ onBeforeUnmount(() => {
.nav-1depth.active { .nav-1depth.active {
@apply bg-theme-foreground-reversal-8 md:bg-transparent; @apply bg-theme-foreground-reversal-8 md:bg-transparent;
} }
.nav-1depth.has-link {
@apply hover:bg-theme-foreground-reversal-4 active:bg-theme-foreground-reversal-10 md:hover:bg-transparent md:active:bg-transparent;
}
.nav-2depth { .nav-2depth {
@apply text-[15px] md:hidden md:absolute md:top-[64px] md:left-[-28px] md:pt-1; @apply text-[15px] md:hidden md:absolute md:top-[64px] md:left-[-28px] md:pt-1;
@@ -480,15 +494,16 @@ onBeforeUnmount(() => {
.btn-start:hover .nav-2depth { .btn-start:hover .nav-2depth {
@apply md:block; @apply md:block;
} }
.btn-start:deep(.nav-1depth) { .btn-start:deep(> .btn-base) {
@apply w-full h-[48px] px-10 md:w-auto; @apply w-full h-[48px] px-10;
} }
.btn-start:deep(.nav-1depth) .icon-platform { .btn-start:deep(> .btn-base) .icon-platform {
@apply hidden; @apply hidden;
} }
.btn-start:deep(.nav-1depth) .btn-content { .btn-start:deep(> .btn-base) .btn-content {
@apply justify-center text-center; @apply justify-center;
} }
.btn-start .nav-2depth { .btn-start .nav-2depth {
@apply left-[unset] right-[-40px]; @apply left-[unset] right-[-40px];
} }

View File

@@ -14,12 +14,13 @@ export const BREAKPOINTS = {
*/ */
export const useResponsiveBreakpoints = () => { export const useResponsiveBreakpoints = () => {
const breakpoints = useBreakpoints(BREAKPOINTS) const breakpoints = useBreakpoints(BREAKPOINTS)
const isXs = breakpoints.smaller('sm') // < 768px const isXs = breakpoints.smaller('sm') // < 768
const isSm = breakpoints.smaller('md') // < 1024px const isSm = breakpoints.between('sm', 'md') // 768 <= x < 1024
const isMd = breakpoints.smaller('lg') // < 1440px const isMd = breakpoints.between('md', 'lg') // 1024 <= x < 1440
const isLg = breakpoints.greater('lg') // >= 1440px const isLg = breakpoints.greaterOrEqual('lg') // >= 1440
const isMobile = isXs || isSm
const isDesktop = isLg || isMd const isMobile = breakpoints.smaller('md') // < 1024
const isDesktop = breakpoints.greaterOrEqual('md') // >= 1024
return computed(() => ({ return computed(() => ({
isXs: isXs.value, isXs: isXs.value,

View File

@@ -131,7 +131,7 @@ const onArrowClick = (direction, targetIndex) => {
:description=" :description="
formatTimestamp(item.create_datetime, 'YYYY.MM.DD') formatTimestamp(item.create_datetime, 'YYYY.MM.DD')
" "
:img-path="getResolvedHost(item.media_thumbnail_url)" :img-path="getImageHost(item.media_thumbnail_url)"
:url="getArticleUrl(item.article_id)" :url="getArticleUrl(item.article_id)"
link-target="_blank" link-target="_blank"
/> />

View File

@@ -41,7 +41,7 @@ const handleSplideMove = (_splide: SplideType, newIndex: number) => {
</script> </script>
<template> <template>
<section class="section-container relative"> <section class="section-wrap">
<BlocksSlideFade <BlocksSlideFade
v-if="slideData" v-if="slideData"
ref="splideRef" ref="splideRef"

View File

@@ -22,7 +22,7 @@ const paginationData = computed(() => {
</script> </script>
<template> <template>
<section class="section-container relative"> <section class="section-wrap">
<BlocksSlideThumbnail <BlocksSlideThumbnail
:slide-data="slideData" :slide-data="slideData"
:pagination-data="paginationData" :pagination-data="paginationData"

View File

@@ -43,7 +43,7 @@ const handleSplideMove = (_splide: SplideType, newIndex: number) => {
</script> </script>
<template> <template>
<section class="section-container relative"> <section class="section-wrap">
<BlocksSlideThumbnail <BlocksSlideThumbnail
:slide-data="slideData" :slide-data="slideData"
:pagination-data="paginationData" :pagination-data="paginationData"

View File

@@ -102,7 +102,7 @@ const onArrowClick = (direction, targetIndex) => {
</script> </script>
<template> <template>
<section class="section-container min-h-[700px]"> <section class="section-wrap min-h-[700px]">
<WidgetsBackground v-if="backgroundData" :resources-data="backgroundData" /> <WidgetsBackground v-if="backgroundData" :resources-data="backgroundData" />
<div class="section-content"> <div class="section-content">
<WidgetsMainTitle <WidgetsMainTitle

View File

@@ -59,7 +59,7 @@ const onArrowClick = (direction, targetIndex) => {
</script> </script>
<template> <template>
<section class="section-container"> <section class="section-wrap">
<WidgetsBackground v-if="backgroundData" :resources-data="backgroundData" /> <WidgetsBackground v-if="backgroundData" :resources-data="backgroundData" />
<div class="section-content px-0"> <div class="section-content px-0">
<WidgetsMainTitle <WidgetsMainTitle
@@ -98,7 +98,7 @@ const onArrowClick = (direction, targetIndex) => {
</template> </template>
<style scoped> <style scoped>
.section-container { .section-wrap {
@apply before:hidden md:before:block before:content-[''] before:absolute before:top-0 before:left-0 before:w-[104px] before:h-full before:bg-gradient-to-l from-transparent to-[rgba(0,0,0,0.7)] before:z-[5] @apply before:hidden md:before:block before:content-[''] before:absolute before:top-0 before:left-0 before:w-[104px] before:h-full before:bg-gradient-to-l from-transparent to-[rgba(0,0,0,0.7)] before:z-[5]
after:hidden md:after:block after:content-[''] after:absolute after:top-0 after:right-0 after:w-[104px] after:h-full after:bg-gradient-to-r from-transparent to-[rgba(0,0,0,0.7)]; after:hidden md:after:block after:content-[''] after:absolute after:top-0 after:right-0 after:w-[104px] after:h-full after:bg-gradient-to-r from-transparent to-[rgba(0,0,0,0.7)];
} }

View File

@@ -9,9 +9,6 @@ interface Props {
const props = defineProps<Props>() const props = defineProps<Props>()
const { locale } = useI18n()
const { sendLog, useAnalyticsLogDataDirect } = useAnalytics()
const backgroundData = computed(() => const backgroundData = computed(() =>
getComponentGroup(props.components, 'background') getComponentGroup(props.components, 'background')
) )
@@ -27,17 +24,10 @@ const videoPlayData = computed(() =>
const buttonListData = computed(() => const buttonListData = computed(() =>
getComponentGroupAry(props.components, 'buttonList') getComponentGroupAry(props.components, 'buttonList')
) )
const handleSendLog = (index: number) => {
sendLog(
locale.value,
useAnalyticsLogDataDirect(buttonListData.value[index], props.pageVerTmplSeq)
)
}
</script> </script>
<template> <template>
<section class="section-container"> <section class="section-wrap">
<WidgetsBackground <WidgetsBackground
v-if="backgroundData" v-if="backgroundData"
:resources-data="backgroundData" :resources-data="backgroundData"

View File

@@ -5,7 +5,7 @@ import {
getComponentContainer, getComponentContainer,
} from '#layers/utils/dataUtil' } from '#layers/utils/dataUtil'
import { formatTimestamp } from '#layers/utils/formatUtil' import { formatTimestamp } from '#layers/utils/formatUtil'
import { getResolvedHost } from '#layers/utils/styleUtil' import { getImageHost } from '#layers/utils/styleUtil'
import type { PageDataTemplateComponents } from '#layers/types/api/pageData' import type { PageDataTemplateComponents } from '#layers/types/api/pageData'
import type { OperateGroupItem } from '#layers/types/api/resourcesData' import type { OperateGroupItem } from '#layers/types/api/resourcesData'
@@ -118,7 +118,7 @@ const onArrowClick = direction => {
<BlocksCardNews <BlocksCardNews
:title="item.title" :title="item.title"
:description="formatTimestamp(item.reg_dt, 'YYYY.MM.DD')" :description="formatTimestamp(item.reg_dt, 'YYYY.MM.DD')"
:img-path="getResolvedHost(item.img_path)" :img-path="getImageHost(item.img_path)"
:url="item.url" :url="item.url"
:link-target="item.link_target" :link-target="item.link_target"
class="slide-inner" class="slide-inner"

View File

@@ -33,7 +33,7 @@ const onArrowClick = direction => {
</script> </script>
<template> <template>
<section class="section-container"> <section class="section-wrap">
<BlocksSlideFade <BlocksSlideFade
v-if="slideData" v-if="slideData"
:arrows="true" :arrows="true"

View File

@@ -13,40 +13,35 @@ import type {
* @param path 이미지 경로 * @param path 이미지 경로
* @returns 완전한 이미지 URL * @returns 완전한 이미지 URL
*/ */
export const getImageHost = (path: string): string => { export const getImageHost = (
// path가 없으면 빈 문자열 반환 path: string,
if (!path || typeof path !== 'string') return '' options: { imageType?: 'common' | 'game' } = {}
): string => {
if (!path) return ''
if (/^(https?:\/\/|www\.)/.test(path)) return path
const config = useRuntimeConfig() const config = useRuntimeConfig()
const { imageType = 'game' } = options
const { staticUrl, runType } = config.public
const isDev = process.env.NODE_ENV === 'development' const isDevelopment = process.env.NODE_ENV === 'development'
const rootPath = isDev ? '' : `${config.public.staticUrl}` const isCommon = imageType === 'common'
return `${rootPath}${path}` // * [TODO] 수정 필요 : 게임별 이미지 로컬에 추가 필요.
if (!isCommon) {
return `${staticUrl}${path}`
} }
/** // 개발 환경일 때는 루트 경로 생략
* [TODO] 수정 필요 if (isDevelopment) return path
* 이미지 경로를 완전한 호스트 URL로 변환합니다.
* @param path 이미지 경로
* @returns 완전한 이미지 URL
*/
export const getResolvedHost = (path: string): string => {
// path가 없으면 빈 문자열 반환
if (!path || typeof path !== 'string') return ''
if ( // 공통/게임 여부에 따른 경로 결정
path.startsWith('http://') || const basePath = isCommon
path.startsWith('https://') || ? `${staticUrl}/${runType}/templates/brand`
path.startsWith('www.') : staticUrl
) {
return path
}
const config = useRuntimeConfig() return `${basePath}${path}`
const rootPath = config.public.staticUrl
return `${rootPath}${path}`
} }
/** /**
@@ -75,8 +70,8 @@ export const getDeviceSrc = (
if (!pcPath && !mobilePath) return null if (!pcPath && !mobilePath) return null
const resolvedImages = { const resolvedImages = {
pc: pcPath ? getResolvedHost(pcPath) : '', pc: pcPath ? getImageHost(pcPath) : '',
mobile: mobilePath ? getResolvedHost(mobilePath) : '', mobile: mobilePath ? getImageHost(mobilePath) : '',
} }
return { return {