Skip to content

Conversation

@Chiman2937
Copy link
Collaborator

@Chiman2937 Chiman2937 commented Jun 9, 2025

✨ 작업 내용

💡작업 내용을 이해하기 위해 알아야 할 내용

변경사항 설명에 앞서, 현재 롤링페이퍼 POST Request 구조에 대해 설명합니다.

파일을 직접 사용하는 방법만 보고 싶으신 분들은 파일 사용 방법란으로 이동하세요.


❔기존:

backgroundColor는 beige, purple, blue, green이라는 고유의 key 값만 저장이 가능했습니다.
image

backgroundURL은 유효한 url 주소만 입력 or null값만 입력이 가능합니다.
image

따라서,

기존에 컬러를 선택했을 경우에는 backgroundURL은 null로 처리
backgroundColor는 4가지 key 중 한개를 선택하여 request를 보냈습니다.

{
  backgroundColor: 'purple', //key 중 하나인 purple이라는 string 값 자체를 지정합니다.
  backgroundImageURL: null, //컬러를 선택했을 경우에는 기본값으로 null을 지정합니다.
}

기존에 이미지를 선택했을 경우에는 서버에서 실제 저장된 이미지만 이용했기 때문에 선택한 imageUrl을 그대로 request 보냅니다.

{
  backgroundColor: 'beige' //이미지를 선택했을 경우에는 기본키값으로 beige를 지정합니다.
  backgroundImageURL: 'https://...' //실제 Rolling api 백엔드 서버에 저장된 imageUrl
}

❗변경:

  1. 커스텀 색상 선택 기능 구현

기본 색상 말고 커스텀 색상을 선택할 수 있는 기능을 구현하기 위해서는 backgroundColor 필드에 request를 보내는 방식을 이용할 수 없었기 때문에
색상 자체를 이미지로 변환하여 cloudinary에 저장하고, backgroundImageURL에 색상이미지 경로를 넣어 request를 보내는 방식으로 구현했습니다.

색상 선택 => 색상 자체를 이미지객체로 만들어 클라우드에 이미지 저장 => 클라우드에 저장된 이미지 Url을 Rolling Api에 request 전송
{
  backgroundColor: 'beige' //항상 기본값을 beige로 사용합니다.
  backgroundImageURL: 'https://res.cloudinary.com/.../colors/4b2a2a.png' //type은 colors이고, 색상은 #4b2a2a 입니다.
  //#FFFFFF 와 같은 단색을 가진 이미지를 만들어 request를 보냅니다.
}
  1. 로컬에서 직접 이미지 선택 기능 구현

로컬에서 직접 이미지를 선택해 등록하는 기능을 구현하기 위해서는 backgroundImageURL 필드에 파일 객체를 바로 request 보내 등록하는 방식을 이용할 수 없었기 때문에
로컬에서 선택한 이미지 객체를 cloudinary이 저장하여 웹 주소를 return 받고, 이 주소를 backgroundImageURL에 이미지 경로를 넣어 REQUEST를 보내는 방식으로 구현했습니다.

{
  backgroundColor: 'beige' //항상 기본값을 beige로 사용합니다.
  backgroundImageURL: 'https://res.cloudinary.com/.../images/파일명' //type은 images이고, 파일명은 랜덤입니다.
}

❓그래서?

이제 post 데이터를 가지고 실제 list 페이지와 post/{id} 페이지에 색상/이미지를 표현해 줄 때, 경우의 수가 이렇게 나뉩니다.

1. backgroundImageURL이 null 일때

  • backgroundColor의 key값에 대응하는 color를 이용해 스타일 지정하기
  const style = {
    backgroundColor: `var(--color-${backgroundColor}-200)`,
  }

2. backgroundImageURL이 일반 이미지일때

  • 바로 backgroundImage에 적용하기
  const style = {
    backgroundImage: `url(${backgroundImageURL})`,
  }

3. backgroundImageURL이 Cloudinary에 저장된 Color형태의 이미지일때

  • backgroundImageUrl이 Cloudinary의 colors type인 이미지일 경우 파일명에서 색상정보를 불러와 스타일 지정하기
  const style = {
     backgroundColor: getColorFromCloudinaryImageUrl(backgroundImageURL),
  }

