Javascript switch문에서 정규표현식 사용하기(feat. google tag manager)

스크린샷 2016-01-11 오후 5.23.49

Problem

Google Tag Manager에서 event를 만드는데 카테고리를 현재 있는 페이지 이름으로 넣고 싶다.
하지만 그냥 page path를 가져오면 가독성이 좋지 않아 한글화를 하고 싶다.
커스텀 자바스크립트 변수로 switch로 분기태워서 나누면 될 것 같은데,
https://store.pinkfong.com/user/order/2521/에서 2521처럼 동적으로 만들어진 path가 있어 보통 switch문으로 되지 않아 정규표현식을 쓰도록 한다.

Solution

switch에 true를 넣어 무조건 안으로 넣어주고, /정규식/.test(원하는변수)식으로 분기를 태워준다.
GTM의 Custom Javascript타입으로 pathName이란 이름의 Variables를 만들고, 사용할 땐 {{ pathName }}으로 사용해주면 된다.

function() {
    var path = location.pathname;
    var name;
    switch(true) {
        case /^\/$/.test(path):
            name = "메인페이지";
            break;
        case /^\/\d+\/$/.test(path):
            name = "제품상세";
            break;
        case /^\/user\/order\/\d+\/done\/$/.test(path):
            name = "구매완료";
            break;
        case /^\/user\/order\/$/.test(path):
            name = "주문";
            break;
        case /^\/user\/order\/\d+\/$/.test(path):
            name = "주문상세";
            break;
        case /^\/cart\/$/.test(path):
            name = "장바구니";
            break;
        case /^\/order\/$/.test(path):
            name = "주문진행중";
            break;
        default:
            name = path;
    }
    return name;
}

refer

http://stackoverflow.com/questions/2896626/switch-statement-for-string-matching-in-javascript

Javascript, jQuery로 element의 index 구하기

개요

Google Analytics에서 dataLayer를 사용하는데, 제품 노출을 전달할 때 그 제품의 index를 넘겨야 한다.
하지만 tagmanager를 사용하기 위한 dataLayer는 body여는태그 바로 뒤에 삽입해서 jQuery보다 먼저 호출되고만다.

<ul class="product">
  <li class="product">
    <div class="product">
      <div class="product-image">
        <a href="/13"></a>
      </div>
      <div class="product-content">
      </div>
    </div>
  </li>
  <li class="product">...</li>
  <li class="product">...</li>
</ul>

여기서 상품번호 별 li의 index를 어떻게 가져올까?

jQuery

jQuery로는 간단하다.

var position = $('.product-image a[href='/' + {{ product.id }} + '/']&').closest('li.product').index() + 1;

하지만 jQuery를 못 쓰는게 함정

javascript

스택오버플로우에서 루프를 돌지 않고 요소의 index를 받는 함수를 올려놓은 답변을 찾았다.

function getChildNumber(node) {
  return Array.prototype.indexOf.call(node.parentNode.childNodes, node);
}

하지만 내 코드에선 1, 3, 5, 7로 찍혀 나와서 2로 나누고 반올림 해서 수정했다.

function getChildNumber(node) {
  return Math.ceil(Array.prototype.indexOf.call(node.parentNode.childNodes, node)/2);
}

그래서 완성 코드는 이렇게 되었다.

var position = getChildNumber(document.querySelector('.product-image a[href='/' + {{ product.id }} + '/']').parentNode.parentNode.parentNode);

jQuery의 closest같은 경우는 이렇게 구현할 수도 있는데 짜피 한번 쓸거라 걍 parentNode로 올라갔다.

결과

근데 html dom보다 dataLayer가 먼저 불려서 돔 위치를 파악할 수 없어서 결국 fail. 담에 더 파봐야겠다…

(+)160111 추가 내용

jQuery를 GTM 스니펫 위로 올리고, dom ready이후에 추가되는 것들은

$(function() {
 ...
});

제이쿼리로 dom이 만들어진 후에 불리도록 넣었다.

Refer

http://stackoverflow.com/questions/4649699/is-it-possible-to-get-elements-numerical-index-in-its-parent-node-without-loopi
http://stackoverflow.com/questions/22100853/dom-pure-javascript-solution-to-jquery-closest-implementation

[jquery] 브라우저 시작 지점 바꾸기

jQuery

jquery로 하면 크로스브라우징 할 필요 없이 간단하다.

