less 1.7.0 → 1.7.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (109) hide show
  1. package/.grunt/grunt-contrib-jasmine/es5-shim.js +1360 -0
  2. package/.idea/jsLibraryMappings.xml +0 -1
  3. package/.idea/workspace.xml +182 -183
  4. package/.travis.yml +0 -1
  5. package/CHANGELOG.md +60 -2
  6. package/CONTRIBUTING.md +1 -1
  7. package/Gruntfile.js +12 -24
  8. package/LICENSE +0 -2
  9. package/README.md +5 -3
  10. package/benchmark/less-benchmark.js +1 -2
  11. package/bin/lessc +13 -11
  12. package/bower.json +2 -2
  13. package/build/rhino-modules.js +1 -1
  14. package/dist/less-1.7.0.js +59 -59
  15. package/dist/less-1.7.0.min.js +12 -12
  16. package/dist/less-1.7.1.js +7936 -0
  17. package/dist/less-1.7.1.min.js +16 -0
  18. package/dist/less-1.7.2.js +7938 -0
  19. package/dist/less-1.7.2.min.js +16 -0
  20. package/dist/less-1.7.3.js +7942 -0
  21. package/dist/less-1.7.3.min.js +16 -0
  22. package/dist/less-1.7.4.js +7979 -0
  23. package/dist/less-1.7.4.min.js +16 -0
  24. package/dist/less-1.7.5.js +8008 -0
  25. package/dist/less-1.7.5.min.js +16 -0
  26. package/dist/less-rhino-1.7.0.js +48 -48
  27. package/dist/less-rhino-1.7.1.js +9311 -0
  28. package/dist/less-rhino-1.7.2.js +9313 -0
  29. package/dist/less-rhino-1.7.3.js +9317 -0
  30. package/dist/less-rhino-1.7.4.js +9354 -0
  31. package/dist/less-rhino-1.7.5.js +9383 -0
  32. package/dist/lessc-rhino-1.7.0.js +2 -2
  33. package/dist/lessc-rhino-1.7.1.js +449 -0
  34. package/dist/lessc-rhino-1.7.2.js +449 -0
  35. package/dist/lessc-rhino-1.7.3.js +449 -0
  36. package/dist/lessc-rhino-1.7.4.js +449 -0
  37. package/dist/lessc-rhino-1.7.5.js +449 -0
  38. package/lib/less/browser.js +14 -9
  39. package/lib/less/env.js +2 -0
  40. package/lib/less/fs.js +10 -0
  41. package/lib/less/functions.js +41 -38
  42. package/lib/less/import-visitor.js +9 -7
  43. package/lib/less/index.js +30 -18
  44. package/lib/less/lessc_helper.js +1 -0
  45. package/lib/less/parser/parser.js.orig +1747 -0
  46. package/lib/less/parser.js +81 -40
  47. package/lib/less/rhino.js +3 -3
  48. package/lib/less/source-map-output.js +1 -1
  49. package/lib/less/to-css-visitor.js +3 -0
  50. package/lib/less/tree/anonymous.js +7 -3
  51. package/lib/less/tree/directive.js +6 -0
  52. package/lib/less/tree/element.js +6 -22
  53. package/lib/less/tree/import.js +1 -1
  54. package/lib/less/tree/mixin.js +4 -3
  55. package/lib/less/tree/quoted.js +12 -4
  56. package/lib/less/tree/rule.js +7 -4
  57. package/lib/less/tree/rule.js.orig +164 -0
  58. package/lib/less/tree/ruleset.js +27 -2
  59. package/lib/less/tree/selector.js +1 -1
  60. package/lib/less/tree.js +2 -2
  61. package/package.json +13 -12
  62. package/test/browser/less.js +7317 -6931
  63. package/test/css/comments.css +8 -0
  64. package/test/css/css-3.css +9 -0
  65. package/test/css/functions.css +8 -8
  66. package/test/css/import-inline.css +4 -1
  67. package/test/css/import.css +6 -0
  68. package/test/css/javascript.css +5 -0
  69. package/test/css/mixins-guards.css +14 -3
  70. package/test/css/mixins.css +3 -0
  71. package/test/css/property-name-interp.css +1 -0
  72. package/test/css/urls.css +6 -0
  73. package/test/index.js +1 -1
  74. package/test/less/comments.less +14 -1
  75. package/test/less/css-3.less +12 -1
  76. package/test/less/errors/color-invalid-hex-code.less +3 -0
  77. package/test/less/errors/color-invalid-hex-code.txt +4 -0
  78. package/test/less/errors/color-invalid-hex-code2.less +3 -0
  79. package/test/less/errors/color-invalid-hex-code2.txt +4 -0
  80. package/test/less/errors/import-malformed.less +1 -0
  81. package/test/less/errors/import-malformed.txt +3 -0
  82. package/test/less/errors/import-no-semi.txt +1 -1
  83. package/test/less/errors/javascript-error.less +1 -1
  84. package/test/less/errors/javascript-error.txt +2 -2
  85. package/test/less/import-inline.less +1 -0
  86. package/test/less/import.less +8 -1
  87. package/test/less/javascript.less +9 -0
  88. package/test/less/mixins-guards.less +17 -3
  89. package/test/less/mixins.less +4 -0
  90. package/test/less/property-name-interp.less +4 -1
  91. package/test/less/property-name-interp.less.orig +59 -0
  92. package/test/less/urls.less +12 -0
  93. package/test/less-test.js +7 -8
  94. package/test/modify-vars.js +17 -0
  95. package/test/sourcemaps/basic.json +1 -1
  96. package/tmp/browser/test-runner-main.html +4 -0
  97. package/tmp/less.js +8295 -0
  98. package/build/README.md +0 -51
  99. package/tmp/browser/test-postProcessor.html +0 -59
  100. package/tmp/browser/test-runner-browser.html +0 -59
  101. package/tmp/browser/test-runner-errors.html +0 -267
  102. package/tmp/browser/test-runner-global-vars.html +0 -59
  103. package/tmp/browser/test-runner-legacy.html +0 -59
  104. package/tmp/browser/test-runner-modify-vars.html +0 -59
  105. package/tmp/browser/test-runner-no-js-errors.html +0 -59
  106. package/tmp/browser/test-runner-production.html +0 -55
  107. package/tmp/browser/test-runner-relative-urls.html +0 -59
  108. package/tmp/browser/test-runner-rootpath-relative.html +0 -59
  109. package/tmp/browser/test-runner-rootpath.html +0 -59
