--- emogrifier.php.orig	2010-05-18 11:34:18.000000000 +0200
+++ emogrifier.php	2010-08-17 01:50:31.055250000 +0200
@@ -61,11 +61,6 @@
 
 		$xpath = new DOMXPath($xmldoc);
 
-        // before be begin processing the CSS file, parse the document and normalize all existing CSS attributes (changes 'DISPLAY: none' to 'display: none');
-        // we wouldn't have to do this if DOMXPath supported XPath 2.0.
-        $nodes = @$xpath->query('//*[@style]');
-        if ($nodes->length > 0) foreach ($nodes as $node) $node->setAttribute('style',preg_replace('/[A-z\-]+(?=\:)/Se',"strtolower('\\0')",$node->getAttribute('style')));
-
 		// get rid of css comment code
 		$re_commentCSS = '/\/\*.*\*\//sU';
 		$css = preg_replace($re_commentCSS,'',$this->css);
@@ -94,6 +89,17 @@
         // now sort the selectors by precedence
         usort($all_selectors, array('self','sortBySelectorPrecedence'));
 
+        // Before be begin processing the CSS file, parse the document and append all inline CSS properties normalized (changes 'DISPLAY: none' to 'display: none') as selectors with full paths, i.e. highest precedence, so they override any CSS selectors.
+        $nodes = @$xpath->query('//*[@style]');
+        if ($nodes->length > 0) {
+          foreach ($nodes as $node) {
+            $style = preg_replace('/[A-z\-]+(?=\:)/Se', "strtolower('\\0')", $node->getAttribute('style'));
+            $all_selectors[] = array('selector' => $this->calculateXPath($node),
+                                     'attributes' => $style,
+            );
+          }
+        }
+
         foreach ($all_selectors as $value) {
 
             // query the body for the xpath selector
@@ -106,7 +112,7 @@
                     $oldStyleArr = $this->cssStyleDefinitionToArray($node->getAttribute('style'));
                     $newStyleArr = $this->cssStyleDefinitionToArray($value['attributes']);
 
-                    // new styles overwrite the old styles (not technically accurate, but close enough)
+                    // new styles overwrite the old styles
                     $combinedArr = array_merge($oldStyleArr,$newStyleArr);
                     $style = '';
                     foreach ($combinedArr as $k => $v) $style .= (strtolower($k) . ':' . $v . ';');
@@ -154,6 +160,10 @@
 	// right now we only support CSS 1 selectors, but include CSS2/3 selectors are fully possible.
 	// http://plasmasturm.org/log/444/
 	private function translateCSStoXpath($css_selector) {
+      if (substr($css_selector, 0, 1) == '/') {
+        // already an XPath expression
+        return $css_selector;
+      }
 	    // returns an Xpath selector
 	    $search = array(
 	                       '/\s+>\s+/', // Matches any F element that is a child of an element E.
@@ -187,5 +197,21 @@
 	    }
 	    return $retArr;
 	}
+
+  // Calculate full path of a DOM node.
+  // http://stackoverflow.com/questions/2643533/php-getting-xpath-of-a-domnode
+  function calculateXPath(DOMNode $node) {
+    $xpath = '';
+    $q = new DOMXPath($node->ownerDocument);
+
+    do {
+        $position = 1 + $q->query('preceding-sibling::*[name()="' . $node->nodeName . '"]', $node)->length;
+        $xpath    = '/' . $node->nodeName . '[' . $position . ']' . $xpath;
+        $node     = $node->parentNode;
+    }
+    while (!$node instanceof DOMDocument);
+
+    return $xpath;
+  }
 }
 ?>
\ No newline at end of file
