/** * @todo Finish documentation of smarty_function_widgetarea * @param array $params Associative (and/or indexed) array of smarty parameters passed in from the template * @param Smarty_Internal_Template $smarty Parent Smarty template object * * @return string|void */ function smarty_function_widgetarea($params, $smarty) { // Get all widgets set to load in this area. $body = ''; $baseurl = PageRequest::GetSystemRequest()->getBaseURL(); $template = $smarty->template_resource; $tmpl = $smarty->getTemplateVars('__core_template'); $topview = ($tmpl instanceof \Core\Templates\TemplateInterface) ? $tmpl->getView() : \Core\view(); $parameters = []; $name = null; $installable = null; $assign = null; foreach($params as $k => $v){ switch($k){ case 'name': $name = $v; break; case 'installable': $installable = $v; break; case 'assign': $assign = $v; break; default: $parameters[$k] = $v; break; } } // I need to resolve the page template down to the base version in order for the lookup to work. foreach(Core\Templates\Template::GetPaths() as $base){ if(strpos($template, $base) === 0){ $template = substr($template, strlen($base)); break; } } // Given support for page-level widgets, this logic gets slightly more difficult... $factory = new ModelFactory('WidgetInstanceModel'); $factory->order('weight'); if(Core::IsComponentAvailable('multisite') && MultiSiteHelper::IsEnabled()){ $factory->whereGroup('or', ['site = -1', 'site = ' . MultiSiteHelper::GetCurrentSiteID()]); } $subwhere = new Core\Datamodel\DatasetWhereClause(); $subwhere->setSeparator('OR'); // First, the skin-level where clause. $skinwhere = new Core\Datamodel\DatasetWhereClause(); $skinwhere->setSeparator('AND'); $skinwhere->addWhere('template = ' . $template); $skinwhere->addWhere('widgetarea = ' . $name); $subwhere->addWhere($skinwhere); // And second, the page-level where clause. if($baseurl){ $pagewhere = new Core\Datamodel\DatasetWhereClause(); $pagewhere->setSeparator('AND'); $pagewhere->addWhere('page_baseurl = ' . $baseurl); $pagewhere->addWhere('widgetarea = ' . $name); $subwhere->addWhere($pagewhere); } $factory->where($subwhere); $widgetcount = 0; try{ $widgets = $factory->get(); } catch(Exception $e){ if(DEVELOPMENT_MODE){ $body .= '<p class="message-error">Exception while trying to load widget area ' . $name . '!</p>'; $body .= '<pre class="xdebug-var-dump">' . $e->getMessage() . '</pre>'; } else{ \Core\ErrorManagement\exception_handler($e, false); } $widgets = []; ++$widgetcount; } foreach ($widgets as $wi) { /** @var $wi WidgetInstanceModel */ // User cannot access this widget? Don't display it... if(!\Core\user()){ continue; } if (!\Core\user()->checkAccess($wi->get('access'))){ continue; } if($installable){ $wi->set('installable', $installable); } $view = $wi->execute($parameters); // Some widgets may return simply a blank string. Those should just be ignored. if ($view == ''){ continue; } // If it's just a string, return that. if (is_string($view)) { $contents = $view; } elseif($view->error == View::ERROR_NOERROR){ // Ensure that the widget's View knows it's linked to a parent! $view->parent = $topview; $contents = $view->fetch(); } else{ $contents = 'Error displaying widget [' . $wi->get('baseurl') . '], returned error [' . $view->error . ']'; } ++$widgetcount; // Does this widget have controls attached to it? $widget = $wi->getWidget(); if($widget->controls instanceof ViewControls && $widget->controls->hasLinks()){ $contents = '<div class="widget-controls-wrapper">' . '<menu id="widget-controls-' . $wi->get('id') . '">' . $widget->controls->fetch() . '</menu>' . '</div>' . $contents; } $body .= '<div class="widget">' . $contents . '</div>'; } // Do some sanitizing for the css data $class = 'widgetarea-' . strtolower(str_replace(' ', '', $name)); $html = '<div class="widgetarea ' . $class . '" widgetarea="' . $name . '">' . $body . '</div>'; // No widgets, no inner content! if($widgetcount == 0){ $html = ''; } if($assign){ $smarty->assign($assign, $html); } else{ return $html; } }
/** * Get the page model for the current page. * * @return PageModel */ public function getPageModel() { if ($this->_pagemodel === null) { $uri = $this->uriresolved; $pagefac = new ModelFactory('PageModel'); $pagefac->where('rewriteurl = ' . $uri); //$pagefac->where('fuzzy = 0'); $pagefac->limit(1); if(Core::IsComponentAvailable('multisite') && MultiSiteHelper::IsEnabled()){ $pagefac->whereGroup('OR', array('site = -1', 'site = ' . MultiSiteHelper::GetCurrentSiteID())); } $p = $pagefac->get(); // Split this URL, it'll be used somewhere. $pagedat = $this->splitParts(); if ($p) { // :) Found it $this->_pagemodel = $p; } elseif ($pagedat && isset($pagedat['baseurl'])) { // Is this even a valid controller? // This will allow a page to be called with it being in the pages database. $p = new PageModel($pagedat['baseurl']); if(!$p->exists()){ $p->set('rewriteurl', $pagedat['rewriteurl']); } $this->_pagemodel = $p; } else { // No page in the database and no valid controller... sigh $this->_pagemodel = new PageModel(); } //var_dump($p); die(); // Make sure all the parameters from both standard GET and core parameters are tacked on. if ($pagedat && $pagedat['parameters']) { foreach ($pagedat['parameters'] as $k => $v) { $this->_pagemodel->setParameter($k, $v); } } if (is_array($_GET)) { foreach ($_GET as $k => $v) { if (is_numeric($k)) continue; $this->_pagemodel->setParameter($k, $v); } } } return $this->_pagemodel; }
<?php /** * Upgrade file for 2.4.2 to 2.4.3 to handle setting the selectable flag appropriately. Admin pages should * not be selectable. * * @package Core */ // Give me the page system! require_once(ROOT_PDIR . 'core/models/PageModel.class.php'); // Get every page that currently exists $factory = new ModelFactory('PageModel'); $factory->whereGroup( 'OR', array( 'admin = 1', 'baseurl LIKE /user/%', ) ); $pages = $factory->get(); foreach($pages as $page){ /** @var $page PageModel */ $page->set('selectable', '0'); $page->save(); }
/** * Display a listing of all widgets registered in the system. */ public function admin(){ $view = $this->getView(); $request = $this->getPageRequest(); $viewer = \Core\user()->checkAccess('p:/core/widgets/manage'); $manager = \Core\user()->checkAccess('p:/core/widgets/manage'); if(!($viewer || $manager)){ return View::ERROR_ACCESSDENIED; } // Build a list of create pages for all registered components. $components = Core::GetComponents(); $pages = []; $skins = []; $selected = null; $selectedtype = null; $baseurl = null; $selectoptions = []; $links = []; $theme = ThemeHandler::GetTheme(); $formtheme = null; $formskin = null; $formtemplate = null; foreach($components as $c){ /** @var Component_2_1 $c */ $viewdir = $c->getViewSearchDir(); if($viewdir){ $dirlen = strlen($viewdir); $component = $c->getName(); $dh = \Core\Filestore\Factory::Directory($viewdir); //$pagetplfiles = $dh->ls('tpl', true); $pagetplfiles = $dh->ls(null, true); // not sure why getFilename(path) isn't working as expected, but this works too. foreach($pagetplfiles as $obj){ // I don't want directories. if($obj instanceof \Core\Filestore\Directory) continue; /** @var $obj \Core\Filestore\File */ $file = substr($obj->getFilename(), $dirlen); // Since this is a template, it may actually be in a different location than where the package maintainer put it. // ie: user template user/templates/pages/user/view.tpl may be installed to themes/myawesometheme/pages/user/view.tpl instead. $tpl = Core\Templates\Template::Factory($file); if($tpl->hasWidgetAreas()){ $pagetitle = $file; if(strpos($pagetitle, 'pages/') === 0){ $pagetitle = substr($pagetitle, 6); } // Replace directory slashes with a space $pagetitle = str_replace(['/', '-'], ' ', $pagetitle); // Capitalize them $pagetitle = ucwords($pagetitle); // And trim off the ".tpl" suffix. $pagetitle = substr($pagetitle, 0, -4); $pages[$file] = $pagetitle; } } } foreach($c->getXML()->getElements('/widgets/widgetcreate') as $node){ /** @var DOMElement $node */ if($node->getAttribute('baseurl')){ $nodebaseurl = $node->getAttribute('baseurl'); $image = ''; } elseif($node->getAttribute('class')){ /** @var Widget_2_1 $obj */ $obj = Widget_2_1::Factory($node->getAttribute('class')); $nodebaseurl = '/widget/create?class=' . $node->getAttribute('class'); if($obj){ $image = $obj->getPreviewImage(); } else{ \Core\set_message('Invalid "widgetcreate" found in ' .$node->getAttribute('class') . ', ' . $node->getAttribute('title'), 'error'); $image = ''; } } else{ \Core\set_message('Invalid "widgetcreate" found in ' . $c->getName() . ', ' . $node->getAttribute('title'), 'error'); continue; } $links[] = [ 'baseurl' => $nodebaseurl, 'title' => $node->getAttribute('title'), 'preview' => $image, ]; } } // Build the array of skins for the current theme $themeskins = $theme->getSkins(); $defaultskin = null; foreach($themeskins as $dat){ $skins[ 'skins/' . $dat['file'] ] = $dat['title']; if($dat['default']){ $defaultskin = 'skins/' . $dat['file']; } } // Now that the various templates have been loaded into a flat array, I need to sort them. asort($pages); asort($skins); foreach($skins as $k => $v){ $selectoptions[ $k ] = 'Skin: ' . $v; } foreach($pages as $k => $v){ $selectoptions[ $k ] = 'Page: ' . $v; } if($request->getParameter('baseurl')){ // It's a URL-specific request, lookup which template that page used last. $baseurl = $request->getParameter('baseurl'); $page = PageModel::Construct($baseurl); if(!isset($pages[ $page->get('last_template') ])){ \Core\set_message('Requested page template does not seem to contain any widget areas.', 'error'); \Core\go_back(); } $selected = $page->get('last_template'); $selectedtype = 'url'; $formtemplate = $selected; } elseif($request->getParameter('template')){ $selected = $request->getParameter('template'); if(isset($pages[ $selected ])){ $selectedtype = 'page'; $formtemplate = $selected; } else{ $selectedtype = 'skin'; $formtheme = $theme->getKeyName(); $formskin = $selected; } } else{ // Just use the default theme skin. $selected = $defaultskin; $selectedtype = 'skin';$formtheme = $theme->getKeyName(); $formskin = $selected; } $template = \Core\Templates\Template::Factory($selected); $areas = $template->getWidgetAreas(); $installables = [0 => '']; foreach($areas as $k => $dat){ // Ensure that each area has a widgets array, (even if it's empty) $areas[$k]['widgets'] = []; $installables[] = $dat['installable']; } $installables = array_unique($installables); $factory = new ModelFactory('WidgetInstanceModel'); $factory->order('weight'); if(Core::IsComponentAvailable('multisite') && MultiSiteHelper::IsEnabled()){ $factory->whereGroup('or', ['site = -1', 'site = ' . MultiSiteHelper::GetCurrentSiteID()]); } if($selectedtype == 'skin'){ // First, the skin-level where clause. $skinwhere = new Core\Datamodel\DatasetWhereClause(); $skinwhere->setSeparator('AND'); //$skinwhere->addWhere('theme = ' . $theme->getKeyName()); $skinwhere->addWhere('template = ' . $selected); $factory->where($skinwhere); } elseif($selectedtype == 'page'){ $factory->where('template = ' . $selected); } elseif($selectedtype == 'url'){ $factory->where('page_baseurl = ' . $baseurl); } else{ \Core\set_message('Invalid/unknown template type', 'error'); \Core\go_back(); } foreach($factory->get() as $wi){ /** @var $wi WidgetInstanceModel */ $a = $wi->get('widgetarea'); $areas[$a]['widgets'][] = $wi; } $available = WidgetModel::Find(['installable IN ' . implode(', ', $installables)]); /* $table = new Core\ListingTable\Table(); $table->setName('/admin/widgets'); $table->setModelName('WidgetModel'); // Add in all the columns for this listing table. $table->addColumn('Title', 'title'); if(Core::IsComponentAvailable('enterprise') && MultiSiteHelper::IsEnabled() && \Core\user()->checkAccess('g:admin')){ $table->addColumn('Site', 'site', false); $ms = true; } else{ $ms = false; } $table->getModelFactory()->where('installable IN ' . implode(', ', $installables)); $table->addColumn('Base URL', 'baseurl'); $table->addColumn('Installable', 'installable'); $table->addColumn('Created', 'created'); $table->loadFiltersFromRequest(); */ $view->mastertemplate = 'admin'; $view->title = 'All Widgets'; //$view->assign('table', $table); $view->assign('available_widgets', $available); $view->assign('links', $links); $view->assign('manager', $manager); $view->assign('theme', $formtheme); $view->assign('skin', $formskin); $view->assign('template', $selected); $view->assign('page_template', $formtemplate); $view->assign('page_baseurl', $baseurl); $view->assign('options', $selectoptions); $view->assign('selected', $selected); $view->assign('areas', $areas); //$view->assign('multisite', $ms); }
public function sitemap(){ $view = $this->getView(); $req = $this->getPageRequest(); // Give me every registered (public) page! $factory = new ModelFactory('PageModel'); $factory->where('indexable = 1'); $factory->order('title'); // Multisite? if(Core::IsComponentAvailable('multisite') && MultiSiteHelper::IsEnabled()){ $factory->whereGroup( 'OR', array( 'site = ' . MultiSiteHelper::GetCurrentSiteID(), 'site = -1' ) ); $site = MultiSiteHelper::GetCurrentSiteID(); } else{ $site = null; } // Run this through the streamer, just in case there are a lot of pages... $stream = new \Core\Datamodel\DatasetStream($factory->getDataset()); $user = \Core\user(); $toshow = array(); while(($record = $stream->getRecord())){ if(!$user->checkAccess( $record['access'] )){ // Skip any further operations if the user does not have access to this page continue; } if($record['published_status'] != 'published'){ // Skip any further operations if the page isn't even marked as published. continue; } $page = new PageModel(); $page->_loadFromRecord($record); if(!$page->isPublished()){ // Skip out if the page is not marked as published. // This has extended checks other than simply if the status is set as "published", // such as publish date and expiration date. continue; } $toshow[] = $page; } // Anything else? $extra = HookHandler::DispatchHook('/sitemap/getlisting'); $toshow = array_merge($toshow, $extra); // This page allows for a few content types. switch($req->ctype){ case View::CTYPE_XML: $view->contenttype = View::CTYPE_XML; break; case View::CTYPE_HTML: $view->contenttype = View::CTYPE_HTML; break; } $view->title = 'Sitemap'; $view->assign('pages', $toshow); $view->assign('site', $site); }