Skip to content

Commit 20b2513

Browse files
committed
Fix transformation matrix issues by reverting the coordinates system at the beginning
Fix various style inheritance issues
1 parent 7a15090 commit 20b2513

File tree

13 files changed

+191
-170
lines changed

13 files changed

+191
-170
lines changed

src/Svg/DefaultStyle.php

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
<?php
2+
/**
3+
* @package php-svg-lib
4+
* @link http://github.com/PhenX/php-svg-lib
5+
* @author Fabien Ménager <fabien.menager@gmail.com>
6+
* @license http://www.gnu.org/copyleft/lesser.html GNU Lesser General Public License
7+
*/
8+
9+
namespace Svg;
10+
11+
class DefaultStyle extends Style
12+
{
13+
public $color = '';
14+
public $opacity = 1.0;
15+
16+
public $fill = 'black';
17+
public $fillOpacity = 1.0;
18+
public $fillRule = 'nonzero';
19+
20+
public $stroke = 'none';
21+
public $strokeOpacity = 1.0;
22+
public $strokeLinecap = 'butt';
23+
public $strokeLinejoin = 'miter';
24+
public $strokeMiterlimit = 4;
25+
public $strokeWidth = 1.0;
26+
public $strokeDasharray = 0;
27+
public $strokeDashoffset = 0;
28+
}

src/Svg/Document.php

Lines changed: 8 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -66,6 +66,11 @@ public function getStack()
6666
return $this->stack;
6767
}
6868

69+
public function getHeight()
70+
{
71+
return $this->height;
72+
}
73+
6974
public function render(SurfaceInterface $surface)
7075
{
7176
$this->surface = $surface;
@@ -106,7 +111,7 @@ protected function svgOffset($attributes)
106111
}
107112
}
108113

109-
private function _tagStart($parser, $name, $attribs)
114+
private function _tagStart($parser, $name, $attributes)
110115
{
111116
$this->x = 0;
112117
$this->y = 0;
@@ -120,7 +125,7 @@ private function _tagStart($parser, $name, $attribs)
120125

121126
case 'svg':
122127
$tag = $this;
123-
$this->svgOffset($attribs);
128+
$this->svgOffset($attributes);
124129
break;
125130

126131
case 'path':
@@ -182,7 +187,7 @@ private function _tagStart($parser, $name, $attribs)
182187

183188
if ($tag) {
184189
$this->stack[] = $tag;
185-
$tag->handle($attribs);
190+
$tag->handle($attributes);
186191
} else {
187192
echo "Unknown: '$name'\n";
188193
}

src/Svg/Style.php

Lines changed: 25 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,8 @@
88

99
namespace Svg;
1010

11+
use Svg\Tag\AbstractTag;
12+
1113
class Style
1214
{
1315
const TYPE_COLOR = 1;
@@ -16,19 +18,21 @@ class Style
1618
const TYPE_ANGLE = 4;
1719
const TYPE_NUMBER = 5;
1820

19-
public $color = '';
20-
public $fill = 'black';
21-
public $fillOpacity = 1.0;
22-
public $fillRule = 'nonzero';
21+
public $color;
22+
public $opacity;
23+
24+
public $fill;
25+
public $fillOpacity;
26+
public $fillRule;
2327

24-
public $stroke = 'none';
25-
public $strokeOpacity = 1.0;
26-
public $strokeLinecap = 'butt';
27-
public $strokeLinejoin = 'miter';
28-
public $strokeMiterlimit = 4;
29-
public $strokeWidth = 1.0;
30-
public $strokeDasharray = 0;
31-
public $strokeDashoffset = 0;
28+
public $stroke;
29+
public $strokeOpacity;
30+
public $strokeLinecap;
31+
public $strokeLinejoin;
32+
public $strokeMiterlimit;
33+
public $strokeWidth;
34+
public $strokeDasharray;
35+
public $strokeDashoffset;
3236

3337
public $fontFamily = 'serif';
3438
public $fontSize = 12;
@@ -74,18 +78,16 @@ public function fromAttributes($attributes)
7478
}
7579
}
7680

