기본 환경셋팅이나, 자세한 설명보다는 요점만 정리할까 한다.

원형섭씨의 Quick Start Vue.js의 예제를 사용하였다.

https://github.com/stepanowon/vuejs_book

Vue 객체

아주 심플한 사용은 아래와 같다.

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
27
28
29
30
31

<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>hello vue.js</title>
<script src="https://unpkg.com/vue/dist/vue.min.js"></script>
</head>
<body>
<div id="simple">
<h2>{{message}}</h2>
<span>{{sum()}}</span>
</div>
<script type="text/javascript">
var model = {
message : '첫번째 Vue.js 앱 입니다!',
num1 : 0,
num2 : 1
};
var simple = new Vue({
el : '#simple',
data : model,
method: {
sum : function() {
return this.num1 + this.num2;
}
}
})
</script>
</body>
</html>

MVVM 패턴 : View -> View 모델 -> 모델로 데이터가 이동한다. 뷰모델이 중계역할을 함!

mvvm에 대한 이미지 검색결과

  1. 새로운 Vue 객체를 생성

    • el 값에 태그를 입력
    • data에 바인딩시킬 변수를 입력
    • mustache 표현식으로 출력된다!
  2. model.message = '1111'; 과 같은 식으로 변경시 텍스트가 변한다.

    simple.message = ' 111'; simple.$data.message = '1111'; 과도 같다. 인스턴스와 data 옵션 사이에는 프록시를 두어 처리하기 때문!

  3. el : 뷰 인스턴스에 연결할 HTML 돔요소를 지정, 주의할 점은 1개만 등록가능!

  4. method : 뷰 인스턴스에서 사용할 메서드 등록, Mustache 표현식에서도 사용이 가능!

디렉티브

  1. v-text : 와 같음. 화면에 태그 문자열이 그대로 나타남.
  1. v-html : 태그 문자열을 파싱하여 화면에 나타낸다.
1
2
3
4
5
6
7
8
9
10
<h2 v-text="message"></h2>
<h2 v-html="message"></h2>
<script type="text/javascript">
var model = {
message : '<i>랄라</i>'
};
var simple = new Vue({
el : '#simple',
data : model
})
  1. v-bind : 속성 바인딩
    model의 데이터를 속성에 바인딩하고 싶을때 사용한다.

v-bind:src 는 :src와 같다.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
 <div id="simple">
<input id="a" type="text" v-bind:value="message">
<br />
<img v-bind:src="imagePath" />
</div>

<script type="text/javascript">
var model = {
message : 'v-bind 디렉티브',
imagePath : "http://sample.bmaster.kro.kr/photos/61.jpg"
};
var simple = new Vue({
el : '#simple',
data : model
})
</script>
  1. v-model : 양방향 바인딩

1-way바인딩은 모델->뷰 방향만 전달. 2-way바인딩은 뷰-> 모델도 가능하다!

1
2
3
4
5
6
7
8
9
10
11
12
13
<div id="simple">
<input type="text" v-model="name" placeholder="이름을 입력하세요" />
<br />
입력된 이름 : <h2 v-html="name"></h2>
</div>
<script type="text/javascript">
var twoway = new Vue({
el : '#simple',
data : {
name : ''
}
})
</script>
  • 모델 바인딩
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
<div id="simple1">
<div>좋아하는 과일을 모두 골라주세요 : </div>
<input type="checkbox" value="1" v-model="fruits">사과,
<input type="checkbox" value="2" v-model="fruits">키위,
<input type="checkbox" value="3" v-model="fruits">포도
</div>
<hr />
<div id="simple2">
선택한 과일들 : <span v-html="fruits"></span>
</div>
<script type="text/javascript">
var model = {
fruits : []
};
var simple1 = new Vue({
el : '#simple1', data : model
})
var simple2 = new Vue({
el : '#simple2', data : model
});
</script>

다음과 같이 한 모델에 여러 view모델을 바인딩 할 수도 있다.

  1. v-show, v-if, v-else, v-else-if

자세한 설명은 생략한다.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
<div id="account">
잔고 : <input type="text" v-model="balance" />
<br />
회원님의 등급 :
<span v-if="balance >= 1000000">Gold</span>
<span v-else-if="balance >= 500000">Silver</span>
<span v-else-if="balance >= 200000">Bronze</span>
<span v-else>Basic</span>
</div>
<script type="text/javascript">
var simple1 = new Vue({
el : '#account',
data : {
balance : 0
}
})
</script>
  1. v-for : 반복 디렉티브
  • 배열
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
27
28
29
30
<table id="list">
<thead>
<tr>
<th>번호</th><th>이름</th><th>전화번호</th><th>주소</th>
</tr>
</thead>
<tbody id="contacts">
<tr v-for="(contact, index) in contacts">
<td>{{index+1}}</td>
<td>{{contact.name}}</td>
<td>{{contact.address}}</td>
</tr>
</tbody>
</table>
<script type="text/javascript">
var model = {
"pageno": 1,
"pagesize": 10,
"totalcount": 100,
"contacts": [
{ "no": 100,"name": "설현", "address": "서울" },
{ "no": 99, "name": "혜리", "address": "서울" },
{ "no": 98, "name": "하니", "address": "경기" }
]
}
var list = new Vue({
el : "#exmaple",
data : model
});
</script>

