1
|
|
|
<?php |
2
|
|
|
|
3
|
|
|
namespace EaselDrawing\Templates; |
4
|
|
|
|
5
|
|
|
use EaselDrawing\Color; |
6
|
|
|
use EaselDrawing\Elements; |
7
|
|
|
use EaselDrawing\Orientation; |
8
|
|
|
use Symfony\Component\Yaml\Yaml; |
9
|
|
|
|
10
|
|
|
class TemplateFactory |
11
|
|
|
{ |
12
|
|
|
/** @var string */ |
13
|
|
|
private $relativePath; |
14
|
|
|
/** @var ElementFactory */ |
15
|
|
|
private $elementFactory; |
16
|
|
|
|
17
|
|
|
public function __construct(string $relativePath, ElementFactory $elementFactory = null) |
18
|
|
|
{ |
19
|
|
|
$this->relativePath = $relativePath; |
20
|
|
|
$this->elementFactory = $elementFactory ? : $this->getDefaultElementFactory(); |
21
|
|
|
} |
22
|
|
|
|
23
|
|
|
public function getDefaultElementFactory() |
24
|
|
|
{ |
25
|
|
|
$elementFactory = new ElementFactory(); |
26
|
|
|
$elementFactory->register('line', Builders\Line::class); |
27
|
|
|
$elementFactory->register('rectangle', Builders\Rectangle::class); |
28
|
|
|
$elementFactory->register('image', Builders\Image::class); |
29
|
|
|
$elementFactory->register('label', Builders\Label::class); |
30
|
|
|
return $elementFactory; |
31
|
|
|
} |
32
|
|
|
|
33
|
|
|
public function getRelativePath(): string |
34
|
|
|
{ |
35
|
|
|
return $this->relativePath; |
36
|
|
|
} |
37
|
|
|
|
38
|
|
|
public function getElementFactory(): ElementFactory |
39
|
|
|
{ |
40
|
|
|
return $this->elementFactory; |
41
|
|
|
} |
42
|
|
|
|
43
|
|
|
public function setRelativePath(string $relativePath) |
44
|
|
|
{ |
45
|
|
|
$this->relativePath = $relativePath; |
46
|
|
|
} |
47
|
|
|
|
48
|
|
|
public function obtain(string $contents, string $format): Template |
49
|
|
|
{ |
50
|
|
|
// retrieve data from contents |
51
|
|
|
$data = $this->retrieveData($contents, $format); |
52
|
|
|
|
53
|
|
|
// path resolver |
54
|
|
|
$pathResolver = new PathResolver($this->relativePath); |
55
|
|
|
|
56
|
|
|
// width |
57
|
|
View Code Duplication |
if (! isset($data['width']) || ! is_integer($data['width']) || $data['width'] < 1) { |
|
|
|
|
58
|
|
|
$data['width'] = 800; |
59
|
|
|
} |
60
|
|
|
$width = $data['width']; |
61
|
|
|
|
62
|
|
|
// grayscale |
63
|
|
|
if (! isset($data['grayscale']) || ! is_bool($data['grayscale'])) { |
64
|
|
|
$data['grayscale'] = false; |
65
|
|
|
} |
66
|
|
|
$grayscale = $data['grayscale']; |
67
|
|
|
|
68
|
|
|
// orientation |
69
|
|
|
if (! isset($data['orientation']) || ! is_string($data['orientation'])) { |
70
|
|
|
$data['orientation'] = Orientation::LANDSCAPE; |
71
|
|
|
} |
72
|
|
|
$orientation = Utilities::interpretOrientation($data['orientation']); |
73
|
|
|
|
74
|
|
|
// height |
75
|
|
View Code Duplication |
if (! isset($data['height']) || ! is_integer($data['height']) || $data['height'] < 1) { |
|
|
|
|
76
|
|
|
$data['height'] = 600; |
77
|
|
|
} |
78
|
|
|
$height = $data['height']; |
79
|
|
|
|
80
|
|
|
// foreground |
81
|
|
|
if (! isset($data['foreground'])) { |
82
|
|
|
$data['foreground'] = false; |
83
|
|
|
} |
84
|
|
|
$foreground = Utilities::interpretColor($data['foreground'], Color::newFromString('000000')); |
85
|
|
|
|
86
|
|
|
// background |
87
|
|
|
if (! isset($data['background'])) { |
88
|
|
|
$data['background'] = false; |
89
|
|
|
} |
90
|
|
|
$background = Utilities::interpretColor($data['background'], Color::newFromString('ffffff')); |
91
|
|
|
|
92
|
|
|
// fonts |
93
|
|
|
if (! isset($data['fonts']) || ! is_array($data['fonts'])) { |
94
|
|
|
$data['fonts'] = []; |
95
|
|
|
} |
96
|
|
|
$fonts = []; |
97
|
|
|
foreach ($data['fonts'] as $name => $sourceFont) { |
98
|
|
|
$fonts[] = Utilities::interpretFont($name, $sourceFont, $pathResolver); |
99
|
|
|
} |
100
|
|
|
|
101
|
|
|
// template |
102
|
|
|
$elements = new Elements(); |
103
|
|
|
$template = new Template( |
104
|
|
|
$width, |
105
|
|
|
$height, |
106
|
|
|
$foreground, |
107
|
|
|
$background, |
108
|
|
|
$elements, |
109
|
|
|
$fonts, |
110
|
|
|
$pathResolver, |
111
|
|
|
$grayscale, |
112
|
|
|
$orientation |
113
|
|
|
); |
114
|
|
|
|
115
|
|
|
// elements |
116
|
|
|
$elementFactory = $this->getElementFactory(); |
117
|
|
|
if (! isset($data['elements']) || ! is_array($data['elements'])) { |
118
|
|
|
$data['elements'] = []; |
119
|
|
|
} |
120
|
|
|
foreach ($data['elements'] as $index => $sourceElement) { |
121
|
|
|
if (! is_array($sourceElement) || count($sourceElement) !== 1) { |
122
|
|
|
throw new \InvalidArgumentException("The element index $index is not valid"); |
123
|
|
|
} |
124
|
|
|
foreach ($sourceElement as $type => $dataElement) { |
125
|
|
|
$elements->add($elementFactory->element($type, $dataElement, $template)); |
126
|
|
|
} |
127
|
|
|
} |
128
|
|
|
|
129
|
|
|
return $template; |
130
|
|
|
} |
131
|
|
|
|
132
|
|
|
public function obtainFromFile(string $filename, string $format): Template |
133
|
|
|
{ |
134
|
|
|
if (! file_exists($filename) || ! is_readable($filename)) { |
135
|
|
|
throw new \InvalidArgumentException("File $filename does not exists or is not readable"); |
136
|
|
|
} |
137
|
|
|
return $this->obtain(file_get_contents($filename), $format); |
138
|
|
|
} |
139
|
|
|
|
140
|
|
|
public function retrieveData(string $contents, string $format): array |
141
|
|
|
{ |
142
|
|
|
$format = strtoupper($format); |
143
|
|
|
if ('YAML' === $format) { |
144
|
|
|
return Yaml::parse($contents) ? : []; |
|
|
|
|
145
|
|
|
} |
146
|
|
|
if ('JSON' === $format) { |
147
|
|
|
return json_decode($contents, true) ? : []; |
|
|
|
|
148
|
|
|
} |
149
|
|
|
throw new \InvalidArgumentException("Format $format is not recognized"); |
150
|
|
|
} |
151
|
|
|
} |
152
|
|
|
|
Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.
You can also find more detailed suggestions in the “Code” section of your repository.