Huge News!Announcing our $40M Series B led by Abstract Ventures.Learn More
Socket
Socket
Sign inDemoInstall

@mapbox/mapbox-gl-style-spec

Package Overview
Dependencies
Maintainers
2
Versions
101
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

@mapbox/mapbox-gl-style-spec - npm Package Compare versions

Comparing version 12.0.0 to 13.0.0

util/properties.js

13

CHANGELOG.md

@@ -0,2 +1,15 @@

## 13.0.0
### ⚠️ Breaking changes
* Align implicit type behavior of `match` expressions with with `case/==` ([#6684](https://github.com/mapbox/mapbox-gl-js/pull/6684))
* Update spec so that documentation can automatically capture which functions and expressions can be used with which properties ([#6521](https://github.com/mapbox/mapbox-gl-js/pull/6521))
### ✨ Features and improvements
* Add `feature-state` [#6263](https://github.com/mapbox/mapbox-gl-js/pull/6263)
* Add support for GeoJSON attribution ([#6364](https://github.com/mapbox/mapbox-gl-js/pull/6364)) (h/t [andrewharvey](https://github.com/andrewharvey))
* Upgrade to Flow 0.69 ([#6594](https://github.com/mapbox/mapbox-gl-js/pull/6594))
### 🐛 Bug fixes
* Use named exports for style-spec entrypoint module ([#6601](https://github.com/mapbox/mapbox-gl-js/issues/6601)
## 12.0.0

@@ -3,0 +16,0 @@

@@ -172,2 +172,7 @@ // @flow

},
'feature-state': [
ValueType,
[StringType],
(ctx, [key]) => get(key.evaluate(ctx), ctx.featureState || {})
],
'properties': [

@@ -174,0 +179,0 @@ ObjectType,

14

expression/definitions/match.js

@@ -6,2 +6,3 @@ // @flow

import { typeOf } from '../values';
import { ValueType, type Type } from '../types';

@@ -11,3 +12,2 @@ import type { Expression } from '../expression';

import type EvaluationContext from '../evaluation_context';
import type { Type } from '../types';

@@ -89,3 +89,3 @@ // Map input label values to output expression index

const input = context.parse(args[1], 1, inputType);
const input = context.parse(args[1], 1, ValueType);
if (!input) return null;

@@ -97,2 +97,7 @@

assert(inputType && outputType);
if (input.type.kind !== 'value' && context.concat(1).checkSubtype((inputType: any), input.type)) {
return null;
}
return new Match((inputType: any), (outputType: any), input, cases, outputs, otherwise);

@@ -103,3 +108,4 @@ }

const input = (this.input.evaluate(ctx): any);
return (this.outputs[this.cases[input]] || this.otherwise).evaluate(ctx);
const output = (typeOf(input) === this.inputType && this.outputs[this.cases[input]]) || this.otherwise;
return output.evaluate(ctx);
}

@@ -142,3 +148,3 @@

const coerceLabel = (label) => this.input.type.kind === 'number' ? Number(label) : label;
const coerceLabel = (label) => this.inputType.kind === 'number' ? Number(label) : label;

@@ -145,0 +151,0 @@ for (const [outputIndex, labels] of groupedByOutput) {

@@ -5,3 +5,3 @@ // @flow

import type { Feature, GlobalProperties } from './index';
import type { GlobalProperties, Feature, FeatureState } from './index';

@@ -13,2 +13,3 @@ const geometryTypes = ['Unknown', 'Point', 'LineString', 'Polygon'];

feature: ?Feature;
featureState: ?FeatureState;

@@ -15,0 +16,0 @@ _parseColorCache: {[string]: ?Color};

@@ -18,2 +18,3 @@ // @flow

import { success, error } from '../util/result';
import { supportsPropertyExpression, supportsZoomExpression, supportsInterpolation } from '../util/properties';

@@ -33,2 +34,4 @@ import type {Type} from './types';

export type FeatureState = {[string]: any};
export type GlobalProperties = $ReadOnly<{

@@ -58,3 +61,3 @@ zoom: number,

evaluateWithoutErrorHandling(globals: GlobalProperties, feature?: Feature): any {
evaluateWithoutErrorHandling(globals: GlobalProperties, feature?: Feature, featureState?: FeatureState): any {
if (!this._evaluator) {

@@ -66,2 +69,3 @@ this._evaluator = new EvaluationContext();

this._evaluator.feature = feature;
this._evaluator.featureState = featureState;

@@ -71,3 +75,3 @@ return this.expression.evaluate(this._evaluator);

evaluate(globals: GlobalProperties, feature?: Feature): any {
evaluate(globals: GlobalProperties, feature?: Feature, featureState?: FeatureState): any {
if (!this._evaluator) {

@@ -79,2 +83,3 @@ this._evaluator = new EvaluationContext();

this._evaluator.feature = feature;
this._evaluator.featureState = featureState;

@@ -129,2 +134,3 @@ try {

kind: Kind;
isStateDependent: boolean;
_styleExpression: StyleExpression;

@@ -135,10 +141,11 @@

this._styleExpression = expression;
this.isStateDependent = kind !== 'constant' && !isConstant.isStateConstant(expression.expression);
}
evaluateWithoutErrorHandling(globals: GlobalProperties, feature?: Feature): any {
return this._styleExpression.evaluateWithoutErrorHandling(globals, feature);
evaluateWithoutErrorHandling(globals: GlobalProperties, feature?: Feature, featureState?: FeatureState): any {
return this._styleExpression.evaluateWithoutErrorHandling(globals, feature, featureState);
}
evaluate(globals: GlobalProperties, feature?: Feature): any {
return this._styleExpression.evaluate(globals, feature);
evaluate(globals: GlobalProperties, feature?: Feature, featureState?: FeatureState): any {
return this._styleExpression.evaluate(globals, feature, featureState);
}

@@ -150,2 +157,3 @@ }

zoomStops: Array<number>;
isStateDependent: boolean;

@@ -159,2 +167,3 @@ _styleExpression: StyleExpression;

this._styleExpression = expression;
this.isStateDependent = kind !== 'camera' && !isConstant.isStateConstant(expression.expression);
if (zoomCurve instanceof Interpolate) {

@@ -165,8 +174,8 @@ this._interpolationType = zoomCurve.interpolation;

evaluateWithoutErrorHandling(globals: GlobalProperties, feature?: Feature): any {
return this._styleExpression.evaluateWithoutErrorHandling(globals, feature);
evaluateWithoutErrorHandling(globals: GlobalProperties, feature?: Feature, featureState?: FeatureState): any {
return this._styleExpression.evaluateWithoutErrorHandling(globals, feature, featureState);
}
evaluate(globals: GlobalProperties, feature?: Feature): any {
return this._styleExpression.evaluate(globals, feature);
evaluate(globals: GlobalProperties, feature?: Feature, featureState?: FeatureState): any {
return this._styleExpression.evaluate(globals, feature, featureState);
}

@@ -190,3 +199,4 @@

kind: 'source',
+evaluate: (globals: GlobalProperties, feature?: Feature) => any,
isStateDependent: boolean,
+evaluate: (globals: GlobalProperties, feature?: Feature, featureState?: FeatureState) => any,
};

@@ -196,3 +206,3 @@

kind: 'camera',
+evaluate: (globals: GlobalProperties, feature?: Feature) => any,
+evaluate: (globals: GlobalProperties, feature?: Feature, featureState?: FeatureState) => any,
+interpolationFactor: (input: number, lower: number, upper: number) => number,

@@ -204,3 +214,4 @@ zoomStops: Array<number>

kind: 'composite',
+evaluate: (globals: GlobalProperties, feature?: Feature) => any,
isStateDependent: boolean,
+evaluate: (globals: GlobalProperties, feature?: Feature, featureState?: FeatureState) => any,
+interpolationFactor: (input: number, lower: number, upper: number) => number,

@@ -225,8 +236,8 @@ zoomStops: Array<number>

const isFeatureConstant = isConstant.isFeatureConstant(parsed);
if (!isFeatureConstant && !propertySpec['property-function']) {
return error([new ParsingError('', 'property expressions not supported')]);
if (!isFeatureConstant && !supportsPropertyExpression(propertySpec)) {
return error([new ParsingError('', 'data expressions not supported')]);
}
const isZoomConstant = isConstant.isGlobalPropertyConstant(parsed, ['zoom']);
if (!isZoomConstant && propertySpec['zoom-function'] === false) {
if (!isZoomConstant && !supportsZoomExpression(propertySpec)) {
return error([new ParsingError('', 'zoom expressions not supported')]);

@@ -240,3 +251,3 @@ }

return error([zoomCurve]);
} else if (zoomCurve instanceof Interpolate && propertySpec['function'] === 'piecewise-constant') {
} else if (zoomCurve instanceof Interpolate && !supportsInterpolation(propertySpec)) {
return error([new ParsingError('', '"interpolate" expressions cannot be used with this property')]);

@@ -243,0 +254,0 @@ }

@@ -11,2 +11,4 @@ // @flow

return false;
} else if (e.name === 'feature-state') {
return false;
} else if (e.name === 'has' && e.args.length === 1) {

@@ -32,2 +34,15 @@ return false;

function isStateConstant(e: Expression) {
if (e instanceof CompoundExpression) {
if (e.name === 'feature-state') {
return false;
}
}
let result = true;
e.eachChild(arg => {
if (result && !isStateConstant(arg)) { result = false; }
});
return result;
}
function isGlobalPropertyConstant(e: Expression, properties: Array<string>) {

@@ -42,2 +57,2 @@ if (e instanceof CompoundExpression && properties.indexOf(e.name) >= 0) { return false; }

export { isFeatureConstant, isGlobalPropertyConstant };
export { isFeatureConstant, isGlobalPropertyConstant, isStateConstant };

@@ -50,5 +50,8 @@ // @flow

'default': false,
'function': true,
'property-function': true,
'zoom-function': true
'transition': false,
'property-type': 'data-driven',
'expression': {
'interpolated': false,
'parameters': ['zoom', 'feature']
}
};

@@ -55,0 +58,0 @@

@@ -113,2 +113,3 @@ // Generated code; do not edit. Edit build/generate-flow-typed-style-spec.js instead.

"maxzoom"?: number,
"attribution"?: string,
"buffer"?: number,

@@ -115,0 +116,0 @@ "tolerance"?: number,

@@ -8,2 +8,3 @@ import type Pbf from 'pbf';

declare interface VectorTileLayer {
version?: number;
name: string;

@@ -10,0 +11,0 @@ extent: number;

@@ -144,33 +144,20 @@ // @flow

const inputType = typeof stops[0][0];
assert(
inputType === 'string' ||
inputType === 'number' ||
inputType === 'boolean'
);
let input = [inputType, ['get', parameters.property]];
let expression;
let isStep = false;
if (type === 'categorical' && inputType === 'boolean') {
if (type === 'categorical' && typeof stops[0][0] === 'boolean') {
assert(parameters.stops.length > 0 && parameters.stops.length <= 2);
if (parameters.stops[0][0] === false) {
input = ['!', input];
expression = ['case'];
for (const stop of stops) {
expression.push(['==', ['get', parameters.property], stop[0]], stop[1]);
}
expression = [ 'case', input, parameters.stops[0][1] ];
if (parameters.stops.length > 1) {
expression.push(parameters.stops[1][1]);
} else {
expression.push(defaultExpression);
}
expression.push(defaultExpression);
return expression;
} else if (type === 'categorical') {
expression = ['match', input];
expression = ['match', ['get', parameters.property]];
} else if (type === 'interval') {
expression = ['step', input];
expression = ['step', ['number', ['get', parameters.property]]];
isStep = true;
} else if (type === 'exponential') {
const base = parameters.base !== undefined ? parameters.base : 1;
expression = ['interpolate', ['exponential', base], input];
expression = ['interpolate', ['exponential', base], ['number', ['get', parameters.property]]];
} else {

@@ -240,6 +227,5 @@ throw new Error(`Unknown property function type ${type}`);

return parameters.type;
} else if (propertySpec.function) {
return propertySpec.function === 'interpolated' ? 'exponential' : 'interval';
} else {
return 'exponential';
assert(propertySpec.expression);
return (propertySpec.expression: any).interpolated ? 'exponential' : 'interval';
}

@@ -246,0 +232,0 @@ }

@@ -8,2 +8,3 @@

import Interpolate from '../expression/definitions/interpolate';
import { supportsInterpolation } from '../util/properties';

@@ -23,3 +24,3 @@ export function isFunction(value) {

const zoomDependent = zoomAndFeatureDependent || !featureDependent;
const type = parameters.type || (propertySpec.function === 'interpolated' ? 'exponential' : 'interval');
const type = parameters.type || (supportsInterpolation(propertySpec) ? 'exponential' : 'interval');

@@ -26,0 +27,0 @@ if (isColor) {

{
"name": "@mapbox/mapbox-gl-style-spec",
"description": "a specification for mapbox gl styles",
"version": "12.0.0",
"version": "13.0.0",
"author": "Mapbox",

@@ -6,0 +6,0 @@ "keywords": [

// @flow
type ExpressionType = 'data-driven' | 'cross-faded' | 'cross-faded-data-driven' | 'color-ramp' | 'data-constant' | 'constant';
type ExpressionParameters = Array<'zoom' | 'feature' | 'heatmap-density' | 'line-progress'>;
type ExpressionSpecification = {
interpolated: boolean,
parameters: ExpressionParameters
}
export type StylePropertySpecification = {
type: 'number',
'function': boolean,
'property-function': boolean,
'zoom-function': boolean,
'property-type': ExpressionType,
expression?: ExpressionSpecification,
transition: boolean,
default?: number
} | {
type: 'string',
'function': boolean,
'property-function': boolean,
'zoom-function': boolean,
'property-type': ExpressionType,
expression?: ExpressionSpecification,
transition: boolean,
default?: string,

@@ -18,18 +26,18 @@ tokens?: boolean

type: 'boolean',
'function': boolean,
'property-function': boolean,
'zoom-function': boolean,
'property-type': ExpressionType,
expression?: ExpressionSpecification,
transition: boolean,
default?: boolean
} | {
type: 'enum',
'function': boolean,
'property-function': boolean,
'zoom-function': boolean,
'property-type': ExpressionType,
expression?: ExpressionSpecification,
values: {[string]: {}},
transition: boolean,
default?: string
} | {
type: 'color',
'function': boolean,
'property-function': boolean,
'zoom-function': boolean,
'property-type': ExpressionType,
expression?: ExpressionSpecification,
transition: boolean,
default?: string

@@ -39,6 +47,6 @@ } | {

value: 'number',
'function': boolean,
'property-function': boolean,
'zoom-function': boolean,
'property-type': ExpressionType,
expression?: ExpressionSpecification,
length?: number,
transition: boolean,
default?: Array<number>

@@ -48,6 +56,6 @@ } | {

value: 'string',
'function': boolean,
'property-function': boolean,
'zoom-function': boolean,
'property-type': ExpressionType,
expression?: ExpressionSpecification,
length?: number,
transition: boolean,
default?: Array<string>

@@ -54,0 +62,0 @@ };

@@ -7,2 +7,3 @@ // @flow

import { deepUnbundle } from '../util/unbundle_jsonlint';
import { isStateConstant } from '../expression/is_constant';

@@ -22,3 +23,7 @@ export default function validateExpression(options: any) {

if (options.expressionContext === 'property' && options.propertyType === 'layout' &&
(!isStateConstant((expression.value: any)._styleExpression.expression))) {
return [new ValidationError(options.key, options.value, '"feature-state" data expressions are not supported with layout properties.')];
}
return [];
}

@@ -9,2 +9,7 @@

import { unbundle } from '../util/unbundle_jsonlint';
import {
supportsPropertyExpression,
supportsZoomExpression,
supportsInterpolation
} from '../util/properties';

@@ -46,3 +51,3 @@ export default function validateFunction(options) {

if (functionType === 'exponential' && options.valueSpec['function'] === 'piecewise-constant') {
if (functionType === 'exponential' && options.valueSpec.expression && !supportsInterpolation(options.valueSpec)) {
errors.push(new ValidationError(options.key, options.value, 'exponential functions not supported'));

@@ -52,5 +57,5 @@ }

if (options.styleSpec.$version >= 8) {
if (isPropertyFunction && !options.valueSpec['property-function']) {
if (isPropertyFunction && !supportsPropertyExpression(options.valueSpec)) {
errors.push(new ValidationError(options.key, options.value, 'property functions not supported'));
} else if (isZoomFunction && !options.valueSpec['zoom-function'] && options.objectKey !== 'heatmap-color' && options.objectKey !== 'line-gradient') {
} else if (isZoomFunction && !supportsZoomExpression(options.valueSpec)) {
errors.push(new ValidationError(options.key, options.value, 'zoom functions not supported'));

@@ -166,3 +171,3 @@ }

let message = `number expected, ${type} found`;
if (functionValueSpec['property-function'] && functionType === undefined) {
if (supportsPropertyExpression(functionValueSpec) && functionType === undefined) {
message += '\nIf you intended to use a categorical function, specify `"type": "categorical"`.';

@@ -169,0 +174,0 @@ }

@@ -7,2 +7,3 @@

import { unbundle, deepUnbundle } from '../util/unbundle_jsonlint';
import { supportsPropertyExpression } from '../util/properties';

@@ -36,3 +37,3 @@ export default function validateProperty(options, propertyType) {

let tokenMatch;
if (getType(value) === 'string' && valueSpec['property-function'] && !valueSpec.tokens && (tokenMatch = /^{([^}]+)}$/.exec(value))) {
if (getType(value) === 'string' && supportsPropertyExpression(valueSpec) && !valueSpec.tokens && (tokenMatch = /^{([^}]+)}$/.exec(value))) {
return [new ValidationError(

@@ -62,4 +63,5 @@ key, value,

expressionContext: 'property',
propertyType: propertyType,
propertyKey
}));
}

@@ -57,6 +57,6 @@

if (valueSpec.function && isFunction(unbundle(value))) {
if (valueSpec.expression && isFunction(unbundle(value))) {
return validateFunction(options);
} else if (valueSpec.function && isExpression(deepUnbundle(value))) {
} else if (valueSpec.expression && isExpression(deepUnbundle(value))) {
return validateExpression(options);

@@ -63,0 +63,0 @@

Sorry, the diff of this file is too big to display

SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc