import variables from 'modules/variables'; import { useState, memo } from 'react'; import Favourite from './Favourite'; import EventBus from 'modules/helpers/eventbus'; import { MdInfo, MdLocationOn, MdPhotoCamera, MdCrop as Resolution, MdGetApp as Download, MdVisibility as Views, MdIosShare as Share, MdSource as Source, MdFavorite as MdFavourite, MdCategory as Category, MdVisibilityOff as VisibilityOff, } from 'react-icons/md'; import Tooltip from '../../helpers/tooltip/Tooltip'; import Modal from 'react-modal'; import ShareModal from '../../helpers/sharemodal/ShareModal'; const toDataURL = async (url) => { const res = await fetch(url); return URL.createObjectURL(await res.blob()); }; const formatText = (text) => { return text.toLowerCase().replaceAll(',', '').replaceAll(' ', '-'); }; const downloadImage = async (info) => { const link = document.createElement('a'); link.href = await toDataURL(info.url); link.download = `mue-${formatText(info.credit)}-${formatText(info.location)}.jpg`; // image is more likely to be webp or avif btw document.body.appendChild(link); link.click(); document.body.removeChild(link); variables.stats.postEvent('feature', 'Background download'); }; const excludeImage = async (info) => { // eslint-disable-next-line no-restricted-globals const confirmed = confirm( variables.getMessage('widgets.background.exclude_confirm', { category: info.category }), ); if (!confirmed) return; let backgroundExclude = JSON.parse(localStorage.getItem('backgroundExclude')); backgroundExclude.push(info.pun); backgroundExclude = JSON.stringify(backgroundExclude); localStorage.setItem('backgroundExclude', backgroundExclude); EventBus.dispatch('refresh', 'background'); }; function PhotoInformation({ info, url, api }) { const [width, setWidth] = useState(0); const [height, setHeight] = useState(0); const [usePhotoMap, setPhotoMap] = useState(false); const [useMapIcon, setMapIcon] = useState(true); const [showExtraInfo, setshowExtraInfo] = useState(false); //const [showOld, setShowOld] = useState(true); const [other, setOther] = useState(false); const [shareModal, openShareModal] = useState(false); if (info.hidden === true || !info.credit) { return null; } // remove unsplash and pexels text const unsplash = variables.getMessage('widgets.background.unsplash'); const pexels = variables.getMessage('widgets.background.pexels'); let credit = info.credit; let photo = variables.getMessage('widgets.background.credit'); // unsplash and pexels credit if (info.photographerURL && info.photographerURL !== '' && !info.offline && api) { if (api === 'unsplash') { photo = ( {photo} ); credit = ( <> {info.credit} {' '} {unsplash} ); } else { photo = ( {photo} ); credit = ( <> {info.credit} {' '} {pexels} ); } } const ddgProxy = localStorage.getItem('ddgProxy') === 'true'; // get resolution const img = new Image(); img.onload = (event) => { setWidth(event.target.width); setHeight(event.target.height); }; img.src = ddgProxy && !info.offline && !url.startsWith('data:') ? variables.constants.DDG_IMAGE_PROXY + url : url; // info is still there because we want the favourite button to work if (localStorage.getItem('photoInformation') === 'false') { return (
{credit} {info.location} {info.camera} {width}x{height}
); } let showingPhotoMap = false; const photoMap = () => { if ( localStorage.getItem('photoMap') !== 'true' || !info.latitude || !info.longitude || usePhotoMap === false ) { return null; } const tile = variables.constants.API_URL + `/map?latitude=${info.latitude}&longitude=${info.longitude}`; showingPhotoMap = true; return ( location ); }; let photoMapClassList = 'map-concept'; if (photoMap() !== null) { photoMapClassList += ' photoMap'; } // only request map image if the user looks at the photo information // this is to reduce requests to the api try { document.getElementsByClassName('photoInformation')[0].onmouseover = () => { try { setPhotoMap(true); setMapIcon(false); } catch (e) {} }; } catch (e) {} return (
setOther(true)} onMouseLeave={() => setOther(false)} > openShareModal(false)} > openShareModal(false)} /> {localStorage.getItem('widgetStyle') === 'legacy' && (
{photo} {credit}
)} {localStorage.getItem('widgetStyle') !== 'legacy' || other ? (
setshowExtraInfo(true)} onMouseLeave={() => setshowExtraInfo(false)} >
{useMapIcon || photoMap() === null ? : ''}

{photoMap}

{photoMap()}
{showingPhotoMap ? (
{' '} © Mapbox{' '} {' '} •{' '} {' '} © OpenStreetMap{' '} {' '} •{' '} {' '} Improve this map{' '}
) : null}
{(showExtraInfo || other) && info.description ? info.description.length > 40 ? info.description.substring(0, 40) + '...' : info.description : info.location?.split(',').slice(-2).join(', ').trim()} {photo} {credit} {info.views && info.downloads !== null ? (
{info.views.toLocaleString()}
{info.downloads.toLocaleString()}
{!!info.likes ? (
{info.likes.toLocaleString()}
) : null}
) : null}
{showExtraInfo || other ? ( <>
{variables.getMessage('widgets.background.information')} {info.location && info.location !== 'N/A' ? (
{info.location}
) : null} {info.camera && info.camera !== 'N/A' ? (
{info.camera}
) : null}
{width}x{height}
{info.category ? (
{info.category[0].toUpperCase() + info.category.slice(1)}
) : null} {api ? (
{info.photoURL ? ( {api.charAt(0).toUpperCase() + api.slice(1)} ) : ( {api.charAt(0).toUpperCase() + api.slice(1)} )}
) : null}
{!info.offline ? ( openShareModal(true)} /> ) : null} {!info.offline ? ( downloadImage(info)} /> ) : null} {info.pun ? ( excludeImage(info)} /> ) : null}
) : null}
) : null}
); } export default memo(PhotoInformation);