Skip to content

Commit

Permalink
Refactor LineLayer, MapboxLayer and TileLayer
Browse files Browse the repository at this point in the history
  • Loading branch information
frozenhelium committed Mar 11, 2024
1 parent 39e8e70 commit 3dfc598
Show file tree
Hide file tree
Showing 8 changed files with 161 additions and 97 deletions.
102 changes: 58 additions & 44 deletions lib/src/components/Map/Layers/LineLayer.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import { useEffect, useState } from 'react';
import { useEffect, useMemo, useRef } from 'react';
import { isNotDefined } from '@togglecorp/fujs';
import { Map as MapFromLib } from 'ol';
import OLVectorLayer from 'ol/layer/Vector';
import { Vector as VectorSource } from 'ol/source';
Expand All @@ -10,6 +11,8 @@ import {
import { LineLayer } from '../index';
import { rgba } from '../helpers';

const DEFAULT_STROKE_COLOR = '#787878';

interface Props extends Pick<LineLayer, 'zIndex' | 'opacity' | 'style'> {
map: MapFromLib | undefined;
source: VectorSource;
Expand All @@ -24,57 +27,68 @@ function LineLayer(props: Props) {
opacity = 1,
} = props;

const [lineLayer, setLineLayer] = useState(undefined);
const configRef = useRef({
zIndex,
opacity,
});

// line vectors
useEffect(() => {
if (!map) return undefined;
const styles = [];

const lineDash = style.strokeType === 'dash'
? [style.dashSpacing / 3, style.dashSpacing]
: undefined;

const stroke = new Stroke({
width: style.strokeWidth,
color: rgba(style.stroke),
lineDash,
});

if (style) {
styles.push(
new Style({ stroke }),
);
}
const lineLayer = useMemo(
() => {
const styles: Style[] = [];

const lineDash = style.strokeType === 'dash'
? [style.dashSpacing / 3, style.dashSpacing]
: undefined;

const vLayer = new OLVectorLayer({
source,
style() {
return styles;
},
});

map.addLayer(vLayer);
vLayer.setZIndex(zIndex);
vLayer.setOpacity(opacity);
setLineLayer(vLayer);

return () => {
if (map) {
map.removeLayer(vLayer);
const stroke = new Stroke({
width: style.strokeWidth,
color: rgba(style.stroke) ?? DEFAULT_STROKE_COLOR,
lineDash,
});

if (style) {
styles.push(
new Style({ stroke }),
);
}
};
}, [map, JSON.stringify(style)]);

useEffect(() => {
if (!lineLayer) return;
lineLayer.setOpacity(opacity);
}, [lineLayer, opacity]);
return new OLVectorLayer({
source,
style: styles,
zIndex: configRef.current.zIndex,
opacity: configRef.current.opacity,
});
},
[source, style],
);

useEffect(
() => {
const currentMap = map;
const addedLayer = lineLayer;

if (isNotDefined(currentMap) || isNotDefined(addedLayer)) {
return undefined;
}

currentMap.addLayer(addedLayer);

return () => {
currentMap.removeLayer(addedLayer);
};
},
[map, lineLayer],
);

useEffect(() => {
if (!lineLayer) return;
if (isNotDefined(lineLayer)) {
return;
}

lineLayer.setOpacity(opacity);
lineLayer.setZIndex(zIndex);
}, [lineLayer, zIndex]);
}, [lineLayer, opacity, zIndex]);

return null;
}
Expand Down
81 changes: 51 additions & 30 deletions lib/src/components/Map/Layers/MapboxLayer.tsx
Original file line number Diff line number Diff line change
@@ -1,49 +1,70 @@
import { useState, useEffect } from 'react';
import { useEffect, useRef, useMemo } from 'react';
import { isNotDefined } from '@togglecorp/fujs';
import { Map as MapFromLib } from 'ol';
import TileLayer from 'ol/layer/Tile';
import { XYZ } from 'ol/source';

