diff --git a/templates/play.html b/templates/play.html index fb406600..ab635e79 100644 --- a/templates/play.html +++ b/templates/play.html @@ -342,6 +342,26 @@ screenData.elements.filter(function(e){ return !e.parent_id; }).forEach(function(el) { const wrapper = screenDiv.querySelector('.playElement[data-el-id="' + el.id + '"] .playElementInner'); if (!wrapper || !el.rendered_html || el.rendered_html.indexOf(PLACEHOLDER_OPEN) === -1) return; + + // Avant de regénérer ce sous-arbre depuis le HTML D'ORIGINE (nécessaire + // pour ne pas laisser les valeurs d'un mail précédent affichées, voir + // plus haut), sauvegarde l'état visuel TRANSITOIRE posé par une action + // "Modifier un élément" (jamais enregistré en base — voir + // applyElementProperty) sur cet élément ou l'un de ses descendants, + // pour le réappliquer après. Sans ça, un panneau rendu visible par + // cette action (ex. "mail content") redevenait invisible à CHAQUE + // rafraîchissement de données, y compris pour un changement de donnée + // sans rapport avec lui — puisque wrapper.innerHTML = html ci-dessous + // recrée entièrement ses nœuds à partir de leur état PAR DÉFAUT. + const savedState = {}; + wrapper.querySelectorAll('[data-element-id]').forEach(function(node) { + savedState[node.dataset.elementId] = { + style: node.getAttribute('style') || '', + className: node.className, + dataset: Object.assign({}, node.dataset), + }; + }); + let html = el.rendered_html; Object.keys(row).forEach(function(fieldName) { if (fieldName === 'id') return; @@ -351,6 +371,14 @@ html = html.split(PLACEHOLDER_OPEN + fieldName + PLACEHOLDER_CLOSE).join(tmp.innerHTML); }); wrapper.innerHTML = html; + + wrapper.querySelectorAll('[data-element-id]').forEach(function(node) { + const saved = savedState[node.dataset.elementId]; + if (!saved) return; + node.setAttribute('style', saved.style); + node.className = saved.className; + Object.assign(node.dataset, saved.dataset); + }); }); }