Javascript PagesShow PagesHide Event

JavaScript pageshow 이벤트, pagehide 이벤트

네트워크 연결 속도가 느리고 연결 비용이 높은 모바일 환경에서는 pageshow 이벤트와 pagehide 이벤트가 중요하다. PC와는 다르게 모바일 브라우저에서는 이 이벤트가 페이지 캐시를 모두 지원하기 때문에 특별히 활용도가 높다.

pageshow 이벤트와 pagehide 이벤트는 window 객체의 이벤트로서 lod 이벤트, unload 이벤트와 유사하게 동작하며, iOS 4.0 이상의 사파리와 안드로이드 2.2 이상의 기본 브라우저에서만 발생한다.

pageshow 이벤트

pageshow 이벤트는 load 이벤트 다음에 발생하는 이벤트로, 페이지가 열릴 때 마다 항상 발생한다. 단 페이지가 캐싱됐을 때는 load 이벤트가 발생하지 않고 pageshow 이벤트만 발생한다. 페이지가 캐싱됐을 때는 pageshow 이벤트의 persisted 속성값이 true로 반환된다. 반명 페이지가 캐싱되지 않았을 때는 load 이벤트가 발생하고 persisted 속성값이 false로 반환된다.

페이지 캐싱

브라우저가 모바일 기기의 브라우저 세션에 대해 자바스크립트를 포함한 전체 웹 페이지를 메모리에 캐싱하는 것을 말한다. 페이지 캐싱을 사용하면 브라우저의 뒤로 이동 버튼과 앞으로 이동 버튼으로 페이지를 이동할때 페이지를 다시 로딩하지 않고 캐싱된 페이지를 빠르게 보여준다. 그렇기 때문에 네트워크 상황이 좋지 않은 모바일 환경에서는 페이지 캐싱을 중요하게 여긴다.

pagehide 이벤트

pagehide 이벤트는 unload 이벤트처럼 페이지가 언로드(unload)될 때 발생한다. pageshow 이벤트와 마찬가지로 캐싱된 페이지에서는 unload 이벤트는 발생하지 않지만 pagehide 이벤트는 발생한다.

기기별 이벤트 특징

pageshow 이벤트와 pagehide 이벤트는 운영체제와 단말기에 따라 발생하는 시점이 다르고, 상태에 따라 페이지 캐싱 여부가 달라진다.

상황 아이폰에서의
이벤트 발생여부
(iOS 4.x ~ 7.x)
아이패드에서의
이벤트 발생 여부
(iOS 4.x ~ 7.x)
안드로이드에서의
이벤트 발생 여부
(안드로이드 2.x ~ 4.x)
브라우저에서 새창을 열 경우 이벤트 발생 이벤트 발생 안함 이벤트 발생 안함
브라우저 탭을 이동한 경우 이벤트 발생 이벤트 발생 안함 이벤트 발생 안함
홈 버튼을 누른 후 브라우저를
다시 실행 한 경우
이벤트 발생 이벤트 발생 이벤트 발생 안함
전원 버튼을 눌러 잠긴 상태에서
잠금을 해제한 경우
이벤트 발생 이벤트 발생 이벤트 발생 안함

브라우저 탭을 전환하거나 새 창을 여는 경우를 제외하고, iOS 환경에서는 대상 브라우저 페이지가 비활성화되고 다시 활성화됐을 때 모두 pageshow 이벤트와 pagehide 이벤트가 발생환다. 반면 안드로이드 환경에서는 현재 보고 있는 브라우저에 외부 영향이 있을 경우에는 모두 이벤트가 발생하지 않는다.

페이지 캐싱이 되지 않는 경우

모바일 웹에서는 기본적으로 페이지 캐싱을 사용한다. 하지만 브라우저의 특정 기능 사용으로 웹 페이지가 캐싱되되 않는 경우가 있다. 그 경우는 다음과 같다.

  • onunload 이벤트 핸들러나 onbeforeunload 이벤트 핸들러를 사용한 경우
  • “cache-control:no-store”가 HTTP 헤더에 설정된 경우
  • 페이지가 완전히 로딩되기 전에 페이지를 이동한 경우
  • iFrame을 사용한 경우
  • navigation.geolocation을 사용한 경우

모바일 브라우저의 전체 화면 사용하기

주소창을 감추고 브라우저의 전체 화면에 콘텐츠를 보여주는 UI를 구현할 때는 일반적으로 scrollTop() 메서드를 이용한다. scrollTop() 메서드로 문서의 처음으로 이동하면 모바일 브라우저의 주소창이 사라진다. 주소창을 사라지게 한 상태에서 브라우저의 크기를 확인하면 화면 전체의 크기를 구할 수 있다. 하지만 scrollTop() 메서드는 브라우저의 높이보다 문서(document)의 높이가 더 큰 상태에서 호출돼야 한다. 브라우저의 높이보다 문서의 높이가 작다면 scrollTop() 메서드를 호출해도 주소창이 사라지지 않는다.

콘텐츠의 양에 따라 문서의 높이가 브라우저보다 작을 수 있기 때문에 UI를 구현할 때는 scrollTop() 메서드를 호출하지 전에 브라우저 높이보다 큰 DIV 요소를 임시로 넣는 방법을 사용한다. 다음은 DIV 요소를 만들어 문서에 추가한 다음 요소의 높이가 브라우저의 높이보다 200px 더 크게 스타일을 적용하는 코드다. 브라우저의 높이는 window.innerHeight 속성으로 구할 수 있다.

1
2
3
4
5
6
if (!this._fullSizeCheckElement) {
this._fullSizeCheckElement = document.createElemet('div');
document.body.appendChild( this._fullSizeCheckElement );
}

this._fullSizeCheckElement.style.cssText = ''position:absolute;top:0px;width:100p%;height:' + parseInt(window.innerHeight + 200, 10) + 'px;';

임시 div 요소를 추가 했다면 주소창을 사라지게 한다. 브라우저에서 지원하는 API에는 주소창을 사라지게 하는 API가 없지만 자바스크립트의 scrollTop() 함수를 사용하면 모바일 웹 브라우저의 주소창을 사라지게 할 수 있다. 다음과 같이 문서의 위쪽에서 1px 위치로 이동하게 하면 주소창이 사라지면서 전체 화면이 나타난다.

1
window.scrollTop(0, 1);

단, iOS 7의 사파리에서는 scrollTop() 함수를 사용해도 주소창이 사라지지 않는다. 이는 오류가 아닌 iOS 7의 특성이라고 볼 수 있다.

주소창이 사라졌다면 브라우저의 높이와 너비를 구할 차례다.
브라우저의 너비와 높이는 window.innerWidth 속성과 window.innerHeight 속성으로 구할 수 있다. 주소창이 없는 상태에서 브라우저의 너비와 높이를 구한 다음에는 임시 div 요소의 높이를 0px로 바꾼다. 임시 div 요소의 목적이 브라우저의 주소창을 사라지게 하는 것이었으므로 더는 화면에 보일 필요가 없기 때문이다.

1
2
3
4
5
6
var htSize = {
width: window.innerWidth,
height: window.innerHeight
};

this._fullSizeCheckElement.style.height = '0px';
공유하기