ILIAS  release_9 Revision v9.13-25-g2c18ec4c24f
class.ilImagemapPreview.php
Go to the documentation of this file.
1 <?php
2 
19 require_once './Modules/Test/classes/inc.AssessmentConstants.php';
20 
32 {
35  public $areas;
36  public $points;
39  public $lng;
40  private \ilGlobalTemplateInterface $main_tpl;
41 
50  public function __construct($imagemap_filename = "")
51  {
52  global $DIC;
53  $this->main_tpl = $DIC->ui()->mainTemplate();
54  $lng = $DIC['lng'];
55  $this->lng = &$lng;
56  $this->imagemap_filename = $imagemap_filename;
57 
58  if (!@is_file($this->preview_filename)) {
59  $extension = ".jpg";
60  if (preg_match("/.*\.(png|jpg|gif|jpeg)$/", $this->imagemap_filename, $matches)) {
61  $extension = "." . $matches[1];
62  }
63  $this->preview_filename = ilFileUtils::ilTempnam() . $extension;
64  }
65  $this->areas = array();
66  $this->points = array();
67  $this->linewidth_outer = 4;
68  $this->linewidth_inner = 2;
69  }
70 
71  public function getAreaCount(): int
72  {
73  return count($this->areas);
74  }
75 
76  public function getPointCount(): int
77  {
78  return count($this->points);
79  }
80 
81  public function addArea(
82  $index,
83  $shape,
84  $coords,
85  $title = "",
86  $href = "",
87  $target = "",
88  $visible = true,
89  $linecolor = "red",
90  $bordercolor = "white",
91  $fillcolor = "#FFFFFFA0"
92  ): void {
93  if (ini_get("safe_mode")) {
94  if ((strpos($fillcolor, "#") !== false) || (strpos($fillcolor, "rgb") !== false)) {
95  $fillcolor = str_replace("\"", "", $fillcolor);
96  }
97  }
98  $this->areas[$index] = array(
99  "shape" => "$shape",
100  "coords" => "$coords",
101  "title" => htmlspecialchars($title),
102  "href" => "$href",
103  "target" => "$target",
104  "linecolor" => '"' . $linecolor . '"',
105  "fillcolor" => '"' . $fillcolor . '"',
106  "bordercolor" => '"' . $bordercolor . '"',
107  "visible" => (int) $visible
108  );
109  }
110 
111  public function addPoint(
112  $index,
113  $coords,
114  $visible = true,
115  $linecolor = "red",
116  $bordercolor = "white",
117  $fillcolor = "#FFFFFFA0"
118  ): void {
119  $this->points[$index] = array(
120  "coords" => "$coords",
121  "linecolor" => '"' . $linecolor . '"',
122  "fillcolor" => '"' . $fillcolor . '"',
123  "bordercolor" => '"' . $bordercolor . '"',
124  "visible" => (int) $visible
125  );
126  }
127 
128  public function getAreaIdent(): string
129  {
130  if (count($this->areas) + count($this->points) > 0) {
131  $arr = array_merge(array_keys($this->areas), array_keys($this->points));
132  sort($arr, SORT_NUMERIC);
133 
134  $inner = join("_", $arr);
135  if (strlen($inner) > 32) {
136  $inner = md5($inner);
137  }
138  return "preview_" . $inner . "_";
139  } else {
140  return "";
141  }
142  }
143 
144  public function createPreview(): void
145  {
146  if (count($this->areas) + count($this->points) == 0) {
147  return;
148  }
149  $convert_cmd = "-quality 100 ";
150  foreach ($this->points as $point) {
151  if ($point["visible"]) {
152  preg_match("/(\d+)\s*,\s*(\d+)/", $point["coords"], $matches);
153  $x = $matches[1];
154  $y = $matches[2];
155  $r = 6;
156  // draw a circle at the point
157  $convert_cmd .= "-stroke " . $point["bordercolor"] . " -fill " . $point["fillcolor"] . " -strokewidth $this->linewidth_outer -draw \"line " .
158  ($x - $r) . "," . ($y - $r) . " " . ($x + $r) . "," . ($y + $r) . "\" " .
159  "-stroke " . $point["bordercolor"] . " -fill " . $point["fillcolor"] . " -strokewidth $this->linewidth_outer -draw \"line " .
160  ($x + $r) . "," . ($y - $r) . " " . ($x - $r) . "," . ($y + $r) . "\" " .
161  "-stroke " . $point["linecolor"] . " -fill " . $point["fillcolor"] . " -strokewidth $this->linewidth_inner -draw \"line " .
162  ($x - $r) . "," . ($y - $r) . " " . ($x + $r) . "," . ($y + $r) . "\" " .
163  "-stroke " . $point["linecolor"] . " -fill " . $point["fillcolor"] . " -strokewidth $this->linewidth_inner -draw \"line " .
164  ($x + $r) . "," . ($y - $r) . " " . ($x - $r) . "," . ($y + $r) . "\" ";
165  }
166  }
167  foreach ($this->areas as $area) {
168  if ($area["visible"] and strcmp(strtolower($area["shape"]), "rect") == 0) {
169  preg_match("/(\d+)\s*,\s*(\d+)\s*,\s*(\d+)\s*,\s*(\d+)/", $area["coords"], $matches);
170  $x0 = $matches[1];
171  $y0 = $matches[2];
172  $x1 = $matches[3];
173  $y1 = $matches[4];
174  // draw a rect around the selection
175  $convert_cmd .= "-stroke " . $area["bordercolor"] . " -fill " . $area["fillcolor"] . " -strokewidth $this->linewidth_outer -draw \"rectangle " .
176  $x0 . "," . $y0 . " " . ($x1) . "," . $y1 . "\" " .
177  "-stroke " . $area["linecolor"] . " -fill " . $area["fillcolor"] . " -strokewidth $this->linewidth_inner -draw \"rectangle " .
178  $x0 . "," . $y0 . " " . ($x1) . "," . $y1 . "\" ";
179  } elseif ($area["visible"] and strcmp(strtolower($area["shape"]), "circle") == 0) {
180  preg_match("/(\d+)\s*,\s*(\d+)\s*,\s*(\d+)/", $area["coords"], $matches);
181  $x = $matches[1];
182  $y = $matches[2];
183  $r = $matches[3];
184  // draw a circle around the selection
185  $convert_cmd .= "-stroke " . $area["bordercolor"] . " -fill " . $area["fillcolor"] . " -strokewidth $this->linewidth_outer -draw \"circle " .
186  $x . "," . $y . " " . ($x + $r) . "," . $y . "\" " .
187  "-stroke " . $area["linecolor"] . " -fill " . $area["fillcolor"] . " -strokewidth $this->linewidth_inner -draw \"circle " .
188  $x . "," . $y . " " . ($x + $r) . "," . $y . "\" ";
189  } elseif ($area["visible"] and strcmp(strtolower($area["shape"]), "poly") == 0) {
190  $obj = "polygon";
191  // draw a polygon around the selection
192  preg_match_all("/(\d+)\s*,\s*(\d+)/", $area["coords"], $matches, PREG_PATTERN_ORDER);
193  if (count($matches[0]) == 2) {
194  $obj = "line";
195  }
196  $convert_cmd .= "-stroke " . $area["bordercolor"] . " -fill " . $area["fillcolor"] . " -strokewidth $this->linewidth_outer -draw \"$obj ";
197  for ($i = 0; $i < count($matches[0]); $i++) {
198  $convert_cmd .= $matches[1][$i] . "," . $matches[2][$i] . " ";
199  }
200  $convert_cmd .= "\" ";
201  $convert_cmd .= "-stroke " . $area["linecolor"] . " -fill " . $area["fillcolor"] . " -strokewidth $this->linewidth_inner -draw \"$obj ";
202  preg_match_all("/(\d+)\s*,\s*(\d+)/", $area["coords"], $matches, PREG_PATTERN_ORDER);
203  for ($i = 0; $i < count($matches[0]); $i++) {
204  $convert_cmd .= $matches[1][$i] . "," . $matches[2][$i] . " ";
205  }
206  $convert_cmd .= "\" ";
207  }
208  }
209 
210  $source = $this->escapeShellCmd($this->imagemap_filename);
211  $target = $this->escapeShellCmd($this->preview_filename);
212  $convert_cmd = $this->escapeShellCmd($convert_cmd);
213  $convert_cmd = preg_replace('/\\\\(#([a-fA-F0-9]{3}|[a-fA-F0-9]{6}|[a-fA-F0-9]{8}))/', '${1}', $convert_cmd);
214  $convert_cmd = $source . "[0] " . $convert_cmd . " " . $target;
215  $this->execQuoted(PATH_TO_CONVERT, $convert_cmd);
216  }
217 
218  public static function escapeShellCmd($a_arg)
219  {
220  if (ini_get('safe_mode') == 1) {
221  return $a_arg;
222  }
223  setlocale(LC_CTYPE, "UTF8", "en_US.UTF-8"); // fix for PHP escapeshellcmd bug. See: http://bugs.php.net/bug.php?id=45132
224  return escapeshellcmd($a_arg);
225  }
226 
227  public static function execQuoted($cmd, $args = null)
228  {
229  global $DIC;
230 
231  if (ilUtil::isWindows() && strpos($cmd, " ") !== false && substr($cmd, 0, 1) !== '"') {
232  $cmd = '"' . $cmd . '"';
233  if ($args) {
234  $cmd .= " " . $args;
235  }
236  } elseif ($args) {
237  $cmd .= " " . $args;
238  }
239  exec($cmd, $arr);
240 
241  $DIC->logger()->root()->debug("ilUtil::execQuoted: " . $cmd . ".");
242 
243  return $arr;
244  }
245 
246  public function getPreviewFilename($imagePath, $baseFileName)
247  {
248  $filename = $baseFileName;
249  if (count($this->areas) + count($this->points) > 0) {
250  $pfile = $this->preview_filename;
251  if (is_file($pfile)) {
252  $ident = $this->getAreaIdent();
253  $previewfile = $imagePath . $ident . $baseFileName;
254  if (@md5_file($previewfile) != @md5_file($pfile)) {
255  if (strlen($ident) > 0) {
256  @copy($pfile, $previewfile);
257  }
258  }
259  @unlink($pfile);
260  if (strlen($pfile) == 0) {
261  $this->main_tpl->setOnScreenMessage('info', $this->lng->txt("qpl_imagemap_preview_missing"));
262  } else {
263  $filename = basename($previewfile);
264  }
265  } else {
266  $this->main_tpl->setOnScreenMessage('info', $this->lng->txt("qpl_imagemap_preview_missing"));
267  }
268  }
269  return $filename;
270  }
271 
276  public function getImagemap($title): string
277  {
278  $map = "<map name=\"$title\"> ";
279  foreach ($this->areas as $area) {
280  $map .= "<area alt=\"" . $area["title"] . "\" title=\"" . $area["title"] . "\" ";
281  $map .= "shape=\"" . $area["shape"] . "\" ";
282  $map .= "coords=\"" . $area["coords"] . "\" ";
283  if ($area["href"]) {
284  $map .= "href=\"" . $area["href"] . "\" ";
285  if ($area["target"]) {
286  $map .= "target=\"" . $area["target"] . "\" ";
287  }
288  $map .= "/>\n";
289  } else {
290  $map .= "nohref />\n";
291  }
292  }
293  $map .= "</map>";
294  return $map;
295  }
296 }
getPreviewFilename($imagePath, $baseFileName)
This file is part of ILIAS, a powerful learning management system published by ILIAS open source e-Le...
static isWindows()
ilGlobalTemplateInterface $main_tpl
global $DIC
Definition: feed.php:28
static execQuoted($cmd, $args=null)
getImagemap($title)
get imagemap html code note: html code should be placed in template files
__construct($imagemap_filename="")
ilImagemapPreview constructor
addPoint( $index, $coords, $visible=true, $linecolor="red", $bordercolor="white", $fillcolor="#FFFFFFA0")
$filename
Definition: buildRTE.php:78
static ilTempnam(?string $a_temp_path=null)
Returns a unique and non existing Path for e temporary file or directory.
addArea( $index, $shape, $coords, $title="", $href="", $target="", $visible=true, $linecolor="red", $bordercolor="white", $fillcolor="#FFFFFFA0")
$r