css:resize
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 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97
| <!DOCTYPE html> <html lang="ko"> <head> <meta charset="UTF-8"> <meta http-equiv="X-UA-Compatible" content="IE=edge"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>Answer</title> <style> .resizable { resize: both; border: 2px solid blue; overflow: hidden; position: relative; }
.resizable::after{ position: absolute; display: block; bottom: 0; right: 0; width: 10px; height: 10px; background-color: blue; content: ""; cursor: nwse-resize; } </style> </head> <body> <h1>Answer</h1> <form name="image"> <input type="text" name="src" value="./example.jpg"> <button type="submit">불러오기</button> </form> <script> const MAX_WIDTH = 800; const MIN_WIDTH = 300;
const generateRandomId = () => btoa(Math.random()).substr(0, 12); const observer = new MutationObserver((mutations) => { mutations.forEach((mutation) => { const wrap = mutation.target; switch (mutation.attributeName) { case 'style': { let nextWidth = parseInt(wrap.style.width); if (nextWidth > MAX_WIDTH) { nextWidth = MAX_WIDTH; } else if (nextWidth < MIN_WIDTH) { nextWidth = MIN_WIDTH; }
wrap.style.width = `${nextWidth}px`; wrap.style.height = `${nextWidth / wrap.dataset.ratio}px`; } } }); });
const loadImage = (src) => { const id = generateRandomId(); const img = new Image(); img.src = `${src}?v=${id}`; img.id = id; img.onload = (event) => { const _img = document.getElementById(id); const _wrap = _img.parentElement; const { width, height } = _img.getBoundingClientRect();
_wrap.style.width = `${width}px`; _wrap.style.height = `${height}px`; _wrap.dataset.ratio = String((width / height).toFixed(2)); _img.style.width = '100%'; _img.style.height = '100%'; };
const wrap = document.createElement('div'); wrap.classList.add('resizable'); wrap.appendChild(img); document.body.appendChild(wrap); observer.observe(wrap, { attributes: true, }); }
document.forms.image.addEventListener('submit', (event) => { event.preventDefault();
const src = event.target.src.value; if (src) { loadImage(src); } });
</script> </body> </html>
|
js:resize
- 시간될 때 구현해보자.
- handler 를 만들고, nw, ne, sw, se 방향에 childNode를 각각 만들고 after content 로 영역을 생성해야한다.
여담
- 컴포넌트의 기본 단위라고 생각되는 것들에 대해 vanila 로 스니펫을 많이 만들어봐야될 것 같다.
- react-movable React 와 여러 Util Class 를 사용하여 Commits on Aug 12, 2019 부터 만든 것 같은데, 90m 안에 가능했던걸까.