diff --git a/src/components/FeaturePanel/ImageSection/StarButton.tsx b/src/components/FeaturePanel/ImageSection/StarButton.tsx index 813cb3381..713f28a57 100644 --- a/src/components/FeaturePanel/ImageSection/StarButton.tsx +++ b/src/components/FeaturePanel/ImageSection/StarButton.tsx @@ -1,19 +1,12 @@ import Star from '@material-ui/icons/Star'; import StarBorder from '@material-ui/icons/StarBorder'; -import React, { useEffect, useState } from 'react'; +import React from 'react'; import { Tooltip } from '@material-ui/core'; import { t } from '../../../services/intl'; import { useStarsContext } from '../../utils/StarsContext'; import { StyledActionButton } from './utils'; import { useUserThemeContext } from '../../../helpers/theme'; - -const useIsClient = () => { - const [isClient, setIsClient] = useState(false); - useEffect(() => { - setIsClient(true); - }, []); - return isClient; -}; +import { useIsClient } from '../../helpers'; const StarButtonDarkPure = ({ isStarred, toggleStar }) => ( diff --git a/src/components/Map/Map.tsx b/src/components/Map/Map.tsx index 71185701e..c834be246 100644 --- a/src/components/Map/Map.tsx +++ b/src/components/Map/Map.tsx @@ -11,6 +11,7 @@ import { SHOW_PROTOTYPE_UI } from '../../config'; import { LayerSwitcherButton } from '../LayerSwitcher/LayerSwitcherButton'; import { MaptilerLogo } from './MapFooter/MaptilerLogo'; import { TopMenu } from './TopMenu/TopMenu'; +import { ClimbingLegend } from './MapFooter/ClimbingLegend'; const BrowserMap = dynamic(() => import('./BrowserMap'), { ssr: false, @@ -82,9 +83,10 @@ const Map = () => { {SHOW_PROTOTYPE_UI && } + + - ); }; diff --git a/src/components/Map/MapFooter/ClimbingLegend.tsx b/src/components/Map/MapFooter/ClimbingLegend.tsx new file mode 100644 index 000000000..86f37e4d8 --- /dev/null +++ b/src/components/Map/MapFooter/ClimbingLegend.tsx @@ -0,0 +1,88 @@ +import React from 'react'; +import styled from 'styled-components'; +import { IconButton } from '@material-ui/core'; +import CloseIcon from '@material-ui/icons/Close'; +import { useMapStateContext } from '../../utils/MapStateContext'; +import { COLORS } from '../styles/layers/climbingLayers'; +import { usePersistedState } from '../../utils/usePersistedState'; +import { useIsClient } from '../../helpers'; + +const Dot = styled.div<{ color: string }>` + border-radius: 50%; + width: 15px; + height: 15px; + border: solid 2px white; + background: ${({ color }) => color}; + box-shadow: 0 0 3px rgba(0, 0, 0, 0.5); +`; +const Item = styled.div` + display: flex; + align-items: center; + gap: 6px; + font-size: 12px; +`; + +const HeadingRow = styled.div` + display: flex; + align-items: center; + justify-content: space-between; +`; + +const Heading = styled.div` + font-size: 12px; + font-weight: bold; +`; + +const Container = styled.div` + display: flex; + flex-direction: column; + gap: 8px; + border-radius: 8px; + padding: 8px; + box-shadow: 0 0 20px rgba(0, 0, 0, 0.3); + color: ${({ theme }) => theme.palette.text.primary}; + background-color: ${({ theme }) => theme.palette.background.paper}; +`; + +export const ClimbingLegend = () => { + const [isLegendVisible, setIsLegendVisible] = usePersistedState( + 'isLegendVisible', + true, + ); + const isClient = useIsClient(); + const { activeLayers } = useMapStateContext(); + + const isClimbingLayerVisible = activeLayers.includes('climbing'); + + const onLegendClose = () => { + setIsLegendVisible(false); + }; + + return isLegendVisible && isClimbingLayerVisible && isClient ? ( + + + Climbing legend + + + + + + + Area with photos + + + + Crag with photos + + + + Area/crag without photos + + + ) : null; +}; diff --git a/src/components/Map/MapFooter/LangSwitcher.tsx b/src/components/Map/MapFooter/LangSwitcher.tsx index 96a859868..d9aca1fcc 100644 --- a/src/components/Map/MapFooter/LangSwitcher.tsx +++ b/src/components/Map/MapFooter/LangSwitcher.tsx @@ -2,9 +2,17 @@ import getConfig from 'next/config'; import React from 'react'; import { Menu, MenuItem } from '@material-ui/core'; import { useRouter } from 'next/router'; +import LanguageIcon from '@material-ui/icons/Language'; +import styled from 'styled-components'; import { useBoolState } from '../../helpers'; import { changeLang, intl, t } from '../../../services/intl'; +const StyledLanguageIcon = styled(LanguageIcon)` + color: ${({ theme }) => theme.palette.action.active}; + margin: -2px 6px 0 0; + font-size: 17px !important; +`; + export const LangSwitcher = () => { const { publicRuntimeConfig: { languages }, @@ -39,17 +47,16 @@ export const LangSwitcher = () => { ))} - + ); }; diff --git a/src/components/Map/MapFooter/MapFooter.tsx b/src/components/Map/MapFooter/MapFooter.tsx index b8fcb3f15..a7d7100dc 100644 --- a/src/components/Map/MapFooter/MapFooter.tsx +++ b/src/components/Map/MapFooter/MapFooter.tsx @@ -1,22 +1,11 @@ import React, { useEffect, useState } from 'react'; import styled from 'styled-components'; -import getConfig from 'next/config'; import { Tooltip, useMediaQuery } from '@material-ui/core'; import uniq from 'lodash/uniq'; -import { t, Translation } from '../../../services/intl'; -import GithubIcon from '../../../assets/GithubIcon'; -import { LangSwitcher } from './LangSwitcher'; +import { Translation } from '../../../services/intl'; import { useMapStateContext } from '../../utils/MapStateContext'; import { osmappLayers } from '../../LayerSwitcher/osmappLayers'; -const { - publicRuntimeConfig: { osmappVersion, commitHash, commitMessage }, -} = getConfig(); - -const StyledGithubIcon = styled(GithubIcon)` - filter: ${({ theme }) => theme.palette.invertFilter}; -`; - const Wrapper = styled.div` margin-top: 10px; padding: 0 2px; @@ -39,21 +28,6 @@ const Wrapper = styled.div` } `; -const OsmappLink = () => ( - <> - - - osmapp - {' '} - {osmappVersion} - -); - const Attribution = ({ label, link, title }) => ( <> ©{' '} @@ -122,10 +96,6 @@ export const MapFooter = () => ( // TODO find a way how to render this in SSR (keep layer in cookies?) - - {' | '} - - {' | '} diff --git a/src/components/Map/MapFooter/MaptilerLogo.tsx b/src/components/Map/MapFooter/MaptilerLogo.tsx index 63ecbe9c5..4779e0eed 100644 --- a/src/components/Map/MapFooter/MaptilerLogo.tsx +++ b/src/components/Map/MapFooter/MaptilerLogo.tsx @@ -1,15 +1,7 @@ import React from 'react'; -import styled from 'styled-components'; import { useMapStateContext } from '../../utils/MapStateContext'; import { osmappLayers } from '../../LayerSwitcher/osmappLayers'; -const Link = styled.a` - position: absolute; - right: 8px; - bottom: 19px; - z-index: 999; -`; - export const MaptilerLogo = () => { const { activeLayers } = useMapStateContext(); const hasMaptiler = activeLayers.some((layer) => @@ -21,8 +13,8 @@ export const MaptilerLogo = () => { } return ( - + MapTiler logo - + ); }; diff --git a/src/components/Map/TopMenu/HamburgerMenu.tsx b/src/components/Map/TopMenu/HamburgerMenu.tsx index f07a4b276..83326f2d5 100644 --- a/src/components/Map/TopMenu/HamburgerMenu.tsx +++ b/src/components/Map/TopMenu/HamburgerMenu.tsx @@ -19,6 +19,13 @@ import { getIdEditorLink } from '../../../utils'; import { useUserThemeContext } from '../../../helpers/theme'; import { useOsmAuthContext } from '../../utils/OsmAuthContext'; import { LoginIcon } from './LoginIcon'; +import GithubIcon from '../../../assets/GithubIcon'; +import { LangSwitcher } from '../MapFooter/LangSwitcher'; + +const StyledGithubIcon = styled(GithubIcon)` + filter: ${({ theme }) => theme.palette.invertFilter}; + margin: -2px 8px 0 0; +`; const PencilIcon = styled(CreateIcon)` color: ${({ theme }) => theme.palette.action.active}; @@ -108,6 +115,17 @@ const AboutLink = ({ closeMenu }) => { ); }; +const GithubLink = ({ closeMenu }) => ( + + + {t('map.github_title')} + +); const InstallLink = ({ closeMenu }) => { const handleClick = () => { @@ -221,6 +239,8 @@ export const HamburgerMenu = () => { + + isBrowser() && /iPhone|iPad|iPod|Android/i.test(navigator.userAgent); // TODO this can be isomorphic ? otherwise we have hydration error + +export const useIsClient = () => { + const [isClient, setIsClient] = useState(false); + useEffect(() => { + setIsClient(true); + }, []); + return isClient; +}; diff --git a/src/locales/vocabulary.js b/src/locales/vocabulary.js index 2cb98e232..d90be8704 100644 --- a/src/locales/vocabulary.js +++ b/src/locales/vocabulary.js @@ -100,7 +100,7 @@ export default { 'opening_hours.today_closed': 'Closed today', 'opening_hours.days_su_mo_tu_we_th_fr_sa': 'Sunday|Monday|Tuesday|Wednesday|Thursday|Friday|Saturday', - 'map.github_title': 'GitHub', + 'map.github_title': 'GitHub repository', 'map.language_title': 'Change language', 'map.osm_copyright_tooltip': '(c) OpenStreetMap.org contributors
– free map data of the Earth 👌', 'map.maptiler_copyright_tooltip': '(c) MapTiler.com ❤️
– vector tiles, hosting, outdoor map
Big thanks for supporting this project! 🙂 ',