UNPKG

maplibre-gl

Version:

BSD licensed community fork of mapbox-gl, a WebGL interactive maps library

329 lines (282 loc) 15.7 kB
import * as fs from 'fs'; import * as properties from '../src/style-spec/util/properties'; import spec from '../src/style-spec/reference/v8.json' assert {type: 'json'}; function unionType(values) { if (Array.isArray(values)) { return values.map(v => JSON.stringify(v)).join(' | '); } else { return Object.keys(values).map(v => JSON.stringify(v)).join(' | '); } } function propertyType(property) { if (typeof property.type === 'function') { return property.type(); } const baseType = (() => { switch (property.type) { case 'string': case 'number': case 'boolean': return property.type; case 'enum': return unionType(property.values); case 'array': { const elementType = propertyType(typeof property.value === 'string' ? {type: property.value, values: property.values} : property.value); if (property.length) { return `[${Array(property.length).fill(elementType).join(', ')}]`; } else { return `Array<${elementType}>`; } } case 'light': return 'LightSpecification'; case 'sources': return '{[_: string]: SourceSpecification}'; case '*': return 'unknown'; default: return `${property.type.slice(0, 1).toUpperCase()}${property.type.slice(1)}Specification`; } })(); if (properties.supportsPropertyExpression(property)) { return `DataDrivenPropertyValueSpecification<${baseType}>`; } else if (properties.supportsZoomExpression(property)) { return `PropertyValueSpecification<${baseType}>`; } else if (property.expression) { return 'ExpressionSpecification'; } else { return baseType; } } function propertyDeclaration(key, property) { return `"${key}"${property.required ? '' : '?'}: ${propertyType(property)}`; } function objectDeclaration(key, properties) { return `export type ${key} = ${objectType(properties, '')};`; } function objectType(properties, indent) { return `{ ${Object.keys(properties) .filter(k => k !== '*') .map(k => ` ${indent}${propertyDeclaration(k, properties[k])}`) .join(',\n')} ${indent}}`; } function sourceTypeName(key) { return key.replace(/source_(.)(.*)/, (_, _1, _2) => `${_1.toUpperCase()}${_2}SourceSpecification`) .replace(/_dem/, 'DEM') .replace(/Geojson/, 'GeoJSON'); } function layerTypeName(key) { return key.split('-').map(k => k.replace(/(.)(.*)/, (_, _1, _2) => `${_1.toUpperCase()}${_2}`)).concat('LayerSpecification').join(''); } function layerType(key) { const layer = spec.layer as any; layer.type = { type: 'enum', values: [key], required: true }; delete layer.ref; delete layer['paint.*']; layer.paint.type = () => { return objectType(spec[`paint_${key}`], ' '); }; layer.layout.type = () => { return objectType(spec[`layout_${key}`], ' '); }; if (key === 'background') { delete layer.source; delete layer['source-layer']; delete layer.filter; } else { layer.source.required = true; } return objectDeclaration(layerTypeName(key), layer); } const layerTypes = Object.keys(spec.layer.type.values); fs.writeFileSync('src/style-spec/types.g.ts', `// Generated code; do not edit. Edit build/generate-style-spec.ts instead. /* eslint-disable */ export type ColorSpecification = string; export type PaddingSpecification = number | number[]; export type FormattedSpecification = string; export type ResolvedImageSpecification = string; export type PromoteIdSpecification = {[_: string]: string} | string; export type ExpressionInputType = string | number | boolean; export type CollatorExpressionSpecification = ['collator', { 'case-sensitive'?: boolean | ExpressionSpecification, 'diacritic-sensitive'?: boolean | ExpressionSpecification, locale?: string | ExpressionSpecification} ]; // collator export type InterpolationSpecification = | ['linear'] | ['exponential', number | ExpressionSpecification] | ['cubic-bezier', number | ExpressionSpecification, number | ExpressionSpecification, number | ExpressionSpecification, number | ExpressionSpecification] export type ExpressionSpecification = // types | ['array', unknown | ExpressionSpecification] // array | ['array', ExpressionInputType | ExpressionSpecification, unknown | ExpressionSpecification] // array | ['array', ExpressionInputType | ExpressionSpecification, number | ExpressionSpecification, unknown | ExpressionSpecification] // array | ['boolean', ...(unknown | ExpressionSpecification)[], unknown | ExpressionSpecification] // boolean | CollatorExpressionSpecification | ['format', ...(string | ['image', ExpressionSpecification] | ExpressionSpecification | {'font-scale'?: number | ExpressionSpecification, 'text-font'?: string[] | ExpressionSpecification, 'text-color': ColorSpecification | ExpressionSpecification})[]] // string | ['image', unknown | ExpressionSpecification] // image | ['literal', unknown] | ['number', unknown | ExpressionSpecification, ...(unknown | ExpressionSpecification)[]] // number | ['number-format', number | ExpressionSpecification, {'locale'?: string | ExpressionSpecification, 'currency'?: string | ExpressionSpecification, 'min-fraction-digits'?: number | ExpressionSpecification, 'max-fraction-digits'?: number | ExpressionSpecification}] // string | ['object', unknown | ExpressionSpecification, ...(unknown | ExpressionSpecification)[]] // object | ['string', unknown | ExpressionSpecification, ...(unknown | ExpressionSpecification)[]] // string | ['to-boolean', unknown | ExpressionSpecification] // boolean | ['to-color', unknown | ExpressionSpecification, ...(unknown | ExpressionSpecification)[]] // color | ['to-number', unknown | ExpressionSpecification, ...(unknown | ExpressionSpecification)[]] // number | ['to-string', unknown | ExpressionSpecification] // string // feature data | ['accumulated'] | ['feature-state', string] | ['geometry-type'] // string | ['id'] | ['line-progress'] // number | ['properties'] // object // lookup | ['at', number | ExpressionSpecification, ExpressionSpecification] | ['get', string | ExpressionSpecification, (Record<string, unknown> | ExpressionSpecification)?] | ['has', string | ExpressionSpecification, (Record<string, unknown> | ExpressionSpecification)?] | ['in', ExpressionInputType | ExpressionSpecification, ExpressionInputType | ExpressionSpecification] | ['index-of', ExpressionInputType | ExpressionSpecification, ExpressionInputType | ExpressionSpecification] // number | ['length', string | ExpressionSpecification] | ['slice', string | ExpressionSpecification, number | ExpressionSpecification] // Decision | ['!', boolean | ExpressionSpecification] // boolean | ['!=', ExpressionInputType | ExpressionSpecification, ExpressionInputType | ExpressionSpecification, CollatorExpressionSpecification?] // boolean | ['<', ExpressionInputType | ExpressionSpecification, ExpressionInputType | ExpressionSpecification, CollatorExpressionSpecification?] // boolean | ['<=', ExpressionInputType | ExpressionSpecification, ExpressionInputType | ExpressionSpecification, CollatorExpressionSpecification?] // boolean | ['==', ExpressionInputType | ExpressionSpecification, ExpressionInputType | ExpressionSpecification, CollatorExpressionSpecification?] // boolean | ['>', ExpressionInputType | ExpressionSpecification, ExpressionInputType | ExpressionSpecification, CollatorExpressionSpecification?] // boolean | ['>=', ExpressionInputType | ExpressionSpecification, ExpressionInputType | ExpressionSpecification, CollatorExpressionSpecification?] // boolean | ['all', ...(boolean | ExpressionSpecification)[]] // boolean | ['any', ...(boolean | ExpressionSpecification)[]] // boolean | ['case', boolean | ExpressionSpecification, ExpressionInputType | ExpressionSpecification, ...(boolean | ExpressionInputType | ExpressionSpecification)[], ExpressionInputType | ExpressionSpecification] | ['coalesce', ExpressionInputType | ExpressionSpecification, ExpressionInputType | ExpressionSpecification, ...(ExpressionInputType | ExpressionSpecification)[]] | ['match', ExpressionInputType | ExpressionSpecification, ExpressionInputType | ExpressionInputType[], ExpressionInputType | ExpressionSpecification, ...(ExpressionInputType | ExpressionInputType[] | ExpressionSpecification)[], // repeated as above ExpressionInputType] | ['within', unknown | ExpressionSpecification] // Ramps, scales, curves | ['interpolate', InterpolationSpecification, number | ExpressionSpecification, number | ExpressionSpecification, ExpressionInputType | ExpressionSpecification, ...(number | ExpressionInputType | ExpressionSpecification)[]] | ['interpolate-hcl', InterpolationSpecification, number | ExpressionSpecification, number | ExpressionSpecification, ExpressionInputType | ExpressionSpecification, ...(number | ColorSpecification | ExpressionSpecification)[]] | ['interpolate-lab', InterpolationSpecification, number | ExpressionSpecification, number | ExpressionSpecification, ExpressionInputType | ExpressionSpecification, ...(number | ColorSpecification | ExpressionSpecification)[]] | ['step', number | ExpressionSpecification, number | ExpressionSpecification, ExpressionInputType | ExpressionSpecification, ...(number | ExpressionInputType | ExpressionSpecification)[]] // Variable binding | ['let', string, ExpressionInputType | ExpressionSpecification, ...(string | ExpressionInputType | ExpressionSpecification)[]] | ['var', string] // String | ['concat', ExpressionInputType | ExpressionSpecification, ExpressionInputType | ExpressionSpecification, ...(ExpressionInputType | ExpressionSpecification)[]] // string | ['downcase', string | ExpressionSpecification] // string | ['is-supported-script', string | ExpressionSpecification] // boolean | ['resolved-locale', CollatorExpressionSpecification] // string | ['upcase', string | ExpressionSpecification] // string // Color | ['rgb', number | ExpressionSpecification, number | ExpressionSpecification, number | ExpressionSpecification] // color | ['rgba', number | ExpressionSpecification, number | ExpressionSpecification, number | ExpressionSpecification, number | ExpressionSpecification] | ['to-rgba', ColorSpecification | ExpressionSpecification] // Math | ['-', number | ExpressionSpecification, (number | ExpressionSpecification)?] // number | ['*', number | ExpressionSpecification, number | ExpressionSpecification, ...(number | ExpressionSpecification)[]] // number | ['/', number | ExpressionSpecification, number | ExpressionSpecification] // number | ['%', number | ExpressionSpecification, number | ExpressionSpecification] // number | ['^', number | ExpressionSpecification, number | ExpressionSpecification] // number | ['+', number | ExpressionSpecification, number | ExpressionSpecification, ...(number | ExpressionSpecification)[]] // number | ['abs', number | ExpressionSpecification] // number | ['acos', number | ExpressionSpecification] // number | ['asin', number | ExpressionSpecification] // number | ['atan', number | ExpressionSpecification] // number | ['ceil', number | ExpressionSpecification] // number | ['cos', number | ExpressionSpecification] // number | ['distance', Record<string, unknown> | ExpressionSpecification] // number | ['ExpressionSpecification'] // number | ['floor', number | ExpressionSpecification] // number | ['ln', number | ExpressionSpecification] // number | ['ln2'] // number | ['log10', number | ExpressionSpecification] // number | ['log2', number | ExpressionSpecification] // number | ['max', number | ExpressionSpecification, ...(number | ExpressionSpecification)[]] // number | ['min', number | ExpressionSpecification, ...(number | ExpressionSpecification)[]] // number | ['pi'] // number | ['round', number | ExpressionSpecification] // number | ['sin', number | ExpressionSpecification] // number | ['sqrt', number | ExpressionSpecification] // number | ['tan', number | ExpressionSpecification] // number // Zoom | ['zoom'] // number // Heatmap | ['heatmap-density'] // number export type ExpressionFilterSpecification = boolean | ExpressionSpecification export type LegacyFilterSpecification = // Existential | ['has', string] | ['!has', string] // Comparison | ['==', string, string | number | boolean] | ['!=', string, string | number | boolean] | ['>', string, string | number | boolean] | ['>=', string, string | number | boolean] | ['<', string, string | number | boolean] | ['<=', string, string | number | boolean] // Set membership | ['in', string, ...(string | number | boolean)[]] | ['!in', string, ...(string | number | boolean)[]] // Combining | ['all', ...LegacyFilterSpecification[]] | ['any', ...LegacyFilterSpecification[]] | ['none', ...LegacyFilterSpecification[]] export type FilterSpecification = ExpressionFilterSpecification | LegacyFilterSpecification export type TransitionSpecification = { duration?: number, delay?: number }; // Note: doesn't capture interpolatable vs. non-interpolatable types. export type CameraFunctionSpecification<T> = { type: 'exponential', stops: Array<[number, T]> } | { type: 'interval', stops: Array<[number, T]> }; export type SourceFunctionSpecification<T> = { type: 'exponential', stops: Array<[number, T]>, property: string, default?: T } | { type: 'interval', stops: Array<[number, T]>, property: string, default?: T } | { type: 'categorical', stops: Array<[string | number | boolean, T]>, property: string, default?: T } | { type: 'identity', property: string, default?: T }; export type CompositeFunctionSpecification<T> = { type: 'exponential', stops: Array<[{zoom: number, value: number}, T]>, property: string, default?: T } | { type: 'interval', stops: Array<[{zoom: number, value: number}, T]>, property: string, default?: T } | { type: 'categorical', stops: Array<[{zoom: number, value: string | number | boolean}, T]>, property: string, default?: T }; export type PropertyValueSpecification<T> = T | CameraFunctionSpecification<T> | ExpressionSpecification; export type DataDrivenPropertyValueSpecification<T> = T | CameraFunctionSpecification<T> | SourceFunctionSpecification<T> | CompositeFunctionSpecification<T> | ExpressionSpecification; ${objectDeclaration('StyleSpecification', spec.$root)} ${objectDeclaration('LightSpecification', spec.light)} ${objectDeclaration('TerrainSpecification', spec.terrain)} ${spec.source.map(key => objectDeclaration(sourceTypeName(key), spec[key])).join('\n\n')} export type SourceSpecification = ${spec.source.map(key => ` | ${sourceTypeName(key)}`).join('\n')} ${layerTypes.map(key => layerType(key)).join('\n\n')} export type LayerSpecification = ${layerTypes.map(key => ` | ${layerTypeName(key)}`).join('\n')}; `);