mirror of
https://github.com/less/less.js.git
synced 2026-04-09 03:00:20 -04:00
Added support for variables in certain at-rules (keyframes, namespace, charset).
This commit is contained in:
@@ -1662,7 +1662,7 @@ less.Parser = function Parser(env) {
|
||||
//
|
||||
directive: function () {
|
||||
var index = i, name, value, rules, nonVendorSpecificName,
|
||||
hasBlock, hasIdentifier, hasExpression, identifier;
|
||||
hasIdentifier, hasExpression, hasUnknown, hasBlock = true;
|
||||
|
||||
if (input.charAt(i) !== '@') { return; }
|
||||
|
||||
@@ -1683,9 +1683,8 @@ less.Parser = function Parser(env) {
|
||||
}
|
||||
|
||||
switch(nonVendorSpecificName) {
|
||||
/*
|
||||
case "@font-face":
|
||||
hasBlock = true;
|
||||
break;
|
||||
case "@viewport":
|
||||
case "@top-left":
|
||||
case "@top-left-corner":
|
||||
@@ -1705,42 +1704,55 @@ less.Parser = function Parser(env) {
|
||||
case "@right-bottom":
|
||||
hasBlock = true;
|
||||
break;
|
||||
*/
|
||||
case "@charset":
|
||||
hasIdentifier = true;
|
||||
hasBlock = false;
|
||||
break;
|
||||
case "@namespace":
|
||||
hasExpression = true;
|
||||
hasBlock = false;
|
||||
break;
|
||||
case "@keyframes":
|
||||
hasIdentifier = true;
|
||||
break;
|
||||
case "@host":
|
||||
case "@page":
|
||||
case "@document":
|
||||
case "@supports":
|
||||
case "@keyframes":
|
||||
hasBlock = true;
|
||||
hasIdentifier = true;
|
||||
break;
|
||||
case "@namespace":
|
||||
hasExpression = true;
|
||||
hasUnknown = true;
|
||||
break;
|
||||
}
|
||||
|
||||
if (hasIdentifier) {
|
||||
identifier = ($re(/^[^{]+/) || '').trim();
|
||||
if (identifier) {
|
||||
name += " " + identifier;
|
||||
value = this.entity();
|
||||
if (!value) {
|
||||
error("expected " + name + " identifier");
|
||||
}
|
||||
} else if (hasExpression) {
|
||||
value = this.expression();
|
||||
if (!value) {
|
||||
error("expected " + name + " expression");
|
||||
}
|
||||
} else if (hasUnknown) {
|
||||
value = ($re(/^[^{;]+/) || '').trim();
|
||||
if (value) {
|
||||
value = new(tree.Anonymous)(value);
|
||||
}
|
||||
}
|
||||
|
||||
if (hasBlock) {
|
||||
rules = this.block();
|
||||
if (rules) {
|
||||
return new(tree.Directive)(name, rules, index, env.currentFileInfo);
|
||||
}
|
||||
} else {
|
||||
value = hasExpression ? this.expression() : this.entity();
|
||||
if (value && $char(';')) {
|
||||
var directive = new(tree.Directive)(name, value, index, env.currentFileInfo);
|
||||
if (env.dumpLineNumbers) {
|
||||
directive.debugInfo = getDebugInfo(i, input, env);
|
||||
}
|
||||
return directive;
|
||||
if (rules) {
|
||||
rules = new(tree.Ruleset)(null, rules);
|
||||
}
|
||||
}
|
||||
|
||||
if (rules || (!hasBlock && value && $char(';'))) {
|
||||
return new(tree.Directive)(name, value, rules, index, env.currentFileInfo,
|
||||
env.dumpLineNumbers ? getDebugInfo(index, input, env) : null);
|
||||
}
|
||||
|
||||
restore();
|
||||
},
|
||||
|
||||
|
||||
@@ -1,58 +1,62 @@
|
||||
(function (tree) {
|
||||
|
||||
tree.Directive = function (name, value, index, currentFileInfo) {
|
||||
this.name = name;
|
||||
|
||||
if (Array.isArray(value)) {
|
||||
this.rules = [new(tree.Ruleset)(null, value)];
|
||||
this.rules[0].allowImports = true;
|
||||
} else {
|
||||
this.value = value;
|
||||
tree.Directive = function (name, value, rules, index, currentFileInfo, debugInfo) {
|
||||
this.name = name;
|
||||
this.value = value;
|
||||
if (rules) {
|
||||
this.rules = rules;
|
||||
this.rules.allowImports = true;
|
||||
}
|
||||
this.index = index;
|
||||
this.currentFileInfo = currentFileInfo;
|
||||
|
||||
this.debugInfo = debugInfo;
|
||||
};
|
||||
|
||||
tree.Directive.prototype = {
|
||||
type: "Directive",
|
||||
accept: function (visitor) {
|
||||
if (this.rules) {
|
||||
this.rules = visitor.visitArray(this.rules);
|
||||
var value = this.value, rules = this.rules;
|
||||
if (rules) {
|
||||
rules = visitor.visit(rules);
|
||||
}
|
||||
if (this.value) {
|
||||
this.value = visitor.visit(this.value);
|
||||
if (value) {
|
||||
value = visitor.visit(value);
|
||||
}
|
||||
},
|
||||
genCSS: function (env, output) {
|
||||
var value = this.value, rules = this.rules;
|
||||
output.add(this.name, this.currentFileInfo, this.index);
|
||||
if (this.rules) {
|
||||
tree.outputRuleset(env, output, this.rules);
|
||||
} else {
|
||||
if (value) {
|
||||
output.add(' ');
|
||||
this.value.genCSS(env, output);
|
||||
value.genCSS(env, output);
|
||||
}
|
||||
if (rules) {
|
||||
tree.outputRuleset(env, output, [rules]);
|
||||
} else {
|
||||
output.add(';');
|
||||
}
|
||||
},
|
||||
toCSS: tree.toCSS,
|
||||
eval: function (env) {
|
||||
var evaldDirective = this;
|
||||
if (this.rules) {
|
||||
env.frames.unshift(this);
|
||||
evaldDirective = new(tree.Directive)(this.name, null, this.index, this.currentFileInfo);
|
||||
evaldDirective.rules = [this.rules[0].eval(env)];
|
||||
evaldDirective.rules[0].root = true;
|
||||
env.frames.shift();
|
||||
var value = this.value, rules = this.rules;
|
||||
if (value) {
|
||||
value = value.eval(env);
|
||||
}
|
||||
return evaldDirective;
|
||||
if (rules) {
|
||||
rules = rules.eval(env);
|
||||
rules.root = true;
|
||||
}
|
||||
return new(tree.Directive)(this.name, value, rules,
|
||||
this.index, this.currentFileInfo, this.debugInfo);
|
||||
},
|
||||
variable: function (name) { return tree.Ruleset.prototype.variable.call(this.rules[0], name); },
|
||||
find: function () { return tree.Ruleset.prototype.find.apply(this.rules[0], arguments); },
|
||||
rulesets: function () { return tree.Ruleset.prototype.rulesets.apply(this.rules[0]); },
|
||||
variable: function (name) { if (this.rules) return tree.Ruleset.prototype.variable.call(this.rules, name); },
|
||||
find: function () { if (this.rules) return tree.Ruleset.prototype.find.apply(this.rules, arguments); },
|
||||
rulesets: function () { if (this.rules) return tree.Ruleset.prototype.rulesets.apply(this.rules); },
|
||||
markReferenced: function () {
|
||||
var i, rules;
|
||||
this.isReferenced = true;
|
||||
if (this.rules) {
|
||||
rules = this.rules[0].rules;
|
||||
rules = this.rules.rules;
|
||||
for (i = 0; i < rules.length; i++) {
|
||||
if (rules[i].markReferenced) {
|
||||
rules[i].markReferenced();
|
||||
|
||||
Reference in New Issue
Block a user