function MapboxLayer({
map, zIndex = 1, opacity = 1, styleUrl, accessToken,
}) {
const [mapboxLayer, setMapboxLayer] = useState(undefined);
import { MapboxLayer } from '../index';

useEffect(() => {
if (!map) return undefined;
interface Props extends Pick<MapboxLayer, 'zIndex' | 'opacity' | 'accessToken'> {
map: MapFromLib | undefined;
styleUrl: string;
}

function MapboxLayer(props: Props) {
const {
map,
zIndex = 1,
opacity = 1,
styleUrl,
accessToken,
} = props;

const configRef = useRef({
zIndex,
opacity,
});

const mapboxLayer = useMemo(
() => {
let styleUrlParsed = styleUrl.replace('mapbox://', '');
styleUrlParsed = styleUrlParsed.replace('styles/', 'styles/v1/');

let styleUrlParsed = styleUrl.replace('mapbox://', '');
styleUrlParsed = styleUrlParsed.replace('styles/', 'styles/v1/');
return new TileLayer({
source: new XYZ({
url: `https://api.mapbox.com/${styleUrlParsed}/tiles/{z}/{x}/{y}?access_token=${accessToken}`,
tileSize: 512,
// preload: 10,
crossOrigin: 'anonymous',
}),
zIndex: configRef.current.zIndex,
opacity: configRef.current.opacity,
});
},
[styleUrl, accessToken],
);

const layer = new TileLayer({
source: new XYZ({
url: `https://api.mapbox.com/${styleUrlParsed}/tiles/{z}/{x}/{y}?access_token=${accessToken}`,
tileSize: 512,
preload: 10,
crossOrigin: 'anonymous',
}),
});
useEffect(() => {
const currentMap = map;
const addedLayer = mapboxLayer;

map.addLayer(layer);
layer.setZIndex(zIndex);
layer.setOpacity(opacity);
if (isNotDefined(currentMap) || isNotDefined(addedLayer)) {
return undefined;
}

setMapboxLayer(layer);
currentMap.addLayer(addedLayer);

return () => {
if (map) {
map.removeLayer(layer);
}
currentMap.removeLayer(addedLayer);
};
}, [map, styleUrl, accessToken]);
}, [map, styleUrl, accessToken, mapboxLayer]);

useEffect(() => {
if (!mapboxLayer) return;
mapboxLayer.setOpacity(opacity);
}, [mapboxLayer, opacity]);

useEffect(() => {
if (!mapboxLayer) return;
mapboxLayer.setOpacity(opacity);
mapboxLayer.setZIndex(zIndex);
}, [mapboxLayer, zIndex]);
}, [mapboxLayer, opacity, zIndex]);

return null;
}
Expand Down
67 changes: 47 additions & 20 deletions lib/src/components/Map/Layers/TileLayer.tsx
Original file line number Diff line number Diff line change
@@ -1,35 +1,62 @@
import { useState, useEffect } from 'react';
import { useEffect, useMemo, useRef } from 'react';
import { isNotDefined } from '@togglecorp/fujs';
import { Map as MapFromLib } from 'ol';
import OLTileLayer from 'ol/layer/Tile';
import TileSource from 'ol/source/Tile';

function TileLayer({
map, source, zIndex = 0, opacity = 1,
}) {
const [tileLayer, setTileLayer] = useState(undefined);
import { OsmBackgroundLayer } from '../index';

interface Props extends Pick<OsmBackgroundLayer, 'zIndex' | 'opacity'> {
map: MapFromLib | undefined;
source: TileSource;
}
function TileLayer(props: Props) {
const {
map,
source,
zIndex = 1,
opacity = 1,
} = props;

const configRef = useRef({
zIndex,
opacity,
});

const tileLayer = useMemo(
() => (
new OLTileLayer({
source,
zIndex: configRef.current.zIndex,
opacity: configRef.current.opacity,
})
),
[source],
);

useEffect(() => {
if (!map) return undefined;
const currentMap = map;
const addedLayer = tileLayer;

const tileRasterLayer = new OLTileLayer({
source,
zIndex,
});
map.addLayer(tileRasterLayer);
tileRasterLayer.setZIndex(zIndex);
tileRasterLayer.setOpacity(opacity);
if (isNotDefined(currentMap) || isNotDefined(addedLayer)) {
return undefined;
}

setTileLayer(tileRasterLayer);
currentMap.addLayer(addedLayer);

return () => {
if (map) {
map.removeLayer(tileRasterLayer);
}
currentMap.removeLayer(addedLayer);
};
}, [map, JSON.stringify(source.urls)]);
}, [map, tileLayer]);

useEffect(() => {
if (!tileLayer) return;
if (isNotDefined(tileLayer)) {
return;
}

tileLayer.setOpacity(opacity);
}, [opacity]);
tileLayer.setZIndex(zIndex);
}, [tileLayer, opacity, zIndex]);

return null;
}
Expand Down
File renamed without changes.
File renamed without changes.
File renamed without changes.
8 changes: 5 additions & 3 deletions lib/src/components/Map/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,6 @@ import { createTheme } from '@mui/material/styles';
import grey from '@mui/material/colors/grey';

import './ol.css';
import styles from './styles.module.css';
import {
osm,
vector,
Expand All @@ -40,6 +39,7 @@ import HeatmapLayer from './Layers/HeatmapLayer';
import HexbinLayer from './Layers/HexbinLayer';
import OlMap from './OlMap';
import ColorScale from '../ColorScale';
import styles from './styles.module.css';

// FIXME: may need to update rollup configuration to include files
import cdcf from './assets/logos/cdcf.jpg';
Expand Down Expand Up @@ -140,15 +140,17 @@ interface ShadedMaskLayer {
strokeWidth: number;
};
}
interface OsmBackgroundLayer {

export interface OsmBackgroundLayer {
id: number;
name: string;
opacity: number;
type: 'osm';
visible: number;
zIndex: number;
}
interface MapboxLayer {

export interface MapboxLayer {
accessToken: string; // FIXME: Not sure if we need to pass this
id: number;
name: string;
Expand Down

0 comments on commit 3dfc598

Please sign in to comment.