feat(widget): Widget 配置、loader 与右下角悬浮入口

生成可嵌入站点的 loader 与悬浮按钮,支持展开收起和移动端;附独立宿主测试页。
This commit is contained in:
WangShen007 committed 2026-09-25 20:50:00 +08:00
1 parent e24d3e2a65
commit 5d0a48505a
57 files changed
+32086

No files matched your search

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.8 KiB

@@ -0,0 +1,4 @@
<svg width="120" height="120" viewBox="0 0 120 120" fill="none" xmlns="http://www.w3.org/2000/svg">
<circle cx="60" cy="60" r="60" fill="#FFF3E0"/>
<path d="M60 36C48.95 36 40 44.95 40 56C40 67.05 48.95 76 60 76C71.05 76 80 67.05 80 56C80 44.95 71.05 36 60 36ZM60 44C64.42 44 68 47.58 68 52C68 56.42 64.42 60 60 60C55.58 60 52 56.42 52 52C52 47.58 55.58 44 60 44ZM60 72C54.67 72 50 69.33 50 66C50 62.67 54.67 60 60 60C65.33 60 70 62.67 70 66C70 69.33 65.33 72 60 72Z" fill="#FF9800"/>
</svg>

After

Width:  |  Height:  |  Size: 500 B

@@ -0,0 +1,4 @@
<svg width="120" height="120" viewBox="0 0 120 120" fill="none" xmlns="http://www.w3.org/2000/svg">
<circle cx="60" cy="60" r="60" fill="#F5F5F5"/>
<path d="M60 36C48.95 36 40 44.95 40 56C40 67.05 48.95 76 60 76C71.05 76 80 67.05 80 56C80 44.95 71.05 36 60 36ZM66 64H54V60H66V64ZM66 56H54V52H66V56Z" fill="#9E9E9E"/>
</svg>

After

Width:  |  Height:  |  Size: 332 B

@@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 256 256" width="64px" height="64px" fill-rule="evenodd" clip-rule="evenodd"><circle cx="198.287" cy="104.366" r="32.265" fill="#D7E057" transform="rotate(-76.526 198.291 104.361)"/><path fill="#3A312A" d="M198.287,138.131c-18.618,0-33.765-15.147-33.765-33.765s15.147-33.765,33.765-33.765 c18.618,0,33.765,15.146,33.765,33.765S216.905,138.131,198.287,138.131z M198.287,73.602c-16.964,0-30.765,13.801-30.765,30.765 s13.801,30.765,30.765,30.765s30.765-13.801,30.765-30.765S215.251,73.602,198.287,73.602z"/><path fill="#87796F" d="M196.097,126.921v-5.252c-3.704-0.166-7.297-1.161-9.398-2.377l1.658-6.468 c2.322,1.271,5.583,2.432,9.177,2.432c3.151,0,5.307-1.216,5.307-3.428c0-2.1-1.769-3.427-5.86-4.809 c-5.915-1.99-9.951-4.755-9.951-10.117c0-4.865,3.428-8.68,9.343-9.84v-5.252h5.418v4.865c3.704,0.165,6.191,0.94,8.016,1.825 l-1.603,6.246c-1.437-0.608-3.981-1.88-7.96-1.88c-3.594,0-4.755,1.549-4.755,3.096c0,1.825,1.935,2.986,6.634,4.754 c6.578,2.322,9.232,5.363,9.232,10.338c0,4.92-3.483,9.122-9.841,10.227v5.639H196.097z"/><path fill="#3A312A" d="M201.515,128.421h-5.418c-0.829,0-1.5-0.672-1.5-1.5v-3.855c-3.287-0.323-6.504-1.233-8.649-2.475 c-0.582-0.336-0.869-1.02-0.702-1.67l1.658-6.468c0.115-0.449,0.431-0.819,0.856-1.004c0.424-0.185,0.911-0.162,1.317,0.06 c1.535,0.84,4.673,2.248,8.458,2.248c0.636,0,3.807-0.093,3.807-1.928c0-0.91-0.586-1.95-4.84-3.388 c-5.107-1.718-10.971-4.583-10.971-11.538c0-5.338,3.546-9.479,9.343-11.032v-4.061c0-0.828,0.671-1.5,1.5-1.5h5.418 c0.829,0,1.5,0.672,1.5,1.5v3.464c2.737,0.252,5.094,0.87,7.17,1.877c0.642,0.312,0.976,1.031,0.798,1.723l-1.603,6.246 c-0.109,0.423-0.396,0.777-0.788,0.972c-0.392,0.194-0.848,0.207-1.25,0.037l-0.418-0.181c-1.45-0.63-3.64-1.581-6.958-1.581 c-1.216,0-3.255,0.207-3.255,1.597c0,0.866,1.641,1.836,5.663,3.35c7.144,2.521,10.204,6.035,10.204,11.742 c0,5.566-3.82,9.95-9.84,11.443v4.422C203.015,127.749,202.343,128.421,201.515,128.421z M197.597,125.421h2.418v-4.139 c0-0.73,0.525-1.353,1.243-1.478c5.303-0.922,8.597-4.273,8.597-8.749c0-3.612-1.4-6.513-8.231-8.924 c-4.339-1.632-7.635-3.115-7.635-6.168c0-2.223,1.643-4.597,6.255-4.597c3.063,0,5.339,0.692,6.94,1.321l0.852-3.321 c-1.807-0.692-3.885-1.085-6.311-1.193c-0.802-0.035-1.433-0.695-1.433-1.498v-3.365h-2.418v3.752c0,0.717-0.507,1.334-1.211,1.472 c-5.092,1-8.132,4.128-8.132,8.369c0,3.989,2.67,6.59,8.93,8.695c3.575,1.208,6.881,2.798,6.881,6.23 c0,2.993-2.672,4.928-6.807,4.928c-3.315,0-6.191-0.909-8.181-1.776l-0.902,3.52c2.052,0.911,4.94,1.547,7.713,1.672 c0.801,0.035,1.433,0.695,1.433,1.498V125.421z"/><path fill="#D7E057" d="M162.221,16.576c0,0,2.411,8.954,9.352,9.369c0,0-9.266,3.201-9.422,10.045c0,0-1.824-9.6-9.142-9.944 C153.009,26.046,161.532,24.755,162.221,16.576z"/><path fill="#3A312A" d="M162.15,37.49c-0.714,0-1.337-0.507-1.473-1.22c-0.016-0.082-1.704-8.441-7.739-8.726 c-0.77-0.036-1.388-0.65-1.428-1.421c-0.04-0.77,0.511-1.444,1.273-1.561c0.295-0.047,7.363-1.243,7.942-8.113 c0.061-0.726,0.635-1.303,1.36-1.368c0.732-0.068,1.392,0.399,1.582,1.102l0,0c0.021,0.079,2.228,7.92,7.994,8.265 c0.715,0.042,1.299,0.584,1.396,1.293c0.098,0.709-0.319,1.388-0.996,1.622c-0.081,0.028-8.282,2.953-8.412,8.661 c-0.018,0.768-0.611,1.398-1.376,1.461C162.233,37.488,162.191,37.49,162.15,37.49z M157.631,25.963 c2.107,1.333,3.523,3.395,4.447,5.279c1.376-2.232,3.515-3.871,5.364-4.972c-2.287-1.27-3.884-3.35-4.941-5.224 C161.328,23.334,159.486,24.922,157.631,25.963z"/><path fill="#D7E057" d="M183.919,26.253c0,0,3.408,12.659,13.222,13.246c0,0-13.1,4.525-13.321,14.202 c0,0-2.578-13.572-12.925-14.059C170.895,39.642,182.946,37.817,183.919,26.253z"/><path fill="#3A312A" d="M183.819,55.2c-0.712,0-1.335-0.506-1.472-1.217c-0.024-0.125-2.495-12.418-11.522-12.843 c-0.771-0.036-1.388-0.65-1.428-1.421c-0.04-0.77,0.511-1.444,1.273-1.561c0.441-0.068,10.894-1.817,11.754-12.032 c0.061-0.726,0.634-1.301,1.359-1.367c0.734-0.057,1.393,0.399,1.583,1.101c0.032,0.116,3.259,11.626,11.864,12.141 c0.714,0.042,1.298,0.583,1.396,1.292c0.098,0.708-0.319,1.388-0.994,1.622c-0.121,0.042-12.118,4.311-12.313,12.819 c-0.018,0.767-0.61,1.396-1.374,1.46C183.903,55.198,183.861,55.2,183.819,55.2z M176.078,39.471 c3.878,1.97,6.23,5.746,7.587,8.877c2.026-4.021,5.942-6.787,8.949-8.427c-4.134-1.843-6.783-5.651-8.334-8.723 C182.487,35.559,179.009,38.066,176.078,39.471z"/><path fill="#D7E057" d="M162.221,43.233c0,0,2.411,8.954,9.352,9.369c0,0-9.266,3.201-9.422,10.045c0,0-1.824-9.6-9.142-9.944 C153.009,52.704,161.532,51.412,162.221,43.233z"/><path fill="#3A312A" d="M162.149,64.148c-0.713,0-1.337-0.507-1.472-1.22c-0.016-0.082-1.704-8.442-7.739-8.727 c-0.77-0.036-1.388-0.65-1.428-1.421c-0.04-0.77,0.511-1.444,1.273-1.561c0.295-0.047,7.363-1.243,7.942-8.113 c0.061-0.726,0.635-1.303,1.36-1.368c0.732-0.067,1.392,0.399,1.582,1.102l0,0c0.021,0.079,2.228,7.92,7.994,8.265 c0.715,0.042,1.299,0.584,1.396,1.293c0.098,0.709-0.319,1.388-0.996,1.622c-0.081,0.028-8.282,2.953-8.412,8.662 c-0.018,0.768-0.611,1.398-1.376,1.461C162.233,64.146,162.191,64.148,162.149Line truncated

