sass-list-maps 0.9.9 → 1.0.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +30 -16
- data/_sass-list-maps.scss +434 -87
- metadata +8 -7
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 4cdb2fd397cd4a3805836350c1e574d9956b3c8c
|
4
|
+
data.tar.gz: 544594422b60254ab7f37371d94cad608d9f74f8
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: d20eb2fa1bec7f96d1e9f618754f6ec4ae21595826f6556109bbc87dd2cae4cf9c213e7688d93c697af0753e1e3a3abc2aab5ff97f5f47d471e6102deaef731a
|
7
|
+
data.tar.gz: 3252ce935c5396903ff6324e02e37b92a00964bf6537e66a0cf149ddede15410112760a00c7101f5a6259b4ad49ef1bc10d026a43e919e6fbd025ea686b61e4d
|
data/README.md
CHANGED
@@ -1,11 +1,16 @@
|
|
1
1
|
## Sass List–Maps
|
2
2
|
|
3
|
-
These functions provide forward-compatible map (hash) data-type functionality
|
3
|
+
These functions provide a forward-compatible polyfill for SassScript `map` (hash) data-type functionality in [libsass](http://libsass.org/) and [ruby-sass](http://sass-lang.com/) 3.2.x using the `list` data-type. They feature-match all the current native (ruby-sass) `map` functions, and add nested (or 'chained') `get()`, `set()` and `merge()` functions and inspection / debugging functions as well.
|
4
4
|
|
5
|
-
|
5
|
+
#### NB: these functions may soon be obsolete, as [SassScript Maps may soon land in libsass](https://github.com/sass/libsass/pull/481). At that point I will put up a new library that offers the same advanced functions for the native implementation as for this polyfill.
|
6
|
+
|
7
|
+
![](sass-hash.jpg)
|
6
8
|
|
7
9
|
#### Updates
|
8
10
|
|
11
|
+
* 1.0.0-b3 -- altered use of `list-map-check()` in `map-get()` and `map-get-z()` functions, to avoid double-wrapped-output edge case
|
12
|
+
* 1.0.0-b2 -- updated `map-remove()` function to allow removing multiple keys; conformant to ruby-sass 3.4.
|
13
|
+
* 1.0.0-b -- preparing for 1.0; added npm distribution and newly commented source code thanks to Hugo Giraudel. Next version will use SassDoc-style comments.
|
9
14
|
* 0.9.9 -- added `map-pretty()` function to inspect/debug list-maps in pretty-printed form
|
10
15
|
* 0.9.6-0.9.8 -- argument-handling enhancements; typo fixes
|
11
16
|
* 0.9.3-0.9.5 -- handling single-pair lists automatically. This means no more need for `list()` or `zip()` functions, which are now deprecated.
|
@@ -14,17 +19,21 @@ These functions provide forward-compatible map (hash) data-type functionality fo
|
|
14
19
|
|
15
20
|
#### Try it
|
16
21
|
|
17
|
-
You can test-drive these functions at [Sassmeister, in this pre-loaded gist](http://sassmeister.com/gist/
|
22
|
+
You can test-drive these functions at [Sassmeister, in this pre-loaded gist](http://sassmeister.com/gist/4787415116ed1adbc8d9)—but note that the libsass version at Sassmeister might be a couple of point-releases behind this repo.
|
18
23
|
|
19
24
|
#### Install it
|
20
25
|
|
21
|
-
'Sass List-Maps' can be installed as a Bower component for non-ruby setups (see [node-sass options](http://github.com/sindresorhus/grunt-sass#includepaths) if you are using libsass via node) or as a gem-based Compass extension for ruby setups:
|
26
|
+
'Sass List-Maps' can be installed as a Bower component or NPM module for non-ruby setups (see [node-sass options](http://github.com/sindresorhus/grunt-sass#includepaths) if you are using libsass via node) or as a gem-based Compass extension for ruby setups:
|
22
27
|
|
23
28
|
```sh
|
29
|
+
# installation with npm
|
30
|
+
npm install sass-list-maps
|
31
|
+
|
24
32
|
# installation with bower
|
25
33
|
bower install sass-list-maps
|
26
34
|
|
27
|
-
# if using grunt-sass, you
|
35
|
+
# if using grunt-sass, you might want to set 'includePaths'
|
36
|
+
# to match install location of bower or npm.
|
28
37
|
options: {
|
29
38
|
includePaths: [
|
30
39
|
'./bower_components/sass-list-maps'
|
@@ -42,15 +51,17 @@ You can of course also just fork or download this repo or copy-and-paste, as the
|
|
42
51
|
|
43
52
|
### Introduction
|
44
53
|
|
45
|
-
Maps (known in programming as hashes, dictionaries, or objects<sup>1</sup>) allow dynamic creating, setting, merging and retrieving of data. They are native to ruby-sass as of version 3.3.x, but for earlier ruby-sass versions, and for the libsass C-based compiler (until the point at which maps are integrated there natively), this is an alternative solution which feature-matches ruby-sass' 3.3.x map functionality using the `list` data-type.
|
54
|
+
Maps (known in programming as hashes, dictionaries, or objects<sup>1</sup>) allow dynamic creating, setting, merging and retrieving of data. They are native to ruby-sass as of version 3.3.x, but for earlier ruby-sass versions, and for the libsass C-based compiler (until the point at which maps are integrated there natively), this is an alternative solution which feature-matches ruby-sass' 3.3.x map functionality using the `list` data-type.
|
55
|
+
|
56
|
+
Some additional functions are also provided to allow nested (chained) getting and merging/setting, and inspection for debugging.
|
46
57
|
|
47
58
|
*<sup>1</sup>objects (as in javascript) are not exactly the same thing as maps and hashes, but for these purposes close enough.*
|
48
59
|
|
49
60
|
#### Syntax
|
50
61
|
|
51
|
-
Compared to ruby-sass' native maps, 'list-maps' are lists like any other list in Sass, but they are *lists of pairs*, formatted in such a way as to be interpreted like a map. To this purpose, the first item in each pair is interpreted as the 'key'
|
62
|
+
Compared to ruby-sass' native maps, 'list-maps' are lists like any other list in Sass, but they are *lists of pairs*, formatted in such a way as to be interpreted like a map. To this purpose, the first item in each pair is interpreted as the 'key', while the second is interpreted as the correspondent 'value'. This 'value' can be any Sass-script data-type, including a list—which means list-maps can contain other list-maps, allowing them to form nested data structures. The formatting used here keeps as close as possible to the syntax of native maps, with the difference that there no colons (`:`) used.
|
52
63
|
|
53
|
-
|
64
|
+
*NB: in ruby-sass 3.2.x or lower, the placement of commas is also very critical (no comma after the last item); but in libsass as of 2.0 you can put commas after each item if you wish.*
|
54
65
|
|
55
66
|
```scss
|
56
67
|
/* a single-line list-map -- compatible with any
|
@@ -81,11 +92,11 @@ s$native-map-z: (
|
|
81
92
|
);
|
82
93
|
```
|
83
94
|
|
84
|
-
It should be clear that
|
95
|
+
It should be clear that 'list-maps' and ruby-sass 'native' maps are very similar—in fact, they are in principle the same. For this reason it was possible to reverse engineer the map functions of ruby-sass' 3.3+ to use the SassScript `list` data-type. Moreover, as with native maps in ruby-sass, list functions (e.g. `nth()`, `index()`) can be used on list-maps, since they are still lists.
|
85
96
|
|
86
97
|
### The Functions
|
87
98
|
|
88
|
-
These functions have the same names as the map functions in ruby-sass >= 3.3.x, which means that if they were used in ruby-sass 3.3.x or higher they would conflict. Therefore, the following code assume
|
99
|
+
These functions have the same names as the built-in map functions in ruby-sass >= 3.3.x, which means that if they were used in ruby-sass 3.3.x or higher they would conflict with (or at least overwrite) the built-in ones. Therefore, the following code assume you are using either ruby-sass 3.2.x or earlier, or libsass (currently 2.1b).
|
89
100
|
|
90
101
|
#### Core (matching the ruby-sass 3.3.x native map functions)
|
91
102
|
|
@@ -132,7 +143,7 @@ $short-map: map-remove($list-map, alpha);
|
|
132
143
|
// -> $short-map = ( beta 2, gamma 3)
|
133
144
|
```
|
134
145
|
|
135
|
-
**NB**: you might notice in the second example above, that the second argument to map-merge isn't really a 'list-map' it's just a list of two items. This is the so-called "single item" list conundrum in Sass
|
146
|
+
**NB**: you might notice in the second example above, that the second argument to map-merge isn't really a 'list-map' it's just a list of two items. This is the so-called "single item" list conundrum in Sass. As of v0.9.5 these functions handle this type of input so the API can mimic the native syntax as closely as possible.
|
136
147
|
|
137
148
|
#### Advanced (beyond the ruby-sass 3.3.x native map functions)
|
138
149
|
|
@@ -262,17 +273,20 @@ Since the 'advanced' nested/chained `map-get-z()` and `map-merge-z()` take a var
|
|
262
273
|
|
263
274
|
There are a few points that bear mentioning/repeating:
|
264
275
|
|
265
|
-
* operating on global variables in libsass and in ruby-sass 3.2.x or earlier
|
266
|
-
*
|
267
|
-
*
|
276
|
+
* operating on global variables in libsass and in ruby-sass 3.2.x or earlier works differently than in 3.3.x and later: You can make changes to global variables from inside a mixin scope but you can't create them from there. There is no `!global` flag. This has implications for how you declare and change global variables.
|
277
|
+
* there is no error-checking for the data-type itself (e.g. native maps will produce a warning if you have duplicate keys).
|
278
|
+
* special features of native maps in ruby-sass, such as passing a map to a function in the form `my-function($map...)` whereupon you can reference the key/value pairs inside the function as if they were named variables, doesn't work here.
|
279
|
+
* as noted, the 'list-map' syntax is in ruby-sass 3.2.x or earlier is still less forgiving than that of native maps (watch your commas), but it's a bit more easygoing in libsass, which is the more likely use-case.
|
280
|
+
* as of this writing, this code contains no test-suites or inline error-catches or warnings of any kind. I've been using it in my own work and incrementally optimizing it, but I welcome reports and contributions!
|
268
281
|
|
269
282
|
### To-Dos
|
270
283
|
|
271
|
-
*
|
284
|
+
* Push a SassDoc documented version (this will be 1.0.0 final)
|
285
|
+
* Implement an error/warning system (probably 1.1.0)
|
272
286
|
* Push a native maps version of the 'advanced' functions above
|
273
287
|
|
274
288
|
### Acknowledgements
|
275
289
|
|
276
290
|
First and foremost, gratitude to the core Sass devs (@nex3 and @chriseppstein) for their tireless advancement of the gold-standard of CSS pre-processing, and secondly to @jedfoster and @anotheruiguy for [Sassmeister](http://sassmeister.com/), which makes developing complex functions and mixins relatively painless.
|
277
291
|
|
278
|
-
Also acknowledgements to @HugoGiraudel for [SassyLists](http://sassylists.com/), from which I adapted some early functions, and especially for his list `debug()` function, without which I would not have been able to figure out what was going on (and going wrong) in ruby-sass 3.2.x and libsass.
|
292
|
+
Also acknowledgements to @HugoGiraudel for [SassyLists](http://sassylists.com/), from which I adapted some early functions, and especially for his list `debug()` function, without which I would not have been able to figure out what was going on (and going wrong) in ruby-sass 3.2.x and libsass.
|
data/_sass-list-maps.scss
CHANGED
@@ -1,175 +1,522 @@
|
|
1
|
-
//
|
2
|
-
//
|
3
|
-
//
|
1
|
+
// Sass List-Maps 1.0.0-b3
|
2
|
+
// a libsass polyfill for rubysass "maps" data-type -- using lists
|
3
|
+
// by @lunelson
|
4
|
+
// MIT License
|
4
5
|
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
|
6
|
+
// 88 88 88 88
|
7
|
+
// ,d "" 88 "" ,d ""
|
8
|
+
// 88 88 88
|
9
|
+
// 88 88 MM88MMM 88 88 88 MM88MMM 88 ,adPPYba, ,adPPYba,
|
10
|
+
// 88 88 88 88 88 88 88 88 a8P_____88 I8[ ""
|
11
|
+
// 88 88 88 88 88 88 88 88 8PP""""""" `"Y8ba,
|
12
|
+
// "8a, ,a88 88, 88 88 88 88, 88 "8b, ,aa aa ]8I
|
13
|
+
// `"YbbdP'Y8 "Y888 88 88 88 "Y888 88 `"Ybbd8"' `"YbbdP"'
|
14
|
+
//
|
15
|
+
|
16
|
+
///////////////////////////
|
17
|
+
// list helper functions //
|
18
|
+
///////////////////////////
|
19
|
+
|
20
|
+
// list-slice(): return a sub-list from a list, 'sliced' from/to given indices
|
21
|
+
// ---
|
22
|
+
// @alias slice()
|
23
|
+
// ---
|
24
|
+
// @param [list] $list: list to slice
|
25
|
+
// @param [number] $start (1): start index
|
26
|
+
// @param [number] $end (length($list)): end index
|
27
|
+
// @param [string] $sep ('comma'): default list separator
|
28
|
+
// ---
|
29
|
+
// @return [list]
|
30
|
+
@function list-slice($list, $start: 1, $end: length($list), $sep: 'comma') {
|
11
31
|
$output: ();
|
12
32
|
@for $i from $start through $end {
|
13
33
|
$output: append($output, nth($list, $i), $sep); }
|
14
34
|
@return $output;
|
15
35
|
}
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
36
|
+
// alias
|
37
|
+
@function slice($args...) { @return list-slice($args...); }
|
38
|
+
|
39
|
+
// list-set-nth(): return a list with value at index set/updated to new value
|
40
|
+
// ---
|
41
|
+
// @alias set-nth()
|
42
|
+
// ---
|
43
|
+
// @param [list] $list: list to set
|
44
|
+
// @param [number] $index: index to set
|
45
|
+
// @param [literal] $value: new value
|
46
|
+
// @param [string] $sep ('comma'): list separator
|
47
|
+
// ---
|
48
|
+
// @return [list]
|
49
|
+
@function list-set-nth($list, $index, $value, $sep: 'comma') {
|
50
|
+
$length: length($list);
|
51
|
+
$output: ();
|
52
|
+
@if $index > $length or $index <= 0 {
|
53
|
+
@return $list;
|
54
|
+
}
|
55
|
+
@if $index > 1 {
|
56
|
+
@for $i from 1 through $index - 1 {
|
57
|
+
$output: append($output, nth($list, $i), $sep);
|
58
|
+
}
|
59
|
+
}
|
20
60
|
$output: append($output, $value, $sep);
|
21
|
-
@if $length > 1 {
|
61
|
+
@if $length > 1 {
|
62
|
+
@for $i from $index + 1 through $length {
|
63
|
+
$output: append($output, nth($list, $i), $sep);
|
64
|
+
}
|
65
|
+
}
|
22
66
|
@return $output;
|
23
67
|
}
|
68
|
+
// alias
|
69
|
+
@function set-nth($args...) { @return list-set-nth($args...); }
|
24
70
|
|
25
|
-
|
26
|
-
//
|
27
|
-
|
71
|
+
///////////////////////////////
|
72
|
+
// list-map helper functions //
|
73
|
+
///////////////////////////////
|
28
74
|
|
29
|
-
|
30
|
-
|
75
|
+
// tuple-key(): return the key (first value) from a tuple (pair)
|
76
|
+
// ---
|
77
|
+
// @alias key()
|
78
|
+
// ---
|
79
|
+
// [0.9.3] added alias
|
80
|
+
// ---
|
81
|
+
// @param [list] $tuple: pair (list of length 2), to extract key from
|
82
|
+
// ---
|
83
|
+
// @return [literal]
|
84
|
+
@function tuple-key($tuple) {
|
85
|
+
@if length($tuple) < 1 { @return null; }
|
86
|
+
@return nth($tuple, 1);
|
87
|
+
}
|
88
|
+
// alias
|
31
89
|
@function key($tuple) { @return tuple-key($tuple); }
|
90
|
+
|
91
|
+
// tuple-value(): return the value (second value) from a tuple (pair)
|
92
|
+
// ---
|
93
|
+
// @alias value()
|
94
|
+
// ---
|
95
|
+
// [0.9.3] added alias
|
96
|
+
// ---
|
97
|
+
// @param [list] $tuple: pair (list of length 2), to extract value from
|
98
|
+
// ---
|
99
|
+
// @return [literal]
|
100
|
+
@function tuple-value($tuple) {
|
101
|
+
@if length($tuple) < 2 { @return null; }
|
102
|
+
@return nth($tuple, 2);
|
103
|
+
}
|
104
|
+
// alias
|
32
105
|
@function value($tuple) { @return tuple-value($tuple); }
|
33
106
|
|
34
|
-
//
|
107
|
+
// list-map-check(): return list-map from list; ensure input list-maps are lists-of-lists
|
108
|
+
// ---
|
109
|
+
// [0.9.5] added; replaces use of 'list()' function
|
110
|
+
// @param [list] $list: list-map to check
|
111
|
+
// ---
|
112
|
+
// @return [list]
|
113
|
+
@function list-map-check($list) {
|
114
|
+
@if length($list) == 2 and length(nth($list, 1)) == 1 {
|
115
|
+
@return append((), $list, 'comma');
|
116
|
+
}
|
117
|
+
@return $list;
|
118
|
+
}
|
35
119
|
|
36
|
-
|
120
|
+
//
|
121
|
+
// ,adPPYba, ,adPPYba, 8b,dPPYba, ,adPPYba,
|
122
|
+
// a8" "" a8" "8a 88P' "Y8 a8P_____88
|
123
|
+
// 8b 8b d8 88 8PP"""""""
|
124
|
+
// "8a, ,aa "8a, ,a8" 88 "8b, ,aa
|
125
|
+
// `"Ybbd8"' `"YbbdP"' 88 `"Ybbd8"'
|
126
|
+
//
|
37
127
|
|
38
|
-
|
39
|
-
//
|
40
|
-
|
128
|
+
/////////////////////////////////////////////////////////////////////////
|
129
|
+
// list-map versions of map-keys(), -values() and -has-key() functions //
|
130
|
+
/////////////////////////////////////////////////////////////////////////
|
41
131
|
|
132
|
+
// map-keys(): return comma-separated list of keys from map [conformant with rubysass map-keys()]
|
133
|
+
// ---
|
134
|
+
// @alias keys()
|
135
|
+
// ---
|
136
|
+
// [0.9.5] use list-map-check to handle single pairs automatically
|
137
|
+
// ---
|
138
|
+
// @param [argList] $list: list to retrieve keys from
|
139
|
+
// ---
|
140
|
+
// @return [list]
|
42
141
|
@function map-keys($list...) {
|
43
|
-
|
44
|
-
|
45
|
-
@each $tuple in $list {
|
142
|
+
$list: if(length($list) == 1, list-map-check($list...), list-map-check($list));
|
143
|
+
$output: ();
|
144
|
+
@each $tuple in $list {
|
145
|
+
$output: append($output, tuple-key($tuple), 'comma');
|
146
|
+
}
|
46
147
|
@return $output;
|
47
148
|
}
|
149
|
+
// alias
|
150
|
+
@function keys($list...) { @return map-keys($list...); }
|
151
|
+
|
152
|
+
// map-values(): return comma-separated list of values from map [conformant with rubysass map-values()]
|
153
|
+
// ---
|
154
|
+
// @alias values()
|
155
|
+
// ---
|
156
|
+
// [0.9.5] use list-map-check to handle single pairs automatically
|
157
|
+
// ---
|
158
|
+
// @param [argList] $list: list to retrieve values from
|
159
|
+
// ---
|
160
|
+
// @return [list]
|
48
161
|
@function map-values($list...) {
|
49
|
-
|
50
|
-
|
51
|
-
@each $tuple in $list {
|
162
|
+
$list: if(length($list) == 1, list-map-check($list...), list-map-check($list));
|
163
|
+
$output: ();
|
164
|
+
@each $tuple in $list {
|
165
|
+
$output: append($output, tuple-value($tuple), 'comma');
|
166
|
+
}
|
52
167
|
@return $output;
|
53
168
|
}
|
169
|
+
// alias
|
170
|
+
@function values($list...) { @return map-values($list...); }
|
171
|
+
|
172
|
+
// map-has-key(): check whether key exists in map at root level [conformant with rubysass map-has-key()]
|
173
|
+
// ---
|
174
|
+
// @alias has-key()
|
175
|
+
// ---
|
176
|
+
// @param [list] $list: list to check
|
177
|
+
// @param [literal] $key: key to check in list
|
178
|
+
// ---
|
179
|
+
// @return [bool]
|
54
180
|
@function map-has-key($list, $key) {
|
55
181
|
$list: list-map-check($list);
|
56
|
-
@each $tuple in $list {
|
182
|
+
@each $tuple in $list {
|
183
|
+
@if tuple-key($tuple) == $key {
|
184
|
+
@return true;
|
185
|
+
}
|
186
|
+
}
|
57
187
|
@return false;
|
58
188
|
}
|
59
|
-
|
60
|
-
|
61
|
-
@return nth($keys, index($keys, $key) - 1);
|
62
|
-
}
|
63
|
-
@function map-next-key($list, $key) {
|
64
|
-
$list: list-map-check($list); $keys: map-keys($list);
|
65
|
-
@return nth($keys, index($keys, $key) + 1);
|
66
|
-
}
|
189
|
+
// alias
|
190
|
+
@function has-key($list, $key) { @return map-has-key($list, $key); }
|
67
191
|
|
68
|
-
|
69
|
-
//
|
192
|
+
////////////////////////////////////////////////////////////
|
193
|
+
// list-map versions of map-get(), -merge() and -remove() //
|
194
|
+
////////////////////////////////////////////////////////////
|
70
195
|
|
71
|
-
|
72
|
-
|
73
|
-
|
74
|
-
|
196
|
+
// map-get(): return value corresponding to key in map; conformant to rubysass map-get()
|
197
|
+
// ---
|
198
|
+
// [0.9.5] list-map-check() now handles single-pair inputs / outputs
|
199
|
+
// ---
|
200
|
+
// @param [list] $list: map
|
201
|
+
// @param [literal] $key: key by which to look up value
|
202
|
+
// @param [bool] $check (true): whether or not to check the map format first
|
203
|
+
// ---
|
204
|
+
// @return [literal] | [null]
|
205
|
+
@function map-get($list, $key) {
|
206
|
+
$list: list-map-check($list);
|
207
|
+
@each $tuple in $list {
|
208
|
+
@if tuple-key($tuple) == $key {
|
209
|
+
@return tuple-value($tuple);
|
210
|
+
}
|
211
|
+
}
|
75
212
|
@return null;
|
76
213
|
}
|
214
|
+
|
215
|
+
// map-merge(): return a merge of second map in to first map; conformant to rubysass map-merge()
|
216
|
+
// ---
|
217
|
+
// [0.9.5] list-map-check() handles single pairs; $check param for internal use
|
218
|
+
// ---
|
219
|
+
// @param [list] $list1: first map
|
220
|
+
// @param [list] $list2: second map
|
221
|
+
// @param [bool] $check (true): whether or not to check the map first
|
222
|
+
// ---
|
223
|
+
// @return [list]
|
77
224
|
@function map-merge($list1, $list2, $check: true) {
|
78
|
-
@if $check {
|
225
|
+
@if $check {
|
226
|
+
$list1: list-map-check($list1);
|
227
|
+
$list2: list-map-check($list2);
|
228
|
+
}
|
79
229
|
$keys1: map-keys($list1);
|
80
230
|
@each $tuple in $list2 {
|
81
231
|
$index: index($keys1, tuple-key($tuple));
|
82
232
|
@if $index { $list1: set-nth($list1, $index, $tuple); }
|
83
|
-
@else { $list1: append($list1, $tuple, 'comma'); }
|
233
|
+
@else { $list1: append($list1, $tuple, 'comma'); }
|
234
|
+
}
|
84
235
|
@return $list1;
|
85
236
|
}
|
86
|
-
|
237
|
+
|
238
|
+
// map-remove(): return map with tuples removed, according to keys (if found); conformant to rubysass 3.4 map-remove()
|
239
|
+
// ---
|
240
|
+
// @param [list] $list: map
|
241
|
+
// @param [literal] $key: key
|
242
|
+
// ---
|
243
|
+
// @return [list]
|
244
|
+
@function map-remove($list, $keys...) {
|
87
245
|
$list: list-map-check($list);
|
88
|
-
$
|
89
|
-
@
|
90
|
-
@if
|
246
|
+
$output: ();
|
247
|
+
@each $tuple in $list {
|
248
|
+
@if index($keys, tuple-key($tuple)) == false {
|
249
|
+
$output: append($output, $tuple, 'comma');
|
250
|
+
}
|
251
|
+
}
|
91
252
|
@return $output;
|
92
253
|
}
|
93
254
|
|
94
|
-
//
|
95
|
-
//
|
255
|
+
//
|
256
|
+
// 88 88
|
257
|
+
// 88 88
|
258
|
+
// 88 88
|
259
|
+
// ,adPPYYba, ,adPPYb,88 8b d8 ,adPPYYba, 8b,dPPYba, ,adPPYba, ,adPPYba, ,adPPYb,88
|
260
|
+
// "" `Y8 a8" `Y88 `8b d8' "" `Y8 88P' `"8a a8" "" a8P_____88 a8" `Y88
|
261
|
+
// ,adPPPPP88 8b 88 `8b d8' ,adPPPPP88 88 88 8b 8PP""""""" 8b 88
|
262
|
+
// 88, ,88 "8a, ,d88 `8b,d8' 88, ,88 88 88 "8a, ,aa "8b, ,aa "8a, ,d88
|
263
|
+
// `"8bbdP"Y8 `"8bbdP"Y8 "8" `"8bbdP"Y8 88 88 `"Ybbd8"' `"Ybbd8"' `"8bbdP"Y8
|
264
|
+
//
|
265
|
+
|
266
|
+
//////////////////////////////////////////////////////////////
|
267
|
+
// deep/nested map functions: map-get-z() and map-merge-z() //
|
268
|
+
//////////////////////////////////////////////////////////////
|
96
269
|
|
270
|
+
// map-get-z(): a 'deep', nested or chained version of `map-get` (see above); unique
|
271
|
+
// ---
|
272
|
+
// [0.9.5] now uses list-map-check to handle single-pair list-maps
|
273
|
+
// [0.9.2] aliased to get(); can replace map-get() and map-get-z() in usage
|
274
|
+
// ---
|
275
|
+
// @alias get()
|
276
|
+
// ---
|
277
|
+
// @param [list] $list: map
|
278
|
+
// @param [argList] $keys: nested / chained key list (where to get value)
|
279
|
+
// ---
|
280
|
+
// @return [literal] | [null]
|
97
281
|
@function map-get-z($list, $keys...) {
|
98
|
-
@if $list == null { @return
|
282
|
+
@if $list == null { @return $list; }
|
99
283
|
$length: length($keys);
|
100
284
|
$list: map-get($list, nth($keys, 1));
|
101
285
|
@if $length > 1 {
|
102
286
|
@for $n from 2 through $length {
|
103
|
-
@if $list == null { @return
|
104
|
-
$list: map-get($list, nth($keys, $n)
|
105
|
-
|
106
|
-
|
287
|
+
@if $list == null { @return $list; }
|
288
|
+
$list: map-get($list, nth($keys, $n));
|
289
|
+
}
|
290
|
+
@return $list;
|
291
|
+
}
|
292
|
+
@return $list;
|
107
293
|
}
|
294
|
+
// alias
|
295
|
+
@function get($args...) { @return map-get-z($args...); }
|
296
|
+
|
297
|
+
// map-merge-z(): a 'deep', nested or chained version of `map-merge`; offers `map-set` syntax too
|
298
|
+
// ---
|
299
|
+
// [0.9.5] now uses list-map-check to handle single-pair list-maps
|
300
|
+
// [0.9.2] aliased to merge() and set(); can replace map-merge() and map-merge-z() in usage
|
301
|
+
// ---
|
302
|
+
// @alias merge(), set()
|
303
|
+
// ---
|
304
|
+
// @param [list] $list: map
|
305
|
+
// @param [argList] $keys-and-values: nested / chained key list (where to merge value); final item in list is the value to be merged
|
306
|
+
// ---
|
307
|
+
// @return [list]
|
108
308
|
@function map-merge-z($list, $keys-and-value...) {
|
109
309
|
$arg-length: length($keys-and-value);
|
110
310
|
$value: nth($keys-and-value, $arg-length);
|
111
311
|
$key-length: $arg-length - 1;
|
112
312
|
$list: list-map-check($list);
|
113
313
|
@if $key-length == 0 {
|
114
|
-
$value: if(type-of($value) == 'list', map-merge($list, list-map-check($value), false), map-merge($list, append((), $value (), 'comma'), false));
|
115
|
-
|
314
|
+
$value: if(type-of($value) == 'list', map-merge($list, list-map-check($value), false), map-merge($list, append((), $value (), 'comma'), false));
|
315
|
+
}
|
316
|
+
@else {
|
317
|
+
$start: 1;
|
318
|
+
@if type-of($value) == 'list' {
|
319
|
+
$start: 0;
|
320
|
+
$value: list-map-check($value);
|
321
|
+
}
|
116
322
|
@for $i from $start through $key-length {
|
117
323
|
$new-list: (); $old-list: ();
|
118
|
-
@if $i == 0 { $new-list: $value; }
|
119
|
-
@
|
120
|
-
$
|
324
|
+
@if $i == 0 { $new-list: $value; }
|
325
|
+
@else { $new-list: append((), nth($keys-and-value, $key-length + 1 - $i) $value, 'comma'); }
|
326
|
+
@if $i == $key-length { $old-list: $list; }
|
327
|
+
@else { $old-list: map-get-z($list, slice($keys-and-value, 1, $key-length - $i)...) or (); }
|
328
|
+
$value: map-merge($old-list, $new-list);
|
329
|
+
}
|
330
|
+
}
|
121
331
|
@return $value;
|
122
332
|
}
|
123
|
-
|
124
|
-
// aliases added as of 0.9.2: unify and replace map-*() and map-*-z() variants
|
125
|
-
|
126
|
-
@function get($args...) { @return map-get-z($args...); }
|
333
|
+
// aliases
|
127
334
|
@function merge($args...) { @return map-merge-z($args...); }
|
128
335
|
@function set($args...) { @return map-merge-z($args...); }
|
129
336
|
|
130
|
-
//
|
337
|
+
//
|
338
|
+
// ,d
|
339
|
+
// 88
|
340
|
+
// ,adPPYba, 8b, ,d8 MM88MMM 8b,dPPYba, ,adPPYYba, ,adPPYba,
|
341
|
+
// a8P_____88 `Y8, ,8P' 88 88P' "Y8 "" `Y8 I8[ ""
|
342
|
+
// 8PP""""""" )888( 88 88 ,adPPPPP88 `"Y8ba,
|
343
|
+
// "8b, ,aa ,d8" "8b, 88, 88 88, ,88 aa ]8I
|
344
|
+
// `"Ybbd8"' 8P' `Y8 "Y888 88 `"8bbdP"Y8 `"YbbdP"'
|
345
|
+
//
|
346
|
+
|
347
|
+
/////////////////////////////////////
|
348
|
+
// additional map helper functions //
|
349
|
+
/////////////////////////////////////
|
350
|
+
|
351
|
+
// map-prev-key(): return previous key from map
|
352
|
+
// ---
|
353
|
+
// [0.9.5] added
|
354
|
+
// ---
|
355
|
+
// @alias prev-key()
|
356
|
+
// ---
|
357
|
+
// @param [list] $list: map
|
358
|
+
// @param [literal] $key: pivot key
|
359
|
+
// ---
|
360
|
+
// @return [literal]
|
361
|
+
@function map-prev-key($list, $key) {
|
362
|
+
$list: list-map-check($list);
|
363
|
+
$keys: map-keys($list);
|
364
|
+
@return nth($keys, index($keys, $key) - 1);
|
365
|
+
}
|
366
|
+
// alias
|
367
|
+
@function prev-key($list, $key) { @return map-prev-key($list, $key); }
|
131
368
|
|
369
|
+
// map-next-key(): return next key from map
|
370
|
+
// ---
|
371
|
+
// [0.9.5] added
|
372
|
+
// ---
|
373
|
+
// @alias next-key()
|
374
|
+
// ---
|
375
|
+
// @param [list] $list: map
|
376
|
+
// @param [literal] $key: pivot key
|
377
|
+
// ---
|
378
|
+
// @return [literal]
|
379
|
+
@function map-next-key($list, $key) {
|
380
|
+
$list: list-map-check($list);
|
381
|
+
$keys: map-keys($list);
|
382
|
+
@return nth($keys, index($keys, $key) + 1);
|
383
|
+
}
|
384
|
+
// alias
|
385
|
+
@function next-key($list, $key) { @return map-next-key($list, $key); }
|
386
|
+
|
387
|
+
// map-inspect(): return the string representation of a map
|
388
|
+
// ---
|
389
|
+
// [0.9.5] added
|
390
|
+
// ---
|
391
|
+
// @param [argList] $list: map
|
392
|
+
// ---
|
393
|
+
// @return [string]
|
132
394
|
@function map-inspect($list...) {
|
133
|
-
|
134
|
-
|
135
|
-
$
|
395
|
+
$list: if(length($list) == 1, list-map-check($list...), list-map-check($list));
|
396
|
+
$output: '(';
|
397
|
+
$i: 1;
|
136
398
|
@each $tuple in $list {
|
137
399
|
@if length($tuple) != 2 {
|
138
|
-
$output: $output + '#{$tuple}';
|
400
|
+
$output: $output + '#{$tuple}';
|
401
|
+
}
|
139
402
|
@else {
|
140
|
-
$key:
|
141
|
-
$value:
|
142
|
-
|
143
|
-
|
144
|
-
@if $i < length(map-keys($list)) {
|
403
|
+
$key: tuple-key($tuple);
|
404
|
+
$value: tuple-value($tuple);
|
405
|
+
$output: $output + '#{$key} ' + if(type-of($value) == 'list', '#{map-inspect($value)}', '#{$value}');
|
406
|
+
}
|
407
|
+
@if $i < length(map-keys($list)) {
|
408
|
+
$output: $output + ', ';
|
409
|
+
}
|
145
410
|
$i: $i + 1;
|
146
411
|
}
|
147
412
|
@return $output + ')';
|
148
413
|
}
|
149
414
|
|
150
|
-
//
|
151
|
-
|
415
|
+
// map-pretty(): return the string representation of a map with indents and line breaks
|
416
|
+
// ---
|
417
|
+
// [0.9.9] added
|
418
|
+
// ---
|
419
|
+
// @alias map-inspect-pretty()
|
420
|
+
// ---
|
421
|
+
// @param [list] $list: map
|
422
|
+
// @param [number] $level (1): internal variable, do not touch
|
423
|
+
// ---
|
424
|
+
// @return [string]
|
152
425
|
@function map-pretty($list, $level: 1) {
|
153
|
-
|
154
|
-
|
426
|
+
$tab: ' ';
|
427
|
+
$cr: '
|
428
|
+
';
|
429
|
+
$list: if(length($list) == 1, list-map-check($list...), list-map-check($list));
|
155
430
|
$indent: $tab; $outdent: $tab;
|
156
431
|
@for $n from 1 through $level { $indent: $indent + $tab; }
|
157
432
|
@for $n from 1 through $level - 1 { $outdent: $outdent + $tab; }
|
158
|
-
$output: '(' + $cr + $indent;
|
433
|
+
$output: '(' + $cr + $indent;
|
434
|
+
$i: 1;
|
159
435
|
@each $tuple in $list {
|
160
436
|
@if length($tuple) != 2 {
|
161
|
-
$output: $output + '#{$tuple}';
|
437
|
+
$output: $output + '#{$tuple}';
|
438
|
+
}
|
162
439
|
@else {
|
163
440
|
$key: nth($tuple, 1); $value: nth($tuple, 2);
|
164
441
|
@if type-of($value) == 'list' { $output: $output + '#{$key} #{map-pretty($value, $level+1)}'; }
|
165
|
-
@else { $output: $output + '#{$key} #{$value}'; }
|
442
|
+
@else { $output: $output + '#{$key} #{$value}'; }
|
443
|
+
}
|
166
444
|
@if $i < length(map-keys($list)) { $output: $output + ',' + $cr + $indent; }
|
167
445
|
$i: $i + 1;
|
168
446
|
}
|
169
|
-
// @return unquote($output + $cr + $outdent + ')'); // replace last line with this one for unquoted output in libsass
|
170
447
|
@return $output + $cr + $outdent + ')';
|
171
448
|
}
|
172
|
-
// aliases
|
449
|
+
// aliases
|
173
450
|
@function map-inspect-pretty($list...) { @return map-pretty($list...); }
|
174
|
-
@function map-inspect-p($list...) { @return map-pretty($list...); }
|
175
451
|
|
452
|
+
// map-sort(): return sorted list-map, based on values at given key(s)
|
453
|
+
// ---
|
454
|
+
// [0.9.9] added
|
455
|
+
//
|
456
|
+
// @param [list] $list: map
|
457
|
+
// @param [argList] $keys: nested / chained key list
|
458
|
+
// ---
|
459
|
+
// @return [list]
|
460
|
+
$list-map-sort-dir: 'asc'; // global sort dir variable
|
461
|
+
@function map-sort($list-map, $keys...) {
|
462
|
+
@if length($keys) < 1 { @return $list-map; }
|
463
|
+
$list-map: list-map-check($list-map);
|
464
|
+
@if length($list-map) > 1 {
|
465
|
+
$less: (); $equal: (); $greater: ();
|
466
|
+
$seed: nth($list-map, ceil(length($list-map) / 2));
|
467
|
+
$seed-value: map-get-z(nth($seed, 2), $keys...);
|
468
|
+
@each $item in $list-map {
|
469
|
+
$item-value: map-get-z(nth($item, 2), $keys...);
|
470
|
+
@if $list-map-sort-dir == 'asc' {
|
471
|
+
@if $item-value == $seed-value { $equal: append($equal, $item, 'comma'); }
|
472
|
+
@else if $item-value < $seed-value { $less: append($less, $item, 'comma'); }
|
473
|
+
@else { $greater: append($greater, $item, 'comma'); }
|
474
|
+
}
|
475
|
+
@else {
|
476
|
+
@if $item-value == $seed-value { $equal: append($equal, $item, 'comma'); }
|
477
|
+
@else if $item-value > $seed-value { $less: append($less, $item, 'comma'); }
|
478
|
+
@else { $greater: append($greater, $item, 'comma'); }
|
479
|
+
}
|
480
|
+
}
|
481
|
+
@return join(join(map-sort($less, $keys...), $equal), map-sort($greater, $keys...));
|
482
|
+
}
|
483
|
+
@return $list-map;
|
484
|
+
}
|
485
|
+
|
486
|
+
// map-json(): return json string representation of a map
|
487
|
+
// ---
|
488
|
+
// [1.0.0] added
|
489
|
+
// ---
|
490
|
+
// @param [list] $list: map
|
491
|
+
// @param [number] $level (1): internal variable, do not touch
|
492
|
+
// ---
|
493
|
+
// @return [string]
|
494
|
+
@function map-json($list...) {
|
495
|
+
$list: if(length($list) == 1, list-map-check($list...), list-map-check($list));
|
496
|
+
$output: '{ '; $i: 1;
|
497
|
+
@each $tuple in $list {
|
498
|
+
@if length($tuple) != 2 {
|
499
|
+
$output: $output + '#{$tuple}';
|
500
|
+
}
|
501
|
+
@else {
|
502
|
+
$key: nth($tuple, 1);
|
503
|
+
$value: nth($tuple, 2);
|
504
|
+
@if type-of($value) == 'list' {
|
505
|
+
$output: $output + '"#{$key}": #{map-json($value)}';
|
506
|
+
}
|
507
|
+
@else if type-of($value) == 'number' {
|
508
|
+
$value: if(unitless($value), $value, '"#{$value}"');
|
509
|
+
$output: $output + '"#{$key}": #{$value}';
|
510
|
+
}
|
511
|
+
@else {
|
512
|
+
$value: if(type-of($value) == 'bool', $value, '"#{$value}"');
|
513
|
+
$output: $output + '"#{$key}": #{$value}';
|
514
|
+
}
|
515
|
+
}
|
516
|
+
@if $i < length(map-keys($list)) {
|
517
|
+
$output: $output + ', ';
|
518
|
+
}
|
519
|
+
$i: $i + 1;
|
520
|
+
}
|
521
|
+
@return $output + ' }';
|
522
|
+
}
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: sass-list-maps
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 1.0.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Lu Nelson
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2014-
|
11
|
+
date: 2014-09-30 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: compass
|
@@ -38,15 +38,15 @@ dependencies:
|
|
38
38
|
- - ~>
|
39
39
|
- !ruby/object:Gem::Version
|
40
40
|
version: 3.2.0
|
41
|
-
description:
|
42
|
-
|
41
|
+
description: Polyfill for map (hash/object) data functionality in libsass and ruby-sass
|
42
|
+
< 3.3.x.
|
43
43
|
email: lunelson@gmail.com
|
44
44
|
executables: []
|
45
45
|
extensions: []
|
46
46
|
extra_rdoc_files: []
|
47
47
|
files:
|
48
|
-
- LICENSE
|
49
48
|
- README.md
|
49
|
+
- LICENSE
|
50
50
|
- _sass-list-maps.scss
|
51
51
|
- lib/sass-list-maps.rb
|
52
52
|
homepage: https://github.com/lunelson/sass-list-maps
|
@@ -69,8 +69,9 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
69
69
|
version: '0'
|
70
70
|
requirements: []
|
71
71
|
rubyforge_project:
|
72
|
-
rubygems_version: 2.
|
72
|
+
rubygems_version: 2.0.14
|
73
73
|
signing_key:
|
74
74
|
specification_version: 4
|
75
|
-
summary:
|
75
|
+
summary: Polyfill for map (hash/object) data functionality in libsass and ruby-sass
|
76
|
+
< 3.3.x.
|
76
77
|
test_files: []
|