(contact, index) in contacts에서 index 생략 가능

  • 객체

해시맵 구조이기 때문에 Key, Value 값을 얻어낼 수 있는 구조 사용

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
<div id="exmaple">
<select id="regions">
<option disabled="disabled" selected>지역을 선택하세요</option>
<option v-for="(val, key, index) in regions" v-bind:value="key">{{ index+1 }} : {{val}}</option>
</select>
</div>
<script type="text/javascript">
var regions = {
"A" : "Asia",
"B" : "America",
"C" : "Europe",
"D" : "Africa",
"E" : "Oceania"
};
var list = new Vue({
el : "#exmaple",
data : { regions : regions }
});
</script>

v-for와 v-if를 함께 사용할 경우, v-for가 먼저 작동합니다.

  • 여러 요소를 묶어 반복 렌더링 : <template>
1
2
3
4
5
6
7
8
9
10
11
<template  v-for="(contact, index) in contacts">
<tr>
<td>{{contact.no}}</td>
<td>{{contact.name}}</td>
<td>{{contact.tel}}</td>
<td>{{contact.address}}</td>
</tr>
<tr class="divider" v-if="index % 5===4">
<td colspan="4"></td>
</tr>
</template>
  • 데이터 변경시 주의할 사항

인덱스 번호로 직접 변경시

contacts[0] = { no:100 }; : 화면 변화없음

내부 속성 변경시

contacts[0].no = 100; : 화면 변화

인덱스 번호를 통해 변경하려면

Vue.set(contacts, 0, {no: 100}); : push, pop, shift등 배열 메서드를 사용하면 변경 추적

  • v-pre : html 요소 컴파일 수행하지 않음
  • v-once : html 요소를 한 번만 렌더링
  • v-cloack : mustache 표현식이 나타났다 사라지는 것을 막는다.
1
2
3
4
5
<style>
[v-clock] {display: none;}
</style>
<div v-cloak>
</div>

Vue 객체의 추가 속성

계산형 속성

v-bind로 간단히 바인딩했지만, 그 속성값에 좀 더 복잡한 로직을 추가하고 싶다면!

computed 속성을 사용하자!

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
27
<input type="text" v-model="num" /><br />
1부터 입력된 수까지의 합 : <span>{{sum}}</span>

<script type="text/javascript">
//1부터 입력된 수까지의 합구하기
var vmSum = new Vue({
el : "#example",
data : { num : 0 },
computed : {
sum : function() {
var n = Number(this.num);
if (Number.isNaN(n) || n < 1) return 0;
return ((1+n) * n) / 2;
},
amount : {
get : function() {
// num이 변경 될때 마다 amount가 호출된다.
return this.num;
},
set : function(amt) {
// amount에 값을 할당했을때, 할당한 값이 amt로 들어온다.
// 비동기 호출시에, setter로 하면 값이 어떻게 될까나?
}
}
}
});
</script>

Vue 모델에 computed라는 속성과 함께 함수를 등록해 두면 속성 처럼 사용할 수 있다.

Vue 인스턴스 method와의 차이는, computed는 결과값이 캐싱된다는점! method는 무조건 실행

  • 주의점!

Computed에서는 Arrow Function 사용않기

computed 내부에서 this 사용할때, Arrow Fuction(=>)을 사용하지 말것!, Arrow Fuction 사용시 this의 컨텍스트가 전역 객체를 가리키게 된다.

데이터 타입 주의

html요소 내부에서는 모두 문자열로 다뤄짐을 알자. 연산시에는 명시적으로 Number(this.num)처럼 형변환이 필요하다.

관찰 속성

watch에 등록된 속성들은, 변경시 마다 호출! 그러나 비동기적으로 호출될때 사용 된다.

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
<div id="example">
x : <input type='text' v-model="x" /><br />
y : <input type='text' v-model="y" /><br />
덧셈 결과 : {{sum}}
</div>
<script type="text/javascript">
var vm = new Vue({
el : "#example",
data : { x:0, y:0, sum:0 },
watch : {
x : function(v) {
console.log('## x 변경')
var result = Number(v) + Number(this.y);
if (isNaN(result)) this.sum = 0;
else this.sum = result;
},
y : function(v) {
console.log('## y 변경')
this.y = v;
var result = Number(this.x) + Number(v);
if (isNaN(result)) this.sum = 0;
else this.sum = result;
}
}
})
</script>

라이프 사이클

1
2
3
4
5
new Vue({
...
beforeCreate : function() {
}
})

위와 같이 시점에 맞게 이벤트가 후킹된다. created updated beforeMount 등이 있다.

Reference

Vue.js Quick Start 원형섭