NodeJS

[NodeJs/VueJs] ref 속성을 이용하여 자식 엘리먼트에 접근해보자

Question영 2019. 12. 5. 13:35
반응형

Vue 에 대한 복습을 하다가 ref 속성에 대한 내용이 잘 이해가 안가서 포스팅으로 정리하여 남깁니다.

 

분명히 그전 공부에선 이해하고 넘어갔던 기억이 있는데...

 

머리가 역시 돌인가 봅니다.

 

그럼 간략하게 정리해보도록 하겠습니다!

 

 

이전 포스팅에서 상위, 하위 컴포넌트간 데이터 전달 방법 에 대해 정리한 적 있습니다.

 

[NodeJs/VueJs] 상위, 하위 컴포넌트간 데이터 전달 방법

안녕하세요. 이번에는 Vue 를 사용하면서 저를 많이 혼란스럽게 했던 기능 중 주요 기능인 상위, 하위 컴포넌트간 데이터 전달 방법에 대해 살펴보려고 합니다. 오늘도 미래의 저에게 도움이 될수 있기를! 요 근래..

question0.tistory.com

 

간략하게 v-bind, $emit, v-model 을 이용하여 부모와 자식 컴포넌트 간의 데이터를 주고 받는 내용을 정리했었는데요.

 

저는 이 부분에 해당하는 내용과 ref 속성이 다루고있는 내용을 헷갈렸었습니다.

 

엄밀히 말하면 전~혀 다른 내용인데 말이죠.

 

v-bind, $emit, v-model 들은 데이터를 전달을 담당하는 방면

 

ref 속성은 자식 엘리먼트에 접근하는 기능 입니다.

 

물론 접근해서 데이터를 가져오는 것은 가능하지만 엄현히 접근 까지가 역할입니다.

 

개인적으로 자바스크립트의 getElementById, getElementsByClass ...등의 getElement 함수와

 

querySelector 함수와 같은 비슷한 역할을 합니다.

 

사용법

 

# HelloWorld.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
32
33
34
35
36
<template>
  <div class="hello">
    <h1>{{ msg }}</h1>
    <child ref="usernameInput"></child>
    <button @click="onClick">클릭</button>
  </div>
</template>
 
<script>
import child from '@/components/Child'
 
export default {
  name'HelloWorld',
  data () {
    return {
      msg: 'Welcome to Your Vue.js App'
    }
  },
  components: {
    child
  },
  methods: {
    onClick () {
      const el = this.$refs.usernameInput.$el
      this.$refs.usernameInput.focus()
      console.log('Parents!', el)
    }
  }
}
</script>
 
<!-- Add "scoped" attribute to limit CSS to this component only -->
<style scoped>
...
</style>
 
cs

 

# Child.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
<template>
  <div class="hello">
    <h1>{{ msg }}</h1>
    <input id="contactInput" ref="test"/>
  </div>
</template>
 
<script>
export default {
  name'Child',
  data () {
    return {
      msg: 'Child Page!'
    }
  },
  methods: {
    focus () {
      console.log('매서드의 함수 실행')
      this.$refs.test.focus()
    }
  }
}
</script>
 
cs

 

위의 예제 처럼 Vue 를 기본적으로 생성했을때 만들어지는

 

HelloWorld.vue 파일을 수정하고

 

Child.vue 라는 vue 파일을 만들어봅시다.

 

중요한 것은 접근 이라고 말했었습니다.

 

 

1
<child ref="usernameInput"></child>
cs

 

태그에 id 속성을 적용하는 것처럼 ref 도 동일하게 적용합니다.

 

1
2
3
4
5
6
7
methods: {
  onClick () {
    const el = this.$refs.usernameInput.$el
    this.$refs.usernameInput.focus()
    console.log('Parents!', el)
  }
}
cs

 

ref 속성을 부여한 자식 태그를 호출하기 위해서는 this.$refs 라는 키워드를 사용합니다.

 

플젝을 실행하여 구성된 버튼을 클릭해보시면

 

콘솔창에 정상적으로 지정된 자식 엘리먼트 정보를 가져오는 것을 확인하실수 있습니다.

 

그리고 위의 예제에서 하나 더 확인 하실수 있는 사항은

 

자식 엘리먼트의 대상은 태그로 구성된 대상을 의미한다는 걸 알수 있으실겁니다.

 

좀 더 쉽게 이야기 해서 그냥 태그로 구성된 엘리먼트는 물론 vue 에서 사용하는 컴포넌트도 자식 엘리먼트라면

 

접근 가능한 대상으로 보는 것이죠.

 

1
2
3
4
focus () {
  console.log('매서드의 함수 실행')
  this.$refs.test.focus()
}
cs

 

자식 컴포넌트로 접근했을 경우는 해당 Vue 컴포넌트의 method 함수에도 같이 접근이 가능합니다.

 

위의 예제는 Child.vue 템플릿에 설정되어 있는 input 태그에 ref 속성을 이용하여 focus 를 주도록 했는데요.

 

예제를 실행하여 HelloWorld.vue 에서 설정되어 있는 버튼을 클릭해보신다면

 

input 태그에 정상적으로 focus 가 되는 것을 확인 하실수 있습니다.

 

유의 사항

 

  • 개발자가 DOM 을 직접 다루지 않는 뷰의 목적 중 하나에 위배
  • ref 속성은 컴포넌트가 랜더링이 된 이후 적용되기 때문에 반응형으로 구성하기 위한 computed 나 template 에서 사용하면 안됨

 

결론

 

Vue 방식으로 ref 속성을 사용하는 것은 Vue 의 기본 컨셉에 위배가 되나 기존 DOM 을 접근하는 방식보다 깔끔하고 편리하다.

 

개인적으로 Vue 로 구성하는 프로젝트이기 때문에 자주 사용할 것 같네요.

 


참고 자료

반응형