XOOPS 2.5.6  Final
 All Classes Namespaces Files Functions Variables Pages
theme.php
Go to the documentation of this file.
1 <?php
22 defined('XOOPS_ROOT_PATH') or die('Restricted access');
23 
33 {
34  var $xoBundleIdentifier = 'xos_opal_ThemeFactory';
40  var $allowedThemes = array();
46  var $defaultTheme = 'default';
52  var $allowUserSelection = true;
53 
57  function &createInstance($options = array(), $initArgs = array())
58  {
59  // Grab the theme folder from request vars if present
60  if (empty($options['folderName'])) {
61  if (($req = @$_REQUEST['xoops_theme_select']) && $this->isThemeAllowed($req)) {
62  $options['folderName'] = $req;
63  if (isset($_SESSION) && $this->allowUserSelection) {
64  $_SESSION[$this->xoBundleIdentifier]['defaultTheme'] = $req;
65  }
66  } else if (isset($_SESSION[$this->xoBundleIdentifier]['defaultTheme'])) {
67  $options['folderName'] = $_SESSION[$this->xoBundleIdentifier]['defaultTheme'];
68  } else if (empty($options['folderName']) || ! $this->isThemeAllowed($options['folderName'])) {
69  $options['folderName'] = $this->defaultTheme;
70  }
71  $GLOBALS['xoopsConfig']['theme_set'] = $options['folderName'];
72  }
73  $options['path'] = XOOPS_THEME_PATH . '/' . $options['folderName'];
74  $inst = null;
75  $inst = new xos_opal_Theme();
76  foreach ($options as $k => $v) {
77  $inst->$k = $v;
78  }
79  $inst->xoInit();
80  return $inst;
81  }
82 
89  function isThemeAllowed($name)
90  {
91  return (empty($this->allowedThemes) || in_array($name, $this->allowedThemes));
92  }
93 }
94 
104 class xos_opal_AdminThemeFactory extends xos_opal_ThemeFactory
105 {
106  function &createInstance($options = array(), $initArgs = array())
107  {
108  $options["plugins"] = array();
109  $options['renderBanner'] = false;
110  $inst =& parent::createInstance($options, $initArgs);
111  $inst->path = XOOPS_ADMINTHEME_PATH . '/' . $inst->folderName;
112  $inst->url = XOOPS_ADMINTHEME_URL . '/' . $inst->folderName;
113  $inst->template->assign(array(
114  'theme_path' => $inst->path,
115  'theme_tpl' => $inst->path.'/xotpl',
116  'theme_url' => $inst->url,
117  'theme_img' => $inst->url.'/img',
118  'theme_icons' => $inst->url.'/icons',
119  'theme_css' => $inst->url.'/css',
120  'theme_js' => $inst->url.'/js',
121  'theme_lang' => $inst->url.'/language',
122  ));
123 
124  return $inst;
125  }
126 }
127 
129 {
135  var $renderBanner = true;
141  var $folderName = '';
147  var $path = '';
148  var $url = '';
149 
155  var $bufferOutput = true;
161  var $canvasTemplate = 'theme.html';
162 
168  var $themesPath = 'themes';
169 
176 
178  var $contentCacheId = null;
179 
185  var $content = '';
192  var $plugins = array(
193  'xos_logos_PageBuilder');
194  var $renderCount = 0;
200  var $template = false;
201 
207  var $metas = array(
208  //'http' => array(
209  // 'Content-Script-Type' => 'text/javascript' ,
210  // 'Content-Style-Type' => 'text/css') ,
211  'meta' => array() ,
212  'link' => array() ,
213  'script' => array());
214 
220  var $htmlHeadStrings = array();
226  var $templateVars = array();
227 
234 
255  function xoInit($options = array())
256  {
257  $this->path = XOOPS_THEME_PATH . '/' . $this->folderName;
258  $this->url = XOOPS_THEME_URL . '/' . $this->folderName;
259  $this->template = null;
260  $this->template = new XoopsTpl();
261  $this->template->currentTheme =& $this;
262  $this->template->assign_by_ref('xoTheme', $this);
263  $this->template->assign(array(
264  'xoops_theme' => $GLOBALS['xoopsConfig']['theme_set'] ,
265  'xoops_imageurl' => XOOPS_THEME_URL . '/' . $GLOBALS['xoopsConfig']['theme_set'] . '/',
266  'xoops_themecss' => xoops_getcss($GLOBALS['xoopsConfig']['theme_set']),
267  'xoops_requesturi' => htmlspecialchars($_SERVER['REQUEST_URI'], ENT_QUOTES),
268  'xoops_sitename' => htmlspecialchars($GLOBALS['xoopsConfig']['sitename'], ENT_QUOTES),
269  'xoops_slogan' => htmlspecialchars($GLOBALS['xoopsConfig']['slogan'], ENT_QUOTES),
270  'xoops_dirname' => isset($GLOBALS['xoopsModule'])&& is_object($GLOBALS['xoopsModule']) ? $GLOBALS['xoopsModule']->getVar('dirname') : 'system',
271  'xoops_banner' => ($GLOBALS['xoopsConfig']['banners'] && $this->renderBanner) ? xoops_getbanner() : '&nbsp;',
272  'xoops_pagetitle' => isset($GLOBALS['xoopsModule']) && is_object($GLOBALS['xoopsModule']) ? $GLOBALS['xoopsModule']->getVar('name') : htmlspecialchars($GLOBALS['xoopsConfig']['slogan'], ENT_QUOTES)));
273 
274  if (isset($GLOBALS['xoopsUser']) && is_object($GLOBALS['xoopsUser'])) {
275  $this->template->assign(array(
276  'xoops_isuser' => true,
277  'xoops_avatar' => XOOPS_UPLOAD_URL . "/" . $GLOBALS['xoopsUser']->getVar('user_avatar'),
278  'xoops_userid' => $GLOBALS['xoopsUser']->getVar('uid'),
279  'xoops_uname' => $GLOBALS['xoopsUser']->getVar('uname'),
280  'xoops_name' => $GLOBALS['xoopsUser']->getVar('name'),
281  'xoops_isadmin' => $GLOBALS['xoopsUserIsAdmin'],
282  'xoops_usergroups' => $GLOBALS['xoopsUser']->getGroups()));
283  } else {
284  $this->template->assign(array(
285  'xoops_isuser' => false,
286  'xoops_isadmin' => false,
287  'xoops_usergroups' => array(XOOPS_GROUP_ANONYMOUS)));
288  }
289 
290  // Meta tags
291  $config_handler =& xoops_gethandler('config');
292  $criteria = new CriteriaCompo(new Criteria('conf_modid', 0));
293  $criteria->add(new Criteria('conf_catid', XOOPS_CONF_METAFOOTER));
294  $config = $config_handler->getConfigs($criteria, true);
295  foreach (array_keys($config) as $i) {
296  $name = $config[$i]->getVar('conf_name', 'n');
297  $value = $config[$i]->getVar('conf_value', 'n');
298  if (substr($name, 0, 5) == 'meta_') {
299  $this->addMeta('meta', substr($name, 5), $value);
300  } else {
301  // prefix each tag with 'xoops_'
302  $this->template->assign("xoops_$name", $value);
303  }
304  }
305  // Load global javascript
306  $this->addScript('include/xoops.js');
307  $this->loadLocalization();
308 
309  if ($this->bufferOutput) {
310  ob_start();
311  }
312  $GLOBALS['xoTheme'] =& $this;
313  $GLOBALS['xoopsTpl'] =& $this->template;
314  // Instanciate and initialize all the theme plugins
315  foreach ($this->plugins as $k => $bundleId) {
316  if (!is_object($bundleId)) {
317  $this->plugins[$bundleId] = null;
318  $this->plugins[$bundleId] = new $bundleId();
319  $this->plugins[$bundleId]->theme =& $this;
320  $this->plugins[$bundleId]->xoInit();
321  unset($this->plugins[$k]);
322  }
323  }
324  return true;
325  }
326 
336  function generateCacheId($cache_id, $extraString = '')
337  {
338  static $extra_string;
339  if (!$this->use_extra_cache_id) {
340  return $cache_id;
341  }
342 
343  if (empty($extraString)) {
344  if (empty($extra_string)) {
345  // Generate language section
346  $extra_string = $GLOBALS['xoopsConfig']['language'];
347  // Generate group section
348  if (!isset($GLOBALS['xoopsUser']) || !is_object($GLOBALS['xoopsUser'])) {
349  $extra_string .= '-' . XOOPS_GROUP_ANONYMOUS;
350  } else {
351  $groups = $GLOBALS['xoopsUser']->getGroups();
352  sort($groups);
353  // Generate group string for non-anonymous groups,
354  // XOOPS_DB_PASS and XOOPS_DB_NAME (before we find better variables) are used to protect group sensitive contents
355  $extra_string .= '-' . substr(md5(implode('-', $groups)), 0, 8) . '-' . substr(md5(XOOPS_DB_PASS . XOOPS_DB_NAME . XOOPS_DB_USER), 0, 8);
356  }
357  }
358  $extraString = $extra_string;
359  }
360  $cache_id .= '-' . $extraString;
361  return $cache_id;
362  }
363 
369  function checkCache()
370  {
371  if ($_SERVER['REQUEST_METHOD'] != 'POST' && $this->contentCacheLifetime) {
372  $template = $this->contentTemplate ? $this->contentTemplate : 'db:system_dummy.html';
373  $this->template->caching = 2;
374  $this->template->cache_lifetime = $this->contentCacheLifetime;
375  $uri = str_replace(XOOPS_URL, '', $_SERVER['REQUEST_URI']);
376  // Clean uri by removing session id
377  if (defined('SID') && SID && strpos($uri, SID)) {
378  $uri = preg_replace("/([\?&])(" . SID . "$|" . SID . "&)/", "\\1", $uri);
379  }
380  $this->contentCacheId = $this->generateCacheId('page_' . substr(md5($uri), 0, 8));
381  if ($this->template->is_cached($template, $this->contentCacheId)) {
383  $xoopsLogger->addExtra($template, sprintf('Cached (regenerates every %d seconds)', $this->contentCacheLifetime));
384  $this->render(null, null, $template);
385  return true;
386  }
387  }
388  return false;
389  }
390 
405  function render($canvasTpl = null, $pageTpl = null, $contentTpl = null, $vars = array())
406  {
407  if ($this->renderCount) {
408  return false;
409  }
411  $xoopsLogger->startTime('Page rendering');
412 
413  xoops_load('xoopscache');
414  $cache =& XoopsCache::getInstance();
415 
416  //Get meta information for cached pages
417  if ($this->contentCacheLifetime && $this->contentCacheId && $content = $cache->read($this->contentCacheId)) {
418  //we need to merge metas set by blocks ) with the module cached meta
419  $this->htmlHeadStrings = array_merge($this->htmlHeadStrings, $content['htmlHeadStrings']);
420  foreach ($content['metas'] as $type => $value) {
421  $this->metas[$type] = array_merge($this->metas[$type], $content['metas'][$type]);
422  }
423  $GLOBALS['xoopsOption']['xoops_pagetitle'] = $content['xoops_pagetitle'];
424  $GLOBALS['xoopsOption']['xoops_module_header'] = $content['header'];
425  }
426 
427  if (!empty($GLOBALS['xoopsOption']['xoops_pagetitle'])) {
428  $this->template->assign('xoops_pagetitle', $GLOBALS['xoopsOption']['xoops_pagetitle']);
429  }
430  $header = empty($GLOBALS['xoopsOption']['xoops_module_header']) ? $this->template->get_template_vars('xoops_module_header') : $GLOBALS['xoopsOption']['xoops_module_header'];
431 
432  //save meta information of cached pages
433  if ($this->contentCacheLifetime && $this->contentCacheId && !$contentTpl) {
434  $content['htmlHeadStrings'] = $this->htmlHeadStrings;
435  $content['metas'] = $this->metas;
436  $content['xoops_pagetitle'] = $this->template->get_template_vars('xoops_pagetitle');
437  $content['header'] = $header;
438  $cache->write($this->contentCacheId, $content);
439  }
440 
441  // @internal : Lame fix to ensure the metas specified in the xoops config page don't appear twice
442  $old = array(
443  'robots',
444  'keywords',
445  'description',
446  'rating',
447  'author',
448  'copyright');
449  foreach ($this->metas['meta'] as $name => $value) {
450  if (in_array($name, $old)) {
451  $this->template->assign("xoops_meta_$name", htmlspecialchars($value, ENT_QUOTES));
452  unset($this->metas['meta'][$name]);
453  }
454  }
455 
456  // We assume no overlap between $GLOBALS['xoopsOption']['xoops_module_header'] and $this->template->get_template_vars( 'xoops_module_header' ) ?
457  $this->template->assign('xoops_module_header', $this->renderMetas(null, true) . "\n" . $header);
458 
459 
460  if ($canvasTpl) {
461  $this->canvasTemplate = $canvasTpl;
462  }
463  if ($contentTpl) {
464  $this->contentTemplate = $contentTpl;
465  }
466  if (!empty($vars)) {
467  $this->template->assign($vars);
468  }
469  if ($this->contentTemplate) {
470  $this->content = $this->template->fetch($this->contentTemplate, $this->contentCacheId);
471  }
472  if ($this->bufferOutput) {
473  $this->content .= ob_get_contents();
474  ob_end_clean();
475  }
476 
477  $this->template->assign_by_ref('xoops_contents', $this->content);
478 
479  // Do not cache the main (theme.html) template output
480  $this->template->caching = 0;
481  $this->template->display($this->path . '/' . $this->canvasTemplate);
482  $this->renderCount++;
483  $xoopsLogger->stopTime('Page rendering');
484  return true;
485  }
486 
497  function loadLocalization($type = "main")
498  {
499  $language = xoops_getConfigOption('language');
500  // Load global localization stylesheet if available
501  if (file_exists($GLOBALS['xoops']->path('language/' . $language . '/style.css'))) {
502  $this->addStylesheet($GLOBALS['xoops']->url('language/' . $language . '/style.css'));
503  }
504  $this->addLanguage($type);
505  // Load theme localization stylesheet and scripts if available
506  if (file_exists($this->path . '/language/' . $language . '/script.js')) {
507  $this->addScript($this->url . '/language/' . $language . '/script.js');
508  }
509  if (file_exists($this->path . '/language/' . $language . '/style.css')) {
510  $this->addStylesheet($this->url . '/language/' . $language . '/style.css');
511  }
512  return true;
513  }
514 
521  function addLanguage($type = "main", $language = null)
522  {
523  $language = is_null($language) ? $GLOBALS["xoopsConfig"]["language"] : $language;
524  if (!file_exists($fileinc = $GLOBALS['xoops']->path($this->resourcePath("/language/{$language}/{$type}.php")))) {
525  if (!file_exists($fileinc = $GLOBALS['xoops']->path($this->resourcePath( "/language/english/{$type}.php")))) {
526  return false;
527  }
528  }
529  $ret = include_once $fileinc;
530  return $ret;
531  }
532 
565  function addScript($src = '', $attributes = array(), $content = '', $name = '')
566  {
567  if (empty($attributes)) {
568  $attributes = array();
569  }
570  if (!empty($src)) {
571  $src = $GLOBALS['xoops']->url($this->resourcePath($src));
572  $attributes['src'] = $src;
573  }
574  if (!empty($content)) {
575  $attributes['_'] = $content;
576  }
577  if (!isset($attributes['type'])) {
578  $attributes['type'] = 'text/javascript';
579  }
580  if (empty($name)) {
581  $name = md5(serialize($attributes));
582  }
583  $this->addMeta('script', $name, $attributes);
584  }
585 
586 
596  function addStylesheet($src = '', $attributes = array(), $content = '', $name = '')
597  {
598  if (empty($attributes)) {
599  $attributes = array();
600  }
601  if (!empty($src)) {
602  $src = $GLOBALS['xoops']->url($this->resourcePath($src));
603  $attributes['href'] = $src;
604  }
605  if (!isset($attributes['type'])) {
606  $attributes['type'] = 'text/css';
607  }
608  if (!empty($content)) {
609  $attributes['_'] = $content;
610  }
611  if (empty($name)) {
612  $name = md5(serialize($attributes));
613  }
614  $this->addMeta('stylesheet', $name, $attributes);
615  }
616 
625  function addLink($rel, $href = '', $attributes = array(), $name = '')
626  {
627  if (empty($attributes)) {
628  $attributes = array();
629  }
630  if (!empty($href)) {
631  $attributes['href'] = $href;
632  }
633  $attributes['rel'] = $rel;
634  if (empty($name)) {
635  $name = md5(serialize($attributes));
636  }
637  $this->addMeta('link', $name, $attributes);
638  }
639 
640 
644  function addHttpMeta($name, $value = null)
645  {
646  if (isset($value)) {
647  return $this->addMeta('http', $name, $value);
648  }
649  unset($this->metas['http'][$name]);
650  }
651 
655  function addMeta($type = 'meta', $name = '', $value = '')
656  {
657  if (!isset($this->metas[$type])) {
658  $this->metas[$type] = array();
659  }
660  if (!empty($name)) {
661  $this->metas[$type][$name] = $value;
662  } else {
663  $this->metas[$type][md5(serialize(array($value)))] = $value;
664  }
665  return $value;
666  }
667 
677  function headContent($params, $content, &$smarty, &$repeat)
678  {
679  if (!$repeat) {
680  $this->htmlHeadStrings[] = $content;
681  }
682  }
683 
691  function renderMetas($type = null, $return = false)
692  {
693  $str = '';
694  if (!isset($type)) {
695  foreach (array_keys($this->metas) as $type) {
696  $str .= $this->renderMetas($type, true);
697  }
698  $str .= implode("\n", $this->htmlHeadStrings);
699  } else {
700  switch ($type) {
701  case 'script':
702  foreach ($this->metas[$type] as $attrs) {
703  $str .= "<script" . $this->renderAttributes($attrs) . ">";
704  if (@$attrs['_']) {
705  $str .= "\n//<![CDATA[\n" . $attrs['_'] . "\n//]]>";
706  }
707  $str .= "</script>\n";
708  }
709  break;
710  case 'link':
711  foreach ($this->metas[$type] as $attrs) {
712  $rel = $attrs['rel'];
713  unset($attrs['rel']);
714  $str .= '<link rel="' . $rel . '"' . $this->renderAttributes($attrs) . " />\n";
715  }
716  break;
717  case 'stylesheet':
718  foreach ($this->metas[$type] as $attrs) {
719  if (@$attrs['_']) {
720  $str .= '<style' . $this->renderAttributes($attrs) . ">\n/* <![CDATA[ */\n" . $attrs['_'] . "\n/* //]]> */\n</style>";
721  } else {
722  $str .= '<link rel="stylesheet"' . $this->renderAttributes($attrs) . " />\n";
723  }
724  }
725  break;
726  case 'http':
727  foreach ($this->metas[$type] as $name => $content) {
728  $str .= '<meta http-equiv="' . htmlspecialchars($name, ENT_QUOTES) . '" content="' . htmlspecialchars($content, ENT_QUOTES) . "\" />\n";
729  }
730  break;
731  default:
732  foreach ($this->metas[$type] as $name => $content) {
733  $str .= '<meta name="' . htmlspecialchars($name, ENT_QUOTES) . '" content="' . htmlspecialchars($content, ENT_QUOTES) . "\" />\n";
734  }
735  break;
736  }
737  }
738  if ($return) {
739  return $str;
740  }
741  echo $str;
742  return true;
743  }
744 
751  function genElementId($tagName = 'xos')
752  {
753  static $cache = array();
754  if (!isset($cache[$tagName])) {
755  $cache[$tagName] = 1;
756  }
757  return $tagName . '-' . $cache[$tagName] ++;
758  }
759 
766  function renderAttributes($coll)
767  {
768  $str = '';
769  foreach ($coll as $name => $val) {
770  if ($name != '_') {
771  $str .= ' ' . $name . '="' . htmlspecialchars($val, ENT_QUOTES) . '"';
772  }
773  }
774  return $str;
775  }
776 
783  function resourcePath($path)
784  {
785  if (substr($path, 0, 1) == '/') {
786  $path = substr($path, 1);
787  }
788 
789  if (file_exists(XOOPS_ROOT_PATH . "/{$this->themesPath}/{$this->folderName}/{$path}")) {
790  return "{$this->themesPath}/{$this->folderName}/{$path}";
791  }
792 
793  if (file_exists(XOOPS_ROOT_PATH . "/themes/{$this->folderName}/{$path}")) {
794  return "themes/{$this->folderName}/{$path}";
795  }
796  return $path;
797  }
798 }
799 
800 ?>