Skip to content

Commit

Permalink
Platform Context
Browse files Browse the repository at this point in the history
  • Loading branch information
limistah committed Dec 16, 2023
1 parent 1e676df commit 4f5e926
Show file tree
Hide file tree
Showing 14 changed files with 1,873 additions and 1,579 deletions.
3 changes: 2 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -3,4 +3,5 @@
node_modules
.cache
dist
storybook-static
storybook-static
.rough/
5 changes: 5 additions & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,7 @@
"@storybook/addons": "^7.6.5",
"@storybook/react": "^7.6.5",
"@storybook/react-webpack5": "^7.6.5",
"@types/lodash.merge": "^4.6.9",
"@types/react": "^18.2.45",
"@types/react-dom": "^18.2.17",
"babel-loader": "^9.1.3",
Expand All @@ -70,5 +71,9 @@
"tsdx": "^0.14.1",
"tslib": "^2.6.2",
"typescript": "^5.3.3"
},
"dependencies": {
"@limistah/here-map-js": "^3.1.0",
"lodash.merge": "^4.6.2"
}
}
8 changes: 8 additions & 0 deletions src/components/Map/Map.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
import React from 'react';

export interface IHMapProps {}

export const HMap = () => {
// const Platform = useHPlatform()
return <div>HMap</div>;
};
1 change: 1 addition & 0 deletions src/components/Map/index.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
export * from './Map';
45 changes: 45 additions & 0 deletions src/components/Platform/index.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
import React, { useCallback, useEffect, useState } from 'react';
import { ILoadHMapOptions, loadHMap } from '../libs/loadHMap';
import { initHPlatform } from '../libs/initPlatform';
import { DefaultOptionsType } from '../libs/defaults';
import { PlatformContext } from '../../contexts/platform';

export interface IHPlatform extends ILoadHMapOptions {
children: React.ReactNode | React.ReactNode[];
}

export interface IHPlatformState {
options?: DefaultOptionsType;
platform?: any;
reInitMap?: () => void;
}

export const HPlatform = (props: IHPlatform) => {
const loadMapCB = useCallback(() => {
loadHMap(props).then((options: DefaultOptionsType) => {
const platform = initHPlatform(options);
setPlatformState((prevState: IHPlatformState) => ({
...prevState,
platform,
options,
}));
});
}, [props]);
const [platformState, setPlatformState] = useState<IHPlatformState>({
reInitMap: loadMapCB,
platform: {},
});

useEffect(() => {
loadMapCB();
}, [platformState.platform.A]);
const { platform, options } = platformState;

return (
<PlatformContext.Provider value={platformState}>
{platform?.A == 'api.here.com' &&
(options?.app_code || options?.apikey) &&
props.children}
</PlatformContext.Provider>
);
};
1 change: 1 addition & 0 deletions src/components/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
export * from './Map';
98 changes: 98 additions & 0 deletions src/components/libs/defaults.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,98 @@
/**
* @type {string} Default version for the API
*/
const VERSION = 'v3/3.0';
export type MAP_TYPES =
| 'normal.map'
| 'normal.xbase'
| 'normal.xbasenight'
| 'normal.basen'
| 'normal.basenight'
| 'normal.mapnight'
| 'normal.traffic'
| 'normal.trafficnight'
| 'normal.transit'
| 'normal.panoram'
| 'normal.panoramnight'
| 'normal.labels'
| 'normal.metaInfo'
| 'satellite.xbase'
| 'satellite.base'
| 'satellite.map'
| 'satellite.traffic'
| 'satellite.panorama'
| 'satellite.labels'
| 'terrain.xbase'
| 'terrain.base'
| 'terrain.map'
| 'terrain.traffic'
| 'terrain.panorama'
| 'terrain.labels'
| 'incidents'
| 'venues';

const MAP_TYPE: MAP_TYPES = 'normal.map';

const mapOptions = {
zoom: 8,
center: {
lat: 6.5243793,
lng: 3.3792057,
},
};
const useEvents = false;
const interactive = false;
const includeUI = false;
const containerId = 'HERE_MAP_CONTAINER';

type mapEventTypes =
| 'pointerdown'
| 'pointerup'
| 'pointermove'
| 'pointerenter'
| 'pointerleave'
| 'pointercancel'
| 'dragstart'
| 'drag'
| 'dragend'
| 'tab'
| 'dbltap';

