@redacto.io/consent-sdk-js 0.1.0 → 0.1.2-beta.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/dist/redacto.global.js +2 -2
- package/dist/redacto.global.js.map +1 -1
- package/dist/redacto.js +305 -118
- package/dist/redacto.mjs +305 -118
- package/package.json +3 -3
package/dist/redacto.mjs
CHANGED
|
@@ -67,10 +67,49 @@ function applyAttrs(element, attrs) {
|
|
|
67
67
|
}
|
|
68
68
|
}
|
|
69
69
|
}
|
|
70
|
+
var UNITLESS_PROPS = /* @__PURE__ */ new Set([
|
|
71
|
+
"animationIterationCount",
|
|
72
|
+
"aspectRatio",
|
|
73
|
+
"borderImageOutset",
|
|
74
|
+
"borderImageSlice",
|
|
75
|
+
"borderImageWidth",
|
|
76
|
+
"boxFlex",
|
|
77
|
+
"boxFlexGroup",
|
|
78
|
+
"boxOrdinalGroup",
|
|
79
|
+
"columnCount",
|
|
80
|
+
"columns",
|
|
81
|
+
"flex",
|
|
82
|
+
"flexGrow",
|
|
83
|
+
"flexPositive",
|
|
84
|
+
"flexShrink",
|
|
85
|
+
"flexNegative",
|
|
86
|
+
"flexOrder",
|
|
87
|
+
"fontWeight",
|
|
88
|
+
"gridArea",
|
|
89
|
+
"gridRow",
|
|
90
|
+
"gridRowEnd",
|
|
91
|
+
"gridRowSpan",
|
|
92
|
+
"gridRowStart",
|
|
93
|
+
"gridColumn",
|
|
94
|
+
"gridColumnEnd",
|
|
95
|
+
"gridColumnSpan",
|
|
96
|
+
"gridColumnStart",
|
|
97
|
+
"lineClamp",
|
|
98
|
+
"lineHeight",
|
|
99
|
+
"opacity",
|
|
100
|
+
"order",
|
|
101
|
+
"orphans",
|
|
102
|
+
"scale",
|
|
103
|
+
"tabSize",
|
|
104
|
+
"widows",
|
|
105
|
+
"zIndex",
|
|
106
|
+
"zoom"
|
|
107
|
+
]);
|
|
70
108
|
function applyStyles(element, styles2) {
|
|
71
109
|
for (const [key, value] of Object.entries(styles2)) {
|
|
72
110
|
if (value == null) continue;
|
|
73
|
-
|
|
111
|
+
const stringValue = typeof value === "number" && !UNITLESS_PROPS.has(key) ? `${value}px` : String(value);
|
|
112
|
+
element.style[key] = stringValue;
|
|
74
113
|
}
|
|
75
114
|
}
|
|
76
115
|
function appendChildren(parent, children) {
|
|
@@ -548,19 +587,8 @@ var verifyGuardianStatus = async ({
|
|
|
548
587
|
};
|
|
549
588
|
|
|
550
589
|
// src/styles/inject.ts
|
|
551
|
-
var
|
|
552
|
-
var
|
|
553
|
-
if (stylesInjected || typeof document === "undefined") {
|
|
554
|
-
return;
|
|
555
|
-
}
|
|
556
|
-
const STYLE_ID = "redacto-consent-checkbox-styles";
|
|
557
|
-
if (document.getElementById(STYLE_ID)) {
|
|
558
|
-
stylesInjected = true;
|
|
559
|
-
return;
|
|
560
|
-
}
|
|
561
|
-
const style = document.createElement("style");
|
|
562
|
-
style.id = STYLE_ID;
|
|
563
|
-
style.textContent = `
|
|
590
|
+
var STYLE_ID = "redacto-consent-checkbox-styles";
|
|
591
|
+
var STYLE_CONTENT = `
|
|
564
592
|
/* Redacto Consent SDK Checkbox Styles */
|
|
565
593
|
.redacto-checkbox-large {
|
|
566
594
|
appearance: none !important;
|
|
@@ -691,8 +719,18 @@ var injectCheckboxStyles = () => {
|
|
|
691
719
|
background-color: #2563eb !important;
|
|
692
720
|
}
|
|
693
721
|
`;
|
|
694
|
-
|
|
695
|
-
|
|
722
|
+
var injectCheckboxStyles = (root) => {
|
|
723
|
+
if (typeof document === "undefined") return;
|
|
724
|
+
const existing = root instanceof Document ? root.getElementById(STYLE_ID) : root.querySelector(`#${STYLE_ID}`);
|
|
725
|
+
if (existing) return;
|
|
726
|
+
const style = document.createElement("style");
|
|
727
|
+
style.id = STYLE_ID;
|
|
728
|
+
style.textContent = STYLE_CONTENT;
|
|
729
|
+
if (root instanceof Document) {
|
|
730
|
+
root.head.appendChild(style);
|
|
731
|
+
} else {
|
|
732
|
+
root.appendChild(style);
|
|
733
|
+
}
|
|
696
734
|
};
|
|
697
735
|
|
|
698
736
|
// src/styles/modal.ts
|
|
@@ -747,7 +785,8 @@ var styles = {
|
|
|
747
785
|
topSection: {
|
|
748
786
|
display: "flex",
|
|
749
787
|
justifyContent: "space-between",
|
|
750
|
-
alignItems: "
|
|
788
|
+
alignItems: "flex-start",
|
|
789
|
+
gap: "10px",
|
|
751
790
|
paddingBottom: "15px",
|
|
752
791
|
borderBottom: "none",
|
|
753
792
|
backgroundColor: "#ffffff",
|
|
@@ -759,6 +798,8 @@ var styles = {
|
|
|
759
798
|
display: "flex",
|
|
760
799
|
alignItems: "center",
|
|
761
800
|
gap: "10px",
|
|
801
|
+
flex: "1 1 0",
|
|
802
|
+
minWidth: 0,
|
|
762
803
|
margin: 0,
|
|
763
804
|
padding: 0,
|
|
764
805
|
boxSizing: "border-box"
|
|
@@ -766,7 +807,9 @@ var styles = {
|
|
|
766
807
|
logo: {
|
|
767
808
|
height: "32px",
|
|
768
809
|
width: "auto",
|
|
810
|
+
maxWidth: "140px",
|
|
769
811
|
objectFit: "contain",
|
|
812
|
+
flexShrink: 0,
|
|
770
813
|
margin: 0,
|
|
771
814
|
padding: 0,
|
|
772
815
|
display: "block"
|
|
@@ -778,6 +821,10 @@ var styles = {
|
|
|
778
821
|
letterSpacing: "0.2px",
|
|
779
822
|
verticalAlign: "middle",
|
|
780
823
|
color: "#101828",
|
|
824
|
+
flex: "1 1 auto",
|
|
825
|
+
minWidth: 0,
|
|
826
|
+
wordBreak: "normal",
|
|
827
|
+
overflowWrap: "anywhere",
|
|
781
828
|
margin: 0,
|
|
782
829
|
padding: 0,
|
|
783
830
|
textAlign: "left"
|
|
@@ -789,6 +836,7 @@ var styles = {
|
|
|
789
836
|
display: "flex",
|
|
790
837
|
alignItems: "center",
|
|
791
838
|
justifyContent: "center",
|
|
839
|
+
flexShrink: 0,
|
|
792
840
|
fontWeight: 400,
|
|
793
841
|
fontSize: "12px",
|
|
794
842
|
lineHeight: "150%",
|
|
@@ -1273,12 +1321,41 @@ function createGreenCheckmark(size, ariaLabel) {
|
|
|
1273
1321
|
}
|
|
1274
1322
|
|
|
1275
1323
|
// src/modal/language-selector.ts
|
|
1324
|
+
var LANGUAGE_NATIVE_LABELS = {
|
|
1325
|
+
English: "English",
|
|
1326
|
+
Assamese: "\u0985\u09B8\u09AE\u09C0\u09AF\u09BC\u09BE (Assamese)",
|
|
1327
|
+
Bengali: "\u09AC\u09BE\u0982\u09B2\u09BE (Bengali)",
|
|
1328
|
+
Bodo: "\u092C\u0921\u093C\u094B (Bodo)",
|
|
1329
|
+
Dogri: "\u0921\u094B\u0917\u0930\u0940 (Dogri)",
|
|
1330
|
+
"Goan Konkani": "\u0915\u094B\u0902\u0915\u0923\u0940 (Goan Konkani)",
|
|
1331
|
+
Gujarati: "\u0A97\u0AC1\u0A9C\u0AB0\u0ABE\u0AA4\u0AC0 (Gujarati)",
|
|
1332
|
+
Hindi: "\u0939\u093F\u0928\u094D\u0926\u0940 (Hindi)",
|
|
1333
|
+
Kannada: "\u0C95\u0CA8\u0CCD\u0CA8\u0CA1 (Kannada)",
|
|
1334
|
+
Kashmiri: "\u0643\u0672\u0634\u064F\u0631 (Kashmiri)",
|
|
1335
|
+
Maithili: "\u092E\u0948\u0925\u093F\u0932\u0940 (Maithili)",
|
|
1336
|
+
Malayalam: "\u0D2E\u0D32\u0D2F\u0D3E\u0D33\u0D02 (Malayalam)",
|
|
1337
|
+
Manipuri: "\uABC3\uABE9\uABC7\uABE9\uABC2\uABE3\uABDF (Manipuri)",
|
|
1338
|
+
Marathi: "\u092E\u0930\u093E\u0920\u0940 (Marathi)",
|
|
1339
|
+
Nepali: "\u0928\u0947\u092A\u093E\u0932\u0940 (Nepali)",
|
|
1340
|
+
Odia: "\u0B13\u0B21\u0B3C\u0B3F\u0B06 (Odia)",
|
|
1341
|
+
Punjabi: "\u0A2A\u0A70\u0A1C\u0A3E\u0A2C\u0A40 (Punjabi)",
|
|
1342
|
+
Sanskrit: "\u0938\u0902\u0938\u094D\u0915\u0943\u0924\u092E\u094D (Sanskrit)",
|
|
1343
|
+
Santali: "\u1C65\u1C5F\u1C71\u1C5B\u1C5F\u1C72\u1C64 (Santali)",
|
|
1344
|
+
Sindhi: "\u0633\u0646\u068C\u064A (Sindhi)",
|
|
1345
|
+
Tamil: "\u0BA4\u0BAE\u0BBF\u0BB4\u0BCD (Tamil)",
|
|
1346
|
+
Telugu: "\u0C24\u0C46\u0C32\u0C41\u0C17\u0C41 (Telugu)",
|
|
1347
|
+
Urdu: "\u0627\u0631\u062F\u0648 (Urdu)"
|
|
1348
|
+
};
|
|
1349
|
+
var toNativeLabel = (name) => {
|
|
1350
|
+
var _a;
|
|
1351
|
+
return (_a = LANGUAGE_NATIVE_LABELS[name]) != null ? _a : name;
|
|
1352
|
+
};
|
|
1276
1353
|
function renderLanguageSelector(options) {
|
|
1277
1354
|
var _a, _b, _c, _d;
|
|
1278
|
-
const { languages, selectedLanguage, settings, onSelect } = options;
|
|
1355
|
+
const { languages, selectedLanguage, settings, onSelect, dropdownContainer } = options;
|
|
1279
1356
|
let isOpen = false;
|
|
1280
1357
|
const buttonText = el("span");
|
|
1281
|
-
buttonText.textContent = selectedLanguage;
|
|
1358
|
+
buttonText.textContent = toNativeLabel(selectedLanguage);
|
|
1282
1359
|
const chevronSvg = svg(
|
|
1283
1360
|
"svg",
|
|
1284
1361
|
{
|
|
@@ -1307,7 +1384,7 @@ function renderLanguageSelector(options) {
|
|
|
1307
1384
|
tabIndex: "0",
|
|
1308
1385
|
"aria-haspopup": "listbox",
|
|
1309
1386
|
"aria-expanded": "false",
|
|
1310
|
-
"aria-label": `Language selector, current: ${selectedLanguage}`,
|
|
1387
|
+
"aria-label": `Language selector, current: ${toNativeLabel(selectedLanguage)}`,
|
|
1311
1388
|
onClick: () => toggleDropdown(),
|
|
1312
1389
|
onKeydown: (e) => {
|
|
1313
1390
|
if (e.key === "Enter" || e.key === " ") {
|
|
@@ -1364,13 +1441,11 @@ function renderLanguageSelector(options) {
|
|
|
1364
1441
|
e.target.style.backgroundColor = isSelected ? "#f3f4f6" : "#ffffff";
|
|
1365
1442
|
}
|
|
1366
1443
|
});
|
|
1367
|
-
item.textContent = lang;
|
|
1444
|
+
item.textContent = toNativeLabel(lang);
|
|
1368
1445
|
dropdown.appendChild(item);
|
|
1369
1446
|
}
|
|
1370
1447
|
const container = el("div", { style: styles.languageSelectorContainer }, button);
|
|
1371
|
-
|
|
1372
|
-
document.body.appendChild(dropdown);
|
|
1373
|
-
}
|
|
1448
|
+
dropdownContainer.appendChild(dropdown);
|
|
1374
1449
|
function positionDropdown() {
|
|
1375
1450
|
const rect = button.getBoundingClientRect();
|
|
1376
1451
|
dropdown.style.top = `${rect.bottom + 4}px`;
|
|
@@ -1378,10 +1453,14 @@ function renderLanguageSelector(options) {
|
|
|
1378
1453
|
dropdown.style.left = "auto";
|
|
1379
1454
|
}
|
|
1380
1455
|
const clickOutsideHandler = (e) => {
|
|
1381
|
-
|
|
1382
|
-
|
|
1383
|
-
|
|
1384
|
-
|
|
1456
|
+
var _a2, _b2;
|
|
1457
|
+
const path = (_b2 = (_a2 = e.composedPath) == null ? void 0 : _a2.call(e)) != null ? _b2 : [];
|
|
1458
|
+
if (path.includes(container) || path.includes(dropdown)) return;
|
|
1459
|
+
if (path.length === 0) {
|
|
1460
|
+
const target = e.target;
|
|
1461
|
+
if (container.contains(target) || dropdown.contains(target)) return;
|
|
1462
|
+
}
|
|
1463
|
+
closeDropdown();
|
|
1385
1464
|
};
|
|
1386
1465
|
const repositionHandler = () => {
|
|
1387
1466
|
if (isOpen) positionDropdown();
|
|
@@ -1414,6 +1493,7 @@ function renderLanguageSelector(options) {
|
|
|
1414
1493
|
// src/modal/keyboard.ts
|
|
1415
1494
|
function setupKeyboardTrap(modalEl, onEscape) {
|
|
1416
1495
|
const handler = (e) => {
|
|
1496
|
+
var _a;
|
|
1417
1497
|
if (e.key === "Escape") {
|
|
1418
1498
|
e.preventDefault();
|
|
1419
1499
|
onEscape();
|
|
@@ -1432,13 +1512,15 @@ function setupKeyboardTrap(modalEl, onEscape) {
|
|
|
1432
1512
|
}
|
|
1433
1513
|
const first = focusable[0];
|
|
1434
1514
|
const last = focusable[focusable.length - 1];
|
|
1515
|
+
const root = modalEl.getRootNode();
|
|
1516
|
+
const active = (_a = root.activeElement) != null ? _a : document.activeElement;
|
|
1435
1517
|
if (e.shiftKey) {
|
|
1436
|
-
if (
|
|
1518
|
+
if (active === first) {
|
|
1437
1519
|
e.preventDefault();
|
|
1438
1520
|
last.focus();
|
|
1439
1521
|
}
|
|
1440
1522
|
} else {
|
|
1441
|
-
if (
|
|
1523
|
+
if (active === last) {
|
|
1442
1524
|
e.preventDefault();
|
|
1443
1525
|
first.focus();
|
|
1444
1526
|
}
|
|
@@ -1528,7 +1610,15 @@ var DPO_AUDIO_ELEMENT_MAP = [
|
|
|
1528
1610
|
|
|
1529
1611
|
// src/modal/tts.ts
|
|
1530
1612
|
var TTSManager = class {
|
|
1531
|
-
|
|
1613
|
+
/**
|
|
1614
|
+
* @param onStateChange Invoked whenever playback state changes so the host
|
|
1615
|
+
* can refresh its UI (e.g. swap the play/pause icon).
|
|
1616
|
+
* @param root The root in which to look up highlightable elements by id.
|
|
1617
|
+
* When the modal is rendered inside a shadow root, pass that shadow root
|
|
1618
|
+
* so queries stay scoped to the SDK's tree (and don't accidentally hit
|
|
1619
|
+
* element ids that the host page also defines).
|
|
1620
|
+
*/
|
|
1621
|
+
constructor(onStateChange, root) {
|
|
1532
1622
|
this.audioUrls = null;
|
|
1533
1623
|
this.audioSequence = [];
|
|
1534
1624
|
this.elementIdSequence = [];
|
|
@@ -1540,6 +1630,7 @@ var TTSManager = class {
|
|
|
1540
1630
|
this.highlightedElementId = null;
|
|
1541
1631
|
this.abortController = null;
|
|
1542
1632
|
this.onStateChange = onStateChange;
|
|
1633
|
+
this.root = root;
|
|
1543
1634
|
}
|
|
1544
1635
|
get isPlaying() {
|
|
1545
1636
|
return this._isPlaying;
|
|
@@ -1552,9 +1643,11 @@ var TTSManager = class {
|
|
|
1552
1643
|
}
|
|
1553
1644
|
async fetchAudioUrls(params) {
|
|
1554
1645
|
var _a;
|
|
1555
|
-
this.
|
|
1646
|
+
this.stopInternal();
|
|
1556
1647
|
this._isAvailable = false;
|
|
1557
1648
|
this.audioUrls = null;
|
|
1649
|
+
this.audioSequence = [];
|
|
1650
|
+
this.elementIdSequence = [];
|
|
1558
1651
|
this.onStateChange();
|
|
1559
1652
|
(_a = this.abortController) == null ? void 0 : _a.abort();
|
|
1560
1653
|
this.abortController = new AbortController();
|
|
@@ -1567,13 +1660,15 @@ var TTSManager = class {
|
|
|
1567
1660
|
signal: this.abortController.signal
|
|
1568
1661
|
});
|
|
1569
1662
|
this.audioUrls = response.detail;
|
|
1570
|
-
this._isAvailable = true;
|
|
1571
1663
|
this.buildSequences(params.content);
|
|
1664
|
+
this._isAvailable = this.audioSequence.length > 0;
|
|
1572
1665
|
this.onStateChange();
|
|
1573
1666
|
} catch (error) {
|
|
1574
1667
|
if (error.name !== "AbortError") {
|
|
1575
1668
|
this._isAvailable = false;
|
|
1576
1669
|
this.audioUrls = null;
|
|
1670
|
+
this.audioSequence = [];
|
|
1671
|
+
this.elementIdSequence = [];
|
|
1577
1672
|
this.onStateChange();
|
|
1578
1673
|
}
|
|
1579
1674
|
}
|
|
@@ -1647,6 +1742,16 @@ var TTSManager = class {
|
|
|
1647
1742
|
}
|
|
1648
1743
|
}
|
|
1649
1744
|
stop() {
|
|
1745
|
+
this.stopInternal();
|
|
1746
|
+
this.onStateChange();
|
|
1747
|
+
}
|
|
1748
|
+
/**
|
|
1749
|
+
* Internal stop used by code paths (like fetchAudioUrls) that will fire
|
|
1750
|
+
* their own onStateChange after composing a richer state update — we don't
|
|
1751
|
+
* want the intermediate notification to flicker the UI based on a half-set
|
|
1752
|
+
* state (e.g. _isAvailable still true from the previous language).
|
|
1753
|
+
*/
|
|
1754
|
+
stopInternal() {
|
|
1650
1755
|
if (this.currentAudio) {
|
|
1651
1756
|
this.currentAudio.pause();
|
|
1652
1757
|
this.currentAudio.currentTime = 0;
|
|
@@ -1657,7 +1762,6 @@ var TTSManager = class {
|
|
|
1657
1762
|
this.currentIndex = 0;
|
|
1658
1763
|
this.removeHighlights();
|
|
1659
1764
|
this.highlightedElementId = null;
|
|
1660
|
-
this.onStateChange();
|
|
1661
1765
|
}
|
|
1662
1766
|
destroy() {
|
|
1663
1767
|
var _a;
|
|
@@ -1698,7 +1802,7 @@ var TTSManager = class {
|
|
|
1698
1802
|
this.removeHighlights();
|
|
1699
1803
|
this.highlightedElementId = elementId;
|
|
1700
1804
|
setTimeout(() => {
|
|
1701
|
-
const element =
|
|
1805
|
+
const element = "getElementById" in this.root ? this.root.getElementById(elementId) : this.root.querySelector(`#${CSS.escape(elementId)}`);
|
|
1702
1806
|
if (element) {
|
|
1703
1807
|
element.classList.add("redacto-tts-highlight");
|
|
1704
1808
|
const rect = element.getBoundingClientRect();
|
|
@@ -1714,7 +1818,7 @@ var TTSManager = class {
|
|
|
1714
1818
|
}, 50);
|
|
1715
1819
|
}
|
|
1716
1820
|
removeHighlights() {
|
|
1717
|
-
|
|
1821
|
+
this.root.querySelectorAll(".redacto-tts-highlight").forEach((el2) => {
|
|
1718
1822
|
el2.classList.remove("redacto-tts-highlight");
|
|
1719
1823
|
});
|
|
1720
1824
|
}
|
|
@@ -2521,6 +2625,10 @@ function resolveColors(settings, activeConfig) {
|
|
|
2521
2625
|
// src/modal/index.ts
|
|
2522
2626
|
var ModalController = class {
|
|
2523
2627
|
constructor(options) {
|
|
2628
|
+
this.hostEl = null;
|
|
2629
|
+
this.shadowRoot = null;
|
|
2630
|
+
this.previousBodyOverflow = null;
|
|
2631
|
+
this.previousHtmlOverflow = null;
|
|
2524
2632
|
this.overlayEl = null;
|
|
2525
2633
|
this.modalEl = null;
|
|
2526
2634
|
this.purposeRefs = null;
|
|
@@ -2529,6 +2637,7 @@ var ModalController = class {
|
|
|
2529
2637
|
this.keyboardCleanup = null;
|
|
2530
2638
|
this.abortController = null;
|
|
2531
2639
|
this.unsubscribe = null;
|
|
2640
|
+
this.ttsManager = null;
|
|
2532
2641
|
this.guardianFormRefs = null;
|
|
2533
2642
|
this.statusPollTimeout = null;
|
|
2534
2643
|
this.popupCheckInterval = null;
|
|
@@ -2580,10 +2689,8 @@ var ModalController = class {
|
|
|
2580
2689
|
guardianFormData: { guardianName: "", guardianContact: "", guardianRelationship: "" }
|
|
2581
2690
|
});
|
|
2582
2691
|
this.mediaQuery = createMediaQuery("(max-width: 768px)");
|
|
2583
|
-
this.ttsManager = new TTSManager(() => this.updateTTSButton());
|
|
2584
2692
|
}
|
|
2585
2693
|
async init() {
|
|
2586
|
-
injectCheckboxStyles();
|
|
2587
2694
|
this.unsubscribe = this.store.subscribe((state, prevState) => {
|
|
2588
2695
|
this.handleStateChange(state, prevState);
|
|
2589
2696
|
});
|
|
@@ -2597,18 +2704,22 @@ var ModalController = class {
|
|
|
2597
2704
|
(_b = this.keyboardCleanup) == null ? void 0 : _b.call(this);
|
|
2598
2705
|
(_c = this.unsubscribe) == null ? void 0 : _c.call(this);
|
|
2599
2706
|
this.mediaQuery.destroy();
|
|
2600
|
-
this.ttsManager.destroy();
|
|
2707
|
+
(_d = this.ttsManager) == null ? void 0 : _d.destroy();
|
|
2601
2708
|
this.stopPolling();
|
|
2602
2709
|
this.store.destroy();
|
|
2603
|
-
if (
|
|
2604
|
-
|
|
2710
|
+
if (this.hostEl && this.hostEl.parentNode) {
|
|
2711
|
+
this.hostEl.parentNode.removeChild(this.hostEl);
|
|
2605
2712
|
}
|
|
2606
|
-
if (this.
|
|
2607
|
-
document.body.
|
|
2713
|
+
if (this.previousBodyOverflow !== null) {
|
|
2714
|
+
document.body.style.overflow = this.previousBodyOverflow;
|
|
2715
|
+
this.previousBodyOverflow = null;
|
|
2608
2716
|
}
|
|
2609
|
-
if (this.
|
|
2610
|
-
document.
|
|
2717
|
+
if (this.previousHtmlOverflow !== null) {
|
|
2718
|
+
document.documentElement.style.overflow = this.previousHtmlOverflow;
|
|
2719
|
+
this.previousHtmlOverflow = null;
|
|
2611
2720
|
}
|
|
2721
|
+
this.hostEl = null;
|
|
2722
|
+
this.shadowRoot = null;
|
|
2612
2723
|
this.overlayEl = null;
|
|
2613
2724
|
this.modalEl = null;
|
|
2614
2725
|
this.purposeRefs = null;
|
|
@@ -2777,13 +2888,32 @@ var ModalController = class {
|
|
|
2777
2888
|
}
|
|
2778
2889
|
}
|
|
2779
2890
|
renderOverlayWithLoading() {
|
|
2891
|
+
this.hostEl = document.createElement("div");
|
|
2892
|
+
this.hostEl.setAttribute("data-redacto-consent", "");
|
|
2893
|
+
this.hostEl.style.position = "fixed";
|
|
2894
|
+
this.hostEl.style.top = "0";
|
|
2895
|
+
this.hostEl.style.left = "0";
|
|
2896
|
+
this.hostEl.style.width = "0";
|
|
2897
|
+
this.hostEl.style.height = "0";
|
|
2898
|
+
this.hostEl.style.zIndex = "2147483646";
|
|
2899
|
+
document.body.appendChild(this.hostEl);
|
|
2900
|
+
this.shadowRoot = this.hostEl.attachShadow({ mode: "open" });
|
|
2901
|
+
this.previousBodyOverflow = document.body.style.overflow;
|
|
2902
|
+
this.previousHtmlOverflow = document.documentElement.style.overflow;
|
|
2903
|
+
document.body.style.overflow = "hidden";
|
|
2904
|
+
document.documentElement.style.overflow = "hidden";
|
|
2905
|
+
injectCheckboxStyles(this.shadowRoot);
|
|
2906
|
+
this.ttsManager = new TTSManager(
|
|
2907
|
+
() => this.updateTTSButton(),
|
|
2908
|
+
this.shadowRoot
|
|
2909
|
+
);
|
|
2780
2910
|
const blockUI = this.options.blockUI !== false;
|
|
2781
2911
|
if (blockUI) {
|
|
2782
2912
|
this.overlayEl = el("div", {
|
|
2783
2913
|
style: styles.overlay,
|
|
2784
2914
|
role: "presentation"
|
|
2785
2915
|
});
|
|
2786
|
-
|
|
2916
|
+
this.shadowRoot.appendChild(this.overlayEl);
|
|
2787
2917
|
}
|
|
2788
2918
|
const settingsObj = this.options.settings;
|
|
2789
2919
|
const modalStyle = { ...styles.modal };
|
|
@@ -2809,10 +2939,10 @@ var ModalController = class {
|
|
|
2809
2939
|
);
|
|
2810
2940
|
const contentEl = el("div", { style: styles.content }, loadingEl);
|
|
2811
2941
|
this.modalEl.appendChild(contentEl);
|
|
2812
|
-
|
|
2942
|
+
this.shadowRoot.appendChild(this.modalEl);
|
|
2813
2943
|
}
|
|
2814
2944
|
rebuildUI() {
|
|
2815
|
-
var _a, _b, _c, _d, _e, _f, _g;
|
|
2945
|
+
var _a, _b, _c, _d, _e, _f, _g, _h;
|
|
2816
2946
|
const state = this.store.getState();
|
|
2817
2947
|
if (!state.content || !this.modalEl) return;
|
|
2818
2948
|
const activeConfig = state.content.detail.active_config;
|
|
@@ -2893,15 +3023,22 @@ var ModalController = class {
|
|
|
2893
3023
|
const textColor = colors.text;
|
|
2894
3024
|
const linkColor = colors.link;
|
|
2895
3025
|
const font = colors.font;
|
|
2896
|
-
const logoImg = activeConfig.logo_url ? el("img", {
|
|
3026
|
+
const logoImg = activeConfig.logo_url ? el("img", {
|
|
3027
|
+
src: activeConfig.logo_url,
|
|
3028
|
+
style: {
|
|
3029
|
+
...styles.logo,
|
|
3030
|
+
maxWidth: isMobile ? "96px" : "140px",
|
|
3031
|
+
maxHeight: isMobile ? "28px" : "32px"
|
|
3032
|
+
},
|
|
3033
|
+
alt: "Logo"
|
|
3034
|
+
}) : null;
|
|
2897
3035
|
this.noticeTitleEl = el("span", {
|
|
2898
3036
|
id: "privacy-notice-title",
|
|
2899
3037
|
style: { ...styles.title, color: headingColor, fontFamily: font, fontSize: isMobile ? "16px" : "18px" }
|
|
2900
3038
|
});
|
|
2901
3039
|
this.noticeTitleEl.textContent = this.getTranslatedText("notice_banner_heading", activeConfig.notice_banner_heading);
|
|
2902
|
-
|
|
2903
|
-
|
|
2904
|
-
document.body.removeChild(this.langSelectorRefs.dropdown);
|
|
3040
|
+
if (((_d = this.langSelectorRefs) == null ? void 0 : _d.dropdown) && this.shadowRoot && this.langSelectorRefs.dropdown.parentNode === this.shadowRoot) {
|
|
3041
|
+
this.shadowRoot.removeChild(this.langSelectorRefs.dropdown);
|
|
2905
3042
|
}
|
|
2906
3043
|
const supportedLangs = Object.keys(activeConfig.supported_languages_and_translations || {});
|
|
2907
3044
|
const allLanguages = [activeConfig.default_language || "English", ...supportedLangs.filter((l) => l !== activeConfig.default_language)];
|
|
@@ -2909,7 +3046,8 @@ var ModalController = class {
|
|
|
2909
3046
|
languages: allLanguages,
|
|
2910
3047
|
selectedLanguage: state.selectedLanguage,
|
|
2911
3048
|
settings: settingsObj,
|
|
2912
|
-
onSelect: (lang) => this.handleLanguageSelect(lang)
|
|
3049
|
+
onSelect: (lang) => this.handleLanguageSelect(lang),
|
|
3050
|
+
dropdownContainer: this.shadowRoot
|
|
2913
3051
|
});
|
|
2914
3052
|
const ttsStrokeColor = ((_f = (_e = settingsObj == null ? void 0 : settingsObj.button) == null ? void 0 : _e.language) == null ? void 0 : _f.textColor) || "currentColor";
|
|
2915
3053
|
const speakerSvg = svg(
|
|
@@ -2940,10 +3078,13 @@ var ModalController = class {
|
|
|
2940
3078
|
type: "button",
|
|
2941
3079
|
"aria-label": "Start audio playback",
|
|
2942
3080
|
title: "Start Talkback",
|
|
2943
|
-
onClick: () =>
|
|
3081
|
+
onClick: () => {
|
|
3082
|
+
var _a2;
|
|
3083
|
+
return (_a2 = this.ttsManager) == null ? void 0 : _a2.toggle();
|
|
3084
|
+
}
|
|
2944
3085
|
});
|
|
2945
3086
|
this.ttsButton.appendChild(speakerSvg);
|
|
2946
|
-
this.ttsManager.fetchAudioUrls({
|
|
3087
|
+
(_g = this.ttsManager) == null ? void 0 : _g.fetchAudioUrls({
|
|
2947
3088
|
accessToken: this.options.accessToken,
|
|
2948
3089
|
baseUrl: this.options.baseUrl,
|
|
2949
3090
|
noticeUuid: activeConfig.notice_uuid,
|
|
@@ -2951,9 +3092,44 @@ var ModalController = class {
|
|
|
2951
3092
|
content: activeConfig
|
|
2952
3093
|
});
|
|
2953
3094
|
const topRight = el("div", {
|
|
2954
|
-
style: { display: "flex", alignItems: "center", gap: "8px" }
|
|
3095
|
+
style: { display: "flex", alignItems: "center", gap: "8px", flexShrink: 0 }
|
|
2955
3096
|
}, this.ttsButton, this.langSelectorRefs.container);
|
|
2956
|
-
|
|
3097
|
+
let topSection;
|
|
3098
|
+
if (isMobile) {
|
|
3099
|
+
const headerRow = el(
|
|
3100
|
+
"div",
|
|
3101
|
+
{
|
|
3102
|
+
style: {
|
|
3103
|
+
display: "flex",
|
|
3104
|
+
alignItems: "center",
|
|
3105
|
+
gap: "10px",
|
|
3106
|
+
width: "100%"
|
|
3107
|
+
}
|
|
3108
|
+
},
|
|
3109
|
+
...logoImg ? [logoImg] : [],
|
|
3110
|
+
el(
|
|
3111
|
+
"div",
|
|
3112
|
+
{ style: { marginLeft: "auto", display: "flex", alignItems: "center" } },
|
|
3113
|
+
topRight
|
|
3114
|
+
)
|
|
3115
|
+
);
|
|
3116
|
+
topSection = el(
|
|
3117
|
+
"div",
|
|
3118
|
+
{
|
|
3119
|
+
style: {
|
|
3120
|
+
...styles.topSection,
|
|
3121
|
+
flexDirection: "column",
|
|
3122
|
+
alignItems: "stretch",
|
|
3123
|
+
flexWrap: "nowrap"
|
|
3124
|
+
}
|
|
3125
|
+
},
|
|
3126
|
+
headerRow,
|
|
3127
|
+
this.noticeTitleEl
|
|
3128
|
+
);
|
|
3129
|
+
} else {
|
|
3130
|
+
const topLeft = el("div", { style: styles.topLeft }, logoImg, this.noticeTitleEl);
|
|
3131
|
+
topSection = el("div", { style: styles.topSection }, topLeft, topRight);
|
|
3132
|
+
}
|
|
2957
3133
|
this.middleSection = el("div", { style: styles.middleSection });
|
|
2958
3134
|
const baseTextStyle = { ...styles.privacyText, color: textColor, fontFamily: font, fontSize: isMobile ? "14px" : "16px" };
|
|
2959
3135
|
const noticeTextSpan = el("span", { id: "privacy-notice-text" });
|
|
@@ -3198,7 +3374,7 @@ var ModalController = class {
|
|
|
3198
3374
|
);
|
|
3199
3375
|
this.modalEl.appendChild(contentWrapper);
|
|
3200
3376
|
this.updateAcceptButtonState(state);
|
|
3201
|
-
(
|
|
3377
|
+
(_h = this.keyboardCleanup) == null ? void 0 : _h.call(this);
|
|
3202
3378
|
this.keyboardCleanup = setupKeyboardTrap(this.modalEl, () => this.handleDecline());
|
|
3203
3379
|
}
|
|
3204
3380
|
getLanguageCode(displayLanguage) {
|
|
@@ -3756,54 +3932,56 @@ var ModalController = class {
|
|
|
3756
3932
|
// ─── TTS ───
|
|
3757
3933
|
updateTTSButton() {
|
|
3758
3934
|
var _a, _b, _c;
|
|
3759
|
-
if (!this.ttsButton) return;
|
|
3760
|
-
if (this.ttsManager.isAvailable) {
|
|
3761
|
-
this.ttsButton.style.display = "
|
|
3762
|
-
|
|
3763
|
-
|
|
3764
|
-
|
|
3765
|
-
|
|
3766
|
-
|
|
3767
|
-
|
|
3768
|
-
|
|
3769
|
-
|
|
3770
|
-
|
|
3771
|
-
|
|
3772
|
-
|
|
3773
|
-
|
|
3774
|
-
|
|
3775
|
-
|
|
3776
|
-
|
|
3777
|
-
|
|
3778
|
-
|
|
3779
|
-
|
|
3780
|
-
|
|
3781
|
-
|
|
3782
|
-
|
|
3783
|
-
|
|
3784
|
-
|
|
3785
|
-
|
|
3786
|
-
|
|
3787
|
-
|
|
3788
|
-
|
|
3789
|
-
|
|
3790
|
-
|
|
3791
|
-
|
|
3792
|
-
|
|
3793
|
-
|
|
3794
|
-
|
|
3795
|
-
|
|
3796
|
-
|
|
3797
|
-
|
|
3798
|
-
|
|
3799
|
-
|
|
3800
|
-
|
|
3801
|
-
|
|
3802
|
-
|
|
3803
|
-
|
|
3804
|
-
|
|
3805
|
-
|
|
3806
|
-
|
|
3935
|
+
if (!this.ttsButton || !this.ttsManager) return;
|
|
3936
|
+
if (!this.ttsManager.isAvailable) {
|
|
3937
|
+
this.ttsButton.style.display = "none";
|
|
3938
|
+
return;
|
|
3939
|
+
}
|
|
3940
|
+
this.ttsButton.style.display = "flex";
|
|
3941
|
+
clearElement(this.ttsButton);
|
|
3942
|
+
const strokeColor = ((_c = (_b = (_a = this.options.settings) == null ? void 0 : _a.button) == null ? void 0 : _b.language) == null ? void 0 : _c.textColor) || "currentColor";
|
|
3943
|
+
if (this.ttsManager.isPlaying) {
|
|
3944
|
+
const pauseSvg = svg(
|
|
3945
|
+
"svg",
|
|
3946
|
+
{
|
|
3947
|
+
xmlns: "http://www.w3.org/2000/svg",
|
|
3948
|
+
width: "16",
|
|
3949
|
+
height: "16",
|
|
3950
|
+
viewBox: "0 0 24 24",
|
|
3951
|
+
fill: "none",
|
|
3952
|
+
stroke: strokeColor,
|
|
3953
|
+
"stroke-width": "2",
|
|
3954
|
+
"stroke-linecap": "round",
|
|
3955
|
+
"stroke-linejoin": "round",
|
|
3956
|
+
"aria-hidden": "true"
|
|
3957
|
+
},
|
|
3958
|
+
svg("rect", { x: "6", y: "4", width: "4", height: "16" }),
|
|
3959
|
+
svg("rect", { x: "14", y: "4", width: "4", height: "16" })
|
|
3960
|
+
);
|
|
3961
|
+
this.ttsButton.appendChild(pauseSvg);
|
|
3962
|
+
this.ttsButton.setAttribute("aria-label", "Pause audio playback");
|
|
3963
|
+
this.ttsButton.setAttribute("title", "Pause Talkback");
|
|
3964
|
+
} else {
|
|
3965
|
+
const speakerSvg = svg(
|
|
3966
|
+
"svg",
|
|
3967
|
+
{
|
|
3968
|
+
xmlns: "http://www.w3.org/2000/svg",
|
|
3969
|
+
width: "16",
|
|
3970
|
+
height: "16",
|
|
3971
|
+
viewBox: "0 0 24 24",
|
|
3972
|
+
fill: "none",
|
|
3973
|
+
stroke: strokeColor,
|
|
3974
|
+
"stroke-width": "2",
|
|
3975
|
+
"stroke-linecap": "round",
|
|
3976
|
+
"stroke-linejoin": "round",
|
|
3977
|
+
"aria-hidden": "true"
|
|
3978
|
+
},
|
|
3979
|
+
svg("polygon", { points: "11 5 6 9 2 9 2 15 6 15 11 19 11 5" }),
|
|
3980
|
+
svg("path", { d: "M19.07 4.93a10 10 0 0 1 0 14.14M15.54 8.46a5 5 0 0 1 0 7.07" })
|
|
3981
|
+
);
|
|
3982
|
+
this.ttsButton.appendChild(speakerSvg);
|
|
3983
|
+
this.ttsButton.setAttribute("aria-label", this.ttsManager.isPaused ? "Resume audio playback" : "Start audio playback");
|
|
3984
|
+
this.ttsButton.setAttribute("title", this.ttsManager.isPaused ? "Resume Talkback" : "Start Talkback");
|
|
3807
3985
|
}
|
|
3808
3986
|
}
|
|
3809
3987
|
updateButtonStates(state) {
|
|
@@ -4123,6 +4301,8 @@ function renderInlinePurposes(purposes, options) {
|
|
|
4123
4301
|
var InlineController = class {
|
|
4124
4302
|
constructor(options) {
|
|
4125
4303
|
this.targetEl = null;
|
|
4304
|
+
this.hostEl = null;
|
|
4305
|
+
this.shadowRoot = null;
|
|
4126
4306
|
this.rootEl = null;
|
|
4127
4307
|
this.purposeRefs = null;
|
|
4128
4308
|
this.errorEl = null;
|
|
@@ -4144,7 +4324,6 @@ var InlineController = class {
|
|
|
4144
4324
|
this.mediaQuery = createMediaQuery("(max-width: 768px)");
|
|
4145
4325
|
}
|
|
4146
4326
|
async init() {
|
|
4147
|
-
injectCheckboxStyles();
|
|
4148
4327
|
if (typeof this.options.target === "string") {
|
|
4149
4328
|
this.targetEl = document.querySelector(this.options.target);
|
|
4150
4329
|
if (!this.targetEl) {
|
|
@@ -4153,6 +4332,12 @@ var InlineController = class {
|
|
|
4153
4332
|
} else {
|
|
4154
4333
|
this.targetEl = this.options.target;
|
|
4155
4334
|
}
|
|
4335
|
+
this.hostEl = document.createElement("div");
|
|
4336
|
+
this.hostEl.setAttribute("data-redacto-consent-inline", "");
|
|
4337
|
+
this.hostEl.style.display = "block";
|
|
4338
|
+
this.targetEl.appendChild(this.hostEl);
|
|
4339
|
+
this.shadowRoot = this.hostEl.attachShadow({ mode: "open" });
|
|
4340
|
+
injectCheckboxStyles(this.shadowRoot);
|
|
4156
4341
|
this.unsubscribe = this.store.subscribe((state, prevState) => {
|
|
4157
4342
|
this.handleStateChange(state, prevState);
|
|
4158
4343
|
});
|
|
@@ -4165,9 +4350,11 @@ var InlineController = class {
|
|
|
4165
4350
|
(_a = this.unsubscribe) == null ? void 0 : _a.call(this);
|
|
4166
4351
|
this.mediaQuery.destroy();
|
|
4167
4352
|
this.store.destroy();
|
|
4168
|
-
if (this.
|
|
4169
|
-
this.
|
|
4353
|
+
if (this.hostEl && this.hostEl.parentNode) {
|
|
4354
|
+
this.hostEl.parentNode.removeChild(this.hostEl);
|
|
4170
4355
|
}
|
|
4356
|
+
this.hostEl = null;
|
|
4357
|
+
this.shadowRoot = null;
|
|
4171
4358
|
this.rootEl = null;
|
|
4172
4359
|
this.purposeRefs = null;
|
|
4173
4360
|
}
|
|
@@ -4223,8 +4410,8 @@ var InlineController = class {
|
|
|
4223
4410
|
this.rebuildUI();
|
|
4224
4411
|
}
|
|
4225
4412
|
if (state.hasAlreadyConsented || state.fetchError) {
|
|
4226
|
-
if (this.rootEl && this.
|
|
4227
|
-
this.
|
|
4413
|
+
if (this.rootEl && this.shadowRoot && this.rootEl.parentNode === this.shadowRoot) {
|
|
4414
|
+
this.shadowRoot.removeChild(this.rootEl);
|
|
4228
4415
|
this.rootEl = null;
|
|
4229
4416
|
}
|
|
4230
4417
|
return;
|
|
@@ -4243,7 +4430,7 @@ var InlineController = class {
|
|
|
4243
4430
|
}
|
|
4244
4431
|
renderLoading() {
|
|
4245
4432
|
var _a;
|
|
4246
|
-
if (!this.
|
|
4433
|
+
if (!this.shadowRoot) return;
|
|
4247
4434
|
const textColor = ((_a = this.options.settings) == null ? void 0 : _a.textColor) || "#344054";
|
|
4248
4435
|
this.rootEl = el(
|
|
4249
4436
|
"div",
|
|
@@ -4251,13 +4438,13 @@ var InlineController = class {
|
|
|
4251
4438
|
el("div", { style: inlineStyles.loadingSpinner }),
|
|
4252
4439
|
el("p", { style: { fontSize: "16px", fontWeight: 400, color: textColor } }, "Loading...")
|
|
4253
4440
|
);
|
|
4254
|
-
this.
|
|
4441
|
+
this.shadowRoot.appendChild(this.rootEl);
|
|
4255
4442
|
}
|
|
4256
4443
|
rebuildUI() {
|
|
4257
4444
|
const state = this.store.getState();
|
|
4258
|
-
if (!state.content || !this.
|
|
4259
|
-
if (this.rootEl && this.
|
|
4260
|
-
this.
|
|
4445
|
+
if (!state.content || !this.shadowRoot) return;
|
|
4446
|
+
if (this.rootEl && this.rootEl.parentNode === this.shadowRoot) {
|
|
4447
|
+
this.shadowRoot.removeChild(this.rootEl);
|
|
4261
4448
|
}
|
|
4262
4449
|
this.errorEl = el("div", {
|
|
4263
4450
|
role: "alert",
|
|
@@ -4291,7 +4478,7 @@ var InlineController = class {
|
|
|
4291
4478
|
this.errorEl,
|
|
4292
4479
|
this.purposeRefs.container
|
|
4293
4480
|
);
|
|
4294
|
-
this.
|
|
4481
|
+
this.shadowRoot.appendChild(this.rootEl);
|
|
4295
4482
|
this.notifyValidation(state);
|
|
4296
4483
|
}
|
|
4297
4484
|
getTranslatedText(key, defaultText, itemId) {
|
|
@@ -4518,7 +4705,7 @@ function getErrorMessage(errorCode) {
|
|
|
4518
4705
|
}
|
|
4519
4706
|
function handleDigilockerCallback(options) {
|
|
4520
4707
|
var _a, _b, _c;
|
|
4521
|
-
injectCheckboxStyles();
|
|
4708
|
+
injectCheckboxStyles(document);
|
|
4522
4709
|
const params = new URLSearchParams(window.location.search);
|
|
4523
4710
|
const sessionToken = params.get("session_token");
|
|
4524
4711
|
const urlStatus = params.get("status");
|