'js/libs/jquery/jquery.hashchange.js',
'js/libs/jquery/jquery.scrollto.js',
'js/libs/jquery/jquery.localscroll.js',
+ 'js/libs/jquery/perfect-scrollbar.jquery.js',
'js/libs/gsap/TweenMax.js',
'js/libs/gsap/jquery.gsap.js',
'js/libs/gal/gal.js',
'js/libs/fluidbook/fluidbook.audiodescription.js',
'js/libs/fluidbook/fluidbook.privacy.js',
'js/libs/fluidbook/fluidbook.zoom.js',
- 'js/libs/fluidbook/views/fluidbook.chapters.js',
- 'js/libs/fluidbook/views/fluidbook.index.js',
+ 'js/libs/fluidbook/fluidbook.menu.js',
+ 'js/libs/fluidbook/menu/fluidbook.chapters.js',
+ 'js/libs/fluidbook/menu/fluidbook.index.js',
'js/libs/fluidbook/fluidbook.js',
'js/main.js');
protected $widget = true;
protected $multiApp = false;
protected $pageLabels = array();
+ protected $stylesheets = array();
function __construct($book_id, $version = 'stable', $phonegap = false, $phonegapVersion = 'latest', $dir = null, $standalone = false, $appcache = false, $home = false) {
}
}
- // Copy style folder
- $from = $this->assets . '/style';
- $to = $this->vdir;
+ // Copy fonts folder
+ $from = $this->assets . '/style/fonts/*';
+ $to = $this->vdir . '/style/fonts';
+ if (!file_exists($to)) {
+ mkdir($to, 0777, true);
+ }
`cp -p -r $from $to`;
// Copy images folder
$from = $this->assets . '/images';
+ $to = $this->vdir;
`cp -p -r $from $to`;
// Copy images folder
$from = $this->assets . '/video';
+ $to = $this->vdir;
`cp -p -r $from $to`;
// Copy swf
$this->loadPlugins();
$this->writeImages();
$linksCSS = $this->writeLinks();
- $numCSS = $this->writeCSS($this->vdir . '/data/style/style_%d.css', $linksCSS);
+ $this->writeCSS($this->vdir . '/data/style/style_%d.css', $linksCSS);
$this->writeLangs();
- $this->writeIndex($numCSS);
+ $this->writeIndex();
$this->writeTexts();
$this->writeExtras();
$this->writeJs();
- if (!$this->widget) {
- unlink($this->vdir . '/style/widget.css');
- }
$this->writeCache();
}
$ga .= $this->book->parametres->googleAnalyticsCustom;
}
// Feuilles de style
- $sheets = array('style/fluidbook.css');
- for ($i = 0; $i < $numCSS; $i++) {
- $sheets[] = 'data/style/style_' . $i . '.css';
- }
- $sheets = array_merge($this->pluginCSS, $this->specialCSS, $sheets);
+ $sheets = array_merge($this->stylesheets, $this->specialCSS);
$style = array();
foreach ($sheets as $sheet) {
if ($this->book->parametres->customLinkClass == 'WescoSalesLink') {
$this->specialJsFiles[] = 'js/libs/fluidbook/special/wescosales.js';
- $this->specialCSS[] = 'style/special/wescosales.css';
+ $this->specialCSS[] = 'wescosales';
}
if ($this->book->parametres->customLinkClass == 'AtlanticDownloadLink') {
$this->specialJsFiles[] = 'js/libs/fluidbook/special/atlanticdownload.js';
- $this->specialCSS[] = 'style/special/atlanticdownload.css';
+ $this->specialCSS[] = 'atlanticdownload';
}
$this->config->links = array();
protected function writeCSS($file, $links) {
$res = array();
+ $lessVariables = array();
+
// General theme
$cssWidth = $this->cssWidth;
$cssHeight = $this->cssHeight;
}
$texts = '.texts{' . wsHTML5::writeCSSUA('transform-origin', 'top left') . ';';
$texts .= wsHTML5::writeCSSUA('transform', 'scale(' . round((1 / $this->multiply) * $cssScale * $this->cssSVGScale, 3) . ')') . ';';
- $texts .= 'width:' . ($wm / $this->cssSVGScale) . '; max-width:' . ($wm / $this->cssSVGScale) . ';';
- $texts .= 'height:' . ($hm / $this->cssSVGScale) . '; max-height:' . ($hm / $this->cssSVGScale) . ';';
+ $texts .= 'width:' . ($wm / $this->cssSVGScale) . 'px; max-width:' . ($wm / $this->cssSVGScale) . 'px;';
+ $texts .= 'height:' . ($hm / $this->cssSVGScale) . 'px; max-height:' . ($hm / $this->cssSVGScale) . 'px;';
$texts .= '}';
$res[] = $texts;
$res[] = $shade;
// SVG
-
$res[] = 'svg .fill-c-menu-back{fill:' . wsHTML5::colorToCSS($this->theme->parametres->couleurB) . ';}';
$res[] = 'svg .fill-c-menu-text{fill:' . wsHTML5::colorToCSS($this->theme->parametres->subTextColor) . ';}';
$res[] = '.portrait #fluidbook .bookmark.left{left:' . ($cssWidth - $size) . 'px;}';
// Menus
+
+
$menuColor = new CubeIT_Graphics_Color($this->theme->parametres->couleurB);
$menuColor->setAlpha(1);
$menuTextColor = wsHTML5::colorToCSS($this->theme->parametres->subTextColor);
+ $lessVariables['menu-background'] = $menuColor->toCSS();
+ $lessVariables['menu-text'] = $menuTextColor;
+ $lessVariables['menu-field-background'] = wsHTML5::colorToCSS($this->theme->parametres->subFieldColor);
+ $lessVariables['menu-field-text'] = wsHTML5::colorToCSS($this->theme->parametres->subTextFieldColor);
+
+
$menuMultiply = $menuColor->multiply($menuColor);
$menuMultiply2 = $menuMultiply->multiply($menuColor);
- # View
- $res[] = '.portrait .mview{width:' . $w . ';min-height:' . $h . '}';
- $res[] = '.landscape .mview{width:' . $w2 . ';min-height:' . $h . '}';
- $res[] = '.mview{background-color:' . $menuColor->toCSS() . ';color:' . $menuTextColor . ';}';
-
- # Inner View
- $res[] .= '#innerView>div{background-color:' . $menuColor->toCSS() . ';color:' . $menuTextColor . ';}';
- $res[] .= 'form input[type="text"],form input[type="email"]{background-color:' . wsHTML5::colorToCSS($this->theme->parametres->subFieldColor) . ';color:' . wsHTML5::colorToCSS($this->theme->parametres->subTextFieldColor) . ';}';
// Archives
if ($this->book->parametres->externalArchivesBack) {
$res[] = '.mview.archives{background-image:url("../images/' . $this->book->parametres->externalArchivesBack . '");}';
}
- # Topbar
- $top = $menuColor->toCSS();
- $bottom = $menuMultiply->toCSS();
- $border = $menuMultiply2->setAlpha(0.6)->toCSS();
-
- $caption = ".mview .caption{
- background-image: -moz-linear-gradient(top, $top 0%, $bottom 100%); /* FF3.6+ */
- background-image: -webkit-linear-gradient(top, $top 0%,$bottom 100%); /* Chrome10+,Safari5.1+ */
- background-image: -o-linear-gradient(top, $top 0%,$bottom 100%); /* Opera 11.10+ */
- background-image: -ms-linear-gradient(top, $top 0%,$bottom 100%); /* IE10+ */
- background-image: linear-gradient(top bottom, $top 0%,$bottom 100%); /* W3C */
-}";
-
- $caption .= ".mview .caption a{
- border:1px solid $border;
-}";
- $res[] = $caption;
-
- # Chapters (menu lists)
- $top = $menuColor->setAlpha(0.5)->toCSS();
- $bottom = $menuMultiply->setAlpha(0.5)->toCSS();
- $border = $menuMultiply2->setAlpha(0.5)->toCSS();
-
- $chapters = "ul.chapters a.level-1,ul.chapters a.level0,ul.chapters a.level1,ul.chapters a.level2,ul.chapters a.level3{
- background-image: -moz-linear-gradient(top, $top 0%, $bottom 100%); /* FF3.6+ */
- background-image: -webkit-linear-gradient(top, $top 0%,$bottom 100%); /* Chrome10+,Safari5.1+ */
- background-image: -o-linear-gradient(top, $top 0%,rgba(0,0,0,0.5) 100%); /* Opera 11.10+ */
- background-image: -ms-linear-gradient(top, $top 0%,$bottom 100%); /* IE10+ */
- background-image: linear-gradient(top bottom, $top 0%,$bottom 100%); /* W3C */
- border-bottom:1px solid $border;
-}";
- $res[] = $chapters;
# Index
$ratio = $this->width / $this->height;
$thumbh = round(100 / $ratio);
- $res[] = '#indexView .thumb img{width:100px;height:' . $thumbh . 'px;}';
- $res[] = '#indexView .doubleThumb{height:' . $thumbh . 'px;' . wsHTML5::writeCSSUA('box-shadow', '0 0 3px ' . $shadowColor) . '}';
- $res[] = '#indexView .doubleThumb .overlay{height:' . $thumbh . 'px;}';
- $res[] = '#indexView .doubleThumb .hits.yes{background-color:' . wsHTML5::colorToCSS($this->theme->parametres->subSelectColor) . ';color:' . wsHTML5::colorToCSS($this->theme->parametres->subTextSelectColor) . '}';
+ $lessVariables['thumb-height'] = $thumbh . 'px';
# Tooltip
$res[] = '#tooltip{background-color:' . wsHTML5::colorToCSS($this->theme->parametres->tooltipBackColor) . ';color:' . wsHTML5::colorToCSS($this->theme->parametres->tooltipTextColor) . ';}';
# ZoomPopup close button background
$res[] = '.zoomPopupClose {background-color:' . wsHTML5::colorToCSS($this->theme->parametres->couleurB) . ';}';
+
+ $this->_writeLess($lessVariables);
+
$res = array_chunk($res, 3500);
foreach ($res as $k => $css) {
+ $this->stylesheets[] = 'data/style/style_' . $k . '.css';
file_put_contents(sprintf($file, $k), implode("\n", $css));
}
+
return count($res);
}
+ protected function _writeLess($variables) {
+ $lessFiles = array('fluidbook');
+ if ($this->widget) {
+ $lessFiles[] = 'widget';
+ }
+ foreach ($this->specialCSS as $s) {
+ $lessFiles[] = 'special/' . $s;
+ }
+
+ $tmp = CubeIT_Files::tmpdir();
+
+ copy($this->assets . '/style/variables.less', $tmp . '/variables.less');
+
+ $bookVariables = array();
+ foreach ($variables as $k => $v) {
+ $bookVariables[] = '@' . $k . ':' . $v . ';';
+ }
+ file_put_contents($tmp . '/book-variables.less', implode("\n", $bookVariables));
+ foreach ($lessFiles as $f) {
+ copy($this->assets . '/style/' . $f . '.less', $tmp . '/' . $f . '.less');
+ $less = new CubeIT_CommandLine('lessc');
+ $less->setArg('plugin', 'less-plugin-clean-css');
+ $less->setArg(null, $tmp . '/' . $f . '.less');
+ $less->setArg(null, $this->vdir . '/style/' . $f . '.css');
+ $less->execute();
+ if ($f != 'widget') {
+ $this->stylesheets[] = 'style/' . $f . '.css';
+ }
+ }
+ }
+
protected function _cssBackground() {
$body = '#background,#splash{';
$body .= 'background-color:#' . $this->theme->parametres->backgroundColor . ';';
}
public function getHTMLContent() {
- $w = $this->width * $this->getCssScale();
- $h = $this->height * $this->getCssScale();
+ $w = $this->width;
+ $h = $this->height;
$this->copyExternalFile($this->alternative);
- $alt = '<img src="' . wsHTML5Link::getUniversalLocation($this->alternative) . '" width="' . $w . '" height="' . $h . '" />';
+ $alt = '<img data-width="' . $w . '" data-height="' . $h . '" src="' . wsHTML5Link::getUniversalLocation($this->alternative) . '" width="' . $w . '" height="' . $h . '" />';
return $alt;
}
$i['width'] = $i['video_width'];
$i['height'] = $i['video_height'];
- $l = wsHTML5Link::getMultimediaInstance($this->id . '_content', $i, $this->compiler);
+ $l = self::getMultimediaInstance($this->id . '_content', $i, $this->compiler);
$markup = $l->getHTMLContainer();
return ' data-multimedia="' . rawurlencode($markup) . '" ';
}
public function getAdditionnalContent() {
$dim = getimagesize($this->wdir . '/' . $this->alternative);
- $markup = '<div class="multimediaContainer"><img src="' . wsHTML5Link::getUniversalLocation($this->alternative) . '" width="' . $dim[0] . '" height="' . $dim[1] . '" class="multimedia" /></div>';
+ $markup = '<div class="multimediaContainer"><img data-width="' . $dim[0] . '" data-height="' . $dim[1] . '" src="' . wsHTML5Link::getUniversalLocation($this->alternative) . '" width="' . $dim[0] . '" height="' . $dim[1] . '" class="multimedia" /></div>';
return ' data-multimedia="' . rawurlencode($markup) . '" ';
}
public function getAdditionnalContent() {
$this->video_auto_start = true; // Videos should always autoplay
- return ' data-video="' . rawurlencode(videoLink::makeVideoTag($this, $this->video_width, $this->video_height, $this->compiler)) . '" ';
+ return ' data-video="' . rawurlencode(videoLink::makeVideoTag($this, null, null, $this->compiler)) . '" ';
}
public function keep() {
}
public function getEmbed() {
- return '<iframe width="' . $this->width * $this->getCssScale() . '" height="' . $this->height * $this->getCssScale() . '" src="' . $this->getEmbedURL() . '" frameborder="0" allowfullscreen></iframe>';
+ return '<iframe width="' . $this->width . '" height="' . $this->height . '" src="' . $this->getEmbedURL() . '" frameborder="0" allowfullscreen></iframe>';
}
public function getEmbedURL() {
$iw = $this->_config['width'];
$ih = $this->_config['height'];
- $res = '<iframe width="' . $iw . '" height="' . $ih . '" src="' . $this->_url . '" frameborder="0" marginwidth="0" marginheight="0" scrolling="no" allowfullscreen mozallowfullscreen="true" webkitallowfullscreen="true" onmousewheel=""></iframe>';
+ $res = '<iframe data-width="' . $iw . '" data-height="' . $ih . '" width="' . $iw . '" height="' . $ih . '" src="' . $this->_url . '" frameborder="0" marginwidth="0" marginheight="0" scrolling="no" allowfullscreen mozallowfullscreen="true" webkitallowfullscreen="true" onmousewheel=""></iframe>';
}
if (isset($externalIframe)) {
$iw = $this->_config['width'];
$ih = $this->_config['height'];
- $res = '<iframe width="' . $iw . '" height="' . $ih . '" src="' . $externalIframe . '" frameborder="0" marginwidth="0" marginheight="0" scrolling="no" allowfullscreen mozallowfullscreen="true" webkitallowfullscreen="true" onmousewheel=""></iframe>';
+ $res = '<iframe data-width="' . $iw . '" data-height="' . $ih . '" width="' . $iw . '" height="' . $ih . '" src="' . $externalIframe . '" frameborder="0" marginwidth="0" marginheight="0" scrolling="no" allowfullscreen mozallowfullscreen="true" webkitallowfullscreen="true" onmousewheel=""></iframe>';
}
foreach ($this->_config['inject'] as $i) {
}
public function compile() {
-
$dirsToCreate = array('data/images', 'data/contents', 'data/background', 'data/thumbnails', 'data/style');
if (in_array('flv', $this->getVideosFormats())) {
$dirsToCreate[] = 'swf';
array_push($this->jsFiles, $main);
}
- protected function getVideosFormats($poster = true) {
- if (!$this->phonegap) {
- $res = array('ogv', 'webm', 'mp4', 'flv');
- } elseif ($this->phonegap == 'ios') {
- $res = array('mp4');
- } else if ($this->phonegap == 'android') {
- $res = array('webm', 'mp4');
- }
+ public function getVideosFormats($poster = true) {
+ $res = [];
+//
+// if (!$this->phonegap) {
+// $res = array('ogv', 'webm', 'mp4', 'flv');
+// } elseif ($this->phonegap == 'ios') {
+// $res = array('mp4');
+// } else if ($this->phonegap == 'android') {
+// $res = array('webm', 'mp4');
+// }
+
+ $res[] = 'mp4';
if ($poster) {
$res[] = 'jpg';
file_put_contents($cacheFile, implode("\n", $lines));
}
+ /**
+ * Helper function to add a unique script entry to the JS stack.
+ * Normally this is a relative path but it can be an external URL.
+ * External URLs are added to the pluginJs collection instead of jsFiles.
+ * Duplicate paths are ignored.
+ * @param $path
+ */
+ public function addJs($path) {
+
+ // If JS is external, it will be included via the pluginJs collection
+ // Otherwise, it will be compiled into the main JS file
+ $collection = (preg_match('#^https?://#i', $path) === 1) ? 'pluginJs' : 'jsFiles';
+
+ if (!in_array($path, $this->$collection)) {
+ $this->{$collection}[] = $path;
+ }
+ }
+
+ /**
+ * Helper function to add a unique stylesheet entry to the CSS stack
+ * Duplicate paths are ignored.
+ * @param $path
+ */
+ public function addCSS($path) {
+ if (!in_array($path, $this->pluginCSS)) {
+ $this->pluginCSS[] = $path;
+ }
+ }
+
protected function writeIndex($numCSS) {
global $core;
class videoLink extends wsHTML5Link {
+ public static function addVideoJS($compiler) {
+ $compiler->addJs('js/libs/videojs/video.js');
+ $compiler->addCSS('style/videojs/videojs.css');
+ }
+
+ public function getClasses() {
+ return array_merge(['videoLink'], parent::getClasses());
+ }
+
public function getHTMLContent() {
+
+ static::addVideoJS($this->compiler);
+
$this->copyExternalFile($this->to, true);
$w = round($this->width * $this->getCssScale());
$h = round($this->height * $this->getCssScale());
- return self::makeVideoTag($this, $w, $h, $this->compiler);
+ return $this->makeVideoTag($this, $w, $h, $this->compiler);
}
public static function makeVideoTag($linkDatas, $w = null, $h = null, $compiler = null) {
- $file = $linkDatas->to;
+
+ $attributes = static::getVideoAttributes($linkDatas, $w, $h, $compiler);
+
+ $res = '<div class="videoContainer"';
+ foreach ($attributes as $name => $value) {
+ $res .= " data-{$name}='{$value}'";
+ }
+ $res .= '></div>';
+
+ return $res;
+ }
+
+ public static function getVideoAttributes($data, $w = null, $h = null, $compiler = null) {
+
+ $file = $data->to;
$e = explode('.', $file);
$ext = array_pop($e);
$basename = implode('.', $e);
- $autoplay = ($linkDatas->video_auto_start ? '1' : '0');
- $controls = ($linkDatas->video_controls ? '1' : '0');
- $loop = ($linkDatas->video_loop ? '1' : '0');
- $sound = ($linkDatas->video_sound_on ? '1' : '0');
+ $attr['name'] = $basename;
+ $attr['id'] = 'video_' . $data->id;
+ $attr['autoplay'] = ($data->video_auto_start ? '1' : '0');
+ $attr['controls'] = ($data->video_controls ? '1' : '0');
+ $attr['loop'] = ($data->video_loop ? '1' : '0');
+ $attr['sound'] = ($data->video_sound_on ? '1' : '0');
- $res = '<div class="videoContainer" ';
if (!is_null($w) && !is_null($h)) {
- $res .= 'data-width="' . $w . '" data-height="' . $h . '" ';
+ $attr['width'] = $w;
+ $attr['height'] = $h;
} else if (!is_null($compiler)) {
$path = WS_BOOKS . '/working/' . $compiler->book_id . '/' . $basename . '.jpg';
$dim = getimagesize($path);
- $res .= 'data-width="' . $dim[0] . '" data-height="' . $dim[1] . '" ';
+ $attr['width'] = $dim[0];
+ $attr['height'] = $dim[1];
}
- $res .= ' data-autoplay="' . $autoplay . '"';
- $res .= ' data-controls="' . $controls . '"';
- $res .= ' data-loop="' . $loop . '"';
- $res .= ' data-sound="' . $sound . '"';
- $res .= ' data-name="' . $basename . '"';
- $res .= '></div>';
- return $res;
+
+ return $attr;
}
}
}
public function getAdditionnalContent() {
+ $this->video_auto_start = true; // Videos should always autoplay
return ' data-video="' . rawurlencode(videoLink::makeVideoTag($this, null, null, $this->compiler)) . '" ';
}
}
+
+
class audioPopupLink extends normalLink {
public function getURL() {
class webVideoLink extends videoLink {
+ public static function getVideoAttributes($data, $w = null, $h = null, $compiler = null) {
+ $attributes = parent::getVideoAttributes($data, $w, $h, $compiler);
+
+ // Since the admin interface doesn't offer options for setting controls or sound, we will set some defaults here
+ $attributes['controls'] = '1';
+ $attributes['sound'] = '1';
+
+ $attributes['setup'] = static::getVideoSetup($data, $compiler);
+
+ return $attributes;
+ }
+
+ public static function getVideoSetup($data, $compiler) {
+
+ static::addVideoJS($compiler); // Ensure videoJS core is included first
+
+ switch($data->video_service) {
+ case 0: // YouTube
+ $compiler->addJs('js/libs/videojs/Youtube.js');
+// $compiler->addJs('https://rawgit.com/videojs/videojs-youtube/master/dist/Youtube.js');
+ $setup = [
+ 'techOrder' => ['youtube'],
+ 'sources' => [
+ [
+ 'type' => 'video/youtube',
+ 'src' => 'https://www.youtube.com/watch?v=' . $data->to
+ ]
+ ]
+ ];
+ break;
+ case 1: // Dailymotion
+ // Todo: add local version of script...
+ // Note: this plugin doesn't seem to work currently so it is not included
+ //$compiler->addJs('https://rawgit.com/benjipott/video.js-dailymotion/master/dist-test/videojs-dailymotion.js');
+ $setup = [
+// 'techOrder' => ['dailymotion'],
+// 'sources' => [
+// [
+// 'src' => 'http://www.dailymotion.com/video/' . $data->to
+// ]
+// ]
+ ];
+ break;
+ case 2: // Vimeo
+ // Todo: add local version of script...
+ // Note: Vimeo plugin doesn't seem to be working currently - might need updates to work with latest VideoJS module
+ //$compiler->addJs('https://rawgit.com/videojs/videojs-vimeo/master/dist/videojs-vimeo.min.js');
+ $setup = [
+// 'techOrder' => ['vimeo'],
+// 'sources' => [
+// [
+// 'type' => 'vimeo/vimeo',
+// 'src' => 'https://www.vimeo.com/' . $data->to
+// ]
+// ]
+ ];
+ break;
+ default:
+ $setup = [];
+ }
+
+ return json_encode($setup, JSON_UNESCAPED_SLASHES);
+
+ }
+
public function getHTMLContent() {
+
+ if ($this->video_service !== 0) {
return $this->getEmbed();
}
+ $w = round($this->width * $this->getCssScale());
+ $h = round($this->height * $this->getCssScale());
+
+ return $this->makeVideoTag($this, $w, $h, $this->compiler);
+ }
+
public function getEmbed() {
return '<iframe width="' . $this->width . '" height="' . $this->height . '" src="' . $this->getEmbedURL() . '" frameborder="0" allowfullscreen></iframe>';
}
} elseif ($this->video_service == 1) {
$url = 'https://www.dailymotion.com/embed/video/' . $this->to;
} elseif ($this->video_service == 2) {
+ //Todo: get vimeo embed URL
$url = '';
} elseif ($this->video_service == 3) {
list($playerId, $videoId) = explode('|', $this->to);
class webVideoPopupLink extends videoPopupLink {
+// public function getURL() {
+// if ($this->video_service == 0) {
+// $service = 'youtube';
+// } elseif ($this->video_service == 1) {
+// $service = 'dailymotion';
+// } elseif ($this->video_service == 2) {
+// $service = 'vimeo';
+// } elseif ($this->video_service == 3) {
+// $service = 'brightcove';
+// }
+// return '#/webvideo/' . $service . '/' . $this->to;
+// }
+
public function getURL() {
- if ($this->video_service == 0) {
- $service = 'youtube';
- } elseif ($this->video_service == 1) {
- $service = 'dailymotion';
- } elseif ($this->video_service == 2) {
- $service = 'vimeo';
- } elseif ($this->video_service == 3) {
- $service = 'brightcove';
+ return '#/video/' . $this->to;
}
- return '#/webvideo/' . $service . '/' . $this->to;
+
+ public function getAdditionnalContent() {
+ $this->video_auto_start = true; // Videos should always autoplay
+ return ' data-video="' . rawurlencode(webVideoLink::makeVideoTag($this, $this->video_width, $this->video_height, $this->compiler)) . '" ';
}
}
}
$this->compiler->simpleCopyLinkFile($both, 'data/links/zoom_' . $this->id . '.jpg');
+
+ // Perform tidy up and delete temporary files if they exist
+ $files_to_delete = ['left', 'leftfile', 'right', 'rightfile', 'both'];
+ foreach($files_to_delete as $file) {
+ if (isset($$file) && file_exists($$file)) {
+ unlink($$file);
+ }
+ }
}