프레임워크/Vue
[Vue] 이미지 데이터 바인딩 (Require) / v-bind = : & v-on = @ / props, emit
은돌1113
2024. 4. 23. 13:54
1️⃣ 이미지 데이터 바인딩 (Require)
for in을 사용해서 반복문 돌리면서 img src에 데이터 바인딩을 해야 하는 경우가 있었는 데 그 경우 "'./assets/imgs/img' + i + 'jpg'"를 하면 이미지가 정상적으로 노출되지 않는다. 왜냐하면 저렇게 이미지를 불러오는 경우 String 형태로 인식하기 때문에 이 경우 require()를 사용하여 템플릿 내에서 동적으로 이미지 경로를 생성할 수 있습니다.
🖥️ 코드
<img :src="require(`./assets/imgs/img${i}.jpg`)" alt="img" />
📹 참고
2️⃣ Vue 축약어 (속성에 데이터 바인딩 or Props로 데이터 전달, 이벤트 핸들러)
v-bind:test = :test (속성에 데이터 바인딩 or Props로 데이터 전달)
v-on:click = @click (이벤트 핸들러)
3️⃣ 데이터 전달 방법 (Props, Emit)
Modal창 예제를 만들면서 부모에 있는 modal state 값을 자식 컴포넌트에 전달하고, 자식 컴포넌트에서 버튼이나 모달창 외부 영역을 누르면 모달창을 닫을 수 있도록 코드를 작성하던 중 알게 된 부분이다.
Vue는 단방향 통신 방식이기 때문에 부모에서 자식에게 데이터를 전달하는 방식만 가능하지만, 자식에서 부모에게 데이터를 전달할 때는 2가지 방법을 사용할 수 있다고 한다.
- emit을 사용
v-on:# = @method (부모에서 자식으로 메소드 props로 전달) this.$emit("#", state) = props로 전달 받은 메소드를 사용할 때 (주로 부모에 있는 state 값 변경할 때 사용)
- vuex라는 전역 상태 관리 라이브러리 사용
그중에서 emit을 활용하는 방법을 사용해 보았습니다.
🔍 과정
- 부모 컴포넌트에서 modalShow라는 state와 modalHandler라는 메서드를 <Modal/> 컴포넌트로 전달한다.
- 자식 컴포넌트는 props로 modalShow를 받고, v-if를 사용하여 modalShow가 true이면 UI를 노출하고, false라면 UI를 노출하지 않도록 설정한다.
- 자식 컴포넌트에서는 버튼을 눌렀을 때 modalClose() 메서드를 실행할 수 있도록 설정합니다.
(@click = "modalClose") - modalClose() 메서드 내에서는 this.$emit("부모 컴포넌트에서 props로 받아온 메서드 이름", "파라미터로 전달할 값"); 형태로 this.$emit("modal", false)를 전달합니다.
- emit이 실행되면 부모 컴포넌트의 modalHandler 메서드는 파라미터로 전달된 state 값을 가지고, this.modalShow의 값을 변경합니다.
🖥️ 코드
- 부모 컴포넌트(App.vue)
<template> <Modal title="title" content="content" :modalShow="modalShow" @modal="modalHandler" /> <button @click="modalHandler(true)">모달창 열기</button> </template> <script> import Modal from "./components/Modal.vue"; export default { name: "App", components: { Modal, }, // 데이터 보관함 data() { return { modalShow: false, }; }, // 함수(기능) 보관함 methods: { modalHandler(state) { this.modalShow = state; }, }, }; </script> <style> #app { font-family: Avenir, Helvetica, Arial, sans-serif; -webkit-font-smoothing: antialiased; -moz-osx-font-smoothing: grayscale; text-align: center; color: #2c3e50; } </style>
- 자식 컴포넌트(Modal.vue)
<template> <div class="bg" v-if="this.modalShow"> <div class="content"> <h4>{{ title }}</h4> <p>{{ content }}</p> <button @click="modalClose">모달창 닫기</button> </div> </div> </template> <script> export default { name: "ModalComponent", props: { title: { type: String, default: "타이틀", }, content: { type: String, default: "내용", }, modalShow: { type: Boolean, default: false, }, }, methods: { modalClose() { this.$emit("modal", false); }, }, }; </script> <style> .bg { width: 100%; height: 100%; background: rgba(0, 0, 0, 0.5); position: fixed; padding: 20px; } .content { width: 100%; background: white; border-radius: 8px; padding: 20px; } </style>
📹 참고