var app_offset_top = $('.article-apps').offset().top;
$(window).scrollTop(app_offset_top);

javascript

창 위치를 판단하는 크로스 브라우저 코드 (IE, 오페라 vs 파이어폭스, 사파리/크롬은 양쪽 지원)

var leftPos = (typeof window.screenLeft "number") ? window.screenLeft : window.screenX;
var topPos = (typeof window.screenTop "number") ? window.screenTop : window.screenY;

이 짓 하고 있었는데 멘토님이 지나가시다가 “jquery쓰세요”하시며 알려주셨다.

Javascript history.pushState 오류 – Failed to execute ‘pushState’ on ‘History’

스크린샷 2015-08-02 오후 8.13.53

Uncaught DOMException: Failed to execute ‘pushState’ on ‘History’: A history state object with URL ‘file://localhost/Users/jayjin/Documents/Programming/2015-02-HTML5/active’ cannot be created in a document with origin ‘null’.

투두리스트 웹앱을 만들며 탭간 이동에 history를 주려고 탭을 클릭했을 때

<br />history.pushState({"method":"active"}, null, "active");

이 코드를 실행하게 해두었더니, 글 제일 위의 저런 에러가 뜨는것이었다.

역시나 스택오버플로우 님께서 도와주셨는데,

local에서 돌릴 때 경로 인식이 꼬여서 그런것이었다.

<br />history.pushState({"method":"active"}, null, "#/active");

이와같이 #/active 로 고쳐주니 정상동작!

Refer

http://stackoverflow.com/questions/20079704/javascript-history-pushstate-not-working

javascript event.target VS event.currentTarget

target vs curruntTarget

<div class="yellow" id="yellow" style="background: #ff0; width: 300px; height: 150px">
    <div class="green" style="background: #0f0; width: 200px; height: 100px"></div>
</div>

<script type="text/javascript">
var divYellow = document.getElementById('yellow');
divYellow.onclick = function(e){
    e = e || window.event;
    var target = e.target || e.srcElement; //ie대응
    var current = e.currentTarget || this; //ie대응
    alert('target: '+target.className + ' currentTarget: ' + current.className);
}
</script>

아래노랑네모에 클릭이벤트를 걸고,

  • 위초록네모 클릭-> target:위초록 curruetTarget:아래노랑
  • 아래노랑네모 클릭-> target:아래노랑 currentTarget:아래노랑

위초록네모를 클릭하면 그걸 감싸고 있는 아래노랑네모에 event가 bubbling되어 이벤트 발생.

e.target: 이벤트가 일어난 곳
e.currentTarget: 실제로 이벤트가 걸려있는 위치

jQuery curruntTarget

$( "p" ).click(function( event ) {
  alert( event.currentTarget === this ); // true
});

jquery의 curruntTarget은 this와 동일하다.

Refer

https://api.jquery.com/event.currentTarget/
http://jsfiddle.net/misteroneill/kmn4A/3/
http://lidaf.tistory.com/38

Event delegation (Javascript, jQuery)

Event Delegation

  • child element각각에 이벤트 핸들러를 달지 않고
  • parent element에 단 뒤 이벤트가 발생한 노드를 필터링해 처리.
<JS>
document.getElementById('myTd').addEventListener( 'click', function() {
   //you code goes here...
}, false );

<HTML>
<table id="myTable">
   <tbody>
      <tr>
         <td id="myTd">1, 1</td>
         <td>1, 2</td>
      </tr> 
      <tr>
         <td>2, 1</td>
         <td>2, 2</td>
      </tr>
   </tbody>
</table>

myTd에 클릭이벤트를 달았는데, 다른 td들에도 달고 싶다면
각자 노가다로 달아줄 수 있겠지만, 이럴 땐 이벤트를 위임하는 방법을 쓴다(Event Delegation).

document.getElementById( 'myTable' ).addEventListener( 'click', function( e ) {
      if( e.target && e.target.nodeName == 'TD' ) {
         //you code goes here...
      }
   }, false );

