diff options
Diffstat (limited to 'src/Layout.mjs')
-rw-r--r-- | src/Layout.mjs | 88 |
1 files changed, 44 insertions, 44 deletions
diff --git a/src/Layout.mjs b/src/Layout.mjs index 9cf2ab9..3a835c9 100644 --- a/src/Layout.mjs +++ b/src/Layout.mjs | |||
@@ -1,9 +1,9 @@ | |||
1 | import PlainDraggable from "plain-draggable"; | 1 | import PlainDraggable from 'plain-draggable'; |
2 | import { onRemove, animateRectTransition } from "./utils"; | 2 | import { onRemove, animateRectTransition } from './utils'; |
3 | 3 | ||
4 | export class Layout { | 4 | export class Layout { |
5 | constructor(options = {}) { | 5 | constructor(options = {}) { |
6 | if (!options.name) throw Error("Layout name is not given"); | 6 | if (!options.name) throw Error('Layout name is not given'); |
7 | this.name = options.name; | 7 | this.name = options.name; |
8 | this.enterHandler = options.enterHandler; | 8 | this.enterHandler = options.enterHandler; |
9 | this.leaveHandler = options.leaveHandler; | 9 | this.leaveHandler = options.leaveHandler; |
@@ -12,63 +12,63 @@ export class Layout { | |||
12 | } | 12 | } |
13 | 13 | ||
14 | export class SideBySide extends Layout { | 14 | export class SideBySide extends Layout { |
15 | name = "side-by-side"; | 15 | name = 'side-by-side'; |
16 | 16 | ||
17 | enterHandler = ({ container, htmlHolder, showcase }) => { | 17 | enterHandler = ({ container, htmlHolder, showcase }) => { |
18 | const bar = document.createElement("div"); | 18 | const bar = document.createElement('div'); |
19 | bar.className = "bar"; | 19 | bar.className = 'bar'; |
20 | bar.innerHTML = '<div class="bar-handle"></div>'; | 20 | bar.innerHTML = '<div class="bar-handle"></div>'; |
21 | const handle = bar.querySelector(".bar-handle"); | 21 | const handle = bar.querySelector('.bar-handle'); |
22 | container.appendChild(bar); | 22 | container.appendChild(bar); |
23 | 23 | ||
24 | // Resize views by value | 24 | // Resize views by value |
25 | const resizeByLeft = left => { | 25 | const resizeByLeft = left => { |
26 | htmlHolder.style.width = left + "px"; | 26 | htmlHolder.style.width = left + 'px'; |
27 | showcase.style.width = | 27 | showcase.style.width = |
28 | parseFloat(getComputedStyle(container).width) - left + "px"; | 28 | parseFloat(getComputedStyle(container).width) - left + 'px'; |
29 | }; | 29 | }; |
30 | 30 | ||
31 | const draggable = new PlainDraggable(bar, { | 31 | const draggable = new PlainDraggable(bar, { |
32 | handle: handle, | 32 | handle: handle, |
33 | containment: { left: "25%", top: 0, right: "75%", height: 0 }, | 33 | containment: { left: '25%', top: 0, right: '75%', height: 0 }, |
34 | }); | 34 | }); |
35 | draggable.draggableCursor = "grab"; | 35 | draggable.draggableCursor = 'grab'; |
36 | 36 | ||
37 | draggable.onDrag = pos => { | 37 | draggable.onDrag = pos => { |
38 | handle.style.transform = "unset"; | 38 | handle.style.transform = 'unset'; |
39 | resizeByLeft(pos.left); | 39 | resizeByLeft(pos.left); |
40 | }; | 40 | }; |
41 | draggable.onDragEnd = _ => { | 41 | draggable.onDragEnd = _ => { |
42 | handle.removeAttribute("style"); | 42 | handle.removeAttribute('style'); |
43 | }; | 43 | }; |
44 | 44 | ||
45 | onRemove(bar, () => draggable.remove()); | 45 | onRemove(bar, () => draggable.remove()); |
46 | }; | 46 | }; |
47 | 47 | ||
48 | leaveHandler = ({ container }) => { | 48 | leaveHandler = ({ container }) => { |
49 | container.querySelector(".bar")?.remove(); | 49 | container.querySelector('.bar')?.remove(); |
50 | }; | 50 | }; |
51 | } | 51 | } |
52 | 52 | ||
53 | export class Overlay extends Layout { | 53 | export class Overlay extends Layout { |
54 | name = "overlay"; | 54 | name = 'overlay'; |
55 | 55 | ||
56 | saveLeftTopAsData = element => { | 56 | saveLeftTopAsData = element => { |
57 | const { left, top } = element.getBoundingClientRect(); | 57 | const { left, top } = element.getBoundingClientRect(); |
58 | element.setAttribute("data-left", left); | 58 | element.setAttribute('data-left', left); |
59 | element.setAttribute("data-top", top); | 59 | element.setAttribute('data-top', top); |
60 | }; | 60 | }; |
61 | 61 | ||
62 | addDraggable = element => { | 62 | addDraggable = element => { |
63 | // Make sure current element always on top | 63 | // Make sure current element always on top |
64 | const siblings = Array.from( | 64 | const siblings = Array.from( |
65 | element.parentElement?.querySelectorAll(":scope > *") ?? [], | 65 | element.parentElement?.querySelectorAll(':scope > *') ?? [], |
66 | ); | 66 | ); |
67 | let popTimer = null; | 67 | let popTimer = null; |
68 | element.onmouseover = () => { | 68 | element.onmouseover = () => { |
69 | popTimer = setTimeout(() => { | 69 | popTimer = setTimeout(() => { |
70 | siblings.forEach(e => e.style.removeProperty("z-index")); | 70 | siblings.forEach(e => e.style.removeProperty('z-index')); |
71 | element.style.zIndex = "9001"; | 71 | element.style.zIndex = '9001'; |
72 | }, 200); | 72 | }, 200); |
73 | }; | 73 | }; |
74 | element.onmouseout = () => { | 74 | element.onmouseout = () => { |
@@ -76,9 +76,9 @@ export class Overlay extends Layout { | |||
76 | }; | 76 | }; |
77 | 77 | ||
78 | // Add draggable part | 78 | // Add draggable part |
79 | const draggablePart = document.createElement("div"); | 79 | const draggablePart = document.createElement('div'); |
80 | element.appendChild(draggablePart); | 80 | element.appendChild(draggablePart); |
81 | draggablePart.className = "draggable-part"; | 81 | draggablePart.className = 'draggable-part'; |
82 | draggablePart.innerHTML = '<div class="handle">\u2630</div>'; | 82 | draggablePart.innerHTML = '<div class="handle">\u2630</div>'; |
83 | 83 | ||
84 | // Add draggable instance | 84 | // Add draggable instance |
@@ -91,16 +91,16 @@ export class Overlay extends Layout { | |||
91 | }); | 91 | }); |
92 | 92 | ||
93 | // FIXME use pure CSS to hide utils | 93 | // FIXME use pure CSS to hide utils |
94 | const utils = element.querySelector(".utils"); | 94 | const utils = element.querySelector('.utils'); |
95 | draggable.onDragStart = () => { | 95 | draggable.onDragStart = () => { |
96 | utils.style.display = "none"; | 96 | utils.style.display = 'none'; |
97 | element.classList.add("drag"); | 97 | element.classList.add('drag'); |
98 | }; | 98 | }; |
99 | 99 | ||
100 | draggable.onDragEnd = () => { | 100 | draggable.onDragEnd = () => { |
101 | utils.style = ""; | 101 | utils.style = ''; |
102 | element.classList.remove("drag"); | 102 | element.classList.remove('drag'); |
103 | element.style.zIndex = "9000"; | 103 | element.style.zIndex = '9000'; |
104 | }; | 104 | }; |
105 | 105 | ||
106 | // Reposition draggable instance when resized | 106 | // Reposition draggable instance when resized |
@@ -125,12 +125,12 @@ export class Overlay extends Layout { | |||
125 | // Create draggable blocks and set each position by previous one | 125 | // Create draggable blocks and set each position by previous one |
126 | let [left, top] = [20, 20]; | 126 | let [left, top] = [20, 20]; |
127 | blocks.forEach(block => { | 127 | blocks.forEach(block => { |
128 | const originLeft = Number(block.getAttribute("data-left")); | 128 | const originLeft = Number(block.getAttribute('data-left')); |
129 | const originTop = Number(block.getAttribute("data-top")); | 129 | const originTop = Number(block.getAttribute('data-top')); |
130 | 130 | ||
131 | // Create draggable block | 131 | // Create draggable block |
132 | const wrapper = document.createElement("div"); | 132 | const wrapper = document.createElement('div'); |
133 | wrapper.classList.add("draggable-block"); | 133 | wrapper.classList.add('draggable-block'); |
134 | wrapper.innerHTML = ` | 134 | wrapper.innerHTML = ` |
135 | <div class="utils"> | 135 | <div class="utils"> |
136 | <div id="close">\u274C</div> | 136 | <div id="close">\u274C</div> |
@@ -138,18 +138,18 @@ export class Overlay extends Layout { | |||
138 | <div id="minus-font-size">\u2796</div> | 138 | <div id="minus-font-size">\u2796</div> |
139 | </div> | 139 | </div> |
140 | `; | 140 | `; |
141 | wrapper.title = "Middle-click to hide block"; | 141 | wrapper.title = 'Middle-click to hide block'; |
142 | wrapper.onmouseup = e => { | 142 | wrapper.onmouseup = e => { |
143 | // Hide block with middle click | 143 | // Hide block with middle click |
144 | if (e.button === 1) { | 144 | if (e.button === 1) { |
145 | wrapper.classList.add("hide"); | 145 | wrapper.classList.add('hide'); |
146 | } | 146 | } |
147 | }; | 147 | }; |
148 | 148 | ||
149 | // Set DOMRect for wrapper | 149 | // Set DOMRect for wrapper |
150 | wrapper.appendChild(block); | 150 | wrapper.appendChild(block); |
151 | wrapper.style.left = left + "px"; | 151 | wrapper.style.left = left + 'px'; |
152 | wrapper.style.top = top + "px"; | 152 | wrapper.style.top = top + 'px'; |
153 | htmlHolder.appendChild(wrapper); | 153 | htmlHolder.appendChild(wrapper); |
154 | const { width } = wrapper.getBoundingClientRect(); | 154 | const { width } = wrapper.getBoundingClientRect(); |
155 | left += width + 30; | 155 | left += width + 30; |
@@ -168,7 +168,7 @@ export class Overlay extends Layout { | |||
168 | // Trivial case: | 168 | // Trivial case: |
169 | // This hack make sure utils remains at the same place even when wrapper resized | 169 | // This hack make sure utils remains at the same place even when wrapper resized |
170 | // Prevent DOMRect changes when user clicking plus/minus button many times | 170 | // Prevent DOMRect changes when user clicking plus/minus button many times |
171 | const utils = wrapper.querySelector(".utils"); | 171 | const utils = wrapper.querySelector('.utils'); |
172 | utils.onmouseover = () => { | 172 | utils.onmouseover = () => { |
173 | const { left, top } = utils.getBoundingClientRect(); | 173 | const { left, top } = utils.getBoundingClientRect(); |
174 | utils.style.cssText = `visibility: visible; z-index: 9000; position: fixed; transition: unset; left: ${left}px; top: ${top}px;`; | 174 | utils.style.cssText = `visibility: visible; z-index: 9000; position: fixed; transition: unset; left: ${left}px; top: ${top}px;`; |
@@ -176,20 +176,20 @@ export class Overlay extends Layout { | |||
176 | }; | 176 | }; |
177 | utils.onmouseout = () => { | 177 | utils.onmouseout = () => { |
178 | wrapper.appendChild(utils); | 178 | wrapper.appendChild(utils); |
179 | utils.removeAttribute("style"); | 179 | utils.removeAttribute('style'); |
180 | }; | 180 | }; |
181 | 181 | ||
182 | // Close button | 182 | // Close button |
183 | wrapper.querySelector("#close").onclick = () => { | 183 | wrapper.querySelector('#close').onclick = () => { |
184 | wrapper.classList.add("hide"); | 184 | wrapper.classList.add('hide'); |
185 | utils.removeAttribute("style"); | 185 | utils.removeAttribute('style'); |
186 | }; | 186 | }; |
187 | // Plus/Minus font-size of content | 187 | // Plus/Minus font-size of content |
188 | wrapper.querySelector("#plus-font-size").onclick = () => { | 188 | wrapper.querySelector('#plus-font-size').onclick = () => { |
189 | const fontSize = parseFloat(getComputedStyle(block).fontSize) / 16; | 189 | const fontSize = parseFloat(getComputedStyle(block).fontSize) / 16; |
190 | block.style.fontSize = `${fontSize + 0.2}rem`; | 190 | block.style.fontSize = `${fontSize + 0.2}rem`; |
191 | }; | 191 | }; |
192 | wrapper.querySelector("#minus-font-size").onclick = () => { | 192 | wrapper.querySelector('#minus-font-size').onclick = () => { |
193 | const fontSize = parseFloat(getComputedStyle(block).fontSize) / 16; | 193 | const fontSize = parseFloat(getComputedStyle(block).fontSize) / 16; |
194 | block.style.fontSize = `${fontSize - 0.2}rem`; | 194 | block.style.fontSize = `${fontSize - 0.2}rem`; |
195 | }; | 195 | }; |
@@ -198,7 +198,7 @@ export class Overlay extends Layout { | |||
198 | 198 | ||
199 | leaveHandler = ({ htmlHolder, blocks }) => { | 199 | leaveHandler = ({ htmlHolder, blocks }) => { |
200 | const resumeFromDraggable = block => { | 200 | const resumeFromDraggable = block => { |
201 | const draggableContainer = block.closest(".draggable-block"); | 201 | const draggableContainer = block.closest('.draggable-block'); |
202 | if (!draggableContainer) return; | 202 | if (!draggableContainer) return; |
203 | htmlHolder.appendChild(block); | 203 | htmlHolder.appendChild(block); |
204 | draggableContainer.remove(); | 204 | draggableContainer.remove(); |