From a5d4d4c608083ffa8e388cfab0576980115fa8ee Mon Sep 17 00:00:00 2001 From: Shikiryu Date: Wed, 16 Mar 2011 10:59:32 +0000 Subject: [PATCH] managed | path can be filled (experimental) | colors managed as specifications | path relative & absolute | 'cm' & 'in' virtualized | element param getter factorized --- svgtoimage.php | 485 +++++++++++++++++++++++++++++++++++++++++++------ 1 file changed, 426 insertions(+), 59 deletions(-) diff --git a/svgtoimage.php b/svgtoimage.php index a31a2d0..61c4507 100644 --- a/svgtoimage.php +++ b/svgtoimage.php @@ -3,6 +3,7 @@ // prendre en compte l'opacité grâce à imagecolorallocatealpha ? // ajout de title // ajout de 0 +// refaire path en GROS polygon include 'log.php'; @@ -18,6 +19,7 @@ class SVGTOIMAGE{ protected $_height; protected $_showDesc = false; protected $_desc; + protected $_currentOptions; private $transparentColor = array(0,0,255); public $_debug = true; // change to false to stop debug mode @@ -33,11 +35,159 @@ class SVGTOIMAGE{ 'z' => 'EndingLine', ); - /* array of color names => hex color + /* array of color names => rgb color because some svg creator uses them + used http://www.yoyodesign.org/doc/w3c/svg1/types.html#ColorKeywords */ private $colors = array( - 'black' => '#000000', + 'aliceblue'=>array(240, 248, 255), + 'antiquewhite'=>array(250, 235, 215), + 'aqua'=>array( 0, 255, 255), + 'aquamarine'=>array(127, 255, 212), + 'azure'=>array(240, 255, 255), + 'beige'=>array(245, 245, 220), + 'bisque'=>array(255, 228, 196), + 'black'=>array( 0, 0, 0), + 'blanchedalmond'=>array(255, 235, 205), + 'blue'=>array( 0, 0, 255), + 'blueviolet'=>array(138, 43, 226), + 'brown'=>array(165, 42, 42), + 'burlywood'=>array(222, 184, 135), + 'cadetblue'=>array( 95, 158, 160), + 'chartreuse'=>array(127, 255, 0), + 'chocolate'=>array(210, 105, 30), + 'coral'=>array(255, 127, 80), + 'cornflowerblue'=>array(100, 149, 237), + 'cornsilk'=>array(255, 248, 220), + 'crimson'=>array(220, 20, 60), + 'cyan'=>array( 0, 255, 255), + 'darkblue'=>array( 0, 0, 139), + 'darkcyan'=>array( 0, 139, 139), + 'darkgoldenrod'=>array(184, 134, 11), + 'darkgray'=>array(169, 169, 169), + 'darkgreen'=>array( 0, 100, 0), + 'darkgrey'=>array(169, 169, 169), + 'darkkhaki'=>array(189, 183, 107), + 'darkmagenta'=>array(139, 0, 139), + 'darkolivegreen'=>array( 85, 107, 47), + 'darkorange'=>array(255, 140, 0), + 'darkorchid'=>array(153, 50, 204), + 'darkred'=>array(139, 0, 0), + 'darksalmon'=>array(233, 150, 122), + 'darkseagreen'=>array(143, 188, 143), + 'darkslateblue'=>array( 72, 61, 139), + 'darkslategray'=>array( 47, 79, 79), + 'darkslategrey'=>array( 47, 79, 79), + 'darkturquoise'=>array( 0, 206, 209), + 'darkviolet'=>array(148, 0, 211), + 'deeppink'=>array(255, 20, 147), + 'deepskyblue'=>array( 0, 191, 255), + 'dimgray'=>array(105, 105, 105), + 'dimgrey'=>array(105, 105, 105), + 'dodgerblue'=>array( 30, 144, 255), + 'firebrick'=>array(178, 34, 34), + 'floralwhite'=>array(255, 250, 240), + 'forestgreen'=>array( 34, 139, 34), + 'fuchsia'=>array(255, 0, 255), + 'gainsboro'=>array(220, 220, 220), + 'ghostwhite'=>array(248, 248, 255), + 'gold'=>array(255, 215, 0), + 'goldenrod'=>array(218, 165, 32), + 'gray'=>array(128, 128, 128), + 'grey'=>array(128, 128, 128), + 'green'=>array( 0, 128, 0), + 'greenyellow'=>array(173, 255, 47), + 'honeydew'=>array(240, 255, 240), + 'hotpink'=>array(255, 105, 180), + 'indianred'=>array(205, 92, 92), + 'indigo'=>array( 75, 0, 130), + 'ivory'=>array(255, 255, 240), + 'khaki'=>array(240, 230, 140), + 'lavender'=>array(230, 230, 250), + 'lavenderblush'=>array(255, 240, 245), + 'lawngreen'=>array(124, 252, 0), + 'lemonchiffon'=>array(255, 250, 205), + 'lightblue'=>array(173, 216, 230), + 'lightcoral'=>array(240, 128, 128), + 'lightcyan'=>array(224, 255, 255), + 'lightgoldenrodyellow'=>array(250, 250, 210), + 'lightgray'=>array(211, 211, 211), + 'lightgreen'=>array(144, 238, 144), + 'lightgrey'=>array(211, 211, 211), + 'lightpink'=>array(255, 182, 193), + 'lightsalmon'=>array(255, 160, 122), + 'lightseagreen'=>array( 32, 178, 170), + 'lightskyblue'=>array(135, 206, 250), + 'lightslategray'=>array(119, 136, 153), + 'lightslategrey'=>array(119, 136, 153), + 'lightsteelblue'=>array(176, 196, 222), + 'lightyellow'=>array(255, 255, 224), + 'lime'=>array( 0, 255, 0), + 'limegreen'=>array( 50, 205, 50), + 'linen'=>array(250, 240, 230), + 'magenta'=>array(255, 0, 255), + 'maroon'=>array(128, 0, 0), + 'mediumaquamarine'=>array(102, 205, 170), + 'mediumblue'=>array( 0, 0, 205), + 'mediumorchid'=>array(186, 85, 211), + 'mediumpurple'=>array(147, 112, 219), + 'mediumseagreen'=>array( 60, 179, 113), + 'mediumslateblue'=>array(123, 104, 238), + 'mediumspringgreen'=>array( 0, 250, 154), + 'mediumturquoise'=>array( 72, 209, 204), + 'mediumvioletred'=>array(199, 21, 133), + 'midnightblue'=>array( 25, 25, 112), + 'mintcream'=>array(245, 255, 250), + 'mistyrose'=>array(255, 228, 225), + 'moccasin'=>array(255, 228, 181), + 'navajowhite'=>array(255, 222, 173), + 'navy'=>array( 0, 0, 128), + 'oldlace'=>array(253, 245, 230), + 'olive'=>array(128, 128, 0), + 'olivedrab'=>array(107, 142, 35), + 'orange'=>array(255, 165, 0), + 'orangered'=>array(255, 69, 0), + 'orchid'=>array(218, 112, 214), + 'palegoldenrod'=>array(238, 232, 170), + 'palegreen'=>array(152, 251, 152), + 'paleturquoise'=>array(175, 238, 238), + 'palevioletred'=>array(219, 112, 147), + 'papayawhip'=>array(255, 239, 213), + 'peachpuff'=>array(255, 218, 185), + 'peru'=>array(205, 133, 63), + 'pink'=>array(255, 192, 203), + 'plum'=>array(221, 160, 221), + 'powderblue'=>array(176, 224, 230), + 'purple'=>array(128, 0, 128), + 'red'=>array(255, 0, 0), + 'rosybrown'=>array(188, 143, 143), + 'royalblue'=>array( 65, 105, 225), + 'saddlebrown'=>array(139, 69, 19), + 'salmon'=>array(250, 128, 114), + 'sandybrown'=>array(244, 164, 96), + 'seagreen'=>array( 46, 139, 87), + 'seashell'=>array(255, 245, 238), + 'sienna'=>array(160, 82, 45), + 'silver'=>array(192, 192, 192), + 'skyblue'=>array(135, 206, 235), + 'slateblue'=>array(106, 90, 205), + 'slategray'=>array(112, 128, 144), + 'slategrey'=>array(112, 128, 144), + 'snow'=>array(255, 250, 250), + 'springgreen'=>array( 0, 255, 127), + 'steelblue'=>array( 70, 130, 180), + 'tan'=>array(210, 180, 140), + 'teal'=>array( 0, 128, 128), + 'thistle'=>array(216, 191, 216), + 'tomato'=>array(255, 99, 71), + 'turquoise'=>array( 64, 224, 208), + 'violet'=>array(238, 130, 238), + 'wheat'=>array(245, 222, 179), + 'white'=>array(255, 255, 255), + 'whitesmoke'=>array(245, 245, 245), + 'yellow'=>array(255, 255, 0), + 'yellowgreen'=>array(154, 205, 50) + /*'black' => '#000000', 'red' => '#FF0000', 'white' => '#FFFFFF', 'turquoise' => '#00FFFF', @@ -55,7 +205,7 @@ class SVGTOIMAGE{ 'pastel green' => '#00FF00', 'forest green' => '#808000', 'pink' => '#FF00FF', - 'grass green' => '#408080', + 'grass green' => '#408080',*/ ); /* @@ -74,6 +224,8 @@ class SVGTOIMAGE{ * @return : instance of this class */ public static function load($file){ + $log = new Log('load.dat'); + $log->message('loading : '.$file); $svg = file_get_contents($file); return new SVGTOIMAGE($svg); } @@ -171,18 +323,38 @@ class SVGTOIMAGE{ return $imageSize; } + /** + * @param string size of picture or element + * @return int "real" size of element. To eliminate SVG with centimeters + */ + private function _getSizeType($value){ + $value = rtrim($value); + switch(substr($value,-2,2)){ + case 'cm': + return $value * 30; // approximatively + break; + case 'in': + return $value * 12; // approximatively + break; + case 'px': + case 'pt': + default: + return $value; + } + } + /* * @return int final image width */ private function _getImageWidth(){ - return isset($this->_width) ? $this->_width : $this->_svgXML->attributes()->width; + return isset($this->_width) ? $this->_width : $this->_getSizeType($this->_svgXML->attributes()->width); } /* * @return int final image height */ private function _getImageHeight(){ - return isset($this->_height) ? $this->_height : $this->_svgXML->attributes()->height; + return isset($this->_height) ? $this->_height : $this->_getSizeType($this->_svgXML->attributes()->height); } /* @@ -190,7 +362,7 @@ class SVGTOIMAGE{ * @return array with R | G | B */ private function _parseColor($colorCode){ - if(strlen($colorCode) == 7){ + if(is_string($colorCode) && strlen($colorCode) == 7){ if($this->_debug) $this->_log->message('Parse Color '.$colorCode); return array( base_convert(substr($colorCode, 1, 2), 16, 10), @@ -198,7 +370,7 @@ class SVGTOIMAGE{ base_convert(substr($colorCode, 5, 2), 16, 10), ); } - if(strlen($colorCode) == 4){ + if(is_string($colorCode) && strlen($colorCode) == 4){ if($this->_debug) $this->_log->message('Parse Color '.$colorCode); return array( base_convert(substr($colorCode, 1, 1).substr($colorCode, 1, 1), 16, 10), @@ -206,8 +378,11 @@ class SVGTOIMAGE{ base_convert(substr($colorCode, 3, 1).substr($colorCode, 3, 1), 16, 10), ); } + if(is_array($colorCode) && count($colorCode) == 3){ + return $colorCode; + } if($this->_debug) $this->_log->error('Couleur mal indiquée '.$colorCode); - return array(0,0,0); + return array(0,0,0); // !#FFF || !#FFFFFF || !array(255,255,255) then black } /* @@ -218,9 +393,9 @@ class SVGTOIMAGE{ private function _allocateColor($color){ if($color != '' && array_key_exists(strtolower($color), $this->colors)){ $arrayColor = $this->_parseColor($this->colors[$color]); - }else{ + }elseif($color != ''){ $arrayColor = $this->_parseColor($color); - } + }else return; return imagecolorallocate( $this->_image, $arrayColor[0], $arrayColor[1], $arrayColor[2] ); } @@ -241,6 +416,74 @@ class SVGTOIMAGE{ return $tiret; } + /** + * @param node $element + * @return array options + */ + private function _getParams($element){ + $options = $this->_currentOptions; + foreach($element->attributes() as $name => $value){ + switch($name){ + case 'x': + case 'y': + case 'r': + case 'width': + case 'height': + $options[$name] = $this->_getSizeType($value); + break; + case 'cx': + $options['x'] = $this->_getSizeType($value); + break; + case 'cy': + $options['y'] = $this->_getSizeType($value); + break; + case 'xlink:href': + $options['href'] = $value; + break; + case 'style' : + $allStyle = split('[;:]', $value); + $i = 0; + while ($i < count($allStyle)) { + if($allStyle[$i] == 'display' && $allStyle[$i+1] == 'none') return; // display:none? Stop looking for info + if($allStyle[$i] == 'fill') $options['fill'] = $allStyle[$i+1]; + if($allStyle[$i] == 'stroke') $options['stroke'] = $allStyle[$i+1]; + if($allStyle[$i] == 'stroke-width') $options['strokeWidth'] = $allStyle[$i+1]; + $i=$i+2; + } + break; + case 'd': + case 'points': + $options['path'] = $value; + break; + case 'fill': + $options['fill'] = ($value == 'none') ? '' : $value; + break; + case 'stroke-width' : + $options['strokeWidth'] = $value; + break; + case 'stroke-dasharray' : + $options['strokeDasharray'] = $value; + break; + case 'font-size': + $options['fontSize'] = $value; + break; + case 'font-family': + $options['fontFamily'] = $value; + break; + case 'font-style': + $options['fontStyle'] = $value; + break; + case 'font-weight': + $options['fontWeight'] = $value; + break; + default: + $options[$name] = $value; + break; + } + } + return $options; + } + /* * add the given image from svg to the final image * @param simpleXMLElement @@ -254,7 +497,7 @@ class SVGTOIMAGE{ $href = ''; $transform = ''; $r = 0; - foreach($imageNode->attributes() as $name => $value){ + /*foreach($imageNode->attributes() as $name => $value){ switch($name){ case 'x': $x = $value; break; case 'y': $y = $value; break; @@ -277,7 +520,8 @@ class SVGTOIMAGE{ //if(strripos($value, 'display: none') || strripos($value, 'display:none')) return; break; } - } + }*/ + extract($this->_getParams($imageNode)); if($transform != ''){ $transforms = split('[()]', $transform); $nb = count($transforms); @@ -381,7 +625,7 @@ class SVGTOIMAGE{ $cy=3*($control1Y-$startY); $by=3*($control2Y-$control1Y)-$cy; $ay=$endY-$startY-$cy-$by; - if($this->_debug) $this->_log->message('ax : '.$ax.', ay : '.$ay); + //if($this->_debug) $this->_log->message('ax : '.$ax.', ay : '.$ay); for($t=0; $t<1; $t+=.01) { $xt = $ax * $t * $t * $t + $bx * $t * $t + $cx * $t + $startX; @@ -390,20 +634,90 @@ class SVGTOIMAGE{ } } + + /*EXPERIMENT*/ + + // Calculate the coordinate of the Bezier curve at $t = 0..1 + private function _Bezier_eval($p1,$p2,$p3,$p4,$t) { + // lines between successive pairs of points (degree 1) + $q1 = array((1-$t) * $p1[0] + $t * $p2[0],(1-$t) * $p1[1] + $t * $p2[1]); + $q2 = array((1-$t) * $p2[0] + $t * $p3[0],(1-$t) * $p2[1] + $t * $p3[1]); + $q3 = array((1-$t) * $p3[0] + $t * $p4[0],(1-$t) * $p3[1] + $t * $p4[1]); + // curves between successive pairs of lines. (degree 2) + $r1 = array((1-$t) * $q1[0] + $t * $q2[0],(1-$t) * $q1[1] + $t * $q2[1]); + $r2 = array((1-$t) * $q2[0] + $t * $q3[0],(1-$t) * $q2[1] + $t * $q3[1]); + // final curve between the two 2-degree curves. (degree 3) + return array((1-$t) * $r1[0] + $t * $r2[0],(1-$t) * $r1[1] + $t * $r2[1]); + } + + // Calculate the squared distance between two points + private function _Point_distance2($p1,$p2) { + $dx = $p2[0] - $p1[0]; + $dy = $p2[1] - $p1[1]; + return $dx * $dx + $dy * $dy; + } + + // Convert the curve to a polyline + private function _Bezier_convert($p1,$p2,$p3,$p4,$tolerance) { + $t1 = 0.0; + $prev = $p1; + $t2 = 0.1; + $tol2 = $tolerance * $tolerance; + $result []= $prev[0]; + $result []= $prev[1]; + while ($t1 < 1.0) { + if ($t2 > 1.0) { + $t2 = 1.0; + } + $next = $this->_Bezier_eval($p1,$p2,$p3,$p4,$t2); + $dist = $this->_Point_distance2($prev,$next); + while ($dist > $tol2) { + // Halve the distance until small enough + $t2 = $t1 + ($t2 - $t1) * 0.5; + $next = $this->_Bezier_eval($p1,$p2,$p3,$p4,$t2); + $dist = $this->_Point_distance2($prev,$next); + } + // the image*polygon functions expect a flattened array of coordiantes + $result []= $next[0]; + $result []= $next[1]; + $t1 = $t2; + $prev = $next; + $t2 = $t1 + 0.1; + } + return $result; + } + + // Draw a Bezier curve on an image + private function _Bezier_drawfilled($p1,$p2,$p3,$p4,$color) { + $polygon = $this->_Bezier_convert($p1,$p2,$p3,$p4,0.1); + // if($this->_debug) $this->_log->message('polygon : '.implode(' - ', $polygon)); + // imagefilledpolygon($this->_image,$polygon,count($polygon)/2,$color); + // test + return $polygon; + } + /*END OF EXPERIMENT*/ + + private function _drawPolygon($polygon, $stroke, $fill = ''){ + if($fill != '' && count($polygon) > 6){ + imagefilledpolygon($this->_image,$polygon,count($polygon)/2,$colorFill); + }elseif(count($polygon) > 6){ + imagepolygon($this->_image, $polygon, count($polygon)/2, IMG_COLOR_STYLED); + } + } + + /* * add path/lineS/polyline whatever you name it. * @param simpleXMLElement * @return lines on the final image via _drawLine */ private function _parsePath($pathNode){ - // imagesetbrush - // imagesetstyle (pour dotted, dashed etc) $path = ''; $strokeWidth = 1; $fill = ''; $stroke = ''; $strokeDasharray = ''; - foreach($pathNode->attributes() as $name=>$value){ + /*foreach($pathNode->attributes() as $name=>$value){ switch($name){ case 'd': case 'points': $path = $value; break; case 'stroke': $stroke = $value; break; @@ -422,7 +736,8 @@ class SVGTOIMAGE{ //if(strripos($value, 'display: none') || strripos($value, 'display:none')) return; break; } - } + }*/ + extract($this->_getParams($pathNode)); if(strtolower(substr($path, 0,1)) != 'm' && !is_numeric(substr($path, 0,1))){ if($this->_debug) $this->_log->error('Mauvais path rencontré : '.$path); return; @@ -432,7 +747,8 @@ class SVGTOIMAGE{ if($this->_debug && !$thickness) $this->_log->error('Erreur dans la mise en place de l\'épaisseur du trait'); else $this->_log->message('épaisseur du trait à : '.$this->_parseInt($strokeWidth)); $colorStroke = $stroke != '' ? $this->_allocateColor((string)$stroke) : $this->_allocateColor('black'); - $colorFill = $fill != '' ? $this->_allocateColor((string)$fill) : $this->_allocateColor('black'); + $colorFill = $fill != '' ? $this->_allocateColor((string)$fill) : ''; + //$colorFill = $fill != '' ? $this->_allocateColor((string)$fill) : $this->_allocateColor('black'); if($strokeDasharray != ''){ $strokeDasharray = explode(',', $strokeDasharray); imagesetstyle ( $this->_image , $this->_getDashedStroke($strokeDasharray[0], $strokeDasharray[1], $colorStroke )); @@ -461,13 +777,13 @@ class SVGTOIMAGE{ $j++; } }while(isset($pathArray[$j])); - if($this->_debug) $this->_log->message('Path reconstruit ! '.implode(', ',$pathArray)); + //if($this->_debug) $this->_log->message('Path reconstruit ! '.implode(', ',$pathArray)); } $nbArray = count($pathArray); - $nbLine = (($nbArray-1)/2)-1; - + //$nbLine = (($nbArray-1)/2)-1; + $polyPoints = array(); $i = 0; $lastX = 0; $lastY = 0; @@ -476,6 +792,14 @@ class SVGTOIMAGE{ while ($i < $nbArray) { // Changement de départ if(strtolower(substr($pathArray[$i], 0, 1)) == 'm'){ + if(isset($pathArray[$i-1])){ + $this->_drawPolygon($polyPoints, $colorStroke, $colorFill); + $polyPoints = array(); + $lastX = 0; + $lastY = 0; + $lastMX = 0; + $lastMY = 0; + } $lastX = $this->_parseInt($pathArray[$i]); $lastMX = $this->_parseInt($pathArray[$i]); $lastY = $this->_parseInt($pathArray[$i+1]); @@ -484,38 +808,68 @@ class SVGTOIMAGE{ $i=$i+2; // Ligne }elseif(strtolower(substr($pathArray[$i], 0, 1)) == 'l' || (is_numeric($pathArray[$i]) && strtolower($lastOpe) == 'l')){ - $newX = $this->_parseInt($pathArray[$i]); - $newY = $this->_parseInt($pathArray[$i+1]); - $this->_drawLine($lastX , $lastY , $newX , $newY , IMG_COLOR_STYLED); + if(substr($pathArray[$i], 0, 1) == 'L'){ + $newX = $this->_parseInt($pathArray[$i]); + $newY = $this->_parseInt($pathArray[$i+1]); + }else{ + $newX = $lastX + $this->_parseInt($pathArray[$i]); + $newY = $lastY + $this->_parseInt($pathArray[$i+1]); + } + $polyPoints = array_merge($polyPoints,array($lastX, $lastY, $newX, $newY)); + //$this->_drawLine($lastX , $lastY , $newX , $newY , IMG_COLOR_STYLED); $lastOpe = 'l'; $lastX = $newX; $lastY = $newY; $i=$i+2; // Ligne horizontale }elseif(strtolower(substr($pathArray[$i], 0, 1)) == 'h' || (is_numeric($pathArray[$i]) && strtolower($lastOpe) == 'h')){ - $newX = $this->_parseInt($pathArray[$i]); - $this->_drawLine($lastX , $lastY , $newX , $lastY , IMG_COLOR_STYLED); + if(substr($pathArray[$i], 0, 1) == 'H'){ + $newX = $this->_parseInt($pathArray[$i]); + }else{ + $newX = $lastX + $this->_parseInt($pathArray[$i]); + } + //$this->_drawLine($lastX , $lastY , $newX , $lastY , IMG_COLOR_STYLED); + $polyPoints = array_merge($polyPoints,array($lastX, $lastY, $newX, $newY)); $lastOpe = 'h'; $lastX = $newX; $i++; // Ligne verticale }elseif(strtolower(substr($pathArray[$i], 0, 1)) == 'v' || (is_numeric($pathArray[$i]) && strtolower($lastOpe) == 'v')){ - $newY = $this->_parseInt($pathArray[$i]); - $this->_drawLine($lastX , $lastY , $lastX , $newY , IMG_COLOR_STYLED); + if(substr($pathArray[$i], 0, 1) == 'V'){ + $newY = $this->_parseInt($pathArray[$i]); + }else{ + $newY = $lastY + $this->_parseInt($pathArray[$i]); + } + //$this->_drawLine($lastX , $lastY , $lastX , $newY , IMG_COLOR_STYLED); + $polyPoints = array_merge($polyPoints,array($lastX, $lastY, $newX, $newY)); $lastY = $newY; $lastOpe = 'v'; $i++; // Courbe }elseif(strtolower(substr($pathArray[$i], 0, 1)) == 'c' || (is_numeric($pathArray[$i]) && strtolower($lastOpe) == 'c')){ - $control1x = $this->_parseInt($pathArray[$i]); - $control1y = $this->_parseInt($pathArray[$i+1]); - $control2x = $this->_parseInt($pathArray[$i+2]); - $control2y = $this->_parseInt($pathArray[$i+3]); - $newX = $this->_parseInt($pathArray[$i+4]); - $newY = $this->_parseInt($pathArray[$i+5]); - if($this->_debug) $this->_log->message('Drawing curve : '.$lastX.' - '.$lastY.' - '.$control1x.' - '.$control1y.' - '.$control2x.' - '.$control2y.' - '.$newX.' - '.$newY); + /*SPECIF !!! http://www.w3.org/TR/SVG/paths.html*/ + if(substr($pathArray[$i], 0, 1) == 'C'){ + $control1x = $this->_parseInt($pathArray[$i]); + $control1y = $this->_parseInt($pathArray[$i+1]); + $control2x = $this->_parseInt($pathArray[$i+2]); + $control2y = $this->_parseInt($pathArray[$i+3]); + $newX = $this->_parseInt($pathArray[$i+4]); + $newY = $this->_parseInt($pathArray[$i+5]); + }else{ + $control1x = $lastX + $this->_parseInt($pathArray[$i]); + $control1y = $lastY + $this->_parseInt($pathArray[$i+1]); + $control2x = $lastX + $this->_parseInt($pathArray[$i+2]); + $control2y = $lastY + $this->_parseInt($pathArray[$i+3]); + $newX = $lastX + $this->_parseInt($pathArray[$i+4]); + $newY = $lastY + $this->_parseInt($pathArray[$i+5]); + } - $this->_drawCurve($lastX, $lastY, $control1x, $control1y, $control2x, $control2y, $newX, $newY, IMG_COLOR_STYLED); + /*EXPERIMENT $this->_drawCurve($lastX, $lastY, $control1x, $control1y, $control2x, $control2y, $newX, $newY, IMG_COLOR_STYLED);*/ + //if($fill != ''){ + $polyPoints = array_merge($polyPoints,$this->_Bezier_drawfilled(array($lastX, $lastY),array($control1x, $control1y),array($control2x, $control2y),array($newX, $newY),$colorFill)); + //}else{ + // $this->_drawCurve($lastX, $lastY, $control1x, $control1y, $control2x, $control2y, $newX, $newY, IMG_COLOR_STYLED); + //} $lastX = $newX; $lastY = $newY; @@ -524,7 +878,8 @@ class SVGTOIMAGE{ // Dernière ligne droite }elseif(strtolower(substr($pathArray[$i], 0, 1)) == 'z' || (is_numeric(substr($pathArray[$i], 0, 1)) && strtolower($lastOpe) == 'z')){ if($lastOpe == 'z' && $this->_debug) $this->_log->error('2 bouclages dans une boucle'); - $this->_drawLine($lastX , $lastY , $lastMX , $lastMY , IMG_COLOR_STYLED); + $polyPoints = array_merge($polyPoints,array($lastX, $lastY, $lastMX, $lastMY)); + //$this->_drawLine($lastX , $lastY , $lastMX , $lastMY , IMG_COLOR_STYLED); $lastOpe = 'z'; $i++; // Polyline @@ -534,8 +889,11 @@ class SVGTOIMAGE{ $lastOpe = 'l'; // s'il n'a aucune lettre, c'est une polyline, donc des... lignes. $i=$i+2; } - if($this->_debug) $this->_log->message('counter :'.$i); + //if($this->_debug) $this->_log->message('counter :'.$i); } + + $this->_drawPolygon($polyPoints, $colorStroke, $colorFill); + imagecolordeallocate( $this->_image, $colorStroke); imagecolordeallocate( $this->_image, $colorFill); imagesetthickness ( $this->_image , 1 ); @@ -554,17 +912,18 @@ class SVGTOIMAGE{ $strokeWidth = 1; $fill = ''; $stroke = ''; - foreach($circleNode->attributes() as $name => $value){ + /*foreach($circleNode->attributes() as $name => $value){ switch($name){ - case 'cx': $x = $value; break; - case 'cy': $y = $value; break; - case 'r': $r = $value; break; + case 'cx': $x = $this->_getSizeType($value); break; + case 'cy': $y = $this->_getSizeType($value); break; + case 'r': $r = $this->_getSizeType($value); break; case 'fill': $fill = ($value == 'none') ? '' : $value; break; case 'stroke': $stroke = $value; break; case 'style' : if(strripos($value, 'display: none') || strripos($value, 'display:none')) return; break; case 'stroke-width' : $strokeWidth = $value; break; } - } + }*/ + extract($this->_getParams($circleNode)); if($r == 0) return; if($this->_debug) $this->_log->message('Cercle - x : '.$x.' - y : '.$y.' - rayon : '.$r.'-'.$colorStroke[2].' - épaisseur : '.$strokeWidth); @@ -602,10 +961,10 @@ class SVGTOIMAGE{ $fontFamily = 'SansSerif'; $fontStyle = 'normal'; $fontWeight = 'normal'; - foreach($textNode->attributes() as $name => $value){ + /*foreach($textNode->attributes() as $name => $value){ switch($name){ - case 'x': $x = $value; break; - case 'y': $y = $value; break; + case 'x': $x = $this->_getSizeType($value); break; + case 'y': $y = $this->_getSizeType($value); break; //case 'r': $r = $value; break; // todo case 'fill': $fill = $value; break; case 'font-size': $fontSize = $value; break; @@ -613,7 +972,8 @@ class SVGTOIMAGE{ case 'font-style': $fontStyle = $value; break; case 'font-weight': $fontWeight = $value; break; } - } + }*/ + extract($this->_getParams($textNode)); if($textNode == '') return; @@ -639,14 +999,14 @@ class SVGTOIMAGE{ $stroke = ''; $strokeWidth = 1; $strokeDasharray = ''; - foreach($rectNode->attributes() as $name => $value){ + /*foreach($rectNode->attributes() as $name => $value){ switch($name){ // imagesetstyle (pour dotted, dashed etc) - case 'x': $x = $value; break; - case 'y': $y = $value; break; - case 'r': $r = $value; break; - case 'width': $width = $value; break; - case 'height': $height = $value; break; + case 'x': $x = $this->_getSizeType($value); break; + case 'y': $y = $this->_getSizeType($value); break; + case 'r': $r = $this->_getSizeType($value); break; + case 'width': $width = $this->_getSizeType($value); break; + case 'height': $height = $this->_getSizeType($value); break; case 'fill': $fill = ($value == 'none') ? '' : $value; break; case 'stroke': $stroke = $value; break; case 'stroke-width' : $strokeWidth = $value; break; @@ -665,7 +1025,8 @@ class SVGTOIMAGE{ //if(strripos($value, 'display: none') || strripos($value, 'display:none')) return; break; } - } + }*/ + extract($this->_getParams($rectNode)); if($width == 0 || $height == 0) return; $colorStroke = $this->_allocateColor((string)$stroke); @@ -701,7 +1062,7 @@ class SVGTOIMAGE{ $fill = ''; $stroke = ''; $strokeWidth = 1; - foreach($polyNode->attributes() as $name => $value){ + /*foreach($polyNode->attributes() as $name => $value){ switch($name){ // imagesetstyle (pour dotted, dashed etc) case 'points' : $points = $value; break; @@ -720,7 +1081,8 @@ class SVGTOIMAGE{ //if(strripos($value, 'display: none') || strripos($value, 'display:none')) return; break; } - } + }*/ + extract($this->_getParams($polyNode)); if($points == '') return; $pointArray = split('[ ,]', $points); @@ -750,11 +1112,13 @@ class SVGTOIMAGE{ return imagestring ( $this->_image , 2, 10, $this->_getImageHeight()-20, $desc , imagecolorallocate($this->_image, 255, 255, 255)); } - /* - * ignore group for the moment - * acts like ungrouped + /** + * @param node + * get group attributes to pass it to children + * parse children */ private function _parseGroup($groupNode){ + $this->_currentOptions = $this->_getParams($groupNode); foreach($groupNode->children() as $element){ $this->_chooseParse($element); } @@ -782,6 +1146,8 @@ class SVGTOIMAGE{ $this->_parseGroup($element); if($element->getName() == 'text') $this->_parseText($element); + //if($element->getName() == 'defs') + // $this->_parseDefs($element); //if($element->getName() == 'title') // $this->_parseTitle($element); if($element->getName() == 'desc' && $this->_showDesc) @@ -802,6 +1168,7 @@ class SVGTOIMAGE{ //imageantialias($this->_image, true); // On ne peut pas gérer l'épaisseur des traits si l'antialiasing est activé... lol ? foreach($this->_svgXML->children() as $element){ $this->_chooseParse($element); + $this->_currentOptions = array(); } if($this->_showDesc && $this->_desc != null) $this->_parseDescription($this->_desc); //imagefilter ( $this->_image , IMG_FILTER_SMOOTH, 6);