mirror of
https://github.com/maputnik/editor.git
synced 2026-07-01 11:37:26 +00:00
More migration of components
This commit is contained in:
Generated
+7
@@ -70,6 +70,7 @@
|
|||||||
"@types/codemirror": "^5.60.15",
|
"@types/codemirror": "^5.60.15",
|
||||||
"@types/color": "^3.0.6",
|
"@types/color": "^3.0.6",
|
||||||
"@types/cors": "^2.8.17",
|
"@types/cors": "^2.8.17",
|
||||||
|
"@types/file-saver": "^2.0.7",
|
||||||
"@types/lodash.capitalize": "^4.2.9",
|
"@types/lodash.capitalize": "^4.2.9",
|
||||||
"@types/lodash.isequal": "^4.5.8",
|
"@types/lodash.isequal": "^4.5.8",
|
||||||
"@types/lodash.throttle": "^4.1.9",
|
"@types/lodash.throttle": "^4.1.9",
|
||||||
@@ -4711,6 +4712,12 @@
|
|||||||
"@types/send": "*"
|
"@types/send": "*"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"node_modules/@types/file-saver": {
|
||||||
|
"version": "2.0.7",
|
||||||
|
"resolved": "https://registry.npmjs.org/@types/file-saver/-/file-saver-2.0.7.tgz",
|
||||||
|
"integrity": "sha512-dNKVfHd/jk0SkR/exKGj2ggkB45MAkzvWCaqLUUgkyjITkGNzH8H+yUwr+BLJUBjZOe9w8X3wgmXhZDRg1ED6A==",
|
||||||
|
"dev": true
|
||||||
|
},
|
||||||
"node_modules/@types/find-cache-dir": {
|
"node_modules/@types/find-cache-dir": {
|
||||||
"version": "3.2.1",
|
"version": "3.2.1",
|
||||||
"resolved": "https://registry.npmjs.org/@types/find-cache-dir/-/find-cache-dir-3.2.1.tgz",
|
"resolved": "https://registry.npmjs.org/@types/find-cache-dir/-/find-cache-dir-3.2.1.tgz",
|
||||||
|
|||||||
@@ -99,6 +99,7 @@
|
|||||||
"@types/codemirror": "^5.60.15",
|
"@types/codemirror": "^5.60.15",
|
||||||
"@types/color": "^3.0.6",
|
"@types/color": "^3.0.6",
|
||||||
"@types/cors": "^2.8.17",
|
"@types/cors": "^2.8.17",
|
||||||
|
"@types/file-saver": "^2.0.7",
|
||||||
"@types/lodash.capitalize": "^4.2.9",
|
"@types/lodash.capitalize": "^4.2.9",
|
||||||
"@types/lodash.isequal": "^4.5.8",
|
"@types/lodash.isequal": "^4.5.8",
|
||||||
"@types/lodash.throttle": "^4.1.9",
|
"@types/lodash.throttle": "^4.1.9",
|
||||||
|
|||||||
@@ -1,20 +0,0 @@
|
|||||||
import React from 'react'
|
|
||||||
import PropTypes from 'prop-types'
|
|
||||||
import Block from './Block'
|
|
||||||
import InputCheckbox from './InputCheckbox'
|
|
||||||
|
|
||||||
|
|
||||||
export default class FieldCheckbox extends React.Component {
|
|
||||||
static propTypes = {
|
|
||||||
...InputCheckbox.propTypes,
|
|
||||||
}
|
|
||||||
|
|
||||||
render() {
|
|
||||||
const {props} = this;
|
|
||||||
|
|
||||||
return <Block label={this.props.label}>
|
|
||||||
<InputCheckbox {...props} />
|
|
||||||
</Block>
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@@ -0,0 +1,18 @@
|
|||||||
|
import React from 'react'
|
||||||
|
import Block from './Block'
|
||||||
|
import InputCheckbox, {InputCheckboxProps} from './InputCheckbox'
|
||||||
|
|
||||||
|
|
||||||
|
type FieldCheckboxProps = InputCheckboxProps & {
|
||||||
|
label?: string;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
export default class FieldCheckbox extends React.Component<FieldCheckboxProps> {
|
||||||
|
render() {
|
||||||
|
return <Block label={this.props.label}>
|
||||||
|
<InputCheckbox {...this.props} />
|
||||||
|
</Block>
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@@ -1,21 +0,0 @@
|
|||||||
import React from 'react'
|
|
||||||
import PropTypes from 'prop-types'
|
|
||||||
import Block from './Block'
|
|
||||||
import InputDynamicArray from './InputDynamicArray'
|
|
||||||
import Fieldset from './Fieldset'
|
|
||||||
|
|
||||||
export default class FieldDynamicArray extends React.Component {
|
|
||||||
static propTypes = {
|
|
||||||
...InputDynamicArray.propTypes,
|
|
||||||
name: PropTypes.string,
|
|
||||||
}
|
|
||||||
|
|
||||||
render() {
|
|
||||||
const {props} = this;
|
|
||||||
|
|
||||||
return <Fieldset label={props.label}>
|
|
||||||
<InputDynamicArray {...props} />
|
|
||||||
</Fieldset>
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@@ -0,0 +1,16 @@
|
|||||||
|
import React from 'react'
|
||||||
|
import InputDynamicArray, {FieldDynamicArrayProps as InputDynamicArrayProps} from './InputDynamicArray'
|
||||||
|
import Fieldset from './Fieldset'
|
||||||
|
|
||||||
|
type FieldDynamicArrayProps = InputDynamicArrayProps & {
|
||||||
|
name?: string
|
||||||
|
};
|
||||||
|
|
||||||
|
export default class FieldDynamicArray extends React.Component<FieldDynamicArrayProps> {
|
||||||
|
render() {
|
||||||
|
return <Fieldset label={this.props.label}>
|
||||||
|
<InputDynamicArray {...this.props} />
|
||||||
|
</Fieldset>
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@@ -1,19 +1,18 @@
|
|||||||
import React from 'react'
|
import React from 'react'
|
||||||
import PropTypes from 'prop-types'
|
|
||||||
|
|
||||||
import {latest} from '@maplibre/maplibre-gl-style-spec'
|
import {latest} from '@maplibre/maplibre-gl-style-spec'
|
||||||
import Block from './Block'
|
import Block from './Block'
|
||||||
import InputAutocomplete from './InputAutocomplete'
|
import InputAutocomplete from './InputAutocomplete'
|
||||||
|
|
||||||
export default class FieldSource extends React.Component {
|
type FieldSourceProps = {
|
||||||
static propTypes = {
|
value?: string
|
||||||
value: PropTypes.string,
|
wdKey?: string
|
||||||
wdKey: PropTypes.string,
|
onChange?(...args: unknown[]): unknown
|
||||||
onChange: PropTypes.func,
|
sourceIds?: unknown[]
|
||||||
sourceIds: PropTypes.array,
|
error?: unknown[]
|
||||||
error: PropTypes.object,
|
};
|
||||||
}
|
|
||||||
|
|
||||||
|
export default class FieldSource extends React.Component<FieldSourceProps> {
|
||||||
static defaultProps = {
|
static defaultProps = {
|
||||||
onChange: () => {},
|
onChange: () => {},
|
||||||
sourceIds: [],
|
sourceIds: [],
|
||||||
@@ -29,7 +28,7 @@ export default class FieldSource extends React.Component {
|
|||||||
<InputAutocomplete
|
<InputAutocomplete
|
||||||
value={this.props.value}
|
value={this.props.value}
|
||||||
onChange={this.props.onChange}
|
onChange={this.props.onChange}
|
||||||
options={this.props.sourceIds.map(src => [src, src])}
|
options={this.props.sourceIds?.map(src => [src, src])}
|
||||||
/>
|
/>
|
||||||
</Block>
|
</Block>
|
||||||
}
|
}
|
||||||
@@ -1,18 +1,17 @@
|
|||||||
import React from 'react'
|
import React from 'react'
|
||||||
import PropTypes from 'prop-types'
|
|
||||||
|
|
||||||
import {latest} from '@maplibre/maplibre-gl-style-spec'
|
import {latest} from '@maplibre/maplibre-gl-style-spec'
|
||||||
import Block from './Block'
|
import Block from './Block'
|
||||||
import InputAutocomplete from './InputAutocomplete'
|
import InputAutocomplete from './InputAutocomplete'
|
||||||
|
|
||||||
export default class FieldSourceLayer extends React.Component {
|
type FieldSourceLayerProps = {
|
||||||
static propTypes = {
|
value?: string
|
||||||
value: PropTypes.string,
|
onChange?(...args: unknown[]): unknown
|
||||||
onChange: PropTypes.func,
|
sourceLayerIds?: unknown[]
|
||||||
sourceLayerIds: PropTypes.array,
|
isFixed?: boolean
|
||||||
isFixed: PropTypes.bool,
|
};
|
||||||
}
|
|
||||||
|
|
||||||
|
export default class FieldSourceLayer extends React.Component<FieldSourceLayerProps> {
|
||||||
static defaultProps = {
|
static defaultProps = {
|
||||||
onChange: () => {},
|
onChange: () => {},
|
||||||
sourceLayerIds: [],
|
sourceLayerIds: [],
|
||||||
@@ -27,7 +26,7 @@ export default class FieldSourceLayer extends React.Component {
|
|||||||
keepMenuWithinWindowBounds={!!this.props.isFixed}
|
keepMenuWithinWindowBounds={!!this.props.isFixed}
|
||||||
value={this.props.value}
|
value={this.props.value}
|
||||||
onChange={this.props.onChange}
|
onChange={this.props.onChange}
|
||||||
options={this.props.sourceLayerIds.map(l => [l, l])}
|
options={this.props.sourceLayerIds?.map(l => [l, l])}
|
||||||
/>
|
/>
|
||||||
</Block>
|
</Block>
|
||||||
}
|
}
|
||||||
@@ -12,7 +12,7 @@ import InputUrl from './InputUrl'
|
|||||||
|
|
||||||
export type FieldDynamicArrayProps = {
|
export type FieldDynamicArrayProps = {
|
||||||
value?: (string | number)[]
|
value?: (string | number)[]
|
||||||
type?: 'url' | 'number' | 'enum'
|
type?: 'url' | 'number' | 'enum' | 'string'
|
||||||
default?: (string | number)[]
|
default?: (string | number)[]
|
||||||
onChange?(...args: unknown[]): unknown
|
onChange?(...args: unknown[]): unknown
|
||||||
style?: object
|
style?: object
|
||||||
|
|||||||
@@ -17,7 +17,7 @@ export type InputJsonProps = {
|
|||||||
onChange?(...args: unknown[]): unknown
|
onChange?(...args: unknown[]): unknown
|
||||||
lineNumbers?: boolean
|
lineNumbers?: boolean
|
||||||
lineWrapping?: boolean
|
lineWrapping?: boolean
|
||||||
getValue(data: any): string
|
getValue?(data: any): string
|
||||||
gutters?: string[]
|
gutters?: string[]
|
||||||
className?: string
|
className?: string
|
||||||
onFocus?(...args: unknown[]): unknown
|
onFocus?(...args: unknown[]): unknown
|
||||||
@@ -58,13 +58,13 @@ export default class InputJson extends React.Component<InputJsonProps, InputJson
|
|||||||
this.state = {
|
this.state = {
|
||||||
isEditing: false,
|
isEditing: false,
|
||||||
showMessage: false,
|
showMessage: false,
|
||||||
prevValue: this.props.getValue(this.props.layer),
|
prevValue: this.props.getValue!(this.props.layer),
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
componentDidMount () {
|
componentDidMount () {
|
||||||
this._doc = CodeMirror(this._el!, {
|
this._doc = CodeMirror(this._el!, {
|
||||||
value: this.props.getValue(this.props.layer),
|
value: this.props.getValue!(this.props.layer),
|
||||||
mode: this.props.mode || {
|
mode: this.props.mode || {
|
||||||
name: "mgl",
|
name: "mgl",
|
||||||
},
|
},
|
||||||
@@ -117,7 +117,7 @@ export default class InputJson extends React.Component<InputJsonProps, InputJson
|
|||||||
if (!this.state.isEditing && prevProps.layer !== this.props.layer) {
|
if (!this.state.isEditing && prevProps.layer !== this.props.layer) {
|
||||||
this._cancelNextChange = true;
|
this._cancelNextChange = true;
|
||||||
this._doc!.setValue(
|
this._doc!.setValue(
|
||||||
this.props.getValue(this.props.layer),
|
this.props.getValue!(this.props.layer),
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,29 +1,32 @@
|
|||||||
import React from 'react'
|
import React from 'react'
|
||||||
import PropTypes from 'prop-types'
|
|
||||||
|
|
||||||
import {latest} from '@maplibre/maplibre-gl-style-spec'
|
|
||||||
import InputButton from './InputButton'
|
import InputButton from './InputButton'
|
||||||
import Modal from './Modal'
|
import Modal from './Modal'
|
||||||
|
|
||||||
import FieldType from './FieldType'
|
import FieldType from './FieldType'
|
||||||
import FieldId from './FieldId'
|
import FieldId from './FieldId'
|
||||||
import FieldSource from './FieldSource'
|
import FieldSource from './FieldSource'
|
||||||
import FieldSourceLayer from './FieldSourceLayer'
|
import FieldSourceLayer from './FieldSourceLayer'
|
||||||
|
|
||||||
export default class ModalAdd extends React.Component {
|
type ModalAddProps = {
|
||||||
static propTypes = {
|
layers: unknown[]
|
||||||
layers: PropTypes.array.isRequired,
|
onLayersChange(...args: unknown[]): unknown
|
||||||
onLayersChange: PropTypes.func.isRequired,
|
isOpen: boolean
|
||||||
isOpen: PropTypes.bool.isRequired,
|
onOpenToggle(...args: unknown[]): unknown
|
||||||
onOpenToggle: PropTypes.func.isRequired,
|
|
||||||
|
|
||||||
// A dict of source id's and the available source layers
|
// A dict of source id's and the available source layers
|
||||||
sources: PropTypes.object.isRequired,
|
sources: any
|
||||||
}
|
};
|
||||||
|
|
||||||
|
type ModalAddState = {
|
||||||
|
type: string
|
||||||
|
id: string
|
||||||
|
source?: string
|
||||||
|
'source-layer'?: string
|
||||||
|
};
|
||||||
|
|
||||||
|
export default class ModalAdd extends React.Component<ModalAddProps, ModalAddState> {
|
||||||
addLayer = () => {
|
addLayer = () => {
|
||||||
const changedLayers = this.props.layers.slice(0)
|
const changedLayers = this.props.layers.slice(0)
|
||||||
const layer = {
|
const layer: ModalAddState = {
|
||||||
id: this.state.id,
|
id: this.state.id,
|
||||||
type: this.state.type,
|
type: this.state.type,
|
||||||
}
|
}
|
||||||
@@ -41,20 +44,21 @@ export default class ModalAdd extends React.Component {
|
|||||||
this.props.onOpenToggle(false)
|
this.props.onOpenToggle(false)
|
||||||
}
|
}
|
||||||
|
|
||||||
constructor(props) {
|
constructor(props: ModalAddProps) {
|
||||||
super(props)
|
super(props)
|
||||||
this.state = {
|
const state: ModalAddState = {
|
||||||
type: 'fill',
|
type: 'fill',
|
||||||
id: '',
|
id: '',
|
||||||
}
|
}
|
||||||
|
|
||||||
if(props.sources.length > 0) {
|
if(props.sources.length > 0) {
|
||||||
this.state.source = Object.keys(this.props.sources)[0]
|
state.source = Object.keys(this.props.sources)[0];
|
||||||
this.state['source-layer'] = this.props.sources[this.state.source][0]
|
state['source-layer'] = this.props.sources[state.source as keyof ModalAddProps["sources"]][0]
|
||||||
}
|
}
|
||||||
|
this.state = state;
|
||||||
}
|
}
|
||||||
|
|
||||||
componentDidUpdate(prevProps, prevState) {
|
componentDidUpdate(_prevProps: ModalAddProps, prevState: ModalAddState) {
|
||||||
// Check if source is valid for new type
|
// Check if source is valid for new type
|
||||||
const oldType = prevState.type;
|
const oldType = prevState.type;
|
||||||
const newType = this.state.type;
|
const newType = this.state.type;
|
||||||
@@ -67,9 +71,9 @@ export default class ModalAdd extends React.Component {
|
|||||||
oldType !== newType
|
oldType !== newType
|
||||||
&& prevState.source !== ""
|
&& prevState.source !== ""
|
||||||
// Was a valid source previously
|
// Was a valid source previously
|
||||||
&& availableSourcesOld.indexOf(prevState.source) > -1
|
&& availableSourcesOld.indexOf(prevState.source!) > -1
|
||||||
// And is not a valid source now
|
// And is not a valid source now
|
||||||
&& availableSourcesNew.indexOf(this.state.source) < 0
|
&& availableSourcesNew.indexOf(this.state.source!) < 0
|
||||||
) {
|
) {
|
||||||
// Clear the source
|
// Clear the source
|
||||||
this.setState({
|
this.setState({
|
||||||
@@ -78,12 +82,12 @@ export default class ModalAdd extends React.Component {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
getLayersForSource(source) {
|
getLayersForSource(source: string) {
|
||||||
const sourceObj = this.props.sources[source] || {};
|
const sourceObj = this.props.sources[source] || {};
|
||||||
return sourceObj.layers || [];
|
return sourceObj.layers || [];
|
||||||
}
|
}
|
||||||
|
|
||||||
getSources(type) {
|
getSources(type: string) {
|
||||||
const sources = [];
|
const sources = [];
|
||||||
|
|
||||||
const types = {
|
const types = {
|
||||||
@@ -108,8 +112,9 @@ export default class ModalAdd extends React.Component {
|
|||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
|
||||||
for(let [key, val] of Object.entries(this.props.sources)) {
|
for(let [key, val] of Object.entries(this.props.sources) as any) {
|
||||||
if(types[val.type] && types[val.type].indexOf(type) > -1) {
|
const valType = val.type as keyof typeof types;
|
||||||
|
if(types[valType] && types[valType].indexOf(type) > -1) {
|
||||||
sources.push(key);
|
sources.push(key);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -120,7 +125,7 @@ export default class ModalAdd extends React.Component {
|
|||||||
|
|
||||||
render() {
|
render() {
|
||||||
const sources = this.getSources(this.state.type);
|
const sources = this.getSources(this.state.type);
|
||||||
const layers = this.getLayersForSource(this.state.source);
|
const layers = this.getLayersForSource(this.state.source!);
|
||||||
|
|
||||||
return <Modal
|
return <Modal
|
||||||
isOpen={this.props.isOpen}
|
isOpen={this.props.isOpen}
|
||||||
@@ -131,25 +136,23 @@ export default class ModalAdd extends React.Component {
|
|||||||
>
|
>
|
||||||
<div className="maputnik-add-layer">
|
<div className="maputnik-add-layer">
|
||||||
<FieldId
|
<FieldId
|
||||||
label="ID"
|
|
||||||
fieldSpec={latest.layer.id}
|
|
||||||
value={this.state.id}
|
value={this.state.id}
|
||||||
wdKey="add-layer.layer-id"
|
wdKey="add-layer.layer-id"
|
||||||
onChange={v => {
|
onChange={(v: string) => {
|
||||||
this.setState({ id: v })
|
this.setState({ id: v })
|
||||||
}}
|
}}
|
||||||
/>
|
/>
|
||||||
<FieldType
|
<FieldType
|
||||||
value={this.state.type}
|
value={this.state.type}
|
||||||
wdKey="add-layer.layer-type"
|
wdKey="add-layer.layer-type"
|
||||||
onChange={v => this.setState({ type: v })}
|
onChange={(v: string) => this.setState({ type: v })}
|
||||||
/>
|
/>
|
||||||
{this.state.type !== 'background' &&
|
{this.state.type !== 'background' &&
|
||||||
<FieldSource
|
<FieldSource
|
||||||
sourceIds={sources}
|
sourceIds={sources}
|
||||||
wdKey="add-layer.layer-source-block"
|
wdKey="add-layer.layer-source-block"
|
||||||
value={this.state.source}
|
value={this.state.source}
|
||||||
onChange={v => this.setState({ source: v })}
|
onChange={(v: string) => this.setState({ source: v })}
|
||||||
/>
|
/>
|
||||||
}
|
}
|
||||||
{['background', 'raster', 'hillshade', 'heatmap'].indexOf(this.state.type) < 0 &&
|
{['background', 'raster', 'hillshade', 'heatmap'].indexOf(this.state.type) < 0 &&
|
||||||
@@ -157,7 +160,7 @@ export default class ModalAdd extends React.Component {
|
|||||||
isFixed={true}
|
isFixed={true}
|
||||||
sourceLayerIds={layers}
|
sourceLayerIds={layers}
|
||||||
value={this.state['source-layer']}
|
value={this.state['source-layer']}
|
||||||
onChange={v => this.setState({ 'source-layer': v })}
|
onChange={(v: string) => this.setState({ 'source-layer': v })}
|
||||||
/>
|
/>
|
||||||
}
|
}
|
||||||
<InputButton
|
<InputButton
|
||||||
@@ -1,21 +1,27 @@
|
|||||||
import React from 'react'
|
import React from 'react'
|
||||||
import PropTypes from 'prop-types'
|
|
||||||
|
|
||||||
import Modal from './Modal'
|
import Modal from './Modal'
|
||||||
|
|
||||||
|
|
||||||
export default class ModalDebug extends React.Component {
|
type ModalDebugProps = {
|
||||||
static propTypes = {
|
isOpen: boolean
|
||||||
isOpen: PropTypes.bool.isRequired,
|
renderer: string
|
||||||
renderer: PropTypes.string.isRequired,
|
onChangeMaboxGlDebug(...args: unknown[]): unknown
|
||||||
onChangeMaboxGlDebug: PropTypes.func.isRequired,
|
onChangeOpenlayersDebug(...args: unknown[]): unknown
|
||||||
onChangeOpenlayersDebug: PropTypes.func.isRequired,
|
onOpenToggle(...args: unknown[]): unknown
|
||||||
onOpenToggle: PropTypes.func.isRequired,
|
maplibreGlDebugOptions?: object
|
||||||
maplibreGlDebugOptions: PropTypes.object,
|
openlayersDebugOptions?: object
|
||||||
openlayersDebugOptions: PropTypes.object,
|
mapView: {
|
||||||
mapView: PropTypes.object,
|
zoom: number
|
||||||
|
center: {
|
||||||
|
lng: string
|
||||||
|
lat: string
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
export default class ModalDebug extends React.Component<ModalDebugProps> {
|
||||||
render() {
|
render() {
|
||||||
const {mapView} = this.props;
|
const {mapView} = this.props;
|
||||||
|
|
||||||
@@ -33,10 +39,10 @@ export default class ModalDebug extends React.Component {
|
|||||||
<h1>Options</h1>
|
<h1>Options</h1>
|
||||||
{this.props.renderer === 'mlgljs' &&
|
{this.props.renderer === 'mlgljs' &&
|
||||||
<ul>
|
<ul>
|
||||||
{Object.entries(this.props.maplibreGlDebugOptions).map(([key, val]) => {
|
{Object.entries(this.props.maplibreGlDebugOptions!).map(([key, val]) => {
|
||||||
return <li key={key}>
|
return <li key={key}>
|
||||||
<label>
|
<label>
|
||||||
<input type="checkbox" checked={val} onClick={(e) => this.props.onChangeMaboxGlDebug(key, e.target.checked)} /> {key}
|
<input type="checkbox" checked={val} onChange={(e) => this.props.onChangeMaboxGlDebug(key, e.target.checked)} /> {key}
|
||||||
</label>
|
</label>
|
||||||
</li>
|
</li>
|
||||||
})}
|
})}
|
||||||
@@ -44,10 +50,10 @@ export default class ModalDebug extends React.Component {
|
|||||||
}
|
}
|
||||||
{this.props.renderer === 'ol' &&
|
{this.props.renderer === 'ol' &&
|
||||||
<ul>
|
<ul>
|
||||||
{Object.entries(this.props.openlayersDebugOptions).map(([key, val]) => {
|
{Object.entries(this.props.openlayersDebugOptions!).map(([key, val]) => {
|
||||||
return <li key={key}>
|
return <li key={key}>
|
||||||
<label>
|
<label>
|
||||||
<input type="checkbox" checked={val} onClick={(e) => this.props.onChangeOpenlayersDebug(key, e.target.checked)} /> {key}
|
<input type="checkbox" checked={val} onChange={(e) => this.props.onChangeOpenlayersDebug(key, e.target.checked)} /> {key}
|
||||||
</label>
|
</label>
|
||||||
</li>
|
</li>
|
||||||
})}
|
})}
|
||||||
@@ -1,13 +1,13 @@
|
|||||||
import React from 'react'
|
import React from 'react'
|
||||||
import PropTypes from 'prop-types'
|
|
||||||
import Slugify from 'slugify'
|
import Slugify from 'slugify'
|
||||||
import {saveAs} from 'file-saver'
|
import {saveAs} from 'file-saver'
|
||||||
import {version} from 'maplibre-gl'
|
import {version} from 'maplibre-gl/package.json'
|
||||||
import {format} from '@maplibre/maplibre-gl-style-spec'
|
import {StyleSpecification, format} from '@maplibre/maplibre-gl-style-spec'
|
||||||
|
import {MdFileDownload} from 'react-icons/md'
|
||||||
|
|
||||||
import FieldString from './FieldString'
|
import FieldString from './FieldString'
|
||||||
import InputButton from './InputButton'
|
import InputButton from './InputButton'
|
||||||
import Modal from './Modal'
|
import Modal from './Modal'
|
||||||
import {MdFileDownload} from 'react-icons/md'
|
|
||||||
import style from '../libs/style'
|
import style from '../libs/style'
|
||||||
import fieldSpecAdditional from '../libs/field-spec-additional'
|
import fieldSpecAdditional from '../libs/field-spec-additional'
|
||||||
|
|
||||||
@@ -15,17 +15,15 @@ import fieldSpecAdditional from '../libs/field-spec-additional'
|
|||||||
const MAPLIBRE_GL_VERSION = version;
|
const MAPLIBRE_GL_VERSION = version;
|
||||||
|
|
||||||
|
|
||||||
export default class ModalExport extends React.Component {
|
type ModalExportProps = {
|
||||||
static propTypes = {
|
mapStyle: StyleSpecification & { id: string }
|
||||||
mapStyle: PropTypes.object.isRequired,
|
onStyleChanged(...args: unknown[]): unknown
|
||||||
onStyleChanged: PropTypes.func.isRequired,
|
isOpen: boolean
|
||||||
isOpen: PropTypes.bool.isRequired,
|
onOpenToggle(...args: unknown[]): unknown
|
||||||
onOpenToggle: PropTypes.func.isRequired,
|
};
|
||||||
}
|
|
||||||
|
|
||||||
constructor(props) {
|
|
||||||
super(props);
|
export default class ModalExport extends React.Component<ModalExportProps> {
|
||||||
}
|
|
||||||
|
|
||||||
tokenizedStyle () {
|
tokenizedStyle () {
|
||||||
return format(
|
return format(
|
||||||
@@ -88,11 +86,11 @@ export default class ModalExport extends React.Component {
|
|||||||
saveAs(blob, exportName + ".json");
|
saveAs(blob, exportName + ".json");
|
||||||
}
|
}
|
||||||
|
|
||||||
changeMetadataProperty(property, value) {
|
changeMetadataProperty(property: string, value: any) {
|
||||||
const changedStyle = {
|
const changedStyle = {
|
||||||
...this.props.mapStyle,
|
...this.props.mapStyle,
|
||||||
metadata: {
|
metadata: {
|
||||||
...this.props.mapStyle.metadata,
|
...this.props.mapStyle.metadata as any,
|
||||||
[property]: value
|
[property]: value
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -119,13 +117,13 @@ export default class ModalExport extends React.Component {
|
|||||||
<FieldString
|
<FieldString
|
||||||
label={fieldSpecAdditional.maputnik.maptiler_access_token.label}
|
label={fieldSpecAdditional.maputnik.maptiler_access_token.label}
|
||||||
fieldSpec={fieldSpecAdditional.maputnik.maptiler_access_token}
|
fieldSpec={fieldSpecAdditional.maputnik.maptiler_access_token}
|
||||||
value={(this.props.mapStyle.metadata || {})['maputnik:openmaptiles_access_token']}
|
value={(this.props.mapStyle.metadata || {} as any)['maputnik:openmaptiles_access_token']}
|
||||||
onChange={this.changeMetadataProperty.bind(this, "maputnik:openmaptiles_access_token")}
|
onChange={this.changeMetadataProperty.bind(this, "maputnik:openmaptiles_access_token")}
|
||||||
/>
|
/>
|
||||||
<FieldString
|
<FieldString
|
||||||
label={fieldSpecAdditional.maputnik.thunderforest_access_token.label}
|
label={fieldSpecAdditional.maputnik.thunderforest_access_token.label}
|
||||||
fieldSpec={fieldSpecAdditional.maputnik.thunderforest_access_token}
|
fieldSpec={fieldSpecAdditional.maputnik.thunderforest_access_token}
|
||||||
value={(this.props.mapStyle.metadata || {})['maputnik:thunderforest_access_token']}
|
value={(this.props.mapStyle.metadata || {} as any)['maputnik:thunderforest_access_token']}
|
||||||
onChange={this.changeMetadataProperty.bind(this, "maputnik:thunderforest_access_token")}
|
onChange={this.changeMetadataProperty.bind(this, "maputnik:thunderforest_access_token")}
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
@@ -1,12 +1,10 @@
|
|||||||
import React from 'react'
|
import React from 'react'
|
||||||
import PropTypes from 'prop-types'
|
import {GeoJSONSourceSpecification, RasterDEMSourceSpecification, RasterSourceSpecification, SourceSpecification, StyleSpecification, VectorSourceSpecification, latest} from '@maplibre/maplibre-gl-style-spec'
|
||||||
import {latest} from '@maplibre/maplibre-gl-style-spec'
|
|
||||||
import Modal from './Modal'
|
import Modal from './Modal'
|
||||||
import InputButton from './InputButton'
|
import InputButton from './InputButton'
|
||||||
import Block from './Block'
|
|
||||||
import FieldString from './FieldString'
|
import FieldString from './FieldString'
|
||||||
import FieldSelect from './FieldSelect'
|
import FieldSelect from './FieldSelect'
|
||||||
import ModalSourcesTypeEditor from './ModalSourcesTypeEditor'
|
import ModalSourcesTypeEditor, { EditorMode } from './ModalSourcesTypeEditor'
|
||||||
|
|
||||||
import style from '../libs/style'
|
import style from '../libs/style'
|
||||||
import { deleteSource, addSource, changeSource } from '../libs/source'
|
import { deleteSource, addSource, changeSource } from '../libs/source'
|
||||||
@@ -14,14 +12,14 @@ import publicSources from '../config/tilesets.json'
|
|||||||
|
|
||||||
import {MdAddCircleOutline, MdDelete} from 'react-icons/md'
|
import {MdAddCircleOutline, MdDelete} from 'react-icons/md'
|
||||||
|
|
||||||
class PublicSource extends React.Component {
|
type PublicSourceProps = {
|
||||||
static propTypes = {
|
id: string
|
||||||
id: PropTypes.string.isRequired,
|
type: string
|
||||||
type: PropTypes.string.isRequired,
|
title: string
|
||||||
title: PropTypes.string.isRequired,
|
onSelect(...args: unknown[]): unknown
|
||||||
onSelect: PropTypes.func.isRequired,
|
};
|
||||||
}
|
|
||||||
|
|
||||||
|
class PublicSource extends React.Component<PublicSourceProps> {
|
||||||
render() {
|
render() {
|
||||||
return <div className="maputnik-public-source">
|
return <div className="maputnik-public-source">
|
||||||
<InputButton
|
<InputButton
|
||||||
@@ -39,7 +37,7 @@ class PublicSource extends React.Component {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
function editorMode(source) {
|
function editorMode(source: SourceSpecification) {
|
||||||
if(source.type === 'raster') {
|
if(source.type === 'raster') {
|
||||||
if(source.tiles) return 'tilexyz_raster'
|
if(source.tiles) return 'tilexyz_raster'
|
||||||
return 'tilejson_raster'
|
return 'tilejson_raster'
|
||||||
@@ -69,16 +67,15 @@ function editorMode(source) {
|
|||||||
return null
|
return null
|
||||||
}
|
}
|
||||||
|
|
||||||
class ActiveModalSourcesTypeEditor extends React.Component {
|
type ActiveModalSourcesTypeEditorProps = {
|
||||||
static propTypes = {
|
sourceId: string
|
||||||
sourceId: PropTypes.string.isRequired,
|
source: SourceSpecification
|
||||||
source: PropTypes.object.isRequired,
|
onDelete(...args: unknown[]): unknown
|
||||||
onDelete: PropTypes.func.isRequired,
|
onChange(...args: unknown[]): unknown
|
||||||
onChange: PropTypes.func.isRequired,
|
};
|
||||||
}
|
|
||||||
|
|
||||||
|
class ActiveModalSourcesTypeEditor extends React.Component<ActiveModalSourcesTypeEditorProps> {
|
||||||
render() {
|
render() {
|
||||||
const inputProps = { }
|
|
||||||
return <div className="maputnik-active-source-type-editor">
|
return <div className="maputnik-active-source-type-editor">
|
||||||
<div className="maputnik-active-source-type-editor-header">
|
<div className="maputnik-active-source-type-editor-header">
|
||||||
<span className="maputnik-active-source-type-editor-header-id">#{this.props.sourceId}</span>
|
<span className="maputnik-active-source-type-editor-header-id">#{this.props.sourceId}</span>
|
||||||
@@ -103,12 +100,18 @@ class ActiveModalSourcesTypeEditor extends React.Component {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class AddSource extends React.Component {
|
type AddSourceProps = {
|
||||||
static propTypes = {
|
onAdd(...args: unknown[]): unknown
|
||||||
onAdd: PropTypes.func.isRequired,
|
};
|
||||||
}
|
|
||||||
|
|
||||||
constructor(props) {
|
type AddSourceState = {
|
||||||
|
mode: EditorMode
|
||||||
|
sourceId: string
|
||||||
|
source: SourceSpecification
|
||||||
|
};
|
||||||
|
|
||||||
|
class AddSource extends React.Component<AddSourceProps, AddSourceState> {
|
||||||
|
constructor(props: AddSourceProps) {
|
||||||
super(props)
|
super(props)
|
||||||
this.state = {
|
this.state = {
|
||||||
mode: 'tilejson_vector',
|
mode: 'tilejson_vector',
|
||||||
@@ -117,7 +120,7 @@ class AddSource extends React.Component {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
defaultSource(mode) {
|
defaultSource(mode: EditorMode): SourceSpecification {
|
||||||
const source = (this.state || {}).source || {}
|
const source = (this.state || {}).source || {}
|
||||||
const {protocol} = window.location;
|
const {protocol} = window.location;
|
||||||
|
|
||||||
@@ -128,38 +131,38 @@ class AddSource extends React.Component {
|
|||||||
}
|
}
|
||||||
case 'geojson_json': return {
|
case 'geojson_json': return {
|
||||||
type: 'geojson',
|
type: 'geojson',
|
||||||
cluster: source.cluster || false,
|
cluster: (source as GeoJSONSourceSpecification).cluster || false,
|
||||||
data: {}
|
data: {}
|
||||||
}
|
}
|
||||||
case 'tilejson_vector': return {
|
case 'tilejson_vector': return {
|
||||||
type: 'vector',
|
type: 'vector',
|
||||||
url: source.url || `${protocol}//localhost:3000/tilejson.json`
|
url: (source as VectorSourceSpecification).url || `${protocol}//localhost:3000/tilejson.json`
|
||||||
}
|
}
|
||||||
case 'tilexyz_vector': return {
|
case 'tilexyz_vector': return {
|
||||||
type: 'vector',
|
type: 'vector',
|
||||||
tiles: source.tiles || [`${protocol}//localhost:3000/{x}/{y}/{z}.pbf`],
|
tiles: (source as VectorSourceSpecification).tiles || [`${protocol}//localhost:3000/{x}/{y}/{z}.pbf`],
|
||||||
minZoom: source.minzoom || 0,
|
minzoom: (source as VectorSourceSpecification).minzoom || 0,
|
||||||
maxZoom: source.maxzoom || 14
|
maxzoom: (source as VectorSourceSpecification).maxzoom || 14
|
||||||
}
|
}
|
||||||
case 'tilejson_raster': return {
|
case 'tilejson_raster': return {
|
||||||
type: 'raster',
|
type: 'raster',
|
||||||
url: source.url || `${protocol}//localhost:3000/tilejson.json`
|
url: (source as RasterSourceSpecification).url || `${protocol}//localhost:3000/tilejson.json`
|
||||||
}
|
}
|
||||||
case 'tilexyz_raster': return {
|
case 'tilexyz_raster': return {
|
||||||
type: 'raster',
|
type: 'raster',
|
||||||
tiles: source.tiles || [`${protocol}//localhost:3000/{x}/{y}/{z}.pbf`],
|
tiles: (source as RasterSourceSpecification).tiles || [`${protocol}//localhost:3000/{x}/{y}/{z}.pbf`],
|
||||||
minzoom: source.minzoom || 0,
|
minzoom: (source as RasterSourceSpecification).minzoom || 0,
|
||||||
maxzoom: source.maxzoom || 14
|
maxzoom: (source as RasterSourceSpecification).maxzoom || 14
|
||||||
}
|
}
|
||||||
case 'tilejson_raster-dem': return {
|
case 'tilejson_raster-dem': return {
|
||||||
type: 'raster-dem',
|
type: 'raster-dem',
|
||||||
url: source.url || `${protocol}//localhost:3000/tilejson.json`
|
url: (source as RasterDEMSourceSpecification).url || `${protocol}//localhost:3000/tilejson.json`
|
||||||
}
|
}
|
||||||
case 'tilexyz_raster-dem': return {
|
case 'tilexyz_raster-dem': return {
|
||||||
type: 'raster-dem',
|
type: 'raster-dem',
|
||||||
tiles: source.tiles || [`${protocol}//localhost:3000/{x}/{y}/{z}.pbf`],
|
tiles: (source as RasterDEMSourceSpecification).tiles || [`${protocol}//localhost:3000/{x}/{y}/{z}.pbf`],
|
||||||
minzoom: source.minzoom || 0,
|
minzoom: (source as RasterDEMSourceSpecification).minzoom || 0,
|
||||||
maxzoom: source.maxzoom || 14
|
maxzoom: (source as RasterDEMSourceSpecification).maxzoom || 14
|
||||||
}
|
}
|
||||||
case 'image': return {
|
case 'image': return {
|
||||||
type: 'image',
|
type: 'image',
|
||||||
@@ -183,7 +186,7 @@ class AddSource extends React.Component {
|
|||||||
[0,0],
|
[0,0],
|
||||||
],
|
],
|
||||||
}
|
}
|
||||||
default: return {}
|
default: return {} as any
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -192,7 +195,7 @@ class AddSource extends React.Component {
|
|||||||
this.props.onAdd(sourceId, source);
|
this.props.onAdd(sourceId, source);
|
||||||
}
|
}
|
||||||
|
|
||||||
onChangeSource = (source) => {
|
onChangeSource = (source: SourceSpecification) => {
|
||||||
this.setState({source});
|
this.setState({source});
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -213,7 +216,7 @@ class AddSource extends React.Component {
|
|||||||
label={"Source ID"}
|
label={"Source ID"}
|
||||||
fieldSpec={{doc: "Unique ID that identifies the source and is used in the layer to reference the source."}}
|
fieldSpec={{doc: "Unique ID that identifies the source and is used in the layer to reference the source."}}
|
||||||
value={this.state.sourceId}
|
value={this.state.sourceId}
|
||||||
onChange={v => this.setState({ sourceId: v})}
|
onChange={(v: string) => this.setState({ sourceId: v})}
|
||||||
/>
|
/>
|
||||||
<FieldSelect
|
<FieldSelect
|
||||||
label={"Source Type"}
|
label={"Source Type"}
|
||||||
@@ -230,8 +233,8 @@ class AddSource extends React.Component {
|
|||||||
['image', 'Image'],
|
['image', 'Image'],
|
||||||
['video', 'Video'],
|
['video', 'Video'],
|
||||||
]}
|
]}
|
||||||
onChange={mode => this.setState({mode: mode, source: this.defaultSource(mode)})}
|
onChange={(mode: EditorMode) => this.setState({mode: mode, source: this.defaultSource(mode)})}
|
||||||
value={this.state.mode}
|
value={this.state.mode as string}
|
||||||
/>
|
/>
|
||||||
<ModalSourcesTypeEditor
|
<ModalSourcesTypeEditor
|
||||||
onChange={this.onChangeSource}
|
onChange={this.onChangeSource}
|
||||||
@@ -248,15 +251,15 @@ class AddSource extends React.Component {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export default class ModalSources extends React.Component {
|
type ModalSourcesProps = {
|
||||||
static propTypes = {
|
mapStyle: StyleSpecification
|
||||||
mapStyle: PropTypes.object.isRequired,
|
isOpen: boolean
|
||||||
isOpen: PropTypes.bool.isRequired,
|
onOpenToggle(...args: unknown[]): unknown
|
||||||
onOpenToggle: PropTypes.func.isRequired,
|
onStyleChanged(...args: unknown[]): unknown
|
||||||
onStyleChanged: PropTypes.func.isRequired,
|
};
|
||||||
}
|
|
||||||
|
|
||||||
stripTitle(source) {
|
export default class ModalSources extends React.Component<ModalSourcesProps> {
|
||||||
|
stripTitle(source: SourceSpecification & {title?: string}): SourceSpecification {
|
||||||
const strippedSource = {...source}
|
const strippedSource = {...source}
|
||||||
delete strippedSource['title']
|
delete strippedSource['title']
|
||||||
return strippedSource
|
return strippedSource
|
||||||
@@ -270,13 +273,13 @@ export default class ModalSources extends React.Component {
|
|||||||
key={sourceId}
|
key={sourceId}
|
||||||
sourceId={sourceId}
|
sourceId={sourceId}
|
||||||
source={source}
|
source={source}
|
||||||
onChange={src => this.props.onStyleChanged(changeSource(mapStyle, sourceId, src))}
|
onChange={(src: SourceSpecification) => this.props.onStyleChanged(changeSource(mapStyle, sourceId, src))}
|
||||||
onDelete={() => this.props.onStyleChanged(deleteSource(mapStyle, sourceId))}
|
onDelete={() => this.props.onStyleChanged(deleteSource(mapStyle, sourceId))}
|
||||||
/>
|
/>
|
||||||
})
|
})
|
||||||
|
|
||||||
const tilesetOptions = Object.keys(publicSources).filter(sourceId => !(sourceId in mapStyle.sources)).map(sourceId => {
|
const tilesetOptions = Object.keys(publicSources).filter((sourceId: string) => !(sourceId in mapStyle.sources)).map((sourceId: string) => {
|
||||||
const source = publicSources[sourceId]
|
const source = publicSources[sourceId as keyof typeof publicSources] as SourceSpecification & {title: string};
|
||||||
return <PublicSource
|
return <PublicSource
|
||||||
key={sourceId}
|
key={sourceId}
|
||||||
id={sourceId}
|
id={sourceId}
|
||||||
@@ -286,7 +289,6 @@ export default class ModalSources extends React.Component {
|
|||||||
/>
|
/>
|
||||||
})
|
})
|
||||||
|
|
||||||
const inputProps = { }
|
|
||||||
return <Modal
|
return <Modal
|
||||||
data-wd-key="modal:sources"
|
data-wd-key="modal:sources"
|
||||||
isOpen={this.props.isOpen}
|
isOpen={this.props.isOpen}
|
||||||
@@ -303,7 +305,7 @@ export default class ModalSources extends React.Component {
|
|||||||
<p>
|
<p>
|
||||||
Add one of the publicly available sources to your style.
|
Add one of the publicly available sources to your style.
|
||||||
</p>
|
</p>
|
||||||
<div className="maputnik-public-sources" style={{maxwidth: 500}}>
|
<div className="maputnik-public-sources" style={{maxWidth: 500}}>
|
||||||
{tilesetOptions}
|
{tilesetOptions}
|
||||||
</div>
|
</div>
|
||||||
</section>
|
</section>
|
||||||
@@ -312,7 +314,7 @@ export default class ModalSources extends React.Component {
|
|||||||
<h1>Add New Source</h1>
|
<h1>Add New Source</h1>
|
||||||
<p>Add a new source to your style. You can only choose the source type and id at creation time!</p>
|
<p>Add a new source to your style. You can only choose the source type and id at creation time!</p>
|
||||||
<AddSource
|
<AddSource
|
||||||
onAdd={(sourceId, source) => this.props.onStyleChanged(addSource(mapStyle, sourceId, source))}
|
onAdd={(sourceId: string, source: SourceSpecification) => this.props.onStyleChanged(addSource(mapStyle, sourceId, source))}
|
||||||
/>
|
/>
|
||||||
</section>
|
</section>
|
||||||
</Modal>
|
</Modal>
|
||||||
+58
-40
@@ -1,5 +1,4 @@
|
|||||||
import React from 'react'
|
import React from 'react'
|
||||||
import PropTypes from 'prop-types'
|
|
||||||
import {latest} from '@maplibre/maplibre-gl-style-spec'
|
import {latest} from '@maplibre/maplibre-gl-style-spec'
|
||||||
import Block from './Block'
|
import Block from './Block'
|
||||||
import FieldUrl from './FieldUrl'
|
import FieldUrl from './FieldUrl'
|
||||||
@@ -10,14 +9,18 @@ import FieldArray from './FieldArray'
|
|||||||
import FieldJson from './FieldJson'
|
import FieldJson from './FieldJson'
|
||||||
import FieldCheckbox from './FieldCheckbox'
|
import FieldCheckbox from './FieldCheckbox'
|
||||||
|
|
||||||
|
export type EditorMode = "video" | "image" | "tilejson_vector" | "tilexyz_raster" | "tilejson_raster" | "tilexyz_raster-dem" | "tilejson_raster-dem" | "tilexyz_vector" | "geojson_url" | "geojson_json" | null;
|
||||||
|
|
||||||
class TileJSONSourceEditor extends React.Component {
|
type TileJSONSourceEditorProps = {
|
||||||
static propTypes = {
|
source: {
|
||||||
source: PropTypes.object.isRequired,
|
url: string
|
||||||
onChange: PropTypes.func.isRequired,
|
|
||||||
children: PropTypes.node,
|
|
||||||
}
|
}
|
||||||
|
onChange(...args: unknown[]): unknown
|
||||||
|
children?: React.ReactNode
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
class TileJSONSourceEditor extends React.Component<TileJSONSourceEditorProps> {
|
||||||
render() {
|
render() {
|
||||||
return <div>
|
return <div>
|
||||||
<FieldUrl
|
<FieldUrl
|
||||||
@@ -34,14 +37,18 @@ class TileJSONSourceEditor extends React.Component {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class TileURLSourceEditor extends React.Component {
|
type TileURLSourceEditorProps = {
|
||||||
static propTypes = {
|
source: {
|
||||||
source: PropTypes.object.isRequired,
|
tiles: string[]
|
||||||
onChange: PropTypes.func.isRequired,
|
minzoom: number
|
||||||
children: PropTypes.node,
|
maxzoom: number
|
||||||
}
|
}
|
||||||
|
onChange(...args: unknown[]): unknown
|
||||||
|
children?: React.ReactNode
|
||||||
|
};
|
||||||
|
|
||||||
changeTileUrls(tiles) {
|
class TileURLSourceEditor extends React.Component<TileURLSourceEditorProps> {
|
||||||
|
changeTileUrls(tiles: string[]) {
|
||||||
this.props.onChange({
|
this.props.onChange({
|
||||||
...this.props.source,
|
...this.props.source,
|
||||||
tiles,
|
tiles,
|
||||||
@@ -86,14 +93,17 @@ class TileURLSourceEditor extends React.Component {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class ImageSourceEditor extends React.Component {
|
type ImageSourceEditorProps = {
|
||||||
static propTypes = {
|
source: {
|
||||||
source: PropTypes.object.isRequired,
|
coordinates: [number, number][]
|
||||||
onChange: PropTypes.func.isRequired,
|
url: string
|
||||||
}
|
}
|
||||||
|
onChange(...args: unknown[]): unknown
|
||||||
|
};
|
||||||
|
|
||||||
|
class ImageSourceEditor extends React.Component<ImageSourceEditorProps> {
|
||||||
render() {
|
render() {
|
||||||
const changeCoord = (idx, val) => {
|
const changeCoord = (idx: number, val: [number, number]) => {
|
||||||
const coordinates = this.props.source.coordinates.slice(0);
|
const coordinates = this.props.source.coordinates.slice(0);
|
||||||
coordinates[idx] = val;
|
coordinates[idx] = val;
|
||||||
|
|
||||||
@@ -122,7 +132,7 @@ class ImageSourceEditor extends React.Component {
|
|||||||
type="number"
|
type="number"
|
||||||
value={this.props.source.coordinates[idx]}
|
value={this.props.source.coordinates[idx]}
|
||||||
default={[0, 0]}
|
default={[0, 0]}
|
||||||
onChange={(val) => changeCoord(idx, val)}
|
onChange={(val: [number, number]) => changeCoord(idx, val)}
|
||||||
/>
|
/>
|
||||||
);
|
);
|
||||||
})}
|
})}
|
||||||
@@ -130,14 +140,17 @@ class ImageSourceEditor extends React.Component {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class VideoSourceEditor extends React.Component {
|
type VideoSourceEditorProps = {
|
||||||
static propTypes = {
|
source: {
|
||||||
source: PropTypes.object.isRequired,
|
coordinates: [number, number][]
|
||||||
onChange: PropTypes.func.isRequired,
|
urls: string[]
|
||||||
}
|
}
|
||||||
|
onChange(...args: unknown[]): unknown
|
||||||
|
};
|
||||||
|
|
||||||
|
class VideoSourceEditor extends React.Component<VideoSourceEditorProps> {
|
||||||
render() {
|
render() {
|
||||||
const changeCoord = (idx, val) => {
|
const changeCoord = (idx: number, val: [number, number]) => {
|
||||||
const coordinates = this.props.source.coordinates.slice(0);
|
const coordinates = this.props.source.coordinates.slice(0);
|
||||||
coordinates[idx] = val;
|
coordinates[idx] = val;
|
||||||
|
|
||||||
@@ -147,7 +160,7 @@ class VideoSourceEditor extends React.Component {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
const changeUrls = (urls) => {
|
const changeUrls = (urls: string[]) => {
|
||||||
this.props.onChange({
|
this.props.onChange({
|
||||||
...this.props.source,
|
...this.props.source,
|
||||||
urls,
|
urls,
|
||||||
@@ -160,7 +173,7 @@ class VideoSourceEditor extends React.Component {
|
|||||||
fieldSpec={latest.source_video.urls}
|
fieldSpec={latest.source_video.urls}
|
||||||
type="string"
|
type="string"
|
||||||
value={this.props.source.urls}
|
value={this.props.source.urls}
|
||||||
default={""}
|
default={[]}
|
||||||
onChange={changeUrls}
|
onChange={changeUrls}
|
||||||
/>
|
/>
|
||||||
{["top left", "top right", "bottom right", "bottom left"].map((label, idx) => {
|
{["top left", "top right", "bottom right", "bottom left"].map((label, idx) => {
|
||||||
@@ -172,7 +185,7 @@ class VideoSourceEditor extends React.Component {
|
|||||||
type="number"
|
type="number"
|
||||||
value={this.props.source.coordinates[idx]}
|
value={this.props.source.coordinates[idx]}
|
||||||
default={[0, 0]}
|
default={[0, 0]}
|
||||||
onChange={val => changeCoord(idx, val)}
|
onChange={(val: [number, number]) => changeCoord(idx, val)}
|
||||||
/>
|
/>
|
||||||
);
|
);
|
||||||
})}
|
})}
|
||||||
@@ -180,12 +193,14 @@ class VideoSourceEditor extends React.Component {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class GeoJSONSourceUrlEditor extends React.Component {
|
type GeoJSONSourceUrlEditorProps = {
|
||||||
static propTypes = {
|
source: {
|
||||||
source: PropTypes.object.isRequired,
|
data: string
|
||||||
onChange: PropTypes.func.isRequired,
|
|
||||||
}
|
}
|
||||||
|
onChange(...args: unknown[]): unknown
|
||||||
|
};
|
||||||
|
|
||||||
|
class GeoJSONSourceUrlEditor extends React.Component<GeoJSONSourceUrlEditorProps> {
|
||||||
render() {
|
render() {
|
||||||
return <FieldUrl
|
return <FieldUrl
|
||||||
label={"GeoJSON URL"}
|
label={"GeoJSON URL"}
|
||||||
@@ -199,12 +214,15 @@ class GeoJSONSourceUrlEditor extends React.Component {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class GeoJSONSourceFieldJsonEditor extends React.Component {
|
type GeoJSONSourceFieldJsonEditorProps = {
|
||||||
static propTypes = {
|
source: {
|
||||||
source: PropTypes.object.isRequired,
|
data: any,
|
||||||
onChange: PropTypes.func.isRequired,
|
cluster: boolean
|
||||||
}
|
}
|
||||||
|
onChange(...args: unknown[]): unknown
|
||||||
|
};
|
||||||
|
|
||||||
|
class GeoJSONSourceFieldJsonEditor extends React.Component<GeoJSONSourceFieldJsonEditorProps> {
|
||||||
render() {
|
render() {
|
||||||
return <div>
|
return <div>
|
||||||
<Block label={"GeoJSON"} fieldSpec={latest.source_geojson.data}>
|
<Block label={"GeoJSON"} fieldSpec={latest.source_geojson.data}>
|
||||||
@@ -238,13 +256,13 @@ class GeoJSONSourceFieldJsonEditor extends React.Component {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export default class ModalSourcesTypeEditor extends React.Component {
|
type ModalSourcesTypeEditorProps = {
|
||||||
static propTypes = {
|
mode: EditorMode
|
||||||
mode: PropTypes.string.isRequired,
|
source: any
|
||||||
source: PropTypes.object.isRequired,
|
onChange(...args: unknown[]): unknown
|
||||||
onChange: PropTypes.func.isRequired,
|
};
|
||||||
}
|
|
||||||
|
|
||||||
|
export default class ModalSourcesTypeEditor extends React.Component<ModalSourcesTypeEditorProps> {
|
||||||
render() {
|
render() {
|
||||||
const commonProps = {
|
const commonProps = {
|
||||||
source: this.props.source,
|
source: this.props.source,
|
||||||
Reference in New Issue
Block a user