After

Width:  |  Height:  |  Size: 19 KiB

@@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 128 128" width="64px" height="64px"><path fill="#fff" d="M98.2,116.8l-22.2-9c-1.5,5.3-7.7,8.3-12.2,8.9v0.1c-0.7,0-1.9-0.1-2-0.1c-4.3-0.8-8.3-3.7-9.7-8.8 l-22.2,9l0,0C52,123.9,76,123.9,98.2,116.8L98.2,116.8z"/><path fill="#f7ebde" d="M76,102v6.5l0,0c-3.5,12-20.5,12-23.9,0l0,0V102"/><path fill="#f7ebde" d="M96.3,59.8c0-26.4-13.1-39.9-32.3-39.9S31.7,33.5,31.7,59.8c-6.2,0.5-4.8,14.6,2.2,13.8 c2,5.7,4.2,10.4,6.5,14.4c7.9,13.5,16.9,17.5,23.5,17.5c8.5,0,21.1-6.6,30-31.8C101.1,74.4,102.5,60.3,96.3,59.8z"/><path fill="#454b54" d="M30 120.5c-1.2 0-2.3-.7-2.8-1.9-.6-1.5.1-3.3 1.6-3.9l22.1-9c1.5-.6 3.3.1 3.9 1.6.6 1.5-.1 3.3-1.6 3.9l-22.1 9C30.7 120.4 30.3 120.5 30 120.5zM98.1 120.5c-.4 0-.8-.1-1.1-.2l-22.1-9c-1.5-.6-2.3-2.4-1.6-3.9.6-1.5 2.4-2.3 3.9-1.6l22.1 9c1.5.6 2.3 2.4 1.6 3.9C100.4 119.8 99.2 120.5 98.1 120.5z"/><path fill="#454b54" d="M64,120.5c-7.1,0-12.9-4.4-14.8-11.2c-0.5-1.6,0.5-3.3,2.1-3.7c1.6-0.5,3.3,0.5,3.7,2.1 c1.5,5.1,5.6,6.9,9.1,6.9s7.6-1.8,9.1-6.9c0.5-1.6,2.1-2.5,3.7-2.1c1.6,0.5,2.5,2.1,2.1,3.7C76.9,116.1,71.1,120.5,64,120.5z"/><path fill="#454b54" d="M64,108.4c-5.4,0-16-2.3-25.5-18c-0.9-1.4-0.4-3.3,1-4.1c1.4-0.9,3.3-0.4,4.1,1 c8,13.2,16.2,15.1,20.4,15.1c5,0,17.6-2.9,27.2-29.8c0.6-1.6,2.3-2.4,3.8-1.8c1.6,0.6,2.4,2.3,1.8,3.8C86,105.1,70.3,108.4,64,108.4 z"/><path fill="#c88b79" d="M96.7,59.9c-0.101,0-0.2,0-0.4,0C96.3,33.5,83.2,20,64,20c-14,0-24.8,7.2-29.6,21.4 c-1.7,4.9-2.6,10.6-2.7,17.1c7.712-18.368,17.85-11.435,31.374-4.503C72.521,58.84,83.621,63.684,96.7,59.9"/><path fill="#454b54" d="M87.1,64.3c-10.899,0-20.3-4.9-28.2-9c-6.8-3.6-12.7-6.6-16.9-5.1c-2.8,1-5.3,4.1-7.5,9.4 c-0.6,1.5-2.4,2.2-3.9,1.6c-1.5-0.6-2.2-2.4-1.6-3.9c2.9-7,6.5-11.1,11-12.8c6.7-2.4,13.7,1.2,21.7,5.4C71.5,55,82.6,60.8,95.8,57 c1.601-0.5,3.3,0.4,3.7,2c0.5,1.6-0.4,3.3-2,3.7C93.9,63.8,90.4,64.2,87.1,64.3"/><path fill="#fff" d="M59.864,55.8H36.34c-0.635,1.109-1.248,2.375-1.84,3.8c-0.455,1.137-1.599,1.814-2.78,1.814 c-0.179,0-0.358-0.015-0.536-0.047c0.204,5.363,0.505,13.239,0.515,13.239c0,0,0-0.002,0-0.006c0,2.601,2.1,4.7,4.7,4.7h17 c2.1,0,4-1.5,4.5-3.6l1-5.9c0.2-1.3,1.4-2.3,2.8-2.3c1.4,0,2.5,1,2.8,2.3l1,5.9c0.5,2.1,2.4,3.6,4.5,3.6h17c2.6,0,4.7-2.1,4.7-4.7 l0.414-10.714c-1.712,0.243-3.388,0.365-5.015,0.414C76.64,64.3,67.561,59.788,59.864,55.8"/><path fill="#faf4f2" d="M90.7,55.8H74.419c4.027,1.448,8.273,2.424,12.777,2.424c1.682,0,3.399-0.136,5.154-0.435L92.4,56.5 C92,56,91.4,55.8,90.7,55.8"/><path fill="#ededee" d="M74.419,55.8H59.864c7.697,3.988,16.776,8.5,27.236,8.5c1.627-0.049,3.303-0.171,5.015-0.414 l0.236-6.096c-1.756,0.299-3.473,0.435-5.154,0.435C82.693,58.224,78.447,57.247,74.419,55.8"/><path fill="#fff" d="M98.9,81.3l-8.1-1.4L96.3,48l8.1,1.4c3.5,0.6,5.8,4,5.2,7.5L106.3,76 C105.7,79.5,102.4,81.9,98.9,81.3z"/><path fill="#454b54" d="M100,84.4c-0.5,0-1.1,0-1.6-0.1L90.8,83c-1.6-0.3-2.7-1.8-2.5-3.4l5-32c0.1-0.8,0.6-1.5,1.2-2 s1.5-0.6,2.3-0.5l8.1,1.4c5.1,0.9,8.6,5.8,7.6,11l-3.4,19.1C108.5,81.1,104.6,84.4,100,84.4z M94.8,77.5l4.6,0.8 c0.2,0,0.4,0.1,0.6,0.1c1.7,0,3.1-1.2,3.4-2.9l3.4-19.1c0.3-1.9-0.9-3.7-2.8-4l-5.1-0.9L94.8,77.5z"/><path fill="#fff" d="M29.1,81.3l8.1-1.4L31.7,48l-8.1,1.4c-3.5,0.6-5.8,4-5.2,7.5L21.7,76C22.3,79.5,25.6,81.9,29.1,81.3z"/><path fill="#454b54" d="M28,84.4L28,84.4c-4.6,0-8.5-3.3-9.3-7.8l-3.4-19.1c-0.9-5.1,2.5-10,7.6-11l8.1-1.4 c0.8-0.1,1.6,0,2.2,0.5c0.7,0.5,1.1,1.2,1.2,1.9L40,79.3c0.3,1.6-0.8,3.2-2.4,3.5l-8.1,1.4C29.1,84.3,28.6,84.4,28,84.4z M29.2,51.5 L24,52.4c-1.9,0.3-3.1,2.1-2.8,4l3.4,19.1c0.3,1.7,1.7,2.9,3.4,2.9l0,0c0.2,0,0.4,0,0.6-0.1l5.2-0.9L29.2,51.5z"/><path fill="#454b54" d="M25.4,50.8h-0.1c-1.7-0.1-2.9-1.5-2.9-3.1C23.3,25.1,41.5,7.5,64,7.5c22.1,0,40.3,17.3,41.5,39.4 c0.1,1.7-1.2,3.1-2.8,3.2c-1.7,0.1-3.1-1.2-3.2-2.8c-1-18.9-16.6-33.7-35.5-33.7c-19.2,0-34.8,15.1-35.6,34.4 C28.4,49.5,27,50.8,25.4,50.8z"/><path fill="#454b54" d="M96.3,62.8c-1.7,0-3-1.3-3-3c0-23.4-10.7-36.9-29.3-36.9c-12.8,0-21.9,6.3-26.3,18.2 c-0.6,1.6-2.3,2.3-3.9,1.8c-1.6-0.6-2.3-2.3-1.8-3.9c5.4-14.2,16.7-22.1,32-22.1c22.1,0,35.3,16,35.3,42.9 C99.3,61.5,97.9,62.8,96.3,62.8z"/></svg>

After

Width:  |  Height:  |  Size: 4.0 KiB

