Skip to content
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

Map core feature breakout #962

Merged
merged 5 commits into from
May 24, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
193 changes: 103 additions & 90 deletions app/scripts/components/common/blocks/block-map.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -9,11 +9,18 @@ import {
validateProjectionBlockProps
} from '../map/controls/map-options/projections';
import { Basemap } from '../map/style-generators/basemap';
import { LayerLegend, LayerLegendContainer } from '../mapbox/layer-legend';
import { LayerLegend, LayerLegendContainer } from '../map/layer-legend';
import MapCoordsControl from '../map/controls/coords';
import MapMessage from '../mapbox/map-message';
import { formatCompareDate, formatSingleDate, resolveConfigFunctions } from '../map/utils';
import { BasemapId, DEFAULT_MAP_STYLE_URL } from '../map/controls/map-options/basemap';
import MapMessage from '../map/map-message';
import {
formatCompareDate,
formatSingleDate,
resolveConfigFunctions
} from '../map/utils';
import {
BasemapId,
DEFAULT_MAP_STYLE_URL
} from '../map/controls/map-options/basemap';
import { utcString2userTzDate } from '$utils/date';
import Map, { Compare, MapControls } from '$components/common/map';
import { validateRangeNum } from '$utils/utils';
Expand All @@ -23,10 +30,11 @@ import {
ScaleControl
} from '$components/common/map/controls';
import { Layer } from '$components/exploration/components/map/layer';
import { S_SUCCEEDED } from '$utils/status';
import {
S_SUCCEEDED
} from '$utils/status';
import { TimelineDataset, TimelineDatasetSuccess } from '$components/exploration/types.d.ts';
TimelineDataset,
TimelineDatasetSuccess
} from '$components/exploration/types.d.ts';

import { reconcileDatasets } from '$components/exploration/data-utils';
import { datasetLayers } from '$components/exploration/data-utils';
Expand Down Expand Up @@ -134,24 +142,30 @@ function MapBlock(props: MapBlockProps) {
projectionParallels,
basemapId
} = props;

const errors = validateBlockProps(props);
if (errors.length) {
throw new HintedError('Malformed Map Block', errors);
}

const [ baseLayers, setBaseLayers] = useState<TimelineDataset[] | undefined>();
const [ compareLayers, setCompareLayers] = useState<TimelineDataset[] | undefined>();
const [baseLayers, setBaseLayers] = useState<TimelineDataset[] | undefined>();
const [compareLayers, setCompareLayers] = useState<
TimelineDataset[] | undefined
>();

const [ baseMapStaticData ] = reconcileDatasets([layerId], datasetLayers, []);
const [baseMapStaticData] = reconcileDatasets([layerId], datasetLayers, []);
const baseMapStaticCompareData = baseMapStaticData.data.compare;