@@ -63,22 +63,22 @@ tree.functions = {
63
63
  },
64
64
 
65
65
  hue: function (color) {
66
- return new(tree.Dimension)(Math.round(color.toHSL().h));
66
+ return new(tree.Dimension)(color.toHSL().h);
67
67
  },
68
68
  saturation: function (color) {
69
- return new(tree.Dimension)(Math.round(color.toHSL().s * 100), '%');
69
+ return new(tree.Dimension)(color.toHSL().s * 100, '%');
70
70
  },
71
71
  lightness: function (color) {
72
- return new(tree.Dimension)(Math.round(color.toHSL().l * 100), '%');
72
+ return new(tree.Dimension)(color.toHSL().l * 100, '%');
73
73
  },
74
74
  hsvhue: function(color) {
75
- return new(tree.Dimension)(Math.round(color.toHSV().h));
75
+ return new(tree.Dimension)(color.toHSV().h);
76
76
  },
77
77
  hsvsaturation: function (color) {
78
- return new(tree.Dimension)(Math.round(color.toHSV().s * 100), '%');
78
+ return new(tree.Dimension)(color.toHSV().s * 100, '%');
79
79
  },
80
80
  hsvvalue: function (color) {
81
- return new(tree.Dimension)(Math.round(color.toHSV().v * 100), '%');
81
+ return new(tree.Dimension)(color.toHSV().v * 100, '%');
82
82
  },