4. backgroundImageURL이 Cloudinary에 저장된 Image형태의 이미지일때

  • backgroundImageUrl이 Cloudinary의 image type인 이미지일 경우 바로 backgroundImage에 적용하기
  const style = {
    backgroundImage: `url(${backgroundImageURL})`,
  }

💡 getBackgroundStylesFromPostData.js

getBackgroundStylesFromPostData는 배경이미지 자체에 지정할 스타일을 정해 return 해주는 함수입니다.

//backgroundImageURL이 null 일 경우
  backgroundStyle = {
    backgroundColor: 'var(--color-purple-200',
    backgroundImage: 'none',
    backgroundRepeat: 'no-repeaet',
    backgroundPosition: 'center',
    backgroundSize: 'cover',
  };

//색상 type일 경우 return
  backgroundStyle = {
    backgroundColor: '#FFFFFF' //Cloudinary에서 색상값 추출해서 지정해줍니다.
    backgroundImage: 'none',
    backgroundRepeat: 'no-repeaet',
    backgroundPosition: 'center',
    backgroundSize: 'cover',
  };

//이미지 type일 경우 return
  backgroundStyle = {
    backgroundColor: 'none'
    backgroundImage: 'https://...', //response받은 이미지 경로를 지정합니다.
    backgroundRepeat: 'no-repeaet',
    backgroundPosition: 'center',
    backgroundSize: 'cover',
  };

💡getBackgroundStylesFromPostData.js 사용 방법

