Day 16 - Mouse Move Shadow

See the Pen Day16-MouseMove by Jeon Jin Heo (@zinirun) on CodePen.

mousemove 이벤트에 textshadow css 속성을 조절하는 과제이다.
사실 offsetX, offsetY 등의 좌표값에 대한 계산 말고는 특별한 것은 없는 것 같고, 나는 크게 contenteditable 속성과 {} 선언법을 알았다.

contenteditable 속성

html 태그에 contenteditable을 속성을 true로 설정하면 input 태그처럼 수정할 수 있다. 원래는 <h1 contenteditable="true"> 처럼 속성을 줘야 하지만 true는 명시하지 않고 속성명만 적어도 된다. h 태그처럼 텍스트 태그에만 한정되있는게 아니고 div 등에도 걸 수 있다.

당연히 새로고침하면 원래의 값으로 돌아가니 Notion처럼 값을 지속적으로 유지하고 싶다면 Database를 쓰거나 LocalStorage를 쓰거나 해야한다.

{}로 한꺼번에 선언하기

hero 객체에는 offsetWidth, offsetHeight 값이 있는데, 이를 width, height라는 변수로 선언하고 싶다면 일반적으로

1
2
const width = hero.offsetWidth;
const height = hero.offsetHeight;

이렇게 많이 할 것이다. ES6 문법을 사용하면

1
const { offsetWidth: width, offsetHeight: height } = hero;

가독성과 코드 낭비를 한번에 해결할 수 있다.

css - textshadow

사실 css 속성은 필요할 때 검색해서 그대로 쓰거나 변형하면 되기에 정말 자주쓰는 속성이 아니면 깊게 들어가지는 않는 편이다.

아무튼 text-shadow 속성의 문법은

1
text-shadow: offset-x offset-y blur-radius color | none | initial | inherit

이렇게 사용한다.

  • offset-x: 그림자의 수평 거리
  • offset-y: 그림자의 수직 거리
  • blur-radius: 흐림 정도(기본 0)
  • color: 색상 (기본 브라우저 기본값)
  • none: 그림자 효과 없애기
  • initial: 기본값으로
  • inherit: 부모의 속성값 상속

여기서 필수적인 항목은 offset-xoffset-y이다. 절대 안 외워도 된다. 구글에는 CSS로 만들어진 갖가지 속성들이 엄청나게 많으니 마음에 드는 걸 가져다 쓰면 된다.

이제 이것들을 활용해서 원래의 과제인 shadow 함수를 작성하자.

Full Script

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
const hero = document.querySelector(".hero");
const text = hero.querySelector("h1");
const walk = 100; //100px
function shadow(e) {
// const width = hero.offsetWidth;
// const height = hero.offsetHeight;
const { offsetWidth: width, offsetHeight: height } = hero;
let { offsetX: x, offsetY: y } = e;

if (this !== e.target) {
x = x + e.target.offsetLeft;
y = y + e.target.offsetTop;
}

const xWalk = Math.round((x / width) * walk - walk / 2);
const yWalk = Math.round((y / height) * walk - walk / 2);

//use back ticks
text.style.textShadow = `
${xWalk}px ${yWalk}px 0 rgba(255,0,255,0.7),
${xWalk * -1}px ${yWalk}px 0 rgba(0,255,255,0.7),
${yWalk}px ${xWalk * -1}px 0 rgba(0,255,0,0.7),
${yWalk * -1}px ${xWalk}px 0 rgba(0,0,255,0.7)
`;
}
hero.addEventListener("mousemove", shadow);

shadow의 픽셀 값을 계산해서 back tick을 사용해서 넣어주는 것 말고는 지금까지 이벤트를 넣은 방법과 동일하다.