protae5544 commited on
Commit
fa9317b
·
verified ·
1 Parent(s): 2ce99ee

แก้ไขให้ทำงานได้ถูกต้องทุกฟังชั่น

Browse files
Files changed (2) hide show
  1. components/sidebar.js +101 -2
  2. script.js +25 -21
components/sidebar.js CHANGED
@@ -181,8 +181,107 @@ class AppSidebar extends HTMLElement {
181
  <div id="pdf-name" class="file-name">No file selected</div>
182
  </div>
183
  </div>
184
-
185
  <div class="section">
186
  <h3><i data-feather="download"></i> Export</h3>
187
  <button id="btn-download-pdf" class="action-btn btn-primary">
188
- <i data
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
181
  <div id="pdf-name" class="file-name">No file selected</div>
182
  </div>
183
  </div>
 
184
  <div class="section">
185
  <h3><i data-feather="download"></i> Export</h3>
186
  <button id="btn-download-pdf" class="action-btn btn-primary">
187
+ <i data-feather="download"></i> Download PDF
188
+ </button>
189
+ <button id="btn-download-all" class="action-btn btn-secondary">
190
+ <i data-feather="download-cloud"></i> Download All
191
+ </button>
192
+ <button id="btn-qr-modal" class="action-btn btn-indigo">
193
+ <i data-feather="grid"></i> Add QR & Download
194
+ </button>
195
+ </div>
196
+
197
+ <div class="section">
198
+ <h3><i data-feather="layout"></i> Layout Management</h3>
199
+ <div class="form-group">
200
+ <input type="text" id="layout-name-input" placeholder="Layout name" class="form-control mb-2">
201
+ </div>
202
+ <div class="form-group">
203
+ <input type="file" id="layout-import" accept=".json" class="hidden">
204
+ <label for="layout-import" class="file-label">
205
+ <i data-feather="upload"></i> Import Layout
206
+ </label>
207
+ <div id="layout-import-name" class="file-name">No file selected</div>
208
+ </div>
209
+ <button id="btn-export-layout" class="action-btn btn-secondary">
210
+ <i data-feather="save"></i> Export Layout
211
+ </button>
212
+ <button id="btn-save-layout" class="action-btn btn-primary">
213
+ <i data-feather="database"></i> Save to History
214
+ </button>
215
+ <button id="btn-new-layout" class="action-btn btn-secondary">
216
+ <i data-feather="file-plus"></i> New Layout
217
+ </button>
218
+ </div>
219
+ </div>
220
+
221
+ <!-- Design Mode Sidebar Content -->
222
+ <div id="sidebar-design" style="display: none;">
223
+ <div class="section">
224
+ <h3><i data-feather="sliders"></i> Field Properties</h3>
225
+ <div id="no-field-selected" class="text-center py-4 text-slate-500">
226
+ <i data-feather="mouse-pointer" class="w-8 h-8 mx-auto mb-2"></i>
227
+ <p>Select a field to edit</p>
228
+ </div>
229
+ <div id="field-controls" style="display: none;">
230
+ <div class="form-group">
231
+ <label>Field ID</label>
232
+ <div id="prop-id" class="font-mono text-sm p-2 bg-slate-100 dark:bg-slate-700 rounded"></div>
233
+ </div>
234
+ <div class="grid grid-cols-2 gap-2">
235
+ <div class="form-group">
236
+ <label for="prop-x">X Position</label>
237
+ <input type="number" id="prop-x" class="form-control" step="1">
238
+ </div>
239
+ <div class="form-group">
240
+ <label for="prop-y">Y Position</label>
241
+ <input type="number" id="prop-y" class="form-control" step="1">
242
+ </div>
243
+ </div>
244
+ <div class="form-group">
245
+ <label for="prop-size">Font Size</label>
246
+ <input type="number" id="prop-size" class="form-control" min="8" max="72">
247
+ </div>
248
+ <div class="form-group">
249
+ <label for="prop-weight">Font Weight</label>
250
+ <select id="prop-weight" class="form-control">
251
+ <option value="normal">Normal</option>
252
+ <option value="bold">Bold</option>
253
+ <option value="lighter">Light</option>
254
+ </select>
255
+ </div>
256
+ <div class="form-group">
257
+ <label for="prop-color">Text Color</label>
258
+ <input type="color" id="prop-color" class="form-control h-10">
259
+ </div>
260
+ </div>
261
+ </div>
262
+
263
+ <div class="section">
264
+ <h3><i data-feather="layout"></i> Layout Actions</h3>
265
+ <div class="form-group">
266
+ <input type="text" id="design-layout-name" placeholder="Layout name" class="form-control mb-2">
267
+ </div>
268
+ <button id="btn-export-design" class="action-btn btn-secondary">
269
+ <i data-feather="save"></i> Export Layout
270
+ </button>
271
+ <button id="btn-save-design" class="action-btn btn-primary">
272
+ <i data-feather="database"></i> Save to History
273
+ </button>
274
+ <button id="btn-new-design" class="action-btn btn-secondary">
275
+ <i data-feather="file-plus"></i> New Layout
276
+ </button>
277
+ </div>
278
+ </div>
279
+ `;
280
+
281
+ // Icons
282
+ feather.replace();
283
+ }
284
+ }
285
+
286
+ customElements.define('app-sidebar', AppSidebar);
287
+
script.js CHANGED
@@ -86,6 +86,11 @@ function setupGlobalListeners() {
86
  document.getElementById('btn-save-layout')?.addEventListener('click', saveLayoutToDB);
87
  document.getElementById('btn-new-layout')?.addEventListener('click', newLayout);
88
  document.getElementById('layout-import')?.addEventListener('change', (e) => importLayout(e.target.files[0]));
 
 
 
 
 
89
  // View Switching
90
  document.querySelectorAll('.tab-btn').forEach(btn => {
91
  btn.addEventListener('click', () => switchTab(btn.dataset.tab));
@@ -728,9 +733,8 @@ function updateTemplateZoom() {
728
  }
729
  // --- Export & Generation ---
730
  async function exportLayout() {
731
- const layout = await saveLayoutToStorage();
732
- const name = document.getElementById('layout-name-input').value || layout.metadata.name || 'layout';
733
- layout.metadata.name = name;
734
 
735
  const blob = new Blob([JSON.stringify(layout, null, 2)], { type: 'application/json' });
736
  const link = document.createElement('a');
@@ -740,7 +744,6 @@ async function exportLayout() {
740
 
741
  toast('Layout Exported', 'success');
742
  }
743
-
744
  async function importLayout(file) {
745
  if (!file || !file.name.endsWith('.json')) {
746
  toast('Please select a layout JSON file', 'error');
@@ -759,24 +762,18 @@ async function importLayout(file) {
759
 
760
  state.currentLayoutConfig = layout;
761
  applyLayoutConfig(layout);
762
-
763
  // Update form inputs
764
- document.getElementById('layout-name-input').value = layout.metadata?.name || 'Imported Layout';
 
 
 
765
 
766
- // Load background images if they are base64
767
- layout.pages.forEach(pageConfig => {
768
- if (pageConfig.background && pageConfig.background.startsWith('data:')) {
769
- if (pageConfig.id === 'page1') {
770
- state.bg1B64 = pageConfig.background;
771
- } else if (pageConfig.id === 'page2') {
772
- state.bg2B64 = pageConfig.background;
773
- }
774
- }
775
- });
776
 
777
  toast('Layout Imported Successfully', 'success');
778
  state.isLayoutLoaded = true;
779
- } catch (err) {
780
  toast('Failed to import layout: ' + err.message, 'error');
781
  debugLog(err);
782
  }
@@ -886,13 +883,15 @@ async function importLayout(file) {
886
  }
887
  state.currentLayoutConfig = layout;
888
  applyLayoutConfig(layout);
889
-
890
  // Update form inputs
891
- document.getElementById('layout-name-input').value = layout.metadata?.name || 'Unnamed Layout';
 
 
 
892
 
893
  toast('Layout Imported Successfully', 'success');
894
  state.isLayoutLoaded = true;
895
- } catch (err) {
896
  toast('Failed to import layout: ' + err.message, 'error');
897
  debugLog(err);
898
  }
@@ -942,7 +941,12 @@ function newLayout() {
942
  metadata: {}
943
  };
944
  state.isLayoutLoaded = false;
945
- state.currentLayoutName = 'New Layout';
 
 
 
 
 
946
 
947
  deselectField();
948
  localStorage.removeItem('pdf_field_config');
 
86
  document.getElementById('btn-save-layout')?.addEventListener('click', saveLayoutToDB);
87
  document.getElementById('btn-new-layout')?.addEventListener('click', newLayout);
88
  document.getElementById('layout-import')?.addEventListener('change', (e) => importLayout(e.target.files[0]));
89
+
90
+ // Design Mode Actions
91
+ document.getElementById('btn-export-design')?.addEventListener('click', exportLayout);
92
+ document.getElementById('btn-save-design')?.addEventListener('click', saveLayoutToDB);
93
+ document.getElementById('btn-new-design')?.addEventListener('click', newLayout);
94
  // View Switching
95
  document.querySelectorAll('.tab-btn').forEach(btn => {
96
  btn.addEventListener('click', () => switchTab(btn.dataset.tab));
 
733
  }
734
  // --- Export & Generation ---
735
  async function exportLayout() {
736
+ const layout = saveLayoutToStorage();
737
+ const name = layout.metadata.name || 'layout';
 
738
 
739
  const blob = new Blob([JSON.stringify(layout, null, 2)], { type: 'application/json' });
740
  const link = document.createElement('a');
 
744
 
745
  toast('Layout Exported', 'success');
746
  }
 
747
  async function importLayout(file) {
748
  if (!file || !file.name.endsWith('.json')) {
749
  toast('Please select a layout JSON file', 'error');
 
762
 
763
  state.currentLayoutConfig = layout;
764
  applyLayoutConfig(layout);
 
765
  // Update form inputs
766
+ const layoutNameInput = document.getElementById('layout-name-input') || document.getElementById('design-layout-name');
767
+ if (layoutNameInput) {
768
+ layoutNameInput.value = layout.metadata?.name || 'Imported Layout';
769
+ }
770
 
771
+ // Apply layout
772
+ applyLayoutConfig(layout);
 
 
 
 
 
 
 
 
773
 
774
  toast('Layout Imported Successfully', 'success');
775
  state.isLayoutLoaded = true;
776
+ } catch (err) {
777
  toast('Failed to import layout: ' + err.message, 'error');
778
  debugLog(err);
779
  }
 
883
  }
884
  state.currentLayoutConfig = layout;
885
  applyLayoutConfig(layout);
 
886
  // Update form inputs
887
+ const layoutNameInput = document.getElementById('layout-name-input') || document.getElementById('design-layout-name');
888
+ if (layoutNameInput) {
889
+ layoutNameInput.value = layout.metadata?.name || 'Unnamed Layout';
890
+ }
891
 
892
  toast('Layout Imported Successfully', 'success');
893
  state.isLayoutLoaded = true;
894
+ } catch (err) {
895
  toast('Failed to import layout: ' + err.message, 'error');
896
  debugLog(err);
897
  }
 
941
  metadata: {}
942
  };
943
  state.isLayoutLoaded = false;
944
+
945
+ // Reset layout name input
946
+ const layoutNameInput = document.getElementById('layout-name-input') || document.getElementById('design-layout-name');
947
+ if (layoutNameInput) {
948
+ layoutNameInput.value = 'New Layout';
949
+ }
950
 
951
  deselectField();
952
  localStorage.removeItem('pdf_field_config');