개발노트/Vue.js

[Vue.JS] Vue.js 시작하기

Dahoon06 2021. 9. 30. 17:20
728x90
반응형

Vue.JS 공부 시작은 인프런의 제로초님의 "웹 게임을 만들며 배우는 Vue" 를 보며 시작하였다.

 

학습을 하면서 부가적인 내용이 많아졌기 때문에 따로 정리 해볼려고 한다.

 

<script>태그를 불러와서 Vue.JS 시작하기

npm 에서 다운로드를 받지 않고 <script>태그를 선언하는 것만으로도 Vue.JS 를 시작 할 수 있다.

자세한 내용은 Vue.JS 레퍼런스를 참고하면 자세히 안내되어있다. 

<!-- vue.js 웹 모듈 -->
<script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>

 

첫 단계로 구구단을 만들어 보는 걸로 시작한다.

 

일단 전체적인 HTML 코드는 이렇게 된다.

 

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>구구단</title>
    <!-- vue.js 웹 모듈 -->
    <script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
</head>

<body>
    <div id="root">
        <div> {{firstNum}} X {{secondNum}} = ???</div>
        <form v-on:submit="onSubmitForm">
            <!-- ref 를 통하여 태그에 이름을 줘서 접근할 것이다. input 의 이름은 answer가 되었다.(vue가 부를때) -->
            <input type="number" ref="answer" v-model="value" /> <!-- v-model => vue와 html 바인딩!! data value를 input 과 연결 -->
            <button type="submit">입력</button>
        </form>
        <div id="result">{{result}}</div>
    </div>
</body>

    <script>
        const app = new Vue({
           el: '#root',
           data: {
               firstNum: Math.ceil(Math.random() * 9), // 1~9까지의 숫자 랜덤
               secondNum:Math.ceil(Math.random() * 9),
               value:'',
               result:'',
           },
           methods:{
               onSubmitForm(e){
                   e.preventDefault(); //form의 기능을 막기 위함( 새로고침!! )
                   if(this.firstNum * this.secondNum === parseInt(this.value)){
                       this.result = '정답입니다.!!';

                       this.firstNum = Math.ceil(Math.random() * 9);
                       this.secondNum = Math.ceil(Math.random() * 9);
                       this.value = '';

                       this.$refs.answer.focus();
                   } else {
                       this.result = '틀렸어요..';
                       this.value = '';

                       this.$refs.answer.focus(); // document.querySelect~~이런 느낌의 ref 이다.
                                                    // data 로 접근이 힘들 경우에만 ref를 활용, 항상 data 를 바꿔주는 걸로 생각해야한다.
                   }
               },
           },
        });
    </script>

</html>

 

스크립트 내부에 app이라는 변수에 Vue 인스턴스를 생성하였다.

여기서 중요한건 el, data, methods 이다.

 

el 값에 '#root' 를 통하여 해당 아이디 값을 Vue에서 관리한다고 선언하였다.

 

<div id="root">

       // 이 내부 코드는 이제 Vue에서 관리하게 된다.

</div>

 

설명에의하면 Vue 에서 가장 중요한것은 화면단이 아닌 data의 움직임이라고 한다.

data 에 사용할 변수와 변수값을 설정해줌으로써 화면단에서 해당 data들이 움직이게 될 것이다.

 

thymleaf에서 사용했던 th:onclick="함수"가 Vue에서는 v-on:click="함수" 가 된다.

이때 사용할 함수의 경우 methods 내부에 정의 해주면 된다.

 

thymleaf에서 사용했던 [[변수명]] 또한 vue에서는 {{변수명}} 이 된다.

th:value = "" 의 역할 또한 v-model="변수명"이 되며, 변수명은 data에 선언된 변수값이 된다.

 

** vue를 시작한지 얼마되지 않았기 때문에.. 아직까지는 thymleaf가 익숙하여 비교하여 학습하는게 더 이해하기 편하므로...

 

form태그 내부에 보면 v-on:submit="함수" 있다.

이 속성은 submit이 눌렀을 경우 해당 함수에 v-model="값" 즉, input 값을 해당 함수에 보내 처리 한다는 의미!!

 

Vue에서는 ref 속성을 통하여 해당 태그에 직접 접근이 가능하다.

ref="변수명" 선언하고 Vue 인스턴스 내부에서 해당 $refs.변수명 을 통하여 직접 접근이 가능하다.

하지만 이러한 방법은 해당 태그에 어쩔수 없이 직접 접근할 때 이외에는 사용을 자제해야한다고 한다.

 

if ~ else

두번째 강의에서 Vue 의 조건문이 사용되었다.

 

코드는 이러하다.

<div id="root">
	<div v-if="liked">좋아요 눌렀습니다.</div>
	<button v-else v-on:click="onClickBtn">Like</button>
</div>

단, else를 사용할 때 주의해야할점은 if문은 준 태그와 인접해 있어야 사용가능하다.

 

