-
Notifications
You must be signed in to change notification settings - Fork 3.6k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
3D Tiles Styling - treat colors as vec4 #4849
Changes from 2 commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -36,8 +36,6 @@ define([ | |
var scratchColor = new Color(); | ||
|
||
var ScratchStorage = { | ||
scratchColorIndex : 0, | ||
scratchColorArray : [new Color()], | ||
scratchArrayIndex : 0, | ||
scratchArrayArray : [[]], | ||
scratchCartesian2Index : 0, | ||
|
@@ -47,18 +45,11 @@ define([ | |
scratchCartesian3Array : [new Cartesian3()], | ||
scratchCartesian4Array : [new Cartesian4()], | ||
reset : function() { | ||
this.scratchColorIndex = 0; | ||
this.scratchArrayIndex = 0; | ||
this.scratchCartesian2Index = 0; | ||
this.scratchCartesian3Index = 0; | ||
this.scratchCartesian4Index = 0; | ||
}, | ||
getColor : function() { | ||
if (this.scratchColorIndex >= this.scratchColorArray.length) { | ||
this.scratchColorArray.push(new Color()); | ||
} | ||
return this.scratchColorArray[this.scratchColorIndex++]; | ||
}, | ||
getArray : function() { | ||
if (this.scratchArrayIndex >= this.scratchArrayArray.length) { | ||
this.scratchArrayArray.push([]); | ||
|
@@ -184,18 +175,17 @@ define([ | |
* {@link https://github.com/AnalyticalGraphicsInc/3d-tiles/tree/master/Styling|3D Tiles Styling language} | ||
* is of type <code>Boolean</code>, <code>Number</code>, or <code>String</code>, the corresponding JavaScript | ||
* primitive type will be returned. If the result is a <code>RegExp</code>, a Javascript <code>RegExp</code> | ||
* object will be returned. If the result is a <code>Color</code>, a {@link Color} object will be returned. | ||
* If the result is a <code>Cartesian2</code>, <code>Cartesian3</code>, or <code>Cartesian4</code>, | ||
* object will be returned. If the result is a <code>Cartesian2</code>, <code>Cartesian3</code>, or <code>Cartesian4</code>, | ||
* a {@link Cartesian2}, {@link Cartesian3}, or {@link Cartesian4} object will be returned. | ||
* | ||
* @param {FrameState} frameState The frame state. | ||
* @param {Cesium3DTileFeature} feature The feature who's properties may be used as variables in the expression. | ||
* @returns {Boolean|Number|String|Color|Cartesian2|Cartesian3|Cartesian4|RegExp} The result of evaluating the expression. | ||
* @returns {Boolean|Number|String|Cartesian2|Cartesian3|Cartesian4|RegExp} The result of evaluating the expression. | ||
*/ | ||
Expression.prototype.evaluate = function(frameState, feature) { | ||
ScratchStorage.reset(); | ||
var result = this._runtimeAst.evaluate(frameState, feature); | ||
if ((result instanceof Color) || (result instanceof Cartesian2) || (result instanceof Cartesian3) || (result instanceof Cartesian4)) { | ||
if ((result instanceof Cartesian2) || (result instanceof Cartesian3) || (result instanceof Cartesian4)) { | ||
return result.clone(); | ||
} | ||
return result; | ||
|
@@ -212,7 +202,7 @@ define([ | |
Expression.prototype.evaluateColor = function(frameState, feature, result) { | ||
ScratchStorage.reset(); | ||
var color = this._runtimeAst.evaluate(frameState, feature); | ||
return Color.clone(color, result); | ||
return Color.fromCartesian4(color, result); | ||
}; | ||
|
||
/** | ||
|
@@ -776,46 +766,46 @@ define([ | |
}; | ||
|
||
Node.prototype._evaluateLiteralColor = function(frameState, feature) { | ||
var result = ScratchStorage.getColor(); | ||
var color = scratchColor; | ||
var args = this._left; | ||
if (this._value === 'color') { | ||
if (!defined(args)) { | ||
return Color.fromBytes(255, 255, 255, 255, result); | ||
Color.fromBytes(255, 255, 255, 255, color); | ||
} else if (args.length > 1) { | ||
Color.fromCssColorString(args[0].evaluate(frameState, feature), result); | ||
result.alpha = args[1].evaluate(frameState, feature); | ||
Color.fromCssColorString(args[0].evaluate(frameState, feature), color); | ||
color.alpha = args[1].evaluate(frameState, feature); | ||
} else { | ||
Color.fromCssColorString(args[0].evaluate(frameState, feature), result); | ||
Color.fromCssColorString(args[0].evaluate(frameState, feature), color); | ||
} | ||
} else if (this._value === 'rgb') { | ||
Color.fromBytes( | ||
args[0].evaluate(frameState, feature), | ||
args[1].evaluate(frameState, feature), | ||
args[2].evaluate(frameState, feature), | ||
255, result); | ||
255, color); | ||
} else if (this._value === 'rgba') { | ||
// convert between css alpha (0 to 1) and cesium alpha (0 to 255) | ||
var a = args[3].evaluate(frameState, feature) * 255; | ||
Color.fromBytes( | ||
args[0].evaluate(frameState, feature), | ||
args[1].evaluate(frameState, feature), | ||
args[2].evaluate(frameState, feature), | ||
a, result); | ||
a, color); | ||
} else if (this._value === 'hsl') { | ||
Color.fromHsl( | ||
args[0].evaluate(frameState, feature), | ||
args[1].evaluate(frameState, feature), | ||
args[2].evaluate(frameState, feature), | ||
1.0, result); | ||
1.0, color); | ||
} else if (this._value === 'hsla') { | ||
Color.fromHsl( | ||
args[0].evaluate(frameState, feature), | ||
args[1].evaluate(frameState, feature), | ||
args[2].evaluate(frameState, feature), | ||
args[3].evaluate(frameState, feature), | ||
result); | ||
color); | ||
} | ||
return result; | ||
return Cartesian4.fromColor(color, ScratchStorage.getCartesian4()); | ||
}; | ||
|
||
Node.prototype._evaluateLiteralVector = function(frameState, feature) { | ||
|
@@ -917,19 +907,18 @@ define([ | |
} | ||
|
||
var member = this._right.evaluate(frameState, feature); | ||
if (property instanceof Color) { | ||
// Color components may be accessed with .x, .y, .z, .w and implicitly with .red, .green, .blue, .alpha | ||
if (member === 'x') { | ||
return property.red; | ||
} else if (member === 'y') { | ||
return property.green; | ||
} else if (member === 'z') { | ||
return property.blue; | ||
} else if (member === 'w') { | ||
return property.alpha; | ||
if ((property instanceof Cartesian2) || (property instanceof Cartesian3) || (property instanceof Cartesian4)) { | ||
// Vector components may be accessed with .red, .green, .blue, .alpha and implicitly with .x, .y, .z, .w | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Like how glsl can access components of a vector with There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Let's keep it, but go with Also, given that styles are often very concise and look like equations, this will fit well. @pmconne this will be a small breaking change for your styles. |
||
if (member === 'red') { | ||
return property.x; | ||
} else if (member === 'green') { | ||
return property.y; | ||
} else if (member === 'blue') { | ||
return property.z; | ||
} else if (member === 'alpha') { | ||
return property.w; | ||
} | ||
} | ||
|
||
return property[member]; | ||
}; | ||
|
||
|
@@ -943,27 +932,16 @@ define([ | |
} | ||
|
||
var member = this._right.evaluate(frameState, feature); | ||
if (property instanceof Color) { | ||
// Color components may be accessed with [0][1][2][3], ['x']['y']['z']['w'], and implicitly with ['red']['green']['blue']['alpha'] | ||
if (member === 0 || member === 'x') { | ||
return property.red; | ||
} else if (member === 1 || member === 'y') { | ||
return property.green; | ||
} else if (member === 2 || member === 'z') { | ||
return property.blue; | ||
} else if (member === 3 || member === 'w') { | ||
return property.alpha; | ||
} | ||
} else if ((property instanceof Cartesian2) || (property instanceof Cartesian3) || (property instanceof Cartesian4)) { | ||
// Vector components may be accessed with [0][1][2][3] and implicitly with ['x']['y']['z']['w'] | ||
if ((property instanceof Cartesian2) || (property instanceof Cartesian3) || (property instanceof Cartesian4)) { | ||
// Vector components may be accessed with [0][1][2][3], ['red']['green']['blue']['alpha'] and implicitly with ['x']['y']['z']['w'] | ||
// For Cartesian2 and Cartesian3 out-of-range components will just return undefined | ||
if (member === 0) { | ||
if (member === 0 || member === 'red') { | ||
return property.x; | ||
} else if (member === 1) { | ||
} else if (member === 1 || member === 'green') { | ||
return property.y; | ||
} else if (member === 2) { | ||
} else if (member === 2 || member === 'blue') { | ||
return property.z; | ||
} else if (member === 3) { | ||
} else if (member === 3 || member === 'alpha') { | ||
return property.w; | ||
} | ||
} | ||
|
@@ -999,7 +977,7 @@ define([ | |
|
||
Node.prototype._evaluatePositive = function(frameState, feature) { | ||
var left = this._left.evaluate(frameState, feature); | ||
if ((left instanceof Color) || (left instanceof Cartesian2) || (left instanceof Cartesian3) || (left instanceof Cartesian4)) { | ||
if ((left instanceof Cartesian2) || (left instanceof Cartesian3) || (left instanceof Cartesian4)) { | ||
return left; | ||
} | ||
return +left; | ||
|
@@ -1076,9 +1054,7 @@ define([ | |
Node.prototype._evaluatePlus = function(frameState, feature) { | ||
var left = this._left.evaluate(frameState, feature); | ||
var right = this._right.evaluate(frameState, feature); | ||
if ((right instanceof Color) && (left instanceof Color)) { | ||
return Color.add(left, right, ScratchStorage.getColor()); | ||
} else if ((right instanceof Cartesian2) && (left instanceof Cartesian2)) { | ||
if ((right instanceof Cartesian2) && (left instanceof Cartesian2)) { | ||
return Cartesian2.add(left, right, ScratchStorage.getCartesian2()); | ||
} else if ((right instanceof Cartesian3) && (left instanceof Cartesian3)) { | ||
return Cartesian3.add(left, right, ScratchStorage.getCartesian3()); | ||
|
@@ -1091,9 +1067,7 @@ define([ | |
Node.prototype._evaluateMinus = function(frameState, feature) { | ||
var left = this._left.evaluate(frameState, feature); | ||
var right = this._right.evaluate(frameState, feature); | ||
if ((right instanceof Color) && (left instanceof Color)) { | ||
return Color.subtract(left, right, ScratchStorage.getColor()); | ||
} else if ((right instanceof Cartesian2) && (left instanceof Cartesian2)) { | ||
if ((right instanceof Cartesian2) && (left instanceof Cartesian2)) { | ||
return Cartesian2.subtract(left, right, ScratchStorage.getCartesian2()); | ||
} else if ((right instanceof Cartesian3) && (left instanceof Cartesian3)) { | ||
return Cartesian3.subtract(left, right, ScratchStorage.getCartesian3()); | ||
|
@@ -1106,13 +1080,7 @@ define([ | |
Node.prototype._evaluateTimes = function(frameState, feature) { | ||
var left = this._left.evaluate(frameState, feature); | ||
var right = this._right.evaluate(frameState, feature); | ||
if ((right instanceof Color) && (left instanceof Color)) { | ||
return Color.multiply(left, right, ScratchStorage.getColor()); | ||
} else if ((right instanceof Color) && (typeof(left) === 'number')) { | ||
return Color.multiplyByScalar(right, left, ScratchStorage.getColor()); | ||
} else if ((left instanceof Color) && (typeof(right) === 'number')) { | ||
return Color.multiplyByScalar(left, right, ScratchStorage.getColor()); | ||
} else if ((right instanceof Cartesian2) && (left instanceof Cartesian2)) { | ||
if ((right instanceof Cartesian2) && (left instanceof Cartesian2)) { | ||
return Cartesian2.multiplyComponents(left, right, ScratchStorage.getCartesian2()); | ||
} else if ((right instanceof Cartesian2) && (typeof(left) === 'number')) { | ||
return Cartesian2.multiplyByScalar(right, left, ScratchStorage.getCartesian2()); | ||
|
@@ -1137,11 +1105,7 @@ define([ | |
Node.prototype._evaluateDivide = function(frameState, feature) { | ||
var left = this._left.evaluate(frameState, feature); | ||
var right = this._right.evaluate(frameState, feature); | ||
if ((right instanceof Color) && (left instanceof Color)) { | ||
return Color.divide(left, right, ScratchStorage.getColor()); | ||
} else if ((left instanceof Color) && (typeof(right) === 'number')) { | ||
return Color.divideByScalar(left, right, ScratchStorage.getColor()); | ||
} else if ((right instanceof Cartesian2) && (left instanceof Cartesian2)) { | ||
if ((right instanceof Cartesian2) && (left instanceof Cartesian2)) { | ||
return Cartesian2.divideComponents(left, right, ScratchStorage.getCartesian2()); | ||
} else if ((left instanceof Cartesian2) && (typeof(right) === 'number')) { | ||
return Cartesian2.divideByScalar(left, right, ScratchStorage.getCartesian2()); | ||
|
@@ -1160,9 +1124,7 @@ define([ | |
Node.prototype._evaluateMod = function(frameState, feature) { | ||
var left = this._left.evaluate(frameState, feature); | ||
var right = this._right.evaluate(frameState, feature); | ||
if ((right instanceof Color) && (left instanceof Color)) { | ||
return Color.mod(left, right, ScratchStorage.getColor()); | ||
} else if ((right instanceof Cartesian2) && (left instanceof Cartesian2)) { | ||
if ((right instanceof Cartesian2) && (left instanceof Cartesian2)) { | ||
return Cartesian2.fromElements(left.x % right.x, left.y % right.y, ScratchStorage.getCartesian2()); | ||
} else if ((right instanceof Cartesian3) && (left instanceof Cartesian3)) { | ||
return Cartesian3.fromElements(left.x % right.x, left.y % right.y, left.z % right.z, ScratchStorage.getCartesian3()); | ||
|
@@ -1175,8 +1137,7 @@ define([ | |
Node.prototype._evaluateEqualsStrict = function(frameState, feature) { | ||
var left = this._left.evaluate(frameState, feature); | ||
var right = this._right.evaluate(frameState, feature); | ||
if ((right instanceof Color) && (left instanceof Color) || | ||
(right instanceof Cartesian2) && (left instanceof Cartesian2) || | ||
if ((right instanceof Cartesian2) && (left instanceof Cartesian2) || | ||
(right instanceof Cartesian3) && (left instanceof Cartesian3) || | ||
(right instanceof Cartesian4) && (left instanceof Cartesian4)) { | ||
return left.equals(right); | ||
|
@@ -1187,8 +1148,7 @@ define([ | |
Node.prototype._evaluateEquals = function(frameState, feature) { | ||
var left = this._left.evaluate(frameState, feature); | ||
var right = this._right.evaluate(frameState, feature); | ||
if ((right instanceof Color) && (left instanceof Color) || | ||
(right instanceof Cartesian2) && (left instanceof Cartesian2) || | ||
if ((right instanceof Cartesian2) && (left instanceof Cartesian2) || | ||
(right instanceof Cartesian3) && (left instanceof Cartesian3) || | ||
(right instanceof Cartesian4) && (left instanceof Cartesian4)) { | ||
return left.equals(right); | ||
|
@@ -1202,8 +1162,7 @@ define([ | |
Node.prototype._evaluateNotEqualsStrict = function(frameState, feature) { | ||
var left = this._left.evaluate(frameState, feature); | ||
var right = this._right.evaluate(frameState, feature); | ||
if ((right instanceof Color) && (left instanceof Color) || | ||
(right instanceof Cartesian2) && (left instanceof Cartesian2) || | ||
if ((right instanceof Cartesian2) && (left instanceof Cartesian2) || | ||
(right instanceof Cartesian3) && (left instanceof Cartesian3) || | ||
(right instanceof Cartesian4) && (left instanceof Cartesian4)) { | ||
return !left.equals(right); | ||
|
@@ -1214,8 +1173,7 @@ define([ | |
Node.prototype._evaluateNotEquals = function(frameState, feature) { | ||
var left = this._left.evaluate(frameState, feature); | ||
var right = this._right.evaluate(frameState, feature); | ||
if ((right instanceof Color) && (left instanceof Color) || | ||
(right instanceof Cartesian2) && (left instanceof Cartesian2) || | ||
if ((right instanceof Cartesian2) && (left instanceof Cartesian2) || | ||
(right instanceof Cartesian3) && (left instanceof Cartesian3) || | ||
(right instanceof Cartesian4) && (left instanceof Cartesian4)) { | ||
return !left.equals(right); | ||
|
@@ -1321,7 +1279,7 @@ define([ | |
|
||
Node.prototype._evaluateToString = function(frameState, feature) { | ||
var left = this._left.evaluate(frameState, feature); | ||
if ((left instanceof RegExp) || (left instanceof Color) || (left instanceof Cartesian2) || (left instanceof Cartesian3) || (left instanceof Cartesian4)) { | ||
if ((left instanceof RegExp) || (left instanceof Cartesian2) || (left instanceof Cartesian3) || (left instanceof Cartesian4)) { | ||
return String(left); | ||
} | ||
//>>includeStart('debug', pragmas.debug); | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I figured
evaluateColor
should return aColor
object.evaluate
will just return aCartesian4
.There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes, agreed. It is fine for the Cesium implementation to map
vec4
to Cesium'sColor
when we know it is thecolor
property. This is an implementation detail and does not affect the spec.