diff --git a/client/public/assets/casper-custom/sticker/charge-max.png b/client/public/assets/casper-custom/sticker/charge-max.png deleted file mode 100644 index 4e5e13a8..00000000 Binary files a/client/public/assets/casper-custom/sticker/charge-max.png and /dev/null differ diff --git a/client/public/assets/casper-custom/sticker/charge-max.svg b/client/public/assets/casper-custom/sticker/charge-max.svg new file mode 100644 index 00000000..5635c085 --- /dev/null +++ b/client/public/assets/casper-custom/sticker/charge-max.svg @@ -0,0 +1,8 @@ + + + + + + + + diff --git a/client/public/assets/casper-custom/sticker/charge-none.png b/client/public/assets/casper-custom/sticker/charge-none.png deleted file mode 100644 index 9da6e528..00000000 Binary files a/client/public/assets/casper-custom/sticker/charge-none.png and /dev/null differ diff --git a/client/public/assets/casper-custom/sticker/charge-none.svg b/client/public/assets/casper-custom/sticker/charge-none.svg new file mode 100644 index 00000000..f77b3507 --- /dev/null +++ b/client/public/assets/casper-custom/sticker/charge-none.svg @@ -0,0 +1,22 @@ + + + + + + + + + + + + + + + + + + + + + + diff --git a/client/public/assets/casper-custom/sticker/electric.png b/client/public/assets/casper-custom/sticker/electric.png deleted file mode 100644 index 1f770fa7..00000000 Binary files a/client/public/assets/casper-custom/sticker/electric.png and /dev/null differ diff --git a/client/public/assets/casper-custom/sticker/electric.svg b/client/public/assets/casper-custom/sticker/electric.svg new file mode 100644 index 00000000..7effe3b5 --- /dev/null +++ b/client/public/assets/casper-custom/sticker/electric.svg @@ -0,0 +1,462 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/client/public/assets/casper-custom/sticker/lovely.png b/client/public/assets/casper-custom/sticker/lovely.png deleted file mode 100644 index 0c8213d7..00000000 Binary files a/client/public/assets/casper-custom/sticker/lovely.png and /dev/null differ diff --git a/client/public/assets/casper-custom/sticker/lovely.svg b/client/public/assets/casper-custom/sticker/lovely.svg new file mode 100644 index 00000000..a9868378 --- /dev/null +++ b/client/public/assets/casper-custom/sticker/lovely.svg @@ -0,0 +1,716 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/client/public/assets/casper-custom/sticker/twinkle.png b/client/public/assets/casper-custom/sticker/twinkle.png deleted file mode 100644 index 1cadd1ce..00000000 Binary files a/client/public/assets/casper-custom/sticker/twinkle.png and /dev/null differ diff --git a/client/public/assets/casper-custom/sticker/twinkle.svg b/client/public/assets/casper-custom/sticker/twinkle.svg new file mode 100644 index 00000000..e7eb5f0c --- /dev/null +++ b/client/public/assets/casper-custom/sticker/twinkle.svg @@ -0,0 +1,1081 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/client/src/constants/CasperCustom/casper.ts b/client/src/constants/CasperCustom/casper.ts index 6194326d..0adfae47 100644 --- a/client/src/constants/CasperCustom/casper.ts +++ b/client/src/constants/CasperCustom/casper.ts @@ -1,3 +1,5 @@ +import { ColorOptionType, StickerOptionType } from "@/types/casperCustom"; + export const CUSTOM_OPTION = { EYES: "eyes", EYES_DIRECTION: "eyesDirection", @@ -47,7 +49,7 @@ export const COLOR_OPTION = { R_AMBER: "#FFD96B", R_YELLOW: "#FEFF78", } as const; -const STICKER_OPTION = { +export const STICKER_OPTION = { ELECTRIC: "electric", CHARGE_MAX: "charge-max", CHARGE_NONE: "charge-none", @@ -80,6 +82,43 @@ export const COLOR_BACKGROUND_MAP = [ COLOR_OPTION.R_LIGHTBLUE, ] as const; +export const STICKER_COLOR_MAP = { + [STICKER_OPTION.CHARGE_MAX]: { + default: "#515867", + exception: "#333741", + }, + [STICKER_OPTION.CHARGE_NONE]: { + default: "#5CDD6A", + exception: "#FEFF78", + }, + [STICKER_OPTION.ELECTRIC]: { + default: "#FEFF78", + exception: "#FEFF78", + }, + [STICKER_OPTION.LOVELY]: { + default: "#FF6EB0", + exception: "#11CCF2", + }, + [STICKER_OPTION.TWINKLE]: { + default: "#11CCF2", + exception: "#FEFF78", + }, +} as const; + +export const COLOR_STICKER_EXCEPTION: Partial> = { + [COLOR_OPTION.C_SILVER]: STICKER_OPTION.CHARGE_MAX, + [COLOR_OPTION.R_PURPLE]: STICKER_OPTION.CHARGE_MAX, + [COLOR_OPTION.R_ORANGE]: STICKER_OPTION.CHARGE_NONE, + [COLOR_OPTION.R_INDIGO]: STICKER_OPTION.CHARGE_NONE, + [COLOR_OPTION.R_LIGHTBLUE]: STICKER_OPTION.LOVELY, + [COLOR_OPTION.R_AMBER]: STICKER_OPTION.LOVELY, + [COLOR_OPTION.R_MAGENTA]: STICKER_OPTION.TWINKLE, + [COLOR_OPTION.R_YELLOW]: STICKER_OPTION.TWINKLE, + [COLOR_OPTION.C_BLACK]: STICKER_OPTION.TWINKLE, + [COLOR_OPTION.R_DEEPPURPLE]: STICKER_OPTION.TWINKLE, + [COLOR_OPTION.C_ORANGE]: STICKER_OPTION.TWINKLE, +}; + export const CASPER_Z_INDEX = { CASPER: 2, UNDER_CASPER: 1, diff --git a/client/src/features/CasperCustom/CasperCard/CasperCardFrontUI.tsx b/client/src/features/CasperCustom/CasperCard/CasperCardFrontUI.tsx index b4a242e1..bef524d2 100644 --- a/client/src/features/CasperCustom/CasperCard/CasperCardFrontUI.tsx +++ b/client/src/features/CasperCustom/CasperCard/CasperCardFrontUI.tsx @@ -8,11 +8,14 @@ import { CASPER_SIZE_OPTION, CASPER_Z_INDEX, COLOR_BACKGROUND_MAP, + COLOR_STICKER_EXCEPTION, CUSTOM_OPTION, + STICKER_COLOR_MAP, } from "@/constants/CasperCustom/casper"; import { SelectedCasperIdxType } from "@/types/casperCustom"; import { getCasperEyesComponent } from "@/utils/CasperCustom/getCasperEyesComponent"; import { getCasperMouthComponent } from "@/utils/CasperCustom/getCasperMouthComponent"; +import { getCasperStickerComponent } from "@/utils/CasperCustom/getCasperStickerComponent"; import CasperEyesLayout from "/public/assets/casper-custom/eyes/layout.svg?react"; import CasperFace from "/public/assets/casper-custom/face.svg?react"; @@ -67,6 +70,10 @@ function CasperCardFrontUI({ CASPER_OPTION[CUSTOM_OPTION.EYES_DIRECTION][selectedEyesDirectionIdx]; const selectedMouth = CASPER_OPTION[CUSTOM_OPTION.MOUTH][selectedMouthIdx]; const selectedColor = CASPER_OPTION[CUSTOM_OPTION.COLOR][selectedColorIdx]; + const selectedSticker = + selectedStickerIdx !== null + ? CASPER_OPTION[CUSTOM_OPTION.STICKER][selectedStickerIdx] + : null; const { CARD_WIDTH, CARD_HEIGHT } = CASPER_CARD_SIZE[size]; const { @@ -85,6 +92,20 @@ function CasperCardFrontUI({ selectedEyesDirection.id ); const CasperMouthSvgComponent = getCasperMouthComponent(selectedMouth.id); + const CasperStickerSvgComponent = getCasperStickerComponent( + selectedSticker !== null ? selectedSticker.id : null + ); + + const getStickerColor = () => { + if (!selectedSticker) { + return ""; + } + + const isException = COLOR_STICKER_EXCEPTION[selectedColor.id] === selectedSticker.id; + return isException + ? STICKER_COLOR_MAP[selectedSticker.id].exception + : STICKER_COLOR_MAP[selectedSticker.id].default; + }; return (
- {CasperEyesSvgComponent && ( - - )} - {CasperMouthSvgComponent && ( - - )} + +
- {selectedStickerIdx !== null && ( - 캐스퍼 일렉트릭 봇 스티커 )} diff --git a/client/src/types/casperCustom.ts b/client/src/types/casperCustom.ts index e5fac514..945e4369 100644 --- a/client/src/types/casperCustom.ts +++ b/client/src/types/casperCustom.ts @@ -1,5 +1,18 @@ import { Dispatch } from "react"; -import { CUSTOM_OPTION } from "@/constants/CasperCustom/casper"; +import { + COLOR_OPTION, + CUSTOM_OPTION, + EYES_OPTION, + MOUTH_OPTION, + POSITION_OPTION, + STICKER_OPTION, +} from "@/constants/CasperCustom/casper"; + +export type ColorOptionType = (typeof COLOR_OPTION)[keyof typeof COLOR_OPTION]; +export type StickerOptionType = (typeof STICKER_OPTION)[keyof typeof STICKER_OPTION]; +export type EyesOptionType = (typeof EYES_OPTION)[keyof typeof EYES_OPTION]; +export type EyesDirectionOptionType = (typeof POSITION_OPTION)[keyof typeof POSITION_OPTION]; +export type MouthOptionType = (typeof MOUTH_OPTION)[keyof typeof MOUTH_OPTION]; export type CustomOptionType = (typeof CUSTOM_OPTION)[keyof typeof CUSTOM_OPTION]; type CasperFaceKeys = Exclude; diff --git a/client/src/utils/CasperCustom/getCasperEyesComponent.tsx b/client/src/utils/CasperCustom/getCasperEyesComponent.tsx index bf1fbdb8..a0338402 100644 --- a/client/src/utils/CasperCustom/getCasperEyesComponent.tsx +++ b/client/src/utils/CasperCustom/getCasperEyesComponent.tsx @@ -1,4 +1,4 @@ -import { EYES_OPTION, POSITION_OPTION } from "@/constants/CasperCustom/casper"; +import { EyesDirectionOptionType, EyesOptionType } from "@/types/casperCustom"; import Alloy15Center from "/public/assets/casper-custom/eyes/15inch-alloy-center.svg?react"; import Alloy15Left from "/public/assets/casper-custom/eyes/15inch-alloy-left.svg?react"; import Alloy15Right from "/public/assets/casper-custom/eyes/15inch-alloy-right.svg?react"; @@ -24,13 +24,7 @@ import VacantCenter from "/public/assets/casper-custom/eyes/vacant-center.svg?re import VacantLeft from "/public/assets/casper-custom/eyes/vacant-left.svg?react"; import VacantRight from "/public/assets/casper-custom/eyes/vacant-right.svg?react"; -type EyesOptionType = (typeof EYES_OPTION)[keyof typeof EYES_OPTION]; -type EyesDirectionOptionType = (typeof POSITION_OPTION)[keyof typeof POSITION_OPTION]; - -const EYES_COMPONENT_MAP: Record< - string, - React.ComponentType> | null -> = { +const EYES_COMPONENT_MAP: Record>> = { "15inch-alloy-center": Alloy15Center, "15inch-alloy-left": Alloy15Left, "15inch-alloy-right": Alloy15Right, @@ -60,7 +54,7 @@ const EYES_COMPONENT_MAP: Record< export function getCasperEyesComponent( eyesOption: EyesOptionType, eyesDirectionOption: EyesDirectionOptionType -): React.ComponentType> | null { +): React.ComponentType> { const componentKey = `${eyesOption}-${eyesDirectionOption}`; return EYES_COMPONENT_MAP[componentKey]; } diff --git a/client/src/utils/CasperCustom/getCasperMouthComponent.tsx b/client/src/utils/CasperCustom/getCasperMouthComponent.tsx index cd56ac04..85a31df6 100644 --- a/client/src/utils/CasperCustom/getCasperMouthComponent.tsx +++ b/client/src/utils/CasperCustom/getCasperMouthComponent.tsx @@ -1,23 +1,20 @@ -import { MOUTH_OPTION } from "@/constants/CasperCustom/casper"; +import { MouthOptionType } from "@/types/casperCustom"; import Cloudy from "/public/assets/casper-custom/mouth/cloudy.svg?react"; import Expressionsless from "/public/assets/casper-custom/mouth/expressionless.svg?react"; import Laugh from "/public/assets/casper-custom/mouth/laugh.svg?react"; import Mocking from "/public/assets/casper-custom/mouth/mocking.svg?react"; import Smile from "/public/assets/casper-custom/mouth/smile.svg?react"; -type MouthOptionType = (typeof MOUTH_OPTION)[keyof typeof MOUTH_OPTION]; - -const mouthComponentMap: Record> | null> = - { - cloudy: Cloudy, - expressionless: Expressionsless, - laugh: Laugh, - mocking: Mocking, - smile: Smile, - }; +const mouthComponentMap: Record>> = { + cloudy: Cloudy, + expressionless: Expressionsless, + laugh: Laugh, + mocking: Mocking, + smile: Smile, +}; export function getCasperMouthComponent( mouth: MouthOptionType -): React.ComponentType> | null { +): React.ComponentType> { return mouthComponentMap[mouth]; } diff --git a/client/src/utils/CasperCustom/getCasperStickerComponent.tsx b/client/src/utils/CasperCustom/getCasperStickerComponent.tsx new file mode 100644 index 00000000..3e1732d1 --- /dev/null +++ b/client/src/utils/CasperCustom/getCasperStickerComponent.tsx @@ -0,0 +1,26 @@ +import { StickerOptionType } from "@/types/casperCustom"; +import ChargeMax from "/public/assets/casper-custom/sticker/charge-max.svg?react"; +import ChargeNone from "/public/assets/casper-custom/sticker/charge-none.svg?react"; +import Electric from "/public/assets/casper-custom/sticker/electric.svg?react"; +import Lovely from "/public/assets/casper-custom/sticker/lovely.svg?react"; +import Twinkle from "/public/assets/casper-custom/sticker/twinkle.svg?react"; + +const STICKER_COMPONENT_MAP: Record< + string, + React.ComponentType> | null +> = { + "charge-max": ChargeMax, + "charge-none": ChargeNone, + electric: Electric, + lovely: Lovely, + twinkle: Twinkle, +}; + +export function getCasperStickerComponent( + sticker: StickerOptionType | null +): React.ComponentType> | null { + if (sticker === null) { + return null; + } + return STICKER_COMPONENT_MAP[sticker]; +}