list 페이지의 경우 ItemCard.jsx

  const backgroundStyle = getBackgroundStylesFromPostData({ backgroundColor, backgroundImageURL });

  return (
    <Link to={`/post/${id}`} className={styles['item-card__link']}>
      <div className={styles['item-card']} style={backgroundStyle}> {/*이 부분에 style로 지정해주세요*/}
        <div className={styles['item-card__content']} style={contentStyle}>

post/{id} 페이지의 경우 RollingPaperItemPage.jsx
기존 코드에서 아래처럼 변경만 해주시면 됩니다. (주석이 기존코드)

  const containerStyle = getBackgroundStylesFromPostData({
    backgroundColor: recipientData?.backgroundColor,
    backgroundImageURL: recipientData?.backgroundImageURL,
  });

  // const containerStyle = {
  //   backgroundColor: !recipientData?.backgroundImageURL
  //     ? COLOR_STYLES[recipientData?.backgroundColor]?.primary
  //     : '',
  //   backgroundImage: recipientData?.backgroundImageURL
  //     ? `url(${recipientData?.backgroundImageURL})`
  //     : 'none',
  //   backgroundRepeat: 'no-repeat',
  //   backgroundPosition: 'center',
  //   backgroundSize: 'cover',
  // };

💡getIsDark.js

getIsDark는 이미지 hex값(ex. #FFFFFF)가 어두운 색인지, 밝은 색인지 계산하여 return 해주는 함수입니다.
이 함수의 필요성은 getContentStylesFromPostData.js 에서 설명하겠습니다.

💡getContentStylesFromPostData.js

getContentStylesFromPostData.js 는 List 페이지의 카드의 스타일을 지정해주는 함수입니다.

지정해야 할 스타일은 3가지로 나뉩니다.

  1. 배경이 밝은 색상일 경우
  • 배경이 밝은 색상일 경우 기존 스타일만 적용합니다.
    image
  1. 배경이 어두운 색상일 경우
  • 배경이 어두운 색상일 경우 흰색 텍스트만 적용합니다.
    image
  1. 배경이 이미지일 경우
  • 배경이 이미지일 경우 흰색 텍스트, 투명도가 있는 검정색 Overlay를 적용합니다.
    image

getContentStylesFromPostData.js는 스타일을 이렇게 3가지로 나누고, 각 유형에 맞는 스타일을 return 해줍니다.
기본적인 검증 방식은 getBackgroundStylesFromPostData.js와 동일합니다.

  // 
  const contentNormalColorStyle = {};

  const contentDarkColorStyle = {
    color: `var(--color-white)`,
  };

  const contentImageStyle = {
    color: `var(--color-white)`,
    background: `linear-gradient(180deg, rgba(0, 0, 0, 0.54) 0%, rgba(0, 0, 0, 0.54) 100%)`,
  };

💡getContentStylesFromPostData.js 사용방법

List페이지의 경우 (ItemCard.jsx)

  // 밝은 색: 검정 텍스트
  // 어두운 색: 하얀색 텍스트
  // 이미지: 하얀색 텍스트 / 어두운색 overlay 적용
  const contentStyle = getContentStylesFromPostData(backgroundImageURL);

    <Link to={`/post/${id}`} className={styles['item-card__link']}>
      <div className={styles['item-card']} style={backgroundStyle}>
        <div className={styles['item-card__content']} style={contentStyle}> {/*이 요소에 스타일 적용해주세요*/}
          <h3 className={styles['item-card__title']}>To. {name}</h3>

💡 최종적으로 프로젝트에 적용하는 방법

아래 내용만 보고 그대로 적용하셔도 됩니다.

ItemCard.jsx

  // 배경 설정: 이미지가 있으면 이미지, 없으면 컬러
  // const backgroundStyle = backgroundImageURL
  //   ? {
  //       backgroundImage: `url(${backgroundImageURL})`,
  //       backgroundSize: 'cover',
  //       backgroundPosition: 'center',
  //     }
  //   : {
  //       backgroundColor: `var(--color-${backgroundColor}-200)`,
  //     };

  // 이미지 배경인 경우 텍스트를 흰색으로 바꾸는 클래스
  // const contentClass = backgroundImageURL
  //   ? `${styles['item-card__content']} ${styles['item-card__content--image']}`
  //   : styles['item-card__content'];


  // 배경 설정: 이미지가 있으면 이미지, 없으면 컬러
  const backgroundStyle = getBackgroundStylesFromPostData({ backgroundColor, backgroundImageURL });

  // 밝은 색: 검정 텍스트
  // 어두운 색: 하얀색 텍스트
  // 이미지: 하얀색 텍스트 / 어두운색 overlay 적용
  const contentStyle = getContentStylesFromPostData(backgroundImageURL);

  // 최근 메시지 중 상위 3개만 가져오기
  const topThree = recentMessages.slice(0, 3);
  // 남은 작성자 수 계산
  const extraCount = Math.max(0, messageCount - topThree.length);

  return (
    <Link to={`/post/${id}`} className={styles['item-card__link']}>
      <div className={styles['item-card']} style={backgroundStyle}>
        {/*<div className={contentClass}>*/}
        <div className={styles['item-card__content']} style={contentStyle}>
          <h3 className={styles['item-card__title']}>To. {name}</h3>
          <p className={styles['item-card__meta']}>{messageCount}명이 작성했어요!</p>

          {/* 최대 3개 프로필 표시 */}
          {topThree.length > 0 && (
            <div className={styles['item-card__avatars']}>

RollingPaperItemPage.jsx

  const containerStyle = getBackgroundStylesFromPostData({
    backgroundColor: recipientData?.backgroundColor,
    backgroundImageURL: recipientData?.backgroundImageURL,
  });

  // const containerStyle = {
  //   backgroundColor: !recipientData?.backgroundImageURL
  //     ? COLOR_STYLES[recipientData?.backgroundColor]?.primary
  //     : '',
  //   backgroundImage: recipientData?.backgroundImageURL
  //     ? `url(${recipientData?.backgroundImageURL})`
  //     : 'none',
  //   backgroundRepeat: 'no-repeat',
  //   backgroundPosition: 'center',
  //   backgroundSize: 'cover',
  // };

🔗 관련 이슈

Fixes #95

@vercel
Copy link

vercel bot commented Jun 9, 2025

The latest updates on your projects. Learn more about Vercel for Git ↗︎

Name Status Preview Comments Updated (UTC)
team2-rolling-app ✅ Ready (Inspect) Visit Preview 💬 Add feedback Jun 9, 2025 4:18pm

@Chiman2937 Chiman2937 changed the title feat: 롤링페이퍼 POST 데이터에 따라 자동으로 스타일 객체 반환하는 함수 제작 [Feat] 롤링페이퍼 POST 데이터에 따라 자동으로 스타일 객체 반환하는 함수 제작 Jun 9, 2025
Copy link
Collaborator

@looseeyeon looseeyeon left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

고생하셨습니다! 확인했습니다~!

@Chiman2937 Chiman2937 merged commit 18e50be into main Jun 10, 2025
2 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

롤링페이퍼 POST 데이터에 따라 자동으로 스타일 객체 반환하는 함수 제작

3 participants