This commit is contained in:
the-djmaze 2023-02-16 14:02:55 +01:00
parent 5216535278
commit b240c26667
3 changed files with 63 additions and 70 deletions

View file

@ -382,6 +382,10 @@ html.rl-bottom-preview-pane #V-MailMessageView .top-toolbar {
opacity: 0.8; opacity: 0.8;
padding: 0 10px; padding: 0 10px;
margin: 0; margin: 0;
blockquote {
opacity: 1;
}
} }
&.html { &.html {

View file

@ -101,26 +101,29 @@ abstract class HtmlUtils
'object', 'embed', 'applet', 'mocha', 'iframe', 'frame', 'frameset', 'video', 'audio', 'area', 'map', 'object', 'embed', 'applet', 'mocha', 'iframe', 'frame', 'frameset', 'video', 'audio', 'area', 'map',
'head', 'style' 'head', 'style'
); );
foreach ($aRemoveTags as $name) {
$aRemove = array(); $aNodes = $oBody->getElementsByTagName($name);
$sIdRight = \md5(\microtime());
$aNodes = $oBody->getElementsByTagName('*');
foreach ($aNodes as /* @var $oElement \DOMElement */ $oElement) { foreach ($aNodes as /* @var $oElement \DOMElement */ $oElement) {
$sTagNameLower = \strtolower($oElement->nodeName); if (isset($oElement->parentNode)) {
@$oElement->parentNode->removeChild($oElement);
if (\in_array($sTagNameLower, $aRemoveTags)) { }
$aRemove[] = $oElement; }
continue;
} }
// images $xpath = new \DomXpath($oDoc);
if ($oElement->hasAttribute('data-x-src-broken') || $oElement->hasAttribute('data-x-src-hidden')) { foreach ($xpath->query('//*[@data-x-src-broken]') as $oElement) {
$aRemove[] = $oElement; if (isset($oElement->parentNode)) {
continue; @$oElement->parentNode->removeChild($oElement);
} }
if ($oElement->hasAttribute('data-x-src-cid')) { }
foreach ($xpath->query('//*[@data-x-src-hidden]') as $oElement) {
if (isset($oElement->parentNode)) {
@$oElement->parentNode->removeChild($oElement);
}
}
foreach ($xpath->query('//*[@data-x-src-cid]') as $oElement) {
$sCid = $oElement->getAttribute('data-x-src-cid'); $sCid = $oElement->getAttribute('data-x-src-cid');
$oElement->removeAttribute('data-x-src-cid'); $oElement->removeAttribute('data-x-src-cid');
if (!empty($sCid)) { if (!empty($sCid)) {
@ -128,17 +131,16 @@ abstract class HtmlUtils
$oElement->setAttribute('src', 'cid:'.$sCid); $oElement->setAttribute('src', 'cid:'.$sCid);
} }
} }
if ($oElement->hasAttribute('data-x-src')) {
foreach ($xpath->query('//*[@data-x-src]') as $oElement) {
$oElement->setAttribute('src', $oElement->getAttribute('data-x-src')); $oElement->setAttribute('src', $oElement->getAttribute('data-x-src'));
$oElement->removeAttribute('data-x-src'); $oElement->removeAttribute('data-x-src');
} }
foreach ($xpath->query('//*[@data-x-style-url]') as $oElement) {
// style attribute images // style attribute images
$aCid = array();
if ($oElement->hasAttribute('data-x-style-url')) {
$aCid = \array_merge($aCid, \json_decode($oElement->getAttribute('data-x-style-url'), true)); $aCid = \array_merge($aCid, \json_decode($oElement->getAttribute('data-x-style-url'), true));
$oElement->removeAttribute('data-x-style-url'); $oElement->removeAttribute('data-x-style-url');
}
if ($aCid) { if ($aCid) {
foreach ($aCid as $sCidName => $sCid) { foreach ($aCid as $sCidName => $sCid) {
$sCidName = \strtolower(\preg_replace('/([A-Z])/', '-\1', $sCidName)); $sCidName = \strtolower(\preg_replace('/([A-Z])/', '-\1', $sCidName));
@ -158,8 +160,11 @@ abstract class HtmlUtils
} }
} }
} }
}
// Remove all remaining data-* attributes // Remove all remaining data-* attributes
foreach ($xpath->query('//*[@*[starts-with(name(), "data-")]]') as $oElement) {
$sTagNameLower = \strtolower($oElement->nodeName);
if ($oElement->hasAttributes()) { if ($oElement->hasAttributes()) {
foreach ($oElement->attributes as $oAttr) { foreach ($oElement->attributes as $oAttr) {
if ('data-' === \substr(\strtolower($oAttr->nodeName), 0, 5)) { if ('data-' === \substr(\strtolower($oAttr->nodeName), 0, 5)) {
@ -167,8 +172,11 @@ abstract class HtmlUtils
} }
} }
} }
}
if ('img' === $sTagNameLower) { $sIdRight = \md5(\microtime());
$aNodes = $oBody->getElementsByTagName('IMG');
foreach ($aNodes as /* @var $oElement \DOMElement */ $oElement) {
$sSrc = $oElement->getAttribute('src'); $sSrc = $oElement->getAttribute('src');
if ('data:image/' === \strtolower(\substr($sSrc, 0, 11))) { if ('data:image/' === \strtolower(\substr($sSrc, 0, 11))) {
$sHash = \md5($sSrc) . '@' . $sIdRight; $sHash = \md5($sSrc) . '@' . $sIdRight;
@ -176,13 +184,6 @@ abstract class HtmlUtils
$oElement->setAttribute('src', 'cid:'.$sHash); $oElement->setAttribute('src', 'cid:'.$sHash);
} }
} }
}
foreach ($aRemove as /* @var $oElement \DOMElement */ $oElement) {
if (isset($oElement->parentNode)) {
@$oElement->parentNode->removeChild($oElement);
}
}
return '<!DOCTYPE html><html><head><meta http-equiv="Content-Type" content="text/html; charset=utf-8"></head>' return '<!DOCTYPE html><html><head><meta http-equiv="Content-Type" content="text/html; charset=utf-8"></head>'
. $oDoc->saveHTML($oBody) . '</html>'; . $oDoc->saveHTML($oBody) . '</html>';

