stylus-source 0.15.4

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 (113) hide show
  1. data/.DS_Store +0 -0
  2. data/README.md +3 -0
  3. data/lib/.DS_Store +0 -0
  4. data/lib/node_modules/cssom/.idea/CSSOM.iml +9 -0
  5. data/lib/node_modules/cssom/.idea/dictionaries/nv.xml +3 -0
  6. data/lib/node_modules/cssom/.idea/encodings.xml +5 -0
  7. data/lib/node_modules/cssom/.idea/misc.xml +17 -0
  8. data/lib/node_modules/cssom/.idea/modules.xml +9 -0
  9. data/lib/node_modules/cssom/.idea/projectCodeStyle.xml +82 -0
  10. data/lib/node_modules/cssom/.idea/vcs.xml +8 -0
  11. data/lib/node_modules/cssom/.idea/workspace.xml +467 -0
  12. data/lib/node_modules/cssom/.livereload +19 -0
  13. data/lib/node_modules/cssom/Jakefile +37 -0
  14. data/lib/node_modules/cssom/README.mdown +33 -0
  15. data/lib/node_modules/cssom/Rakefile +23 -0
  16. data/lib/node_modules/cssom/docs/.livereload +19 -0
  17. data/lib/node_modules/cssom/docs/bar.css +3 -0
  18. data/lib/node_modules/cssom/docs/demo.css +0 -0
  19. data/lib/node_modules/cssom/docs/foo.css +4 -0
  20. data/lib/node_modules/cssom/docs/parse.html +170 -0
  21. data/lib/node_modules/cssom/docs/parse2.html +431 -0
  22. data/lib/node_modules/cssom/index.html +100 -0
  23. data/lib/node_modules/cssom/lib/CSSImportRule.js +34 -0
  24. data/lib/node_modules/cssom/lib/CSSMediaRule.js +38 -0
  25. data/lib/node_modules/cssom/lib/CSSOM.js +3 -0
  26. data/lib/node_modules/cssom/lib/CSSRule.js +38 -0
  27. data/lib/node_modules/cssom/lib/CSSStyleDeclaration.js +130 -0
  28. data/lib/node_modules/cssom/lib/CSSStyleRule.js +187 -0
  29. data/lib/node_modules/cssom/lib/CSSStyleSheet.js +85 -0
  30. data/lib/node_modules/cssom/lib/MediaList.js +61 -0
  31. data/lib/node_modules/cssom/lib/StyleSheet.js +15 -0
  32. data/lib/node_modules/cssom/lib/clone.js +69 -0
  33. data/lib/node_modules/cssom/lib/index.js +10 -0
  34. data/lib/node_modules/cssom/lib/parse.js +195 -0
  35. data/lib/node_modules/cssom/media.html +17 -0
  36. data/lib/node_modules/cssom/package.json +30 -0
  37. data/lib/node_modules/cssom/plugins/toHTML.js +32 -0
  38. data/lib/node_modules/cssom/server/index.html +22 -0
  39. data/lib/node_modules/cssom/server/index.js +21 -0
  40. data/lib/node_modules/cssom/shorthands.html +21 -0
  41. data/lib/node_modules/cssom/test/CSSStyleDeclaration.test.js +35 -0
  42. data/lib/node_modules/cssom/test/CSSStyleRule.test.js +12 -0
  43. data/lib/node_modules/cssom/test/CSSStyleSheet.test.js +16 -0
  44. data/lib/node_modules/cssom/test/MediaList.test.js +21 -0
  45. data/lib/node_modules/cssom/test/clone.test.js +38 -0
  46. data/lib/node_modules/cssom/test/fixtures/dummy.css +3 -0
  47. data/lib/node_modules/cssom/test/helper.js +97 -0
  48. data/lib/node_modules/cssom/test/index.html +42 -0
  49. data/lib/node_modules/cssom/test/parse.test.js +346 -0
  50. data/lib/node_modules/cssom/test/vendor/qunit.css +189 -0
  51. data/lib/node_modules/cssom/test/vendor/qunit.js +1341 -0
  52. data/lib/node_modules/growl/History.md +16 -0
  53. data/lib/node_modules/growl/Readme.md +74 -0
  54. data/lib/node_modules/growl/lib/growl.js +82 -0
  55. data/lib/node_modules/growl/package.json +6 -0
  56. data/lib/node_modules/growl/test.js +17 -0
  57. data/lib/stylus/colors.js +156 -0
  58. data/lib/stylus/convert/css.js +130 -0
  59. data/lib/stylus/errors.js +58 -0
  60. data/lib/stylus/functions/image.js +120 -0
  61. data/lib/stylus/functions/index.js +722 -0
  62. data/lib/stylus/functions/index.styl +123 -0
  63. data/lib/stylus/functions/url.js +98 -0
  64. data/lib/stylus/lexer.js +728 -0
  65. data/lib/stylus/middleware.js +223 -0
  66. data/lib/stylus/nodes/arguments.js +65 -0
  67. data/lib/stylus/nodes/binop.js +54 -0
  68. data/lib/stylus/nodes/block.js +99 -0
  69. data/lib/stylus/nodes/boolean.js +103 -0
  70. data/lib/stylus/nodes/call.js +57 -0
  71. data/lib/stylus/nodes/charset.js +42 -0
  72. data/lib/stylus/nodes/comment.js +32 -0
  73. data/lib/stylus/nodes/each.js +56 -0
  74. data/lib/stylus/nodes/expression.js +168 -0
  75. data/lib/stylus/nodes/fontface.js +55 -0
  76. data/lib/stylus/nodes/function.js +104 -0
  77. data/lib/stylus/nodes/group.js +79 -0
  78. data/lib/stylus/nodes/hsla.js +256 -0
  79. data/lib/stylus/nodes/ident.js +127 -0
  80. data/lib/stylus/nodes/if.js +55 -0
  81. data/lib/stylus/nodes/import.js +30 -0
  82. data/lib/stylus/nodes/index.js +52 -0
  83. data/lib/stylus/nodes/jsliteral.js +32 -0
  84. data/lib/stylus/nodes/keyframes.js +78 -0
  85. data/lib/stylus/nodes/literal.js +92 -0
  86. data/lib/stylus/nodes/media.js +42 -0
  87. data/lib/stylus/nodes/node.js +209 -0
  88. data/lib/stylus/nodes/null.js +72 -0
  89. data/lib/stylus/nodes/page.js +43 -0
  90. data/lib/stylus/nodes/params.js +72 -0
  91. data/lib/stylus/nodes/property.js +72 -0
  92. data/lib/stylus/nodes/return.js +44 -0
  93. data/lib/stylus/nodes/rgba.js +335 -0
  94. data/lib/stylus/nodes/root.js +50 -0
  95. data/lib/stylus/nodes/selector.js +57 -0
  96. data/lib/stylus/nodes/string.js +120 -0
  97. data/lib/stylus/nodes/ternary.js +51 -0
  98. data/lib/stylus/nodes/unaryop.js +46 -0
  99. data/lib/stylus/nodes/unit.js +207 -0
  100. data/lib/stylus/parser.js +1514 -0
  101. data/lib/stylus/renderer.js +157 -0
  102. data/lib/stylus/source.rb +7 -0
  103. data/lib/stylus/stack/frame.js +66 -0
  104. data/lib/stylus/stack/index.js +146 -0
  105. data/lib/stylus/stack/scope.js +53 -0
  106. data/lib/stylus/stylus.js +102 -0
  107. data/lib/stylus/token.js +53 -0
  108. data/lib/stylus/utils.js +237 -0
  109. data/lib/stylus/visitor/compiler.js +472 -0
  110. data/lib/stylus/visitor/evaluator.js +1070 -0
  111. data/lib/stylus/visitor/index.js +31 -0
  112. data/stylus-source.gemspec +15 -0
  113. metadata +158 -0
