Skip to content

Commit d4290a7

Browse files
committed
v1.0.0
2 parents c1e41f7 + 408f982 commit d4290a7

16 files changed

+399
-35
lines changed

.csscomb.json

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@
1717
"stick-brace": "\n",
1818
"strip-spaces": true,
1919
"unitless-zero": true,
20+
"vendor-prefix-align": true,
2021
"sort-order": [
2122
[
2223
"font",

CHANGELOG.md

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,10 @@
11
# Changelog
22

3+
## 1.0.0 - 2013-11-06
4+
- Option: vendor-prefix-align
5+
- Dependencies updated
6+
- Fixed options order in readme
7+
38
## 0.1.0 - 2013-10-11
49
- CLI: lint mode
510

README.md

Lines changed: 41 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -43,7 +43,6 @@ Example configuration:
4343
"exclude": ["node_modules/**"],
4444
"verbose": true,
4545

46-
"remove-empty-rulesets": true,
4746
"always-semicolon": true,
4847
"block-indent": true,
4948
"colon-space": true,
@@ -52,10 +51,12 @@ Example configuration:
5251
"element-case": "lower",
5352
"eof-newline": true,
5453
"leading-zero": false,
54+
"remove-empty-rulesets": true,
5555
"rule-indent": true,
5656
"stick-brace": true,
5757
"strip-spaces": true,
58-
"unitless-zero": true
58+
"unitless-zero": true,
59+
"vendor-prefix-align": true
5960
}
6061
```
6162
@@ -90,14 +91,6 @@ $ ./bin/csscomb ./test --verbose
9091
$ ./bin/csscomb ./test -v
9192
```
9293
93-
### remove-empty-rulesets
94-
95-
Available values: `{Boolean}` `true`
96-
97-
Example: `{ "remove-empty-rulesets": true }` - remove rulesets that have no declarations or comments.
98-
99-
`a { color: red; } p { /* hey */ } b { }` → `a { color: red; } p { /* hey */ } `
100-
10194
### always-semicolon
10295
10396
Available value: `{Boolean}` `true`
@@ -296,6 +289,14 @@ p { padding: 0.5em }
296289
p { padding: .5em }
297290
```
298291
292+
### remove-empty-rulesets
293+
294+
Available values: `{Boolean}` `true`
295+
296+
Example: `{ "remove-empty-rulesets": true }` - remove rulesets that have no declarations or comments.
297+
298+
`a { color: red; } p { /* hey */ } b { }` → `a { color: red; } p { /* hey */ } `
299+
299300
### rule-indent
300301
301302
**Note**: better to use with [block-indent](#block-indent)
@@ -404,6 +405,36 @@ img { border: 0px }
404405
img { border: 0 }
405406
```
406407
408+
### vendor-prefix-align
409+
410+
Available value: `{Boolean}` `true`
411+
412+
Example: `{ "vendor-prefix-align": true }`
413+
414+
```css
415+
/* before */
416+
a
417+
{
418+
-webkit-border-radius: 3px;
419+
-moz-border-radius: 3px;
420+
border-radius: 3px;
421+
background: -webkit-linear-gradient(top, #fff 0, #eee 100%);
422+
background: -moz-linear-gradient(top, #fff 0, #eee 100%);
423+
background: linear-gradient(to bottom, #fff 0, #eee 100%);
424+
}
425+
426+
/* after */
427+
a
428+
{
429+
-webkit-border-radius: 3px;
430+
-moz-border-radius: 3px;
431+
border-radius: 3px;
432+
background: -webkit-linear-gradient(top, #fff 0, #eee 100%);
433+
background: -moz-linear-gradient(top, #fff 0, #eee 100%);
434+
background: linear-gradient(to bottom, #fff 0, #eee 100%);
435+
}
436+
```
437+
407438
## Tests
408439
409440
Run `npm test` for tests.

lib/csscomb.js

Lines changed: 12 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,8 @@ var Comb = function() {
2626
'rule-indent',
2727
'block-indent',
2828
'unitless-zero',
29-
'sort-order'
29+
'sort-order',
30+
'vendor-prefix-align'
3031
];
3132
this._exclude = null;
3233
};
@@ -70,7 +71,13 @@ Comb.prototype = {
7071
* @returns {Array}
7172
*/
7273
processTree: function(tree) {
73-
this.processNode(['tree', tree], 0);
74+
75+
// We walk across complete tree for each handler,
76+
// because we need strictly maintain order in which handlers work,
77+
// despite fact that handlers work on different level of the tree.
78+
this._handlers.forEach(function(handler) {
79+
this.processNode(['tree', tree], 0, handler);
80+
}, this);
7481
return tree;
7582
},
7683

@@ -79,19 +86,17 @@ Comb.prototype = {
7986
* @param {Array} node Tree node
8087
* @param {Number} level Indent level
8188
*/
82-
processNode: function(node, level) {
89+
processNode: function(node, level, handler) {
8390
node.forEach(function(node) {
8491
if (!Array.isArray(node)) return;
8592

8693
var nodeType = node.shift();
87-
this._handlers.forEach(function(handler) {
88-
handler.process(nodeType, node, level);
89-
});
94+
handler.process(nodeType, node, level);
9095
node.unshift(nodeType);
9196

9297
if (nodeType === 'atrulers') level++;
9398

94-
this.processNode(node, level);
99+
this.processNode(node, level, handler);
95100
}, this);
96101
},
97102

lib/options/vendor-prefix-align.js

Lines changed: 159 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,159 @@
1+
module.exports = {
2+
3+
/**
4+
* Internal
5+
*
6+
* Containt vendor-prefixes list.
7+
*/
8+
_prefixesList: [
9+
'webkit',
10+
'moz',
11+
'ms',
12+
'o'
13+
],
14+
15+
/**
16+
* Internal
17+
*
18+
* Create object which contains info about vendor prefix used in propertyName.
19+
* @param {String} propertyName property name
20+
* @returns {Object|undefined}
21+
*/
22+
_getPrefixInfo: function(propertyName) {
23+
if (!propertyName) return;
24+
25+
var result = { baseName: propertyName, prefixLength: 0 };
26+
27+
this._prefixesList.some(function(prefix) {
28+
prefix = '-' + prefix + '-';
29+
if (propertyName.indexOf(prefix) !== 0) return;
30+
result = {
31+
baseName: propertyName.substr(prefix.length),
32+
prefixLength: prefix.length
33+
};
34+
return true;
35+
});
36+
37+
return result;
38+
},
39+
40+
/**
41+
* Internal
42+
*
43+
* Walk across nodes, and call payload for every node that pass selector check.
44+
* @param {node} node
45+
* @param {function} selector
46+
* @param {function} payload
47+
*/
48+
_walk: function(node, selector, payload) {
49+
node.forEach(function(item, i) {
50+
var info = this._getPrefixInfo(selector(item));
51+
if (!info) return;
52+
payload(info, i);
53+
}, this);
54+
},
55+
56+
/**
57+
* Internal
58+
*
59+
* Selector for property name.
60+
* @param {node} item
61+
* @returns {String|false|undefined}
62+
*/
63+
_declName: function(item) {
64+
return item[0] === 'declaration' && item[1][1][1];
65+
},
66+
67+
/**
68+
* Internal
69+
*
70+
* Selector for value name.
71+
* @param {node} item
72+
* @returns {String|false|undefined}
73+
*/
74+
_valName: function(item) {
75+
return item[0] === 'declaration' && item[2] && item[2][2] &&
76+
item[2][2][0] === 'funktion' && item[2][2][1][0] === 'ident' &&
77+
item[2][2][1][1];
78+
},
79+
80+
/**
81+
* Internal
82+
*
83+
* Update dict which contains info about items align.
84+
* @param {Object} info,
85+
* @param {Object} dict,
86+
* @param {String} whitespaceNode
87+
*/
88+
_updateDict: function(info, dict, whitespaceNode) {
89+
if (info.prefixLength === 0) return;
90+
91+
var indent = dict[info.baseName] || { prefixLength: 0, baseLength: 0 };
92+
93+
dict[info.baseName] = indent.prefixLength > info.prefixLength ?
94+
indent :
95+
{
96+
prefixLength: info.prefixLength,
97+
baseLength: whitespaceNode.substr(whitespaceNode.lastIndexOf('\n') + 1).length
98+
};
99+
},
100+
101+
/**
102+
* Return string with correct number of spaces for info.baseName property.
103+
* @param {Object} info,
104+
* @param {Object} dict,
105+
* @param {String} whitespaceNode
106+
* @returns {String}
107+
*/
108+
_updateIndent: function(info, dict, whitespaceNode) {
109+
if (!dict[info.baseName])
110+
return whitespaceNode;
111+
112+
var firstPart = whitespaceNode.substr(0, whitespaceNode.lastIndexOf('\n') + 1 );
113+
var extraIndent = new Array(
114+
dict[info.baseName].prefixLength -
115+
info.prefixLength +
116+
dict[info.baseName].baseLength + 1).join(' ');
117+
118+
return firstPart.concat(extraIndent);
119+
},
120+
121+
/**
122+
* Sets handler value.
123+
*
124+
* @param {Array} value Option value
125+
* @returns {Object|undefined}
126+
*/
127+
setValue: function(value) {
128+
return value ? this : undefined;
129+
},
130+
131+
/**
132+
* Processes tree node.
133+
* @param {String} nodeType
134+
* @param {node} node
135+
*/
136+
process: function(nodeType, node) {
137+
if (nodeType !== 'block') return;
138+
139+
var dict = {};
140+
var _this = this;
141+
142+
// Gathering Info
143+
this._walk(node, this._declName, function(info, i) {
144+
_this._updateDict(info, dict, node[i - 1][1]);
145+
});
146+
this._walk(node, this._valName, function(info, i) {
147+
_this._updateDict(info, dict, node[i][2][1][1]);
148+
});
149+
150+
// Update nodes
151+
this._walk(node, this._declName, function(info, i) {
152+
node[i - 1][1] = _this._updateIndent(info, dict, node[i - 1][1]);
153+
});
154+
this._walk(node, this._valName, function(info, i) {
155+
node[i][2][1][1] = _this._updateIndent(info, dict, node[i][2][1][1]);
156+
});
157+
}
158+
159+
};

package.json

Lines changed: 9 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
{
22
"name": "csscomb",
33
"description": "CSS coding style formatter",
4-
"version": "0.1.0",
4+
"version": "1.0.0",
55
"homepage": "http://csscomb.com/",
66
"author": "Mikhail Troshev <mishanga@yandex-team.ru>",
77
"repository": "https://github.com/csscomb/csscomb.js",
@@ -39,17 +39,17 @@
3939
"node": ">= 0.8.0"
4040
},
4141
"dependencies": {
42-
"commander": "1.1.1",
43-
"gonzales": "1.0.6",
42+
"commander": "2.0.0",
43+
"gonzales": "1.0.7",
4444
"minimatch": "0.2.12",
45-
"vow": "0.3.7",
46-
"vow-fs": "0.1.13"
45+
"vow": "0.3.11",
46+
"vow-fs": "0.2.3"
4747
},
4848
"devDependencies": {
49-
"jshint-groups": "0.5.1",
50-
"jshint": "2.1.7",
51-
"jscs": "1.0.5",
52-
"mocha": "1.11.0"
49+
"jshint-groups": "0.5.3",
50+
"jshint": "2.3.0",
51+
"jscs": "1.0.11",
52+
"mocha": "1.14.0"
5353
},
5454
"main": "./lib/csscomb.js",
5555
"bin": {

test/integral.expect.css

Lines changed: 9 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -5,28 +5,28 @@
55
{
66
background: rgba(0,0,0,.4);
77
background: -webkit-linear-gradient(top, rgba(0,0,0,.2) 0,rgba(0,0,0,.4) 100%);
8-
background: -moz-linear-gradient(top, rgba(0,0,0,.2) 0, rgba(0,0,0,.4) 100%);
9-
background: -o-linear-gradient(top, rgba(0,0,0,.2) 0,rgba(0,0,0,.4) 100%);
10-
background: linear-gradient(to bottom, rgba(0,0,0,.2) 0,rgba(0,0,0,.4) 100%);
8+
background: -moz-linear-gradient(top, rgba(0,0,0,.2) 0, rgba(0,0,0,.4) 100%);
9+
background: -o-linear-gradient(top, rgba(0,0,0,.2) 0,rgba(0,0,0,.4) 100%);
10+
background: linear-gradient(to bottom, rgba(0,0,0,.2) 0,rgba(0,0,0,.4) 100%);
1111
-moz-box-shadow: 0 1px 0 rgba(0,0,0,.07);
12-
box-shadow: 0 1px 0 rgba(0,0,0,.07);
12+
box-shadow: 0 1px 0 rgba(0,0,0,.07);
1313
}
1414

1515
/* :after — фон */
1616
.radio-button_theme_normal .radio-button__radio:after
1717
{
1818
background: #fff;
1919
background: -webkit-linear-gradient(top, #fff 0,#eee 100%);
20-
background: -moz-linear-gradient(top, #fff 0, #eee 100%);
21-
background: -o-linear-gradient(top, #fff 0,#eee 100%);
22-
background: linear-gradient(to bottom, #fff 0,#eee 100%);
20+
background: -moz-linear-gradient(top, #fff 0, #eee 100%);
21+
background: -o-linear-gradient(top, #fff 0,#eee 100%);
22+
background: linear-gradient(to bottom, #fff 0,#eee 100%);
2323
}
2424

2525
/* _focused_yes */
2626
.radio-button_theme_normal .radio-button__radio_focused_yes:before
2727
{
2828
-moz-box-shadow: 0 0 6px 2px rgba(255,204,0,.7), 0 1px 0 rgba(0,0,0,.07);
29-
box-shadow: 0 0 6px 2px rgba(255,204,0,.7), 0 1px 0 rgba(0,0,0,.07);
29+
box-shadow: 0 0 6px 2px rgba(255,204,0,.7), 0 1px 0 rgba(0,0,0,.07);
3030
}
3131
}
3232

@@ -85,7 +85,7 @@ div p em
8585
.input__control
8686
{
8787
-moz-box-sizing: border-box;
88-
box-sizing: border-box;
88+
box-sizing: border-box;
8989
padding: .4em 0;
9090

9191
border: 0;

0 commit comments

Comments
 (0)