jade
Version:
Jade template engine
231 lines (198 loc) • 3.92 kB
JavaScript
/*!
* Stylus - HSLA
* Copyright(c) 2010 LearnBoost <dev@learnboost.com>
* MIT Licensed
*/
/**
* Module dependencies.
*/
var Node = require('./node')
, nodes = require('./');
/**
* Initialize a new `HSLA` with the given h,s,l,a component values.
*
* @param {Number} h
* @param {Number} s
* @param {Number} l
* @param {Number} a
* @api public
*/
var HSLA = exports = module.exports = function HSLA(h,s,l,a){
Node.call(this);
this.h = clampDegrees(h);
this.s = clampPercentage(s);
this.l = clampPercentage(l);
this.a = clampAlpha(a);
this.hsla = this;
};
/**
* Inherit from `Node.prototype`.
*/
HSLA.prototype.__proto__ = Node.prototype;
/**
* Return hsla(n,n,n,n).
*
* @return {String}
* @api public
*/
HSLA.prototype.toString = function(){
return 'hsla('
+ this.h + ','
+ this.s + ','
+ this.l + ','
+ this.a + ')';
};
/**
* Return a clone of this node.
*
* @return {Node}
* @api public
*/
HSLA.prototype.clone = function(){
var clone = new HSLA(
this.h
, this.s
, this.l
, this.a);
clone.lineno = this.lineno;
return clone;
};
/**
* Return rgba `RGBA` representation.
*
* @return {RGBA}
* @api public
*/
HSLA.prototype.__defineGetter__('rgba', function(){
return nodes.RGBA.fromHSLA(this);
});
/**
* Return hash.
*
* @return {String}
* @api public
*/
HSLA.prototype.__defineGetter__('hash', function(){
return this.rgba.toString();
});
/**
* Coerce RGBA to HSLA.
*
* @param {Node} other
* @return {Node}
* @api public
*/
HSLA.prototype.coerce = function(other){
if (other instanceof nodes.RGBA) {
return other.hsla;
} else {
return Node.prototype.coerce.call(this, other);
}
};
/**
* Operate on `right` with the given `op`.
*
* @param {String} op
* @param {Node} right
* @return {Node}
* @api public
*/
HSLA.prototype.operate = function(op, right){
switch (op) {
case '+':
return new HSLA(
this.h + right.h
, this.s + right.s
, this.l + right.l
, 1 == right.a ? this.a : (this.a + right.a)
);
case '-':
return new HSLA(
this.h - right.h
, this.s - right.s
, this.l - right.l
, 1 == right.a ? this.a : (this.a - right.a)
);
case '*':
return new HSLA(
this.h * right.h
, this.s * right.s
, this.l * right.l
, this.a * right.a
);
case '/':
return new HSLA(
this.h / right.h
, this.s / right.s
, this.l / right.l
, this.a / right.a
);
default:
return Node.prototype.operate.call(this, op, right);
}
};
/**
* Return `HSLA` representation of the given `color`.
*
* @param {RGBA} color
* @return {HSLA}
* @api public
*/
exports.fromRGBA = function(rgba){
var r = rgba.r / 255
, g = rgba.g / 255
, b = rgba.b / 255
, a = rgba.a;
var min = Math.min(r,g,b)
, max = Math.max(r,g,b)
, l = (max + min) / 2
, d = max - min
, h, s;
switch (max) {
case min: h = 0; break;
case r: h = 60 * (g-b) / d; break;
case g: h = 60 * (b-r) / d + 120; break;
case b: h = 60 * (r-g) / d + 240; break;
}
if (max == min) {
s = 0;
} else if (l < .5) {
s = d / (2 * l);
} else {
s = d / (2 - 2 * l);
}
h %= 360;
s *= 100;
l *= 100;
return new HSLA(h,s,l,a);
};
/**
* Clamp degree `n` >= 0 and <= 360.
*
* @param {Number} n
* @return {Number}
* @api private
*/
function clampDegrees(n) {
return Math.max(0, Math.min(n, 360));
}
/**
* Clamp percentage `n` >= 0 and <= 100.
*
* @param {Number} n
* @return {Number}
* @api private
*/
function clampPercentage(n) {
return Math.max(0, Math.min(n, 100));
}
/**
* Clamp alpha `n` >= 0 and <= 1.
*
* @param {Number} n
* @return {Number}
* @api private
*/
function clampAlpha(n) {
return Math.max(0, Math.min(n, 1));
}