@product7/feedback-sdk 1.4.4 → 1.4.7
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 +4 -7
- package/dist/README.md +4 -7
- package/dist/feedback-sdk.js +94 -69
- package/dist/feedback-sdk.js.map +1 -1
- package/dist/feedback-sdk.min.js +1 -1
- package/dist/feedback-sdk.min.js.map +1 -1
- package/package.json +1 -1
- package/src/docs/framework-integrations.md +707 -0
- package/src/styles/feedback.js +6 -1
- package/src/widgets/ButtonWidget.js +21 -9
- package/src/widgets/ChangelogWidget.js +52 -51
- package/src/widgets/MessengerWidget.js +16 -9
- package/src/widgets/messenger/MessengerState.js +1 -1
- package/src/widgets/messenger/views/ChangelogView.js +1 -1
- package/src/widgets/messenger/views/HelpView.js +1 -1
- package/src/widgets/messenger/views/HomeView.js +1 -1
package/README.md
CHANGED
|
@@ -86,13 +86,10 @@ widget.mount();
|
|
|
86
86
|
|
|
87
87
|
## Documentation
|
|
88
88
|
|
|
89
|
-
- [Installation Guide](docs/installation.md)
|
|
90
|
-
- [
|
|
91
|
-
- [
|
|
92
|
-
- [
|
|
93
|
-
- [Theming Guide](docs/theming.md)
|
|
94
|
-
- [Examples](docs/examples.md)
|
|
95
|
-
- [Migration Guide](docs/migration.md)
|
|
89
|
+
- [Installation Guide](src/docs/installation.md)
|
|
90
|
+
- [Framework Integrations](src/docs/framework-integrations.md)
|
|
91
|
+
- [API Reference](src/docs/api.md)
|
|
92
|
+
- [Examples](src/docs/example.md)
|
|
96
93
|
|
|
97
94
|
---
|
|
98
95
|
|
package/dist/README.md
CHANGED
|
@@ -86,13 +86,10 @@ widget.mount();
|
|
|
86
86
|
|
|
87
87
|
## Documentation
|
|
88
88
|
|
|
89
|
-
- [Installation Guide](docs/installation.md)
|
|
90
|
-
- [
|
|
91
|
-
- [
|
|
92
|
-
- [
|
|
93
|
-
- [Theming Guide](docs/theming.md)
|
|
94
|
-
- [Examples](docs/examples.md)
|
|
95
|
-
- [Migration Guide](docs/migration.md)
|
|
89
|
+
- [Installation Guide](src/docs/installation.md)
|
|
90
|
+
- [Framework Integrations](src/docs/framework-integrations.md)
|
|
91
|
+
- [API Reference](src/docs/api.md)
|
|
92
|
+
- [Examples](src/docs/example.md)
|
|
96
93
|
|
|
97
94
|
---
|
|
98
95
|
|
package/dist/feedback-sdk.js
CHANGED
|
@@ -2202,6 +2202,21 @@
|
|
|
2202
2202
|
const button = this.element.querySelector('.feedback-trigger-btn');
|
|
2203
2203
|
const minimizeIcon = this.element.querySelector('.feedback-minimize-icon');
|
|
2204
2204
|
const expandIcon = this.element.querySelector('.feedback-expand-icon');
|
|
2205
|
+
const isControlIcon = (target) => {
|
|
2206
|
+
if (!(target instanceof Element)) return false;
|
|
2207
|
+
return Boolean(
|
|
2208
|
+
target.closest('.feedback-minimize-icon') ||
|
|
2209
|
+
target.closest('.feedback-expand-icon')
|
|
2210
|
+
);
|
|
2211
|
+
};
|
|
2212
|
+
const openIfAllowed = (target) => {
|
|
2213
|
+
if (isControlIcon(target)) {
|
|
2214
|
+
return;
|
|
2215
|
+
}
|
|
2216
|
+
if (!this.isMinimized) {
|
|
2217
|
+
this.openPanel();
|
|
2218
|
+
}
|
|
2219
|
+
};
|
|
2205
2220
|
|
|
2206
2221
|
minimizeIcon.addEventListener('click', (e) => {
|
|
2207
2222
|
e.stopPropagation();
|
|
@@ -2216,16 +2231,13 @@
|
|
|
2216
2231
|
});
|
|
2217
2232
|
|
|
2218
2233
|
button.addEventListener('click', (e) => {
|
|
2219
|
-
|
|
2220
|
-
|
|
2221
|
-
e.target.closest('.feedback-expand-icon')
|
|
2222
|
-
) {
|
|
2223
|
-
return;
|
|
2224
|
-
}
|
|
2234
|
+
openIfAllowed(e.target);
|
|
2235
|
+
});
|
|
2225
2236
|
|
|
2226
|
-
|
|
2227
|
-
|
|
2228
|
-
|
|
2237
|
+
// Pointer events improve consistency across touch and mouse devices.
|
|
2238
|
+
button.addEventListener('pointerup', (e) => {
|
|
2239
|
+
if (e.pointerType === 'mouse') return;
|
|
2240
|
+
openIfAllowed(e.target);
|
|
2229
2241
|
});
|
|
2230
2242
|
}
|
|
2231
2243
|
|
|
@@ -2370,18 +2382,14 @@
|
|
|
2370
2382
|
|
|
2371
2383
|
this.modalElement
|
|
2372
2384
|
.querySelector('.changelog-modal-container')
|
|
2373
|
-
.addEventListener('click', (e) =>
|
|
2374
|
-
e.stopPropagation();
|
|
2375
|
-
});
|
|
2385
|
+
.addEventListener('click', (e) => e.stopPropagation());
|
|
2376
2386
|
|
|
2377
2387
|
this.modalElement
|
|
2378
2388
|
.querySelector('.changelog-modal-close')
|
|
2379
2389
|
.addEventListener('click', () => this.closeModal());
|
|
2380
2390
|
|
|
2381
2391
|
this._escapeHandler = (e) => {
|
|
2382
|
-
if (e.key === 'Escape')
|
|
2383
|
-
this.closeModal();
|
|
2384
|
-
}
|
|
2392
|
+
if (e.key === 'Escape') this.closeModal();
|
|
2385
2393
|
};
|
|
2386
2394
|
document.addEventListener('keydown', this._escapeHandler);
|
|
2387
2395
|
}
|
|
@@ -2459,9 +2467,7 @@
|
|
|
2459
2467
|
}
|
|
2460
2468
|
|
|
2461
2469
|
setTimeout(() => {
|
|
2462
|
-
if (container.parentNode)
|
|
2463
|
-
container.parentNode.removeChild(container);
|
|
2464
|
-
}
|
|
2470
|
+
if (container.parentNode) container.parentNode.removeChild(container);
|
|
2465
2471
|
}, 2500);
|
|
2466
2472
|
}
|
|
2467
2473
|
|
|
@@ -2524,18 +2530,14 @@
|
|
|
2524
2530
|
|
|
2525
2531
|
this.listModalElement
|
|
2526
2532
|
.querySelector('.changelog-list-modal-container')
|
|
2527
|
-
.addEventListener('click', (e) =>
|
|
2528
|
-
e.stopPropagation();
|
|
2529
|
-
});
|
|
2533
|
+
.addEventListener('click', (e) => e.stopPropagation());
|
|
2530
2534
|
|
|
2531
2535
|
this.listModalElement
|
|
2532
2536
|
.querySelector('.changelog-list-modal-close')
|
|
2533
2537
|
.addEventListener('click', () => this.closeSidebar());
|
|
2534
2538
|
|
|
2535
2539
|
this._listModalEscapeHandler = (e) => {
|
|
2536
|
-
if (e.key === 'Escape')
|
|
2537
|
-
this.closeSidebar();
|
|
2538
|
-
}
|
|
2540
|
+
if (e.key === 'Escape') this.closeSidebar();
|
|
2539
2541
|
};
|
|
2540
2542
|
document.addEventListener('keydown', this._listModalEscapeHandler);
|
|
2541
2543
|
}
|
|
@@ -2545,9 +2547,7 @@
|
|
|
2545
2547
|
'.changelog-list-modal-body'
|
|
2546
2548
|
);
|
|
2547
2549
|
|
|
2548
|
-
if (this.isLoading)
|
|
2549
|
-
return;
|
|
2550
|
-
}
|
|
2550
|
+
if (this.isLoading) return;
|
|
2551
2551
|
|
|
2552
2552
|
if (this.changelogs.length === 0) {
|
|
2553
2553
|
body.innerHTML = `
|
|
@@ -2570,8 +2570,7 @@
|
|
|
2570
2570
|
|
|
2571
2571
|
body.querySelectorAll('.changelog-list-item').forEach((item, index) => {
|
|
2572
2572
|
item.addEventListener('click', () => {
|
|
2573
|
-
|
|
2574
|
-
this._handleViewUpdate(changelog);
|
|
2573
|
+
this._handleViewUpdate(this.changelogs[index]);
|
|
2575
2574
|
});
|
|
2576
2575
|
});
|
|
2577
2576
|
}
|
|
@@ -2582,6 +2581,10 @@
|
|
|
2582
2581
|
const date = changelog.published_at
|
|
2583
2582
|
? this._formatDate(changelog.published_at)
|
|
2584
2583
|
: '';
|
|
2584
|
+
const description = this._truncateDescription(
|
|
2585
|
+
changelog.excerpt || changelog.description,
|
|
2586
|
+
120
|
|
2587
|
+
);
|
|
2585
2588
|
|
|
2586
2589
|
return `
|
|
2587
2590
|
<div class="changelog-list-item" data-index="${index}">
|
|
@@ -2613,13 +2616,7 @@
|
|
|
2613
2616
|
: ''
|
|
2614
2617
|
}
|
|
2615
2618
|
<h3 class="changelog-list-item-title">${changelog.title}</h3>
|
|
2616
|
-
${
|
|
2617
|
-
changelog.excerpt || changelog.description
|
|
2618
|
-
? `
|
|
2619
|
-
<p class="changelog-list-item-description">${changelog.excerpt || changelog.description}</p>
|
|
2620
|
-
`
|
|
2621
|
-
: ''
|
|
2622
|
-
}
|
|
2619
|
+
${description ? `<p class="changelog-list-item-description">${description}</p>` : ''}
|
|
2623
2620
|
</div>
|
|
2624
2621
|
</div>
|
|
2625
2622
|
</div>
|
|
@@ -2646,9 +2643,7 @@
|
|
|
2646
2643
|
_renderCurrentChangelog() {
|
|
2647
2644
|
const content = this.modalElement.querySelector('.changelog-modal-content');
|
|
2648
2645
|
|
|
2649
|
-
if (this.isLoading)
|
|
2650
|
-
return;
|
|
2651
|
-
}
|
|
2646
|
+
if (this.isLoading) return;
|
|
2652
2647
|
|
|
2653
2648
|
if (this.changelogs.length === 0) {
|
|
2654
2649
|
content.innerHTML = `
|
|
@@ -2667,6 +2662,10 @@
|
|
|
2667
2662
|
const hasImage = changelog.cover_image || changelog.image;
|
|
2668
2663
|
const imageUrl = changelog.cover_image || changelog.image;
|
|
2669
2664
|
const hasMultiple = this.changelogs.length > 1;
|
|
2665
|
+
const description = this._truncateDescription(
|
|
2666
|
+
changelog.excerpt || changelog.description,
|
|
2667
|
+
160
|
|
2668
|
+
);
|
|
2670
2669
|
|
|
2671
2670
|
content.innerHTML = `
|
|
2672
2671
|
<div class="changelog-popup-item">
|
|
@@ -2681,13 +2680,7 @@
|
|
|
2681
2680
|
}
|
|
2682
2681
|
<div class="changelog-popup-body">
|
|
2683
2682
|
<h2 class="changelog-popup-title">${changelog.title}</h2>
|
|
2684
|
-
${
|
|
2685
|
-
changelog.excerpt || changelog.description
|
|
2686
|
-
? `
|
|
2687
|
-
<p class="changelog-popup-description">${changelog.excerpt || changelog.description}</p>
|
|
2688
|
-
`
|
|
2689
|
-
: ''
|
|
2690
|
-
}
|
|
2683
|
+
${description ? `<p class="changelog-popup-description">${description}</p>` : ''}
|
|
2691
2684
|
<button class="changelog-popup-btn" type="button">
|
|
2692
2685
|
${this.options.viewButtonText || 'View Update'}
|
|
2693
2686
|
</button>
|
|
@@ -2734,8 +2727,7 @@
|
|
|
2734
2727
|
if (hasMultiple) {
|
|
2735
2728
|
content.querySelectorAll('.changelog-dot').forEach((dot) => {
|
|
2736
2729
|
dot.addEventListener('click', (e) => {
|
|
2737
|
-
|
|
2738
|
-
this.currentIndex = index;
|
|
2730
|
+
this.currentIndex = parseInt(e.target.dataset.index, 10);
|
|
2739
2731
|
this._renderCurrentChangelog();
|
|
2740
2732
|
});
|
|
2741
2733
|
});
|
|
@@ -2745,10 +2737,19 @@
|
|
|
2745
2737
|
_handleViewUpdate(changelog) {
|
|
2746
2738
|
this.sdk.eventBus.emit('changelog:view', { changelog });
|
|
2747
2739
|
|
|
2748
|
-
|
|
2749
|
-
|
|
2750
|
-
|
|
2751
|
-
|
|
2740
|
+
const changelogBase = (this.options.changelogBaseUrl || '').replace(
|
|
2741
|
+
/\/$/,
|
|
2742
|
+
''
|
|
2743
|
+
);
|
|
2744
|
+
const url =
|
|
2745
|
+
changelog.url ||
|
|
2746
|
+
(changelog.slug && changelogBase
|
|
2747
|
+
? `${changelogBase}/${changelog.slug}`
|
|
2748
|
+
: null) ||
|
|
2749
|
+
changelogBase ||
|
|
2750
|
+
null;
|
|
2751
|
+
|
|
2752
|
+
if (url) {
|
|
2752
2753
|
if (this.options.openInNewTab !== false) {
|
|
2753
2754
|
window.open(url, '_blank', 'noopener,noreferrer');
|
|
2754
2755
|
} else {
|
|
@@ -2761,10 +2762,26 @@
|
|
|
2761
2762
|
}
|
|
2762
2763
|
}
|
|
2763
2764
|
|
|
2765
|
+
_stripHtml(html) {
|
|
2766
|
+
const tmp = document.createElement('div');
|
|
2767
|
+
tmp.innerHTML = html;
|
|
2768
|
+
return (tmp.textContent || tmp.innerText || '').trim();
|
|
2769
|
+
}
|
|
2770
|
+
|
|
2771
|
+
_truncateDescription(html, maxLength = 120) {
|
|
2772
|
+
if (!html) return '';
|
|
2773
|
+
const plain = this._stripHtml(html);
|
|
2774
|
+
if (plain.length <= maxLength) return plain;
|
|
2775
|
+
return plain.substring(0, maxLength).trimEnd() + '...';
|
|
2776
|
+
}
|
|
2777
|
+
|
|
2764
2778
|
_formatDate(dateString) {
|
|
2765
2779
|
const date = new Date(dateString);
|
|
2766
|
-
|
|
2767
|
-
|
|
2780
|
+
return date.toLocaleDateString('en-US', {
|
|
2781
|
+
year: 'numeric',
|
|
2782
|
+
month: 'short',
|
|
2783
|
+
day: 'numeric',
|
|
2784
|
+
});
|
|
2768
2785
|
}
|
|
2769
2786
|
|
|
2770
2787
|
_getContrastColor(hexColor) {
|
|
@@ -2778,16 +2795,12 @@
|
|
|
2778
2795
|
|
|
2779
2796
|
hideBadge() {
|
|
2780
2797
|
const badge = this.element?.querySelector('.changelog-badge');
|
|
2781
|
-
if (badge)
|
|
2782
|
-
badge.style.display = 'none';
|
|
2783
|
-
}
|
|
2798
|
+
if (badge) badge.style.display = 'none';
|
|
2784
2799
|
}
|
|
2785
2800
|
|
|
2786
2801
|
showBadge() {
|
|
2787
2802
|
const badge = this.element?.querySelector('.changelog-badge');
|
|
2788
|
-
if (badge)
|
|
2789
|
-
badge.style.display = 'block';
|
|
2790
|
-
}
|
|
2803
|
+
if (badge) badge.style.display = 'block';
|
|
2791
2804
|
}
|
|
2792
2805
|
|
|
2793
2806
|
nextChangelog() {
|
|
@@ -6234,16 +6247,20 @@
|
|
|
6234
6247
|
const response = await this.apiService.getHelpCollections();
|
|
6235
6248
|
if (response.success && response.data) {
|
|
6236
6249
|
const collections = response.data.collections || response.data;
|
|
6237
|
-
const helpBase = (this.messengerOptions.helpUrl || '').replace(
|
|
6250
|
+
const helpBase = (this.messengerOptions.helpUrl || '').replace(
|
|
6251
|
+
/\/$/,
|
|
6252
|
+
''
|
|
6253
|
+
);
|
|
6238
6254
|
|
|
6239
6255
|
return collections.map((collection) => ({
|
|
6240
6256
|
id: collection.id,
|
|
6241
6257
|
title: collection.title,
|
|
6242
6258
|
description: collection.description || '',
|
|
6243
6259
|
articleCount: collection.article_count || 0,
|
|
6244
|
-
url:
|
|
6245
|
-
|
|
6246
|
-
|
|
6260
|
+
url:
|
|
6261
|
+
collection.url_slug && helpBase
|
|
6262
|
+
? `${helpBase}/collections/${collection.url_slug}`
|
|
6263
|
+
: helpBase || null,
|
|
6247
6264
|
}));
|
|
6248
6265
|
}
|
|
6249
6266
|
return [];
|
|
@@ -6456,7 +6473,9 @@
|
|
|
6456
6473
|
|
|
6457
6474
|
if (response.success && response.data) {
|
|
6458
6475
|
const changelogs = Array.isArray(response.data) ? response.data : [];
|
|
6459
|
-
const changelogBase = (
|
|
6476
|
+
const changelogBase = (
|
|
6477
|
+
this.messengerOptions.changelogUrl || ''
|
|
6478
|
+
).replace(/\/$/, '');
|
|
6460
6479
|
|
|
6461
6480
|
const mappedItems = changelogs.map((item) => ({
|
|
6462
6481
|
id: item.id,
|
|
@@ -6465,9 +6484,10 @@
|
|
|
6465
6484
|
tags: item.labels ? item.labels.map((label) => label.name) : [],
|
|
6466
6485
|
coverImage: item.cover_image || null,
|
|
6467
6486
|
publishedAt: item.published_at,
|
|
6468
|
-
url:
|
|
6469
|
-
|
|
6470
|
-
|
|
6487
|
+
url:
|
|
6488
|
+
item.slug && changelogBase
|
|
6489
|
+
? `${changelogBase}/${item.slug}`
|
|
6490
|
+
: changelogBase || null,
|
|
6471
6491
|
}));
|
|
6472
6492
|
|
|
6473
6493
|
return {
|
|
@@ -8854,7 +8874,7 @@
|
|
|
8854
8874
|
const feedbackStyles = `
|
|
8855
8875
|
.feedback-widget-button {
|
|
8856
8876
|
position: fixed;
|
|
8857
|
-
z-index: var(--z-
|
|
8877
|
+
z-index: var(--z-notification);
|
|
8858
8878
|
}
|
|
8859
8879
|
|
|
8860
8880
|
.feedback-widget-button.position-bottom-right {
|
|
@@ -8896,6 +8916,8 @@
|
|
|
8896
8916
|
background: var(--color-primary);
|
|
8897
8917
|
box-shadow: var(--shadow-md);
|
|
8898
8918
|
width: fit-content;
|
|
8919
|
+
touch-action: manipulation;
|
|
8920
|
+
-webkit-tap-highlight-color: transparent;
|
|
8899
8921
|
}
|
|
8900
8922
|
|
|
8901
8923
|
.feedback-trigger-btn:hover:not(:disabled) {
|
|
@@ -8934,6 +8956,7 @@
|
|
|
8934
8956
|
transition: opacity var(--transition-base);
|
|
8935
8957
|
box-shadow: var(--shadow-sm);
|
|
8936
8958
|
cursor: pointer;
|
|
8959
|
+
pointer-events: none;
|
|
8937
8960
|
}
|
|
8938
8961
|
|
|
8939
8962
|
.feedback-minimize-icon svg,
|
|
@@ -8946,6 +8969,7 @@
|
|
|
8946
8969
|
|
|
8947
8970
|
.feedback-widget-button:not(.minimized) .feedback-trigger-btn:hover .feedback-minimize-icon {
|
|
8948
8971
|
opacity: 1;
|
|
8972
|
+
pointer-events: auto;
|
|
8949
8973
|
}
|
|
8950
8974
|
|
|
8951
8975
|
.feedback-widget-button.minimized .feedback-trigger-btn {
|
|
@@ -8965,6 +8989,7 @@
|
|
|
8965
8989
|
|
|
8966
8990
|
.feedback-widget-button.minimized .feedback-trigger-btn:hover .feedback-expand-icon {
|
|
8967
8991
|
opacity: 1;
|
|
8992
|
+
pointer-events: auto;
|
|
8968
8993
|
}
|
|
8969
8994
|
|
|
8970
8995
|
.feedback-panel {
|