If you look at this CssToInlineStyles class on github. It is essentially trying to make CSS all inline. However, it has prio开发者_运维技巧rity all wrong when it comes to the already inline CSS being overwritten by the definitions in the style block!
I think on line 312 I need to put in a condition to make sure the inline styles already present should never be overwritten by any definition in the CSS properties. But it looks like it isn't that easy!
Any ideas? I've tried contacting the owner of the class, no reply. If I fix this, I'll make a pull request on github.
Update
If you have the following in a style block:
p{font-family:Arial;font-size:0.9em;color:#53534a;}
.webv {font-size: 10px; padding:5px 0 0 150px}
Then if you have a p tag like so:
<p class="webv" >Testing</p>
Then the class .webv
needs to take effect in terms of font-size
.
Update 2
Hakre's solution works well but there is one case it doesn't work. For example if you have this style block:
*{padding:0;margin:0;}
h1{padding-bottom:10px;}
The padding for the h1 is still 0, the second h1 doesn't take over which it should! So it looks like this:
<h1 style="padding:0; margin:0;">Test</h1>
If you don't want to have them overwritten you first need to obtain the existing properties from the HTML source.
You then can either check if those are already set before setting the new to prevent overwriting, or you just overwrite them later on to the default ones.
As existing properties are already extracted before, it might work as:
foreach($rule['properties'] as $key => $value)
if(!isset($properties[$key])) $properties[$key] = $value;
(this will overwrite NULL
properties, in case it's a problem, use array_key_exists
instead of isset
).
You should add a flag to the class/function to change the behavior, so the current behavior does not break but you make your needs optional.
Edit: As multiple rules can apply, the next rule will not overwrite something of the previous rule (which it should but is prevented by the edit above), so this needs more control to preserve the original properties:
$originalProperties = $properties;
foreach($rule['properties'] as $key => $value) $properties[$key] = $value;
$properties = $originalProperties + $properties;
Edit 2: The second suggestion won't work as well. Basically there is need to get the very original values because that function changes the style attribute while it iterates over rules and elements. The same element can become modified twice, so the $originalProperties
are not really the original properties but can be modified ones.
Maybe this works with spl_object_hash
to create a consistent id/key for each element, but I'm not sure. Maybe DomElement offers something comparable internally, but I have not found such (which should fit better). With a specific key/id per each concrete element, only on first appearance, the very original properties can be preserved:
$elementId = spl_object_hash($element);
if(!isset($originalProperties[$elementId]))
{
$originalProperties[$elementId] = $properties;
$originalElements[$elementId] = $element; // Needed to make spl_object_hash work
}
foreach($rule['properties'] as $key => $value) $properties[$key] = $value;
$properties = $originalProperties[$elementId] + $properties;
You can use !important
after the CSS definition to make sure it takes priority.
E.g.
.yourstyle
{
color: #000 !important;
}
Fortunately the owner of this class has fixed this issue! The updated class can be found here.
精彩评论