-- 1페이지 필기
event 전달
{~~~} -> component
: 특수한 property
(속성)들이 들어감
(template, data, methods, components, props)
component data 전달
1. props
2. event 처리
: 웹페이지간의 이동을 의미
: 우리는 지금 SPA를 하고 있음
: 그래서 전체 page를 다시 그리는게 아니라, 필요한 부분만 다시 그리는 방식으로 page 전환
: Routing 라이브러리 중 가장 대표적인 것
: React, Anguler, Vue 범용
: Vue.js에서는 Vue 라우터(Vue.js의 공식 library)를 이용
Vue 라우터를 위한 CDN
<script src="https://unpkg.com/vue-router@3.5.3/dist/vue-router.js"></script>
230127_Vue01.html
코드넣기
누르면
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
<!-- Vue.js를 이용해보아요! CDN을 포함시켜요 -->
<script src="https://cdn.jsdelivr.net/npm/vue@2.7.14/dist/vue.js"></script>
<!-- Vue 라우터를 위한 CDN을 포함시킴 (*버전 주의) -->
<script src="https://unpkg.com/vue-router@3.5.3/dist/vue-router.js"></script>
</head>
<body>
<div id="app">
<!-- router-link가 없어도 router view는 있어야됨 -->
<router-view></router-view>
</div>
<script>
// member component 생성
let memberComponent = {
template: `<div>
여기는 member component입니다.
<router-view></router-view>
</div>`
// nested routing 가능하도록 router-view 잡아줌
}
// profile component 생성
let profileComponent = {
template: '<div>여기는 profile component</div>'
}
// post component 생성
let postComponent = {
template: '<div>여기는 post component</div>'
}
// 컴포넌트 다 만들었고, 이제 경로 설정
// 어떤 경로가 어떤 컴포넌트와 매칭되는지 설정
// routes => 경로들
let routes = [{
path: '/member', // 이 경로가 들어오면
component: memberComponent,
// children라우팅 안에서 라우팅을 한번 더 잡아줌
// 22번 <router-view></router-view>에 ..
children: [{
path: '/profile', // /member/profile
component: profileComponent
},{
path: '/post', // /member/post
component: postComponent
}]
}]
// 경로를 만든 후, VueRouter객체 생성
let router = new VueRouter({
// routes: routes 는 아래와 같은 의미
routes
})
// 1. Root component(mount가 붙어있으니까)
new Vue({
router
}).$mount('#app')
</script>
</body>
</html>
url 주목!
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
<!-- Vue.js를 이용해보아요! CDN을 포함시켜요 -->
<script src="https://cdn.jsdelivr.net/npm/vue@2.7.14/dist/vue.js"></script>
<!-- Vue 라우터를 위한 CDN을 포함시킴 (*버전 주의) -->
<script src="https://unpkg.com/vue-router@3.5.3/dist/vue-router.js"></script>
</head>
<body>
<!-- EventBus를 이용해서 하위component에서 상위component로 event를 전달 -->
<div id="app">
<!-- router-link가 없어도 router view는 있어야됨 -->
<!-- 하나의 url에 대해서 하나의 component를 넣는게 기본이었음 -->
<!-- named View : 하나의 url에 대해서 여러개의 component를 내가 원하는 위치에 넣어보자 -->
<!-- 각각의 router-view에 이름을 줌 -->
<!-- 이름을 지정하지 않으면 default. -->
<router-view name="header"></router-view>
<router-view></router-view>
<router-view name="footer"></router-view>
</div>
<script>
// 3개의 component 생성
let headerCmp = {
template: '<div>여기는 Header</div>'
}
let bodyCmp = {
template: '<div>여기는 Body</div>'
}
let footerCmp = {
template: '<div>여기는 Footer</div>'
}
let router = new VueRouter({
routes : [{
path: '/', // 이 url에 component를 여러개 쓰겠다 => components
components: {
header: headerCmp,
footer: footerCmp,
default: bodyCmp
}
}]
})
new Vue({
router
}).$mount('#app')
</script>
</body>
</html>
(외부 API를 호출해서 결과를 가져오고 싶음)
: 기존에는 JQuery가 제공하는 AJAX문법을 이용하여 처리해봄
: $.ajax({})
: Vue에서는 AJAX를 어떻게 해야하나요?
: (Vue resource라는 공식 library가 없어지고) Axios라는 외부 library
: JQuery와 대동소이
: 사용하려면 CDN
<script src="https://unpkg.com/axios/dist/axios.min.js"></script>
230127_Vue04.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
<!-- Vue.js를 이용해보아요! CDN을 포함시켜요 -->
<script src="https://cdn.jsdelivr.net/npm/vue@2.7.14/dist/vue.js"></script>
<!-- Vue 라우터를 위한 CDN을 포함시킴 (*버전 주의) -->
<script src="https://unpkg.com/vue-router@3.5.3/dist/vue-router.js"></script>
<!-- Axios를 위한 CDN -->
<script src="https://unpkg.com/axios/dist/axios.min.js"></script>
</head>
<body>
<div id="app">
<button v-on:click="myFunc">AJAX 호출</button>
</div>
<script>
new Vue({
methods:{
myFunc: function(){
// Axios를 이용한 AJAX 호출
// $.ajax({
// success: function() {}
// });
// axios정보로 요청하고 성공하면 then, 실패하면 catch
axios({
// 영화진흥위원회 openAPI
url: 'http://www.kobis.or.kr/kobisopenapi/webservice/rest/boxoffice/searchDailyBoxOfficeList.xml',
method: 'GET',
// data는 POST, PUT, DELETE 메소드방식에만 적용 가능
// data: {
//
// }
// params는 URL parameter를 지칭함
// Query String 방식으로 전달되는 데이터를 의미. 당연히 GET방식 !
// params를 이용해 데이터를 넘겨줌
params:{
key:'8af68cecd7d222e2af7cafbc370d06d9',
targetDt: '20230101'
},
// json이 기본값이라 안 써도 됨
responseType: 'json'
}).then(function() {
alert('호출성공!')
}).catch(function() {
alert('호출실패!')
});
}
}
}).$mount('#app');
</script>
</body>
</html>
① template속성을 이용하여 component를 화면에 출력
: 이 방법은 쉽고 간단하지만, 한계가 있음
② Single File Component 방식
: <template> </template>
: JavaScript객체의 data(Model)를 화면에 표현하기 위해 특수한 표기법으로 연동하는 것
: {{ }} Mustache Syntax
: v-bind
: directive : v-
로 시작하는 tag 속성 ( v-on, v-bind... )
{{ }}
: text interpolation(텍스트 삽입)
v-bind
: HTML의 tag속성(attribute)
: id의 값을 객체와 연동할 때 사용,
: class..
:<div id='app'>
에서 id
{{ }}
의 다양한 사용법230127_Vue05.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
<!-- Vue.js를 이용해보아요! CDN을 포함시켜요 -->
<script src="https://cdn.jsdelivr.net/npm/vue@2.7.14/dist/vue.js"></script>
<!-- Vue 라우터를 위한 CDN을 포함시킴 (*버전 주의) -->
<script src="https://unpkg.com/vue-router@3.5.3/dist/vue-router.js"></script>
<!-- Axios를 위한 CDN -->
<script src="https://unpkg.com/axios/dist/axios.min.js"></script>
</head>
<body>
<!-- EventBus를 이용해서 하위component에서 상위component로 event를 전달 -->
<div id="app">
안녕하세요 ! {{ message }}
</div>
<script>
new Vue({
// template으로 덮어씌움
// div로 감싸야함 왜????
template: `<div>
하이하이 {{ message }}
</div>`,
data: {
message: '홍길동'
}
}).$mount('#app');
</script>
</body>
</html>
230127_Vue06.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
<!-- Vue.js를 이용해보아요! CDN을 포함시켜요 -->
<script src="https://cdn.jsdelivr.net/npm/vue@2.7.14/dist/vue.js"></script>
<!-- Vue 라우터를 위한 CDN을 포함시킴 (*버전 주의) -->
<script src="https://unpkg.com/vue-router@3.5.3/dist/vue-router.js"></script>
<!-- Axios를 위한 CDN -->
<script src="https://unpkg.com/axios/dist/axios.min.js"></script>
<style>
.myStyle{
background-color: skyblue;
}
</style>
</head>
<body>
<!-- EventBus를 이용해서 하위component에서 상위component로 event를 전달 -->
<div id="app">
<div v-bind:id="myID">소리없는 아우성!</div>
<div>텍스트연동은: {{ message }}</div>
<div v-bind:class="styleValue">스타일 연동</div>
<!-- v-bind는 생략 가능 -->
<div v-bind:class="styleValue">스타일 연동</div>
<my-component v-bind:my-data="message"></my-component>
</div>
<script>
// 컴포넌트를 {}생성하면서, Vue.component로 전역컴포넌트로 등록
Vue.component('my-component', {
props : ['myData'],
template: '<div>전달된 데이터: {{ myData}} </div>'
});
new Vue({
data: {
message: '소리없는 아우성!',
myID: 'myDiv',
styleValue: 'myStyle'
}
}).$mount('#app');
</script>
</body>
</html>
{{ }}
의 다양한 사용법230127_Vue07.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
<!-- Vue.js를 이용해보아요! CDN을 포함시켜요 -->
<script src="https://cdn.jsdelivr.net/npm/vue@2.7.14/dist/vue.js"></script>
<!-- Vue 라우터를 위한 CDN을 포함시킴 (*버전 주의) -->
<script src="https://unpkg.com/vue-router@3.5.3/dist/vue-router.js"></script>
<!-- Axios를 위한 CDN -->
<script src="https://unpkg.com/axios/dist/axios.min.js"></script>
</head>
<body>
<div id="app">
<div>{{ message }}</div>
<div>{{ message + "!!!" }}</div>
<!-- 아래의 표현은 가능하지만 좋지 X -->
<!-- {{ }}는 가능한 값만 출력하는 역할을 하는게 좋음 -->
<!-- 아래와 같은 경우는 함수를 따로 만들어서 사용하는게 좋음 -->
<div>{{ message.split('').reverse().join('') }}</div>
<!-- <div>{{ let a = 100; }}</div> 이런 거 안 됨 -->
<!-- <div>{{ if(true){ return 100 }}}</div> 이런 거안 됨-->
<div>{{ true ? 10 : 100 }}</div>
<!-- 이 코드는 좋지 않아서 함수를 따로 만들어보자 -->
<div>{{ message.split('').reverse().join('') }}</div>
<!-- 이렇게 바꿈 -->
<div>{{ myFunc() }}</div>
<div>{{ myFunc() }}</div>
<!-- 이런 함수와 약간 다른 성능이 좋은 기능이 있음 -->
<div>{{ myComputed }}</div>
</div>
<script>
new Vue({
data: {
message: '소리없는 아우성',
},
// methods는 안에 있는 함수를 명시적으로 호출
methods: {
myFunc: function(){
console.log('함수호출');
return this.message.split('').reverse().join('')
}
},
// 용도에 따라
// methods는 함수, computed는 변수
// methods보다 computed가 효율적
// computed는 명시적으로 호출하는게 아니라
// 데이터가 변경되는 시점에 미리 계산된 결과를 가져다씀
computed: {
myComputed: function(){
console.log('Computed호출');
return this.message.split('').reverse().join('')
}
}
}).$mount('#app');
</script>
</body>
</html>
: HTML속성에 나오는v-
접두사를 가지는 모든 속성
: v-on:
, v-bind:
...
① v-if
② v-show
③ v-bind
④ v-on
⑤ v-model
: form에서 사용
: 사용자가 입력한 데이터를 component의 data와 연동 가능
: + watch의 속성까지 알아봤음
⑥ v-for : 반복처리
v-if & v-show
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
<!-- Vue.js를 이용해보아요! CDN을 포함시켜요 -->
<script src="https://cdn.jsdelivr.net/npm/vue@2.7.14/dist/vue.js"></script>
<!-- Vue 라우터를 위한 CDN을 포함시킴 (*버전 주의) -->
<script src="https://unpkg.com/vue-router@3.5.3/dist/vue-router.js"></script>
<!-- Axios를 위한 CDN -->
<script src="https://unpkg.com/axios/dist/axios.min.js"></script>
</head>
<body>
<div id="app">
<div v-bind:id="myID">소리없는 아우성</div>
<!-- 만약 v-if의 값이 false면 DOM에서(구성요소에서) 제거 -->
<a v-if="flag" href="http://www.naver.com">네이버로 가기</a>
<br><br>
<!-- v-show의 값이 false일 경우, 화면에서 안 보이지만 DOM에는 존재함 -->
<a v-show="flag" href="http://www.kakao.com">카카오로 가기</a>
</div>
<script>
// Vue instance
new Vue({
data:{
// flag가 false면 DOM에서(구성요소에서) 제거
flag: false,
myID: 'myDIV'
}
}).$mount('#app');
</script>
</body>
</html>
v-show는 false일 경우, 화면에서 안 보이지만 DOM에는 존재함
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
<!-- Vue.js를 이용해보아요! CDN을 포함시켜요 -->
<script src="https://cdn.jsdelivr.net/npm/vue@2.7.14/dist/vue.js"></script>
<!-- Vue 라우터를 위한 CDN을 포함시킴 (*버전 주의) -->
<script src="https://unpkg.com/vue-router@3.5.3/dist/vue-router.js"></script>
<!-- Axios를 위한 CDN -->
<script src="https://unpkg.com/axios/dist/axios.min.js"></script>
</head>
<body>
<div id="app">
<div v-bind:id="myID">소리없는 아우성</div>
<!-- 만약 v-if의 값이 false면 DOM에서(구성요소에서) 제거 -->
<a v-if="flag" href="http://www.naver.com">네이버로 가기</a>
<br><br>
<!-- v-show의 값이 false일 경우, 화면에서 안 보이지만 DOM에는 존재함 -->
<a v-show="flag" href="http://www.kakao.com">카카오로 가기</a>
<br><br>
<input v-model="myTxt">
<button v-on:click="myFunc">입력상자 안 내용을 알아보아요!</button>
</div>
<script>
// Vue instance
new Vue({
data:{
// flag가 false면 DOM에서(구성요소에서) 제거
flag: false,
myID: 'myDIV',
myTxt: ''
},
methods: {
myFunc: function(){
alert(this.myTxt);
}
}
}).$mount('#app');
</script>
</body>
</html>
v-model + watch
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
<!-- Vue.js를 이용해보아요! CDN을 포함시켜요 -->
<script src="https://cdn.jsdelivr.net/npm/vue@2.7.14/dist/vue.js"></script>
<!-- Vue 라우터를 위한 CDN을 포함시킴 (*버전 주의) -->
<script src="https://unpkg.com/vue-router@3.5.3/dist/vue-router.js"></script>
<!-- Axios를 위한 CDN -->
<script src="https://unpkg.com/axios/dist/axios.min.js"></script>
</head>
<body>
<div id="app">
<div v-bind:id="myID">소리없는 아우성</div>
<!-- 만약 v-if의 값이 false면 DOM에서(구성요소에서) 제거 -->
<a v-if="flag" href="http://www.naver.com">네이버로 가기</a>
<br><br>
<!-- v-show의 값이 false일 경우, 화면에서 안 보이지만 DOM에는 존재함 -->
<a v-show="flag" href="http://www.kakao.com">카카오로 가기</a>
<br><br>
<input v-model="myTxt">
<button v-on:click="myFunc">입력상자 안 내용을 알아보아요!</button>
</div>
<script>
// Vue instance
new Vue({
data:{
// flag가 false면 DOM에서(구성요소에서) 제거
flag: false,
myID: 'myDIV',
myTxt: ''
},
methods: {
myFunc: function(){
alert(this.myTxt);
}
},
watch: {
myTxt: function(data){
console.log(data, '로 변경되었어요!');
}
}
}).$mount('#app');
</script>
</body>
</html>
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
<!-- Vue.js를 이용해보아요! CDN을 포함시켜요 -->
<script src="https://cdn.jsdelivr.net/npm/vue@2.7.14/dist/vue.js"></script>
<!-- Vue 라우터를 위한 CDN을 포함시킴 (*버전 주의) -->
<script src="https://unpkg.com/vue-router@3.5.3/dist/vue-router.js"></script>
<!-- Axios를 위한 CDN -->
<script src="https://unpkg.com/axios/dist/axios.min.js"></script>
</head>
<body>
<div id="app">
<div v-bind:id="myID">소리없는 아우성</div>
<!-- 만약 v-if의 값이 false면 DOM에서(구성요소에서) 제거 -->
<a v-if="flag" href="http://www.naver.com">네이버로 가기</a>
<br><br>
<!-- v-show의 값이 false일 경우, 화면에서 안 보이지만 DOM에는 존재함 -->
<a v-show="flag" href="http://www.kakao.com">카카오로 가기</a>
<br><br>
<input v-model="myTxt">
<button v-on:click="myFunc">입력상자 안 내용을 알아보아요!</button>
<br><br>
<ul>
<li v-for="name in names">{{ name }}</li>
</ul>
</div>
<script>
// Vue instance
new Vue({
data:{
// flag가 false면 DOM에서(구성요소에서) 제거
flag: false,
myID: 'myDIV',
myTxt: '',
names:['홍길동', '신사임당', '강감찬']
},
methods: {
myFunc: function(){
alert(this.myTxt);
}
},
watch: {
myTxt: function(data){
console.log(data, '로 변경되었어요!');
}
}
}).$mount('#app');
</script>
</body>
</html>
:Vue CLI를 이용한 Sigle File Component 체계