htmx๋ Bootstrap์ด๋ UIKit๊ณผ ๊ฐ์ CSS ํ๋ ์์ํฌ์ ๋ด์ฅ๋ ๋ค์ด์ผ๋ก๊ทธ์ ์ ์๋ํ์ง๋ง, htmx๋ฅผ ์ฌ์ฉํ๋ฉด ๋ชจ๋ฌ ๋ค์ด์ผ๋ก๊ทธ๋ฅผ ์ฒ์๋ถํฐ ์ฝ๊ฒ ๋ง๋ค ์๋ ์์ต๋๋ค. ์ฌ๊ธฐ์์๋ ๋ชจ๋ฌ ๋ค์ด์ผ๋ก๊ทธ๋ฅผ ๋ง๋๋ ํ ๊ฐ์ง ๋ฐฉ๋ฒ์ ๊ฐ๋จํ ์์๋ก ๋ณด์ฌ๋๋ฆฝ๋๋ค.
์ต์ข ๊ฒฐ๊ณผ์ ๋ฐ๋ชจ๋ฅผ ๋ณด๋ ค๋ฉด ์ฌ๊ธฐ๋ฅผ ํด๋ฆญํ์ธ์:
<button class="btn primary" hx-get="/modal" hx-target="body" hx-swap="beforeend">Open a Modal</button>
์ฐ๋ฆฌ๋ ์๋ฒ์์ ์๊ฒฉ ์ฝํ
์ธ ๋ฅผ ๋ก๋ํ ๋ค์, ์ด๋ฅผ ๋ชจ๋ฌ ๋ค์ด์ผ๋ก๊ทธ์ ํ์ํ๋ ๋ฒํผ์ ๋ง๋ค ๊ฒ์
๋๋ค. ๋ชจ๋ฌ ์ฝํ
์ธ ๋ <body>
์์์ ๋์ #modal
์ด๋ผ๋ ์ด๋ฆ์ div
์ ์ถ๊ฐ๋ ๊ฒ์
๋๋ค.
์ด ๋ฐ๋ชจ์์๋ CSS๋ก ๋ฉ์ง ์ ๋๋ฉ์ด์ ์ ์ ์ํ ๋ค์, ์ฌ์ฉ์๊ฐ ์๋ฃ๋์์ ๋ ๋ชจ๋ฌ์ DOM์์ ์ ๊ฑฐํ๊ธฐ ์ํด Hyperscript๋ฅผ ์ฌ์ฉํ ๊ฒ์ ๋๋ค. htmx์ ํจ๊ป Hyperscript๋ฅผ ๋ฐ๋์ ์ฌ์ฉํ ํ์๋ ์์ง๋ง, ๋ ๊ฐ์ง๋ ํจ๊ป ์ฌ์ฉํ๋๋ก ์ค๊ณ๋์์ผ๋ฉฐ ๋น๋๊ธฐ ๋ฐ ์ด๋ฒคํธ ์ค์ฌ์ ์ฝ๋๋ฅผ ์์ฑํ๋ ๋ฐ JavaScript๋ณด๋ค ํจ์ฌ ๋ ํธ๋ฆฌํ๋ฏ๋ก ์ด ์์์์๋ Hyperscript๋ฅผ ์ ํํ์ต๋๋ค.
<button class="btn primary" hx-get="/modal" hx-target="body" hx-swap="beforeend">Open a Modal</button>
<div id="modal" _="on closeModal add .closing then wait for animationend then remove me">
<div class="modal-underlay" _="on click trigger closeModal"></div>
<div class="modal-content">
<h1>Modal Dialog</h1>
This is the modal content.
You can put anything here, like text, or a form, or an image.
<br>
<br>
<button class="btn danger" _="on click trigger closeModal">Close</button>
</div>
</div>
/***** MODAL DIALOG ****/
#modal {
/* Underlay covers entire screen. */
position: fixed;
top:0px;
bottom: 0px;
left:0px;
right:0px;
background-color:rgba(0,0,0,0.5);
z-index:1000;
/* Flexbox centers the .modal-content vertically and horizontally */
display:flex;
flex-direction:column;
align-items:center;
/* Animate when opening */
animation-name: fadeIn;
animation-duration:150ms;
animation-timing-function: ease;
}
#modal > .modal-underlay {
/* underlay takes up the entire viewport. This is only
required if you want to click to dismiss the popup */
position: absolute;
z-index: -1;
top:0px;
bottom:0px;
left: 0px;
right: 0px;
}
#modal > .modal-content {
/* Position visible dialog near the top of the window */
margin-top:10vh;
/* Sizing for visible dialog */
width:80%;
max-width:600px;
/* Display properties for visible dialog*/
border:solid 1px #999;
border-radius:8px;
box-shadow: 0px 0px 20px 0px rgba(0,0,0,0.3);
background-color:white;
padding:20px;
/* Animate when opening */
animation-name:zoomIn;
animation-duration:150ms;
animation-timing-function: ease;
}
#modal.closing {
/* Animate when closing */
animation-name: fadeOut;
animation-duration:150ms;
animation-timing-function: ease;
}
#modal.closing > .modal-content {
/* Animate when closing */
animation-name: zoomOut;
animation-duration:150ms;
animation-timing-function: ease;
}
@keyframes fadeIn {
0% {opacity: 0;}
100% {opacity: 1;}
}
@keyframes fadeOut {
0% {opacity: 1;}
100% {opacity: 0;}
}
@keyframes zoomIn {
0% {transform: scale(0.9);}
100% {transform: scale(1);}
}
@keyframes zoomOut {
0% {transform: scale(1);}
100% {transform: scale(0.9);}
}