fix: resolve markdown list processing and TinyMCE timing issues

- Rewrite markdown conversion to handle lists before other formatting
- Fix conflict between * for lists and * for italic text formatting
- Improve list detection with proper "* " pattern matching
- Add WordPress tinymce-editor-init event listener for proper initialization
- Store editor reference globally for reliable content insertion
- Enhanced TinyMCE readiness detection with fallback mechanisms

🤖 Generated with [Claude Code](https://claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
ben 2025-09-26 19:13:21 -03:00
parent 875315e2f5
commit c3806f01c3
2 changed files with 67 additions and 38 deletions

View file

@ -576,8 +576,12 @@ jQuery(document).ready(function($) {
// Wait for TinyMCE to be fully initialized // Wait for TinyMCE to be fully initialized
const applyToTinyMCE = () => { const applyToTinyMCE = () => {
if (typeof tinyMCE !== 'undefined' && tinyMCE.get('event_description') && window.hvacTinyMCEReady) { if (window.hvacTinyMCEReady && window.hvacTinyMCEEditor) {
console.log('Setting TinyMCE content'); console.log('Setting TinyMCE content using stored editor reference');
window.hvacTinyMCEEditor.setContent(htmlContent);
return true;
} else if (typeof tinyMCE !== 'undefined' && tinyMCE.get('event_description')) {
console.log('Setting TinyMCE content using direct reference');
tinyMCE.get('event_description').setContent(htmlContent); tinyMCE.get('event_description').setContent(htmlContent);
return true; return true;
} }
@ -742,36 +746,23 @@ jQuery(document).ready(function($) {
* Convert markdown to HTML for rich text editor * Convert markdown to HTML for rich text editor
*/ */
markdownToHtml: function(markdown) { markdownToHtml: function(markdown) {
// Test the function with sample input
if (window.hvacDebugMarkdown) { if (window.hvacDebugMarkdown) {
console.log('Testing markdown conversion:'); console.log('Testing markdown conversion:');
console.log('Input:', markdown); console.log('Input:', markdown);
} }
let html = markdown;
// Convert headers (#### -> h4, ### -> h3, ## -> h2, # -> h1) // First, handle lists BEFORE processing other markdown
html = html.replace(/^#### (.+)$/gm, '<h4>$1</h4>'); // This prevents conflicts between * for lists and * for italic
html = html.replace(/^### (.+)$/gm, '<h3>$1</h3>'); const lines = markdown.split('\n');
html = html.replace(/^## (.+)$/gm, '<h2>$1</h2>');
html = html.replace(/^# (.+)$/gm, '<h1>$1</h1>');
// Convert bold text (**text** -> <strong>text</strong>)
html = html.replace(/\*\*([^*]+)\*\*/g, '<strong>$1</strong>');
// Convert italic text (*text* -> <em>text</em>)
html = html.replace(/\*([^*]+)\*/g, '<em>$1</em>');
// Process lines for better list handling
const lines = html.split('\n');
const processedLines = []; const processedLines = [];
let inList = false; let inList = false;
for (let i = 0; i < lines.length; i++) { for (let i = 0; i < lines.length; i++) {
let line = lines[i].trim(); let line = lines[i].trim();
// Handle bullet list items // Handle bullet list items (must start with * and space)
if (line.match(/^\* (.+)$/)) { if (line.match(/^\* /)) {
const listItemContent = line.replace(/^\* (.+)$/, '$1'); const listItemContent = line.substring(2); // Remove "* "
if (!inList) { if (!inList) {
processedLines.push('<ul>'); processedLines.push('<ul>');
@ -779,9 +770,9 @@ jQuery(document).ready(function($) {
} }
processedLines.push(`<li>${listItemContent}</li>`); processedLines.push(`<li>${listItemContent}</li>`);
// Check if next line is also a list item or if this is the last line // Check if next line is also a list item
const nextLine = i + 1 < lines.length ? lines[i + 1].trim() : ''; const nextLine = i + 1 < lines.length ? lines[i + 1].trim() : '';
if (!nextLine.match(/^\* (.+)$/)) { if (!nextLine.match(/^\* /)) {
processedLines.push('</ul>'); processedLines.push('</ul>');
inList = false; inList = false;
} }
@ -793,11 +784,7 @@ jQuery(document).ready(function($) {
} }
// Add regular line // Add regular line
if (line !== '') { processedLines.push(lines[i]); // Keep original spacing
processedLines.push(line);
} else {
processedLines.push(''); // Preserve empty lines for paragraph breaks
}
} }
} }
@ -806,13 +793,41 @@ jQuery(document).ready(function($) {
processedLines.push('</ul>'); processedLines.push('</ul>');
} }
// Rejoin the processed content
let html = processedLines.join('\n');
// Now process other markdown elements
// Convert headers (#### -> h4, ### -> h3, ## -> h2, # -> h1)
html = html.replace(/^#### (.+)$/gm, '<h4>$1</h4>');
html = html.replace(/^### (.+)$/gm, '<h3>$1</h3>');
html = html.replace(/^## (.+)$/gm, '<h2>$1</h2>');
html = html.replace(/^# (.+)$/gm, '<h1>$1</h1>');
// Convert bold text (**text** -> <strong>text</strong>)
html = html.replace(/\*\*([^*]+?)\*\*/g, '<strong>$1</strong>');
// Convert italic text (*text* -> <em>text</em>)
// Process line by line to avoid conflicts with list items
const italicLines = html.split('\n').map(line => {
// Skip processing if this line contains list markup
if (line.includes('<li>') || line.includes('<ul>') || line.includes('</ul>')) {
return line;
}
// Apply italic formatting to non-list lines
return line.replace(/\*([^*\n]+?)\*/g, '<em>$1</em>');
});
html = italicLines.join('\n');
// Convert to paragraphs // Convert to paragraphs
const finalLines = html.split('\n');
const paragraphs = []; const paragraphs = [];
let currentParagraph = ''; let currentParagraph = '';
for (let line of processedLines) { for (let line of finalLines) {
const trimmedLine = line.trim();
// Skip empty lines // Skip empty lines
if (line === '') { if (trimmedLine === '') {
if (currentParagraph) { if (currentParagraph) {
paragraphs.push(currentParagraph); paragraphs.push(currentParagraph);
currentParagraph = ''; currentParagraph = '';
@ -821,18 +836,18 @@ jQuery(document).ready(function($) {
} }
// If line is already wrapped in HTML tags, add it as is // If line is already wrapped in HTML tags, add it as is
if (line.match(/^<(h[1-6]|ul|\/ul|li|strong|em)/)) { if (trimmedLine.match(/^<(h[1-6]|ul|\/ul|li)/)) {
if (currentParagraph) { if (currentParagraph) {
paragraphs.push(currentParagraph); paragraphs.push(currentParagraph);
currentParagraph = ''; currentParagraph = '';
} }
paragraphs.push(line); paragraphs.push(trimmedLine);
} else { } else {
// Regular text line // Regular text line
if (currentParagraph) { if (currentParagraph) {
currentParagraph += ' ' + line; currentParagraph += ' ' + trimmedLine;
} else { } else {
currentParagraph = line; currentParagraph = trimmedLine;
} }
} }
} }

View file

@ -1678,18 +1678,32 @@ HTML;
jQuery(document).ready(function($) { jQuery(document).ready(function($) {
// Store reference for AI Assistant // Store reference for AI Assistant
window.hvacTinyMCEReady = false; window.hvacTinyMCEReady = false;
window.hvacTinyMCEEditor = null;
// Check if TinyMCE is ready // Listen for TinyMCE init event
$(document).on('tinymce-editor-init', function(event, editor) {
if (editor.id === 'event_description') {
window.hvacTinyMCEReady = true;
window.hvacTinyMCEEditor = editor;
console.log('TinyMCE editor initialized for event_description');
}
});
// Fallback check if event doesn't fire
function checkTinyMCEReady() { function checkTinyMCEReady() {
if (typeof tinyMCE !== 'undefined' && tinyMCE.get('event_description')) { if (typeof tinyMCE !== 'undefined' && tinyMCE.get('event_description')) {
if (!window.hvacTinyMCEReady) {
window.hvacTinyMCEReady = true; window.hvacTinyMCEReady = true;
console.log('TinyMCE ready for event_description'); window.hvacTinyMCEEditor = tinyMCE.get('event_description');
console.log('TinyMCE ready for event_description (fallback detection)');
}
} else { } else {
setTimeout(checkTinyMCEReady, 100); setTimeout(checkTinyMCEReady, 100);
} }
} }
checkTinyMCEReady(); // Start fallback check
setTimeout(checkTinyMCEReady, 500);
}); });
</script> </script>
</div> </div>