77-
/**
78-
* @param $attributes
79-
*
80-
* @return Style
81-
*/
82-
public function fromGroupAttributes($attributes)
83-
{
84-
$this->fillStyles($attributes);
81+
public function inherit(AbstractTag $tag) {
82+
$group = $tag->getParentGroup();
83+
if ($group) {
84+
$parent_style = $group->getStyle();
8585

86-
if (isset($attributes["style"])) {
87-
$styles = self::parseCssStyle($attributes["style"]);
88-
$this->fillStyles($styles);
86+
foreach ($parent_style as $_key => $_value) {
87+
if ($_value !== null) {
88+
$this->$_key = $_value;
89+
}
90+
}
8991
}
9092
}
9193

src/Svg/Surface/CPdf.php

Lines changed: 12 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -3116,12 +3116,9 @@ function scale($s_x, $s_y, $x, $y)
31163116
$y = $this->currentPageSize["height"] - $y;
31173117

31183118
$tm = array(
3119-
$s_x,
3120-
0,
3121-
0,
3122-
$s_y,
3123-
$x * (1 - $s_x),
3124-
$y * (1 - $s_y)
3119+
$s_x, 0,
3120+
0, $s_y,
3121+
$x * (1 - $s_x), $y * (1 - $s_y)
31253122
);
31263123

31273124
$this->transform($tm);
@@ -3136,12 +3133,9 @@ function scale($s_x, $s_y, $x, $y)
31363133
function translate($t_x, $t_y)
31373134
{
31383135
$tm = array(
3139-
1,
3140-
0,
3141-
0,
3142-
1,
3143-
$t_x,
3144-
-$t_y
3136+
1, 0,
3137+
0, 1,
3138+
$t_x, -$t_y
31453139
);
31463140

31473141
$this->transform($tm);
@@ -3163,12 +3157,9 @@ function rotate($angle, $x, $y)
31633157
$sin_a = sin($a);
31643158

31653159
$tm = array(
3166-
$cos_a,
3167-
-$sin_a,
3168-
$sin_a,
3169-
$cos_a,
3170-
$x - $sin_a * $y - $cos_a * $x,
3171-
$y - $cos_a * $y + $sin_a * $x,
3160+
$cos_a, -$sin_a,
3161+
$sin_a, $cos_a,
3162+
$x - $sin_a * $y - $cos_a * $x, $y - $cos_a * $y + $sin_a * $x,
31723163
);
31733164

31743165
$this->transform($tm);
@@ -3190,12 +3181,9 @@ function skew($angle_x, $angle_y, $x, $y)
31903181
$tan_y = tan(deg2rad($angle_y));
31913182

31923183
$tm = array(
3193-
1,
3194-
-$tan_y,
3195-
-$tan_x,
3196-
1,
3197-
$tan_x * $y,
3198-
$tan_y * $x,
3184+
1, -$tan_y,
3185+
-$tan_x, 1,
3186+
$tan_x * $y, $tan_y * $x,
31993187
);
32003188

32013189
$this->transform($tm);

src/Svg/Surface/SurfaceCpdf.php

Lines changed: 21 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@
99
namespace Svg\Surface;
1010

1111
use Svg\Style;
12+
use Svg\DefaultStyle;
1213

1314
class SurfaceCpdf implements SurfaceInterface
1415
{
@@ -33,6 +34,10 @@ public function __construct($w, $h)
3334

3435
$canvas = new CPdf(array(0, 0, $w, $h));
3536

37+
// Flip PDF coordinate system so that the origin is in
38+
// the top left rather than the bottom left
39+
$canvas->transform(array(1, 0, 0, -1, 0, $h));
40+
3641
$this->canvas = $canvas;
3742
}
3843

@@ -69,19 +74,13 @@ public function rotate($angle)
6974
public function translate($x, $y)
7075
{
7176
if (self::DEBUG) echo __FUNCTION__ . "\n";
72-
$this->canvas->translate($x, -$y);
77+
$this->canvas->translate($x, $y);
7378
}
7479

7580
public function transform($a, $b, $c, $d, $e, $f)
7681
{
7782
if (self::DEBUG) echo __FUNCTION__ . "\n";
78-
$this->canvas->transform(array($a, -$b, -$c, $d, $e, -$f));
79-
}
80-
81-
public function setTransform($a, $b, $c, $d, $e, $f)
82-
{
83-
if (self::DEBUG) echo __FUNCTION__ . "\n";
84-
$this->canvas->transform(array($a, -$b, -$c, $d, $e, -$f));
83+
$this->canvas->transform(array($a, $b, $c, $d, $e, $f));
8584
}
8685

8786
public function beginPath()
@@ -111,15 +110,10 @@ public function clip()
111110
public function fillText($text, $x, $y, $maxWidth = null)
112111
{
113112
if (self::DEBUG) echo __FUNCTION__ . "\n";
114-
$this->canvas->set_text_pos($x, $this->y($y));
113+
$this->canvas->set_text_pos($x, $y);
115114
$this->canvas->show($text);
116115
}
117116

118-
private function y($y)
119-
{
120-
return $this->height - $y;
121-
}
122-
123117
public function strokeText($text, $x, $y, $maxWidth = null)
124118
{
125119
if (self::DEBUG) echo __FUNCTION__ . "\n";
@@ -179,7 +173,7 @@ function image($img, $x, $y, $w, $h, $resolution = "normal")
179173

180174
switch ($type) {
181175
case IMAGETYPE_JPEG:
182-
$this->canvas->addJpegFromFile($img, $x, $this->y($y) - $h, $w, $h);
176+
$this->canvas->addJpegFromFile($img, $x, $y - $h, $w, $h);
183177
break;
184178

185179
case IMAGETYPE_GIF:
@@ -188,7 +182,7 @@ function image($img, $x, $y, $w, $h, $resolution = "normal")
188182
$img = $this->_convert_gif_bmp_to_png($img, $type);
189183

190184
case IMAGETYPE_PNG:
191-
$this->canvas->addPngFromFile($img, $x, $this->y($y) - $h, $w, $h);
185+
$this->canvas->addPngFromFile($img, $x, $y - $h, $w, $h);
192186
break;
193187

194188
default:
@@ -198,13 +192,13 @@ function image($img, $x, $y, $w, $h, $resolution = "normal")
198192
public function lineTo($x, $y)
199193
{
200194
if (self::DEBUG) echo __FUNCTION__ . "\n";
201-
$this->canvas->lineTo($x, $this->y($y));
195+
$this->canvas->lineTo($x, $y);
202196
}
203197

204198
public function moveTo($x, $y)
205199
{
206200
if (self::DEBUG) echo __FUNCTION__ . "\n";
207-
$this->canvas->moveTo($x, $this->y($y));
201+
$this->canvas->moveTo($x, $y);
208202
}
209203

210204
public function quadraticCurveTo($cpx, $cpy, $x, $y)
@@ -216,7 +210,7 @@ public function quadraticCurveTo($cpx, $cpy, $x, $y)
216210
public function bezierCurveTo($cp1x, $cp1y, $cp2x, $cp2y, $x, $y)
217211
{
218212
if (self::DEBUG) echo __FUNCTION__ . "\n";
219-
$this->canvas->curveTo($cp1x, $this->y($cp1y), $cp2x, $this->y($cp2y), $x, $this->y($y));
213+
$this->canvas->curveTo($cp1x, $cp1y, $cp2x, $cp2y, $x, $y);
220214
}
221215

222216
public function arcTo($x1, $y1, $x2, $y2, $radius)
@@ -227,32 +221,32 @@ public function arcTo($x1, $y1, $x2, $y2, $radius)
227221
public function arc($x, $y, $radius, $startAngle, $endAngle, $anticlockwise = false)
228222
{
229223
if (self::DEBUG) echo __FUNCTION__ . "\n";
230-
$this->canvas->arc($x, $this->y($y), $radius, $startAngle, $endAngle);
224+
$this->canvas->arc($x, $y, $radius, $startAngle, $endAngle);
231225
}
232226

233227
public function circle($x, $y, $radius)
234228
{
235229
if (self::DEBUG) echo __FUNCTION__ . "\n";
236-
$this->canvas->ellipse($x, $this->y($y), $radius, $radius, 0, 8, 0, 360, true, false, false, false);
230+
$this->canvas->ellipse($x, $y, $radius, $radius, 0, 8, 0, 360, true, false, false, false);
237231
}
238232

239233
public function ellipse($x, $y, $radiusX, $radiusY, $rotation, $startAngle, $endAngle, $anticlockwise)
240234
{
241235
if (self::DEBUG) echo __FUNCTION__ . "\n";
242-
$this->canvas->ellipse($x, $this->y($y), $radiusX, $radiusY, 0, 8, 0, 360, false, false, false, false);
236+
$this->canvas->ellipse($x, $y, $radiusX, $radiusY, 0, 8, 0, 360, false, false, false, false);
243237
}
244238

245239
public function fillRect($x, $y, $w, $h)
246240
{
247241
if (self::DEBUG) echo __FUNCTION__ . "\n";
248-
$this->rect($x, $this->y($y), $w, $h);
242+
$this->rect($x, $y, $w, $h);
249243
$this->fill();
250244
}
251245

252246
public function rect($x, $y, $w, $h)
253247
{
254248
if (self::DEBUG) echo __FUNCTION__ . "\n";
255-
$this->canvas->rect($x, $this->y($y), $w, -$h);
249+
$this->canvas->rect($x, $y, $w, $h);
256250
}
257251

258252
public function fill()
@@ -264,7 +258,7 @@ public function fill()
264258
public function strokeRect($x, $y, $w, $h)
265259
{
266260
if (self::DEBUG) echo __FUNCTION__ . "\n";
267-
$this->rect($x, $this->y($y), $w, $h);
261+
$this->rect($x, $y, $w, $h);
268262
$this->stroke();
269263
}
270264

@@ -284,9 +278,9 @@ public function measureText($text)
284278
{
285279
if (self::DEBUG) echo __FUNCTION__ . "\n";
286280
$style = $this->getStyle();
287-
$font = $this->getFont($style->fontFamily, $style->fontStyle);
281+
$this->getFont($style->fontFamily, $style->fontStyle);
288282

289-
return $this->canvas->stringwidth($text, $font, $this->getStyle()->fontSize);
283+
return $this->canvas->getTextWidth($this->getStyle()->fontSize, $text);
290284
}
291285

292286
public function getStyle()

0 commit comments

Comments
 (0)