3 class Less_Tree_Mixin_Definition extends Less_Tree_Ruleset{
9 public $lookups = array();
11 public $frames = array();
14 public $type = 'MixinDefinition';
17 // less.js : /lib/less/tree/mixin.js : tree.mixin.Definition
18 public function __construct($name, $params, $rules, $condition, $variadic = false, $frames = array() ){
20 $this->selectors = array(new Less_Tree_Selector(array( new Less_Tree_Element(null, $name))));
22 $this->params = $params;
23 $this->condition = $condition;
24 $this->variadic = $variadic;
25 $this->rules = $rules;
28 $this->arity = count($params);
29 foreach( $params as $p ){
30 if (! isset($p['name']) || ($p['name'] && !isset($p['value']))) {
36 $this->frames = $frames;
37 $this->SetRulesetIndex();
42 //function accept( $visitor ){
43 // $this->params = $visitor->visit($this->params);
44 // $this->rules = $visitor->visit($this->rules);
45 // $this->condition = $visitor->visit($this->condition);
49 public function toCSS(){
53 // less.js : /lib/less/tree/mixin.js : tree.mixin.Definition.evalParams
54 public function compileParams($env, $mixinFrames, $args = array() , &$evaldArguments = array() ){
55 $frame = new Less_Tree_Ruleset(null, array());
56 $params = $this->params;
61 $argsLength = count($args);
62 for($i = 0; $i < $argsLength; $i++ ){
65 if( $arg && $arg['name'] ){
66 $isNamedFound = false;
68 foreach($params as $j => $param){
69 if( !isset($evaldArguments[$j]) && $arg['name'] === $params[$j]['name']) {
70 $evaldArguments[$j] = $arg['value']->compile($env);
71 array_unshift($frame->rules, new Less_Tree_Rule( $arg['name'], $arg['value']->compile($env) ) );
77 array_splice($args, $i, 1);
82 throw new Less_Exception_Compiler("Named argument for " . $this->name .' '.$args[$i]['name'] . ' not found');
89 foreach($params as $i => $param){
91 if ( isset($evaldArguments[$i]) ){ continue; }
94 if( isset($args[$argIndex]) ){
95 $arg = $args[$argIndex];
98 if (isset($param['name']) && $param['name']) {
100 if( isset($param['variadic']) ){
102 for ($j = $argIndex; $j < $argsLength; $j++) {
103 $varargs[] = $args[$j]['value']->compile($env);
105 $expression = new Less_Tree_Expression($varargs);
106 array_unshift($frame->rules, new Less_Tree_Rule($param['name'], $expression->compile($env)));
108 $val = ($arg && $arg['value']) ? $arg['value'] : false;
111 $val = $val->compile($env);
112 } else if ( isset($param['value']) ) {
115 $mixinEnv = new Less_Environment();
116 $mixinEnv->frames = array_merge( array($frame), $mixinFrames);
119 $val = $param['value']->compile($mixinEnv);
120 $frame->resetCache();
122 throw new Less_Exception_Compiler("Wrong number of arguments for " . $this->name . " (" . $argsLength . ' for ' . $this->arity . ")");
125 array_unshift($frame->rules, new Less_Tree_Rule($param['name'], $val));
126 $evaldArguments[$i] = $val;
130 if ( isset($param['variadic']) && $args) {
131 for ($j = $argIndex; $j < $argsLength; $j++) {
132 $evaldArguments[$j] = $args[$j]['value']->compile($env);
138 ksort($evaldArguments);
139 $evaldArguments = array_values($evaldArguments);
144 public function compile($env) {
146 return new Less_Tree_Mixin_Definition($this->name, $this->params, $this->rules, $this->condition, $this->variadic, $this->frames );
148 return new Less_Tree_Mixin_Definition($this->name, $this->params, $this->rules, $this->condition, $this->variadic, $env->frames );
151 public function evalCall($env, $args = NULL, $important = NULL) {
153 Less_Environment::$mixin_stack++;
155 $_arguments = array();
158 $mixinFrames = array_merge($this->frames, $env->frames);
160 $mixinFrames = $env->frames;
163 $frame = $this->compileParams($env, $mixinFrames, $args, $_arguments);
165 $ex = new Less_Tree_Expression($_arguments);
166 array_unshift($frame->rules, new Less_Tree_Rule('@arguments', $ex->compile($env)));
169 $ruleset = new Less_Tree_Ruleset(null, $this->rules);
170 $ruleset->originalRuleset = $this->ruleset_id;
173 $ruleSetEnv = new Less_Environment();
174 $ruleSetEnv->frames = array_merge( array($this, $frame), $mixinFrames );
175 $ruleset = $ruleset->compile( $ruleSetEnv );
178 $ruleset = $ruleset->makeImportant();
181 Less_Environment::$mixin_stack--;
187 public function matchCondition($args, $env) {
189 if( !$this->condition ){
193 // set array to prevent error on array_merge
194 if(!is_array($this->frames)) {
195 $this->frames = array();
198 $frame = $this->compileParams($env, array_merge($this->frames,$env->frames), $args );
200 $compile_env = new Less_Environment();
201 $compile_env->frames = array_merge(
202 array($frame) // the parameter variables
203 , $this->frames // the parent namespace/mixin frames
204 , $env->frames // the current environment frames
207 $compile_env->functions = $env->functions;
209 return (bool)$this->condition->compile($compile_env);
212 public function matchArgs($args, $env = NULL){
213 $argsLength = count($args);
215 if( !$this->variadic ){
216 if( $argsLength < $this->required ){
219 if( $argsLength > count($this->params) ){
223 if( $argsLength < ($this->required - 1)){
228 $len = min($argsLength, $this->arity);
230 for( $i = 0; $i < $len; $i++ ){
231 if( !isset($this->params[$i]['name']) && !isset($this->params[$i]['variadic']) ){
232 if( $args[$i]['value']->compile($env)->toCSS() != $this->params[$i]['value']->compile($env)->toCSS() ){