aboutsummaryrefslogtreecommitdiff
path: root/internal/admin/static/cardeditor.js
diff options
context:
space:
mode:
Diffstat (limited to 'internal/admin/static/cardeditor.js')
-rw-r--r--internal/admin/static/cardeditor.js78
1 files changed, 61 insertions, 17 deletions
diff --git a/internal/admin/static/cardeditor.js b/internal/admin/static/cardeditor.js
index f2316e1..8ff5eaf 100644
--- a/internal/admin/static/cardeditor.js
+++ b/internal/admin/static/cardeditor.js
@@ -175,7 +175,7 @@ function ced_selectSearchResult(el) {
function ced_persistSearchToData(input, value) {
var ed = window._editorData;
- var dataPath = input.getAttribute('data-data-path');
+ var dataPath = input.getAttribute('data-field-path');
if (!ed || !dataPath) return;
var m = dataPath.match(/^(.+)\[(\d+)\]\.(.+)$/);
if (m) {
@@ -195,6 +195,48 @@ function ced_persistSearchToData(input, value) {
}
}
+function ced_setPathInData(ed, dataPath, value) {
+ if (!ed || !dataPath) return;
+ var m = dataPath.match(/^(.+)\[(\d+)\]\.(.+)$/);
+ if (m) {
+ if (!ed[m[1]]) ed[m[1]] = [];
+ if (!ed[m[1]][m[2]]) ed[m[1]][m[2]] = {};
+ ed[m[1]][m[2]][m[3]] = value;
+ } else {
+ var m2 = dataPath.match(/^(.+)\.(.+)$/);
+ if (m2) {
+ if (!ed[m2[1]]) ed[m2[1]] = {};
+ ed[m2[1]][m2[2]] = value;
+ } else {
+ ed[dataPath] = value;
+ }
+ }
+}
+
+function ced_syncDOMToData(ed) {
+ if (!ed) return;
+ var inputs = document.querySelectorAll('[data-field-path]');
+ for (var i = 0; i < inputs.length; i++) {
+ var el = inputs[i];
+ var dataPath = el.getAttribute('data-field-path');
+ if (!dataPath) continue;
+ var val;
+ if (el.tagName === 'TEXTAREA') {
+ val = el.value;
+ } else if (el.type === 'checkbox') {
+ val = el.checked;
+ } else if (el.type === 'number') {
+ var raw = el.value.trim();
+ val = raw === '' ? '' : (parseFloat(raw) || 0);
+ } else if (el.tagName === 'SELECT') {
+ val = el.value;
+ } else {
+ val = el.value;
+ }
+ ced_setPathInData(ed, dataPath, val);
+ }
+}
+
function ced_resolveDataPath(obj, path) {
return path.split('.').reduce(function(o, k) {
if (o === undefined || o === null) return undefined;
@@ -236,6 +278,17 @@ function ced_renderField(sec, f, data, idx, subPath, optStyle, cardPathFn, field
if (!showIf(sectionData)) hiddenStyle = ' style="display:none"';
}
+ var pfx = cardPathFn(sec);
+ var dp;
+ if (idx >= 0) {
+ dp = pfx + '[' + idx + '].' + key;
+ } else if (subPath) {
+ dp = (pfx ? pfx + '.' : '') + subPath + '.' + key;
+ } else {
+ dp = (pfx ? pfx + '.' : '') + key;
+ }
+ var dpAttr = ' data-field-path="' + escAttr(dp) + '"';
+
function wrap(cls, inner) {
var w = (wide === 'wide') ? ' obj-wide' : '';
if (wide === 'narrow') w = ' obj-narrow';
@@ -244,19 +297,19 @@ function ced_renderField(sec, f, data, idx, subPath, optStyle, cardPathFn, field
}
if (type === 'checkbox') {
- return wrap('obj-field obj-check', '<input type="checkbox" id="' + fid + '"' + (val ? ' checked' : '') + '> <span>' + esc(label) + '</span>');
+ return wrap('obj-field obj-check', '<input type="checkbox" id="' + fid + '"' + (val ? ' checked' : '') + dpAttr + '> <span>' + esc(label) + '</span>');
}
if (type === 'json') {
var jstr = typeof val === 'object' ? JSON.stringify(val) : String(val);
- return wrap('obj-field', '<span>' + esc(label) + '</span><textarea id="' + fid + '" rows="2" placeholder="{}">' + esc(jstr) + '</textarea>');
+ return wrap('obj-field', '<span>' + esc(label) + '</span><textarea id="' + fid + '" rows="2" placeholder="{}"' + dpAttr + '>' + esc(jstr) + '</textarea>');
}
if (type === 'textarea') {
var dstr = typeof val === 'object' ? (Array.isArray(val) ? val.map(function(v){return v.text||'';}).join('\n') : JSON.stringify(val)) : String(val);
- return wrap('obj-field', '<span>' + esc(label) + '</span><textarea id="' + fid + '" rows="3">' + esc(dstr) + '</textarea>');
+ return wrap('obj-field', '<span>' + esc(label) + '</span><textarea id="' + fid + '" rows="3"' + dpAttr + '>' + esc(dstr) + '</textarea>');
}
if (type === 'select') {
var opts = hint ? hint.split('|') : [];
- var inner = '<span>' + esc(label) + '</span><select id="' + fid + '">';
+ var inner = '<span>' + esc(label) + '</span><select id="' + fid + '"' + dpAttr + '>';
opts.forEach(function(o) {
inner += '<option value="' + escAttr(o) + '"' + (String(val) === o ? ' selected' : '') + '>' + esc(o) + '</option>';
});
@@ -265,24 +318,15 @@ function ced_renderField(sec, f, data, idx, subPath, optStyle, cardPathFn, field
}
if (type === 'color') {
var swatch = '<span class="color-swatch" style="background:#' + escAttr(String(val) || '808080') + '"></span>';
- return wrap('obj-field color-field', '<span>' + esc(label) + '</span><div class="obj-color-row">' + swatch + '<input id="' + fid + '" value="' + escAttr(String(val)) + '" class="color-input"></div>');
+ return wrap('obj-field color-field', '<span>' + esc(label) + '</span><div class="obj-color-row">' + swatch + '<input id="' + fid + '" value="' + escAttr(String(val)) + '" class="color-input"' + dpAttr + '></div>');
}
if (type === 'search') {
var entity = searchEntity || 'items';
var ph = hint ? ' placeholder="' + esc(hint) + '"' : ' placeholder="Search ' + entity + '..."';
- var pfx = cardPathFn(sec);
- var dp;
- if (idx >= 0) {
- dp = pfx + '[' + idx + '].' + key;
- } else if (subPath) {
- dp = (pfx ? pfx + '.' : '') + subPath + '.' + key;
- } else {
- dp = (pfx ? pfx + '.' : '') + key;
- }
- return wrap('obj-field obj-search', '<span>' + esc(label) + '</span><div style="position:relative;width:100%"><input id="' + fid + '" value="' + escAttr(String(val)) + '" class="search-input" data-search-type="' + entity + '" data-data-path="' + escAttr(dp) + '"' + ph + '><div class="search-results" style="display:none"></div></div>');
+ return wrap('obj-field obj-search', '<span>' + esc(label) + '</span><div style="position:relative;width:100%"><input id="' + fid + '" value="' + escAttr(String(val)) + '" class="search-input" data-search-type="' + entity + '" data-field-path="' + escAttr(dp) + '"' + ph + '><div class="search-results" style="display:none"></div></div>');
}
var ph = hint ? ' placeholder="' + esc(hint) + '"' : '';
- return wrap('obj-field', '<span>' + esc(label) + '</span><input id="' + fid + '" value="' + escAttr(String(val)) + '"' + ph + '>');
+ return wrap('obj-field', '<span>' + esc(label) + '</span><input id="' + fid + '" value="' + escAttr(String(val)) + '"' + ph + dpAttr + '>');
}
// ---- Subtable row add/remove ----