datafolder 1.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +169 -0
- package/index.js +3 -0
- package/package.json +27 -0
- package/sample.js +37 -0
- package/scripts/airbnb.js +73 -0
- package/scripts/airbnb2.js +74 -0
- package/scripts/airbnb2_queries.js +231 -0
- package/scripts/airbnb_queries.js +264 -0
- package/scripts/downloadFile.js +42 -0
- package/scripts/express.js +46 -0
- package/scripts/fastify.js +79 -0
- package/scripts/flights.js +75 -0
- package/scripts/flights2.js +81 -0
- package/scripts/flights2_queries.js +453 -0
- package/scripts/flights_queries.js +403 -0
- package/src/QyAcl.js +252 -0
- package/src/QyAclSaver.js +14 -0
- package/src/QyAclSaver_Worker.js +29 -0
- package/src/QyAclWriter.js +19 -0
- package/src/QyBatch.js +501 -0
- package/src/QyBinWriter.js +140 -0
- package/src/QyCD.js +61 -0
- package/src/QyCache.js +212 -0
- package/src/QyCompressor.js +60 -0
- package/src/QyCompressor_Worker.js +13 -0
- package/src/QyDB.js +122 -0
- package/src/QyDefaultOptions.js +59 -0
- package/src/QyDir.js +192 -0
- package/src/QyFetch.js +38 -0
- package/src/QyFile.js +124 -0
- package/src/QyFileContentUtils.js +175 -0
- package/src/QyFileLogger.js +58 -0
- package/src/QyIndex.js +237 -0
- package/src/QyIndexPropTree.js +92 -0
- package/src/QyIntersectNode.js +48 -0
- package/src/QyItem.js +105 -0
- package/src/QyJsonSaver.js +20 -0
- package/src/QyKVData.js +289 -0
- package/src/QyKVDataCleaner.js +17 -0
- package/src/QyKVDataCleaner_Worker.js +94 -0
- package/src/QyKVDataLoader.js +65 -0
- package/src/QyKVDataSaver.js +17 -0
- package/src/QyKVDataSaver_Worker.js +81 -0
- package/src/QyLogFileSaver.js +14 -0
- package/src/QyLogFileSaver_Worker.js +26 -0
- package/src/QyLogger.js +76 -0
- package/src/QyMessageWorker.js +41 -0
- package/src/QyMessager.js +84 -0
- package/src/QyMessager_Run.js +13 -0
- package/src/QyMod.js +15 -0
- package/src/QyOpRunner.js +73 -0
- package/src/QyQueue.js +60 -0
- package/src/QySaver.js +83 -0
- package/src/QySnapshotCompactor.js +17 -0
- package/src/QySnapshotCompactor_Worker.js +151 -0
- package/src/QySnapshotSaver.js +17 -0
- package/src/QySnapshotSaver_Worker.js +164 -0
- package/src/QySnapshots.js +354 -0
- package/src/QyStructure.js +50 -0
- package/src/QyTrigger.js +133 -0
- package/src/QyUnionNode.js +105 -0
- package/src/QyUtils.js +250 -0
- package/src/QyWorker.js +33 -0
- package/src/hackernews.js +93 -0
- package/src/rpc/evalCode.js +9 -0
- package/src/rpc/getFileContent.js +16 -0
- package/src/rpc/getSubItems.js +32 -0
- package/src/rpc/queryFiles.js +33 -0
- package/src/rpc/reloadRpc.js +1 -0
- package/src/simulate.js +114 -0
- package/src/simulate2.js +110 -0
- package/src/soc_pokec.js +43 -0
- package/static/bootstrap-5.3.8-dist/css/bootstrap.min.css +6 -0
- package/static/bootstrap-5.3.8-dist/js/bootstrap.bundle.js +6312 -0
- package/static/datafolderui/QyStyledElement.js +30 -0
- package/static/datafolderui/QyUIFolderTree.js +203 -0
- package/static/datafolderui/QyUIUtils.js +42 -0
- package/static/datafolderui/display-tree.js +108 -0
- package/static/datafolderui/explore-tree.js +122 -0
- package/static/datafolderui/folder-tree.js +5 -0
- package/static/datafolderui/hscrpt.js +25 -0
- package/static/datafolderui/index.css +6 -0
- package/static/datafolderui/index.html +20 -0
- package/static/datafolderui/json-view.js +74 -0
- package/static/datafolderui/kv-input.js +66 -0
- package/static/datafolderui/list-input.js +52 -0
- package/static/datafolderui/main-page.js +98 -0
- package/static/datafolderui/num-input.js +27 -0
- package/static/datafolderui/query-editor.js +229 -0
- package/static/datafolderui/querySelectorShadowRoot.js +24 -0
- package/static/datafolderui/resizable-input.js +67 -0
- package/static/favicon.ico +0 -0
- package/static/icons-1.13.1/font/bootstrap-icons.min.css +5 -0
- package/static/icons-1.13.1/font/fonts/bootstrap-icons.woff +0 -0
- package/static/icons-1.13.1/font/fonts/bootstrap-icons.woff2 +0 -0
- package/static/json-view/dist/jsonview.js +433 -0
- package/static/tree.js/tree.css +106 -0
- package/static/tree.js/tree.js +374 -0
- package/static/w2ui/dist/w2ui.min.css +2 -0
- package/static/w2ui/src/less/icons/icons.json +1 -0
- package/static/w2ui/src/less/icons/preview.html +33 -0
- package/static/w2ui/src/less/icons/readme.md +15 -0
- package/static/w2ui/src/less/icons/svg/box.svg +3 -0
- package/static/w2ui/src/less/icons/svg/check.svg +3 -0
- package/static/w2ui/src/less/icons/svg/colors.svg +3 -0
- package/static/w2ui/src/less/icons/svg/columns.svg +5 -0
- package/static/w2ui/src/less/icons/svg/cross.svg +4 -0
- package/static/w2ui/src/less/icons/svg/drop.svg +6 -0
- package/static/w2ui/src/less/icons/svg/empty.svg +3 -0
- package/static/w2ui/src/less/icons/svg/eye-dropper.svg +4 -0
- package/static/w2ui/src/less/icons/svg/info.svg +8 -0
- package/static/w2ui/src/less/icons/svg/paste.svg +4 -0
- package/static/w2ui/src/less/icons/svg/pencil.svg +5 -0
- package/static/w2ui/src/less/icons/svg/plus.svg +3 -0
- package/static/w2ui/src/less/icons/svg/reload.svg +5 -0
- package/static/w2ui/src/less/icons/svg/search.svg +3 -0
- package/static/w2ui/src/less/icons/svg/settings.svg +8 -0
- package/static/w2ui/src/less/icons/w2ui-font.css +36 -0
- package/static/w2ui/src/less/icons/w2ui-font.woff +0 -0
- package/static/w2ui/src/less/src/buttons.less +184 -0
- package/static/w2ui/src/less/src/common.less +541 -0
- package/static/w2ui/src/less/src/fields.less +302 -0
- package/static/w2ui/src/less/src/form.less +319 -0
- package/static/w2ui/src/less/src/grid.less +1057 -0
- package/static/w2ui/src/less/src/icons.less +37 -0
- package/static/w2ui/src/less/src/layout.less +86 -0
- package/static/w2ui/src/less/src/mixins.less +87 -0
- package/static/w2ui/src/less/src/popup.less +277 -0
- package/static/w2ui/src/less/src/sidebar.less +343 -0
- package/static/w2ui/src/less/src/tabs.less +145 -0
- package/static/w2ui/src/less/src/toolbar.less +219 -0
- package/static/w2ui/src/less/src/tooltip.less +948 -0
- package/static/w2ui/src/less/w2ui.less +196 -0
- package/static/w2ui/src/locale/az-az.json +114 -0
- package/static/w2ui/src/locale/ba-ba.json +114 -0
- package/static/w2ui/src/locale/bg-bg.json +114 -0
- package/static/w2ui/src/locale/ca-es.json +114 -0
- package/static/w2ui/src/locale/da-dk.json +114 -0
- package/static/w2ui/src/locale/de-de.json +114 -0
- package/static/w2ui/src/locale/en-gb.json +17 -0
- package/static/w2ui/src/locale/en-us.json +17 -0
- package/static/w2ui/src/locale/es-ar.json +115 -0
- package/static/w2ui/src/locale/es-cr.json +119 -0
- package/static/w2ui/src/locale/es-es.json +114 -0
- package/static/w2ui/src/locale/es-mx.json +114 -0
- package/static/w2ui/src/locale/fr-fr.json +114 -0
- package/static/w2ui/src/locale/gl-es.json +114 -0
- package/static/w2ui/src/locale/hr-hr.json +114 -0
- package/static/w2ui/src/locale/hu-hu.json +114 -0
- package/static/w2ui/src/locale/id-id.json +114 -0
- package/static/w2ui/src/locale/it-it.json +114 -0
- package/static/w2ui/src/locale/ja-jp.json +114 -0
- package/static/w2ui/src/locale/kk-kz.json +116 -0
- package/static/w2ui/src/locale/ko-kr.json +114 -0
- package/static/w2ui/src/locale/lt-lt.json +114 -0
- package/static/w2ui/src/locale/nl-nl.json +114 -0
- package/static/w2ui/src/locale/no-no.json +114 -0
- package/static/w2ui/src/locale/pl-pl.json +114 -0
- package/static/w2ui/src/locale/pt-br.json +114 -0
- package/static/w2ui/src/locale/ru-ru.json +116 -0
- package/static/w2ui/src/locale/sk-sk.json +114 -0
- package/static/w2ui/src/locale/sl-si.json +116 -0
- package/static/w2ui/src/locale/sr-rs.json +114 -0
- package/static/w2ui/src/locale/tr-tr.json +114 -0
- package/static/w2ui/src/locale/uk-ua.json +114 -0
- package/static/w2ui/src/locale/zh-cn.json +114 -0
- package/static/w2ui/src/locale/zh-tw.json +114 -0
- package/static/w2ui/src/query.js +583 -0
- package/static/w2ui/src/readme.md +11 -0
- package/static/w2ui/src/w2base.js +311 -0
- package/static/w2ui/src/w2compat.js +207 -0
- package/static/w2ui/src/w2field.js +1854 -0
- package/static/w2ui/src/w2form.js +2411 -0
- package/static/w2ui/src/w2grid.js +8916 -0
- package/static/w2ui/src/w2layout.js +1194 -0
- package/static/w2ui/src/w2locale.js +129 -0
- package/static/w2ui/src/w2popup.js +909 -0
- package/static/w2ui/src/w2sidebar.js +1769 -0
- package/static/w2ui/src/w2tabs.js +669 -0
- package/static/w2ui/src/w2toolbar.js +1180 -0
- package/static/w2ui/src/w2tooltip.js +3134 -0
- package/static/w2ui/src/w2utils.js +2457 -0
|
@@ -0,0 +1,583 @@
|
|
|
1
|
+
/* mQuery 0.7 (nightly) (8/15/2023, 11:44:12 AM), vitmalina@gmail.com */
|
|
2
|
+
class Query {
|
|
3
|
+
static version = 0.8
|
|
4
|
+
constructor(selector, context) {
|
|
5
|
+
this.context = context ?? document
|
|
6
|
+
let nodes = []
|
|
7
|
+
if (Array.isArray(selector)) {
|
|
8
|
+
nodes = selector
|
|
9
|
+
} else if (selector instanceof Node || selector instanceof Window) { // any html element or Window
|
|
10
|
+
nodes = [selector]
|
|
11
|
+
} else if (selector instanceof Query) {
|
|
12
|
+
nodes = selector.nodes
|
|
13
|
+
} else if (typeof selector == 'string') {
|
|
14
|
+
if (typeof this.context.querySelector != 'function') {
|
|
15
|
+
throw new Error('Invalid context')
|
|
16
|
+
}
|
|
17
|
+
nodes = Array.from(this.context.querySelectorAll(selector))
|
|
18
|
+
} else if (selector == null) {
|
|
19
|
+
nodes = []
|
|
20
|
+
} else {
|
|
21
|
+
// if selector is itterable, then try to create nodes from it, also supports jQuery
|
|
22
|
+
let arr = Array.from(selector ?? [])
|
|
23
|
+
if (typeof selector == 'object' && Array.isArray(arr)) {
|
|
24
|
+
nodes = arr
|
|
25
|
+
} else {
|
|
26
|
+
throw new Error(`Invalid selector "${selector}"`)
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
this.nodes = nodes
|
|
30
|
+
this.length = nodes.length
|
|
31
|
+
// map nodes to object propoerties
|
|
32
|
+
this.each((node, ind) => {
|
|
33
|
+
this[ind] = node
|
|
34
|
+
})
|
|
35
|
+
}
|
|
36
|
+
static _fragment(html) {
|
|
37
|
+
let tmpl = document.createElement('template')
|
|
38
|
+
tmpl.innerHTML = html
|
|
39
|
+
tmpl.content.childNodes.forEach(node => {
|
|
40
|
+
let newNode = Query._scriptConvert(node)
|
|
41
|
+
if (newNode != node) {
|
|
42
|
+
tmpl.content.replaceChild(newNode, node)
|
|
43
|
+
}
|
|
44
|
+
})
|
|
45
|
+
return tmpl.content
|
|
46
|
+
}
|
|
47
|
+
// innerHTML, append, etc. script tags will not be executed unless they are proper script tags
|
|
48
|
+
static _scriptConvert(node) {
|
|
49
|
+
let convert = (txtNode) => {
|
|
50
|
+
let doc = txtNode.ownerDocument
|
|
51
|
+
let scNode = doc.createElement('script')
|
|
52
|
+
scNode.text = txtNode.text
|
|
53
|
+
let attrs = txtNode.attributes
|
|
54
|
+
for (let i = 0; i < attrs.length; i++) {
|
|
55
|
+
scNode.setAttribute(attrs[i].name, attrs[i].value)
|
|
56
|
+
}
|
|
57
|
+
return scNode
|
|
58
|
+
}
|
|
59
|
+
if (node.tagName == 'SCRIPT') {
|
|
60
|
+
node = convert(node)
|
|
61
|
+
}
|
|
62
|
+
if (node.querySelectorAll) {
|
|
63
|
+
node.querySelectorAll('script').forEach(textNode => {
|
|
64
|
+
textNode.parentNode.replaceChild(convert(textNode), textNode)
|
|
65
|
+
})
|
|
66
|
+
}
|
|
67
|
+
return node
|
|
68
|
+
}
|
|
69
|
+
static _fixProp(name) {
|
|
70
|
+
let fixes = {
|
|
71
|
+
cellpadding: 'cellPadding',
|
|
72
|
+
cellspacing: 'cellSpacing',
|
|
73
|
+
class: 'className',
|
|
74
|
+
colspan: 'colSpan',
|
|
75
|
+
contenteditable: 'contentEditable',
|
|
76
|
+
for: 'htmlFor',
|
|
77
|
+
frameborder: 'frameBorder',
|
|
78
|
+
maxlength: 'maxLength',
|
|
79
|
+
readonly: 'readOnly',
|
|
80
|
+
rowspan: 'rowSpan',
|
|
81
|
+
tabindex: 'tabIndex',
|
|
82
|
+
usemap: 'useMap'
|
|
83
|
+
}
|
|
84
|
+
return fixes[name] ? fixes[name] : name
|
|
85
|
+
}
|
|
86
|
+
_insert(method, html) {
|
|
87
|
+
let nodes = []
|
|
88
|
+
let len = this.length
|
|
89
|
+
if (len < 1) return
|
|
90
|
+
let self = this
|
|
91
|
+
// TODO: need good unit test coverage for this function
|
|
92
|
+
if (typeof html == 'string') {
|
|
93
|
+
this.each(node => {
|
|
94
|
+
let clone = Query._fragment(html)
|
|
95
|
+
nodes.push(...clone.childNodes)
|
|
96
|
+
node[method](clone)
|
|
97
|
+
})
|
|
98
|
+
} else if (html instanceof Query) {
|
|
99
|
+
let single = (len == 1) // if inserting into a single container, then move it there
|
|
100
|
+
html.each(el => {
|
|
101
|
+
this.each(node => {
|
|
102
|
+
// if insert before a single node, just move new one, else clone and move it
|
|
103
|
+
let clone = (single ? el : el.cloneNode(true))
|
|
104
|
+
nodes.push(clone)
|
|
105
|
+
node[method](clone)
|
|
106
|
+
Query._scriptConvert(clone)
|
|
107
|
+
})
|
|
108
|
+
})
|
|
109
|
+
if (!single) html.remove()
|
|
110
|
+
} else if (html instanceof Node) { // any HTML element
|
|
111
|
+
this.each(node => {
|
|
112
|
+
// if insert before a single node, just move new one, else clone and move it
|
|
113
|
+
let clone = (len === 1 ? html : Query._fragment(html.outerHTML))
|
|
114
|
+
nodes.push(...(len === 1 ? [html] : clone.childNodes))
|
|
115
|
+
node[method](clone)
|
|
116
|
+
})
|
|
117
|
+
if (len > 1) html.remove()
|
|
118
|
+
} else {
|
|
119
|
+
throw new Error(`Incorrect argument for "${method}(html)". It expects one string argument.`)
|
|
120
|
+
}
|
|
121
|
+
if (method == 'replaceWith') {
|
|
122
|
+
self = new Query(nodes, this.context) // must return a new collection
|
|
123
|
+
}
|
|
124
|
+
return self
|
|
125
|
+
}
|
|
126
|
+
_save(node, name, value) {
|
|
127
|
+
node._mQuery = node._mQuery ?? {}
|
|
128
|
+
if (Array.isArray(value)) {
|
|
129
|
+
node._mQuery[name] = node._mQuery[name] ?? []
|
|
130
|
+
node._mQuery[name].push(...value)
|
|
131
|
+
} else if (value != null) {
|
|
132
|
+
node._mQuery[name] = value
|
|
133
|
+
} else {
|
|
134
|
+
delete node._mQuery[name]
|
|
135
|
+
}
|
|
136
|
+
}
|
|
137
|
+
get(index) {
|
|
138
|
+
if (index < 0) index = this.length + index
|
|
139
|
+
let node = this[index]
|
|
140
|
+
if (node) {
|
|
141
|
+
return node
|
|
142
|
+
}
|
|
143
|
+
if (index != null) {
|
|
144
|
+
return null
|
|
145
|
+
}
|
|
146
|
+
return this.nodes
|
|
147
|
+
}
|
|
148
|
+
eq(index) {
|
|
149
|
+
if (index < 0) index = this.length + index
|
|
150
|
+
let nodes = [this[index]]
|
|
151
|
+
if (nodes[0] == null) nodes = []
|
|
152
|
+
return new Query(nodes, this.context) // must return a new collection
|
|
153
|
+
}
|
|
154
|
+
then(fun) {
|
|
155
|
+
let ret = fun(this)
|
|
156
|
+
return ret != null ? ret : this
|
|
157
|
+
}
|
|
158
|
+
find(selector) {
|
|
159
|
+
let nodes = []
|
|
160
|
+
this.each(node => {
|
|
161
|
+
let nn = Array.from(node.querySelectorAll(selector))
|
|
162
|
+
if (nn.length > 0) {
|
|
163
|
+
nodes.push(...nn)
|
|
164
|
+
}
|
|
165
|
+
})
|
|
166
|
+
return new Query(nodes, this.context) // must return a new collection
|
|
167
|
+
}
|
|
168
|
+
filter(selector) {
|
|
169
|
+
let nodes = []
|
|
170
|
+
this.each(node => {
|
|
171
|
+
if (node === selector
|
|
172
|
+
|| (typeof selector == 'string' && node.matches && node.matches(selector))
|
|
173
|
+
|| (typeof selector == 'function' && selector(node))
|
|
174
|
+
) {
|
|
175
|
+
nodes.push(node)
|
|
176
|
+
}
|
|
177
|
+
})
|
|
178
|
+
return new Query(nodes, this.context) // must return a new collection
|
|
179
|
+
}
|
|
180
|
+
next() {
|
|
181
|
+
let nodes = []
|
|
182
|
+
this.each(node => {
|
|
183
|
+
let nn = node.nextElementSibling
|
|
184
|
+
if (nn) { nodes.push(nn) }
|
|
185
|
+
})
|
|
186
|
+
return new Query(nodes, this.context) // must return a new collection
|
|
187
|
+
}
|
|
188
|
+
prev() {
|
|
189
|
+
let nodes = []
|
|
190
|
+
this.each(node => {
|
|
191
|
+
let nn = node.previousElementSibling
|
|
192
|
+
if (nn) { nodes.push(nn)}
|
|
193
|
+
})
|
|
194
|
+
return new Query(nodes, this.context) // must return a new collection
|
|
195
|
+
}
|
|
196
|
+
shadow(selector) {
|
|
197
|
+
let nodes = []
|
|
198
|
+
this.each(node => {
|
|
199
|
+
// select shadow root if available
|
|
200
|
+
if (node.shadowRoot) nodes.push(node.shadowRoot)
|
|
201
|
+
})
|
|
202
|
+
let col = new Query(nodes, this.context)
|
|
203
|
+
return selector ? col.find(selector) : col
|
|
204
|
+
}
|
|
205
|
+
closest(selector) {
|
|
206
|
+
let nodes = []
|
|
207
|
+
this.each(node => {
|
|
208
|
+
let nn = node.closest(selector)
|
|
209
|
+
if (nn) {
|
|
210
|
+
nodes.push(nn)
|
|
211
|
+
}
|
|
212
|
+
})
|
|
213
|
+
return new Query(nodes, this.context) // must return a new collection
|
|
214
|
+
}
|
|
215
|
+
host(all) {
|
|
216
|
+
let nodes = []
|
|
217
|
+
// find shadow root or body
|
|
218
|
+
let top = (node) => {
|
|
219
|
+
if (node.parentNode) {
|
|
220
|
+
return top(node.parentNode)
|
|
221
|
+
} else {
|
|
222
|
+
return node
|
|
223
|
+
}
|
|
224
|
+
}
|
|
225
|
+
let fun = (node) => {
|
|
226
|
+
let nn = top(node)
|
|
227
|
+
nodes.push(nn.host ? nn.host : nn)
|
|
228
|
+
if (nn.host && all) fun(nn.host)
|
|
229
|
+
}
|
|
230
|
+
this.each(node => {
|
|
231
|
+
fun(node)
|
|
232
|
+
})
|
|
233
|
+
return new Query(nodes, this.context) // must return a new collection
|
|
234
|
+
}
|
|
235
|
+
parent(selector) {
|
|
236
|
+
return this.parents(selector, true)
|
|
237
|
+
}
|
|
238
|
+
parents(selector, firstOnly) {
|
|
239
|
+
let nodes = []
|
|
240
|
+
let add = (node) => {
|
|
241
|
+
if (nodes.indexOf(node) == -1) {
|
|
242
|
+
nodes.push(node)
|
|
243
|
+
}
|
|
244
|
+
if (!firstOnly && node.parentNode) {
|
|
245
|
+
return add(node.parentNode)
|
|
246
|
+
}
|
|
247
|
+
}
|
|
248
|
+
this.each(node => {
|
|
249
|
+
if (node.parentNode) add(node.parentNode)
|
|
250
|
+
})
|
|
251
|
+
let col = new Query(nodes, this.context)
|
|
252
|
+
return selector ? col.filter(selector) : col
|
|
253
|
+
}
|
|
254
|
+
add(more) {
|
|
255
|
+
let nodes = more instanceof Query ? more.nodes : (Array.isArray(more) ? more : [more])
|
|
256
|
+
return new Query(this.nodes.concat(nodes), this.context) // must return a new collection
|
|
257
|
+
}
|
|
258
|
+
each(func) {
|
|
259
|
+
this.nodes.forEach((node, ind) => { func(node, ind, this) })
|
|
260
|
+
return this
|
|
261
|
+
}
|
|
262
|
+
append(html) {
|
|
263
|
+
return this._insert('append', html)
|
|
264
|
+
}
|
|
265
|
+
prepend(html) {
|
|
266
|
+
return this._insert('prepend', html)
|
|
267
|
+
}
|
|
268
|
+
after(html) {
|
|
269
|
+
return this._insert('after', html)
|
|
270
|
+
}
|
|
271
|
+
before(html) {
|
|
272
|
+
return this._insert('before', html)
|
|
273
|
+
}
|
|
274
|
+
replace(html) {
|
|
275
|
+
return this._insert('replaceWith', html)
|
|
276
|
+
}
|
|
277
|
+
remove() {
|
|
278
|
+
// remove from dom, but keep in current query
|
|
279
|
+
this.each(node => { node.remove() })
|
|
280
|
+
return this
|
|
281
|
+
}
|
|
282
|
+
css(key, value) {
|
|
283
|
+
let css = key
|
|
284
|
+
let len = arguments.length
|
|
285
|
+
if (len === 0 || (len === 1 && typeof key == 'string')) {
|
|
286
|
+
if (this[0]) {
|
|
287
|
+
let st = this[0].style
|
|
288
|
+
// do not do computedStyleMap as it is not what on immediate element
|
|
289
|
+
if (typeof key == 'string') {
|
|
290
|
+
let pri = st.getPropertyPriority(key)
|
|
291
|
+
return st.getPropertyValue(key) + (pri ? '!' + pri : '')
|
|
292
|
+
} else {
|
|
293
|
+
return Object.fromEntries(
|
|
294
|
+
this[0].style.cssText
|
|
295
|
+
.split(';')
|
|
296
|
+
.filter(a => !!a) // filter non-empty
|
|
297
|
+
.map(a => {
|
|
298
|
+
return a.split(':').map(a => a.trim()) // trim strings
|
|
299
|
+
})
|
|
300
|
+
)
|
|
301
|
+
}
|
|
302
|
+
} else {
|
|
303
|
+
return undefined
|
|
304
|
+
}
|
|
305
|
+
} else {
|
|
306
|
+
if (typeof key != 'object') {
|
|
307
|
+
css = {}
|
|
308
|
+
css[key] = value
|
|
309
|
+
}
|
|
310
|
+
this.each((el, ind) => {
|
|
311
|
+
Object.keys(css).forEach(key => {
|
|
312
|
+
let imp = String(css[key]).toLowerCase().includes('!important') ? 'important' : ''
|
|
313
|
+
el.style.setProperty(key, String(css[key]).replace(/\!important/i, ''), imp)
|
|
314
|
+
})
|
|
315
|
+
})
|
|
316
|
+
return this
|
|
317
|
+
}
|
|
318
|
+
}
|
|
319
|
+
addClass(classes) {
|
|
320
|
+
this.toggleClass(classes, true)
|
|
321
|
+
return this
|
|
322
|
+
}
|
|
323
|
+
removeClass(classes) {
|
|
324
|
+
this.toggleClass(classes, false)
|
|
325
|
+
return this
|
|
326
|
+
}
|
|
327
|
+
toggleClass(classes, force) {
|
|
328
|
+
// split by comma or space
|
|
329
|
+
if (typeof classes == 'string') classes = classes.split(/[,\s]+/)
|
|
330
|
+
this.each(node => {
|
|
331
|
+
let classes2 = classes
|
|
332
|
+
// if not defined, remove all classes
|
|
333
|
+
if (classes2 == null && force === false) classes2 = Array.from(node.classList)
|
|
334
|
+
classes2.forEach(className => {
|
|
335
|
+
if (className !== '') {
|
|
336
|
+
let act = 'toggle'
|
|
337
|
+
if (force != null) act = force ? 'add' : 'remove'
|
|
338
|
+
node.classList[act](className)
|
|
339
|
+
}
|
|
340
|
+
})
|
|
341
|
+
})
|
|
342
|
+
return this
|
|
343
|
+
}
|
|
344
|
+
hasClass(classes) {
|
|
345
|
+
// split by comma or space
|
|
346
|
+
if (typeof classes == 'string') classes = classes.split(/[,\s]+/)
|
|
347
|
+
if (classes == null && this.length > 0) {
|
|
348
|
+
return Array.from(this[0].classList)
|
|
349
|
+
}
|
|
350
|
+
let ret = false
|
|
351
|
+
this.each(node => {
|
|
352
|
+
ret = ret || classes.every(className => {
|
|
353
|
+
return Array.from(node.classList ?? []).includes(className)
|
|
354
|
+
})
|
|
355
|
+
})
|
|
356
|
+
return ret
|
|
357
|
+
}
|
|
358
|
+
on(events, options, callback) {
|
|
359
|
+
if (typeof options == 'function') {
|
|
360
|
+
callback = options
|
|
361
|
+
options = undefined
|
|
362
|
+
}
|
|
363
|
+
let delegate
|
|
364
|
+
if (options?.delegate) {
|
|
365
|
+
delegate = options.delegate
|
|
366
|
+
delete options.delegate // not to pass to addEventListener
|
|
367
|
+
}
|
|
368
|
+
events = events.split(/[,\s]+/) // separate by comma or space
|
|
369
|
+
events.forEach(eventName => {
|
|
370
|
+
let [ event, scope ] = String(eventName).toLowerCase().split('.')
|
|
371
|
+
if (delegate) {
|
|
372
|
+
let fun = callback
|
|
373
|
+
callback = (event) => {
|
|
374
|
+
// event.target or any ancestors match delegate selector
|
|
375
|
+
let parent = query(event.target).parents(delegate)
|
|
376
|
+
if (parent.length > 0) { event.delegate = parent[0] } else { event.delegate = event.target }
|
|
377
|
+
if (event.target.matches(delegate) || parent.length > 0) {
|
|
378
|
+
fun(event)
|
|
379
|
+
}
|
|
380
|
+
}
|
|
381
|
+
}
|
|
382
|
+
this.each(node => {
|
|
383
|
+
this._save(node, 'events', [{ event, scope, callback, options }])
|
|
384
|
+
node.addEventListener(event, callback, options)
|
|
385
|
+
})
|
|
386
|
+
})
|
|
387
|
+
return this
|
|
388
|
+
}
|
|
389
|
+
off(events, options, callback) {
|
|
390
|
+
if (typeof options == 'function') {
|
|
391
|
+
callback = options
|
|
392
|
+
options = undefined
|
|
393
|
+
}
|
|
394
|
+
events = (events ?? '').split(/[,\s]+/) // separate by comma or space
|
|
395
|
+
events.forEach(eventName => {
|
|
396
|
+
let [ event, scope ] = String(eventName).toLowerCase().split('.')
|
|
397
|
+
this.each(node => {
|
|
398
|
+
if (Array.isArray(node._mQuery?.events)) {
|
|
399
|
+
for (let i = node._mQuery.events.length - 1; i >= 0; i--) {
|
|
400
|
+
let evt = node._mQuery.events[i]
|
|
401
|
+
if (scope == null || scope === '') {
|
|
402
|
+
// if no scope, has to be exact match
|
|
403
|
+
if ((evt.event == event || event === '') && (evt.callback == callback || callback == null)) {
|
|
404
|
+
node.removeEventListener(evt.event, evt.callback, evt.options)
|
|
405
|
+
node._mQuery.events.splice(i, 1)
|
|
406
|
+
}
|
|
407
|
+
} else {
|
|
408
|
+
if ((evt.event == event || event === '') && evt.scope == scope) {
|
|
409
|
+
node.removeEventListener(evt.event, evt.callback, evt.options)
|
|
410
|
+
node._mQuery.events.splice(i, 1)
|
|
411
|
+
}
|
|
412
|
+
}
|
|
413
|
+
}
|
|
414
|
+
}
|
|
415
|
+
})
|
|
416
|
+
})
|
|
417
|
+
return this
|
|
418
|
+
}
|
|
419
|
+
trigger(name, options) {
|
|
420
|
+
let event,
|
|
421
|
+
mevent = ['click', 'dblclick', 'mousedown', 'mouseup', 'mousemove'],
|
|
422
|
+
kevent = ['keydown', 'keyup', 'keypress']
|
|
423
|
+
if (name instanceof Event || name instanceof CustomEvent) {
|
|
424
|
+
// MouseEvent and KeyboardEvent are instances of Event, no need to explicitly add
|
|
425
|
+
event = name
|
|
426
|
+
} else if (mevent.includes(name)) {
|
|
427
|
+
event = new MouseEvent(name, options)
|
|
428
|
+
} else if (kevent.includes(name)) {
|
|
429
|
+
event = new KeyboardEvent(name, options)
|
|
430
|
+
} else {
|
|
431
|
+
event = new Event(name, options)
|
|
432
|
+
}
|
|
433
|
+
this.each(node => { node.dispatchEvent(event) })
|
|
434
|
+
return this
|
|
435
|
+
}
|
|
436
|
+
attr(name, value) {
|
|
437
|
+
if (value === undefined && typeof name == 'string') {
|
|
438
|
+
return this[0] ? this[0].getAttribute(name) : undefined
|
|
439
|
+
} else {
|
|
440
|
+
let obj = {}
|
|
441
|
+
if (typeof name == 'object') obj = name; else obj[name] = value
|
|
442
|
+
this.each(node => {
|
|
443
|
+
Object.entries(obj).forEach(([nm, val]) => { node.setAttribute(nm, val) })
|
|
444
|
+
})
|
|
445
|
+
return this
|
|
446
|
+
}
|
|
447
|
+
}
|
|
448
|
+
removeAttr() {
|
|
449
|
+
this.each(node => {
|
|
450
|
+
Array.from(arguments).forEach(attr => {
|
|
451
|
+
node.removeAttribute(attr)
|
|
452
|
+
})
|
|
453
|
+
})
|
|
454
|
+
return this
|
|
455
|
+
}
|
|
456
|
+
prop(name, value) {
|
|
457
|
+
if (value === undefined && typeof name == 'string') {
|
|
458
|
+
return this[0] ? this[0][name] : undefined
|
|
459
|
+
} else {
|
|
460
|
+
let obj = {}
|
|
461
|
+
if (typeof name == 'object') obj = name; else obj[name] = value
|
|
462
|
+
this.each(node => {
|
|
463
|
+
Object.entries(obj).forEach(([nm, val]) => {
|
|
464
|
+
let prop = Query._fixProp(nm)
|
|
465
|
+
node[prop] = val
|
|
466
|
+
if (prop == 'innerHTML') {
|
|
467
|
+
Query._scriptConvert(node)
|
|
468
|
+
}
|
|
469
|
+
})
|
|
470
|
+
})
|
|
471
|
+
return this
|
|
472
|
+
}
|
|
473
|
+
}
|
|
474
|
+
removeProp() {
|
|
475
|
+
this.each(node => {
|
|
476
|
+
Array.from(arguments).forEach(prop => { delete node[Query._fixProp(prop)] })
|
|
477
|
+
})
|
|
478
|
+
return this
|
|
479
|
+
}
|
|
480
|
+
data(key, value) {
|
|
481
|
+
if (key instanceof Object) {
|
|
482
|
+
Object.entries(key).forEach(item => { this.data(item[0], item[1]) })
|
|
483
|
+
return
|
|
484
|
+
}
|
|
485
|
+
if (key && key.indexOf('-') != -1) {
|
|
486
|
+
console.error(`Key "${key}" contains "-" (dash). Dashes are not allowed in property names. Use camelCase instead.`)
|
|
487
|
+
}
|
|
488
|
+
if (arguments.length < 2) {
|
|
489
|
+
if (this[0]) {
|
|
490
|
+
let data = Object.assign({}, this[0].dataset)
|
|
491
|
+
Object.keys(data).forEach(key => {
|
|
492
|
+
if (data[key].startsWith('[') || data[key].startsWith('{')) {
|
|
493
|
+
try { data[key] = JSON.parse(data[key]) } catch (e) {}
|
|
494
|
+
}
|
|
495
|
+
})
|
|
496
|
+
return key ? data[key] : data
|
|
497
|
+
} else {
|
|
498
|
+
return undefined
|
|
499
|
+
}
|
|
500
|
+
} else {
|
|
501
|
+
this.each(node => {
|
|
502
|
+
if (value != null) {
|
|
503
|
+
node.dataset[key] = value instanceof Object ? JSON.stringify(value) : value
|
|
504
|
+
} else {
|
|
505
|
+
delete node.dataset[key]
|
|
506
|
+
}
|
|
507
|
+
})
|
|
508
|
+
return this
|
|
509
|
+
}
|
|
510
|
+
}
|
|
511
|
+
removeData(key) {
|
|
512
|
+
if (typeof key == 'string') key = key.split(/[,\s]+/)
|
|
513
|
+
this.each(node => {
|
|
514
|
+
key.forEach(k => { delete node.dataset[k] })
|
|
515
|
+
})
|
|
516
|
+
return this
|
|
517
|
+
}
|
|
518
|
+
show() {
|
|
519
|
+
return this.toggle(true)
|
|
520
|
+
}
|
|
521
|
+
hide() {
|
|
522
|
+
return this.toggle(false)
|
|
523
|
+
}
|
|
524
|
+
toggle(force) {
|
|
525
|
+
return this.each(node => {
|
|
526
|
+
let prev = node.style.display
|
|
527
|
+
let dsp = getComputedStyle(node).display
|
|
528
|
+
let isHidden = (prev == 'none' || dsp == 'none')
|
|
529
|
+
if (isHidden && (force == null || force === true)) { // show
|
|
530
|
+
let def = node instanceof HTMLTableRowElement
|
|
531
|
+
? 'table-row'
|
|
532
|
+
: node instanceof HTMLTableCellElement
|
|
533
|
+
? 'table-cell'
|
|
534
|
+
: 'block'
|
|
535
|
+
node.style.display = node._mQuery?.prevDisplay ?? (prev == dsp && dsp != 'none' ? '' : def)
|
|
536
|
+
this._save(node, 'prevDisplay', null)
|
|
537
|
+
}
|
|
538
|
+
if (!isHidden && (force == null || force === false)) { // hide
|
|
539
|
+
if (dsp != 'none') this._save(node, 'prevDisplay', dsp)
|
|
540
|
+
node.style.setProperty('display', 'none')
|
|
541
|
+
}
|
|
542
|
+
})
|
|
543
|
+
}
|
|
544
|
+
empty() {
|
|
545
|
+
return this.html('')
|
|
546
|
+
}
|
|
547
|
+
html(html) {
|
|
548
|
+
if (html instanceof HTMLElement) {
|
|
549
|
+
return this.empty().append(html)
|
|
550
|
+
} else {
|
|
551
|
+
return this.prop('innerHTML', html)
|
|
552
|
+
}
|
|
553
|
+
}
|
|
554
|
+
text(text) {
|
|
555
|
+
return this.prop('textContent', text)
|
|
556
|
+
}
|
|
557
|
+
val(value) {
|
|
558
|
+
return this.prop('value', value) // must be prop
|
|
559
|
+
}
|
|
560
|
+
change() {
|
|
561
|
+
return this.trigger('change')
|
|
562
|
+
}
|
|
563
|
+
click() {
|
|
564
|
+
return this.trigger('click')
|
|
565
|
+
}
|
|
566
|
+
}
|
|
567
|
+
// create a new object each time
|
|
568
|
+
let query = function (selector, context) {
|
|
569
|
+
// if a function, use as onload event
|
|
570
|
+
if (typeof selector == 'function') {
|
|
571
|
+
if (document.readyState == 'complete') {
|
|
572
|
+
selector()
|
|
573
|
+
} else {
|
|
574
|
+
window.addEventListener('load', selector)
|
|
575
|
+
}
|
|
576
|
+
} else {
|
|
577
|
+
return new Query(selector, context)
|
|
578
|
+
}
|
|
579
|
+
}
|
|
580
|
+
// str -> doc-fragment
|
|
581
|
+
query.html = (str) => { let frag = Query._fragment(str); return query(frag.children, frag) }
|
|
582
|
+
query.version = Query.version
|
|
583
|
+
export { query as $, query as default, query, Query }
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
## JS Files
|
|
2
|
+
|
|
3
|
+
Final JS file - w2ui.js, w2ui.min.js - is compiled from a number of files in /src directory. You should not change the files in /dist directory directly, but do all changes in src directory and compile (concatenate and minify) them.
|
|
4
|
+
|
|
5
|
+
## LESS files
|
|
6
|
+
|
|
7
|
+
Final CSS files are compiled from LESS counterparts. Do not change files in /dist directory. In less/src folder you will find all source files for all widgets, as well as mixing and variables. If you want to create a new theme, you can clone
|
|
8
|
+
|
|
9
|
+
- css/less/w2ui.less
|
|
10
|
+
|
|
11
|
+
and change colors, etc. All of the variables are conveniently included into this file. Once you are done, you can compile the final file with lessc compiler.
|