View file

@ -280,6 +280,8 @@ const
// Recursively examine container nodes and wrap any inline children. // Recursively examine container nodes and wrap any inline children.
fixContainer = ( container, root ) => { fixContainer = ( container, root ) => {
/*
// Live, but very slow
let children = container.childNodes; let children = container.childNodes;
let wrapper = null; let wrapper = null;
let i = 0, l = children.length, child, isBR; let i = 0, l = children.length, child, isBR;
@ -290,16 +292,12 @@ const
if ( !isBR && isInline( child ) if ( !isBR && isInline( child )
// && (root.__squire__._config.blockTag !== 'DIV' || (child.matches && !child.matches(phrasingElements))) // && (root.__squire__._config.blockTag !== 'DIV' || (child.matches && !child.matches(phrasingElements)))
) { ) {
if ( !wrapper ) { wrapper = wrapper || createElement( 'div' );
wrapper = createElement( 'div' );
}
wrapper.append( child ); wrapper.append( child );
--i; --i;
--l; --l;
} else if ( isBR || wrapper ) { } else if ( isBR || wrapper ) {
if ( !wrapper ) { wrapper = wrapper || createElement( 'div' );
wrapper = createElement( 'div' );
}
fixCursor( wrapper, root ); fixCursor( wrapper, root );
if ( isBR ) { if ( isBR ) {
child.replaceWith( wrapper ); child.replaceWith( wrapper );
@ -312,34 +310,24 @@ const
} }
isContainer( child ) && fixContainer( child, root ); isContainer( child ) && fixContainer( child, root );
} }
/* */
// Not live let wrapper, isBR;
// Not live, and fast
[...container.children].forEach(child => { [...container.children].forEach(child => {
isBR = child.nodeName === 'BR'; isBR = child.nodeName === 'BR';
if ( !isBR && isInline( child ) if ( !isBR && isInline( child )
// && (root.__squire__._config.blockTag !== 'DIV' || (child.matches && !child.matches(phrasingElements))) // && (root.__squire__._config.blockTag !== 'DIV' || (child.matches && !child.matches(phrasingElements)))
) { ) {
if ( !wrapper ) { wrapper = wrapper || createElement( 'div' );
wrapper = createElement( 'div' );
}
wrapper.append( child ); wrapper.append( child );
} else if ( isBR || wrapper ) { } else if ( isBR || wrapper ) {
if ( !wrapper ) { wrapper = wrapper || createElement( 'div' );
wrapper = createElement( 'div' );
}
fixCursor( wrapper, root ); fixCursor( wrapper, root );
if ( isBR ) { isBR ? child.replaceWith( wrapper ) : child.before( wrapper );
child.replaceWith( wrapper );
} else {
child.before( wrapper );
}
wrapper = null; wrapper = null;
} }
if ( isContainer( child ) ) { isContainer( child ) && fixContainer( child, root );
fixContainer( child, root );
}
}); });
*/
wrapper && container.append( fixCursor( wrapper, root ) ); wrapper && container.append( fixCursor( wrapper, root ) );
return container; return container;
}, },