I. 스타일 파일구조 관련
1) css 는 public? asstet?
public 은 변환기를 가치지 않는 영역이야
CSS 가 그대로 간다는거야
assat에 있는 css는 변환기를 거쳐 안좋을수도 있는데, 장점이 있어
minify / minified 은 배포용으로 화이트스페이스가 없는 한줄짜리임
개발버전과 배보버전 다름
2)
페이지는 하나인데, 컴포넌트가 있을 떄 어떡해야?
헤더푸터는 루트 레이아웃
나머지는 멤버에 들어가는 레이아웃
다른것은 어드민에 들어가는 레이아웃
vue에다가 넣을 수 있지만, 공통화 하기가 어려움
II. Vue.js
1. 들어가며
(1)
1)
어제 newlist 에다가 props 로 값을 전달할 수 있다.
2. 모달 띄어보기
(1) Modal.vue 파일 만들기와 slot
1) 파일만들기
modal 로 띄어보자
<Modal.vue>
<script setup>
let props = defineProps({
title : ""
});
</script>
<template>
<section>
<h1>{{ props.title }}</h1>
<div>
</div>
<div>
<button>OK</button>
<button>CANCEL</button>
</div>
</section>
</template>
<style scoped>
</style>
새로운 vue 파일을 만든다.
<App.vue>
<!-- <newList :list="model.newList" :title="추천메뉴" :b="b" /> -->
<newList :list="model.newList" :title="b" />
<Modal title="공지사항" />
</template>
2) modal 에서 컨텐트 부분 가져오기 [ slot ]
이 경우 모달은 띄우기만하고, 컨텐츠는 메인에서 받아오는 방식인경우...
<App.vue>
<Modal title="공지사항" >
<div>
안녕하세요 ㅋㅅㅋ
</div>
</Modal>
이 경우 slot 을 쓰자
<Modal.vue>
<template>
<section>
<h1>{{ props.title }}</h1>
<div>
<slot></slot>
</div>
<div>
<button>OK</button>
<button>CANCEL</button>
</div>
</section>
</template>
<slot> 을 쓰면 저기에 컨텐트가 들어간다
<style scoped>
section{
background-color: red;
}
</style>
스타일도 쉽게 지정이 가능하다.
(2) Modal 띄우기
1) Model.vue
<template>
<div class="screen">
<section>
<h1>{{ props.title }}</h1>
<div class="content">
<slot></slot>
</div>
<div class="commadns">
<button>OK</button>
<button>CANCEL</button>
</div>
</section>
</div>
</template>
스타일설정
<style scoped>
.screen{
background-color: rgba(0, 0, 0, 0.79);
/* opacity: 0.8; */
position: fixed;
left: 0;
top : 0;
/* 부모기준 */
/* width: 100%; */
/* 화면기준 */
width: 100vw;
height: 100vh;
display: flex;
flex-direction: column;
justify-content: center;
align-items: center;
}
section{
background-color: #fff;
display: inline-block;
border-radius: .7em;
}
section>h1{
font-size: 14px;
padding: 0px 10px;
}
section>.content{
border-top: 1px solid;
border-bottom: 1px solid;
padding: 10px 20px;
}
section > .commadns{
display: flex;
justify-content: space-around;
}
/* .screen >section{
opacity: 1;
} */
</style>
모달을 띄우는데, 이 경우 크기나 위치에 대해서 잘 고민해야한다
화면 기준이라면 vw,vh 로 하고/ 부모 기준이라면 % 로 한다.
3. 버튼 눌렀을 때 모달 출력하기
(1) 버튼만들기
1) <button> 만들고, showModl에 값넣기
이렇게 해서 버튼을 누르면 무엇이 뜨게 해야해
<App.vue>
<script>
let showModal = ref(false);
function showHandler(){
console.log("showHandler");
showModal.value = true;
}
</script>
<template>
<div>
<button @click="showHandler">show</button>
</div>
<Modal title="공지사항" :show="showModal">
<div>
안녕하세요 ㅋㅅㅋ<br>
소머리 깎아라
</div>
</Modal>
우선 <button> 태그를 만든다
그러고 나서 이 태그에 대한 이벤트핸들러로 showModal이라는 반응형 값을 가지게한다.
<modal.vue>
<script setup>
let props = defineProps({
title : "",
show : false
});
</script>
<template>
<div class="screen" :class="{'d-none':!props.show}">
<section>
<h1>{{ props.title }}</h1>
<div class="content">
<slot></slot>
</div>
<div class="commadns">
<button>OK</button>
<button>CANCEL</button>
</div>
</section>
</div>
</template>
:class 에서 active 라는 클래스를 넣기위해서는 isActive 가 true 여야한다
이런것 처럼 위 코드에도 d-none 이 적용되기 위해서는 props.show 가 true 여야한다
그렇기 때문에 show 는 true 여야 modal 이 출력된다.
2) "OK" 버튼눌렀을 때 반응시키기
<script setup>
let props = defineProps({
title : "",
show : false
});
function okHandler(){
props.show=false;
}
</script>
<template>
<div class="screen" :class="{'d-none':!props.show}">
<section>
<h1>{{ props.title }}</h1>
<div class="content">
<slot></slot>
</div>
<div class="commadns">
<button @click="okHandler">OK</button>
<button>CANCEL</button>
</div>
</section>
</div>
</template>
OK 를 클릭 했을 때 핸들러로 값을 전달한다.
그런데 props.show 는 읽기전용이다 readonly 라서 값을 전달할 수없다.
3) emit
그러면 다른방식으로 닫아보자 emit!!
<App.vue>
<script setup>
function dlgOkhandler(){
//
console.log("d오케이 한거임?");
showModal.value=false;
}
</script>
<template>
<div>
<button @click="showHandler">show</button>
</div>
<Modal title="공지사항" :show="showModal" @ok="dlgOkhandler">
<div>
안녕하세요 ㅋㅅㅋ<br>
소머리 깎아라
</div>
</Modal>
</template>
@ok 라는 이벤트 핸들러를 컴포넌트에서 받는다.
<Modal.vue>
<script setup>
let props = defineProps({
title : "",
show : false
});
function okHandler(){
props.show=false;
}
</script>
<template>
<div class="screen" :class="{'d-none':!props.show}">
<section>
<h1>{{ props.title }}</h1>
<div class="content">
<slot></slot>
</div>
<div class="commadns">
<button @click="$emit('ok')">OK</button>
<button>CANCEL</button>
</div>
</section>
</div>
</template>
이벤트는 $emit() 를 해서 'OK' 라는 이벤트를 기본 레이아웃으로 보내주는것이다.
4) emit 에 대한 고찰
두개 emit(a,b) 보내주면 이렇게 두개나옴
5) $event 란?
$event 는 뭐임? 이벤트 객체 보내주는것이다
즉 emit(a, $event) 로 하는 방식이다
4. 모달 출력에 트랜지션 하기
(1)
1)
모달버튼이 발생할 때 이동시키는 트랜지션 하기!
<script setup>
let props = defineProps({
title : "",
show : false
});
function okHandler(){
props.show=false;
}
</script>
<template>
<div class="screen" :class="{'d-none':!props.show}">
<section :class="{'show-effect':props.show}">
<h1>{{ props.title }}</h1>
<div class="content">
<slot></slot>
</div>
<div class="commadns">
<button @click="$emit('ok',$event)">OK</button>
<button>CANCEL</button>
</div>
</section>
</div>
</template>
<style scoped>
@keyframes show-effect {
from{
transform: translateY(-300px);
}
to{
transform: translateY(-200px);
}
}
section.show-effect{
animation: show-effect 0.5s forwards;
}
</style>
미리 실행이 되었기 때문에, 이미 기존에 트랜지션방식은 완수가 되었다
이런 상황을 미연에 방지하기 위해서 모달 발생 이벤트가 있을 때 마다 실행하기 위해서 @keyframes 를 이용한다.
1. 보충
2. 회고
1) 모달을 dom 을 안쓰고 이렇게 할 수있어서 재밌다.
'배움 __IL > TIL 1기' 카테고리의 다른 글
TIL : 102번째- 230503 [5-1-수] (0) | 2023.05.03 |
---|---|
TIL : 101번째- 230501 [5-1-월] (0) | 2023.05.01 |
TIL : 99번째- 230427 [4-4-목] (0) | 2023.04.27 |
TIL : 98번째- 230426 [4-4-수] (0) | 2023.04.26 |
TIL : 97번째- 230425 [4-4-화] (1) | 2023.04.25 |