Spaces:
Running
Running
File size: 10,981 Bytes
e912915 b9fe4f1 e912915 3024053 58d7ea5 e912915 f80e511 3024053 f80e511 58d7ea5 f80e511 58d7ea5 f80e511 58d7ea5 f80e511 58d7ea5 f80e511 3024053 58d7ea5 e912915 58d7ea5 e912915 58d7ea5 e912915 58d7ea5 e912915 58d7ea5 e912915 58d7ea5 e912915 58d7ea5 e912915 58d7ea5 949d7d1 3024053 58d7ea5 3024053 e912915 3024053 4e37599 58d7ea5 4e37599 58d7ea5 4e37599 58d7ea5 4e37599 e912915 949d7d1 3024053 58d7ea5 6c6c4eb 58d7ea5 949d7d1 3024053 58d7ea5 949d7d1 58d7ea5 949d7d1 58d7ea5 949d7d1 58d7ea5 949d7d1 e912915 3024053 e912915 4e37599 58d7ea5 4e37599 527614f 14e9683 d1b354f | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 | <!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Visual JSON Editor</title>
<script src="https://cdn.tailwindcss.com"></script>
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/6.4.0/css/all.min.css">
<link rel="stylesheet" href="style.css">
<script>
tailwind.config = {
theme: {
extend: {
colors: {
primary: '#3b82f6',
secondary: '#1e40af',
dark: '#0f172a',
light: '#f8fafc'
}
}
}
}
</script>
</head>
<body class="bg-slate-900 h-screen overflow-hidden p-0">
<div class="w-full h-screen flex flex-col">
<header class="flex-shrink-0 mb-1 text-center py-1">
<h1 class="text-2xl font-bold text-slate-100">Visual JSON Editor</h1>
<p class="text-slate-400 text-sm">The way JSON should <i class="italic font-semibold">ALWAYS</i> been editored!</p>
</header>
<!-- Menu Bar -->
<div class="menu-bar flex flex-wrap py-1 px-2 flex-shrink-0">
<div class="dropdown">
<div class="menu-item px-2 py-1">File</div>
<div class="dropdown-content">
<a href="#" id="newBtn"><i class="fas fa-plus mr-2"></i>New</a>
<a href="#" id="openBtn"><i class="fas fa-folder-open mr-2"></i>Open</a>
<a href="#" id="saveBtn"><i class="fas fa-save mr-2"></i>Save</a>
</div>
</div>
<div class="dropdown">
<div class="menu-item px-2 py-1">Edit</div>
<div class="dropdown-content">
<a href="#" id="undoBtn"><i class="fas fa-undo mr-2"></i>Undo</a>
<a href="#" id="redoBtn"><i class="fas fa-redo mr-2"></i>Redo</a>
<a href="#" id="copyBtnMenu"><i class="fas fa-copy mr-2"></i>Copy</a>
<a href="#" id="cutBtnMenu"><i class="fas fa-cut mr-2"></i>Cut</a>
<a href="#" id="pasteBtnMenu"><i class="fas fa-paste mr-2"></i>Paste</a>
<a href="#" id="preferencesBtn"><i class="fas fa-cog mr-2"></i>Preferences</a>
</div>
</div>
<div class="dropdown">
<div class="menu-item px-2 py-1">Tools</div>
<div class="dropdown-content">
<a href="#" id="formatBtn"><i class="fas fa-indent mr-2"></i>Format</a>
<a href="#" id="validateBtn"><i class="fas fa-check-circle mr-2"></i>Validate</a>
</div>
</div>
<div class="dropdown">
<div class="menu-item px-2 py-1">Help</div>
<div class="dropdown-content">
<a href="#" id="instructionsBtn"><i class="fas fa-info-circle mr-2"></i>Instructions</a>
<a href="#" id="sampleBtn"><i class="fas fa-code mr-2"></i>Sample JSON</a>
</div>
</div>
</div>
<div class="bg-slate-800 rounded-lg overflow-hidden mb-1 border border-slate-700 flex-1 flex flex-col overflow-hidden">
<div class="p-2 bg-slate-700 border-b border-slate-600 flex flex-wrap items-center justify-between gap-2">
<div class="flex flex-wrap gap-1">
<button id="newBtn2" class="btn bg-primary hover:bg-secondary text-white px-3 py-1.5 rounded flex items-center gap-1 text-sm">
<i class="fas fa-plus text-xs"></i> New
</button>
<button id="openBtn2" class="btn bg-slate-600 hover:bg-slate-500 px-3 py-1.5 rounded flex items-center gap-1 text-sm">
<i class="fas fa-folder-open text-xs"></i> Open
</button>
<button id="saveBtn2" class="btn bg-slate-600 hover:bg-slate-500 px-3 py-1.5 rounded flex items-center gap-1 text-sm">
<i class="fas fa-save text-xs"></i> Save
</button>
</div>
<div class="flex flex-wrap gap-1">
<button id="undoBtn2" class="btn bg-slate-600 hover:bg-slate-500 px-2 py-1.5 rounded text-sm">
<i class="fas fa-undo text-xs"></i>
</button>
<button id="redoBtn2" class="btn bg-slate-600 hover:bg-slate-500 px-2 py-1.5 rounded text-sm">
<i class="fas fa-redo text-xs"></i>
</button>
<button id="formatBtn2" class="btn bg-slate-600 hover:bg-slate-500 px-2 py-1.5 rounded text-sm">
<i class="fas fa-indent text-xs"></i>
</button>
<button id="validateBtn2" class="btn bg-slate-600 hover:bg-slate-500 px-2 py-1.5 rounded text-sm">
<i class="fas fa-check-circle text-xs"></i>
</button>
</div>
</div>
<div class="flex flex-col lg:flex-row gap-0.5">
<!-- Left Panel - Visual JSON Editor -->
<div class="w-full lg:w-1/2">
<div class="bg-slate-700 h-full flex flex-col" style="height: calc(100vh - 120px);">
<div class="flex justify-between items-center px-2 py-1 border-b border-slate-600">
<h2 class="text-sm font-semibold text-slate-200">Visual Editor</h2>
<span class="text-xs text-slate-400">Click to edit • Tab nav • Ctrl+Tab indent</span>
</div>
<div class="relative json-editor border-none overflow-auto flex-1" style="min-height: 100%;">
<!-- Left line numbers -->
<div id="lineNumbersLeft" class="absolute left-0 top-0 bottom-0 w-8 bg-slate-800 text-slate-500 text-xs font-mono text-right pr-2 select-none overflow-hidden z-10 pt-1 border-r border-slate-700"></div>
<!-- Right line numbers -->
<div id="lineNumbersRight" class="absolute right-0 top-0 bottom-0 w-8 bg-slate-800 text-slate-500 text-xs font-mono text-left pl-2 select-none overflow-hidden z-10 pt-1 border-l border-slate-700"></div>
<!-- JSON content -->
<div id="jsonEditor" class="pl-9 pr-9 py-1 font-mono text-sm">
<!-- JSON content will be rendered here -->
</div>
</div>
</div>
</div>
<!-- Right Panel - JSON Code Editor -->
<div class="w-full lg:w-1/2">
<div class="bg-gray-50 h-full flex flex-col" style="height: calc(100vh - 120px);">
<div class="flex justify-between items-center px-2 py-1 border-b border-gray-300 bg-gray-100">
<h2 class="text-sm font-semibold text-gray-700">Code Editor</h2>
<div class="flex gap-1 items-center">
<span id="autoSaveStatus" class="text-xs text-green-600 hidden"><i class="fas fa-check-circle mr-1"></i>Auto-saved</span>
<button id="applyCodeBtn" class="btn bg-green-500 hover:bg-green-600 text-white px-2 py-1 rounded text-xs">
<i class="fas fa-check mr-1"></i> Apply
</button>
</div>
</div>
<textarea id="jsonOutput" class="w-full flex-1 font-mono text-sm p-1 border-none bg-white focus:outline-none resize-none" style="min-height: 100%;"></textarea>
<div class="px-2 py-1 border-t border-gray-300 flex flex-wrap gap-1 justify-between items-center bg-gray-100">
<div class="flex gap-1">
<button id="copyBtn" class="btn bg-gray-200 hover:bg-gray-300 px-2 py-1 rounded text-xs">
<i class="fas fa-copy mr-1"></i> Copy
</button>
<button id="downloadBtn" class="btn bg-primary hover:bg-secondary text-white px-2 py-1 rounded text-xs">
<i class="fas fa-download mr-1"></i> Download
</button>
</div>
<div id="validationStatus" class="flex items-center gap-1 text-xs">
<i class="fas fa-check-circle text-green-500"></i>
<span class="text-green-600">Valid</span>
</div>
</div>
</div>
</div>
</div>
</div>
<div id="notification" class="notification fixed bottom-4 right-4 bg-white shadow-lg rounded-lg p-4 border-l-4 border-green-500 max-w-md z-50">
<div class="flex items-start">
<i class="fas fa-check-circle text-green-500 text-xl mt-0.5 mr-3"></i>
<div>
<h4 class="font-bold text-gray-800">Success!</h4>
<p class="text-gray-600 mt-1">Your JSON has been updated successfully.</p>
</div>
</div>
</div>
<!-- Coordinates display - fixed position -->
<div id="coordinates" class="fixed top-16 right-2 bg-slate-800 text-slate-300 px-2 py-1 rounded text-xs font-mono shadow-lg z-50 opacity-80 hover:opacity-100 transition-opacity border border-slate-600">
<span id="coordLine">L:0</span> <span id="coordChar">C:0</span> <span id="coordDepth">D:0</span>
</div>
<!-- Context menu -->
<div id="contextMenu" class="context-menu">
<div class="context-menu-item" id="ctxInsertAfter">
<i class="fas fa-plus"></i> Insert Line After
</div>
<div class="context-menu-item" id="ctxInsertBefore">
<i class="fas fa-arrow-up"></i> Insert Line Before
</div>
<div class="context-menu-divider"></div>
<div class="context-menu-item" id="ctxCopyKey">
<i class="fas fa-copy"></i> Copy Key
</div>
<div class="context-menu-item" id="ctxCopyValue">
<i class="fas fa-copy"></i> Copy Value
</div>
<div class="context-menu-item" id="ctxDelete">
<i class="fas fa-trash"></i> Delete
</div>
</div>
</div>
<script src="script.js"></script>
</body> |