jQuery Event Delegation

  • 이벤트 위임은 이벤트의 bubble 속성을 사용한 것입니다.
  • A 엘리먼트에 이벤트 핸들러를 등록하고 싶을 때 그 엘리먼트에 바로 붙이지 않고 그보다 상위 엘리먼트에 B에 등록합니다.
  • 이벤트가 A에서 발생했어도 B로 bubble 되어 올라가는데 이때 B에 등록된 핸들러에서 A에서 발생한 것인지 살펴보고 맞으면 이벤트 핸들러를 실행하는 방식이 이벤트 위임입니다.
  • .bind(), .live(), .delegate() 메서드 모두 jQuery 내부적으로는 .on() 메서드를 사용하게 소스코드가 바뀌었습니다.
  • 그래서 jQuery 1.7 이상 버전을 사용하신다면 여러 메서드들 중 하나를 선택하실 필요없이 그냥 .on() 메서드를 사용하시면 됩니다.
// Attach a delegated event handler
$( "#list" ).on( "click", "a", function( event ) {
    event.preventDefault();
    console.log( $( this ).text() );
});

Refer

http://regularmotion.kr/javascript-patterns-event-delegate/
http://hersheyweb.blogspot.kr/2013/04/javascript-event-delegation.html
http://codefactory.kr/2011/12/07/jquery-performance-tips-and-tricks/
http://learn.jquery.com/events/event-delegation/

Javascript Template – Handlebar.js

Handlebar

  • Mustache계열 템플릿
  • 사용할 수 있는 제어가 매우 한정적
  • template 레이아웃 기능 지원
  • helper라는 기능으로 여러가지 커스터마이징 제공

간단한 How to

1 handlebar.jsjquery를 html에 추가한다.
2 html에 원하는 템플릿을 id와 함께 추가한다.(handlebar.js 밑에)

<script id="todo-template" type="text/x-handlebars-template">
    <li class="{}">
        <div class="view">
            <input class="toggle" type="checkbox" {}>
            <label>{{todo}}</label>
            <button class="destroy"></button>
        </div>
    </li>
</script>

3 javascript에 코드를 써준다.

var source   = $("#todo-template").html();
var template = Handlebars.compile(source);
var data = { todo : $('#new-todo').val()};
$("#todo-list").append(template(data));

Refer

javascript micro templating
handlebar js
handlebar 간단한 사용법
handlebar js tutorial
Javascript Template 사용 가이드

자바스크립트&제이쿼리 (존 두켓 지음, 제이펍 출판) – “세상에서 가장 아름다운 프로그래밍 서적”

진유림_-_휴대폰_업로드

4월 초, 페이스북을 뜨겁게 달군 한 책이 있다.

충격적인 카피 때문일 것이었다.

“지금 여러분은 세상에서 가장 아름다운 프로그래밍 서적을 보고 있습니다!”

라니. 자고로 프로그래밍 서적은 노란책이나 코뿔소책처럼 그림은 존재하지 않는 작은 텍스트 뿐인게 대부분 아닌가.

그러나 이 책은 조금 달랐다.

위 사진의 댓글 분들이 요구하신 것처럼(그리고 모종의 잿밥을 향하여), 간단한 서평을 써보겠다.

S__9166854

(외모가 많이 다르다. 위:자바스크립트 노란책)

이 책이 다른 책들과 다른 점은,

  1. 텍스트로만 이해하기 힘든 부분들은 잘 다듬어 비쥬얼라이제이션 해두었고(책 전체를 아울러서!)

  2. 왼쪽 페이지에 DOMNodeInserted와 같은 개념을 설명한 후엔, 오른쪽엔 그 개념들을 어울러 실용적인 예제들을 만들어둔게 참 좋았다.

그것이이 이해-습득의 작은 루틴을 만들어 공부에 리듬감을 주었다.

S__9166856

(이런 식. 예제는 ‘구매 물품 목록 만들기’의 변형본을 계속 사용하여 익숙한 느낌을 준다)

630페이지를 돌파하는 두꺼운 책이지만, 사실 처음에는 이틀이면 완독할 줄 알았었다.

참 많이 부족하긴 하지만, 그래도 프론트엔드 신입 개발자로 일하고 있는 나였고, 주 언어는 자바스크립트였으니까.

아는 부분은 슬렁 슬렁 넘어가야지 하며 가벼운 마음으로 읽기 시작했는데

얼마 지나지 않아 내가 모르는 부분들이 나오는 것에 당황스러워 하다가,

곧 자세잡고 정독&블로그정리 하며 읽었다.

이는 그 산출물들이다.

https://milooy.wordpress.com/2015/04/03/javascript-dom/

https://milooy.wordpress.com/2015/05/15/javascript-event/

https://milooy.wordpress.com/2015/05/17/jquery/

