PluginProbe
MxChat – AI Chatbot & Content Generation for WordPress / 1.5.7
MxChat – AI Chatbot & Content Generation for WordPress v1.5.7
3.2.21 3.2.20 3.2.19 3.2.18 3.2.17 3.2.16 3.2.15 3.2.14 3.2.12 3.2.13 3.2.11 3.2.10 3.2.9 3.2.8 3.2.7 3.2.6 3.2.5 3.2.4 3.2.3 3.2.2 3.2.1 2.0.3 2.0.4 2.0.5 2.0.6 All 152 releases
← All changes | js/chat-script.js +121 -377 2.0.51.5.7 View file →
@@ -1,8 +1,8 @@
1 1 jQuery(document).ready(function($) {
2 2 //console.log('mxchatChat object:', mxchatChat);
3 3 //console.log('Link Target Toggle Value:', mxchatChat.link_target_toggle);
4 -// Add these variables at the top of your chat-script.js file
4 +
5 5 const toolbarIconColor = mxchatChat.toolbar_icon_color || '#212121';
6 6
7 7 // Initialize color settings
8 8 var userMessageBgColor = mxchatChat.user_message_bg_color;
@@ -14,11 +14,9 @@
14 14 var liveAgentMessageFontColor = mxchatChat.live_agent_message_font_color;
15 15
16 16
17 17 var linkTarget = mxchatChat.link_target_toggle === 'on' ? '_blank' : '_self';
18 - let lastSeenMessageId = '';
19 - let notificationCheckInterval;
20 - let notificationBadge;
18 + var lastSeenMessageId = '';
21 19 // Initialize session ID
22 20 var sessionId = getChatSession();
23 21
24 22 let pollingInterval; // Variable to store the interval ID
@@ -28,107 +26,10 @@
28 26 let activePdfFile = null;
29 27 let activeWordFile = null;
30 28
31 29
32 -// Function to create and append notification badge
33 -// Function to create and append notification badge
34 -function createNotificationBadge() {
35 - console.log("Creating notification badge...");
36 - const chatButton = document.getElementById('floating-chatbot-button');
37 - console.log("Chat button found:", !!chatButton);
38 -
39 - if (!chatButton) return;
40 30
41 - // Remove any existing badge first
42 - const existingBadge = chatButton.querySelector('.chat-notification-badge');
43 - if (existingBadge) {
44 - console.log("Removing existing badge");
45 - existingBadge.remove();
46 - }
47 31
48 - notificationBadge = document.createElement('div');
49 - notificationBadge.className = 'chat-notification-badge';
50 - notificationBadge.style.cssText = `
51 - display: none;
52 - position: absolute;
53 - top: -5px;
54 - right: -5px;
55 - background-color: red;
56 - color: white;
57 - border-radius: 50%;
58 - padding: 4px 8px;
59 - font-size: 12px;
60 - font-weight: bold;
61 - z-index: 10001;
62 - `;
63 - chatButton.style.position = 'relative';
64 - chatButton.appendChild(notificationBadge);
65 -
66 - console.log("Notification badge created and appended:", {
67 - exists: !!notificationBadge,
68 - parent: notificationBadge?.parentNode?.id,
69 - display: notificationBadge?.style?.display
70 - });
71 -}
72 -
73 -// Function to check for new messages
74 -function checkForNewMessages() {
75 - const sessionId = getChatSession();
76 - const chatPersistenceEnabled = mxchatChat.chat_persistence_toggle === 'on';
77 -
78 - if (!chatPersistenceEnabled) return;
79 -
80 - $.ajax({
81 - url: mxchatChat.ajax_url,
82 - type: 'POST',
83 - data: {
84 - action: 'mxchat_check_new_messages',
85 - session_id: sessionId,
86 - last_seen_id: lastSeenMessageId,
87 - nonce: mxchatChat.nonce
88 - },
89 - success: function(response) {
90 - if (response.success && response.data.hasNewMessages) {
91 - showNotification();
92 - }
93 - }
94 - });
95 -}
96 -
97 -// Function to show notification
98 -function showNotification() {
99 - const badge = document.getElementById('chat-notification-badge');
100 - if (badge && $('#floating-chatbot').hasClass('hidden')) {
101 - badge.style.display = 'block';
102 - badge.textContent = '1';
103 - }
104 -}
105 -
106 -function hideNotification() {
107 - const badge = document.getElementById('chat-notification-badge');
108 - if (badge) {
109 - badge.style.display = 'none';
110 - }
111 -}
112 -// Function to start notification checking
113 -function startNotificationChecking() {
114 - const chatPersistenceEnabled = mxchatChat.chat_persistence_toggle === 'on';
115 - if (!chatPersistenceEnabled) return;
116 -
117 - createNotificationBadge();
118 - notificationCheckInterval = setInterval(checkForNewMessages, 30000); // Check every 30 seconds
119 -}
120 -
121 -// Function to stop notification checking
122 -function stopNotificationChecking() {
123 - if (notificationCheckInterval) {
124 - clearInterval(notificationCheckInterval);
125 - }
126 -}
127 -
128 -
129 -
130 -
131 32 function getChatSession() {
132 33 var sessionId = getCookie('mxchat_session_id');
133 34 //console.log("Session ID retrieved from cookie: ", sessionId);
134 35
@@ -256,48 +157,24 @@
256 157 sendMessageToChatbot(question);
257 158 });
258 159
259 160
260 -// Add this new function to handle markdown headers
261 -function formatMarkdownHeaders(text) {
262 - // Handle h1 to h6 headers
263 - return text.replace(/^(#{1,6})\s(.+)$/gm, function(match, hashes, content) {
264 - const level = hashes.length;
265 - return `<h${level} class="chat-heading">${content}</h${level}>`;
266 - });
267 -}
268 -
269 -// Update the linkify function to handle both URLs and markdown
270 -// Modified linkify function that only processes URLs in user content
161 +// Use the linkTarget in your linkify function
271 162 function linkify(inputText) {
272 - if (!inputText) return '';
273 -
274 - // Process markdown headers
275 - let processedText = formatMarkdownHeaders(inputText);
276 -
277 - // Process markdown links
278 - const markdownLinkPattern = /\[([^\]]+)\]\((https?:\/\/[^\s]+)\)/g;
279 - processedText = processedText.replace(markdownLinkPattern, (match, text, url) => {
280 - const safeUrl = encodeURI(url);
281 - const safeText = sanitizeUserInput(text);
282 - return `<a href="${safeUrl}" target="${linkTarget}">${safeText}</a>`;
283 - });
163 + // Check for already linked URLs and skip them
164 + // We use negative lookaheads to skip anything already in an <a> tag
165 + var markdownLinkPattern = /\[([^\]]+)\]\((https?:\/\/[^\s]+)\)/g;
166 + var replacedText = inputText.replace(markdownLinkPattern, '<a href="$2" target="' + linkTarget + '">$1</a>');
284 167
285 - // Process standalone URLs
286 - const urlPattern = /(^|[^">])(https?:\/\/[^\s<]+)/gim;
287 - processedText = processedText.replace(urlPattern, (match, prefix, url) => {
288 - const safeUrl = encodeURI(url);
289 - return `${prefix}<a href="${safeUrl}" target="${linkTarget}">${url}</a>`;
290 - });
168 + // Replace standalone URLs not already in an <a> tag
169 + var urlPattern = /(^|[^">])(https?:\/\/[^\s<]+)/gim;
170 + replacedText = replacedText.replace(urlPattern, '$1<a href="$2" target="' + linkTarget + '">$2</a>');
291 171
292 - // Process www. URLs
293 - const wwwPattern = /(^|[^">])(www\.[\S]+(\b|$))(?![^<]*<\/a>)/gim;
294 - processedText = processedText.replace(wwwPattern, (match, prefix, url) => {
295 - const safeUrl = encodeURI(`http://${url}`);
296 - return `${prefix}<a href="${safeUrl}" target="${linkTarget}">${url}</a>`;
297 - });
172 + // Replace "www." prefixed URLs not already in an <a> tag
173 + var wwwPattern = /(^|[^">])(www\.[\S]+(\b|$))(?![^<]*<\/a>)/gim;
174 + replacedText = replacedText.replace(wwwPattern, '$1<a href="http://$2" target="' + linkTarget + '">$2</a>');
298 175
299 - return processedText;
176 + return replacedText;
300 177 }
301 178
302 179
303 180 function scrollElementToTop(element) {
@@ -344,17 +221,19 @@
344 221 return text.replace(/\*\*(.*?)\*\*/g, '<strong>$1</strong>');
345 222 }
346 223
347 224 // Function to convert newline characters to HTML line breaks and handle paragraph spacing
348 -function convertNewlinesToBreaks(text) {
349 - // Split the text into paragraphs (marked by double newlines or multiple <br> tags)
350 - const paragraphs = text.split(/(?:\n\n|\<br\>\s*\<br\>)/g);
351 -
352 - // Wrap each paragraph in <p> tags
353 - return paragraphs
354 - .map(para => `<p>${para.trim()}</p>`)
355 - .join('');
356 -}
225 + function convertNewlinesToBreaks(text) {
226 + var lines = text.split('\n');
227 + var formattedText = '';
228 +
229 + for (var i = 0; i < lines.length; i++) {
230 + formattedText += lines[i] + '<br>';
231 + }
232 +
233 + return formattedText;
234 + }
235 +
357 236 // Copy to clipboard function
358 237 // Function to copy text to clipboard
359 238 function copyToClipboard(text) {
360 239 var tempInput = $('<input>');
@@ -379,8 +258,10 @@
379 258 }
380 259 }
381 260
382 261 function callMxChat(message, callback) {
262 + //console.log("Sending message to chatbot:", message);
263 +
383 264 $.ajax({
384 265 url: mxchatChat.ajax_url,
385 266 type: 'POST',
386 267 dataType: 'json',
@@ -390,38 +271,41 @@
390 271 session_id: getChatSession(),
391 272 nonce: mxchatChat.nonce
392 273 },
393 274 success: function(response) {
394 - // Existing chat mode check
275 + //console.log("callMxChat response:", response);
276 +
277 + // Check for chat_mode in the response
395 278 if (response.chat_mode) {
396 279 updateChatModeIndicator(response.chat_mode);
397 280 }
281 + // Also check in fallbackResponse if exists
398 282 else if (response.fallbackResponse && response.fallbackResponse.chat_mode) {
399 283 updateChatModeIndicator(response.fallbackResponse.chat_mode);
400 284 }
401 -
402 285 // Add PDF filename handling
403 286 if (response.data && response.data.filename) {
404 287 showActivePdf(response.data.filename);
405 288 activePdfFile = response.data.filename;
406 289 }
407 -
408 - // Add redirect check here
290 + // Add redirect check here
409 291 if (response.redirect_url) {
292 + // Show the message first
410 293 let responseText = response.text || '';
411 294 if (responseText) {
412 295 replaceLastMessage("bot", responseText);
413 296 }
297 + // Then redirect after a short delay
414 298 setTimeout(() => {
415 299 window.location.href = response.redirect_url;
416 300 }, 1500);
417 - return;
301 + return; // Exit early since we're redirecting
418 302 }
419 303
420 -
421 304 // Check for live agent response
422 305 if (response.success && response.data && response.data.status === 'waiting_for_agent') {
423 306 updateChatModeIndicator('agent');
307 + // Do not replace the thinking dots; just wait for the agent's actual response
424 308 return;
425 309 }
426 310
427 311 // Handle other responses
@@ -428,33 +312,31 @@
428 312 let responseText = response.text || '';
429 313 let responseHtml = response.html || '';
430 314 let responseMessage = response.message || '';
431 315
316 + // Check for mode change in text response
432 317 if (responseText === 'You are now chatting with the AI chatbot.') {
433 318 updateChatModeIndicator('ai');
434 319 }
435 320
436 - // Handle the message and show notification if chat is hidden
437 - if (responseText || responseHtml || responseMessage) {
438 - // Update the messages as before
439 - if (responseText && responseHtml) {
440 - replaceLastMessage("bot", responseText, responseHtml);
441 - } else if (responseText) {
442 - replaceLastMessage("bot", responseText);
443 - } else if (responseHtml) {
444 - replaceLastMessage("bot", "", responseHtml);
445 - } else if (responseMessage) {
446 - replaceLastMessage("bot", responseMessage);
447 - }
448 -
449 - // Check if chat is hidden and show notification
450 - if ($('#floating-chatbot').hasClass('hidden')) {
451 - const badge = $('#chat-notification-badge');
452 - if (badge.length) {
453 - badge.show();
454 - }
455 - }
456 - } else {
321 + // For product card or chatbot responses with HTML
322 + if (responseText && responseHtml) {
323 + replaceLastMessage("bot", responseText, responseHtml);
324 + }
325 + // For regular chatbot responses with just text
326 + else if (responseText) {
327 + replaceLastMessage("bot", responseText);
328 + }
329 + // For responses with only HTML (like product cards)
330 + else if (responseHtml) {
331 + replaceLastMessage("bot", "", responseHtml);
332 + }
333 + // For legacy message format
334 + else if (responseMessage) {
335 + replaceLastMessage("bot", responseMessage);
336 + }
337 + // Fallback error case
338 + else {
457 339 console.error("Unexpected response format:", response);
458 340 replaceLastMessage("bot", "I'm sorry, something went wrong.");
459 341 }
460 342
@@ -462,22 +344,17 @@
462 344 lastSeenMessageId = response.message_id;
463 345 }
464 346 },
465 347 error: function(xhr, status, error) {
348 + //console.log("Error communicating with the server:", xhr.status, error);
466 349 replaceLastMessage("bot", "An unexpected error occurred.");
467 350 }
468 351 });
469 352 }
470 353
471 -// Sanitize only user input
472 -function sanitizeUserInput(text) {
473 - const div = document.createElement('div');
474 - div.textContent = text;
475 - return div.innerHTML;
476 -}
354 +function appendMessage(sender, messageText = '', messageHtml = '', images = [], isTemporary = false) {
355 + //console.log("Appending message. Sender:", sender, "Content:", messageText);
477 356
478 -// Modified appendMessage function that only sanitizes user content
479 -function appendMessage(sender, messageText = '', messageHtml = '', images = [], isTemporary = false) {
480 357 try {
481 358 // Determine styles based on sender type
482 359 let messageClass, bgColor, fontColor;
483 360
@@ -484,15 +361,13 @@
484 361 if (sender === "user") {
485 362 messageClass = "user-message";
486 363 bgColor = userMessageBgColor;
487 364 fontColor = userMessageFontColor;
488 - // Only sanitize user input
489 - messageText = sanitizeUserInput(messageText);
490 - } else if (sender === "agent") {
491 - messageClass = "agent-message";
492 - bgColor = liveAgentMessageBgColor;
493 - fontColor = liveAgentMessageFontColor;
494 - } else {
365 + } else if (sender === "agent") {
366 + messageClass = "agent-message";
367 + bgColor = liveAgentMessageBgColor;
368 + fontColor = liveAgentMessageFontColor;
369 + } else {
495 370 messageClass = "bot-message";
496 371 bgColor = botMessageBgColor;
497 372 fontColor = botMessageFontColor;
498 373 }
@@ -501,35 +376,22 @@
501 376 .addClass(messageClass)
502 377 .css({
503 378 'background': bgColor,
504 379 'color': fontColor,
505 - 'margin-bottom': '1em'
506 380 });
507 381
508 - // Process the message content based on sender
509 - let fullMessage;
510 - if (sender === "user") {
511 - // For user messages, apply linkify after sanitization
512 - fullMessage = linkify(formatBoldText(convertNewlinesToBreaks(formatCodeBlocks(messageText))));
513 - } else {
514 - // For bot/agent messages, preserve HTML
515 - fullMessage = messageText;
516 - }
382 + // Format and process the message content
383 + let fullMessage = linkify(formatBoldText(convertNewlinesToBreaks(formatCodeBlocks(messageText))));
517 384
518 385 // Add images if provided
519 386 if (images && images.length > 0) {
520 387 fullMessage += '<div class="image-gallery">';
521 388 images.forEach(img => {
522 - // Ensure image URLs and titles are properly escaped
523 - const safeTitle = sanitizeUserInput(img.title);
524 - const safeUrl = encodeURI(img.image_url);
525 - const safeThumbnail = encodeURI(img.thumbnail_url);
526 -
527 389 fullMessage += `
528 390 <div style="margin-bottom: 10px;">
529 - <strong>${safeTitle}</strong><br>
530 - <a href="${safeUrl}" target="_blank">
531 - <img src="${safeThumbnail}" alt="${safeTitle}" style="max-width: 100px; height: auto; margin: 5px;" />
391 + <strong>${img.title}</strong><br>
392 + <a href="${img.image_url}" target="_blank">
393 + <img src="${img.thumbnail_url}" alt="${img.title}" style="max-width: 100px; height: auto; margin: 5px;" />
532 394 </a>
533 395 </div>`;
534 396 });
535 397 fullMessage += '</div>';
@@ -535,20 +397,23 @@
535 397 fullMessage += '</div>';
536 398 }
537 399
538 400 // Append HTML content if provided
539 - if (messageHtml && sender !== "user") {
401 + if (messageHtml) {
540 402 fullMessage += '<br><br>' + messageHtml;
541 403 }
542 404
543 405 messageDiv.html(fullMessage);
544 406
407 + // Add a class for temporary messages if needed
545 408 if (isTemporary) {
546 409 messageDiv.addClass('temporary-message');
547 410 }
548 411
549 - messageDiv.hide().appendTo('#chat-box').fadeIn(300, function() {
412 + // Append the message to the chat box
413 + messageDiv.hide().appendTo('#chat-box').fadeIn(300, function () {
550 414 if (sender === "bot") {
415 + // After bot's message is displayed, scroll the last user message to the top
551 416 const lastUserMessage = $('#chat-box').find('.user-message').last();
552 417 if (lastUserMessage.length) {
553 418 scrollElementToTop(lastUserMessage);
554 419 }
@@ -554,14 +419,14 @@
554 419 }
555 420 }
556 421 });
557 422
423 + // Update the last seen message ID if applicable
558 424 if (messageText.id) {
559 425 lastSeenMessageId = messageText.id;
560 - hideNotification();
561 426 }
562 427 } catch (error) {
563 - console.error("Error rendering message:", error);
428 + console.error("Error rendering message with images:", error);
564 429 }
565 430 }
566 431
567 432
@@ -612,17 +477,14 @@
612 477 'color': fontColor,
613 478 })
614 479 .removeClass('temporary-message')
615 480 .fadeIn(200, function() {
481 + // After message is displayed, scroll last user message to top
616 482 if (sender === "bot" || sender === "agent") {
617 483 const lastUserMessage = $('#chat-box').find('.user-message').last();
618 484 if (lastUserMessage.length) {
619 485 scrollElementToTop(lastUserMessage);
620 486 }
621 - // Show notification if chat is hidden
622 - if ($('#floating-chatbot').hasClass('hidden')) {
623 - showNotification();
624 - }
625 487 }
626 488 });
627 489 });
628 490 } else {
@@ -647,11 +509,11 @@
647 509 }
648 510 }
649 511
650 512
651 -// Update your checkForAgentMessages function
652 513 function checkForAgentMessages() {
653 514 const sessionId = getChatSession();
515 +
654 516 $.ajax({
655 517 url: mxchatChat.ajax_url,
656 518 type: 'POST',
657 519 dataType: 'json',
@@ -661,24 +523,17 @@
661 523 last_seen_id: lastSeenMessageId,
662 524 nonce: mxchatChat.nonce
663 525 },
664 526 success: function (response) {
527 + //console.log("Agent messages polling response:", response);
665 528 if (response.success && response.data?.new_messages) {
666 - let hasNewMessage = false;
667 -
668 529 response.data.new_messages.forEach(function (message) {
669 530 if (message.role === "agent" && !processedMessageIds.has(message.id)) {
670 - hasNewMessage = true;
671 531 replaceLastMessage("agent", message.content);
672 532 lastSeenMessageId = message.id;
673 533 processedMessageIds.add(message.id);
674 534 }
675 535 });
676 -
677 - if (hasNewMessage && $('#floating-chatbot').hasClass('hidden')) {
678 - showNotification();
679 - }
680 -
681 536 scrollToBottom(true);
682 537 }
683 538 },
684 539 error: function (xhr, status, error) {
@@ -805,37 +660,29 @@
805 660 return textArea.value;
806 661 }
807 662
808 663
809 -// Update formatCodeBlocks function
810 664 function formatCodeBlocks(text) {
811 - // First handle raw PHP tags
812 - text = text.replace(/(<\?php[\s\S]*?\?>)/g, (match) => {
813 - return `<pre><code class="language-php">${escapeHtml(match)}</code></pre>`;
814 - });
665 + // Ensure the input is a string; otherwise, convert or return empty
666 + if (typeof text !== 'string') {
667 + console.error("formatCodeBlocks: Input is not a string:", text);
668 + return typeof text === 'object' && text.text ? text.text : ""; // Use .text if available, else empty
669 + }
815 670
816 - // Then handle code blocks with backticks
817 - text = text.replace(/```php5?\n([\s\S]+?)```/gi, (match, code) => {
818 - return `<pre><code class="language-php">${escapeHtml(code)}</code></pre>`;
671 + const codeBlockPattern = /```(\w+)?\n?([\s\S]+?)```/g;
672 +
673 + return text.replace(codeBlockPattern, (_, language, codeContent) => {
674 + language = language || 'plaintext';
675 +
676 + return `
677 + <div class="mxchat-code-block-container">
678 + <button class="mxchat-copy-button" aria-label="Copy to clipboard">Copy</button>
679 + <pre class="mxchat-code-block"><code class="mxchat-language-${language}">${escapeHtml(codeContent)}</code></pre>
680 + </div>`;
819 681 });
682 +}
820 683
821 - return text;
822 -}
823 684
824 -// Update escapeHtml function to preserve existing code blocks
825 -function escapeHtml(unsafe) {
826 - // First check if it's already a code block
827 - if (unsafe.includes('<pre><code') || unsafe.includes('</code></pre>')) {
828 - return unsafe;
829 - }
830 -
831 - return unsafe
832 - .replace(/&/g, "&amp;")
833 - .replace(/</g, "&lt;")
834 - .replace(/>/g, "&gt;")
835 - .replace(/"/g, "&quot;")
836 - .replace(/'/g, "&#039;");
837 -}
838 685 // Utility function to escape HTML
839 686 function escapeHtml(unsafe) {
840 687 return unsafe
841 688 .replace(/&/g, "&amp;")
@@ -849,18 +696,20 @@
849 696
850 697
851 698 // Function to convert newlines, skipping preformatted text
852 699 function convertNewlinesToBreaks(text) {
853 - // Split while preserving code blocks
854 - return text.split(/(<pre\b[^>]*>[\s\S]*?<\/pre>)/g).map(part => {
855 - if (part.startsWith('<pre')) return part;
856 - return part.replace(/(^|[^>])\n/g, '$1<br>');
857 - }).join('');
700 + // Regex to exclude <pre> and <code> tags from adding <br> tags
701 + return text.replace(/(^|[^>])\n/g, '$1<br>');
858 702 }
859 703
860 704
861 705
706 +$(document).ready(function() {
707 + loadChatHistory();
708 +});
862 709
710 +
711 +
863 712 // Helper function to check if a string is an image HTML
864 713 function isImageHtml(str) {
865 714 return str.startsWith('<img') && str.endsWith('>');
866 715 }
@@ -916,9 +765,9 @@
916 765 // Then handle the fade
917 766 $('#floating-chatbot-button').fadeTo(500, 1);
918 767 // Force visibility
919 768 $('#floating-chatbot-button').removeClass('hidden');
920 - //console.log('Showing widget');
769 + console.log('Showing widget');
921 770 }
922 771
923 772 // Function to hide the chatbot widget
924 773 function hideChatWidget() {
@@ -923,13 +772,13 @@
923 772 // Function to hide the chatbot widget
924 773 function hideChatWidget() {
925 774 $('#floating-chatbot-button').css('display', 'none');
926 775 $('#floating-chatbot-button').addClass('hidden');
927 - //console.log('Hiding widget');
776 + console.log('Hiding widget');
928 777 }
929 778
930 779 function initializeChatVisibility() {
931 - //console.log('Initializing chat visibility');
780 + console.log('Initializing chat visibility');
932 781 const complianzEnabled = mxchatChat.complianz_toggle === 'on' ||
933 782 mxchatChat.complianz_toggle === '1' ||
934 783 mxchatChat.complianz_toggle === 1;
935 784
@@ -938,9 +787,9 @@
938 787 checkConsentAndShowChat();
939 788
940 789 // Listen for consent changes
941 790 $(document).on('cmplz_status_change', function(event) {
942 - //console.log('Status change detected');
791 + console.log('Status change detected');
943 792 checkConsentAndShowChat();
944 793 });
945 794 } else {
946 795 // If Complianz is not enabled, always show
@@ -952,16 +801,23 @@
952 801 // Also check pre-chat message when Complianz is not enabled
953 802 checkPreChatDismissal();
954 803 }
955 804 }
805 +// Initialize when document is ready
806 +$(document).ready(function() {
807 + console.log('Document ready - starting initialization');
808 + initializeChatVisibility();
809 +});
956 810
957 811
958 -
959 812 function checkConsentAndShowChat() {
960 813 var consentStatus = cmplz_has_consent('marketing');
961 814 var consentType = complianz.consenttype;
962 815
963 - //console.log('Checking consent:', {status: consentStatus,type: consentType});
816 + console.log('Checking consent:', {
817 + status: consentStatus,
818 + type: consentType
819 + });
964 820
965 821 let $widget = $('#floating-chatbot-button');
966 822 let $chatbot = $('#floating-chatbot');
967 823 let $preChat = $('#pre-chat-message');
@@ -966,9 +822,9 @@
966 822 let $chatbot = $('#floating-chatbot');
967 823 let $preChat = $('#pre-chat-message');
968 824
969 825 if (consentStatus === true) {
970 - //console.log('Consent granted - showing widget');
826 + console.log('Consent granted - showing widget');
971 827 $widget
972 828 .removeClass('no-consent')
973 829 .css('display', 'flex')
974 830 .removeClass('hidden')
@@ -977,9 +833,9 @@
977 833
978 834 // Show pre-chat message if not dismissed
979 835 checkPreChatDismissal();
980 836 } else {
981 - //console.log('No consent - hiding widget');
837 + console.log('No consent - hiding widget');
982 838 $widget
983 839 .addClass('no-consent')
984 840 .fadeTo(500, 0, function() {
985 841 $(this)
@@ -1023,15 +879,16 @@
1023 879 var chatbot = $('#floating-chatbot');
1024 880 if (chatbot.hasClass('hidden')) {
1025 881 chatbot.removeClass('hidden').addClass('visible');
1026 882 $(this).addClass('hidden');
1027 - $('#chat-notification-badge').hide(); // Hide notification when opening chat
1028 883 disableScroll();
884 + // Hide the pre-chat message without dismissing it
1029 885 $('#pre-chat-message').fadeOut(250);
1030 886 } else {
1031 887 chatbot.removeClass('visible').addClass('hidden');
1032 888 $(this).removeClass('hidden');
1033 889 enableScroll();
890 + // Show the pre-chat message again if it hasn't been dismissed
1034 891 checkPreChatDismissal();
1035 892 }
1036 893 });
1037 894
@@ -1070,10 +927,12 @@
1070 927 $(':root').css('--vh', vh + 'px');
1071 928 }
1072 929
1073 930 // Set the height when the page loads
931 + $(document).ready(function() {
932 + setFullHeight();
933 + });
1074 934
1075 -
1076 935 // Set the height on resize and orientation change events
1077 936 $(window).on('resize orientationchange', function() {
1078 937 setFullHeight();
1079 938 });
@@ -1454,122 +1313,10 @@
1454 1313 });
1455 1314
1456 1315
1457 1316
1458 -// Ensure essential elements are defined
1459 -const emailForm = document.getElementById('email-collection-form');
1460 -const emailBlocker = document.getElementById('email-blocker');
1461 -const chatbotWrapper = document.getElementById('chat-container');
1462 -
1463 -if (emailForm && emailBlocker && chatbotWrapper) {
1464 - // Check if email exists for the current session
1465 - function checkSessionAndEmail() {
1466 - const sessionId = getChatSession();
1467 - //console.log("[DEBUG JS] checkSessionAndEmail -> sessionId:", sessionId);
1468 -
1469 - fetch(mxchatChat.ajax_url, {
1470 - method: 'POST',
1471 - headers: {
1472 - 'Content-Type': 'application/x-www-form-urlencoded',
1473 - },
1474 - body: new URLSearchParams({
1475 - action: 'mxchat_check_email_provided',
1476 - session_id: sessionId,
1477 - nonce: mxchatChat.nonce,
1478 - }),
1479 - })
1480 - .then((response) => response.json())
1481 - .then((data) => {
1482 - //console.log("[DEBUG JS] mxchat_check_email_provided response:", data);
1483 -
1484 - if (data.success) {
1485 - if (data.data.logged_in) {
1486 - //console.log("[DEBUG JS] User is logged in. Hiding email form.");
1487 - emailBlocker.style.display = 'none';
1488 - chatbotWrapper.style.display = 'flex';
1489 - } else if (data.data.email) {
1490 - //console.log("[DEBUG JS] Email found for session. Hiding email form.");
1491 - emailBlocker.style.display = 'none';
1492 - chatbotWrapper.style.display = 'flex';
1493 - } else {
1494 - //console.log("[DEBUG JS] No email provided. Showing email form.");
1495 - emailBlocker.style.display = 'flex';
1496 - chatbotWrapper.style.display = 'none';
1497 - }
1498 - } else {
1499 - //console.log("[DEBUG JS] Error or no data received. Showing email form.");
1500 - emailBlocker.style.display = 'flex';
1501 - chatbotWrapper.style.display = 'none';
1502 - }
1503 - })
1504 - .catch((error) => {
1505 - // console.error("[DEBUG JS] Fetch error -> forcing email form visible:", error);
1506 - emailBlocker.style.display = 'flex';
1507 - chatbotWrapper.style.display = 'none';
1508 - });
1509 -}
1510 -
1511 -
1512 -
1513 - // Handle email form submission
1514 - emailForm.addEventListener('submit', function (event) {
1515 - event.preventDefault();
1516 - const userEmail = document.getElementById('user-email').value;
1517 - const sessionId = getChatSession();
1518 -
1519 - if (userEmail) {
1520 - fetch(mxchatChat.ajax_url, {
1521 - method: 'POST',
1522 - headers: {
1523 - 'Content-Type': 'application/x-www-form-urlencoded',
1524 - },
1525 - body: new URLSearchParams({
1526 - action: 'mxchat_handle_save_email_and_response',
1527 - email: userEmail,
1528 - session_id: sessionId,
1529 - nonce: mxchatChat.nonce,
1530 - }),
1531 - })
1532 - .then((response) => response.json())
1533 - .then((data) => {
1534 - //console.log('Backend response:', data);
1535 - if (data.success) {
1536 - //console.log('Email saved successfully:', userEmail);
1537 - emailBlocker.style.display = 'none';
1538 - chatbotWrapper.style.display = 'flex';
1539 -
1540 - // Optionally handle bot response
1541 - if (data.message) {
1542 - appendMessage('bot', data.message);
1543 - scrollToBottom();
1544 - }
1545 - } else {
1546 - console.error('Error saving email:', data.message || 'Unknown error');
1547 - }
1548 - })
1549 - .catch((error) => {
1550 - console.error('AJAX error:', error);
1551 - });
1552 - }
1553 - });
1554 -
1555 - // Check session and email status on page load
1556 - checkSessionAndEmail();
1557 -} else {
1558 - console.error('Essential elements for email handling are missing.');
1559 -}
1560 -
1561 -
1562 -// Initialize when document is ready
1563 -$(document).ready(function() {
1564 - setFullHeight();
1565 - initializeChatVisibility();
1566 - loadChatHistory();
1567 -
1568 1317 });
1569 1318
1570 -});
1571 -
1572 1319 // Event listener for copy button
1573 1320 document.addEventListener("click", (e) => {
1574 1321 if (e.target.classList.contains("mxchat-copy-button")) {
1575 1322 const copyButton = e.target;
@@ -1590,7 +1337,4 @@
1590 1337 });
1591 1338 }
1592 1339 }
1593 1340 });
1594 -
1595 -
1596 -