@@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" viewBox="0,0,256,256" width="64px" height="64px" fill-rule="nonzero"><g fill="none" fill-rule="nonzero" stroke="none" stroke-width="1" stroke-linecap="butt" stroke-linejoin="miter" stroke-miterlimit="10" stroke-dasharray="" stroke-dashoffset="0" font-family="none" font-weight="none" font-size="none" text-anchor="none" style="mix-blend-mode: normal"><g><path d="M202.5,241.644h-149c-1.657,0 -3,-1.343 -3,-3v-8c0,-1.657 1.343,-3 3,-3h149c1.657,0 3,1.343 3,3v8c0,1.657 -1.343,3 -3,3z" fill="#4671c6"></path><path d="M202.5,243.644h-149c-2.757,0 -5,-2.243 -5,-5v-8c0,-2.757 2.243,-5 5,-5h149c2.757,0 5,2.243 5,5v8c0,2.757 -2.243,5 -5,5zM53.5,229.644c-0.551,0 -1,0.449 -1,1v8c0,0.551 0.449,1 1,1h149c0.552,0 1,-0.449 1,-1v-8c0,-0.551 -0.448,-1 -1,-1z" fill="#3762cc"></path><path d="M35.331,143.801c-1.657,0 -3,-1.343 -3,-3v-4c0,-1.657 1.343,-3 3,-3c1.657,0 3,1.343 3,3v4c0,1.656 -1.344,3 -3,3z" fill="#a4c9ff"></path><path d="M215.615,199.536h-7.876c-1.657,0 -3,-1.343 -3,-3c0,-1.657 1.343,-3 3,-3h7.876c1.657,0 3,1.343 3,3c0,1.657 -1.343,3 -3,3zM198.879,199.536h-7.876c-1.657,0 -3,-1.343 -3,-3c0,-1.657 1.343,-3 3,-3h7.876c1.657,0 3,1.343 3,3c0,1.657 -1.343,3 -3,3zM182.143,199.536h-7.876c-1.657,0 -3,-1.343 -3,-3c0,-1.657 1.343,-3 3,-3h7.876c1.657,0 3,1.343 3,3c0,1.657 -1.343,3 -3,3zM165.406,199.536h-7.875c-1.657,0 -3,-1.343 -3,-3c0,-1.657 1.343,-3 3,-3h7.875c1.657,0 3,1.343 3,3c0,1.657 -1.343,3 -3,3zM148.671,199.536h-7.876c-1.657,0 -3,-1.343 -3,-3c0,-1.657 1.343,-3 3,-3h7.876c1.657,0 3,1.343 3,3c0,1.657 -1.343,3 -3,3zM131.935,199.536h-7.876c-1.657,0 -3,-1.343 -3,-3c0,-1.657 1.343,-3 3,-3h7.876c1.657,0 3,1.343 3,3c0,1.657 -1.343,3 -3,3zM115.198,199.536h-7.875c-1.657,0 -3,-1.343 -3,-3c0,-1.657 1.343,-3 3,-3h7.875c1.657,0 3,1.343 3,3c0,1.657 -1.343,3 -3,3zM98.462,199.536h-7.876c-1.657,0 -3,-1.343 -3,-3c0,-1.657 1.343,-3 3,-3h7.876c1.657,0 3,1.343 3,3c0,1.657 -1.343,3 -3,3zM81.727,199.536h-7.876c-1.657,0 -3,-1.343 -3,-3c0,-1.657 1.343,-3 3,-3h7.876c1.657,0 3,1.343 3,3c0,1.657 -1.344,3 -3,3zM64.99,199.536h-7.876c-1.657,0 -3,-1.343 -3,-3c0,-1.657 1.343,-3 3,-3h7.876c1.657,0 3,1.343 3,3c0,1.657 -1.343,3 -3,3zM48.254,199.536h-7.876c-1.657,0 -3,-1.343 -3,-3c0,-1.657 1.343,-3 3,-3h7.876c1.657,0 3,1.343 3,3c0,1.657 -1.343,3 -3,3zM220.686,194.032c-1.657,0 -3,-1.343 -3,-3v-7.876c0,-1.657 1.343,-3 3,-3c1.657,0 3,1.343 3,3v7.876c0,1.657 -1.343,3 -3,3zM35.331,194.009c-1.657,0 -3,-1.343 -3,-3v-7.876c0,-1.657 1.343,-3 3,-3c1.657,0 3,1.343 3,3v7.876c0,1.657 -1.344,3 -3,3zM220.686,177.296c-1.657,0 -3,-1.343 -3,-3v-7.876c0,-1.657 1.343,-3 3,-3c1.657,0 3,1.343 3,3v7.876c0,1.657 -1.343,3 -3,3zM35.331,177.273c-1.657,0 -3,-1.343 -3,-3v-7.876c0,-1.657 1.343,-3 3,-3c1.657,0 3,1.343 3,3v7.876c0,1.657 -1.344,3 -3,3zM220.686,160.56c-1.657,0 -3,-1.343 -3,-3v-7.876c0,-1.657 1.343,-3 3,-3c1.657,0 3,1.343 3,3v7.876c0,1.657 -1.343,3 -3,3zM35.331,160.537c-1.657,0 -3,-1.343 -3,-3v-7.876c0,-1.657 1.343,-3 3,-3c1.657,0 3,1.343 3,3v7.876c0,1.657 -1.344,3 -3,3z" fill="#a4c9ff"></path><path d="M220.686,143.801c-1.657,0 -3,-1.343 -3,-3v-4c0,-1.657 1.343,-3 3,-3c1.657,0 3,1.343 3,3v4c0,1.656 -1.343,3 -3,3z" fill="#a4c9ff"></path><ellipse cx="220.686" cy="112.489" rx="32.314" ry="32.095" fill="#6bdddd"></ellipse><path d="M169.779,136.801h-23.373v0.671c0,9.976 -8.087,18.062 -18.062,18.062c-9.975,0 -18.062,-8.087 -18.062,-18.062v-0.671h-23.373c-8.97,0 -16.242,7.272 -16.242,16.242v51.889h115.355v-51.889c0,-8.97 -7.272,-16.242 -16.243,-16.242z" fill="#e0ebfc"></path><path d="M128.344,128.869c-6.43,0 -12.538,-1.352 -18.062,-3.772v12.375c0,9.976 8.087,18.062 18.062,18.062c9.975,0 18.062,-8.087 18.062,-18.062v-12.375c-5.524,2.421 -11.632,3.772 -18.062,3.772z" fill="#f9cfcf"></path><path d="M186.021,206.932h-115.354c-1.104,0 -2,-0.896 -2,-2v-51.889c0,-10.059 8.184,-18.242 18.242,-18.242h23.373c1.104,0 2,0.896 2,2v0.67c0,8.857 7.206,16.063 16.062,16.063c8.856,0 16.063,-7.206 16.063,-16.063v-0.67c0,-1.104 0.896,-2 2,-2h23.373c10.059,0 18.242,8.184 18.242,18.242v51.889c-0.001,1.105 -0.896,2 -2.001,2zM72.667,202.932h111.355v-49.889c0,-7.853 -6.389,-14.242 -14.242,-14.242h-21.417c-0.687,10.445 -9.403,18.733 -20.019,18.733c-10.616,0 -19.332,-8.288 -20.019,-18.733h-21.416c-7.853,0 -14.242,6.389 -14.242,14.242z" fill="#3762cc"></path><path d="M128.344,157.534c-11.062,0 -20.062,-9 -20.062,-20.063v-12.375c0,-0.675 0.341,-1.305 0.906,-1.674c0.565,-0.37 1.279,-0.428 1.897,-0.158c5.458,2.392 11.265,3.604 17.259,3.604c5.995,0 11.802,-1.213 17.26,-3.604c0.618,-0.27 1.332,-0.211 1.896,0.158c0.565,0.37 0.906,0.999 0.906,1.674v12.375c0,11.063 -9,20.063 -20.062,20.063zM112.282,128.052v9.419c0,8.857 7.206,16.063 16.062,16.063c8.856,0 16.063,-7.206 16.063,-16.063v-9.419c-5.138,1.871 -10.527,2.817 -16.063,2.817c-5.535,0 -10.925,-0.947 -16.062,-2.817z" fill="#3762cc"></path><path d="M173.087,73.675h-5.851v-5.907c0,-5.827 -2.859,-10.974 -7.239,-14.155c0.018,-0.027 0.032,-0.055 0.05,-0.082c-4.52,6.895 -12.313,11.45 -21.Line truncated

After

Width:  |  Height:  |  Size: 18 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 15 KiB

+6
View File
@@ -0,0 +1,6 @@
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32">
<rect x="1.5" y="1.5" width="29" height="29" rx="8.5" fill="#C9F24E"/>
<circle cx="10.5" cy="16" r="2.3" fill="#0B0C10"/>
<circle cx="16" cy="16" r="2.3" fill="#0B0C10"/>
<circle cx="21.5" cy="16" r="2.3" fill="#0B0C10"/>
</svg>

After

Width:  |  Height:  |  Size: 298 B

+18
View File
@@ -0,0 +1,18 @@
<svg width="32" height="32" viewBox="0 0 120 120" fill="none" xmlns="http://www.w3.org/2000/svg">
<!-- Chat bubble background -->
<path
d="M95 20H25C22.2386 20 20 22.2386 20 25V75C20 77.7614 22.2386 80 25 80H45L55 95L65 80H95C97.7614 80 100 77.7614 100 75V25C100 22.2386 97.7614 20 95 20Z"
fill="#FFFFFF"
/>
<!-- Letter C -->
<path
d="M75 40C75 40 65 35 60 35C50 35 45 42 45 50C45 58 50 65 60 65C65 65 75 60 75 60V52C75 52 68 55 63 55C57 55 53 53 53 50C53 47 57 45 63 45C68 45 75 48 75 48V40Z"
fill="#f34611"
/>
<!-- Dots -->
<!-- <circle cx="45" cy="50" r="3" fill="#BFEEAA"/>
<circle cx="60" cy="50" r="3" fill="#BFEEAA"/>
<circle cx="75" cy="50" r="3" fill="#BFEEAA"/> -->
</svg>

After

Width:  |  Height:  |  Size: 728 B