처음에 자바스크립트를 학교에서 공부한 이후로는, 필요한 기능이 있을때마다 api문서나 스택오버플로우만 찾아보며 닥친 문제를 해결하곤 했는데, 이 책은 실용적인 기능들을 체계적으로 샅샅히 흝어가는 느낌이 참 좋았다.

나는 참 구멍뚫린 곳들이 많았구나….

S__9166851

(예를 들면 이런 것들. before()과 prepend()의 차이.)

자바스크립트나 제이쿼리를 처음 접하는 사람들에게,

아니면 배웠지만 나처럼 빵꾸가 많이 뚫려있는 사람에게,

혹은 유려한 편집디자인의 미를 느끼며 개괄적으로 흝고 싶은 사람에게 추천한다.

(나는 예쁜 것에도 민감하여, 이 책 한장 한장 디자인이 예뻐서 공부할 맛이 났다)

아, 그리고 위에 정리해둔 링크를 보면 알겠지만, 아직 읽어야 할 장들이 좀 남았는데 이는

8. Ajax와 JSON

9. API

10. 오류 처리와 디버깅

등등으로 더더욱 실무적인 내용이 있다. 취약했던 부분을 예쁜걸로 배운다니 마음이 꽁냥하다.

다른 직업도 마찬가지겠지만, 개발자는 정말 끊임없는 공부가 필요하다. 그리고 그것을 즐겨야 큰 개발자가 될 수 있다.

주변에 “아… 일시정지 누르고 ㅇㅇ(swift/go/polymer등등)좀 배우고 다시 일했으면 좋겠다 ㅠㅠ”라며

‘자신이 현재 하는 일 외의 개발’을 취미생활(혹은 사치생활!)로 여기며 배움에 대한 갈망을 내보이는 개발자들이 참 많다.

그런 사람들과 함께할때마다 배가 간질간질해지며 그들이 참 귀엽고 이런 개발자 세계가 좋다.

신기술은 끊임없이 나오고, 스피드웨건같은 블로거님들과 출판사님들 덕분에 참 개발공부하기 좋은 때이다.

이 시기와 환경을 십분 이용해먹어야지 슈퍼개발자가 되어야지 파워블로거도 되어야지 주짓수 챔피언이 되어야지


(p.s HTML CSS가 부족하다면 같은 저자가 집필한 이 책도 추천드려요)

책정보__HTML_CSS___네이버_책

자바스크립트 & 제이쿼리 (jpub) – 7장 jQuery

