locize 3.2.5 → 4.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/CHANGELOG.md +4 -0
- package/README.md +74 -36
- package/dist/cjs/{processLegacy.js → _processLegacy.js} +1 -2
- package/dist/cjs/{startStandalone.js → _startStandalone.js} +2 -2
- package/dist/cjs/api/handleCommitKeys.js +7 -0
- package/dist/cjs/api/handleEditKey.js +1 -1
- package/dist/cjs/api/handleIsLocizeEnabled.js +2 -2
- package/dist/cjs/api/handleRequestPopupChanges.js +11 -0
- package/dist/cjs/api/handleSendMatchedUninstrumented.js +26 -0
- package/dist/cjs/api/postMessage.js +32 -45
- package/dist/cjs/clickHandler.js +11 -4
- package/dist/cjs/implementations/dummyImplementation.js +35 -0
- package/dist/cjs/implementations/i18nextImplementation.js +94 -0
- package/dist/cjs/index.d.ts +9 -16
- package/dist/cjs/index.js +4 -9
- package/dist/cjs/locizePlugin.js +6 -90
- package/dist/cjs/observer.js +1 -0
- package/dist/cjs/parser.js +100 -14
- package/dist/cjs/process.js +37 -5
- package/dist/cjs/store.js +1 -0
- package/dist/cjs/ui/elements/highlightBox.js +13 -0
- package/dist/cjs/ui/elements/icons.js +1 -17
- package/dist/cjs/ui/elements/popup.js +3 -3
- package/dist/cjs/ui/elements/ribbonBox.js +3 -6
- package/dist/cjs/ui/highlightNode.js +28 -77
- package/dist/cjs/ui/popup.js +10 -0
- package/dist/cjs/ui/utils.js +18 -0
- package/dist/cjs/uninstrumentedStore.js +18 -2
- package/dist/cjs/utils.js +54 -0
- package/dist/cjs/vars.js +5 -2
- package/dist/esm/{processLegacy.js → _processLegacy.js} +1 -2
- package/dist/esm/{startStandalone.js → _startStandalone.js} +1 -1
- package/dist/esm/api/handleCommitKeys.js +7 -0
- package/dist/esm/api/handleEditKey.js +1 -1
- package/dist/esm/api/handleIsLocizeEnabled.js +2 -2
- package/dist/esm/api/handleRequestPopupChanges.js +11 -0
- package/dist/esm/api/handleSendMatchedUninstrumented.js +20 -0
- package/dist/esm/api/postMessage.js +33 -44
- package/dist/esm/clickHandler.js +11 -4
- package/dist/esm/implementations/dummyImplementation.js +31 -0
- package/dist/esm/implementations/i18nextImplementation.js +85 -0
- package/dist/esm/index.d.ts +9 -16
- package/dist/esm/index.js +5 -8
- package/dist/esm/locizePlugin.js +5 -85
- package/dist/esm/observer.js +1 -0
- package/dist/esm/parser.js +101 -16
- package/dist/esm/process.js +38 -6
- package/dist/esm/store.js +1 -0
- package/dist/esm/ui/elements/highlightBox.js +9 -0
- package/dist/esm/ui/elements/icons.js +2 -16
- package/dist/esm/ui/elements/popup.js +3 -3
- package/dist/esm/ui/elements/ribbonBox.js +4 -7
- package/dist/esm/ui/highlightNode.js +28 -78
- package/dist/esm/ui/popup.js +10 -0
- package/dist/esm/ui/utils.js +18 -1
- package/dist/esm/uninstrumentedStore.js +18 -2
- package/dist/esm/utils.js +53 -1
- package/dist/esm/vars.js +5 -3
- package/dist/umd/locize.js +736 -500
- package/dist/umd/locize.min.js +1 -1
- package/index.d.ts +9 -16
- package/locize.js +736 -500
- package/locize.min.js +1 -1
- package/package.json +1 -1
- package/src/_startStandalone.js +22 -0
- package/src/api/handleCommitKeys.js +9 -0
- package/src/api/handleEditKey.js +5 -11
- package/src/api/handleIsLocizeEnabled.js +7 -2
- package/src/api/handleRequestPopupChanges.js +27 -0
- package/src/api/handleSendMatchedUninstrumented.js +38 -0
- package/src/api/index.js +1 -4
- package/src/api/postMessage.js +37 -53
- package/src/clickHandler.js +30 -8
- package/src/implementations/dummyImplementation.js +29 -0
- package/src/implementations/i18nextImplementation.js +114 -0
- package/src/implementations/index.js +2 -0
- package/src/index.js +8 -7
- package/src/locizePlugin.js +51 -28
- package/src/observer.js +1 -0
- package/src/parser.js +207 -19
- package/src/process.js +52 -5
- package/src/startStandalone.js +4 -17
- package/src/store.js +2 -0
- package/src/ui/elements/highlightBox.js +17 -0
- package/src/ui/elements/popup.js +4 -4
- package/src/ui/elements/ribbonBox.js +12 -8
- package/src/ui/highlightNode.js +102 -71
- package/src/ui/popup.js +33 -5
- package/src/ui/utils.js +28 -1
- package/src/uninstrumentedStore.js +18 -2
- package/src/utils.js +72 -5
- package/src/vars.js +6 -4
- package/dist/cjs/api/handleTurnOff.js +0 -8
- package/dist/cjs/api/handleTurnOn.js +0 -8
- package/dist/esm/api/handleTurnOff.js +0 -6
- package/dist/esm/api/handleTurnOn.js +0 -6
- /package/src/{processLegacy.js → _processLegacy.js} +0 -0
- /package/src/api/{handleTurnOff.js → _handleTurnOff.js} +0 -0
- /package/src/api/{handleTurnOn.js → _handleTurnOn.js} +0 -0
package/src/parser.js
CHANGED
|
@@ -1,7 +1,12 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import {
|
|
2
|
+
unwrap,
|
|
3
|
+
containsHiddenMeta,
|
|
4
|
+
containsHiddenStartMarker
|
|
5
|
+
} from 'i18next-subliminal'
|
|
2
6
|
import { store } from './store.js'
|
|
3
7
|
import { uninstrumentedStore } from './uninstrumentedStore.js'
|
|
4
|
-
import { validAttributes } from './vars.js'
|
|
8
|
+
import { validAttributes, ignoreElements } from './vars.js'
|
|
9
|
+
import { getI18nMetaFromNode } from './utils'
|
|
5
10
|
|
|
6
11
|
import './shims/uniqueID.js'
|
|
7
12
|
|
|
@@ -15,27 +20,44 @@ export function setImplementation (impl) {
|
|
|
15
20
|
|
|
16
21
|
function walk (node, func) {
|
|
17
22
|
if (node.dataset && node.dataset.i18nextEditorElement === 'true') return
|
|
23
|
+
|
|
24
|
+
// parse node
|
|
18
25
|
func(node)
|
|
19
26
|
|
|
20
|
-
|
|
27
|
+
// check if it is is any store - if so remove parent from uninstrumented
|
|
28
|
+
// this avoids situations where a div has inner text (not instrumented) and some children that are instrumented showing a big box around all
|
|
29
|
+
const instr = store.get(node.uniqueID)
|
|
30
|
+
const uninstr = uninstrumentedStore.get(node.uniqueID)
|
|
31
|
+
|
|
32
|
+
if (instr || uninstr) {
|
|
33
|
+
const id = node.parentElement?.uniqueID
|
|
34
|
+
uninstrumentedStore.remove(id, node.parentElement)
|
|
35
|
+
}
|
|
21
36
|
|
|
37
|
+
// parse children
|
|
38
|
+
const children = node.childNodes
|
|
22
39
|
for (
|
|
23
40
|
let i = 0;
|
|
24
41
|
i < children.length;
|
|
25
42
|
i++ // Children are siblings to each other
|
|
26
|
-
) {
|
|
43
|
+
) {
|
|
44
|
+
walk(children[i], func)
|
|
45
|
+
}
|
|
27
46
|
}
|
|
28
47
|
|
|
29
|
-
function
|
|
48
|
+
function extractHiddenMeta (id, type, meta, children) {
|
|
30
49
|
const { invisibleMeta, text } = meta
|
|
31
50
|
if (!invisibleMeta || !invisibleMeta.key || !invisibleMeta.ns) return
|
|
32
51
|
|
|
33
|
-
if (!currentSourceLng) currentSourceLng = i18n
|
|
52
|
+
if (!currentSourceLng) currentSourceLng = i18n.getSourceLng()
|
|
34
53
|
|
|
35
54
|
return {
|
|
36
55
|
eleUniqueID: id,
|
|
37
56
|
textType: type,
|
|
38
|
-
children:
|
|
57
|
+
children:
|
|
58
|
+
children && children.map
|
|
59
|
+
? children.map(c => c.childIndex).join(',')
|
|
60
|
+
: null,
|
|
39
61
|
qualifiedKey: `${invisibleMeta.ns}:${invisibleMeta.key}`,
|
|
40
62
|
...invisibleMeta,
|
|
41
63
|
extractedText: text,
|
|
@@ -44,11 +66,57 @@ function extractMeta (id, type, meta, children) {
|
|
|
44
66
|
i18nRawText: {
|
|
45
67
|
[`${invisibleMeta.lng}`]:
|
|
46
68
|
invisibleMeta.source === 'translation' && i18n
|
|
47
|
-
? i18n
|
|
69
|
+
? i18n?.getResource(
|
|
70
|
+
invisibleMeta.lng,
|
|
71
|
+
invisibleMeta.ns,
|
|
72
|
+
invisibleMeta.key
|
|
73
|
+
)
|
|
48
74
|
: null,
|
|
49
75
|
[`${currentSourceLng}`]:
|
|
50
76
|
invisibleMeta.source === 'translation' && i18n
|
|
51
|
-
? i18n
|
|
77
|
+
? i18n?.getResource(
|
|
78
|
+
currentSourceLng,
|
|
79
|
+
invisibleMeta.ns,
|
|
80
|
+
invisibleMeta.key
|
|
81
|
+
)
|
|
82
|
+
: null
|
|
83
|
+
}
|
|
84
|
+
}
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
export function extractNodeMeta (id, type, nodeMeta = {}, text, children) {
|
|
88
|
+
const meta = nodeMeta[type]
|
|
89
|
+
if (!meta) return
|
|
90
|
+
|
|
91
|
+
if (!currentSourceLng) currentSourceLng = i18n.getSourceLng()
|
|
92
|
+
const i18nTargetLng = i18n.getLng()
|
|
93
|
+
|
|
94
|
+
// console.warn('lng', i18nTargetLng)
|
|
95
|
+
|
|
96
|
+
return {
|
|
97
|
+
eleUniqueID: id,
|
|
98
|
+
textType: type,
|
|
99
|
+
children:
|
|
100
|
+
children && children.map
|
|
101
|
+
? children.map(c => c.childIndex).join(',')
|
|
102
|
+
: null,
|
|
103
|
+
qualifiedKey:
|
|
104
|
+
meta.key && (meta.ns || i18n?.getDefaultNS())
|
|
105
|
+
? `${meta.ns || i18n?.getDefaultNS()}:${meta.key}`
|
|
106
|
+
: null,
|
|
107
|
+
key: meta.key,
|
|
108
|
+
ns: meta.ns || i18n?.getDefaultNS(),
|
|
109
|
+
extractedText: text,
|
|
110
|
+
i18nTargetLng,
|
|
111
|
+
i18nSourceLng: currentSourceLng,
|
|
112
|
+
i18nRawText: {
|
|
113
|
+
[`${i18nTargetLng}`]:
|
|
114
|
+
i18n && meta.ns && meta.key
|
|
115
|
+
? i18n?.getResource(i18nTargetLng, meta.ns, meta.key) || text
|
|
116
|
+
: text,
|
|
117
|
+
[`${currentSourceLng}`]:
|
|
118
|
+
i18n && meta.ns && meta.key
|
|
119
|
+
? i18n?.getResource(currentSourceLng, meta.ns, meta.key)
|
|
52
120
|
: null
|
|
53
121
|
}
|
|
54
122
|
}
|
|
@@ -58,40 +126,79 @@ function containsOnlySpaces (str) {
|
|
|
58
126
|
return /^\s*$/.test(str)
|
|
59
127
|
}
|
|
60
128
|
|
|
129
|
+
function storeIfQualifiedKey (
|
|
130
|
+
id,
|
|
131
|
+
subliminal,
|
|
132
|
+
type,
|
|
133
|
+
nodeI18nMeta,
|
|
134
|
+
node,
|
|
135
|
+
children,
|
|
136
|
+
txt
|
|
137
|
+
) {
|
|
138
|
+
// if we got some key, ns from locize and stored that - reuse it on this run
|
|
139
|
+
const stored = store.get(id)
|
|
140
|
+
const storedMeta = (stored && stored.keys[`${type}`]) || {}
|
|
141
|
+
const typeMeta = nodeI18nMeta[`${type}`] || {}
|
|
142
|
+
|
|
143
|
+
if (!typeMeta.key && storedMeta.key) typeMeta.key = storedMeta.key
|
|
144
|
+
if (!typeMeta.ns && storedMeta.ns) typeMeta.ns = storedMeta.ns
|
|
145
|
+
nodeI18nMeta[`${type}`] = typeMeta
|
|
146
|
+
|
|
147
|
+
// extract metas
|
|
148
|
+
const meta = extractNodeMeta(id, type, nodeI18nMeta, txt, children)
|
|
149
|
+
|
|
150
|
+
// if we can 100% identify that ns:key store - else uninstrumented
|
|
151
|
+
if (meta.qualifiedKey) {
|
|
152
|
+
store.save(id, null, type, meta, node, children)
|
|
153
|
+
uninstrumentedStore.removeKey(i, type, node)
|
|
154
|
+
} else {
|
|
155
|
+
uninstrumentedStore.save(id, type, node, txt)
|
|
156
|
+
}
|
|
157
|
+
}
|
|
158
|
+
|
|
61
159
|
function handleNode (node) {
|
|
160
|
+
if (ignoreElements.indexOf(node.nodeName) > -1) return
|
|
161
|
+
|
|
162
|
+
const nodeI18nMeta = getI18nMetaFromNode(node)
|
|
163
|
+
let usedSubliminalForText = false
|
|
164
|
+
|
|
62
165
|
// test for inner text - but ignore text for elements merged to html containing translation
|
|
63
166
|
if (node.childNodes && !ignoreMergedEleUniqueIds.includes(node.uniqueID)) {
|
|
64
167
|
let merge = []
|
|
168
|
+
|
|
65
169
|
node.childNodes.forEach((child, i) => {
|
|
66
170
|
if (merge.length && child.nodeName !== '#text') {
|
|
67
171
|
ignoreMergedEleUniqueIds.push(child.uniqueID)
|
|
68
172
|
merge.push({ childIndex: i, child })
|
|
69
173
|
}
|
|
70
|
-
if (child.nodeName !== '#text') return
|
|
71
174
|
|
|
175
|
+
if (child.nodeName !== '#text') return
|
|
72
176
|
const txt = child.textContent
|
|
73
177
|
if (containsOnlySpaces(txt)) return
|
|
74
178
|
|
|
75
179
|
const hasHiddenMeta = containsHiddenMeta(txt)
|
|
76
180
|
const hasHiddenStartMarker = containsHiddenStartMarker(txt)
|
|
77
181
|
|
|
182
|
+
if (hasHiddenMeta) usedSubliminalForText = true
|
|
183
|
+
|
|
78
184
|
// console.warn(
|
|
79
185
|
// 'child',
|
|
80
186
|
// child,
|
|
81
187
|
// child.nodeName,
|
|
82
188
|
// child.innerText,
|
|
83
189
|
// hasHiddenStartMarker,
|
|
84
|
-
// hasHiddenMeta
|
|
85
|
-
// )
|
|
190
|
+
// hasHiddenMeta
|
|
191
|
+
// )
|
|
86
192
|
|
|
87
193
|
if (hasHiddenStartMarker && hasHiddenMeta) {
|
|
88
194
|
const meta = unwrap(txt)
|
|
89
195
|
|
|
196
|
+
uninstrumentedStore.remove(node.uniqueID, node) // might be instrumented later and already in uninstrumentedStore - so remove it there first
|
|
90
197
|
store.save(
|
|
91
198
|
node.uniqueID,
|
|
92
199
|
meta.invisibleMeta,
|
|
93
200
|
'text',
|
|
94
|
-
|
|
201
|
+
extractHiddenMeta(node.uniqueID, 'text', meta),
|
|
95
202
|
node
|
|
96
203
|
)
|
|
97
204
|
} else if (hasHiddenStartMarker) {
|
|
@@ -107,21 +214,87 @@ function handleNode (node) {
|
|
|
107
214
|
}, '')
|
|
108
215
|
)
|
|
109
216
|
|
|
217
|
+
uninstrumentedStore.removeKey(node.uniqueID, 'html', node, txt) // might be instrumented later and already in uninstrumentedStore - so remove it there first
|
|
110
218
|
store.save(
|
|
111
219
|
node.uniqueID,
|
|
112
220
|
meta.invisibleMeta,
|
|
113
221
|
'html',
|
|
114
|
-
|
|
222
|
+
extractHiddenMeta(node.uniqueID, 'html', meta, merge),
|
|
115
223
|
node,
|
|
116
224
|
merge
|
|
117
225
|
)
|
|
118
226
|
|
|
119
227
|
// reset
|
|
120
228
|
merge = []
|
|
121
|
-
} else if (txt) {
|
|
122
|
-
uninstrumentedStore.save(node.uniqueID, 'text', node)
|
|
123
229
|
}
|
|
124
230
|
})
|
|
231
|
+
|
|
232
|
+
// no subliminal in text
|
|
233
|
+
if (!usedSubliminalForText) {
|
|
234
|
+
node.childNodes.forEach((child, i) => {
|
|
235
|
+
if (merge.length && child.nodeName !== '#text') {
|
|
236
|
+
ignoreMergedEleUniqueIds.push(child.uniqueID)
|
|
237
|
+
// merge.push({ childIndex: i, child }) // will be pushed regular below with txt
|
|
238
|
+
}
|
|
239
|
+
|
|
240
|
+
// if (child.nodeName !== '#text') return
|
|
241
|
+
const txt = child.textContent
|
|
242
|
+
// if (containsOnlySpaces(txt)) return
|
|
243
|
+
|
|
244
|
+
// merge and add data-i18n=[html]key
|
|
245
|
+
if (
|
|
246
|
+
nodeI18nMeta &&
|
|
247
|
+
nodeI18nMeta['html'] &&
|
|
248
|
+
i < node.childNodes.length - 1
|
|
249
|
+
) {
|
|
250
|
+
merge.push({ childIndex: i, child, text: txt })
|
|
251
|
+
} else if (
|
|
252
|
+
nodeI18nMeta &&
|
|
253
|
+
nodeI18nMeta['html'] &&
|
|
254
|
+
i === node.childNodes.length - 1
|
|
255
|
+
) {
|
|
256
|
+
merge.push({ childIndex: i, child, text: txt })
|
|
257
|
+
|
|
258
|
+
storeIfQualifiedKey(
|
|
259
|
+
node.uniqueID,
|
|
260
|
+
null,
|
|
261
|
+
'html',
|
|
262
|
+
nodeI18nMeta,
|
|
263
|
+
node,
|
|
264
|
+
merge,
|
|
265
|
+
node.innerHTML
|
|
266
|
+
)
|
|
267
|
+
|
|
268
|
+
// reset
|
|
269
|
+
merge = []
|
|
270
|
+
} else if (txt) {
|
|
271
|
+
// console.warn(
|
|
272
|
+
// 'nodeI18nMeta',
|
|
273
|
+
// txt,
|
|
274
|
+
// nodeI18nMeta,
|
|
275
|
+
// hasHiddenMeta,
|
|
276
|
+
// hasHiddenStartMarker
|
|
277
|
+
// )
|
|
278
|
+
|
|
279
|
+
// add data-i18n=key (inner text)
|
|
280
|
+
if (nodeI18nMeta && nodeI18nMeta['text']) {
|
|
281
|
+
storeIfQualifiedKey(
|
|
282
|
+
node.uniqueID,
|
|
283
|
+
null,
|
|
284
|
+
'text',
|
|
285
|
+
nodeI18nMeta,
|
|
286
|
+
node,
|
|
287
|
+
undefined,
|
|
288
|
+
txt
|
|
289
|
+
)
|
|
290
|
+
} else if (child.nodeName === '#text' && !containsOnlySpaces(txt)) {
|
|
291
|
+
// if no metas at all and is a text node that is not just some spaces (html indent)
|
|
292
|
+
// add to uninstrumented for a lookup (locize search)
|
|
293
|
+
uninstrumentedStore.save(node.uniqueID, 'text', node, txt)
|
|
294
|
+
}
|
|
295
|
+
}
|
|
296
|
+
})
|
|
297
|
+
}
|
|
125
298
|
}
|
|
126
299
|
|
|
127
300
|
// test attibutes
|
|
@@ -132,18 +305,33 @@ function handleNode (node) {
|
|
|
132
305
|
if (containsHiddenMeta(txt)) {
|
|
133
306
|
const meta = unwrap(txt)
|
|
134
307
|
|
|
308
|
+
uninstrumentedStore.removeKey(node.uniqueID, attr, node) // might be instrumented later and already in uninstrumentedStore - so remove it there first
|
|
135
309
|
store.save(
|
|
136
310
|
node.uniqueID,
|
|
137
311
|
meta.invisibleMeta,
|
|
138
|
-
|
|
139
|
-
|
|
312
|
+
attr,
|
|
313
|
+
extractHiddenMeta(node.uniqueID, `${attr}`, meta),
|
|
140
314
|
node
|
|
141
315
|
)
|
|
142
316
|
} else if (txt) {
|
|
143
|
-
|
|
317
|
+
if (nodeI18nMeta && nodeI18nMeta[attr]) {
|
|
318
|
+
storeIfQualifiedKey(
|
|
319
|
+
node.uniqueID,
|
|
320
|
+
null,
|
|
321
|
+
attr,
|
|
322
|
+
nodeI18nMeta,
|
|
323
|
+
node,
|
|
324
|
+
undefined,
|
|
325
|
+
txt
|
|
326
|
+
)
|
|
327
|
+
} else {
|
|
328
|
+
uninstrumentedStore.save(node.uniqueID, attr, node, txt)
|
|
329
|
+
}
|
|
144
330
|
}
|
|
145
331
|
})
|
|
146
332
|
|
|
333
|
+
// console.warn('store', store)
|
|
334
|
+
|
|
147
335
|
// TODO: how to handle react Trans things?!?
|
|
148
336
|
}
|
|
149
337
|
|
package/src/process.js
CHANGED
|
@@ -5,17 +5,34 @@ import { initDragElement, initResizeElement } from './ui/popup.js'
|
|
|
5
5
|
import { Popup, popupId } from './ui/elements/popup.js'
|
|
6
6
|
import { getIframeUrl } from './vars.js'
|
|
7
7
|
import { api } from './api/index.js'
|
|
8
|
+
import { getQsParameterByName } from './utils.js'
|
|
9
|
+
import * as implementations from './implementations/index.js'
|
|
10
|
+
|
|
11
|
+
const dummyImplementation = implementations.dummy.getImplementation()
|
|
12
|
+
|
|
13
|
+
let isInIframe = typeof window !== 'undefined'
|
|
14
|
+
try {
|
|
15
|
+
// eslint-disable-next-line no-undef, no-restricted-globals
|
|
16
|
+
isInIframe = self !== top
|
|
17
|
+
// eslint-disable-next-line no-empty
|
|
18
|
+
} catch (e) {}
|
|
8
19
|
|
|
9
20
|
// eslint-disable-next-line no-unused-vars
|
|
10
21
|
let data = []
|
|
11
22
|
|
|
12
|
-
export function start (
|
|
23
|
+
export function start (
|
|
24
|
+
implementation = dummyImplementation,
|
|
25
|
+
opt = { show: false, qsProp: 'incontext' }
|
|
26
|
+
) {
|
|
13
27
|
if (typeof document === 'undefined') return
|
|
28
|
+
|
|
29
|
+
const showInContext = opt.show || getQsParameterByName(opt.qsProp) === 'true'
|
|
30
|
+
|
|
14
31
|
// get locize id, version
|
|
15
32
|
const scriptEle = document.getElementById('locize')
|
|
16
33
|
|
|
17
|
-
let config = {}
|
|
18
|
-
['projectId', 'version'].forEach(attr => {
|
|
34
|
+
let config = {}
|
|
35
|
+
;['projectId', 'version'].forEach(attr => {
|
|
19
36
|
if (!scriptEle) return
|
|
20
37
|
let value =
|
|
21
38
|
scriptEle.getAttribute(attr.toLowerCase()) ||
|
|
@@ -24,9 +41,10 @@ export function start (implementation = {}) {
|
|
|
24
41
|
if (value === 'false') value = false
|
|
25
42
|
if (value !== undefined && value !== null) config[attr] = value
|
|
26
43
|
})
|
|
27
|
-
config = { ...implementation.getLocizeDetails(), ...config }
|
|
44
|
+
config = { ...implementation.getLocizeDetails(), ...config, ...opt }
|
|
28
45
|
|
|
29
46
|
// init stuff
|
|
47
|
+
api.config = config
|
|
30
48
|
api.init(implementation)
|
|
31
49
|
setImplementation(implementation)
|
|
32
50
|
|
|
@@ -36,6 +54,9 @@ export function start (implementation = {}) {
|
|
|
36
54
|
})
|
|
37
55
|
|
|
38
56
|
function continueToStart () {
|
|
57
|
+
// don't show if not in iframe and no qs
|
|
58
|
+
if (!isInIframe && !showInContext) return
|
|
59
|
+
|
|
39
60
|
const observer = createObserver(document.body, eles => {
|
|
40
61
|
eles.forEach(ele => {
|
|
41
62
|
data = parseTree(ele)
|
|
@@ -47,7 +68,7 @@ export function start (implementation = {}) {
|
|
|
47
68
|
startMouseTracking(observer)
|
|
48
69
|
|
|
49
70
|
// append popup
|
|
50
|
-
if (!document.getElementById(popupId)) {
|
|
71
|
+
if (!isInIframe && !document.getElementById(popupId)) {
|
|
51
72
|
document.body.append(
|
|
52
73
|
Popup(getIframeUrl(), () => {
|
|
53
74
|
api.requestInitialize(config)
|
|
@@ -56,6 +77,32 @@ export function start (implementation = {}) {
|
|
|
56
77
|
initDragElement()
|
|
57
78
|
initResizeElement()
|
|
58
79
|
}
|
|
80
|
+
|
|
81
|
+
// propagate url changes
|
|
82
|
+
if (typeof window !== 'undefined') {
|
|
83
|
+
let oldHref = window.document.location.href
|
|
84
|
+
api.sendHrefchanged(oldHref)
|
|
85
|
+
|
|
86
|
+
const bodyList = window.document.querySelector('body')
|
|
87
|
+
|
|
88
|
+
const observer = new window.MutationObserver(mutations => {
|
|
89
|
+
mutations.forEach(mutation => {
|
|
90
|
+
if (oldHref !== window.document.location.href) {
|
|
91
|
+
// console.warn('url changed', oldHref, document.location.href);
|
|
92
|
+
oldHref = window.document.location.href
|
|
93
|
+
|
|
94
|
+
api.sendHrefchanged(oldHref)
|
|
95
|
+
}
|
|
96
|
+
})
|
|
97
|
+
})
|
|
98
|
+
|
|
99
|
+
const config = {
|
|
100
|
+
childList: true,
|
|
101
|
+
subtree: true
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
observer.observe(bodyList, config)
|
|
105
|
+
}
|
|
59
106
|
}
|
|
60
107
|
|
|
61
108
|
if (document.body) return continueToStart()
|
package/src/startStandalone.js
CHANGED
|
@@ -1,21 +1,8 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { start } from './process.js'
|
|
2
2
|
|
|
3
|
-
export function startStandalone () {
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
return {}
|
|
7
|
-
},
|
|
8
|
-
getLng: () => {
|
|
9
|
-
return undefined
|
|
10
|
-
},
|
|
11
|
-
setResource: () => {},
|
|
12
|
-
triggerRerender: () => {},
|
|
13
|
-
getResourceBundle: () => {
|
|
14
|
-
return {}
|
|
15
|
-
},
|
|
16
|
-
bindMissingKeyHandler: () => {},
|
|
17
|
-
bindLanguageChange: () => {}
|
|
18
|
-
})
|
|
3
|
+
export function startStandalone (options) {
|
|
4
|
+
const { implementation, ...rest } = options
|
|
5
|
+
start(implementation, rest)
|
|
19
6
|
}
|
|
20
7
|
|
|
21
8
|
if (typeof window !== 'undefined')
|
package/src/store.js
CHANGED
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
export function HighlightBox (ele, borderColor, shadowColor) {
|
|
2
|
+
const rect = ele.getBoundingClientRect()
|
|
3
|
+
|
|
4
|
+
const box = document.createElement('div')
|
|
5
|
+
box.style = `position: absolute; top: ${
|
|
6
|
+
rect.top - 2 + window.scrollY
|
|
7
|
+
}px; left: ${rect.left - 2 + window.scrollX}px; height: ${
|
|
8
|
+
rect.height + 4
|
|
9
|
+
}px; width: ${
|
|
10
|
+
rect.width + 4
|
|
11
|
+
}px; border: 1px solid ${borderColor}; border-radius: 2px; ${
|
|
12
|
+
shadowColor ? `box-shadow: 0 0 20px 0 ${shadowColor};` : ''
|
|
13
|
+
}`
|
|
14
|
+
box.setAttribute('data-i18next-editor-element', 'true')
|
|
15
|
+
|
|
16
|
+
return box
|
|
17
|
+
}
|
package/src/ui/elements/popup.js
CHANGED
|
@@ -95,7 +95,7 @@ function Ribbon (popupEle, onMaximize) {
|
|
|
95
95
|
background-color: rgba(249, 249, 249, 0.2);
|
|
96
96
|
backdrop-filter: blur(3px);
|
|
97
97
|
box-shadow: 0 0 15px rgba(0, 0, 0, 0.2);
|
|
98
|
-
border-radius: 50
|
|
98
|
+
border-radius: 50%;
|
|
99
99
|
`
|
|
100
100
|
|
|
101
101
|
ribbon.onclick = () => {
|
|
@@ -155,8 +155,8 @@ export function Popup (url, cb) {
|
|
|
155
155
|
min-width: 300px;
|
|
156
156
|
--i18next-editor-popup-width: 400px;
|
|
157
157
|
width: var(--i18next-editor-popup-width);
|
|
158
|
-
max-height:
|
|
159
|
-
max-width:
|
|
158
|
+
max-height: 800px;
|
|
159
|
+
max-width: 1000px;
|
|
160
160
|
|
|
161
161
|
position: fixed;
|
|
162
162
|
--i18next-editor-popup-position-top: calc(100vh - var(--i18next-editor-popup-height) - 10px);
|
|
@@ -205,7 +205,7 @@ export function Popup (url, cb) {
|
|
|
205
205
|
iframe.style = `
|
|
206
206
|
z-index: 100;
|
|
207
207
|
width: 100%;
|
|
208
|
-
height: calc(100% -
|
|
208
|
+
height: calc(100% - 32px);
|
|
209
209
|
border: none;
|
|
210
210
|
background: #fff;
|
|
211
211
|
`
|
|
@@ -2,18 +2,18 @@ import { colors } from '../../vars.js'
|
|
|
2
2
|
import { sheet } from '../stylesheet.js'
|
|
3
3
|
import { api } from '../../api/index.js'
|
|
4
4
|
|
|
5
|
-
import {
|
|
5
|
+
import { EditIcon } from './icons.js'
|
|
6
6
|
|
|
7
7
|
if (sheet) {
|
|
8
8
|
sheet.insertRule(
|
|
9
|
-
'.i18next-editor-button:hover { background-color: rgba(
|
|
9
|
+
'.i18next-editor-button:hover { background-color: rgba(21, 65, 154, 1) !important; }'
|
|
10
10
|
)
|
|
11
11
|
}
|
|
12
12
|
export function RibbonButton (text, attrTitle, onClick) {
|
|
13
13
|
const btn = document.createElement('button')
|
|
14
14
|
|
|
15
15
|
btn.style =
|
|
16
|
-
'font-family: Arial; position: relative; backdrop-filter: blur(3px); cursor: pointer; padding: 2px 10px 2px 20px; font-size: 15px; font-weight: 300; text-transform: uppercase; color: #fff; background-color: rgba(
|
|
16
|
+
'font-family: Arial; position: relative; backdrop-filter: blur(3px); cursor: pointer; padding: 2px 10px 2px 20px; font-size: 15px; font-weight: 300; text-transform: uppercase; color: #fff; background-color: rgba(25, 118, 210, 0.8); border: none; border-radius: 12px; z-index: 99999;'
|
|
17
17
|
btn.classList.add('i18next-editor-button')
|
|
18
18
|
btn.setAttribute('data-i18next-editor-element', 'true')
|
|
19
19
|
btn.setAttribute('title', attrTitle)
|
|
@@ -53,8 +53,8 @@ export function RibbonBox (keys = {}) {
|
|
|
53
53
|
`
|
|
54
54
|
box.appendChild(arrow)
|
|
55
55
|
|
|
56
|
-
const logo = RibbonLogo()
|
|
57
|
-
box.appendChild(logo)
|
|
56
|
+
// const logo = RibbonLogo()
|
|
57
|
+
// box.appendChild(logo)
|
|
58
58
|
|
|
59
59
|
const btnbox = document.createElement('div')
|
|
60
60
|
btnbox.style =
|
|
@@ -63,9 +63,13 @@ export function RibbonBox (keys = {}) {
|
|
|
63
63
|
Object.keys(keys).forEach(k => {
|
|
64
64
|
const data = keys[k]
|
|
65
65
|
|
|
66
|
-
const btn = RibbonButton(
|
|
67
|
-
|
|
68
|
-
|
|
66
|
+
const btn = RibbonButton(
|
|
67
|
+
k.replace('attr:', ''),
|
|
68
|
+
`${data.ns}:${data.key}`,
|
|
69
|
+
() => {
|
|
70
|
+
api.selectKey(data)
|
|
71
|
+
}
|
|
72
|
+
)
|
|
69
73
|
btn.style.marginBottom = '2px'
|
|
70
74
|
btnbox.appendChild(btn)
|
|
71
75
|
})
|