@@ -0,0 +1,20 @@
<svg width="1200" height="1200" viewBox="0 0 120 120" fill="none" xmlns="http://www.w3.org/2000/svg">
<!-- Chat bubble background with subtle outline -->
<path
d="M95 20H25C22.2386 20 20 22.2386 20 25V75C20 77.7614 22.2386 80 25 80H45L55 95L65 80H95C97.7614 80 100 77.7614 100 75V25C100 22.2386 97.7614 20 95 20Z"
fill="#f34611"
stroke="#EEEEEE"
stroke-width="1"
/>
<!-- Letter C -->
<path
d="M75 40C75 40 65 35 60 35C50 35 45 42 45 50C45 58 50 65 60 65C65 65 75 60 75 60V52C75 52 68 55 63 55C57 55 53 53 53 50C53 47 57 45 63 45C68 45 75 48 75 48V40Z"
fill="#FFFFFF"
/>
<!-- Dots -->
<!-- <circle cx="45" cy="50" r="3" fill="#BFEEAA"/>
<circle cx="60" cy="50" r="3" fill="#BFEEAA"/>
<circle cx="75" cy="50" r="3" fill="#BFEEAA"/> -->
</svg>

After

Width:  |  Height:  |  Size: 794 B

+32
View File
@@ -0,0 +1,32 @@
// Runtime configuration - this file gets replaced at container startup
// Assigned to `self` so the service worker can importScripts() it too;
// in a page self === window, so window.APP_CONFIG still works.
self.APP_CONFIG = {
// API URLs
API_URL: "https://devapi.chattermate.chat/api/v1",
WS_URL: "wss://devapi.chattermate.chat",
WIDGET_URL: "https://devapp.chattermate.chat",
// Firebase Configuration
FIREBASE_API_KEY: "AIzaSyDTwDgANnBItYx39qm-6shq4cUws6QY4wI",
FIREBASE_AUTH_DOMAIN: "chattermate-13e0a.firebaseapp.com",
FIREBASE_PROJECT_ID: "chattermate-13e0a",
FIREBASE_MESSAGING_SENDER_ID: "680125690355",
FIREBASE_APP_ID: "1:680125690355:web:466f50999a6c91935ae286",
FIREBASE_STORAGE_BUCKET: "chattermate-13e0a.firebasestorage.app",
FIREBASE_MEASUREMENT_ID: "G-7LGB58R2Q7",
FIREBASE_VAPID_KEY: "BJKnggErez2qK3AxBhHyEV-EoS9lfcWO1GDXhRwUKIHbT_PH23vhY_8HRIz_KyuC-0gbuViSrtSMiFp7zgyYY4g",
// Razorpay Checkout
RAZORPAY_KEY_ID: "rzp_test_T92OR9gqPBht0N",
GTM_ID: "",
// Google Fonts API
GOOGLE_FONTS_API_KEY: "AIzaSyCTQCSK_ybLEglabeusbyekQGEyvFr2C5o",
DEMO_WIDGET_ID: "a6ee36e9-b70e-4b12-8f94-cc5a5b147f26",
// Node Environment
NODE_ENV: "development",
HOST: "0.0.0.0"
};
+30
View File
@@ -0,0 +1,30 @@
// Runtime configuration - this file gets replaced at container startup
// Assigned to `self` so the service worker can importScripts() it too;
// in a page self === window, so window.APP_CONFIG still works.
self.APP_CONFIG = {
// API URLs
API_URL: "http://localhost:8000/api/v1",
WS_URL: "ws://localhost:8000",
WIDGET_URL: "http://localhost:8000",
// Firebase Configuration
FIREBASE_API_KEY: "",
FIREBASE_AUTH_DOMAIN: "",
FIREBASE_PROJECT_ID: "",
FIREBASE_MESSAGING_SENDER_ID: "680125690355",
FIREBASE_APP_ID: "",
FIREBASE_STORAGE_BUCKET: "",
FIREBASE_MEASUREMENT_ID: "",
FIREBASE_VAPID_KEY: "",
// Razorpay Checkout
RAZORPAY_KEY_ID: "rzp_test_T92OR9gqPBht0N",
GTM_ID: "",
// Google Fonts API
GOOGLE_FONTS_API_KEY: "",
// Node Environment
NODE_ENV: "development",
HOST: "0.0.0.0"
};
Binary file not shown.

After

Width:  |  Height:  |  Size: 15 KiB

+6
View File
@@ -0,0 +1,6 @@
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 32 32">
<rect x="1.5" y="1.5" width="29" height="29" rx="8.5" fill="#C9F24E"/>
<circle cx="10.5" cy="16" r="2.3" fill="#0B0C10"/>
<circle cx="16" cy="16" r="2.3" fill="#0B0C10"/>
<circle cx="21.5" cy="16" r="2.3" fill="#0B0C10"/>
</svg>

After

Width:  |  Height:  |  Size: 298 B

+6
View File
@@ -0,0 +1,6 @@
<svg width="32" height="32" viewBox="0 0 120 120" fill="none" xmlns="http://www.w3.org/2000/svg">
<rect x="20" y="20" width="80" height="80" rx="22" fill="#C9F24E"/>
<circle cx="42" cy="60" r="6" fill="#0B0C10"/>
<circle cx="60" cy="60" r="6" fill="#0B0C10"/>
<circle cx="78" cy="60" r="6" fill="#0B0C10"/>
</svg>

After

Width:  |  Height:  |  Size: 322 B

+29
View File
@@ -0,0 +1,29 @@
<!doctype html>
<!--
OAuth redirect target for Facebook Login for Business (Messenger/Instagram).
Meta redirects the login popup here with ?code&state; this relays them to the
opener and closes. It's a static file (not the SPA) so the popup stays light,
and it must be registered as a Valid OAuth Redirect URI on the Meta app.
-->
<html>
<head><meta charset="utf-8" /><title>Connecting…</title></head>
<body>
Connecting…
<script>
(function () {
var params = new URLSearchParams(window.location.search)
var message = {
source: 'meta-oauth',
code: params.get('code'),
state: params.get('state'),
error: params.get('error_description') || params.get('error'),
}
if (window.opener) {
window.opener.postMessage(message, window.location.origin)
}
window.close()
})()
</script>
</body>
</html>
Binary file not shown.

After

Width:  |  Height:  |  Size: 516 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.4 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 17 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 12 KiB