@@ -0,0 +1,19 @@
1
+ # Lines starting with pound sign (#) are ignored.
2
+
3
+ # additional extensions to monitor
4
+ #config.exts << 'haml'
5
+
6
+ # exclude files with NAMES matching this mask
7
+ #config.exclusions << '~*'
8
+ # exclude files with PATHS matching this mask (if the mask contains a slash)
9
+ #config.exclusions << '/excluded_dir/*'
10
+ # exclude files with PATHS matching this REGEXP
11
+ #config.exclusions << /somedir.*(ab){2,4}.(css|js)$/
12
+
13
+ # reload the whole page when .js changes
14
+ #config.apply_js_live = false
15
+ # reload the whole page when .css changes
16
+ #config.apply_css_live = false
17
+
18
+ # wait 100ms for more changes before reloading a page
19
+ #config.grace_period = 0.1
@@ -0,0 +1,37 @@
1
+ var PATH = require("path");
2
+ var FS = require("fs");
3
+
4
+ function readFile(path) {
5
+ var abs_path = PATH.join(__dirname, "lib", path);
6
+ return FS.readFileSync(abs_path, "utf8");
7
+ }
8
+
9
+ function stripCommonJS(text) {
10
+ return text.replace(/\/\/\.CommonJS(?:.|\n)*?\/\/\/CommonJS/g, "");
11
+ }
12
+
13
+ desc("Packages lib files into the one huge");
14
+ task("default", [], function(){
15
+ var files = [readFile("CSSOM.js")];
16
+ var index_file = readFile("index.js");
17
+
18
+ (function(){
19
+ var exports = {};
20
+ function require(path) {
21
+ var text = readFile(path + ".js");
22
+ files.push(stripCommonJS(text).trimLeft());
23
+ return {};
24
+ }
25
+ eval(index_file);
26
+ })();
27
+
28
+ var build_dir = PATH.join(__dirname, "build");
29
+ try {
30
+ FS.statSync(build_dir);
31
+ } catch(e) {
32
+ FS.mkdirSync(build_dir, 0755);
33
+ }
34
+ var build_path = PATH.join(build_dir, "CSSOM.js");
35
+ FS.writeFileSync(build_path, files.join(""));
36
+ process.stdout.write("build/CSSOM.js is done\n");
37
+ });
@@ -0,0 +1,33 @@
1
+ # CSSOM
2
+
3
+ CSSOM.js is a CSS parser written in pure JavaScript. It also a partial implementation of [CSS Object Model](http://dev.w3.org/csswg/cssom/).
4
+
5
+ CSSOM.parse("body {color: black}")
6
+ -> {
7
+ cssRules: [
8
+ {
9
+ selectorText: "body",
10
+ style: {
11
+ 0: "color",
12
+ color: "black",
13
+ length: 1
14
+ }
15
+ }
16
+ ]
17
+ }
18
+
19
+
20
+ ## [Parser demo](http://nv.github.com/CSSOM/docs/parse.html)
21
+
22
+
23
+ ## [Tests](http://nv.github.com/CSSOM/test/)
24
+
25
+ Works well in Google Chrome 6+, Safari 5+, Firefox 3.6+, Opera 10.63+.
26
+ Doesn't work in IE < 9 because of unsupported getters/setters.
27
+
28
+ ## Build
29
+
30
+ Build one-file version of CSSOM.js with [Jake](http://github.com/mde/node-jake):
31
+
32
+ ➤ jake
33
+ build/CSSOM.js is done
@@ -0,0 +1,23 @@
1
+ def version
2
+ git_describe_tags = `git describe --tags`
3
+ tag = git_describe_tags.split('-').first || git_describe_tags
4
+ tag.strip!
5
+ commit = `git rev-list --full-history #{tag}.. -- src/ | wc -l`.strip
6
+ tag.slice! 0
7
+ "#{tag}.#{commit}"
8
+ end
9
+
10
+ task :upload do
11
+ require 'net/github-upload'
12
+ gh = Net::GitHub::Upload.new(
13
+ :login => `git config github.user`.chomp,
14
+ :token => `git config github.token`.chomp
15
+ )
16
+ puts gh.upload(
17
+ :repos => 'CSSOM',
18
+ :file => 'build/CSSOM.js',
19
+ :name => "CSSOM.v#{version}.js",
20
+ :content_type => 'text/javascript',
21
+ :description => "CSS Object Model implemented in pure JavaScript"
22
+ )
23
+ end
@@ -0,0 +1,19 @@
1
+ # Lines starting with pound sign (#) are ignored.
2
+
3
+ # additional extensions to monitor
4
+ #config.exts << 'haml'
5
+
6
+ # exclude files with NAMES matching this mask
7
+ #config.exclusions << '~*'
8
+ # exclude files with PATHS matching this mask (if the mask contains a slash)
9
+ #config.exclusions << '/excluded_dir/*'
10
+ # exclude files with PATHS matching this REGEXP
11
+ #config.exclusions << /somedir.*(ab){2,4}.(css|js)$/
12
+
13
+ # reload the whole page when .js changes
14
+ #config.apply_js_live = false
15
+ # reload the whole page when .css changes
16
+ #config.apply_css_live = false
17
+
18
+ # wait 100ms for more changes before reloading a page
19
+ #config.grace_period = 0.1
@@ -0,0 +1,3 @@
1
+ body * {
2
+ color: red !important;
3
+ }
File without changes
@@ -0,0 +1,4 @@
1
+ @import "bar.css" screen;
2
+ body {
3
+ background: black !important;
4
+ }
@@ -0,0 +1,170 @@
1
+ <!DOCTYPE html>
2
+ <html>
3
+ <head>
4
+ <meta charset="utf-8">
5
+ <title>CSSOM.js parse method</title>
6
+ <script>
7
+ var exports = {};
8
+ function require(){
9
+ return exports;
10
+ }
11
+ </script>
12
+ <script src="../lib/CSSStyleDeclaration.js"></script>
13
+ <script src="../lib/CSSRule.js"></script>
14
+ <script src="../lib/CSSStyleRule.js"></script>
15
+ <script src="../lib/CSSImportRule.js"></script>
16
+ <script src="../lib/MediaList.js"></script>
17
+ <script src="../lib/CSSMediaRule.js"></script>
18
+ <script src="../lib/StyleSheet.js"></script>
19
+ <script src="../lib/CSSStyleSheet.js"></script>
20
+ <script src="../lib/parse.js"></script>
21
+ <script>
22
+ window.CSSOM = exports;
23
+ </script>
24
+ <style type="text/css">
25
+ html, body {
26
+ background: #333;
27
+ color: #EEE;
28
+ font: 12px sans-serif;
29
+ margin: 0;
30
+ height: 100%;
31
+ }
32
+ body {
33
+ padding-bottom: 1.7em;
34
+ -webkit-box-sizing: border-box;
35
+ -moz-box-sizing: border-box;
36
+ box-sizing: border-box;
37
+ }
38
+ table {
39
+ width: 100%;
40
+ table-layout: fixed;
41
+ margin: 0 auto;
42
+ }
43
+ td {
44
+ vertical-align: top;
45
+ }
46
+ h1 {
47
+ font: normal 1em sans-serif;
48
+ display: inline;
49
+ }
50
+ #labels {
51
+ color: #FFE992;
52
+ width: 66%;
53
+ }
54
+ #labels td {
55
+ width: 50%;
56
+ text-align: center;
57
+ }
58
+ #labels td::before {
59
+ content: '↱ ';
60
+ color: #998e62;
61
+ position: relative;
62
+ top: .4em;
63
+ }
64
+ #labels td::after {
65
+ content: ' ↴';
66
+ color: #998e62;
67
+ position: relative;
68
+ top: .4em;
69
+ }
70
+ #content {
71
+ width: 100%;
72
+ height: 100%;
73
+ }
74
+ #content td {
75
+ width: 33%;
76
+ }
77
+ #content td + td {
78
+ padding-left: 1%;
79
+ }
80
+ .style-cell textarea {
81
+ width: 99%;
82
+ height: 100%;
83
+ font: 12px monospace;
84
+ white-space: pre-wrap;
85
+ }
86
+ .serialized-cell {
87
+ border-left: 1px solid #363636;
88
+ }
89
+ #message {
90
+ visibility: hidden;
91
+ }
92
+ .error #message {
93
+ visibility: visible;
94
+ position: absolute;
95
+ top: 0;
96
+ left: 34%;
97
+ padding: 1em;
98
+ background: black;
99
+ color: #e34343;
100
+ font-size: 24px;
101
+ }
102
+ </style>
103
+ </head>
104
+ <body>
105
+ <table id="labels">
106
+ <tr><td><h1>CSSOM.parse</h1></td><td>.toString</td></tr>
107
+ </table>
108
+ <table id="content">
109
+ <tr>
110
+ <td class="style-cell">
111
+ <textarea id="style" spellcheck="false" rows="40">img {
112
+ border: none
113
+ }</textarea></td>
114
+ <td class="output-cell"><pre id="output"></pre></td>
115
+ <td class="serialized-cell"><pre id="serialized"></pre></td>
116
+ </tr>
117
+ </table>
118
+ <div id="message"></div>
119
+ <script defer>
120
+ var errors = [];
121
+ if (!("__defineGetter__" in {})) {
122
+ errors.push("Object.prototype.__defineGetter__ isn’t supported");
123
+ }
124
+ if (errors.length) {
125
+ document.getElementById("message").innerHTML = errors.join("<br>");
126
+ document.body.className = "error";
127
+ throw errors.join("\n\n");
128
+ }
129
+
130
+ var style = document.getElementById("style");
131
+ var output = document.getElementById("output");
132
+ var serialized = document.getElementById("serialized");
133
+
134
+ function outputUpdated(){
135
+ var value = style.value;
136
+ if (value != style.prevValue) {
137
+ var css = CSSOM.parse(value);
138
+ output.innerHTML = JSON.stringify(css, null, 2);
139
+ serialized.innerHTML = css.toString();
140
+ style.prevValue = value;
141
+ }
142
+ }
143
+
144
+ function hashChanged(){
145
+ var hash = location.hash;
146
+ var splitted = hash.split("=");
147
+ if (splitted.length < 2) {
148
+ return;
149
+ }
150
+ var name = splitted[0];
151
+ var value = splitted[1];
152
+ if (name == "#css") {
153
+ style.value = decodeURIComponent(value);
154
+ outputUpdated();
155
+ }
156
+ }
157
+
158
+ hashChanged();
159
+ outputUpdated();
160
+
161
+ window.onhashchange = hashChanged;
162
+ style.onkeyup = style.onpaste = function changed(){
163
+ outputUpdated();
164
+ };
165
+ style.onchange = function updateLocation(){
166
+ location.hash = "css=" + encodeURIComponent(style.value);
167
+ };
168
+ </script>
169
+ </body>
170
+ </html>
@@ -0,0 +1,431 @@
1
+ <!DOCTYPE html>
2
+ <html>
3
+ <head>
4
+ <meta charset="utf-8">
5
+ <title>CSSOM.js parse method</title>
6
+ <script>
7
+ var exports = {};
8
+ function require(){
9
+ return exports;
10
+ }
11
+ </script>
12
+ <script src="../lib/CSSStyleDeclaration.js"></script>
13
+ <script src="../lib/CSSRule.js"></script>
14
+ <script src="../lib/CSSStyleRule.js"></script>
15
+ <script src="../lib/CSSImportRule.js"></script>
16
+ <script src="../lib/MediaList.js"></script>
17
+ <script src="../lib/CSSMediaRule.js"></script>
18
+ <script src="../lib/StyleSheet.js"></script>
19
+ <script src="../lib/CSSStyleSheet.js"></script>
20
+ <script src="../lib/parse.js"></script>
21
+ <script>
22
+ window.CSSOM = exports;
23
+ </script>
24
+ <style>
25
+ html {
26
+ padding: 0;
27
+ }
28
+ </style>
29
+ <style type="text/css">
30
+ html, body {
31
+ background: #333;
32
+ color: #EEE;
33
+ font: 12px sans-serif;
34
+ margin: 0;
35
+ height: 100%;
36
+ }
37
+ body {
38
+ padding-bottom: 1.7em;
39
+ -webkit-box-sizing: border-box;
40
+ -moz-box-sizing: border-box;
41
+ box-sizing: border-box;
42
+ }
43
+ table {
44
+ width: 100%;
45
+ table-layout: fixed;
46
+ margin: 0 auto;
47
+ }
48
+ td {
49
+ vertical-align: top;
50
+ }
51
+ h1 {
52
+ font: normal 1em sans-serif;
53
+ display: inline;
54
+ }
55
+ #labels {
56
+ color: #FFE992;
57
+ width: 66%;
58
+ }
59
+ #labels td {
60
+ width: 50%;
61
+ text-align: center;
62
+ }
63
+ #labels td::before {
64
+ content: '↱ ';
65
+ color: #998e62;
66
+ position: relative;
67
+ top: .4em;
68
+ }
69
+ #labels td::after {
70
+ content: ' ↴';
71
+ color: #998e62;
72
+ position: relative;
73
+ top: .4em;
74
+ }
75
+ #content {
76
+ width: 100%;
77
+ height: 100%;
78
+ }
79
+ #content td {
80
+ width: 33%;
81
+ }
82
+ #content td + td {
83
+ padding-left: 1%;
84
+ }
85
+ .style-cell textarea {
86
+ width: 99%;
87
+ height: 100%;
88
+ font: 12px monospace;
89
+ white-space: pre-wrap;
90
+ }
91
+ .serialized-cell {
92
+ border-left: 1px solid #363636;
93
+ }
94
+ #message {
95
+ visibility: hidden;
96
+ }
97
+ .error #message {
98
+ visibility: visible;
99
+ position: absolute;
100
+ top: 0;
101
+ left: 34%;
102
+ padding: 1em;
103
+ background: black;
104
+ color: #e34343;
105
+ font-size: 24px;
106
+ }
107
+ </style>
108
+ </head>
109
+ <body>
110
+ <table id="labels">
111
+ <tr><td><h1>CSSOM.parse</h1></td><td>.toString</td></tr>
112
+ </table>
113
+ <table id="content">
114
+ <tr>
115
+ <td class="style-cell">
116
+ <textarea id="style" spellcheck="false" rows="40">img {
117
+ border: none
118
+ }</textarea></td>
119
+ <td class="output-cell"><pre id="output"></pre></td>
120
+ <td class="serialized-cell"><pre id="serialized"></pre></td>
121
+ </tr>
122
+ </table>
123
+ <div id="message"></div>
124
+ <script defer>
125
+ console.dir(document.styleSheets[0].cssRules[0].style);
126
+ //console.log(document.styleSheets[0].cssRules[0].style["table-layout"]);
127
+ var CSS = {
128
+ background: [
129
+ "background-image",
130
+ "background-repeat",
131
+ "background-attachment",
132
+ "background-position",
133
+ "background-origin",
134
+ "background-clip",
135
+ "background-color"
136
+ ],
137
+ "background-repeat": [
138
+ "background-repeat-x",
139
+ "background-repeat-y"
140
+ ],
141
+ "background-position": [
142
+ "background-position-x",
143
+ "background-position-y"
144
+ ],
145
+ border: [
146
+ "border-top",
147
+ "border-right",
148
+ "border-bottom",
149
+ "border-left",
150
+ "border-width",
151
+ "border-style",
152
+ "border-color"
153
+ ],
154
+ "border-top": [
155
+ "border-top-width",
156
+ "border-top-style",
157
+ "border-top-color"
158
+ ],
159
+ "border-right": [
160
+ "border-right-width",
161
+ "border-right-style",
162
+ "border-right-color"
163
+ ],
164
+ "border-bottom": [
165
+ "border-bottom-width",
166
+ "border-bottom-style",
167
+ "border-bottom-color"
168
+ ],
169
+ "border-left": [
170
+ "border-left-width",
171
+ "border-left-style",
172
+ "border-left-color"
173
+ ],
174
+ font: [
175
+ "font-style",
176
+ "font-variant",
177
+ "font-weight",
178
+ "font-size",
179
+ "font-size-adjust",
180
+ "font-stretch",
181
+ "line-height",
182
+ "font-family"
183
+ ],
184
+ "list-style": [
185
+ "list-style-type",
186
+ "list-style-position",
187
+ "list-style-image"
188
+ ],
189
+ margin: [
190
+ "margin-top",
191
+ "margin-right",
192
+ "margin-bottom",
193
+ "margin-left"
194
+ ],
195
+ padding: [
196
+ "padding-top",
197
+ "padding-right",
198
+ "padding-bottom",
199
+ "padding-left"
200
+ ]
201
+ };
202
+
203
+ function camelize(string) {
204
+ return string.replace(/-+(.)?/g, function(match, chr) {
205
+ return chr ? chr.toUpperCase() : '';
206
+ });
207
+ }
208
+
209
+ CSS["background-repeat"].shorthand = function(style) {
210
+ if (style["background-repeat-x"] == style["background-repeat-y"]) {
211
+ return style["background-repeat-x"];
212
+ } else {
213
+ return style["background-repeat-x"] + " " + style["background-repeat-y"];
214
+ }
215
+ };
216
+
217
+ CSS["background-position"].shorthand = function(style) {
218
+ if (style["background-position-x"] == style["background-position-y"]) {
219
+ return style["background-position-x"];
220
+ } else {
221
+ return style["background-position-x"] + " " + style["background-position-y"];
222
+ }
223
+ };
224
+
225
+ CSS.background.shorthand = function(style) {
226
+ var values = [];
227
+
228
+ //FIXME
229
+ // Support CSS3 background shorthand
230
+ // http://www.w3.org/TR/css3-background/#the-background
231
+
232
+ var backgroundColor = style["background-color"];
233
+ if (backgroundColor != "initial" && backgroundColor != "transparent") {
234
+ values.push(backgroundColor);
235
+ }
236
+
237
+ var backgroundImage = style["background-image"];
238
+ if (backgroundImage != "initial" && backgroundImage != "none") {
239
+ values.push(backgroundImage);
240
+ }
241
+
242
+ var backgroundRepeat = style["background-repeat"];
243
+ if (backgroundRepeat != "initial" && backgroundRepeat != "repeat") {
244
+ values.push(backgroundRepeat);
245
+ }
246
+
247
+ var backgroundAttachment = style["background-attachment"];
248
+ if (backgroundAttachment != "initial" && backgroundAttachment != "scroll") {
249
+ values.push(backgroundAttachment);
250
+ }
251
+
252
+ var backgroundPosition = style["background-position"];
253
+ if (backgroundPosition != "initial" && parseInt(backgroundPosition) !== 0) {
254
+ values.push(backgroundPosition);
255
+ }
256
+
257
+ return values.join(" ") || "";
258
+ };
259
+
260
+
261
+ (function(){
262
+ for (var key in CSS) {
263
+ var longhand = CSS[key];
264
+ if (!longhand.length) {
265
+ continue;
266
+ }
267
+ for (var i=0, ii=longhand.length; i<ii; i++) {
268
+ var siblings = longhand.slice(0);
269
+ siblings.splice(i, 1);
270
+ if (CSS[longhand[i]]) {
271
+ //console.log("array", CSS[longhand[i]]);
272
+ } else {
273
+ CSS[longhand[i]] = {}
274
+ }
275
+ CSS[longhand[i]].parent = key;
276
+ CSS[longhand[i]].siblings = siblings;
277
+ }
278
+ }
279
+ })();
280
+
281
+
282
+ function cloneMinimized(stylesheet) {
283
+ var cloned = new CSSOM.CSSStyleSheet;
284
+
285
+ var rules = stylesheet.cssRules;
286
+ if (!rules) {
287
+ return cloned;
288
+ }
289
+
290
+ var RULE_TYPES = {
291
+ 1: CSSOM.CSSStyleRule,
292
+ 4: CSSOM.CSSMediaRule
293
+ //FIXME
294
+ //3: CSSOM.CSSImportRule,
295
+ //5: CSSOM.CSSFontFaceRule,
296
+ //6: CSSOM.CSSPageRule,
297
+ };
298
+
299
+ for (var i=0, rulesLength=rules.length; i < rulesLength; i++) {
300
+ var rule = rules[i];
301
+ var ruleClone = cloned.cssRules[i] = new RULE_TYPES[rule.type];
302
+
303
+ var style = rule.style;
304
+ if (style) {
305
+ var styleClone = ruleClone.style = minimizeStyle(style);
306
+ }
307
+
308
+ if ("selectorText" in rule) {
309
+ ruleClone.selectorText = rule.selectorText;
310
+ }
311
+
312
+ if ("mediaText" in rule) {
313
+ ruleClone.mediaText = rule.mediaText;
314
+ }
315
+
316
+ if ("cssRules" in rule) {
317
+ rule.cssRules = clone(rule).cssRules;
318
+ }
319
+ }
320
+
321
+ return cloned;
322
+
323
+ };
324
+
325
+ function minimizeStyle(style) {
326
+ var result = new CSSOM.CSSStyleDeclaration;
327
+ for (var i=0; i<style.length; i++) {
328
+ var name = closestShorthand(style, style[i]);
329
+ if (!(name in result)) {
330
+ result[name] = style[camelize(name)];
331
+ result[result.length++] = name;
332
+ }
333
+ }
334
+ return result;
335
+ }
336
+
337
+ function closestShorthand(style, name) {
338
+ if (!(name in CSS)) {
339
+ return name;
340
+ }
341
+ var siblings = CSS[name].siblings;
342
+ if (!siblings || !siblings.length) {
343
+ return name;
344
+ }
345
+ var properties = {};
346
+ var allPresent = true;
347
+ for (var j=0; j<siblings.length; j++) {
348
+ var sibling = siblings[j];
349
+ var aSibling = camelize(sibling);
350
+ if (style[aSibling] === "") {
351
+ console.warn(sibling);
352
+ if (CSS[sibling].length) {
353
+ for (var i=0; i<CSS[sibling].length; i++) {
354
+ if (style[camelize(CSS[sibling][i])] === "") {
355
+ allPresent = false;
356
+ break;
357
+ }
358
+ }
359
+ } else {
360
+ allPresent = false;
361
+ break;
362
+ }
363
+ }
364
+ }
365
+ if (allPresent) {
366
+ return closestShorthand(style, CSS[name].parent);
367
+ } else {
368
+ return name;
369
+ }
370
+
371
+ }
372
+
373
+ console.log(cloneMinimized(document.styleSheets[0]).toString());
374
+ //console.log(CSSOM.CSSStyleSheet.prototype.toString.call(minimize(document.styleSheets[0].cssRules[0].style)));
375
+ //console.log(document.styleSheets[0].cssRules[0].style["background-image"]);
376
+
377
+ //console.log(CSS);
378
+
379
+
380
+
381
+ var errors = [];
382
+ //if (!Object.defineProperty) {
383
+ // errors.push("Object.defineProperty isn’t supported");
384
+ //}
385
+ if (errors.length) {
386
+ document.getElementById("message").innerHTML = errors.join("<br>");
387
+ document.body.className = "error";
388
+ throw errors.join("\n\n");
389
+ }
390
+
391
+ var style = document.getElementById("style");
392
+ var output = document.getElementById("output");
393
+ var serialized = document.getElementById("serialized");
394
+
395
+ function outputUpdated(){
396
+ var value = style.value;
397
+ if (value != style.prevValue) {
398
+ var css = CSSOM.parse(value);
399
+ output.innerHTML = JSON.stringify(css, null, 2);
400
+ serialized.innerHTML = css.toString();
401
+ style.prevValue = value;
402
+ }
403
+ }
404
+
405
+ function hashChanged(){
406
+ var hash = location.hash;
407
+ var splitted = hash.split("=");
408
+ if (splitted.length < 2) {
409
+ return;
410
+ }
411
+ var name = splitted[0];
412
+ var value = splitted[1];
413
+ if (name == "#css") {
414
+ style.value = decodeURIComponent(value);
415
+ outputUpdated();
416
+ }
417
+ }
418
+
419
+ hashChanged();
420
+ outputUpdated();
421
+
422
+ window.onhashchange = hashChanged;
423
+ style.onkeyup = style.onpaste = function changed(){
424
+ outputUpdated();
425
+ };
426
+ style.onchange = function updateLocation(){
427
+ location.hash = "css=" + encodeURIComponent(style.value);
428
+ };
429
+ </script>
430
+ </body>
431
+ </html>