This repository has been archived by the owner on Apr 20, 2023. It is now read-only.
/
BgPosition.js
104 lines (94 loc) · 4.09 KB
/
BgPosition.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
/**
* Wrapper for a CSS3 bg-position value. Takes up to 2 position keywords and 2 lengths/percentages.
* @constructor
* @param {Array.<PIE.Tokenizer.Token>} tokens The tokens making up the background position value.
*/
PIE.BgPosition = (function() {
var length_fifty = PIE.getLength( '50%' ),
vert_idents = { 'top': 1, 'center': 1, 'bottom': 1 },
horiz_idents = { 'left': 1, 'center': 1, 'right': 1 };
function BgPosition( tokens ) {
this.tokens = tokens;
}
BgPosition.prototype = {
/**
* Normalize the values into the form:
* [ xOffsetSide, xOffsetLength, yOffsetSide, yOffsetLength ]
* where: xOffsetSide is either 'left' or 'right',
* yOffsetSide is either 'top' or 'bottom',
* and x/yOffsetLength are both PIE.Length objects.
* @return {Array}
*/
getValues: function() {
if( !this._values ) {
var tokens = this.tokens,
len = tokens.length,
Tokenizer = PIE.Tokenizer,
identType = Tokenizer.Type,
length_zero = PIE.getLength( '0' ),
type_ident = identType.IDENT,
type_length = identType.LENGTH,
type_percent = identType.PERCENT,
type, value,
vals = [ 'left', length_zero, 'top', length_zero ];
// If only one value, the second is assumed to be 'center'
if( len === 1 ) {
tokens.push( new Tokenizer.Token( type_ident, 'center' ) );
len++;
}
// Two values - CSS2
if( len === 2 ) {
// If both idents, they can appear in either order, so switch them if needed
if( type_ident & ( tokens[0].tokenType | tokens[1].tokenType ) &&
tokens[0].tokenValue in vert_idents && tokens[1].tokenValue in horiz_idents ) {
tokens.push( tokens.shift() );
}
if( tokens[0].tokenType & type_ident ) {
if( tokens[0].tokenValue === 'center' ) {
vals[1] = length_fifty;
} else {
vals[0] = tokens[0].tokenValue;
}
}
else if( tokens[0].isLengthOrPercent() ) {
vals[1] = PIE.getLength( tokens[0].tokenValue );
}
if( tokens[1].tokenType & type_ident ) {
if( tokens[1].tokenValue === 'center' ) {
vals[3] = length_fifty;
} else {
vals[2] = tokens[1].tokenValue;
}
}
else if( tokens[1].isLengthOrPercent() ) {
vals[3] = PIE.getLength( tokens[1].tokenValue );
}
}
// Three or four values - CSS3
else {
// TODO
}
this._values = vals;
}
return this._values;
},
/**
* Find the coordinates of the background image from the upper-left corner of the background area.
* Note that these coordinate values are not rounded.
* @param {Element} el
* @param {number} width - the width for percentages (background area width minus image width)
* @param {number} height - the height for percentages (background area height minus image height)
* @return {Object} { x: Number, y: Number }
*/
coords: function( el, width, height ) {
var vals = this.getValues(),
pxX = vals[1].pixels( el, width ),
pxY = vals[3].pixels( el, height );
return {
x: vals[0] === 'right' ? width - pxX : pxX,
y: vals[2] === 'bottom' ? height - pxY : pxY
};
}
};
return BgPosition;
})();