PageRenderTime 48ms CodeModel.GetById 15ms RepoModel.GetById 0ms app.codeStats 1ms

/src/legacy/Zikula/View/Theme.php

https://github.com/antoniom/core
PHP | 1007 lines | 479 code | 140 blank | 388 comment | 102 complexity | 819cc8b4f7365872c81e4429c8684001 MD5 | raw file
Possible License(s): GPL-3.0, LGPL-3.0, MIT
  1. <?php
  2. /**
  3. * Copyright Zikula Foundation 2009 - Zikula Application Framework
  4. *
  5. * This work is contributed to the Zikula Foundation under one or more
  6. * Contributor Agreements and licensed to You under the following license:
  7. *
  8. * @license GNU/LGPLv3 (or at your option, any later version).
  9. * @package Zikula_View
  10. *
  11. * Please see the NOTICE file distributed with this source code for further
  12. * information regarding copyright and licensing.
  13. */
  14. use Zikula\Core\Event\GenericEvent;
  15. use Zikula\Component\DependencyInjection\ContainerBuilder;
  16. use Symfony\Component\Yaml\Yaml;
  17. /**
  18. * Zikula_View_Theme class.
  19. */
  20. class Zikula_View_Theme extends Zikula_View
  21. {
  22. // base theme info
  23. /**
  24. * Theme name.
  25. *
  26. * @var string
  27. */
  28. public $name;
  29. /**
  30. * Directory.
  31. *
  32. * @var string
  33. */
  34. public $directory;
  35. /**
  36. * Version.
  37. *
  38. * @var string
  39. */
  40. public $version;
  41. /**
  42. * State.
  43. *
  44. * @var integer
  45. */
  46. public $state;
  47. /**
  48. * XHTML capable.
  49. *
  50. * @var integer
  51. */
  52. public $xhtml;
  53. // base theme properties
  54. /**
  55. * Theme base path.
  56. *
  57. * @var string
  58. */
  59. public $themepath;
  60. /**
  61. * Theme image path.
  62. *
  63. * @var string
  64. */
  65. public $imagepath;
  66. /**
  67. * Theme language image path.
  68. *
  69. * @var string
  70. */
  71. public $imagelangpath;
  72. /**
  73. * Theme stylesheet path.
  74. *
  75. * @var string
  76. */
  77. public $stylepath;
  78. /**
  79. * Theme script path.
  80. *
  81. * @var string
  82. */
  83. public $scriptpath;
  84. /**
  85. * Theme config.
  86. *
  87. * @var array
  88. */
  89. public $themeconfig;
  90. // base user information
  91. /**
  92. * User id.
  93. *
  94. * @var integer
  95. */
  96. public $uid;
  97. /**
  98. * Whether or not the user is logged in.
  99. *
  100. * @var boolean.
  101. */
  102. public $isloggedin;
  103. // publics to identify our page
  104. /**
  105. * Page type.
  106. *
  107. * @var string
  108. */
  109. public $pagetype;
  110. /**
  111. * Query string.
  112. *
  113. * @var string
  114. */
  115. public $qstring;
  116. /**
  117. * Request Uri.
  118. *
  119. * @var string
  120. */
  121. public $requesturi;
  122. /**
  123. * Internal override Map.
  124. *
  125. * @var array
  126. */
  127. protected $_overrideMap = array();
  128. /**
  129. * Constructor.
  130. *
  131. * @param ContainerBuilder $container ServiceManager.
  132. * @param string $themeName Theme name.
  133. */
  134. public function __construct(ContainerBuilder $container, $themeName)
  135. {
  136. // store our theme information
  137. $this->themeinfo = ThemeUtil::getInfo(ThemeUtil::getIDFromName($themeName));
  138. // prevents any case mismatch
  139. $themeName = $this->themeinfo['name'];
  140. foreach (array('name', 'directory', 'version', 'state', 'xhtml') as $key) {
  141. $this->$key = $this->themeinfo[$key];
  142. }
  143. parent::__construct($container);
  144. if ($this->themeinfo['i18n']) {
  145. ZLanguage::bindThemeDomain($this->name);
  146. // property for {gt} template plugin to detect language domain
  147. $this->domain = ZLanguage::getThemeDomain($this->name);
  148. } else {
  149. $this->domain = null;
  150. }
  151. EventUtil::attachCustomHandlers("themes/$themeName/EventHandlers");
  152. if (is_readable("themes/$themeName/Resources/config/overrides.yml")) {
  153. $this->dispatcher->addListener('zikula_view.template_override', array($this, '_templateOverride'), 0);
  154. $this->_overrideMap = Yaml::parse("themes/$themeName/Resources/config/overrides.yml");
  155. }
  156. $event = new GenericEvent($this);
  157. $this->dispatcher->dispatch('theme.preinit', $event);
  158. // change some base settings from our parent class
  159. // template compilation
  160. $this->compile_dir = CacheUtil::getLocalDir('Theme_compiled');
  161. $this->compile_check = ModUtil::getVar('Theme', 'compile_check');
  162. $this->force_compile = ModUtil::getVar('Theme', 'force_compile');
  163. // template caching
  164. $this->cache_dir = CacheUtil::getLocalDir('Theme_cache');
  165. $this->caching = (int)ModUtil::getVar('Theme', 'enablecache');
  166. //if ($this->caching) {
  167. // $this->cache_modified_check = true;
  168. //}
  169. // if caching and is not an admin controller
  170. if ($this->caching && strpos($this->type, 'admin') !== 0) {
  171. $modulesnocache = explode(',', ModUtil::getVar('Theme', 'modulesnocache'));
  172. if (in_array($this->toplevelmodule, $modulesnocache)) {
  173. $this->caching = Zikula_View::CACHE_DISABLED;
  174. }
  175. } else {
  176. $this->caching = Zikula_View::CACHE_DISABLED;
  177. }
  178. // halt caching for write operations to prevent strange things happening
  179. if (isset($_POST) && count($_POST) != 0) {
  180. $this->caching = Zikula_View::CACHE_DISABLED;
  181. }
  182. // and also for GET operations with csrftoken/authkey
  183. if (isset($_GET['csrftoken']) || isset($_GET['authkey'])) {
  184. $this->caching = Zikula_View::CACHE_DISABLED;
  185. }
  186. $this->cache_lifetime = ModUtil::getVar('Theme', 'cache_lifetime');
  187. if (!$this->homepage) {
  188. $this->cache_lifetime = ModUtil::getVar('Theme', 'cache_lifetime_mods');
  189. }
  190. // assign all our base template variables
  191. $this->_base_vars();
  192. // define the plugin directories
  193. $this->_plugin_dirs();
  194. // load the theme configuration
  195. $this->load_config();
  196. // check for cached output
  197. // turn on caching, check for cached output and then disable caching
  198. // to prevent blocks from being cached
  199. if ($this->caching && $this->is_cached($this->themeconfig['page'], $this->cache_id)) {
  200. $this->display($this->themeconfig['page'], $this->cache_id);
  201. System::shutdown();
  202. }
  203. // register page vars output filter
  204. $this->load_filter('output', 'pagevars');
  205. // register short urls output filter
  206. if (System::getVar('shorturls')) {
  207. $this->load_filter('output', 'shorturls');
  208. }
  209. // register trim whitespace output filter if requried
  210. if (ModUtil::getVar('Theme', 'trimwhitespace')) {
  211. $this->load_filter('output', 'trimwhitespace');
  212. }
  213. $event = new GenericEvent($this);
  214. $this->dispatcher->dispatch('theme.init', $event);
  215. }
  216. /**
  217. * Get Theme instance.
  218. *
  219. * @param string $themeName Theme name.
  220. * @param integer|null $caching Whether or not to cache (Zikula_View::CACHE_*) or use config variable (null).
  221. * @param string $cache_id Cache Id.
  222. *
  223. * @return Zikula_Theme This instance.
  224. */
  225. public static function getInstance($themeName = '', $caching = null, $cache_id = null)
  226. {
  227. if (!$themeName) {
  228. $themeName = UserUtil::getTheme();
  229. }
  230. $themeName = preg_match('/\w+Theme$/', $themeName) ? $themeName : $themeName.'Theme';
  231. $serviceId = 'zikula.theme';
  232. $container = ServiceUtil::getManager();
  233. if (!$container->has($serviceId)) {
  234. $themeInstance = new self($container, $themeName);
  235. $container->set($serviceId, $themeInstance);
  236. } else {
  237. $themeInstance = $container->get($serviceId);
  238. }
  239. if (!is_null($caching)) {
  240. $themeInstance->caching = $caching;
  241. }
  242. if (!is_null($cache_id)) {
  243. $themeInstance->cache_id = $cache_id;
  244. }
  245. return $themeInstance;
  246. }
  247. /**
  248. * Display the page output.
  249. *
  250. * @return string
  251. */
  252. public function themefooter($maincontent)
  253. {
  254. // add the module wrapper
  255. if (!$this->themeinfo['system'] && (bool)$this->themeconfig['modulewrapper'] && $this->toplevelmodule) {
  256. $maincontent = '<div id="z-maincontent" class="'.($this->homepage ? 'z-homepage ' : '').'z-module-' . DataUtil::formatForDisplay(strtolower($this->toplevelmodule)) . '">' . $maincontent . '</div>';
  257. }
  258. $event = new GenericEvent($this, array(), $maincontent);
  259. $this->dispatcher->dispatch('theme.prefetch', $event);
  260. $maincontent = $event->getData();
  261. // Assign the main content area to the template engine
  262. $this->assign('maincontent', $maincontent);
  263. // render the page using the correct template
  264. $output = $this->fetch($this->themeconfig['page'], $this->cache_id);
  265. $event = new GenericEvent($this, array(), $output);
  266. $this->dispatcher->dispatch('theme.postfetch', $event);
  267. return $event->getData();
  268. }
  269. /**
  270. * Display a block.
  271. *
  272. * @param array $block Block information.
  273. *
  274. * @return string The rendered output.
  275. */
  276. public function themesidebox($block)
  277. {
  278. // assign the block information
  279. $this->assign($block);
  280. $bid = $block['bid'];
  281. $bkey = strtolower($block['bkey']);
  282. $position = strtolower($block['position']);
  283. // fix block positions - for now....
  284. if ($position == 'l') {
  285. $position = 'left';
  286. }
  287. if ($position == 'c') {
  288. $position = 'center';
  289. }
  290. if ($position == 'r') {
  291. $position = 'right';
  292. }
  293. // HACK: Save/restore output filters - we don't want to output-filter blocks
  294. $outputfilters = $this->_plugins['outputfilter'];
  295. $this->_plugins['outputfilter'] = array();
  296. // HACK: Save/restore cache settings
  297. $caching = $this->caching;
  298. $this->caching = Zikula_View::CACHE_DISABLED;
  299. $return = '';
  300. // determine the correct template and construct the output
  301. if (isset($this->themeconfig['blockinstances'][$bid]) && !empty($this->themeconfig['blockinstances'][$bid])) {
  302. $return .= $this->fetch($this->themeconfig['blockinstances'][$bid]);
  303. } elseif (isset($this->themeconfig['blocktypes'][$bkey]) && !empty($this->themeconfig['blocktypes'][$bkey])) {
  304. $return .= $this->fetch($this->themeconfig['blocktypes'][$bkey]);
  305. } elseif (isset($this->themeconfig['blockpositions'][$position]) && !empty($this->themeconfig['blockpositions'][$position])) {
  306. $return .= $this->fetch($this->themeconfig['blockpositions'][$position]);
  307. } elseif (!empty($this->themeconfig['block'])) {
  308. $return .= $this->fetch($this->themeconfig['block']);
  309. } else {
  310. if (!empty($block['title'])) {
  311. $return .= '<h4>' . DataUtil::formatForDisplayHTML($block['title']) . ' ' . $block['minbox'] . '</h4>';
  312. }
  313. $return .= $block['content'];
  314. }
  315. // HACK: Save/restore output filters
  316. $this->_plugins['outputfilter'] = $outputfilters;
  317. // HACK: Save/restore cache settings
  318. $this->caching = $caching;
  319. if ((bool)$this->themeconfig['blockwrapper']) {
  320. $return = '<div class="z-block z-blockposition-' . DataUtil::formatForDisplay($block['position']) . ' z-bkey-' . DataUtil::formatForDisplay(strtolower($block['bkey'])) . ' z-bid-' . DataUtil::formatForDisplay($block['bid']) . '">' . "\n" . $return . "</div>\n";
  321. }
  322. return $return;
  323. }
  324. /**
  325. * Checks which path to use for required template.
  326. *
  327. * @param string $template The template name.
  328. *
  329. * @return string Template path.
  330. */
  331. public function get_template_path($template)
  332. {
  333. if (isset($this->templateCache[$template])) {
  334. return $this->templateCache[$template];
  335. }
  336. // get the theme path to templates
  337. $themeDir = DataUtil::formatForOS($this->directory);
  338. $osTemplate = DataUtil::formatForOS($template);
  339. if (is_dir("themes/$themeDir/Resources/views")) {
  340. $relativePath = "themes/$themeDir/Resources/views";
  341. }
  342. $templateFile = "$relativePath/$osTemplate";
  343. $override = self::getTemplateOverride($templateFile);
  344. if ($override === false) {
  345. if (is_readable($templateFile)) {
  346. $this->templateCache[$template] = $relativePath;
  347. return $relativePath;
  348. } else {
  349. return false;
  350. }
  351. } else {
  352. if (is_readable($override)) {
  353. $path = substr($override, 0, strrpos($override, $osTemplate));
  354. $this->templateCache[$template] = $path;
  355. return $path;
  356. }
  357. }
  358. // when we arrive here, no path was found
  359. return false;
  360. }
  361. /**
  362. * Define all our plugin directories.
  363. *
  364. * @return void
  365. */
  366. private function _plugin_dirs()
  367. {
  368. // add theme specific plugins directories, if they exist
  369. $this->addPluginDir('themes/' . $this->directory . '/Resources/views/plugins');
  370. }
  371. /**
  372. * Clears the cache for a specific cache_id's in all active themes.
  373. *
  374. * @param string $cache_ids Array of given cache ID's for which to clear theme cache.
  375. * @param string $themes Array of theme objects for which to clear theme cache, defaults to all active themes.
  376. *
  377. * @return boolean True on success.
  378. */
  379. public function clear_cacheid_allthemes($cache_ids, $themes = null)
  380. {
  381. if ($cache_ids) {
  382. if (!is_array($cache_ids)) {
  383. $cache_ids = array($cache_ids);
  384. }
  385. if (!$themes) {
  386. $themes = ThemeUtil::getAllThemes();
  387. }
  388. $theme = Zikula_View_Theme::getInstance();
  389. foreach ($themes as $themearr) {
  390. foreach ($cache_ids as $cache_id) {
  391. $theme->clear_cache(null, $cache_id, null, null, $themearr['directory']);
  392. }
  393. }
  394. }
  395. return true;
  396. }
  397. /**
  398. * Get a concrete filename for automagically created content.
  399. *
  400. * Generates a filename path like: Theme / auto_id [/ source_dir / filename-l{lang}.ext]
  401. * the final part gets generated only if $auto_source is specified.
  402. *
  403. * @param string $path The base path.
  404. * @param string $auto_source The file name (optional).
  405. * @param string $auto_id The ID (optional).
  406. *
  407. * @return string The concrete path and file name to the content.
  408. */
  409. public function _get_auto_filename($path, $auto_source = null, $auto_id = null, $themedir = null)
  410. {
  411. // enables a flags to detect when is treating compiled templates
  412. $tocompile = ($path == $this->compile_dir) ? true : false;
  413. // format auto_source for os to make sure that id does not contain 'ugly' characters
  414. $auto_source = DataUtil::formatForOS($auto_source);
  415. // add the Theme name as first folder
  416. if (empty($themedir)) {
  417. $path .= '/' . $this->directory;
  418. } else {
  419. $path .= '/' . $themedir;
  420. }
  421. // the last folder is the cache_id if set
  422. $path .= !empty($auto_id) ? '/' . $auto_id : '';
  423. // takes in account the source subdirectory
  424. $path .= strpos($auto_source, '/') !== false ? '/' . dirname($auto_source) : '';
  425. // make sure the path exists to write the compiled/cached template there
  426. if (!file_exists($path)) {
  427. mkdir($path, $this->container['system.chmod_dir'], true);
  428. }
  429. // if there's a explicit source, it
  430. if ($auto_source) {
  431. $path .= '/';
  432. $extension = FileUtil::getExtension($auto_source);
  433. // isolates the filename on the source path passed
  434. $path .= FileUtil::getFilebase($auto_source);
  435. // if we are compiling we do not include cache variables
  436. if (!$tocompile) {
  437. // add the variable stuff only if $auto_source is present
  438. // to allow a easy flush cache for all the languages (if needed)
  439. $path .= '-l';
  440. if (System::getVar('multilingual') == 1) {
  441. $path .= $this->language;
  442. }
  443. // end with a suffix convention of filename--Themename-lang.ext
  444. $path .= ($extension ? ".$extension" : '');
  445. }
  446. }
  447. return $path;
  448. }
  449. /**
  450. * Assign template vars for base theme paths and other useful variables.
  451. *
  452. * @return void
  453. */
  454. private function _base_vars()
  455. {
  456. // identify the page type
  457. $this->pagetype = 'module';
  458. if ((stristr(System::serverGetVar('PHP_SELF'), 'admin.php') || strtolower($this->type) == 'admin')) {
  459. $this->pagetype = 'admin';
  460. } else {
  461. $module = FormUtil::getPassedValue('module', null, 'GETPOST', FILTER_SANITIZE_STRING);
  462. if (empty($module)) {
  463. $this->pagetype = 'home';
  464. }
  465. }
  466. // set some basic class variables from Zikula
  467. $this->isloggedin = UserUtil::isLoggedIn();
  468. $this->uid = UserUtil::getVar('uid');
  469. // assign the query string
  470. $this->qstring = System::serverGetVar('QUERY_STRING', '');
  471. // assign the current script
  472. $this->requesturi = System::getCurrentUri();
  473. // define the cache_id if not set yet
  474. if ($this->caching && !$this->cache_id) {
  475. // module / type / function / customargs|homepage/startpageargs / uid_X|guest
  476. $this->cache_id = $this->toplevelmodule . '/' . $this->type . '/' . $this->func
  477. . (!$this->homepage ? $this->_get_customargs() : '/homepage/' . str_replace(',', '/', System::getVar('startargs')))
  478. . '/' . UserUtil::getUidCacheString();
  479. }
  480. // assign some basic paths for the engine
  481. $this->template_dir = $this->themepath . '/templates'; // default directory for templates
  482. $this->themepath = 'themes/' . $this->directory;
  483. $this->imagepath = $this->themepath . '/Resources/public/images';
  484. $this->imagelangpath = $this->themepath . '/Resources/public/images/' . $this->language;
  485. $this->stylepath = $this->themepath . '/Resources/public/css';
  486. $this->scriptpath = $this->themepath . '/Resources/public/js';
  487. // make the base vars available to all templates
  488. $this->assign('module', $this->toplevelmodule)
  489. ->assign('uid', $this->uid)
  490. ->assign('loggedin', $this->isloggedin)
  491. ->assign('pagetype', $this->pagetype)
  492. ->assign('themepath', $this->themepath)
  493. ->assign('imagepath', $this->imagepath)
  494. ->assign('imagelangpath', $this->imagelangpath)
  495. ->assign('stylepath', $this->stylepath)
  496. ->assign('scriptpath', $this->scriptpath);
  497. // load the theme variables
  498. $variables = ModUtil::apiFunc('ThemeModule', 'user', 'getvariables', array('theme' => $this->name));
  499. $this->assign($variables['variables']);
  500. }
  501. /**
  502. * Normalizes the current page parameters.
  503. *
  504. * Used on the page cache_id and the pageassignments keys.
  505. *
  506. * @return string Custom arguments string.
  507. */
  508. private function _get_customargs()
  509. {
  510. static $customargs;
  511. if (isset($customargs)) {
  512. return $customargs;
  513. }
  514. // parse the query string into individual arguments discarding common arguments
  515. // common arguments are ones that we don't want affecting our url matching or ones that are
  516. // already considered; These are same args defined as reserved by the MDG.
  517. $customargs = '';
  518. if ($this->pagetype != 'admin' && System::getVar('shorturls')) {
  519. // remove the base URI and the entrypoint from the request URI
  520. $customargs = str_replace(System::getBaseUri(), '', $this->requesturi);
  521. $entrypoint = System::getVar('entrypoint');
  522. $customargs = str_replace("/{$entrypoint}/", '/', $customargs);
  523. $customargs = ($customargs == '/') ? '' : $customargs;
  524. } else {
  525. $queryparts = explode('&', $this->qstring);
  526. foreach ($queryparts as $querypart) {
  527. if (!stristr($querypart, 'module=') && !stristr($querypart, 'type=') && !stristr($querypart, 'func=') && !stristr($querypart, 'theme=') && !stristr($querypart, 'authid=') && !stristr($querypart, 'csrftoken=')) {
  528. $customargs .= '/' . $querypart;
  529. }
  530. }
  531. }
  532. return $customargs;
  533. }
  534. /**
  535. * Load the base theme configuration.
  536. *
  537. * Can be used into the system but if the themeconfig['page'] is changed the cache
  538. * gets canceled because there will be no match between initial cache_id and default page.
  539. * Try to change only theme variables that changes the behaviour of the output.
  540. *
  541. * @return void
  542. */
  543. public function load_config()
  544. {
  545. if (!$this->themeconfig) {
  546. // load the page configurations
  547. $pageconfigurations = ModUtil::apiFunc('ThemeModule', 'user', 'getpageconfigurations', array('theme' => $this->name));
  548. // identify and load the correct module configuration
  549. // checks homepage match
  550. if ($this->homepage && isset($pageconfigurations['*home'])) {
  551. // allow us to match any non-zikula query string
  552. $homeWithArgs = 'home' . '/' . $this->qstring;
  553. if (isset($pageconfigurations[$homeWithArgs])) {
  554. $file = $pageconfigurations[$homeWithArgs]['file'];
  555. } else {
  556. $file = $pageconfigurations['*home']['file'];
  557. }
  558. $file = $pageconfigurations['*home']['file'];
  559. // identify a type match
  560. } elseif (isset($pageconfigurations['*'.$this->type])) {
  561. $file = $pageconfigurations['*'.$this->type]['file'];
  562. // identify an admin-like type
  563. } elseif (strpos($this->type, 'admin') === 0 && isset($pageconfigurations['*admin'])) {
  564. $file = $pageconfigurations['*admin']['file'];
  565. // search for arguments match
  566. } else {
  567. $customargs = $this->toplevelmodule . '/' . $this->type . '/' . $this->func . $this->_get_customargs();
  568. // find any page configurations that match in a sub string comparison
  569. $match = '';
  570. $matchlength = 0;
  571. foreach (array_keys($pageconfigurations) as $pageconfiguration) {
  572. if (stristr($customargs, $pageconfiguration) && $matchlength < strlen($pageconfiguration)) {
  573. $match = $pageconfiguration;
  574. $matchlength = strlen($match);
  575. if (isset($pageconfigurations[$pageconfiguration]['important']) && $pageconfigurations[$pageconfiguration]['important']) {
  576. break;
  577. }
  578. }
  579. }
  580. if (!empty($match)) {
  581. $file = $pageconfigurations[$match]['file'];
  582. }
  583. }
  584. if (empty($file)) {
  585. $file = $pageconfigurations['master']['file'];
  586. }
  587. // load the page configuration
  588. $this->themeconfig = ModUtil::apiFunc('ThemeModule', 'user', 'getpageconfiguration', array('theme' => $this->name, 'filename' => $file));
  589. // check if we've not got a valid theme configation
  590. if (!$this->themeconfig['page']) {
  591. $file = 'master.ini';
  592. $this->themeconfig = ModUtil::apiFunc('ThemeModule', 'user', 'getpageconfiguration', array('theme' => $this->name, 'filename' => $file));
  593. }
  594. }
  595. if (empty($this->themeconfig['page'])) {
  596. throw new Exception(__f("Empty 'page' specified in your theme page configuration on file %s.", array($file)));
  597. }
  598. // register any filters
  599. if (!empty($this->themeconfig['filters'])) {
  600. // check for output filters
  601. if (isset($this->themeconfig['filters']['outputfilters']) && !empty($this->themeconfig['filters']['outputfilters'])) {
  602. $filters = $this->themeconfig['filters']['outputfilters'];
  603. $filters = !is_array($filters) ? explode(',', $filters) : $filters;
  604. foreach ($filters as $filter) {
  605. $this->load_filter('output', $filter);
  606. }
  607. }
  608. // check for pre filters
  609. if (isset($this->themeconfig['filters']['prefilters']) && !empty($this->themeconfig['filters']['prefilters'])) {
  610. $filters = $this->themeconfig['filters']['prefilters'];
  611. $filters = !is_array($filters) ? explode(',', $filters) : $filters;
  612. foreach ($filters as $filter) {
  613. $this->load_filter('pre', $filter);
  614. }
  615. }
  616. // check for post filters
  617. if (isset($this->themeconfig['filters']['postfilters']) && !empty($this->themeconfig['filters']['postfilters'])) {
  618. $filters = $this->themeconfig['filters']['postfilters'];
  619. $filters = !is_array($filters) ? explode(',', $filters) : $filters;
  620. foreach ($filters as $filter) {
  621. $this->load_filter('post', $filter);
  622. }
  623. }
  624. }
  625. // load the pageconfiguration variables
  626. if (!empty($this->themeconfig['variables'])) {
  627. $this->assign($this->themeconfig['variables']);
  628. }
  629. // load the palette if set
  630. if (!empty($this->themeconfig['palette'])) {
  631. $palette = ModUtil::apiFunc('ThemeModule', 'user', 'getpalette', array('theme' => $this->name, 'palette' => $this->themeconfig['palette']));
  632. $this->assign('palette', $palette);
  633. }
  634. $event = new GenericEvent($this);
  635. $this->dispatcher->dispatch('theme.load_config', $event);
  636. }
  637. /**
  638. * Template override handler for 'zikula_view.template_override'.
  639. *
  640. * @param GenericEvent $event Event handler.
  641. *
  642. * @return void
  643. */
  644. public function _templateOverride(GenericEvent $event)
  645. {
  646. if (array_key_exists($event->data, $this->_overrideMap)) {
  647. $event->data = $this->_overrideMap[$event->data];
  648. $event->stopPropagation();
  649. }
  650. }
  651. /**
  652. * Clear CSS/JS combination cached files.
  653. *
  654. * Using this function, the user can clear all CSS/JS combination cached
  655. * files for the system.
  656. *
  657. * @return boolean
  658. */
  659. public function clear_cssjscombinecache()
  660. {
  661. $cache_dir = $this->cache_dir;
  662. $cached_files = FileUtil::getFiles($cache_dir, true, false, array('php'), null, false);
  663. foreach ($cached_files as $cf) {
  664. unlink(realpath($cf));
  665. }
  666. // The configuration has been changed, so we clear all caches.
  667. // clear Zikula_View_Theme cache
  668. self::clear_all_cache();
  669. // clear Zikula_View cache (really needed?)
  670. Zikula_View::getInstance()->clear_all_cache();
  671. return true;
  672. }
  673. /**
  674. * Clears the Theme configuration located on the temporary directory.
  675. *
  676. * @return boolean True on success, false otherwise.
  677. */
  678. public function clear_theme_config()
  679. {
  680. $configdir = CacheUtil::getLocalDir('Theme_Config');
  681. return $this->clear_folder($configdir, null, null, null);
  682. }
  683. /**
  684. * Retrieve the name of the theme.
  685. *
  686. * @return string The name.
  687. */
  688. public function getName()
  689. {
  690. return $this->name;
  691. }
  692. /**
  693. * Retrieve the theme directory name.
  694. *
  695. * @return <type>
  696. */
  697. public function getDirectory()
  698. {
  699. return $this->directory;
  700. }
  701. /**
  702. * Retrieve the theme's version string.
  703. *
  704. * @return string The version of the theme.
  705. */
  706. public function getVersion()
  707. {
  708. return $this->version;
  709. }
  710. /**
  711. * Retrieve the state of the theme.
  712. *
  713. * Values:
  714. * <ul>
  715. * <li>ThemeUtil::STATE_ACTIVE</li>
  716. * <li>ThemeUtil::STATE_INACTIVE</li>
  717. * <li>ThemeUtil::STATE_ALL</li>
  718. * </ul>
  719. *
  720. * @return integer The theme's state.
  721. */
  722. public function getState()
  723. {
  724. return $this->state;
  725. }
  726. /**
  727. * Indicates whether the theme is an XHTML-based theme or an HTML-based theme.
  728. *
  729. * @return integer 1 for XHTML-capable, otherwise HTML.
  730. */
  731. public function getXhtml()
  732. {
  733. return $this->xhtml;
  734. }
  735. /**
  736. * Retrieve the path to the theme.
  737. *
  738. * @return string The path to the theme.
  739. */
  740. public function getThemePath()
  741. {
  742. return $this->themepath;
  743. }
  744. /**
  745. * Retrieve the path to the theme's images.
  746. *
  747. * @return string The path to the theme's images.
  748. */
  749. public function getImagePath()
  750. {
  751. return $this->imagepath;
  752. }
  753. /**
  754. * Retrieve the path to the theme's language-specific images.
  755. *
  756. * @return string The path to the theme's language-specific images.
  757. */
  758. public function getImageLangPath()
  759. {
  760. return $this->imagelangpath;
  761. }
  762. /**
  763. * Retrieve the path to the theme's stylesheets.
  764. *
  765. * @return string The path to the theme's stylesheets.
  766. */
  767. public function getStylePath()
  768. {
  769. return $this->stylepath;
  770. }
  771. /**
  772. * Retrieve the path to the theme's javascript files.
  773. *
  774. * @return string The path to the theme's javascript files.
  775. */
  776. public function getScriptPath()
  777. {
  778. return $this->scriptpath;
  779. }
  780. /**
  781. * Retrieve the theme configuration.
  782. *
  783. * @return array The contents of the theme configuration (or the master configuration).
  784. */
  785. public function getThemeConfig()
  786. {
  787. return $this->themeconfig;
  788. }
  789. /**
  790. * Indicates whether this is a home page or not.
  791. *
  792. * @return boolean True if this is a home page (module name is empty), otherwise false.
  793. */
  794. public function isHomePage()
  795. {
  796. return $this->homepage;
  797. }
  798. /**
  799. * Retrieve the current user's uid.
  800. *
  801. * @return numeric The current user's uid.
  802. */
  803. public function getUid()
  804. {
  805. return $this->uid;
  806. }
  807. /**
  808. * Indicates whether the current user is logged in.
  809. *
  810. * @return boolean True if the current user is logged in, false if the current user is anonymous (a guest).
  811. */
  812. public function getIsLoggedIn()
  813. {
  814. return $this->isloggedin;
  815. }
  816. /**
  817. * The current page's type.
  818. *
  819. * @return string One of 'module', 'admin' or 'home'.
  820. */
  821. public function getPageType()
  822. {
  823. return $this->pagetype;
  824. }
  825. /**
  826. * Retrieve the query string for the current page request.
  827. *
  828. * @return string The query string for the current request.
  829. */
  830. public function getQstring()
  831. {
  832. return $this->qstring;
  833. }
  834. /**
  835. * Retrieve the current page's request URI.
  836. *
  837. * @return string The current page's request URI.
  838. */
  839. public function getRequestUri()
  840. {
  841. return $this->requesturi;
  842. }
  843. /**
  844. * Set the current cache ID.
  845. *
  846. * @param string $cache_id Cache ID to set.
  847. *
  848. * @return void
  849. */
  850. public function setCacheId($cache_id)
  851. {
  852. $this->cache_id = $cache_id;
  853. }
  854. /**
  855. * Set the theme configuration.
  856. *
  857. * @param array $themeconfig Theme configuration array to set.
  858. *
  859. * @return void
  860. */
  861. public function setThemeConfig($themeconfig)
  862. {
  863. if ($themeconfig && is_array($themeconfig)) {
  864. $this->themeconfig = $themeconfig;
  865. }
  866. }
  867. }