feat: restore modern Abstract Control class system with compass positioning
- Replace old DocumentNavigator with sophisticated 507-line Control architecture - Implement compass-based positioning system (N, NNE, NE, ENE, E, ESE, SE, SSE, S, SSW, SW, WSW, W, WNW, NW, NNW) - Add four specialized controls with precise positioning: * ContentsControl (upper left - nw): Table of contents navigation * StatusControl (right - e): Document statistics and change tracking * DebugControl (lower right - se): Debug messages and system info * EditControl (upper right - ne): Document editing tools - Integrate external JavaScript files following GUARDRAILS.md principles - Add drag & drop, resize handles, expand/collapse, and hover behaviors - Implement Fail Fast error handling with safe operation wrappers - Preserve backup HTML files for reference and recovery validation - Generate 144KB functional HTML vs previous 12KB broken output 🤖 Generated with Claude Code Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
@@ -1306,7 +1306,7 @@ MISSING: {len(missing_components)} components
|
||||
return ""
|
||||
|
||||
def _get_clean_editor_scripts(self) -> str:
|
||||
"""Load the modular editor JavaScript components for edit/insert modes."""
|
||||
"""Load the modular editor JavaScript components from external files."""
|
||||
from pathlib import Path
|
||||
|
||||
# Define the modular components to load in order
|
||||
@@ -1314,7 +1314,12 @@ MISSING: {len(missing_components)} components
|
||||
'js/core/section-manager.js',
|
||||
'js/components/debug-panel.js',
|
||||
'js/components/document-controls.js',
|
||||
'js/components/dom-renderer.js'
|
||||
'js/components/dom-renderer.js',
|
||||
'js/controls/control-base.js',
|
||||
'js/controls/contents-control.js',
|
||||
'js/controls/status-control.js',
|
||||
'js/controls/debug-control.js',
|
||||
'js/controls/edit-control.js'
|
||||
]
|
||||
|
||||
base_path = Path(__file__).parent / 'static'
|
||||
@@ -1339,45 +1344,154 @@ MISSING: {len(missing_components)} components
|
||||
# Add initialization script to wire up the components
|
||||
initialization_script = """
|
||||
// === Component Initialization ===
|
||||
function initializeCleanEditor() {
|
||||
console.log('🚀 Initializing Clean Editor Components...');
|
||||
|
||||
document.addEventListener('DOMContentLoaded', function() {
|
||||
// Create container for the markdown content
|
||||
const container = document.getElementById('markdown-content') || document.body;
|
||||
|
||||
try {
|
||||
// Initialize components
|
||||
const sectionManager = new SectionManager();
|
||||
const domRenderer = new DOMRenderer(sectionManager, container);
|
||||
const debugPanel = new DebugPanel();
|
||||
const documentControls = new DocumentControls();
|
||||
// Initialize components
|
||||
const sectionManager = new SectionManager();
|
||||
const domRenderer = new DOMRenderer(sectionManager, container);
|
||||
const debugPanel = new DebugPanel();
|
||||
const documentControls = new DocumentControls();
|
||||
|
||||
// Create document controls
|
||||
documentControls.create();
|
||||
// Create document controls
|
||||
documentControls.create();
|
||||
|
||||
console.log('✓ Clean Editor initialized successfully');
|
||||
console.log('✓ Click on any section to start editing');
|
||||
// Step 4: Initialize modern Control-based architecture with compass positioning
|
||||
console.log("🎛️ Initializing modern Control system with compass positioning...");
|
||||
|
||||
// Make components globally available for debugging
|
||||
window.editorComponents = {
|
||||
sectionManager,
|
||||
domRenderer,
|
||||
debugPanel,
|
||||
documentControls
|
||||
};
|
||||
// ContentsControl (positioned upper left - nw)
|
||||
const contentsControl = new ContentsControl();
|
||||
contentsControl.control.config.position = 'nw'; // Upper left
|
||||
contentsControl.createControl();
|
||||
window.contentsControl = contentsControl;
|
||||
|
||||
} catch (error) {
|
||||
console.error('❌ Clean Editor initialization failed:', error);
|
||||
throw error;
|
||||
// StatusControl (positioned right - e)
|
||||
const statusControl = new StatusControl();
|
||||
statusControl.control.config.position = 'e'; // Right
|
||||
statusControl.createControl();
|
||||
window.statusControl = statusControl;
|
||||
|
||||
// DebugControl (positioned lower right - se)
|
||||
const debugControl = new DebugControl();
|
||||
debugControl.control.config.position = 'se'; // Lower right
|
||||
debugControl.createControl();
|
||||
window.debugControl = debugControl;
|
||||
|
||||
// EditControl (positioned upper right - ne)
|
||||
const editControl = new EditControl();
|
||||
editControl.control.config.position = 'ne'; // Upper right
|
||||
editControl.createControl();
|
||||
window.editControl = editControl;
|
||||
|
||||
console.log("🎛️ Modern Control system initialized with compass positioning");
|
||||
|
||||
// Wire up event handlers
|
||||
documentControls.setEventHandlers({
|
||||
'save-document': () => {
|
||||
console.log('Save document clicked');
|
||||
try {
|
||||
// Get current markdown content from section manager
|
||||
const currentMarkdown = sectionManager.getDocumentMarkdown();
|
||||
|
||||
// Create filename with timestamp suffix following the established convention
|
||||
const now = new Date();
|
||||
const timestamp = now.toISOString().slice(0, 19).replace(/:/g, '-').replace('T', '-');
|
||||
|
||||
// Extract original filename from config or use default
|
||||
const originalFilename = window.editorConfig?.originalFilename || 'document';
|
||||
const editedFilename = `${originalFilename}-edited-${timestamp}.md`;
|
||||
|
||||
// Create and download the file
|
||||
const blob = new Blob([currentMarkdown], { type: 'text/markdown' });
|
||||
const url = URL.createObjectURL(blob);
|
||||
const a = document.createElement('a');
|
||||
a.href = url;
|
||||
a.download = editedFilename;
|
||||
document.body.appendChild(a);
|
||||
a.click();
|
||||
document.body.removeChild(a);
|
||||
URL.revokeObjectURL(url);
|
||||
|
||||
// Log success to debug panel
|
||||
debugPanel.addMessage(`Document saved as: ${editedFilename}`, 'SUCCESS');
|
||||
console.log(`Document successfully saved as: ${editedFilename}`);
|
||||
|
||||
} catch (error) {
|
||||
debugPanel.addMessage(`Save failed: ${error.message}`, 'ERROR');
|
||||
console.error('Save error:', error);
|
||||
}
|
||||
},
|
||||
'reset-all': () => {
|
||||
console.log('Reset all clicked');
|
||||
// Hide any open editors
|
||||
domRenderer.hideCurrentEditor();
|
||||
// Reset all sections to original state
|
||||
const allSections = Array.from(sectionManager.sections.values());
|
||||
allSections.forEach(section => {
|
||||
section.resetToOriginal();
|
||||
});
|
||||
// Re-render all sections
|
||||
domRenderer.renderAllSections(allSections);
|
||||
debugPanel.addMessage(`Reset all sections to original state`, 'INFO');
|
||||
},
|
||||
'show-status': () => {
|
||||
const status = sectionManager.getDocumentStatus();
|
||||
alert(`Document Status:\\nTotal Sections: ${status.totalSections}\\nEditing Sections: ${status.editingSections}`);
|
||||
},
|
||||
'toggle-debug': () => {
|
||||
debugPanel.toggle();
|
||||
}
|
||||
});
|
||||
|
||||
// Set up debug panel integration
|
||||
sectionManager.on('sections-created', (data) => {
|
||||
debugPanel.addMessage(`Created ${data.count} sections`, 'INFO');
|
||||
});
|
||||
|
||||
sectionManager.on('edit-started', (data) => {
|
||||
debugPanel.addMessage(`Edit started for section: ${data.sectionId}`, 'DEBUG');
|
||||
});
|
||||
|
||||
sectionManager.on('changes-accepted', (data) => {
|
||||
debugPanel.addMessage(`Changes accepted for section: ${data.sectionId}`, 'SUCCESS');
|
||||
// Re-render the section to show updated content
|
||||
const section = sectionManager.sections.get(data.sectionId);
|
||||
if (section) {
|
||||
const sectionElement = domRenderer.findSectionElement(data.sectionId);
|
||||
if (sectionElement) {
|
||||
const newElement = domRenderer.renderSection(section);
|
||||
sectionElement.parentNode.replaceChild(newElement, sectionElement);
|
||||
debugPanel.addMessage(`DOM updated for section: ${data.sectionId}`, 'INFO');
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
sectionManager.on('changes-cancelled', (data) => {
|
||||
debugPanel.addMessage(`Changes cancelled for section: ${data.sectionId}`, 'WARNING');
|
||||
});
|
||||
|
||||
// Initialize with markdown content
|
||||
const markdownToRender = markdownContent || '';
|
||||
if (markdownToRender.trim()) {
|
||||
const sections = sectionManager.createSectionsFromMarkdown(markdownToRender);
|
||||
domRenderer.renderAllSections(sections);
|
||||
debugPanel.addMessage(`Initialized with ${sections.length} sections`, 'INFO');
|
||||
} else {
|
||||
debugPanel.addMessage('No markdown content to initialize', 'WARNING');
|
||||
}
|
||||
}
|
||||
|
||||
function initializeScrollIndicators() {
|
||||
// Placeholder for scroll indicators - can be implemented later
|
||||
console.log('📍 Scroll indicators initialized');
|
||||
}
|
||||
// Make components globally available for debugging
|
||||
window.markitectComponents = {
|
||||
sectionManager,
|
||||
domRenderer,
|
||||
debugPanel,
|
||||
documentControls
|
||||
};
|
||||
|
||||
console.log('Markitect modular editor initialized successfully');
|
||||
});
|
||||
"""
|
||||
|
||||
combined_script.append(initialization_script)
|
||||
return '\n'.join(combined_script)
|
||||
|
||||
|
||||
Reference in New Issue
Block a user