Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
automatic1111
GitHub Repository: automatic1111/stable-diffusion-webui
Path: blob/master/javascript/resizeHandle.js
3055 views
1
(function() {
2
const GRADIO_MIN_WIDTH = 320;
3
const PAD = 16;
4
const DEBOUNCE_TIME = 100;
5
const DOUBLE_TAP_DELAY = 200; //ms
6
7
const R = {
8
tracking: false,
9
parent: null,
10
parentWidth: null,
11
leftCol: null,
12
leftColStartWidth: null,
13
screenX: null,
14
lastTapTime: null,
15
};
16
17
let resizeTimer;
18
let parents = [];
19
20
function setLeftColGridTemplate(el, width) {
21
el.style.gridTemplateColumns = `${width}px 16px 1fr`;
22
}
23
24
function displayResizeHandle(parent) {
25
if (!parent.needHideOnMoblie) {
26
return true;
27
}
28
if (window.innerWidth < GRADIO_MIN_WIDTH * 2 + PAD * 4) {
29
parent.style.display = 'flex';
30
parent.resizeHandle.style.display = "none";
31
return false;
32
} else {
33
parent.style.display = 'grid';
34
parent.resizeHandle.style.display = "block";
35
return true;
36
}
37
}
38
39
function afterResize(parent) {
40
if (displayResizeHandle(parent) && parent.style.gridTemplateColumns != parent.style.originalGridTemplateColumns) {
41
const oldParentWidth = R.parentWidth;
42
const newParentWidth = parent.offsetWidth;
43
const widthL = parseInt(parent.style.gridTemplateColumns.split(' ')[0]);
44
45
const ratio = newParentWidth / oldParentWidth;
46
47
const newWidthL = Math.max(Math.floor(ratio * widthL), parent.minLeftColWidth);
48
setLeftColGridTemplate(parent, newWidthL);
49
50
R.parentWidth = newParentWidth;
51
}
52
}
53
54
function setup(parent) {
55
56
function onDoubleClick(evt) {
57
evt.preventDefault();
58
evt.stopPropagation();
59
60
parent.style.gridTemplateColumns = parent.style.originalGridTemplateColumns;
61
}
62
63
const leftCol = parent.firstElementChild;
64
const rightCol = parent.lastElementChild;
65
66
parents.push(parent);
67
68
parent.style.display = 'grid';
69
parent.style.gap = '0';
70
let leftColTemplate = "";
71
if (parent.children[0].style.flexGrow) {
72
leftColTemplate = `${parent.children[0].style.flexGrow}fr`;
73
parent.minLeftColWidth = GRADIO_MIN_WIDTH;
74
parent.minRightColWidth = GRADIO_MIN_WIDTH;
75
parent.needHideOnMoblie = true;
76
} else {
77
leftColTemplate = parent.children[0].style.flexBasis;
78
parent.minLeftColWidth = parent.children[0].style.flexBasis.slice(0, -2) / 2;
79
parent.minRightColWidth = 0;
80
parent.needHideOnMoblie = false;
81
}
82
83
if (!leftColTemplate) {
84
leftColTemplate = '1fr';
85
}
86
87
const gridTemplateColumns = `${leftColTemplate} ${PAD}px ${parent.children[1].style.flexGrow}fr`;
88
parent.style.gridTemplateColumns = gridTemplateColumns;
89
parent.style.originalGridTemplateColumns = gridTemplateColumns;
90
91
const resizeHandle = document.createElement('div');
92
resizeHandle.classList.add('resize-handle');
93
parent.insertBefore(resizeHandle, rightCol);
94
parent.resizeHandle = resizeHandle;
95
96
['mousedown', 'touchstart'].forEach((eventType) => {
97
resizeHandle.addEventListener(eventType, (evt) => {
98
if (eventType.startsWith('mouse')) {
99
if (evt.button !== 0) return;
100
} else {
101
if (evt.changedTouches.length !== 1) return;
102
103
const currentTime = new Date().getTime();
104
if (R.lastTapTime && currentTime - R.lastTapTime <= DOUBLE_TAP_DELAY) {
105
onDoubleClick(evt);
106
return;
107
}
108
109
R.lastTapTime = currentTime;
110
}
111
112
evt.preventDefault();
113
evt.stopPropagation();
114
115
document.body.classList.add('resizing');
116
117
R.tracking = true;
118
R.parent = parent;
119
R.parentWidth = parent.offsetWidth;
120
R.leftCol = leftCol;
121
R.leftColStartWidth = leftCol.offsetWidth;
122
if (eventType.startsWith('mouse')) {
123
R.screenX = evt.screenX;
124
} else {
125
R.screenX = evt.changedTouches[0].screenX;
126
}
127
});
128
});
129
130
resizeHandle.addEventListener('dblclick', onDoubleClick);
131
132
afterResize(parent);
133
}
134
135
['mousemove', 'touchmove'].forEach((eventType) => {
136
window.addEventListener(eventType, (evt) => {
137
if (eventType.startsWith('mouse')) {
138
if (evt.button !== 0) return;
139
} else {
140
if (evt.changedTouches.length !== 1) return;
141
}
142
143
if (R.tracking) {
144
if (eventType.startsWith('mouse')) {
145
evt.preventDefault();
146
}
147
evt.stopPropagation();
148
149
let delta = 0;
150
if (eventType.startsWith('mouse')) {
151
delta = R.screenX - evt.screenX;
152
} else {
153
delta = R.screenX - evt.changedTouches[0].screenX;
154
}
155
const leftColWidth = Math.max(Math.min(R.leftColStartWidth - delta, R.parent.offsetWidth - R.parent.minRightColWidth - PAD), R.parent.minLeftColWidth);
156
setLeftColGridTemplate(R.parent, leftColWidth);
157
}
158
});
159
});
160
161
['mouseup', 'touchend'].forEach((eventType) => {
162
window.addEventListener(eventType, (evt) => {
163
if (eventType.startsWith('mouse')) {
164
if (evt.button !== 0) return;
165
} else {
166
if (evt.changedTouches.length !== 1) return;
167
}
168
169
if (R.tracking) {
170
evt.preventDefault();
171
evt.stopPropagation();
172
173
R.tracking = false;
174
175
document.body.classList.remove('resizing');
176
}
177
});
178
});
179
180
181
window.addEventListener('resize', () => {
182
clearTimeout(resizeTimer);
183
184
resizeTimer = setTimeout(function() {
185
for (const parent of parents) {
186
afterResize(parent);
187
}
188
}, DEBOUNCE_TIME);
189
});
190
191
setupResizeHandle = setup;
192
})();
193
194
195
function setupAllResizeHandles() {
196
for (var elem of gradioApp().querySelectorAll('.resize-handle-row')) {
197
if (!elem.querySelector('.resize-handle') && !elem.children[0].classList.contains("hidden")) {
198
setupResizeHandle(elem);
199
}
200
}
201
}
202
203
204
onUiLoaded(setupAllResizeHandles);
205
206
207