+2
View File
@@ -0,0 +1,2 @@
User-agent: *
Disallow: /
+888
View File
@@ -0,0 +1,888 @@
(()=>{var wt=(at,ot,e)=>new Promise((M,d)=>{var j=x=>{try{B(e.next(x))}catch(N){d(N)}},V=x=>{try{B(e.throw(x))}catch(N){d(N)}},B=x=>x.done?M(x.value):Promise.resolve(x.value).then(j,V);B((e=e.apply(at,ot)).next())});window.chattermateId;window.chattermateBaseUrl;window.ChatterMate;window.chattermateConfig;(function(){function at(t){return/^#[0-9A-F]{6}$/i.test(t)}function ot(){return typeof window!="undefined"&&window.chattermateBaseUrl?window.chattermateBaseUrl:typeof window!="undefined"&&window.APP_CONFIG&&window.APP_CONFIG.API_URL?window.APP_CONFIG.API_URL:"https://api.chattermate.chat/api/v1"}let e={baseUrl:ot(),containerId:"chattermate-container",backdropId:"chattermate-backdrop",buttonId:"chattermate-button",chatBubbleColor:"#f34611",loadingContainerId:"chattermate-loading",tokenKey:"ctid",tokenProvider:null,containerBottom:100,containerRight:20,containerWidth:400,containerHeight:560,launcherBottom:20,launcherRight:20,side:"right",displayMode:"floating",launcher:!0,sidebarWidth:420,searchBarWidth:320,searchPlaceholder:"Ask anything...",zIndex:999999,trigger:null,hotkey:!0,surfaceIsPalette:null,chatStyle:null,chatInitiationMessages:[],initiationMessageId:"chattermate-initiation",initiationShownKey:"ctim_shown",unreadCount:0,hasOpened:!1},M={};function d(t,n){e[t]=n,M[t]=!0}let j=["floating","sidebar-left","sidebar-right","search-bar"],V=["ASK_ANYTHING","AURORA"],B=680,x=620,N=140,S={width:!1,height:!1},P=0;function q(){return e.surfaceIsPalette===!1?!1:(V.indexOf(e.chatStyle)!==-1||e.displayMode==="search-bar")&&e.displayMode!=="sidebar-left"&&e.displayMode!=="sidebar-right"}function Z(){let t=document.getElementById(e.containerId);if(!t)return;if(!q()||!P){t.style.height="";return}let n=Math.min(rt().height,Math.round(window.innerHeight*.76));t.style.height=Math.max(N,Math.min(n,P))+"px"}function rt(){return{width:S.width?e.containerWidth:B,height:S.height?e.containerHeight:x}}function _t(t){if(!t||typeof t!="object")return;let n=function(i,o){M[i]||(e[i]=o)};j.indexOf(t.mode)!==-1&&n("displayMode",t.mode),(t.side==="left"||t.side==="right")&&n("side",t.side),typeof t.launcher=="boolean"&&n("launcher",t.launcher),m(t.width)&&(n("containerWidth",Math.max(280,t.width)),M.containerWidth||(S.width=!0)),m(t.height)&&(n("containerHeight",Math.max(400,t.height)),M.containerHeight||(S.height=!0)),m(t.sidebar_width)&&n("sidebarWidth",Math.max(280,t.sidebar_width)),typeof t.search_placeholder=="string"&&t.search_placeholder&&n("searchPlaceholder",t.search_placeholder.slice(0,80)),m(t.offset_bottom)&&n("launcherBottom",Math.max(0,t.offset_bottom)),m(t.offset_side)&&n("launcherRight",Math.max(0,t.offset_side)),m(t.z_index)&&n("zIndex",Math.max(1,Math.floor(t.z_index)))}function It(){let t=q(),n=t?rt():{width:e.containerWidth,height:e.containerHeight};return{type:"WIDGET_DISPLAY",mode:t?"ask-ai":e.displayMode,width:n.width,height:n.height,hotkey:e.hotkey!==!1}}let c=null,R=[],X=!1,g=null,T=null,y=!1;function J(t){c?t():y||R.push(t)}let Q={},st=!1;function _(t,n){let i=Q[t];!i||!i.length||i.slice().forEach(function(o){try{o(n)}catch(h){}})}function Lt(t){let n=/^#?([0-9a-f]{6})$/i.exec((t||"").trim());if(!n)return"#0B0C10";let i=parseInt(n[1],16);return(.299*(i>>16&255)+.587*(i>>8&255)+.114*(i&255))/255>.6?"#0B0C10":"#FFFFFF"}let ct=!1,E=null,lt=[];function F(){if(ct)return;ct=!0,E&&(clearTimeout(E),E=null);let t=document.getElementById(e.buttonId);t&&t.classList.remove("chattermate-pending"),lt.splice(0).forEach(n=>{try{n()}catch(i){}})}function O(){let t=document.getElementById(e.buttonId);if(!t)return;let n=t.querySelector(".cm-badge");if(!n)return;let i=e.hasOpened?e.unreadCount:(e.chatInitiationMessages||[]).length;n.textContent=i>99?"99+":String(i),n.style.display=i>0&&!t.classList.contains("active")?"flex":"none"}function W(){let t=e.displayMode,n=t==="sidebar-left"||t==="sidebar-right",i=t==="sidebar-left"?"left":t==="sidebar-right"?"right":e.side,o=t==="search-bar"?48:64,h=V.indexOf(e.chatStyle)===-1,r=q(),l=rt(),w=document.createElement("style");w.id="chattermate-styles",w.textContent=`
/* ===== Rounded-square launcher (design comp) ===== */
#${e.buttonId} {
position: fixed;
bottom: ${e.launcherBottom}px;
${i}: ${e.launcherRight}px;
width: 64px;
height: 64px;
border-radius: 20px 20px 20px 6px;
background: ${e.chatBubbleColor};
color: ${Lt(e.chatBubbleColor)};
box-shadow: 0 16px 40px -8px ${e.chatBubbleColor}cc, inset 0 0 0 1px rgba(255,255,255,0.08);
cursor: pointer;
z-index: ${e.zIndex};
display: flex;
align-items: center;
justify-content: center;
transition: transform 0.3s cubic-bezier(.34,1.3,.5,1), opacity 320ms ease;
animation: chattermate-float 4s ease-in-out infinite;
}
#${e.buttonId}.active { animation: none; }
/* Stay fully invisible until the org's real brand color is known (or the
widget errors out / times out) \u2014 avoids ever flashing the wrong color. */
#${e.buttonId}.chattermate-pending {
opacity: 0;
pointer-events: none;
}
#${e.buttonId}:hover { transform: scale(1.06); }
/* Expanding rings (closed state only) */
#${e.buttonId} .cm-ring {
position: absolute;
inset: 0;
border-radius: 20px 20px 20px 6px;
border: 1.5px solid ${e.chatBubbleColor};
animation: chattermate-ring 2.4s ease-out infinite;
pointer-events: none;
}
#${e.buttonId} .cm-ring.r2 { animation-delay: 1.2s; }
#${e.buttonId}.active .cm-ring { display: none; }
/* Pulsing 3-dot mark (closed). Absolutely centered so it stays pinned to the
button's center regardless of the button's display mode (flex on desktop,
block when .mobile-closed) or viewport. */
#${e.buttonId} .cm-dots {
display: flex;
gap: 5px;
position: absolute;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
}
#${e.buttonId} .cm-dot {
width: 7px;
height: 7px;
border-radius: 50%;
background: currentColor;
animation: chattermate-pulse 1.5s ease-in-out infinite;
}
#${e.buttonId} .cm-dot:nth-child(2) { animation-delay: .18s; }
#${e.buttonId} .cm-dot:nth-child(3) { animation-delay: .36s; }
#${e.buttonId}.active .cm-dots { display: none; }
/* Chevron (open) \u2014 absolutely centered, pinned to the button center. */
#${e.buttonId} .cm-chevron {
display: none;
position: absolute;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
font-size: 26px;
font-weight: 700;
line-height: 1;
color: currentColor;
}
#${e.buttonId}.active .cm-chevron { display: block; }
/* Unread badge = number of nudges */
#${e.buttonId} .cm-badge {
position: absolute;
top: -5px;
right: -5px;
min-width: 22px;
height: 22px;
padding: 0 6px;
border-radius: 999px;
background: #FF8A73;
color: #0B0C10;
font: 700 11.5px/1 -apple-system, BlinkMacSystemFont, system-ui, sans-serif;
align-items: center;
justify-content: center;
border: 2px solid #F5F3EE;
box-shadow: 0 4px 12px rgba(0,0,0,0.25);
display: none;
}
#${e.buttonId}.active .cm-badge { display: none; }
#${e.buttonId}.loading .cm-dots,
#${e.buttonId}.loading .cm-chevron { visibility: hidden; }
#${e.buttonId}.loading:after {
content: '';
position: absolute;
width: 16px;
height: 16px;
top: 50%;
left: 50%;
margin: -8px 0 0 -8px;
border: 2px solid rgba(255,255,255,0.3);
border-radius: 50%;
border-top-color: #fff;
animation: chattermate-spin 0.6s linear infinite;
}
/* Search-bar trigger content: hidden unless search-bar mode (below) shows it. */
#${e.buttonId} .cm-search { display: none; }
${t==="search-bar"?`
@media (min-width: 769px) {
/* ===== Search-bar mode: the launcher becomes a search-input-like bar.
Same element, same click/toggle/badge logic. Mobile keeps the bubble. ===== */
#${e.buttonId} {
width: ${e.searchBarWidth}px;
height: 48px;
border-radius: 24px;
padding: 0 16px;
background: #ffffff;
color: #374151;
box-shadow: 0 8px 24px rgba(0, 0, 0, 0.14), inset 0 0 0 1.5px ${e.chatBubbleColor}55;
animation: none;
justify-content: flex-start;
box-sizing: border-box;
}
#${e.buttonId}:hover { transform: scale(1.02); }
#${e.buttonId} .cm-ring,
#${e.buttonId} .cm-dots,
#${e.buttonId} .cm-chevron,
#${e.buttonId}.active .cm-chevron { display: none; }
/* Dark spinner \u2014 the stock white one vanishes on the white bar. */
#${e.buttonId}.loading .cm-search { visibility: hidden; }
#${e.buttonId}.loading:after {
border-color: rgba(0, 0, 0, 0.15);
border-top-color: ${e.chatBubbleColor};
}
#${e.buttonId} .cm-search {
display: flex;
align-items: center;
gap: 10px;
min-width: 0;
width: 100%;
}
#${e.buttonId} .cm-search svg {
flex-shrink: 0;
color: ${e.chatBubbleColor};
}
#${e.buttonId} .cm-search-placeholder {
font: 400 14px/1.2 -apple-system, BlinkMacSystemFont, system-ui, sans-serif;
color: #6b7280;
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
}
}
`:""}
@keyframes chattermate-spin { to { transform: rotate(360deg); } }
@keyframes chattermate-float { 0%, 100% { transform: translateY(0); } 50% { transform: translateY(-5px); } }
@keyframes chattermate-ring { 0% { transform: scale(.85); opacity: .5; } 100% { transform: scale(1.6); opacity: 0; } }
@keyframes chattermate-pulse { 0%, 100% { opacity: .45; } 50% { opacity: 1; } }
@media (prefers-reduced-motion: reduce) {
#${e.buttonId},
#${e.buttonId} .cm-ring,
#${e.buttonId} .cm-dot,
.initiation-orb { animation: none !important; }
/* Open and close in place: no slide, scale or fade for people who asked for less motion. */
#${e.buttonId},
#${e.containerId},
#${e.backdropId} { transition: none !important; }
}
#${e.containerId} {
position: fixed;
/* The window sits above the launcher; when the launcher is moved (via
ChatterMate.init position / setPosition) the window shifts by the same
delta so the two stay together. Mobile is full-screen (media query below)
and is unaffected. */
bottom: ${(e.containerBottom||100)+((e.launcherBottom||20)-20)}px;
${i}: ${(e.containerRight||20)+((e.launcherRight||20)-20)}px;
width: ${e.containerWidth||384}px;
max-width: calc(100vw - 48px);
height: ${e.containerHeight}px;
max-height: calc(100vh - 132px);
background: transparent;
z-index: ${e.zIndex};
overflow: hidden;
/* Animated open/close with slide + fade */
opacity: 0;
visibility: hidden;
transform: translateY(16px) scale(0.98);
transition: opacity 360ms cubic-bezier(0.22, 1, 0.36, 1), transform 360ms cubic-bezier(0.22, 1, 0.36, 1), visibility 0s linear 360ms;
border: none;
padding: 0;
margin: 0;
pointer-events: none;
}
#${e.containerId}.active {
opacity: 1;
visibility: visible;
transform: translateY(0) scale(1);
transition: opacity 420ms cubic-bezier(0.22, 1, 0.36, 1), transform 420ms cubic-bezier(0.22, 1, 0.36, 1);
pointer-events: auto;
}
/* Backdrop element: always in the DOM, so keep it out of the host page's flow
even when it is not in use \u2014 an unstyled div in <body> adds a phantom row to
a flex/grid body layout. */
#${e.backdropId} {
position: fixed;
inset: 0;
display: none;
}
${r?`
/* ===== Ask AI: centered command palette (\u2318K), the pattern people expect from
an "Ask anything" surface \u2014 dimmed page, top-anchored so the eye lands on
the input rather than the middle of the screen. ===== */
#${e.containerId} {
top: 12vh;
bottom: auto;
left: 50%;
right: auto;
width: min(${l.width}px, calc(100vw - 32px));
max-width: none;
/* A cross-document iframe can't size its embedder, so this is a starting
height only: the palette measures its content and posts WIDGET_RESIZE,
which sets an inline height (clamped to this ceiling). height:100% against
an auto-height parent would collapse to the 150px replaced default. */
height: min(${l.height}px, 76vh);
max-height: 76vh;
transform: translate(-50%, -8px) scale(0.98);
z-index: ${e.zIndex+1};
transition: opacity 360ms cubic-bezier(0.22, 1, 0.36, 1),
transform 360ms cubic-bezier(0.22, 1, 0.36, 1),
height 200ms cubic-bezier(0.22, 1, 0.36, 1),
visibility 0s linear 360ms;
}
#${e.containerId}.active {
transform: translate(-50%, 0) scale(1);
transition: opacity 420ms cubic-bezier(0.22, 1, 0.36, 1),
transform 420ms cubic-bezier(0.22, 1, 0.36, 1),
height 200ms cubic-bezier(0.22, 1, 0.36, 1);
}
#${e.containerId} .chattermate-iframe {
border-radius: 16px;
}
#${e.backdropId} {
display: block;
background: rgba(9, 9, 14, 0.45);
backdrop-filter: blur(2px);
z-index: ${e.zIndex};
opacity: 0;
visibility: hidden;
transition: opacity 220ms ease, visibility 0s linear 220ms;
}
#${e.backdropId}.active {
opacity: 1;
visibility: visible;
transition: opacity 220ms ease;
}
/* The palette dims the page and closes on backdrop click / Esc, so the launcher
would just be a stray button floating over the dim. */
#${e.buttonId}.active {
display: none;
}
@media (max-width: 768px) {
/* Full-screen on phones like every other mode. The main mobile block below
pins the edges but never resets transform \u2014 without this the centering
translate would shove the panel half a screen to the left. */
#${e.containerId},
#${e.containerId}.active { transform: none !important; }
#${e.backdropId} { display: none; }
}
`:""}
${n?`
/* ===== Sidebar mode: full-height drawer hugging the ${i} edge ===== */
#${e.containerId} {
top: 0;
bottom: auto;
${i}: 0;
${i==="left"?"right: auto;":"left: auto;"}
width: ${e.sidebarWidth}px;
max-width: 100vw;
height: 100dvh;
max-height: 100dvh;
transform: translateX(${i==="left"?"-100%":"100%"});
box-shadow: ${i==="left"?"":"-"}12px 0 40px rgba(0, 0, 0, 0.12);
}
#${e.containerId}.active {
transform: translateX(0);
}
#${e.containerId} .chattermate-iframe {
border-radius: 0;
}
${h?`
/* The drawer's own header chevron closes it, so keeping the launcher on screen
would just park a duplicate button beside the panel. Hide it while open. */
#${e.buttonId}.active {
display: none;
}
`:`
/* ASK_ANYTHING / AURORA draw no in-panel chevron, and the drawer would paint over
the launcher (later sibling, equal z-index) \u2014 leaving nothing to click. Keep it
reachable: slide it out beside the drawer edge, one layer up. */
#${e.buttonId} {
z-index: ${e.zIndex+1};
transition: transform 0.3s cubic-bezier(.34,1.3,.5,1), opacity 320ms ease,
left 360ms cubic-bezier(0.22, 1, 0.36, 1), right 360ms cubic-bezier(0.22, 1, 0.36, 1);
}
#${e.buttonId}.active {
${i}: ${e.sidebarWidth+20}px;
}
`}
`:""}
/* Clean border around the widget container */
/* The widget panel (inside the iframe) draws its own theme-aware border, so the
container no longer adds one \u2014 avoids a double border (and a white line on dark themes). */
.chattermate-iframe {
width: 100%;
height: 100%;
border: none;
padding: 0;
margin: 0;
display: block;
border-radius: 24px;
/* Rely on corner shadows from container */
box-shadow: none;
}
#chattermate-mobile-close {
display: none;
position: fixed;
top: 20px;
right: 20px;
width: 44px;
height: 44px;
background: transparent;
border: none;
align-items: center;
justify-content: center;
cursor: pointer;
z-index: ${e.zIndex+1};
transition: all 0.3s ease;
}
#chattermate-mobile-topbar {
display: none;
position: fixed;
top: 0;
left: 0;
right: 0;
height: 60px;
background: rgba(255, 255, 255, 0.95);
backdrop-filter: blur(10px);
border-bottom: 1px solid rgba(0, 0, 0, 0.1);
z-index: ${e.zIndex};
align-items: center;
justify-content: space-between;
padding: 0 20px;
box-sizing: border-box;
}
#chattermate-mobile-topbar.active {
display: flex;
}
#chattermate-mobile-topbar .topbar-title {
font-size: 16px;
font-weight: 600;
color: #333;
margin: 0;
}
/* Only ASK_ANYTHING (which has no in-panel header chevron) uses the floating
mobile-close; other styles close via the header chevron, so don't double up. */
.ask-anything-mobile #chattermate-mobile-close.active {
display: flex;
}
@media (max-width: 768px) {
#${e.containerId} {
width: 100vw !important;
height: 100vh !important;
height: 100dvh !important; /* Dynamic viewport height for mobile browsers */
/* Reset the desktop max-width/height clamp \u2014 without this the desktop rule's
max-width: calc(100vw - 48px) / max-height: calc(100vh - 132px) keeps the
window a floating panel instead of going full-screen on mobile. */
max-width: 100vw !important;
max-height: 100vh !important;
max-height: 100dvh !important;
top: 0 !important;
left: 0 !important;
bottom: 0 !important;
right: 0 !important;
border-radius: 0 !important;
position: fixed !important;
margin: 0 !important;
padding: 0 !important;
}
#${e.containerId}.active {
bottom: 0 !important;
}
.chattermate-iframe {
border-radius: 0 !important;
width: 100vw !important;
height: 100vh !important;
height: 100dvh !important; /* Dynamic viewport height for mobile browsers */
position: absolute !important;
top: 0 !important;
left: 0 !important;
margin: 0 !important;
padding: 0 !important;
}
#${e.buttonId} {
display: none;
}
#${e.buttonId}.mobile-closed {
/* flex (not block) keeps the launcher's centering context; the dots/chevron
are absolutely centered regardless, but this keeps it consistent. */
display: flex !important;
width: 56px !important;
height: 56px !important;
/* Respect the configured position on mobile too, so the closed launcher can
clear a fixed bottom nav bar (the main reason to move it up). */
bottom: ${e.launcherBottom}px !important;
${i}: ${e.launcherRight}px !important;
}
.ask-anything-mobile #chattermate-mobile-close.active {
display: flex !important;
}
#chattermate-mobile-close:hover {
opacity: 0.7;
}
/* ASK_ANYTHING style specific mobile topbar */
.ask-anything-mobile #chattermate-mobile-topbar.active {
display: flex !important;
}
.ask-anything-mobile #chattermate-mobile-close.active {
top: 15px !important;
right: 15px !important;
z-index: ${e.zIndex+2} !important;
}
/* When topbar is visible, push iframe down to avoid overlap */
.ask-anything-mobile .chattermate-iframe {
top: 60px !important;
height: calc(100vh - 60px) !important;
height: calc(100dvh - 60px) !important;
}
}
@media (min-width: 769px) {
#chattermate-mobile-close {
display: none !important;
}
}
/* Chat Initiation Message Styles */
#${e.initiationMessageId} {
position: fixed !important;
/* Sit above the launcher (+12px gap) and align to its edge on the active side,
so it never overlaps the icon regardless of the configured position/mode. */
bottom: ${(e.launcherBottom||20)+o+12}px !important;
${i}: ${e.launcherRight||20}px !important;
max-width: 260px !important;
background: white !important;
padding: 12px 36px 12px 14px !important;
border-radius: 14px !important;
box-shadow: 0 3px 16px rgba(0, 0, 0, 0.1) !important;
z-index: ${e.zIndex-1} !important;
cursor: pointer !important;
opacity: 0;
visibility: hidden;
transform: translateY(10px) scale(0.95);
transition: all 0.4s cubic-bezier(0.22, 1, 0.36, 1) !important;
font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, 'Helvetica Neue', Arial, sans-serif !important;
font-size: 14px !important;
box-sizing: border-box !important;
margin: 0 !important;
border: none !important;
display: block !important;
width: auto !important;
height: auto !important;
min-width: 0 !important;
min-height: 0 !important;
max-height: none !important;
line-height: 1.4 !important;
text-align: left !important;
vertical-align: baseline !important;
overflow: visible !important;
}
/* Clamp the nudge text to 4 lines with an ellipsis so a long welcome/initiation
message can never balloon the bubble over the page or into the launcher.
Applied to the text node only, so the orb (left:-34px) is never clipped. */
#${e.initiationMessageId} .initiation-message-text {
margin: 0 !important;
display: -webkit-box !important;
-webkit-line-clamp: 4 !important;
-webkit-box-orient: vertical !important;
overflow: hidden !important;
}
/* Siri-style orb avatar beside the nudge (design comp) */
.initiation-orb {
position: absolute !important;
left: -34px !important;
bottom: 2px !important;
width: 26px !important;
height: 26px !important;
border-radius: 50% !important;
background: conic-gradient(from 0deg, #C9F24E, #9D8CFF, #5FE3D6, #FF8A73, #C9F24E) !important;
box-shadow: 0 4px 14px rgba(157, 140, 255, 0.4) !important;
animation: chattermate-orb-spin 6s linear infinite !important;
z-index: 1 !important;
}
@keyframes chattermate-orb-spin { to { transform: rotate(360deg); } }
${i==="left"?`
/* On the left edge the orb (which protrudes 34px past the bubble) would clip
off-screen \u2014 mirror it to the bubble's page-facing side. */
.initiation-orb {
left: auto !important;
right: -34px !important;
}
`:""}
#${e.initiationMessageId}.show {
opacity: 1;
visibility: visible;
transform: translateY(0) scale(1);
animation: chattermate-bounce-in 0.6s cubic-bezier(0.68, -0.55, 0.265, 1.55);
}
@keyframes chattermate-bounce-in {
0% {
opacity: 0;
transform: translateY(20px) scale(0.8);
}
50% {
transform: translateY(-5px) scale(1.02);
}
100% {
opacity: 1;
transform: translateY(0) scale(1);
}
}
#${e.initiationMessageId}:hover {
transform: translateY(-2px) scale(1.02);
box-shadow: 0 5px 20px rgba(0, 0, 0, 0.14);
}
#${e.initiationMessageId}::after {
content: '' !important;
position: absolute !important;
bottom: -7px !important;
${i}: 30px !important;
width: 14px !important;
height: 14px !important;
min-width: 14px !important;
min-height: 14px !important;
max-width: 14px !important;
max-height: 14px !important;
background: white !important;
transform: rotate(45deg) !important;
box-shadow: 3px 3px 5px rgba(0, 0, 0, 0.06) !important;
clip-path: polygon(0 0, 100% 0, 100% 100%) !important;
border: none !important;
margin: 0 !important;
padding: 0 !important;
box-sizing: border-box !important;
z-index: -1 !important;
}
.initiation-message-text {
font-size: 13px !important;
line-height: 1.4 !important;
color: #374151 !important;
margin: 0 !important;
padding: 0 4px 0 0 !important;
position: relative !important;
z-index: 1 !important;
min-height: 18px !important;
box-sizing: border-box !important;
border: none !important;
background: transparent !important;
display: block !important;
width: 100% !important;
height: auto !important;
max-width: none !important;
max-height: none !important;
text-align: left !important;
vertical-align: baseline !important;
font-weight: normal !important;
font-style: normal !important;
text-decoration: none !important;
text-transform: none !important;
letter-spacing: normal !important;
word-spacing: normal !important;
white-space: normal !important;
overflow-wrap: break-word !important;
word-wrap: break-word !important;
}
.initiation-message-text::after {
content: '|';
animation: blink 1s step-end infinite;
margin-left: 2px;
color: ${e.chatBubbleColor};
font-weight: 500;
}
.initiation-message-text.typing-complete::after {
display: none;
}
@keyframes blink {
0%, 50% { opacity: 1; }
51%, 100% { opacity: 0; }
}
.initiation-close {
position: absolute !important;
top: 10px !important;
right: 10px !important;
width: 20px !important;
height: 20px !important;
min-width: 20px !important;
min-height: 20px !important;
max-width: 20px !important;
max-height: 20px !important;
background: rgba(0, 0, 0, 0.04) !important;
border: none !important;
border-radius: 5px !important;
cursor: pointer !important;
opacity: 0.5 !important;
transition: all 0.2s ease !important;
z-index: 2 !important;
display: flex !important;
align-items: center !important;
justify-content: center !important;
padding: 0 !important;
margin: 0 !important;
box-sizing: border-box !important;
outline: none !important;
box-shadow: none !important;
text-decoration: none !important;
font-size: 0 !important;
line-height: 0 !important;
overflow: hidden !important;
flex-shrink: 0 !important;
}
.initiation-close:hover {
opacity: 1 !important;
background: rgba(0, 0, 0, 0.08) !important;
transform: scale(1.05) !important;
}
.initiation-close::before,
.initiation-close::after {
content: '' !important;
position: absolute !important;
width: 9px !important;
height: 1.5px !important;
min-width: 9px !important;
min-height: 1.5px !important;
max-width: 9px !important;
max-height: 1.5px !important;
background: #4a5568 !important;
border-radius: 1px !important;
top: 50% !important;
left: 50% !important;
margin: -0.75px 0 0 -4.5px !important;
padding: 0 !important;
border: none !important;
box-sizing: border-box !important;
}
.initiation-close::before {
transform: rotate(45deg) !important;
}
.initiation-close::after {
transform: rotate(-45deg) !important;
}
@media (max-width: 768px) {
#${e.initiationMessageId} {
display: none !important;
}
}
/* Error UI Styles */
.chattermate-error-ui {
width: 100%;
height: 100%;
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
background: linear-gradient(135deg, #f8fafc 0%, #f1f5f9 100%);
border-radius: 24px;
overflow: hidden;
position: relative;
}
.chattermate-error-ui::before {
content: '';
position: absolute;
top: 0;
left: 0;
right: 0;
bottom: 0;
background:
radial-gradient(circle at 20% 30%, rgba(99, 102, 241, 0.08) 0%, transparent 50%),
radial-gradient(circle at 80% 70%, rgba(168, 85, 247, 0.06) 0%, transparent 50%);
pointer-events: none;
}
.chattermate-error-card {
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
padding: 32px 24px;
text-align: center;
position: relative;
z-index: 1;
max-width: 90%;
}
.chattermate-error-close {
position: absolute;
top: 12px;
right: 12px;
z-index: 2;
width: 36px;
height: 36px;
display: flex;
align-items: center;
justify-content: center;
border: none;
border-radius: 50%;
background: rgba(120, 120, 140, 0.12);
color: #4b5563;
font-size: 22px;
line-height: 1;
cursor: pointer;
transition: background 0.15s ease;
}
.chattermate-error-close:hover {
background: rgba(120, 120, 140, 0.22);
}
.chattermate-error-icon-wrapper {
display: flex;
align-items: center;
justify-content: center;
width: 72px;
height: 72px;
background: linear-gradient(135deg, #e0e7ff 0%, #c7d2fe 100%);
border-radius: 20px;
margin-bottom: 20px;
box-shadow: 0 8px 24px rgba(99, 102, 241, 0.15);
}
.chattermate-error-icon {
width: 36px;
height: 36px;
color: #6366f1;
}
.chattermate-error-title {
font-size: 20px;
font-weight: 600;
color: #1e293b;
margin: 0 0 12px 0;
letter-spacing: -0.01em;
font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, 'Helvetica Neue', Arial, sans-serif;
}
.chattermate-error-message {
font-size: 14px;
line-height: 1.6;
color: #64748b;
margin: 0 0 24px 0;
max-width: 280px;
font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, 'Helvetica Neue', Arial, sans-serif;
}
.chattermate-error-footer {
display: flex;
align-items: center;
justify-content: center;
gap: 6px;
font-size: 12px;
color: #94a3b8;
opacity: 0.8;
font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, 'Helvetica Neue', Arial, sans-serif;
}
.chattermate-error-footer-link {
color: inherit;
text-decoration: none;
cursor: pointer;
}
.chattermate-error-footer-link:hover {
text-decoration: underline;
}
@media (max-width: 768px) {
.chattermate-error-ui {
border-radius: 0;
}
.chattermate-error-card {
padding: 24px 20px;
}
.chattermate-error-icon-wrapper {
width: 64px;
height: 64px;
border-radius: 16px;
}
.chattermate-error-icon {
width: 32px;
height: 32px;
}
.chattermate-error-title {
font-size: 18px;
}
.chattermate-error-message {
font-size: 13px;
max-width: 260px;
}
}
${e.launcher?"":`
/* Launcher hidden by config \u2014 the site opens the chat with its own trigger or
the JS API. Last in the sheet so it also beats the mobile .mobile-closed
re-show (display: flex !important at equal specificity). */
#${e.buttonId}, #${e.buttonId}.mobile-closed { display: none !important; }
`}
`;let f=document.getElementById("chattermate-styles");f&&f.remove(),document.head.appendChild(w),vt()}function vt(){let t=document.getElementById(e.buttonId);if(!t)return;let n=t.querySelector(".cm-search-placeholder");n&&n.textContent!==e.searchPlaceholder&&(n.textContent=e.searchPlaceholder)}function C(t){if(typeof t!="string")return null;let n=t.trim();return!n||n==="undefined"||n==="null"?null:n}function dt(){return C(window.chattermateToken)||C(localStorage.getItem(e.tokenKey))}function ht(t){let n=C(t);if(!n)return null;let i=n.split(".")[1];if(!i)return null;try{let o=JSON.parse(atob(i.replace(/-/g,"+").replace(/_/g,"/")));return o.sub||o.customer_id||null}catch(o){return null}}function tt(t){t&&localStorage.setItem(e.tokenKey,t)}function H(){localStorage.removeItem(e.tokenKey)}function U(){return window.innerWidth<=768}function zt(t){return t?t.replace(/\uFFFD/g,"").replace(/[��]/g,"").replace(/[\x00-\x1F\x7F-\x9F]/g,"").trim():""}function Bt(){if(!e.chatInitiationMessages||e.chatInitiationMessages.length===0)return null;let t=Math.floor(Math.random()*e.chatInitiationMessages.length),n=e.chatInitiationMessages[t];return n?zt(n):null}function Nt(){return U()||!e.launcher||!e.chatInitiationMessages||e.chatInitiationMessages.length===0?!1:!sessionStorage.getItem(e.initiationShownKey)}function pt(){sessionStorage.setItem(e.initiationShownKey,"true")}function Pt(){let t=Bt();if(!t)return null;let n=document.createElement("div");return n.id=e.initiationMessageId,n.innerHTML=`
<span class="initiation-orb"></span>
<button class="initiation-close" aria-label="Close"></button>
<p class="initiation-message-text"></p>
`,n.dataset.fullMessage=t,n}function Rt(t,n,i=50){let o=t.querySelector(".initiation-message-text");if(!o)return;let h=0,r=setInterval(()=>{h<n.length?(o.textContent+=n.charAt(h),h++):(clearInterval(r),o.classList.add("typing-complete"),t.typeInterval=null)},i);t.typeInterval=r}function Ft(t,n){if(!t||!Nt())return;document.body.appendChild(t),setTimeout(()=>{t.classList.add("show"),setTimeout(()=>{let o=t.dataset.fullMessage;o&&Rt(t,o,40)},300)},1500),t.addEventListener("click",o=>{o.target.classList.contains("initiation-close")||(t.typeInterval&&clearInterval(t.typeInterval),mt(t),n(),pt())});let i=t.querySelector(".initiation-close");i&&i.addEventListener("click",o=>{o.stopPropagation(),t.typeInterval&&clearInterval(t.typeInterval),mt(t),pt()})}function mt(t){t&&(t.classList.remove("show"),setTimeout(()=>{t.parentNode&&t.parentNode.removeChild(t)},400))}function ut(){y=!1,W();let t=document.createElement("div");t.id=e.buttonId,t.classList.add("chattermate-pending"),t.innerHTML=`
<span class="cm-ring"></span>
<span class="cm-ring r2"></span>
<div class="cm-dots"><span class="cm-dot"></span><span class="cm-dot"></span><span class="cm-dot"></span></div>
<span class="cm-chevron">&#8964;</span>
<span class="cm-search">
<svg width="18" height="18" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><circle cx="11" cy="11" r="7"></circle><path d="M21 21l-4.35-4.35"></path></svg>
<span class="cm-search-placeholder"></span>
</span>
<span class="cm-badge"></span>
`,E=setTimeout(F,8e3);let n=document.createElement("div");n.id=e.containerId;let i=document.createElement("div");i.id="chattermate-mobile-close",i.innerHTML=`
<svg width="24" height="24" viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M5 12H19" stroke="#666" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"/>
</svg>
`;let o=document.createElement("div");o.id="chattermate-mobile-topbar",o.innerHTML=`
<h3 class="topbar-title">Chat</h3>
<div style="width: 44px;"></div>
`;let h=document.createElement("div");h.id=e.backdropId,document.body.appendChild(t),document.body.appendChild(h),document.body.appendChild(n),document.body.appendChild(i),document.body.appendChild(o),O(),vt();let r=!1,l=null,w=!1,f=null;function b(){r=!r,n.classList.toggle("active"),h.classList.toggle("active",r),t.classList.toggle("active"),i.classList.toggle("active"),r&&(e.hasOpened=!0,e.unreadCount=0),l&&l.contentWindow&&l.contentWindow.postMessage({type:"WIDGET_VISIBILITY",open:r},"*"),O(),r&&f&&(mt(f),f=null,pt()),U()?r?(t.classList.remove("mobile-closed"),t.style.animation=""):(t.classList.add("mobile-closed"),t.style.animation="chattermate-float 4s ease-in-out infinite",o.classList.remove("active"),document.body.classList.remove("ask-anything-mobile")):r&&i.classList.remove("active"),r&&l&&l.contentWindow.postMessage({type:"SCROLL_TO_BOTTOM"},"*"),_(r?"open":"close")}let K=null,bt=!1;function Yt(a){let s=String(a||"").slice(0,2e3);s&&(bt&&l&&l.contentWindow?l.contentWindow.postMessage({type:"PREFILL_MESSAGE",text:s},"*"):K=s)}let D=0;function Ct(){for(D++;n.firstChild;)n.removeChild(n.firstChild);l=null,g=null,T=null,bt=!1,st=!1,K=null,w=!1,t.classList.remove("loading"),P=0,Z()}function Gt(){r&&b(),Ct(),e.unreadCount=0,e.hasOpened=!1,O(),et()}function jt(){r&&b(),Ct(),window.removeEventListener("resize",Tt),window.removeEventListener("message",St),f&&(f.typeInterval&&clearInterval(f.typeInterval),ft(f),f=null),[t,h,n,i,o].forEach(ft),ft(document.getElementById("chattermate-styles")),document.body.classList.remove("ask-anything-mobile"),ct=!1,E&&(clearTimeout(E),E=null),lt.length=0,e.unreadCount=0,e.hasOpened=!1,c=null,R.length=0,X=!1,y=!0}function At(a){let s=document.createElement("div");s.className="chattermate-error-ui";let I=document.createElement("div");I.className="chattermate-error-card";let v=document.createElement("button");v.type="button",v.className="chattermate-error-close",v.setAttribute("aria-label","Close chat"),v.textContent="\xD7",v.addEventListener("click",function(){r&&b()}),s.appendChild(v);let u=document.createElement("div");u.className="chattermate-error-icon-wrapper";let p=document.createElementNS("http://www.w3.org/2000/svg","svg");p.setAttribute("class","chattermate-error-icon"),p.setAttribute("viewBox","0 0 24 24"),p.setAttribute("fill","none"),p.setAttribute("stroke","currentColor"),p.setAttribute("stroke-width","1.5");let k=document.createElementNS("http://www.w3.org/2000/svg","path");k.setAttribute("d","M12 22s8-4 8-10V5l-8-3-8 3v7c0 6 8 10 8 10z");let $=document.createElementNS("http://www.w3.org/2000/svg","path");$.setAttribute("d","M9 12l2 2 4-4"),p.appendChild(k),p.appendChild($),u.appendChild(p);let A=document.createElement("h2");A.className="chattermate-error-title",A.textContent="Chat Unavailable";let yt=document.createElement("p");yt.className="chattermate-error-message",yt.textContent=a;let it=document.createElement("div");it.className="chattermate-error-footer";let L=document.createElementNS("http://www.w3.org/2000/svg","svg");L.setAttribute("width","14"),L.setAttribute("height","14"),L.setAttribute("viewBox","0 0 60 60"),L.setAttribute("fill","none");let G=document.createElementNS("http://www.w3.org/2000/svg","path");G.setAttribute("d","M18 12 H42 A6 6 0 0 1 48 18 V42 A6 6 0 0 1 42 48 H18 A6 6 0 0 1 12 42 V18 A6 6 0 0 1 18 12 Z M17 30 a4 4 0 1 0 8 0 a4 4 0 1 0 -8 0 Z M26 30 a4 4 0 1 0 8 0 a4 4 0 1 0 -8 0 Z M35 30 a4 4 0 1 0 8 0 a4 4 0 1 0 -8 0 Z"),G.setAttribute("fill-rule","evenodd"),G.setAttribute("fill","currentColor"),G.setAttribute("opacity","0.6"),L.appendChild(G);let z=document.createElement("a");return z.href="https://chattermate.chat",z.target="_blank",z.rel="noopener noreferrer",z.className="chattermate-error-footer-link",z.textContent="Powered by ChatterMate",it.appendChild(L),it.appendChild(z),I.appendChild(u),I.appendChild(A),I.appendChild(yt),I.appendChild(it),s.appendChild(I),s}function et(){return wt(this,null,function*(){if(w||l)return;let a=D;try{w=!0,t.classList.add("loading");let s=dt(),I=`${e.baseUrl}/widgets/${window.chattermateId}/data?widget_id=${window.chattermateId}`,v={method:"GET",mode:"cors",headers:s?{Authorization:`Bearer ${s}`}:{}};fetch(I,v).then(u=>wt(null,null,function*(){if(a!==D)return null;if(u.status===401)try{let k=(yield u.json()).detail;if(k&&k.code==="identity_expired")return t.classList.remove("loading"),_("identityExpired"),Vt(),null;let $=typeof k=="string"?k:"";if($.includes("generate-token")||$.includes("API key")||$.includes("Token must be obtained")){t.classList.remove("loading"),H();let A=At("This chat widget is not currently configured. Please contact the website administrator to enable chat support.");return n.appendChild(A),F(),null}}catch(p){}if(!u.ok)throw new Error("HTTP error! status: "+u.status);return u.text()})).then(u=>{u!==null&&a===D&&(l=document.createElement("iframe"),l.className="chattermate-iframe",l.title="Chat",l.srcdoc=u,l.addEventListener("load",function(){bt=!0,l.contentWindow.postM Line truncated