v-if-else-if 를 사용하여 else if 기능 또한 사용 가능하다.

 

component 처리

이러한 코드가 존재한다.

<div id="root">
	<div>
		<div>{{word}}</div>
		<form v-on:submit="wordList">
			<input type="text" ref="answer" v-model="value" />
			<button type="submit">입력</button>
		<div >{{result}}</div>
		</form>
	</div>
</div>

 

1개의 게임 말고 2개 ..3개 의 게임을 만들고 싶다면?

<div id="root">
	<div>
		<div>{{word}}</div>
		<form v-on:submit="wordList">
			<input type="text" ref="answer" v-model="value" />
			<button type="submit">입력</button>
		<div >{{result}}</div>
		</form>
	</div>
    
    <div>
		<div>{{word}}</div>
		<form v-on:submit="wordList">
			<input type="text" ref="answer" v-model="value" />
			<button type="submit">입력</button>
		<div >{{result}}</div>
		</form>
	</div>
    
    <div>
		<div>{{word}}</div>
		<form v-on:submit="wordList">
			<input type="text" ref="answer" v-model="value" />
			<button type="submit">입력</button>
		<div >{{result}}</div>
		</form>
	</div>
</div>

이렇게 중복된 코드가 발생하게 된다.

또한 영역이 3개가 된 만큼 data 영역에 새로운 변수를 선언해야하고, methods 영역 또한 필요한 메소드를 2개를 더 만들어야한다.

 

이걸 해결하는 방법은 기준이 되는 html 태그를 component 처리 하는 것이다.

 

   <script>
        //Vue component 사용!!
        //전역 컴포넌트
        Vue.component('word-game',{ // Vue.component(tagName, options) references!!!!
            template: `
              <div> <!-- component의 템플릿은 항상 코드를 하나의 태그로 묶어 줘야한다.!! -->
                  <div>{{word}}</div>
                  <form v-on:submit="wordList">
                    <input type="text" ref="answer" v-model="value" />
                    <button type="submit">입력</button>
                    <div >{{result}}</div>
                  </form>
              </div>
            `,
            props: ['startWord'],
            data(){
                return{
                    word: this.startWord,
                    result: '',
                    value: '',
                };
            }, // component에서 데이터를 넣을 때는 항상 함수형으로 만들어 리턴 시켜줘야한다.!!
            methods:{
                wordList(e){
                    e.preventDefault();
                    if(this.word[this.word.length -1] === this.value[0] ){
                        this.result = '정답입니다.';
                        this.word = this.value;

                        this.value = ''; // 인풋칸 비워주기
                        this.$refs.answer.focus();
                    } else {
                        this.result = '틀렸어요';
                        this.value = '';

                        this.$refs.answer.focus();
                    }
                }
            },
        });
    </script>

    <script>
        const app = new Vue({ //Vue instance
           el : '#root',
        });
    </script>

 

app을 보면 Vue instance를 생성하고 그 아래 있던 data와 methods는 component 를 만드는 곳으로 옮겨졌다.

Vue.component('word-game',{ ~~~} 

 

word-game이라는 이름에 해당 component 내용을 저장해 주었다.

<word-game start-word="첫번째 게임"></word-game> 이와같이 컴포넌트를 사용할 수 있게 되었다.

 

이 태그는 컴포넌트 내부의 template의 코드를 사용하게 된다.

자바스크립트에서 CamelCase를 사용하여 변수를 선언하게 되어도
Vue에서는 KebabCase로 변수를 사용해야 적용된다.!! ( Vue 규칙 ) 

 

props를 사용하여 data를 조작할 수 있다.

//component 내부 중 옵션
props: ['startWord'],
data(){
   return{
        word: this.startWord,

word 라는 data를 태그 내부의 props를 통하여 조작 해주었다.

 

위에서 게임을 3개 만들때 전체 코드를 사용하였다면, component를 사용하게 되면

<div id="root">
  <word-game start-word="첫번째 게임"></word-game> <!-- start-word의 경우 componetn에서 props로 받을 것이다.! -->
  <word-game start-word="두번째 게임"></word-game>
  <word-game start-word="마지막"></word-game>
</div>

이와 같이 사용하면 위에서 중복되었던 코드와 동일한 화면이 출력 될것이다.

data영역에 3개의 data를 사용했던 방법과 달리 props 하나만 사용하여 3개의 영역을 변경시킬 수 있게 되었다.

 

이 챕터까지는 HTML에 직접 Vue를 불러와서 사용하므로써 webpack를 사용하지 않고 진행하였다.

 

다음 챕터에서는 webpack을 사용하여 진행하게 된다.


webpack

 

 

728x90
반응형

'개발노트 > Vue.js' 카테고리의 다른 글

[Vue.JS] Composition API  (0) 2023.03.06
[VueJS] 프로젝트 시작  (0) 2021.10.04