Event
브라우저는 이벤트를 감지할 수 있고 이벤트 발생 시 그에 맞는 응답을 전달해줄 수 있다.
이러한 과정을 통해 사용자는 웹페이지와 상호작용이 가능하게 된다.
이벤트 발생 시 그에 맞는 응답을 정의하는 함수를 이벤트 핸들러라고 한다.
<!DOCTYPE html>
<html>
<body>
<button class="myButton">Click me!</button>
<script>
document.querySelector('.myButton').addEventListener('click',
function () { // 이벤트 핸들러
alert('Clicked!');
});
</script>
</body>
</html>
이벤트 핸들러는 Timer함수(setTimeout, setInterval), Ajax요청과 더불어 비동기식 처리 모델로 동작한다.
동기식(synchronous): 직렬적 처리
비동기식(asynchronous): 병렬적 처리
//동기식
function func1() {
console.log('func1');
func2();
}
function func2() {
console.log('func2');
func3();
}
function func3() {
console.log('func3');
}
func1();
//func1
//func2
//func3
//비동기식
function func1() {
console.log('func1');
func2();
}
function func2() {
setTimeout(function () {
console.log('func2');
}, 0);
func3();
}
function func3() {
console.log('func3');
}
func1();
//func1
//func3
//func2
이벤트 핸들러는 이벤트 루프(Event Loop)를 통해 비동기적으로 처리된다.
2021/02/08 - [개발/WEB] - 이벤트 루프 (Event Loop)
이벤트 종류
developer.mozilla.org/ko/docs/Web/Events
이벤트 핸들러 등록
이벤트 핸들러를 등록하는 방법은 3가지가 있다.
- 인라인 이벤트 핸들러
- 이벤트 핸들러 프로퍼티
- addEventListener 메서드
인라인 이벤트 핸들러
HTML 요소의 이벤트 핸들러 어트리뷰트에 이벤트 핸들러를 등록하는 방법
<!DOCTYPE html>
<html>
<body>
<button onclick="myHandler()">Click me</button>
<script>
function myHandler() {
alert('Button clicked!');
}
</script>
</body>
</html>
인라인 이벤트 핸들러 참고
-
이 방식은 더 이상 사용되지 않으며 사용해서도 안 된다.
오래된 코드에서 간혹 이 방식을 사용한 것이 있기 때문에 알아둘 필요는 있다.
HTML과 Javascript는 관심사가 다르므로 분리하는 것이 좋다. -
이벤트 핸들러 내부의 this는 전역 객체 window를 가리킨다.
이벤트 핸들러 프로퍼티
HTML과 Javascript가 뒤섞이는 문제는 해결할 수 있지만, 이벤트 핸들러 프로퍼티에 하나의 이벤트 핸들러만을 바인딩할 수 있다는 단점이 있다.
<!DOCTYPE html>
<html>
<body>
<button class="btn">Click me</button>
<script>
const btn = document.querySelector('.btn');
// 이벤트 핸들러 프로퍼티 방식은 이벤트에 하나의 이벤트 핸들러만을 바인딩할 수 있다
// 첫번째 바인딩된 이벤트 핸들러 => 실행되지 않는다.
btn.onclick = function () {
alert('① Button clicked 1');
};
// 두번째 바인딩된 이벤트 핸들러
btn.onclick = function () {
alert('① Button clicked 2');
};
// addEventListener 메소드 방식
// 첫번째 바인딩된 이벤트 핸들러
btn.addEventListener('click', function () {
alert('② Button clicked 1');
});
// 두번째 바인딩된 이벤트 핸들러
btn.addEventListener('click', function () {
alert('② Button clicked 2');
});
</script>
</body>
</html>
이벤트 핸들러 프로퍼티 참고
-
이벤트 핸들러 내부의 this는 이벤트에 바인딩된 요소(button class="btn")를 가리킨다.
이벤트 객체의 currentTarget프로퍼티와 같다.
addEventListener 메서드
*은 옵션
addEventListener 메서드를 이용하여 대상 DOM 요소(target)에 이벤트를 바인딩하고 해당 이벤트가 발생했을 때 실행될 콜백 함수(이벤트 핸들러)를 지정한다.
target.addEventListener(이벤트 타입, 이벤트 핸들러, *capture 사용 여부);
-
하나의 이벤트에 대해 하나 이상의 이벤트 핸들러를 추가할 수 있다.
-
캡처링과 버블링을 지원한다.
-
HTML 요소뿐만 아니라 모든 DOM 요소(HTML, XML, SVG)에 대해 동작한다.
브라우저는 웹 문서(HTML, XML, SVG)를 로드한 후, 파싱 하여 DOM을 생성한다.
<!DOCTYPE html>
<html>
<body>
<label>User name <input type='text'></label>
<em class="message"></em>
<script>
const MIN_USER_NAME_LENGTH = 2; // 이름 최소 길이
const input = document.querySelector('input[type=text]');
const msg = document.querySelector('.message');
function checkUserNameLength(n) {
if (input.value.length < n) {
msg.innerHTML = '이름은 ' + n + '자 이상이어야 합니다';
} else {
msg.innerHTML = '';
}
}
input.addEventListener('blur', function () {
// 이벤트 핸들러 내부에서 함수를 호출하면서 인수를 전달한다.
checkUserNameLength(MIN_USER_NAME_LENGTH);
});
// 이벤트 핸들러 프로퍼티 방식도 동일한 방식으로 인수를 전달할 수 있다.
// input.onblur = function () {
// // 이벤트 핸들러 내부에서 함수를 호출하면서 인수를 전달한다.
// checkUserNameLength(MIN_USER_NAME_LENGTH);
// };
</script>
</body>
</html>
addEventListener 메서드 참고
-
이벤트 핸들러(callback함수) 내부의 this는 이벤트 리스너에 바인딩된 요소(input type='text')를 가리킨다.
이벤트 객체의 currentTarget 프로퍼티와 같다.
event 객체
event 객체는 이벤트가 발생하면 동적으로 생성되며, 암묵적으로 이벤트 핸들러에게 전달된다.
<!DOCTYPE html>
<html>
<body>
<p>클릭하세요. 클릭한 곳의 좌표가 표시됩니다.</p>
<em class="message"></em>
<script>
function showCoords(e) { // e: event 객체
const msg = document.querySelector('.message');
msg.innerHTML =
'clientX value: ' + e.clientX + '<br>' + //클릭한 곳의 좌표가 실시간으로 표시된다.
'clientY value: ' + e.clientY;
}
addEventListener('click', showCoords);
</script>
</body>
</html>
event 객체 참고
-
이벤트 핸들러를 선언할 때 event 객체를 전달받을 첫 번째 매개변수를 선언해야 한다.
-
위 코드에서는 매개변수로 e라는 이름을 선택했지만 다른 이름을 선택해도 상관없다.
event 객체 속성 종류
developer.mozilla.org/ko/docs/Web/API/Event#%EC%86%8D%EC%84%B1
이벤트의 흐름
계층적 구조에 포함되어 있는 HTML 요소에 이벤트가 발생할 경우 이벤트가 전파(Event Propagation)되는데,
전파 방향에 따라 버블링(Event Bubbling)과 캡처링(Event Capturing)으로 구분할 수 있다.
캡처링 : 자식 요소에서 발생한 이벤트가 부모 요소부터 시작하여 이벤트를 발생시킨 자식 요소까지 도달하는 것
버블링 : 자식 요소에서 발생한 이벤트가 부모 요소로 전파되는 것
버블링과 캡처링은 둘 중에 하나만 발생하는 것이 아니라 캡처링부터 시작하여 버블링으로 종료한다.
*addEventListener 메서드의 매개변수(*capture 사용 여부)에 true를 설정하면 캡처링으로 전파되는 이벤트를 캐치하고
false 또는 미설정하면 버블링으로 전파되는 이벤트를 캐치한다.
참고
'개발 > Javascript' 카테고리의 다른 글
Promise (0) | 2021.02.10 |
---|---|
Ajax (Asyncronous Javascript and XML) (0) | 2021.02.09 |
데이터 타입, 표준 내장 객체(Standard Built-in Object), 타입 변환 (0) | 2021.02.03 |
prototype(프로토타입) (0) | 2021.02.02 |
this (0) | 2021.01.29 |