derivatives) && !empty($this->derivatives[$derivative_id])) { return $this->derivatives[$derivative_id]; } $this->getDerivativeDefinitions($base_plugin_definition); return $this->derivatives[$derivative_id]; } /** * Implements DerivativeInterface::getDerivativeDefinitions(). */ public function getDerivativeDefinitions(array $base_plugin_definition) { $available_layout_providers = array(); // Add all modules as possible layout providers. // @todo Inject the module handler. foreach (drupal_container()->get('module_handler')->getModuleList() as $module => $filename) { $available_layout_providers[$module] = array( 'type' => 'module', 'provider' => $module, 'dir' => dirname($filename), ); } // Add all themes as possible layout providers. foreach (list_themes() as $theme_id => $theme) { $available_layout_providers[$theme_id] = array( 'type' => 'theme', 'provider' => $theme->name, 'dir' => drupal_get_path('theme', $theme->name), ); } foreach ($available_layout_providers as $provider) { // Looks for layouts in the 'layout' directory under the module/theme. // There could be subdirectories under there with one layout defined // in each. $dir = $provider['dir'] . DIRECTORY_SEPARATOR . 'layouts' . DIRECTORY_SEPARATOR . $this->type; if (file_exists($dir)) { $this->iterateDirectories($dir, $provider); } } return $this->derivatives; } /** * Finds layout definitions by looking for layout metadata. */ protected function iterateDirectories($dir, $provider) { $directories = new DirectoryIterator($dir); foreach ($directories as $fileinfo) { if ($fileinfo->isDir() && !$fileinfo->isDot()) { // Keep discovering in subdirectories to arbitrary depth. $this->iterateDirectories($fileinfo->getPathname(), $provider); } elseif ($fileinfo->isFile() && pathinfo($fileinfo->getFilename(), PATHINFO_EXTENSION) == 'yml') { // Declarative layout definitions are defined with a .yml file in a // layout subdirectory. This provides all information about the layout // such as layout markup template and CSS and JavaScript files to use. $directory = new FileStorage($fileinfo->getPath()); $key = $provider['provider'] . '__' . $fileinfo->getBasename('.yml'); $this->derivatives[$key] = $directory->read($fileinfo->getBasename('.yml')); $this->derivatives[$key]['theme'] = $key; $this->derivatives[$key]['path'] = $fileinfo->getPath(); $this->derivatives[$key]['provider'] = $provider; // If the layout author didn't specify a template name, assume the same // name as the yml file. if (!isset($this->derivatives[$key]['template'])) { $this->derivatives[$key]['template'] = $fileinfo->getBasename('.yml'); } } } } }