let compareLayerId: undefined | string;
if (baseMapStaticCompareData && ('layerId' in baseMapStaticCompareData)) {
if (baseMapStaticCompareData && 'layerId' in baseMapStaticCompareData) {
compareLayerId = baseMapStaticCompareData.layerId;
}

const [ compareMapStaticData ] = reconcileDatasets(compareLayerId ? [compareLayerId] : [], datasetLayers, []);
const [compareMapStaticData] = reconcileDatasets(
compareLayerId ? [compareLayerId] : [],
datasetLayers,
[]
);

useReconcileWithStacMetadata([baseMapStaticData], setBaseLayers);
useReconcileWithStacMetadata([compareMapStaticData], setCompareLayers);
Expand All @@ -162,7 +176,7 @@ function MapBlock(props: MapBlockProps) {
const selectedCompareDatetime = compareDateTime
? utcString2userTzDate(compareDateTime)
: undefined;

const projectionStart = useMemo(() => {
if (projectionId) {
// Ensure that the default center and parallels are used if none are
Expand All @@ -184,26 +198,32 @@ function MapBlock(props: MapBlockProps) {
const [, setProjection] = useState(projectionStart);

const dataset = datasetId ? datasets[datasetId] : null;

const resolverBag = useMemo<DatasetDatumFnResolverBag>(
() => ({ datetime: selectedDatetime, compareDatetime: selectedCompareDatetime, dateFns }),
() => ({
datetime: selectedDatetime,
compareDatetime: selectedCompareDatetime,
dateFns
}),
[selectedDatetime, selectedCompareDatetime]
);

const [baseLayerResolvedData] = useMemo(() => {
if (!baseLayers || baseLayers.length !== 1) return [null, null];
const baseLayer = baseLayers[0];

if (baseLayer.status !== S_SUCCEEDED ) return [null, null];
if (baseLayer.status !== S_SUCCEEDED) return [null, null];

const bag = { ...resolverBag, raw: baseLayer.data };
const data = resolveConfigFunctions(baseLayer.data, bag);
return [data];
}, [baseLayers, resolverBag]);

const baseDataLayer: TimelineDataset | null = ({data: baseLayerResolvedData} as unknown) as TimelineDataset;
const baseDataLayer: TimelineDataset | null = {
data: baseLayerResolvedData
} as unknown as TimelineDataset;
const baseTimeDensity = baseLayerResolvedData?.timeDensity;

// Resolve data needed for the compare layer once it is loaded.
const [compareLayerResolvedData] = useMemo(() => {
if (!compareLayers || compareLayers.length !== 1) return [null, null];
Expand All @@ -216,7 +236,9 @@ function MapBlock(props: MapBlockProps) {
return [data];
}, [compareLayers, resolverBag]);

const compareDataLayer: TimelineDataset | null = ({data: compareLayerResolvedData} as unknown) as TimelineDataset;
const compareDataLayer: TimelineDataset | null = {
data: compareLayerResolvedData
} as unknown as TimelineDataset;
const compareTimeDensity = compareLayerResolvedData?.timeDensity;

const mapOptions: Partial<MapboxOptions> = {
Expand All @@ -227,17 +249,17 @@ function MapBlock(props: MapBlockProps) {
dragRotate: false,
zoom: 1
};

const getMapPositionOptions = (position) => {
const opts = {} as Pick<typeof mapOptions, 'center' | 'zoom'>;
if (position?.lng !== undefined && position?.lat !== undefined) {
opts.center = [position.lng, position.lat];
}

if (position?.zoom) {
opts.zoom = position.zoom;
}

return opts;
};

Expand Down Expand Up @@ -285,27 +307,28 @@ function MapBlock(props: MapBlockProps) {
compareTimeDensity
]);

const initialPosition = useMemo(() => center ? { lng: center[0], lat: center[1], zoom } : undefined , [center, zoom]);
const initialPosition = useMemo(
() => (center ? { lng: center[0], lat: center[1], zoom } : undefined),
[center, zoom]
);
return (
<Carto>
<Map id={generatedId} mapOptions={{...mapOptions, ...getMapPositionOptions(initialPosition)}}>
<Basemap
basemapStyleId={mapBasemapId}
/>
{
dataset &&
selectedDatetime &&
layerId &&
baseLayerResolvedData &&
(
<Layer
key={baseLayerResolvedData?.id}
id={`base-${baseLayerResolvedData?.id}`}
dataset={(baseDataLayer as unknown) as TimelineDatasetSuccess}
selectedDay={selectedDatetime}
/>
)
}
<Map
id={generatedId}
mapOptions={{
...mapOptions,
...getMapPositionOptions(initialPosition)
}}
>
<Basemap basemapStyleId={mapBasemapId} />
{dataset && selectedDatetime && layerId && baseLayerResolvedData && (
<Layer
key={baseLayerResolvedData?.id}
id={`base-${baseLayerResolvedData?.id}`}
dataset={baseDataLayer as unknown as TimelineDatasetSuccess}
selectedDay={selectedDatetime}
/>
)}
{baseLayerResolvedData?.legend && (
// Map overlay element
// Layer legend for the active layer.
Expand All @@ -330,60 +353,50 @@ function MapBlock(props: MapBlockProps) {
</LayerLegendContainer>
)}
<MapControls>
{
(selectedDatetime && selectedCompareDatetime) ?
(
<MapMessage
id='compare-message'
active={
!!(
selectedCompareDatetime &&
compareLayerResolvedData
)
}
>
{computedCompareLabel}
</MapMessage>
) :
(
<MapMessage
id='single-map-message'
active={!!(selectedDatetime && baseLayerResolvedData)}
>
{selectedDatetime && formatSingleDate(selectedDatetime, baseLayerResolvedData?.timeDensity)}
</MapMessage>
)
}
{selectedDatetime && selectedCompareDatetime ? (
<MapMessage
id='compare-message'
active={!!(selectedCompareDatetime && compareLayerResolvedData)}
>
{computedCompareLabel}
</MapMessage>
) : (
<MapMessage
id='single-map-message'
active={!!(selectedDatetime && baseLayerResolvedData)}
>
{selectedDatetime &&
formatSingleDate(
selectedDatetime,
baseLayerResolvedData?.timeDensity
)}
</MapMessage>
)}
<ScaleControl />
<NavigationControl position='top-left' />
<MapCoordsControl />
</MapControls>
{
selectedCompareDatetime && (
<Compare>
<Basemap
basemapStyleId={mapBasemapId}
/>
{
dataset &&
selectedCompareDatetime &&
layerId &&
compareLayerResolvedData &&
(
<Layer
key={compareLayerResolvedData.id}
id={`compare-${compareLayerResolvedData.id}`}
dataset={(compareDataLayer as unknown) as TimelineDatasetSuccess}
selectedDay={selectedCompareDatetime}
/>
)
}
</Compare>
)
}
{selectedCompareDatetime && (
<Compare>
<Basemap basemapStyleId={mapBasemapId} />
{dataset &&
selectedCompareDatetime &&
layerId &&
compareLayerResolvedData && (
<Layer
key={compareLayerResolvedData.id}
id={`compare-${compareLayerResolvedData.id}`}
dataset={
compareDataLayer as unknown as TimelineDatasetSuccess
}
selectedDay={selectedCompareDatetime}
/>
)}
</Compare>
)}
</Map>
</Carto>
);
}

export default MapBlock;
export default MapBlock;
4 changes: 2 additions & 2 deletions app/scripts/components/common/blocks/scrollytelling/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -37,8 +37,8 @@ import Hug from '$styles/hug';
import {
LayerLegendContainer,
LayerLegend
} from '$components/common/mapbox/layer-legend';
import MapMessage from '$components/common/mapbox/map-message';
} from '$components/common/map/layer-legend';
import MapMessage from '$components/common/map/map-message';
import { MapLoading } from '$components/common/loading-skeleton';
import { HintedError } from '$utils/hinted-error';
import { formatSingleDate } from '$components/common/mapbox/utils';
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -27,8 +27,6 @@ import {
WidgetItemHGroup
} from '$styles/panel';

// @NOTE: File should be moved under "/common/map" as we are working to deprecate "/common/mapbox" dir

dzole0311 marked this conversation as resolved.
Show resolved Hide resolved
interface LayerLegendCommonProps {
id: string;
title: string;
Expand Down Expand Up @@ -167,13 +165,13 @@ const LegendList = styled.dl`
}

.unit {
grid-row: 3;
width: 100%;
text-align: center;
font-size: 0.75rem;
line-height: 1rem;
justify-content: center;
}
grid-row: 3;
width: 100%;
text-align: center;
font-size: 0.75rem;
line-height: 1rem;
justify-content: center;
}
`;

const LegendSwatch = styled.span<LegendSwatchProps>`
Expand Down Expand Up @@ -255,11 +253,9 @@ export function LayerLegend(
)}
renderBody={() => (
<LegendBody>

<div className='scroll-inner'>
{description || <p>No info available for this layer.</p>}
</div>

<div className='scroll-inner'>
{description || <p>No info available for this layer.</p>}
</div>
</LegendBody>
)}
/>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,7 @@ import { Transition, TransitionGroup } from 'react-transition-group';
import { glsp, themeVal } from '@devseed-ui/theme-provider';
import { variableGlsp } from '$styles/variable-utils';

// @NOTE: File should be moved under "/common/map" as we are working to deprecate "/common/mapbox" dir

const fadeDuration = 240;
const FADE_DURATION = 240;

interface MessageProps {
show: boolean;
Expand Down Expand Up @@ -45,7 +43,7 @@ const Message = styled.div<MessageProps>`
background: #fff;
`}

transition: all ${fadeDuration}ms ease-in-out;
transition: all ${FADE_DURATION}ms ease-in-out;
${({ show }) =>
show
? css`
Expand All @@ -72,7 +70,7 @@ export default function MapMessage(props: MapMessageProps) {
return (
<TransitionGroup component={null}>
{active && (
<Transition key={id} timeout={fadeDuration}>
<Transition key={id} timeout={FADE_DURATION}>
{(state) => {
return (
<Message
Expand Down
Loading
Loading