2015-02-24 181 views
2

我有一个项目使用来自不同源文件夹的资产。其中一些资产可能会覆盖其他资产。我想引用一个树枝模板中的资产。如果资源存在于多个源文件夹中,则应选择第一个资源文件夹(例如,设计图像会覆盖模块图像)。我打算使用kriswallsmith/assetic包,但找不到指定多个根文件夹的方法。 我想要的是类似Twig_Loader_Filesystem::addPath但是用于资产。使用资产覆盖资产

例子:

源文件夹:

  • assets/design(包含images/red.jpg除了其他资产)
  • assets/module(包含images/red.jpg除了其他资产)

在树枝模板我想以参考

{% image 'images/red.jpg' %}<img src="{{ asset_url }}" />{% endimage %} 

库现在应该选择图像assets/design/images/red.jpg

这可能与assetic库? 如果我需要扩展任何类,你能给我一些指针吗? 或者是否有另一个库可以更好地满足我的需求?

回答

0

好吧,我意识到如何解决我的问题:

我必须扩展AssetFactory并覆盖parseInput方法。我想出了以下解决方案:

use Assetic\Asset\AssetInterface; 
use Assetic\Factory\AssetFactory; 

class MyAssetFactory extends AssetFactory 
{ 
    /** 
    * @var string[] 
    */ 
    private $rootFolders; 

    /** 
    * @param string[] $rootFolders 
    * @param bool $debug 
    */ 
    public function __construct($rootFolders, $debug = false) 
    { 
     if (empty($rootFolders)) { 
      throw new \Exception('there must be at least one folder'); 
     } 

     parent::__construct($rootFolders[0], $debug); 

     $this->rootFolders = $rootFolders; 
    } 

    /** 
    * @param string $input 
    * @param array $options 
    * @return AssetInterface an asset 
    */ 
    protected function parseInput($input, array $options = array()) 
    { 
     // let the parent handle references, http assets, absolute path and glob assets 
     if ('@' == $input[0] || false !== strpos($input, '://') || 0 === strpos($input, '//') || self::isAbsolutePath($input) || false !== strpos($input, '*')) { 
      return parent::parseInput($input, $options); 
     } 

     // now we have a relatve path eg js/file.js 
     // let's match it with the given rootFolders 
     $root = ''; 
     $path = $input; 
     foreach ($this->rootFolders as $root) { 
      if (file_exists($root . DIRECTORY_SEPARATOR . $input)) { 
       $path = $input; 
       $input = $root . $path; 
       break; 
      } 
     } 

     // TODO: what to do, if the asset was not found..? 

     return $this->createFileAsset($input, $root, $path, $options['vars']); 
    } 

    /** 
    * copied from AssetFactory, as it was private 
    * 
    * @param string $path 
    * @return bool 
    */ 
    private static function isAbsolutePath($path) 
    { 
     return '/' == $path[0] || '\\' == $path[0] || (3 < strlen($path) && ctype_alpha($path[0]) && $path[1] == ':' && ('\\' == $path[2] || '/' == $path[2])); 
    } 
} 

现在我可以用不同的源文件夹创建一个新工厂。

$factory = new MyAssetFactory(array('/folder/alpha/', '/folder/beta/')); 
// $factory->set some stuff 
$twig->addExtension(new AsseticExtension($factory));