83
83
  red: function (color) {
84
84
  return new(tree.Dimension)(color.rgb[0]);
@@ -93,7 +93,7 @@ tree.functions = {
93
93
  return new(tree.Dimension)(color.toHSL().a);
94
94
  },
95
95
  luma: function (color) {
96
- return new(tree.Dimension)(Math.round(color.luma() * color.alpha * 100), '%');
96
+ return new(tree.Dimension)(color.luma() * color.alpha * 100, '%');
97
97
  },
98
98
  luminance: function (color) {
99
99
  var luminance =
@@ -101,7 +101,7 @@ tree.functions = {
101
101
  + (0.7152 * color.rgb[1] / 255)
102
102
  + (0.0722 * color.rgb[2] / 255);
103
103
 
104
- return new(tree.Dimension)(Math.round(luminance * color.alpha * 100), '%');
104
+ return new(tree.Dimension)(luminance * color.alpha * 100, '%');
105
105
  },
106
106
  saturate: function (color, amount) {
107
107
  // filter: saturate(3.2);
@@ -221,7 +221,7 @@ tree.functions = {
221
221
  }
222
222
  },
223
223
  e: function (str) {
224
- return new(tree.Anonymous)(str instanceof tree.JavaScript ? str.evaluated : str);
224
+ return new(tree.Anonymous)(str instanceof tree.JavaScript ? str.evaluated : str.value);
225
225
  },
226
226
  escape: function (str) {
227
227
  return new(tree.Anonymous)(encodeURI(str.value).replace(/=/g, "%3D").replace(/:/g, "%3A").replace(/#/g, "%23").replace(/;/g, "%3B").replace(/\(/g, "%28").replace(/\)/g, "%29"));
@@ -302,7 +302,7 @@ tree.functions = {
302
302
  continue;
303
303
  }
304
304
  currentUnified = current.unit.toString() === "" && unitClone !== undefined ? new(tree.Dimension)(current.value, unitClone).unify() : current.unify();
305
- unit = currentUnified.unit.toString() === "" && unitStatic !== undefined ? unitStatic : currentUnified.unit.toString();
305
+ unit = currentUnified.unit.toString() === "" && unitStatic !== undefined ? unitStatic : currentUnified.unit.toString();
306
306
  unitStatic = unit !== "" && unitStatic === undefined || unit !== "" && order[0].unify().unit.toString() === "" ? unit : unitStatic;
307
307
  unitClone = unit !== "" && unitClone === undefined ? current.unit.toString() : unitClone;
308
308
  j = values[""] !== undefined && unit !== "" && unit === unitStatic ? values[""] : values[unit];
@@ -392,12 +392,12 @@ tree.functions = {
392
392
  },
393
393
  shade: function(color, amount) {
394
394
  return this.mix(this.rgb(0, 0, 0), color, amount);
395
- },
395
+ },
396
396
  extract: function(values, index) {
397
- index = index.value - 1; // (1-based index)
397
+ index = index.value - 1; // (1-based index)
398
398
  // handle non-array values as an array of length 1
399
399
  // return 'undefined' if index is invalid
400
- return Array.isArray(values.value)
400
+ return Array.isArray(values.value)
401
401
  ? values.value[index] : Array(values)[index];
402
402
  },
403
403
  length: function(values) {
@@ -414,7 +414,7 @@ tree.functions = {
414
414
  var mimetype = mimetypeNode.value;
415
415
  var filePath = (filePathNode && filePathNode.value);
416
416
 
417
- var fs = require('fs'),
417
+ var fs = require('./fs'),
418
418
  path = require('path'),
419
419
  useBase64 = false;
420
420
 
@@ -422,6 +422,13 @@ tree.functions = {
422
422
  filePath = mimetype;
423
423
  }
424
424
 
425
+ var fragmentStart = filePath.indexOf('#');
426
+ var fragment = '';
427
+ if (fragmentStart!==-1) {
428
+ fragment = filePath.slice(fragmentStart);
429
+ filePath = filePath.slice(0, fragmentStart);
430
+ }
431
+
425
432
  if (this.env.isPathRelative(filePath)) {
426
433
  if (this.currentFileInfo.relativeUrls) {
427
434
  filePath = path.join(this.currentFileInfo.currentDirectory, filePath);
@@ -470,7 +477,7 @@ tree.functions = {
470
477
  buf = useBase64 ? buf.toString('base64')
471
478
  : encodeURIComponent(buf);
472
479
 
473
- var uri = "\"data:" + mimetype + ',' + buf + "\"";
480
+ var uri = "\"data:" + mimetype + ',' + buf + fragment + "\"";
474
481
  return new(tree.URL)(new(tree.Anonymous)(uri));
475
482
  },
476
483
 
@@ -583,15 +590,15 @@ tree._mime = {
583
590
 
584
591
  var mathFunctions = {
585
592
  // name, unit
586
- ceil: null,
587
- floor: null,
588
- sqrt: null,
593
+ ceil: null,
594
+ floor: null,
595
+ sqrt: null,
589
596
  abs: null,
590
- tan: "",
591
- sin: "",
597
+ tan: "",
598
+ sin: "",
592
599
  cos: "",
593
- atan: "rad",
594
- asin: "rad",
600
+ atan: "rad",
601
+ asin: "rad",
595
602
  acos: "rad"
596
603
  };
597
604
 
@@ -616,19 +623,19 @@ function colorBlend(mode, color1, color2) {
616
623
  var ab = color1.alpha, cb, // backdrop
617
624
  as = color2.alpha, cs, // source
618
625
  ar, cr, r = []; // result
619
-
626
+
620
627
  ar = as + ab * (1 - as);
621
628
  for (var i = 0; i < 3; i++) {
622
629
  cb = color1.rgb[i] / 255;
623
630
  cs = color2.rgb[i] / 255;
624
631
  cr = mode(cb, cs);
625
632
  if (ar) {
626
- cr = (as * cs + ab * (cb
633
+ cr = (as * cs + ab * (cb
627
634
  - as * (cb + cs - cr))) / ar;
628
635
  }
629
636
  r[i] = cr * 255;
630
637
  }
631
-
638
+
632
639
  return new(tree.Color)(r, ar);
633
640
  }
634
641
 
@@ -638,7 +645,7 @@ var colorBlendMode = {
638
645
  },
639
646
  screen: function(cb, cs) {
640
647
  return cb + cs - cb * cs;
641
- },
648
+ },
642
649
  overlay: function(cb, cs) {
643
650
  cb *= 2;
644
651
  return (cb <= 1)
@@ -651,7 +658,7 @@ var colorBlendMode = {
651
658
  e = 1;
652
659
  d = (cb > 0.25) ? Math.sqrt(cb)
653
660
  : ((16 * cb - 12) * cb + 4) * cb;
654
- }
661
+ }
655
662
  return cb - (1 - 2 * cs) * e * (d - cb);
656
663
  },
657
664
  hardlight: function(cb, cs) {
@@ -698,25 +705,25 @@ tree.defaultFunc = {
698
705
 
699
706
  function initFunctions() {
700
707
  var f, tf = tree.functions;
701
-
708
+
702
709
  // math
703
710
  for (f in mathFunctions) {
704
711
  if (mathFunctions.hasOwnProperty(f)) {
705
712
  tf[f] = _math.bind(null, Math[f], mathFunctions[f]);
706
713
  }
707
714
  }
708
-
715
+
709
716
  // color blending
710
717
  for (f in colorBlendMode) {
711
718
  if (colorBlendMode.hasOwnProperty(f)) {
712
719
  tf[f] = colorBlend.bind(null, colorBlendMode[f]);
713
720
  }
714
721
  }
715
-
722
+
716
723
  // default
717
724
  f = tree.defaultFunc;
718
725
  tf["default"] = f.eval.bind(f);
719
-
726
+
720
727
  } initFunctions();
721
728
 
722
729
  function hsla(color) {
@@ -749,13 +756,9 @@ function clamp(val) {
749
756
  }
750
757
 
751
758
  tree.fround = function(env, value) {
752
- var p;
753
- if (env && (env.numPrecision != null)) {
754
- p = Math.pow(10, env.numPrecision);
755
- return Math.round(value * p) / p;
756
- } else {
757
- return value;
758
- }
759
+ var p = env && env.numPrecision;
760
+ //add "epsilon" to ensure numbers like 1.000000005 (represented as 1.000000004999....) are properly rounded...
761
+ return (p == null) ? value : Number((value + 2e-16).toFixed(p));
759
762
  };
760
763
 
761
764
  tree.functionCall = function(env, currentFileInfo) {
@@ -38,7 +38,7 @@
38
38
  var importVisitor = this,
39
39
  evaldImportNode,
40
40
  inlineCSS = importNode.options.inline;
41
-
41
+
42
42
  if (!importNode.css || inlineCSS) {
43
43
 
44
44
  try {
@@ -61,10 +61,13 @@
61
61
  }
62
62
 
63
63
  this._importer.push(importNode.getPath(), importNode.currentFileInfo, importNode.options, function (e, root, importedAtRoot, fullPath) {
64
- if (e && !e.filename) { e.index = importNode.index; e.filename = importNode.currentFileInfo.filename; }
64
+ if (e && !e.filename) {
65
+ e.index = importNode.index; e.filename = importNode.currentFileInfo.filename;
66
+ }
65
67
 
66
- if (!env.importMultiple) {
67
- if (importedAtRoot) {
68
+ var duplicateImport = importedAtRoot || fullPath in importVisitor.recursionDetector;
69
+ if (!env.importMultiple) {
70
+ if (duplicateImport) {
68
71
  importNode.skip = true;
69
72
  } else {
70
73
  importNode.skip = function() {
@@ -73,7 +76,7 @@
73
76
  }
74
77
  importVisitor.onceFileDetectionMap[fullPath] = true;
75
78
  return false;
76
- };
79
+ };
77
80
  }
78
81
  }
79
82
 
@@ -88,7 +91,6 @@
88
91
  if (root) {
89
92
  importNode.root = root;
90
93
  importNode.importedFilename = fullPath;
91
- var duplicateImport = importedAtRoot || fullPath in importVisitor.recursionDetector;
92
94
 
93
95
  if (!inlineCSS && (env.importMultiple || !duplicateImport)) {
94
96
  importVisitor.recursionDetector[fullPath] = true;
@@ -131,7 +133,7 @@
131
133
  this.env.frames.shift();
132
134
  },
133
135
  visitMedia: function (mediaNode, visitArgs) {
134
- this.env.frames.unshift(mediaNode.ruleset);
136
+ this.env.frames.unshift(mediaNode.rules[0]);
135
137
  return mediaNode;
136
138
  },
137
139
  visitMediaOut: function (mediaNode) {
package/lib/less/index.js CHANGED
@@ -1,10 +1,10 @@
1
1
  var path = require('path'),
2
2
  url = require('url'),
3
3
  request,
4
- fs = require('fs');
4
+ fs = require('./fs');
5
5
 
6
6
  var less = {
7
- version: [1, 7, 0],
7
+ version: [1, 7, 5],
8
8
  Parser: require('./parser').Parser,
9
9
  tree: require('./tree'),
10
10
  render: function (input, options, callback) {
@@ -24,19 +24,19 @@ var less = {
24
24
  var css;
25
25
  try {
26
26
  css = root && root.toCSS && root.toCSS(options);
27
- }
27
+ }
28
28
  catch (err) { callback(err); return; }
29
29
  callback(null, css);
30
- });
30
+ }, options);
31
31
  } else {
32
32
  ee = new (require('events').EventEmitter)();
33
33
 
34
34
  process.nextTick(function () {
35
35
  parser.parse(input, function (e, root) {
36
36
  if (e) { return ee.emit('error', e); }
37
- try { ee.emit('success', root.toCSS(options)); }
37
+ try { ee.emit('success', root.toCSS(options)); }
38
38
  catch (err) { ee.emit('error', err); }
39
- });
39
+ }, options);
40
40
  });
41
41
  return ee;
42
42
  }
@@ -143,13 +143,13 @@ less.Parser.fileLoader = function (file, currentFileInfo, callback, env) {
143
143
  function handleDataAndCallCallback(data) {
144
144
  var j = file.lastIndexOf('/');
145
145
 
146
- // Pass on an updated rootpath if path of imported file is relative and file
146
+ // Pass on an updated rootpath if path of imported file is relative and file
147
147
  // is in a (sub|sup) directory
148
- //
149
- // Examples:
148
+ //
149
+ // Examples:
150
150
  // - If path of imported file is 'module/nav/nav.less' and rootpath is 'less/',
151
151
  // then rootpath should become 'less/module/nav/'
152
- // - If path of imported file is '../mixins.less' and rootpath is 'less/',
152
+ // - If path of imported file is '../mixins.less' and rootpath is 'less/',
153
153
  // then rootpath should become 'less/../'
154
154
  if(newFileInfo.relativeUrls && !/^(?:[a-z-]+:|\/)/.test(file) && j != -1) {
155
155
  var relativeSubDirectory = file.slice(0, j+1);
@@ -160,7 +160,7 @@ less.Parser.fileLoader = function (file, currentFileInfo, callback, env) {
160
160
 
161
161
  callback(null, data, pathname, newFileInfo);
162
162
  }
163
-
163
+
164
164
  var isUrl = isUrlRe.test( file );
165
165
  if (isUrl || isUrlRe.test(currentFileInfo.currentDirectory)) {
166
166
  if (request === undefined) {
@@ -175,7 +175,16 @@ less.Parser.fileLoader = function (file, currentFileInfo, callback, env) {
175
175
  var urlStr = isUrl ? file : url.resolve(currentFileInfo.currentDirectory, file),
176
176
  urlObj = url.parse(urlStr);
177
177
 
178
+ if (!urlObj.protocol) {
179
+ urlObj.protocol = "http";
180
+ urlStr = urlObj.format();
181
+ }
182
+
178
183
  request.get({uri: urlStr, strictSSL: !env.insecure }, function (error, res, body) {
184
+ if (error) {
185
+ callback({ type: 'File', message: "resource '" + urlStr + "' gave this Error:\n "+ error +"\n" });
186
+ return;
187
+ }
179
188
  if (res.statusCode === 404) {
180
189
  callback({ type: 'File', message: "resource '" + urlStr + "' was not found\n" });
181
190
  return;
@@ -183,17 +192,15 @@ less.Parser.fileLoader = function (file, currentFileInfo, callback, env) {
183
192
  if (!body) {
184
193
  console.error( 'Warning: Empty body (HTTP '+ res.statusCode + ') returned by "' + urlStr +'"' );
185
194
  }
186
- if (error) {
187
- callback({ type: 'File', message: "resource '" + urlStr + "' gave this Error:\n "+ error +"\n" });
188
- }
189
195
  pathname = urlStr;
190
196
  dirname = urlObj.protocol +'//'+ urlObj.host + urlObj.pathname.replace(/[^\/]*$/, '');
191
197
  handleDataAndCallCallback(body);
192
198
  });
193
199
  } else {
194
200
 
195
- var paths = [currentFileInfo.currentDirectory].concat(env.paths);
196
- paths.push('.');
201
+ var paths = [currentFileInfo.currentDirectory];
202
+ if (env.paths) paths.push.apply(paths, env.paths);
203
+ if (paths.indexOf('.') === -1) paths.push('.');
197
204
 
198
205
  if (env.syncImport) {
199
206
  for (var i = 0; i < paths.length; i++) {
@@ -226,8 +233,13 @@ less.Parser.fileLoader = function (file, currentFileInfo, callback, env) {
226
233
  tryPathIndex(i + 1);
227
234
  } else {
228
235
  fs.readFile(pathname, 'utf-8', function(e, data) {
229
- if (e) { callback(e); }
230
- handleDataAndCallCallback(data);
236
+ if (e) { callback(e); return; }
237
+
238
+ // do processing in the next tick to allow
239
+ // file handling to dispose
240
+ process.nextTick(function() {
241
+ handleDataAndCallCallback(data);
242
+ });
231
243
  });
232
244
  }
233
245
  });
@@ -59,6 +59,7 @@ var lessc_helper = {
59
59
  console.log(" --strict-units=on|off that cannot be represented.");
60
60
  console.log(" --global-var='VAR=VALUE' Defines a variable that can be referenced by the file.");
61
61
  console.log(" --modify-var='VAR=VALUE' Modifies a variable already declared in the file.");
62
+ console.log(" --url-args='QUERYSTRING' Adds params into url tokens (e.g. 42, cb=42 or 'a=1&b=2')");
62
63
  console.log("");
63
64
  console.log("-------------------------- Deprecated ----------------");
64
65
  console.log(" -O0, -O1, -O2 Set the parser's optimization level. The lower");