const defaultClassName = 'here-map-container';

const includePlaces = false;

// Function that does really nothing, still it is a function, and has its right!
const noop = () => {};

const mapEvents: Record<mapEventTypes, typeof noop> = {
pointercancel: noop,
drag: noop,
dragend: noop,
tab: noop,
dbltap: noop,
pointerdown: noop,
pointerenter: noop,
pointerleave: noop,
pointermove: noop,
pointerup: noop,
dragstart: noop,
};

export type DefaultOptionsType = typeof defaultOptions;

export const defaultOptions = {
VERSION,
mapEvents,
MAP_TYPE,
mapOptions,
interactive,
includeUI,
includePlaces,
useEvents,
containerId,
defaultClassName,
app_id: '',
app_code: '',
apikey: '',
};
1 change: 1 addition & 0 deletions src/components/libs/here-map-js.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
declare module '@limistah/here-map-js';
14 changes: 14 additions & 0 deletions src/components/libs/initPlatform.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
import { DefaultOptionsType } from './defaults';

export const initHPlatform = (options: DefaultOptionsType) => {
const { app_id, app_code, apikey } = options;
if ((!app_id || !app_code) && !apikey) {
throw new Error('Options must include appId and appCode OR an apiKey');
}
// @ts-ignore
const h = window.H;
if (typeof h === 'undefined' || !h.service) {
throw new Error('Here Map JavaScript files are not loaded.');
}
return new h.service.Platform(options);
};
40 changes: 40 additions & 0 deletions src/components/libs/loadHMap.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
import hereMapJS from '@limistah/here-map-js';
import { DefaultOptionsType, defaultOptions } from './defaults';
import merge from 'lodash.merge';

// Merges the option with the defaults to create a unison and make required values available
const optionMerger = (options: ILoadHMapOptions) =>
merge(defaultOptions, options);

export interface ILoadHMapOptions {
version?: string; // Version of the api to load. Defaults to v3
interactive?: boolean; // Adds interactive scripts
includeUI?: boolean; // Should add the UI scripts
includePlaces?: boolean; // Include the places script
}

export const loadHMap = async (
options: ILoadHMapOptions = {
includePlaces: false,
includeUI: false,
interactive: false,
version: 'v3/3.0',
}
): Promise<DefaultOptionsType> => {
const mergedOptions = optionMerger(options);
const {
VERSION,
version,
interactive,
includeUI,
includePlaces,
} = mergedOptions;
// Returns async loading of the component
// First load the core, to save us reference error if all of the libraries are loaded asynchronously due to race conditions
return hereMapJS({
includeUI,
includePlaces,
interactive,
version: version || VERSION,
}).then(() => mergedOptions);
};
8 changes: 8 additions & 0 deletions src/contexts/platform.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
// provider a provider
// provider a consumer

import { createContext } from 'react';
import { IHPlatformState } from '../components/Platform';

// create a hook for the platform context
export const PlatformContext = createContext<IHPlatformState>({});
11 changes: 10 additions & 1 deletion src/index.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import React, { FC, HTMLAttributes, ReactChild } from 'react';
import { HPlatform } from './components/Platform';

export interface Props extends HTMLAttributes<HTMLDivElement> {
/** custom content, defaults to 'the snozzberries taste like snozzberries' */
Expand All @@ -11,5 +12,13 @@ export interface Props extends HTMLAttributes<HTMLDivElement> {
* A custom Thing component. Neat!
*/
export const Thing: FC<Props> = ({ children }) => {
return <div>{children || `the snozzberries taste like snozzberries`}</div>;
return (
<div>
<HPlatform >
{children || `the snozzberries taste like snozzberries`}
</HPlatform>
</div>
);
};

export * from './components';
20 changes: 20 additions & 0 deletions stories/Map.stories.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
import React from 'react';
import { Meta, Story } from '@storybook/react';
import { HMap, IHMapProps } from '../src';

const meta: Meta = {
title: 'HMap',
component: HMap,
argTypes: {},
parameters: {},
};

export default meta;

const Template: Story<IHMapProps> = args => <HMap {...args} />;

// By passing using the Args format for exported stories, you can control the props for a component for reuse in a test
// https://storybook.js.org/docs/react/workflows/unit-testing
export const Default = Template.bind({});

Default.args = {};
Loading

0 comments on commit 4f5e926

Please sign in to comment.