한 아이콘이 있다. 그 부분에 마우스를 갖다 댔을 때 아이콘이 다른 아이콘으로 변경되기를 원했다. 매우 간절.
나는 한 아이콘을 흰색 버전 / 검정 버전으로 이미지 2개를 저장하고, 흰 아이콘을 처음에 보여준 후 hover 했을 때 검정 아이콘으로 바뀌도록 코드를 짰다.
CSS로는 classname 로 스타일 주거나, 삼항연산자로 조건을 걸어주거나, 부모 요소와 자식 요소를 결합하며 >
기호 쓰는 등 .. 하면 되는데 Styled-component로는 어떻게 해야 할지 몰라서 검색을 했고 결과적으로 hover 했을 때 content 에 이미지 경로를 작성하면 된다고 한다.
width: 50px;
cursor: pointer;
&:hover {
content: url('images/icon/github-bk.png');
}
이렇게 말이다!
그런데 나는 스무스하게 이미지가 변경되기를 원해서 transition 로 단순하게 꾸며주면 된다고 생각했는데 왜인지 계속 스타일이 안먹혔다. GPT에 물어보기도 하고 검색해서 나오는 웬만한 코드는 다 적용해보았는데 계속 안되었다.
Maybe.. 🤔 내가 판단한 이유는 이미지끼리 변환돼서인 것 같았다. 예를 들어 적용했었던 코드 중 몇몇을 보면 보면,
//JS
<a
href="https://github.com/zunyange"
target="_blank"
rel="noreferrer noopener"
>
<S.GoToGithub src="/images/icon/github.png" alt="Github" />
</a>
//Styled-component
export const 부모 = styled.div`
position: relative;
`;
export const GoToGithub = styled.img`
width: 50px;
cursor: pointer;
position: absolute;
top: 0px;
left: 0px;
opacity: 0;
transition: opacity 0.5s linear;
&:hover {
content: url('images/icon/github-bk.png');
opacity: 1;
}
`;
부모에 relative 를 주고 top, left로 위치 지정 후(왜인지는 모르겠다), hover 전에 opacity 를 0으로 준다. 그리고 hover시에 opacity 를 1로 하여 이미지를 변경하는 과정에서 transition 이 적용될 것이다. 그런데 ,, 잘 되는 듯 싶지만 처음에 이미지가 아예 보이지가 않는다.
왜냐? opacity : 0
이니깐 ..
그래서 hover 전에도 opacity : 1
를 한다 해도 transition 이 적용되지 않고 뚝딱뚝딱 이미지가 바뀔 뿐이다 ..
//Styled-component
export const GoToGithub = styled.img`
width: 50px;
cursor: pointer;
transition: opacity 0.8s;
&:hover {
animation: fadeImage 1s;
}
@keyframes fadeImage {
0% {
opacity: 1;
}
50% {
content: url('images/icon/github-bk.png');
opacity: 0.5;
}
100% {
content: url('images/icon/github-bk.png');
opacity: 1;
}
}
`;
이 방법도 잘 되는 듯 싶지만 마우스를 잘 보면 마우스가 계속 hover 돼있다면 검정 아이콘에서 멈춰야 하는데 다시 원래 흰색 아이콘로 돌아오는 문제점이 있었다. 그 외에도 아래와 같은 수많은 방법을 시도해보았다.
transition: all 0.5s ease;
&:hover {
content: url('images/github-bk.png');
}
transition 안됨.
transition: all 0.5s;
&:hover {
content: url('images/github-bk.png');
transition: all 0.5s;
}
transition 안됨22.
transition: 1s ease;
&:hover {
content: url('images/github-bk.png');
transition: 1s ease;
}
transition 안됨33.
transition 을 어떻게 적느냐는 중요한 게 아니군!!
export const GoToGithub = styled.img`
width: 50px;
cursor: pointer;
-webkit-transition: 0.5s ease-in-out;
transition: 0.5s ease-in-out;
&:hover {
content: url('images/github-bk.png');
}
`;
// OR
export const GoToGithub = styled.img`
width: 50px;
cursor: pointer;
transition: 0.5s ease-in-out;
&:hover {
content: url('images/github-bk.png');
-webkit-transition: 0.5s ease-in-out;
transition: 0.5s ease-in-out;
}
`;
// OR
export const GoToGithub = styled.img`
width: 50px;
cursor: pointer;
-webkit-transition: 0.5s ease-in-out;
transition: 0.5s ease-in-out;
&:hover {
content: url('images/github-bk.png');
-webkit-transition: 0.5s ease-in-out;
transition: 0.5s ease-in-out;
}
`;
세 가지 모두 안된다. 😭
이렇게 하나하나씩 코드를 수정해가며 원인을 알아보려 했는데 성공한 결과물이 없어 이렇게 문제 해결 과정을 적어보려 한다..
반드시 해결해낸다는 마음으로 .. !! 내가 원하는 디자인 컨셉?이 있는데 뚝딱거리는 스타일보다는 부드럽게 영롱한😉 느낌을 주고 싶었기 때문이다.
다시 검색하면서 느낀게 있다.
사실 처음에 자바스크립트를 배운다면 css 혹은 sass 로 스타일 주는 것이 기본적이고, 검색을 할 때에도 Styled-component 보다는 css 방법이 대부분이다. 그런데 내가 왜 조건을 스타일드라고 부가적으로 검색하지 않고 무작정 "CSS 마우스 오버시 이미지 변환" 이라고 했을까?!
아직까지 뭔가 Styled-component가 완벽하게 100% 이해되지 않은 것도 있고, CSS 로 검색나온거 보고 활용해야지~ 응용해야지~ 라고 생각은 하지만 제대로 설명은 읽지 않고 코드만 일단 내놔!! 일단 복붙해보고 되면 공부해보자는 마음으로 서치를 했던 것 같다. 그래서인지 차근차근 다시 방법을 찾아보며, 리액트는 아니더라도 html & css 로 이미지 변환한 어떤 코드를 보고 아하! 느낀 점이 있다.
이 분의 설명으로는 "div 에 이미지를 2개 포개놓고 div 에 마우스 오버시 opacity:0; 을 줘서 위에 있는 이미지를 가려주는 식으로 처리하는게 가장 간단할듯 하다" 였다.
그러면 나도 hover했을 때 content 속성에 이미지 경로를 넣지 말고 처음부터 자바스크립트 파일에 이미지를 두개 넣으면 되겠네 !! 라는 생각이 번쩍 들었다.
오케이 해보겠숴.
//js
<S.GoTo>
<a
href="https://github.com/zunyange"
target="_blank"
rel="noreferrer noopener">
<S.GoToGithub src="/images/icon/github.png" alt="Github" />
<S.GoToBlack src="/images/icon/github-bk.png" alt="Github" />
</a>
</S.GoTo>
//Styled-component
export const GoToGithub = styled.img`
width: 50px;
cursor: pointer;
transition: 1s;
${GoTo} :hover & {
display: none;
}
`;
export const GoToBlack = styled.img`
width: 50px;
display: none;
${GoTo} :hover & {
display: block;
}
`;
🛠 GoToGithub 태그에 마우스 오버시 opacity가 0으로 설정되고 점차 희미해지며 GoToBlack 태그의 display가 block 및 opacity가 1로 설정되고 점차 페이드 인되는 코드이다. 하지만 여전히 transition 이 안된다. ㅜ_ㅜ 기대했는데 너무 괴롭다.. 분명 방법이 있을텐데 😵
🛠 혹은 onMouseEnter onMouseLeave 프로퍼티를 사용하고 해당 프로퍼티에 state 값을 true / false 로 트리거를 만든 다음 조건부로 렌더링 시키고, 트랜지션을 주입하는 방법도 있다지만 잘 되지 않았다.
//js
<a href="https://github.com/zunyange">
<S.GoToGithub src="/images/icon/github.png" alt="Github" />
</a>
//Styled-component
export const GoToGithub = styled.img`
cursor: pointer;
transition: 1s;
&:hover {
filter: invert(100%);
}
`;
filter 를 사용해서 색깔이나 대비, 블러처리, 그림자 등 이미지에 여러 효과를 줄 수 있다고 한다. 여기서 filter: invert(100%)
는 내가 원하는대로 흰 아이콘에서 검은 아이콘으로 잘 바꼈고, 내가 처음 시도했던 content 이미지 경로가 없어서 transition 도 잘 동작한다!!
그렇게 기쁜 마음에 다른 이미지들도 똑같이 하려 했는데,.. 두번째 이미지는 이번엔 흰 아이콘에서 초록 아이콘이 되길 원했다 ...(Velog 로고)
filter 로 검정색 뿐만 아니라 원하는 색으로 언제든 변경이 가능하다고 알고 있어서 초록으로 바뀌는 코드인 filter: hue-rotate(160deg)
를 해보았는데 .. 다른 색으로 바뀌는 것도 아닌 hover를 해도 계속 흰 아이콘 그대로 였다. 그 외에도 수많은 시도와 gpt와의 대화를 했지만 실패가 거듭되어 지쳐버렸다. 커뮤니티에도 질문을 해보았는데 그나마 2번 방법이 최대 실적이다. 마침 처음 내 의도도 모든 흰 아이콘을 검정으로 바뀌게 하는 거였는데, Velog 나 Linkedin 같이 고유의 색깔이 있는 아이콘은 가시적으로도 의미가 잘 보일 것 같아 수정한 거였는데 다시 바꾸지 뭐 ^-^
늘 문제를 해결하는데 있어서 과정을 까먹지 않으려고 생각나는대로 말하려다 보니 (며칠을 걸쳐서 해결하고 있어서) 너무 횡설수설 말을 하는 것 같은데 결과적으로는 해결하는게 우선이니까 ..! 기록용 메모라고 생각하고 😝 이렇게라도 하다보면 점점 글 쓰는 능력도 점차 성장하지 않을까 싶다.
나중에라도 완벽한 해결책을 찾게 되면 돌아와야지! 🏃🏻♀️🏃🏻♀️🏃🏻♀️