요소 탐색하기

  • 계층 탐색
    • ancestor descendant
    • p>c: 다른 요소의 하위 요소들
    • p+n: 직접적인 자식 요소들(모든 자식요소 하고싶다면 p>*)
    • p~s: 이전 요소의 모든 이웃 요소
  • 기본 필터
    • :not(selector): 셀렉터에 부합하는 요소를 제외한 나머지 요소들(div:not(‘#summary’))
    • :first: 선택된 요소 중 첫 번째 요소
    • :last, even, odd
    • :eq(index): 선택된 요소 중 매개변수로 지정된 인덱스 번호를 가진 요소
    • :gt(index), :lt(index)
    • :header, :animated, :focus
  • 콘텐츠 필터
    • :contains(‘text’): 매개변수로 지정된 텍스트를 가지고 있는 요소들
    • :empty: 자식 요소가 없는 모든 요소들
    • :parent: 위의 반대
    • :has(selector): 선택된 요소 중 매개변수에 지정된 셀렉터에 부합하는 요소를 최소한 하나 이상 가지고 있는 모든 요소 (ex. div:has(p) p요소를 가진 모든 div요소)
  • 가시성 필터
    • :hidden: 화면에서 숨겨진 모든 요소들
    • :visible: 페이지의 레이아웃에서 공간을 차지하고 있는 모든 요소들.
  • 자식 요소 필터
    • :nth-child(expr): 1부터 시작하는 해당 순번의 요소(ul li:nth-child(2)는 두번째 요소를 의미)
    • :first-child, :last-child, :only-child
  • 특성 필터
    • [attribute]: 지정된 특성 갖고있는 요소들
    • [attribute=’value’]
    • [attribute!=’value’]
    • [attribute^=’value’]: 특성값이 지정된 값으로 시작하는 요소들
    • [attribute$=’value’]: 특성값이 지정된 값으로 끝나는 요소들
    • [attribute*=’value’]: 특성값이 지정된 값으로 포함되는 요소들
    • [attribute][attribute2]: 지정된 특성 중 하나를 가진 모든 요소들
    • :input, :text, :password, :radio…
    • :image, :button
    • :selected: 드롭다운 리스트에서 선택된 모든 요소들
    • :enabled, :disabled, :checked(체크된 요소들을 리턴)

선택된 요소에 필요한 작업 수행

  • 콘텐츠 필터
    • 가져오기/수정하기
      • .html(): 첫 번째 요소들과 그 하위 노드들의 HTML코드를 얻음.
      • .text(): 객체집합 내 모든 요소의 텍스트와 그 하위 요소들의 텍스트 리턴.(input요소나 textarea요소에서 내용 가져오려면 .val()메서드 사용.)
      • .replaceWith(): 일치하는 모든 요소에 새로운 동일한 콘텐츠 추가하고 교체된 요소들을 모두 리턴
      • .remove(): 일치하는 모든 요소들을 제거
    • 요소
      • .before(): 선택한 요소 전에
      • .after(): 선택한 요소 다음에
      • prepend(): 선택한 요소의 여는 태그 다음에
        • a.prepend(b)는 a에 b를 추가한다 / a.prependTo(b)는 b에 a를 추가한다.
      • append(): 선택한 요소의 닫는 태그 다음에
      • remove
      • clone
      • unwrap
      • detach
      • empty
      • add: 매개변수로 지정된 셀렉터에 의해 선택된 요소들을 기존 객체집합에 추가
    • 특성
      • attr
        • 가져오기: $(‘li#one’).attr(‘id’);
        • 수정하기: $(‘li#one’).attr(‘id’, ‘hot’);
      • removeAttr
      • addClass
      • removeClass
      • css
        • 가져오기: bg = $(‘li’).class(‘background-color’);
        • 증감하기: $(‘li’).class(‘padding’, ‘+=20’);
        • 여러 속성: $(‘li’).css({‘color’: ‘#272727’, ‘font-family’: ‘Courier’});
    • 폼 값
      • val: input, select, textarea요소에 주로 사용.
      • isNumeric
  • 요소 탐색
    • 일반
      • find: 현재 객체집합에서 셀렉터와 일치하는 요소들 리턴
      • closest: 셀렉터와 일치하는 가장 근접한 상위요소(직계부모~최상위요소 모두)를 리턴
      • parent: 현재 객체집합의 직계부모요소 리턴
      • parents: 모든 부모요소
      • children: 모든 자식 요소
      • siblings: 모든 이웃 요소
      • next: 다음 이웃 요소
      • nextAll
      • prev
      • prevAll
    • 필터/테스트
      • filter: 두 번째 셀렉터를 이용하여 jQuery객체집합을 필터링
      • not
      • has
      • is: 폼요소가 선택 혹은 체크되어있는지 확인
      • :contains()
    • 객체집합 내 순서 평가
      • eq: 인덱스 번호에 해당하는 요소를 리턴
      • :lt
      • :gt
  • 크기/위치
    • 크기
      • height: 영역의 크기
      • with innerHeight(영역의 높이에 안쪽 여백 더한 값) / innerWidth / outerHeight/ outerWidth
      • $(document).height()
      • $(document).width()
      • $(document).height()
      • $(window).height()
      • $(window).width()
    • 위치
      • offset: document객체의 좌측 상단 모서리에서부터 요소까지의 좌표를 가져오거나 지정(offset().top 이런식으로 쓴다)
      • position: 상위 요소 중 기본 흐름 값을 가진 요소로부터 해당 요소까지의 좌표를 가져오거나 지정
      • scrollLeft
      • scrollTop
  • 효과/애니메이션
    • 기본
      • show: 선택된 아이템을 보이게
      • hide: 숨긴다
      • toggle
    • 흐림 효과
      • fadeIn
      • fadeOut
      • fadeTo: 선택된 요소의 불투명도 조절
      • fadeToggle
    • 슬라이딩 효과
      • slideDown
      • slideUp
      • slideToggle
    • 기타
      • delay: 큐 내의 다음 아이템의 실행을 잠시 지연
      • stop: 현재 실행중인 애니메이션 중단
      • animate: 새로운 임의의 애니메이션 생성
  • 이벤트
    • 문서/파일
      • ready
      • laod
    • 사용자 상호작용
      • on
      • (.click(), .hover(), submit()같은 메서드들도 보게 될것인데, 이벤트 처리를 위한 on()메서드가 나타나며 사라짐)

tips

정보

  • 획득
    • jquery객체집합에 둘 이상 요소 저장되어 있으면 ($(‘li’).html();) 첫번째 요소의 정보만 얻어옴.
    • 다른 요소 참조하려면 탐색메서드나 필터 메서드, 혹은 셀렉터 이용.
    • 모든 요소 콘텐츠 가져오려면 .each()메서드 사용.
  • 수정
    • 둘이상 요소 저장되어있고 수정하면 모든 요소 수정됨.

변수에 캐싱

  • 코드가 동일한 객체집합을 한번 이상 사용할 필요가 있다면 객체에 담아두는게 효과적.
  • $listItems = $(‘li’); 와 같이 변수에 jQuery객체를 저장할 때 이렇게 하면 다른 변수들과 구분하는데 도움된다.

체이닝

  • jQuery객체집합을 수정하기 위한 대부분의 메서드는 체이닝 가능
  • 그러나 DOM/브라우저에서 정보를 조회하는 메서드들은 체이닝으로 연결 불가.

페이지가 준비되었는지 확인

// 이 메서드 내부에 작성하면 코드가 페이지의 다른곳이나 다른 파일에 작성된 경우에도 의도대로 동작한다.
$(document).ready(function() {
    //bla bla
});

// 위 함수의 약식 표현
$(function() {
    //bla bla
});
  • .load()
    • load이벤트가 발생할 때 호출.
    • .on()메서드로 대체되었다.
    • 페이지와 나머지 모든 리소스(이미지, CSS, 스크립트)가 로드된 이후에 발생
    • 스크립트가 반드시 로드되어야 하는 리소스에 의존적일 때 사용.
      • ex. 스크립트가 이미지의 크기를 알아야 할 때
  • .ready()
    • 페이지가 빨리 로드된 것처럼 보이도록 브라우저에 DOM이 로드되자마자 실행.
    • 그러나 최신 브라우저들에서만 지원.(구버전: laod이벤트 되면 시작)

컨텐츠를 수정

현재 선택한 요소들의 콘텐츠를 사용하려는 동시에 수정하려면 함수에 매개변수를 전달하면 된다.

$('li.hot').html(function(){
    return '<em>' + $(this).text() + '</em>';
    })

.each()

$(function() {
    $('li').each(function() {
        var ids = this.id;  //$(this).attr('id')보다 이게 좋다.
        $(this).append('<span class="order">' + ids + '</span>');
    });
});

this

$(this)처럼 this키워드를 이용해 새로운 jQeury 객체집합을 만드는 경우도 볼 수 있는데,
이렇게 하면 현재 요소에 대해서도 jQuery메서드들을 사용할 수 있다.

.on()

  • 매개변수를 2개 받는다. 첫번째는 대응할 이벤트, 두번째는 함수(기명/익명)
  • (*친것들은 onready처럼 작업을 더 쉽게 만들어주는 추가 메서드 제공.)
  • focus, blur, change
  • input, keydown keyup, keypress
  • click, dblclick, mouseup, mousedown, mouseover, mousemove, mouseout, *hover
  • submit, select, change
  • *ready, load, *unload
  • error, resize, scroll
//모바일은 마우스오버가 없으니 클릭도 같이 지정.
$listItems.on('mouseover click', functionn(){
    //~~
});

event객체

$('li').on('click', function(e) {
    eventType = e.type;
});

속성

  • type: 이벤트 종류
  • which: 눌려진 버튼이나 키
  • data
  • target: 이벤트가 발생한 DOM요소
  • pageX, pageY
  • timeStamp
  • .preventDefault(): 기본 동작을 취소(ex. 폼 데이터 전송)
  • .stopPropagation(): 상위 객체로 이벤트가 버블링되는 것을 중단.

.animate()

.animate({
    //변경할 스타일들 나열
    }, [, speed][, easing][, complete]);
// speed: 진행될 시간의 길이 밀리초단위. low/fast도 가능
// easing: linear(일정속도) / swing(중간은 빨리 처음끝은 느리게)
// complete: 애니메이션이 종료시 호출될 함수(콜백함수)를 지정 위함

$(this).animate({
    opacity: 0.0,
    paddingLeft: '+=80'
    }, 500, function() {
        $(this).remove();
    });

오타

303p attribute$=’value’
322p $(‘li’).clss(‘~’)
322p ‘background-color’: ‘#272727’,

자바스크립트 & 제이쿼리 (jpub) – 6장 Javascript event

이벤트 종류

웹을 탐색하는 동안 브라우저에서 발생할 수 있는 이벤트

UI Event

사용자가 웹 페이지가 아닌 브라우저의 UI와 상호작용할 때 발생
– load: 페이지가 가지고 있는 모든 요소(이미지, 스크립트 및 광고)가 전부 로드되었을때만 발생. script요소를 html밑에 정의하면, DOM은 스크립트를 실행하기에 앞서 폼 요소를 먼저 로드하므로 이 경우 load이벤트의 발생을 기다릴 필요가 없다.window.addEventListener('load', setup, false);
– unload: 웹 페이지가 언로드될 때 (주로 새로운 페이지를 요청한 경우)
– error: 브라우저가 자바스크립트 오류를 만났거나 요청한 자원이 존재하지 않는 경우
– resize
– scroll: 전체 페이지 뿐만 아니라 특정 요소(스크롤바 가진 textarea)에서도 적용

Keyboard Event

  • input: input/textarea요소 값이 변경될 때
  • keydown: 사용자가 키를 처음 눌렀을 때 (키가 눌린 동안은 계속해서 발생)
  • keypress: 사용자가 눌렀던 키의 문자가 입력되었을 때
  • keyup: 키보드 키 눌렀다 뗄 때. 화면에 문자가 나타난 이후에 발생

이벤트 순서

  1. keydown – 키 누름
  2. keypress – 키 눌렀거나/누르고 있는중이라 페이지에 문자 입력되고있다.
  3. keyup – 키 뗌

Mouse Event

  • click: 마우스 버튼을 눌렀다 뗄 때
  • dblclick
  • mousedown: 마우스 버튼을 누르고 있을 때
  • mouseup: 눌렀던 마우스 버튼을 뗄 때
  • mousemove: 마우스를 움직일 때(터치스크린X)
  • mouseover: 요소 위로 마우스를 움직였을 때(터치스크린X)
  • mouseout: 요소 바깥으로 마우스를 움직였을 때(터치스크린X)

Focus Event

  • focus / focusin: 포커스를 얻었을 때
  • blur / focusout: 포커스를 잃었을 때

Form Event

  • input: 또는요소 값이나 contenteditable특성을 가진 요소 값이 변경되었을 때
  • change: 선택 상자, 체크박스, 라디오 버튼의 상태가 변경되었을 때
  • submit: 사용자가 (버튼이나 키를 이용하여) 폼을 제출할 때 – 사용자가 폼에 입력한 값을 서버로 전달하기에 앞서, 입력한 값이 올바른 것인지 검사할 때 주로 사용됨.
  • reset
  • cut: 사용자가 폼 필드의 콘텐츠를 잘라내기 했을 때
  • copy
  • paste
  • select: 사용자가 폼 필드에서 텍스트를 선택했을 때

요소에 이벤트를 바인딩하는 세 가지 방법

  1. HTML 이벤트 핸들러
    • 그다지 권장하진 않음. 예전 코드에서 종종 사용.
    • <a>
    • HTML 이벤트 핸들러 특성은 저 위 이벤트 이름과 동일하며, 앞에 on을 붙여 사용.
      • a요소는 onclick, onmouseover…, form요소는 onsubmit, input은 onkeypress, onfocus 등등
  2. 전통적인 DOM 이벤트 핸들러
    • 장점: 모든 주요 브라우저에서 지원.
    • 단점: 이벤트별로 단 하나의 함수만 바인딩 가능
function checkUsername(){
    ...
}
var el = document.getElementById('username');
element.onblur = checkUsername;//(함수이름 괄호는 생략)
- (함수를 호출할 때, 함수 이름 뒤에 괄호를 지정하면 JS해석기는 "이 코드를 지금 실행하라"란 의미로 해석.)

3. 이벤트 리스너
– 현재는 이 방법을 제일 많이 사용.
– 하나의 이벤트로 여러 개의 함수를 실행할 수 있다.
– IE8에선 지원 안함. attachEvent로 구현한다.

function checkUsername(){...}
var el = ...;
el.addEventListener('blur', checkUsername, false);  //버블링:false, 캡쳐링:true

//매개변수를 가진 이벤트 핸들러
el2.addEventListener('blur', function(){
    checkUsername(5);   //이벤트핸들러나 리스너를 지정할 때, 함수 이름 다음에 괄호를 사용할 수 없으므로 인수를 전달해야 하는 경우엔 우회 방법이 필요. - 익명함수
}, false);

이벤트 객체

  • 이벤트 객체는 이벤트가 발생할 떄마다 해당 이벤트에 대한 유용한 정보를 제공.
    • 이벤트를 발생시킨 요소
    • keypress 이벤트가 어떤 키에 의해 발생했느지에 대한 정보
    • 사용자가 뷰포트 내의 어떤 요소를 클릭해서 click이벤트가 발생했는지에 대한 정보
  • 이벤트 객체는 이벤트 핸들러나 리스너로 지정된 함수에 전달된다. 전달받기 위한 함수의 매개변수 이름은 보통 e를 사용한다. (일부 개발자들은 error객체 참조할때도 e라 한다. 헷갈 ㄴㄴ)
function checkUsername(e){
    var target = e.target; //이벤트가 발생한 요소를 가져옴.
}
el.addEventListener('blur', checkUsername, false);

function checkUsername2(e, minLength){  //매개변수 가짐
    var target = e.target;
}
el2.addEventListener('blur', function(e){
    checkUsername(e, 5);
}, false);

//IE 5~8 대응하기
function checkUsername3(e, minLength) {
    var el, elMsg;
    if(!e){
        e = window.event;
    }
    el = e.target || e.srcElement;
    elMsg = el.nextSibling;

    if(el.value.length이벤트 핸들러 함수 호출될때 어떤 요소에서 이벤트 발생했는지 알아내는 최고의 방법은 event객체의 target속성 참조하는 방법이다. 근데 this로도 참조 가능.

- `this.value.length` 처럼 받아올 수 있다.
- 근데 함수에 매개변수를 전달하지 않는(그래서 익명 함수에 의해 호출되는 것이 아닌) 경우에만 제대로 동작.

# focus, blur
```javascript
function checkUsername(){
    var username = el.value;
    if(username.length<5){
        elMsg.className = 'warning';
        elMsg.textContent = "이름이 너무 짧습니다.";
    } else {
        elMsg.textContent = "";
    }
}

function tipUsername() {
    elMsg.className = 'tip';
    elMsg.innerHTML = '이름은 다섯 글자 이상이어야 합니다.'
}

//username입력 필드가 포커스를 받거나 잃으면 위의 함수를 호출하도록 한다.
el.addEventListener('focus', tipUsername, false);
el.addEventListener('blur', checkUsername, false);

이벤트가 발생한 지점

  1. 스크린
    • screenX, screenY
    • 모니터 화면 전체를 대상
    • (브라우저가 아닌)화면의 왼쪽 상단 모서리를 기준으로 현재 커서 위치 알려줌
  2. 페이지
    • pageX, pageY
    • 전체 페이지를 기준으로 현재 커서 위치
    • 페이지 최상단은 viewport를 벗어나 있을 수 있기 때문에 커서가 같은 위치에 있다 하더라도 페이지 좌표와 클라이언트 좌표가 다를 수 있다.
  3. 클라이언트
    • clientX, clientY
    • 브라우저 뷰포트 기준으로 커서 위치 알려줌
    • 스크롤 해서 상단 안보이더라도 클라 좌표는 영향 안받음

변형 이벤트

  • DOMNodeInserted: 돔트리에 노드 추가될때. (appendChild(), replaeChild(), insertBefore()메서드를 호출하면 발생한다.)
  • DOMNodeRemoved: 제거될때
  • DOMSubtreeModified: 변경되면
  • DOMNodeInsertedIntoDocument
  • DOMNodeRemovedFromDocument

HTML5 이벤트

  • DOMContentLoaded: 돔트리가 형성될때.더 빠르게 로드되는 것처럼 보일 수 있다. 그러나 스크립트 로딩이 완료되기를 기다리지 않아 미처 로딩되지 않은 스크립트에 의해 생성되는 요소들이 DOM트리에 반영되지 않을 수 있다(window나 document객체 통해 처리)
  • hashchange: URL의 해시가 변경될 때(전체 창이 새로 고쳐지는 것이 아니라)발생. ajax이용해 콘텐츠 로드하는 경우에도 사용.
  • beforeunload: window객체에서 발생. 페이지가 언로드 되기 전에 발생.(ex. 사용자가 폼 데이터를 변경한 상태에서 저장 않고 다른 페이지로 이동하려는 경우에 알림)