diff --git a/public/img/background_start_tiny_at.jpeg b/public/img/background_start_tiny_at.jpeg deleted file mode 100644 index 935fdf29..00000000 Binary files a/public/img/background_start_tiny_at.jpeg and /dev/null differ diff --git a/public/img/background_start_tiny_ch.jpeg b/public/img/background_start_tiny_ch.jpeg deleted file mode 100644 index 28968c43..00000000 Binary files a/public/img/background_start_tiny_ch.jpeg and /dev/null differ diff --git a/public/img/background_start_tiny_de.jpeg b/public/img/background_start_tiny_de.jpeg deleted file mode 100644 index cbfb1e31..00000000 Binary files a/public/img/background_start_tiny_de.jpeg and /dev/null differ diff --git a/public/img/background_start_tiny_fr.jpeg b/public/img/background_start_tiny_fr.jpeg deleted file mode 100644 index 1bbc5e44..00000000 Binary files a/public/img/background_start_tiny_fr.jpeg and /dev/null differ diff --git a/public/img/background_start_tiny_it.jpeg b/public/img/background_start_tiny_it.jpeg deleted file mode 100644 index 50cc7c8d..00000000 Binary files a/public/img/background_start_tiny_it.jpeg and /dev/null differ diff --git a/public/img/background_start_tiny_li.jpeg b/public/img/background_start_tiny_li.jpeg deleted file mode 100644 index 50660418..00000000 Binary files a/public/img/background_start_tiny_li.jpeg and /dev/null differ diff --git a/public/img/background_start_tiny_si.jpeg b/public/img/background_start_tiny_si.jpeg deleted file mode 100644 index 75900f2d..00000000 Binary files a/public/img/background_start_tiny_si.jpeg and /dev/null differ diff --git a/public/index.html b/public/index.html index d0b711d2..74f855a4 100644 --- a/public/index.html +++ b/public/index.html @@ -1,15 +1,6 @@ - - - - - - - - - @@ -21,31 +12,10 @@ - - - - - - - - - - - - - - - -
- \ No newline at end of file diff --git a/src/App.css b/src/App.css index 56165efa..562bdcdb 100644 --- a/src/App.css +++ b/src/App.css @@ -1859,3 +1859,11 @@ top:250px; */ } + +.disabled-button { + background-color: #e0e0e0 !important; + color: #9e9e9e !important; + cursor: not-allowed; + pointer-events: none; + box-shadow: none; +} diff --git a/src/App.js b/src/App.js index 088896ba..b8565059 100644 --- a/src/App.js +++ b/src/App.js @@ -1,119 +1,97 @@ -import CircularProgress from "@mui/material/CircularProgress"; -import ThemeProvider from "@mui/material/styles/ThemeProvider"; import * as React from "react"; -import { lazy, Suspense } from "react"; -import { Navigate, Route, Routes } from "react-router-dom"; import "./App.css"; -import ModalRoot from "./components/ModalRoot"; +import ThemeProvider from "@mui/material/styles/ThemeProvider"; import { theme } from "./theme"; -import Start from "./views/Start/Start"; +import ModalRoot from "./components/ModalRoot"; +import { Route, Routes, Navigate } from "react-router-dom"; +import { lazy, Suspense, useCallback } from "react"; +import CircularProgress from "@mui/material/CircularProgress"; +// import Start from "./views/Start/Start"; // import DetailReworked from "./views/Main/DetailReworked"; // import Search from "./components/Search/Search"; import i18next from "i18next"; import { getTopLevelDomain } from "./utils/globals"; -import "/src/config.js"; +import '/src/config.js'; const Main = lazy(() => import("./views/Main/Main")); const Impressum = lazy(() => import("./views/Pages/Impressum")); const Privacy = lazy(() => import("./views/Pages/Privacy")); -const DetailReworked = lazy(() => import("./views/Main/DetailReworked")); -const Search = lazy(() => import("./components/Search/Search")); -// const Start = lazy(() => import("./views/Start/Start")); +const DetailReworked = lazy(() => import("./views/Main/DetailReworked")); +const Search = lazy(() => import("./components/Search/Search")); +const Start = lazy(() => import("./views/Start/Start")); + + + function App() { - //check if first visit and change code to domain language - if (!localStorage.getItem("visited")) { - let domain = getTopLevelDomain(); + //check if first visit and change code to domain language + if(!localStorage.getItem('visited')) { + + let domain = getTopLevelDomain(); + + //switch to domain language + switch (domain) { + case 'si': + i18next.changeLanguage('sl'); + break; + case 'fr': + i18next.changeLanguage('fr'); + break; + case 'it': + i18next.changeLanguage('it'); + break; + default: + i18next.changeLanguage('de'); + break; + } + + localStorage.setItem('visited',true); + } + + // Matomo tracking + var _mtm = window._mtm = window._mtm || []; + React.useEffect(() => { + _mtm.push({'mtm.startTime': (new Date().getTime()), 'event': 'mtm.Start'}); + var d=document, g=d.createElement('script'), s=d.getElementsByTagName('script')[0]; + g.async=true; g.src='https://stats.bahnzumberg.at/js/container_ANAXmMKf.js'; s.parentNode.insertBefore(g,s); + let language = i18next.resolvedLanguage; + _mtm.push({'language': language}); + }); - //switch to domain language - switch (domain) { - case "si": - i18next.changeLanguage("sl"); - break; - case "fr": - i18next.changeLanguage("fr"); - break; - case "it": - i18next.changeLanguage("it"); - break; - default: - i18next.changeLanguage("de"); - break; - } - localStorage.setItem("visited", true); - } - // Matomo tracking - var _mtm = (window._mtm = window._mtm || []); - React.useEffect(() => { - _mtm.push({ - "mtm.startTime": new Date().getTime(), - event: "mtm.Start", - }); - var d = document, - g = d.createElement("script"), - s = d.getElementsByTagName("script")[0]; - g.async = true; - g.src = "https://stats.bahnzumberg.at/js/container_ANAXmMKf.js"; - s.parentNode.insertBefore(g, s); - let language = i18next.resolvedLanguage; - _mtm.push({ language: language }); - }, []); + return ( + <> + +
+ + +
+ } + > + + } /> + } /> + } /> + } /> + } /> + } /> + } /> + } /> + } /> + } /> - return ( - <> - -
- - -
- } - > - - } /> - } /> - } /> - } - /> - } /> - } - /> - } /> - } /> - } /> - } /> + } /> + + + + +
+ - } - /> -
- - - -
- - ); + ); } export default App; diff --git a/src/components/Filter/Filter.js b/src/components/Filter/Filter.js index 61c387af..f0fe0f45 100644 --- a/src/components/Filter/Filter.js +++ b/src/components/Filter/Filter.js @@ -287,14 +287,20 @@ function Filter({filter, doSubmit, resetFilter, searchParams, loadFilter, isLoad } } - const submit = () => { + let swLat = !!coordinatesSouthWest?.lat && (coordinatesSouthWest?.lat).toFixed(6); + let swLng = !!coordinatesSouthWest?.lng && (coordinatesSouthWest?.lng).toFixed(6); + let neLat = !!coordinatesNorthEast?.lat && (coordinatesNorthEast?.lat).toFixed(6); + let neLng = !!coordinatesNorthEast?.lng && (coordinatesNorthEast?.lng).toFixed(6); const filterValues = { //coordinates: coordinates, //Füg den Wert in die URL ein - coordinatesSouthWest: coordinatesSouthWest, - coordinatesNorthEast: coordinatesNorthEast, + // s: !!coordinatesSouthWest?.lat && (coordinatesSouthWest?.lat).toFixed(6), + s: swLat, + w: swLng, + n: neLat, + e: neLng, singleDayTour: mapPosNegValues(singleDayTour), multipleDayTour: mapPosNegValues(multipleDayTour), summerSeason: mapPosNegValues(summerSeason), @@ -315,7 +321,7 @@ function Filter({filter, doSubmit, resetFilter, searchParams, loadFilter, isLoad } localStorage.setItem("filterValues", JSON.stringify(filterValues)); localStorage.setItem("filterCount", countFilterActive()); - doSubmit({filterValues: filterValues, filterCount: countFilterActive()}); + countFilterActive() > 0 && doSubmit({filterValues: filterValues, filterCount: countFilterActive()}); } const checkIfCheckedFromCheckbox = (list, key) => { @@ -712,11 +718,22 @@ function Filter({filter, doSubmit, resetFilter, searchParams, loadFilter, isLoad justifyContent: { xs: "center", sm: "end" } }}> - + + {/* */} diff --git a/src/components/InteractiveMap.js b/src/components/InteractiveMap.js index 4b6578e5..7718c119 100644 --- a/src/components/InteractiveMap.js +++ b/src/components/InteractiveMap.js @@ -1,6 +1,6 @@ import * as React from 'react'; import {useRef, useEffect, useMemo} from 'react'; -import { MapContainer, TileLayer, Marker, Polyline, useMap } from 'react-leaflet'; +import { MapContainer, TileLayer, Marker, Polyline, useMap, ZoomControl } from 'react-leaflet'; import 'leaflet/dist/leaflet.css'; import L, { divIcon } from 'leaflet'; @@ -81,6 +81,7 @@ useEffect(() => { center={[47.800499, 13.04441]} zoom={12} style={{ height: "100%", width: "100%" }} + zoomControl={false} // whenCreated={(mapInstance)=> { mapRef.current = mapInstance }} > @@ -108,6 +109,7 @@ useEffect(() => { positions={abreiseGpxPositions} /> )} + ) } \ No newline at end of file diff --git a/src/components/Itinerary/ItineraryCalendar.js b/src/components/Itinerary/ItineraryCalendar.js index 83b86274..5dc62213 100644 --- a/src/components/Itinerary/ItineraryCalendar.js +++ b/src/components/Itinerary/ItineraryCalendar.js @@ -1,88 +1,87 @@ +import React from "react"; import moment from "moment"; import "moment/locale/de"; import "moment/locale/fr"; import "moment/locale/it"; import "moment/locale/sl"; -import React from "react"; import { useTranslation } from "react-i18next"; +import * as _ from "lodash"; const formatDate = (date, locale) => { - const formats = { - fr: "dddd D MMMM YYYY", - de: "dddd, D. MMMM YYYY", - sl: "dddd, D. MMMM YYYY", - it: "dddd D MMMM YYYY", - en: "dddd, D MMMM YYYY", - }; - moment.locale(locale); - return date.format(formats[locale]); + const formats = { + fr: "dddd D MMMM YYYY", + de: "dddd, D. MMMM YYYY", + sl: "dddd, D. MMMM YYYY", + it: "dddd D MMMM YYYY", + en: "dddd, D MMMM YYYY", + }; + moment.locale(locale); + return date.format(formats[locale]); }; const dayOfWeek = (date, locale) => { - moment.locale(locale); - return moment(date).format("dd"); + moment.locale(locale); + return moment(date).format("dd"); }; const isWe = (date) => { - const d = date.isoWeekday(); - return d === 6 || d === 7; + const d = date.isoWeekday(); + return d === 6 || d === 7; }; const isSelectedDay = (date, selectedDay) => { - return date.isSame(selectedDay, "day"); + return date.isSame(selectedDay, "day"); }; -const ItineraryCalendar = ({ connectionData, dateIndex, updateConnIndex }) => { - const { t, i18n } = useTranslation(); - let selectedDay = dateIndex; - let days = []; +const ItineraryCalendar = ({ + connectionData, + dateIndex, + updateConnIndex +}) => { + const { t, i18n } = useTranslation(); + let selectedDay = dateIndex; + let days = []; - if (!connectionData || (!dateIndex && dateIndex !== 0)) { - return <>; - } else { - days = connectionData?.map((con) => moment(con.date)); - } + if (!connectionData || (!dateIndex && dateIndex !== 0)) { + return <>; + } else { + days = _.map(connectionData, (con) => moment(con.date)); + } - return ( -
-
- {formatDate( - moment(connectionData[selectedDay].date), - i18n.language - )} -
-
- {days.map((dd) => ( -
- {dayOfWeek(dd, i18n.language)} -
- ))} - {days.map((dd, index) => ( -
updateConnIndex(index)} - > - {dd.date()} -
- ))} -
-
- ); + return ( +
+
+ {formatDate(moment(connectionData[selectedDay].date), i18n.language)} +
+
+ {days.map((dd) => ( +
+ {dayOfWeek(dd, i18n.language)} +
+ ))} + {days.map((dd, index) => ( +
updateConnIndex(index)} + > + {dd.date()} +
+ ))} +
+
+ ); }; export default ItineraryCalendar; diff --git a/src/components/Map/TourMapContainer.js b/src/components/Map/TourMapContainer.js index af4ce987..cd9c0c76 100644 --- a/src/components/Map/TourMapContainer.js +++ b/src/components/Map/TourMapContainer.js @@ -31,7 +31,6 @@ import '/src/config.js'; const PopupCard = lazy(() => import("./PopupCard")); function TourMapContainer({ - tours, filter, setMapInitialized, mapInitialized, @@ -105,15 +104,6 @@ function TourMapContainer({ centerLat = (default_LatSW + default_LatNE) / 2; centerLng = (default_LngSW + default_LngNE) / 2; - - // storing masterMarkers list inside localStorage - useEffect(() => { - if (!isMasterMarkersSet.current && markers && markers.length > 0) { - localStorage.setItem("masterMarkers", JSON.stringify(markers)); - console.log("L112 inside markers useEffect") - isMasterMarkersSet.current = true; // Set the flag to true to avoid future updates - } - }, [markers]); const createStartMarker = () => { return L.icon({ @@ -144,22 +134,34 @@ function TourMapContainer({ : "no-city"; const [city, setCity] = useState(initialCity); const [selectedTour, setSelectedTour] = useState(null); - const [isLoading, setIsLoading] = useState(false); + const [isLoading, setIsLoading] = useState(false);// TODO : no use of isLoading ? let filterValuesLocal = !!localStorage.getItem("filterValues") ? localStorage.getItem("filterValues") : null; - filter = !!filterValuesLocal ? filterValuesLocal : filter; + // console.log("L153 filter", filter) + // console.log("L154 filterValuesLocal", filterValuesLocal) + filter = !!filterValuesLocal ? filterValuesLocal : filter; // TODO: why is that necessary? + // storing masterMarkers list inside localStorage + useEffect(() => { + if (!isMasterMarkersSet.current && markers && markers.length > 0) { + localStorage.setItem("masterMarkers", JSON.stringify(markers)); + localStorage.setItem("visibleMarkers", JSON.stringify(markers)); + isMasterMarkersSet.current = true; // Set the flag to true to avoid future updates + } + }, [markers]); + + //setMapInitialized useEffect(() => { if (!mapInitialized) { setMapInitialized(true); } }, [mapInitialized, setMapInitialized]); + // keep checking until mapRef.current is set useEffect(() => { - // keep checking until mapRef.current is set const interval = setInterval(() => { if (mapRef.current) { setMapLoaded(true); @@ -172,19 +174,25 @@ function TourMapContainer({ }, [mapRef]); + // useEffect(() => { + // console.log("L181 mapLoaded :", mapLoaded) + // }, [mapLoaded]) + // useEffect(() => { + // console.log("L185 mapBounds :", mapBounds) + // }, [mapBounds]) - useEffect(() => { - console.log("L197 mapLoaded :", mapLoaded) - - }, [mapLoaded]) - - - useEffect(() => { - console.log("L161 mapRef.current :", mapRef.current) - console.log("L162 mapBounds :", mapBounds) - console.log("L163 mapInitialized :", mapInitialized) - if (mapRef.current && mapBounds && mapInitialized) { + // useEffect(() => { + // console.log("L185 visibleMarkersArray :", visibleMarkersArray) + // }, [visibleMarkersArray]) + + +const mapChangeHandler = (bounds)=>{ + // console.log("L161 mapRef.current :", mapRef.current) + // console.log("L162 bounds :", bounds) + // console.log("L164 mapInitialized :", mapInitialized) + // console.log("L165 mapLoaded :", mapLoaded) + if ( bounds && mapInitialized) { let _masterMarkers = {}; // Retrieve master markers from local storage if available @@ -193,11 +201,11 @@ function TourMapContainer({ } let visibleMarkersObj = {}; - let visibleMarkersArray =[]; + let _visibleMarkersArray =[]; // if _masterMarkers is not empty - if (Object.keys(_masterMarkers).length > 0) { - visibleMarkersObj = getMarkersListFromBounds(mapBounds, _masterMarkers); + if (!!_masterMarkers && Object.keys(_masterMarkers).length > 0) { + visibleMarkersObj = getMarkersListFromBounds(bounds, _masterMarkers); // Early exit if no list of visible markers is found if (!visibleMarkersObj || Object.keys(visibleMarkersObj).length === 0) { @@ -207,62 +215,44 @@ function TourMapContainer({ handleShowCardContainer(true); // so we can retain the card container when markers are there } // if found extract only IDs in an array - visibleMarkersArray = createIdArray(visibleMarkersObj); + _visibleMarkersArray = createIdArray(visibleMarkersObj); } const storedMarkers = JSON.parse(localStorage.getItem("visibleMarkers")) || []; - const check = checkMarkersChanges(visibleMarkersArray, storedMarkers); + const check = checkMarkersChanges(_visibleMarkersArray, storedMarkers); - console.log("===================") - console.log("L161 check : ", check) - console.log("L162 visibleMarkersObj : ", visibleMarkersObj) - console.log("L163 visibleMarkersArray : ", visibleMarkersArray) - console.log("==================="); + // console.log("L294 check : ", check) + // console.log("===================") + // console.log("L163 _visibleMarkersArray : ", _visibleMarkersArray) + // console.log("==================="); - if (!!check && !!visibleMarkersObj && !!visibleMarkersArray) { - localStorage.setItem("visibleMarkers", JSON.stringify(visibleMarkersArray)); + if (!!check && !!visibleMarkersObj && !!_visibleMarkersArray) { + localStorage.setItem("visibleMarkers", JSON.stringify(_visibleMarkersArray)); handleChangedMarkers(true); // *** handle the Boolean flag in Main /make new call in card container let newBounds = getMarkersBounds(visibleMarkersObj) - !!newBounds ? handleMapBounds(newBounds) : handleMapBounds(mapBounds) + !!newBounds ? handleMapBounds(newBounds) : handleMapBounds(bounds) } else { handleChangedMarkers(false); } } - // eslint-disable-next-line no-use-before-define, react-hooks/exhaustive-deps - }, [mapBounds, mapInitialized]); - +} - useEffect(()=>{ - console.log("L230 mapRef.current:", mapRef.current) - console.log("L231 markers.length:", markers.length) - console.log("L232 mapLoaded:", mapLoaded) - if (markers && markers.length > 0 && mapLoaded) { - // console.log('Update bounds'); - const bounds = getMarkersBounds(markers); - console.log("L219 bounds :", bounds) - if(!!bounds && !!mapRef?.current) { - mapRef.current.fitBounds(bounds); - } - } -}, [markers, mapRef, mapLoaded]); - const getMarkersBounds = (markers) => { const _bounds = L.latLngBounds([]); - console.log("L242 _bounds ", _bounds) + // console.log("L242 _bounds ", _bounds) if(!!markers){ - console.log("L246 markers.length ", markers.length) + // console.log("L246 markers.length ", markers.length) markers.forEach((marker) => { if (marker.lat && marker.lon) { _bounds.extend([marker.lat, marker.lon]); } }); - console.log("L252 _bounds ", _bounds) - + // console.log("L252 _bounds ", _bounds) return _bounds; }else return null }; @@ -288,21 +278,28 @@ function TourMapContainer({ //saves the bounds on localStorage const assignNewMapPosition = (position) => { + // console.log("L281 position :", position) + let swLat = (position?._southWest.lat).toFixed(6); + let swLng = (position?._southWest.lng).toFixed(6); + let neLat = (position?._northEast.lat).toFixed(6); + let neLng = (position?._northEast.lng).toFixed(6); + localStorage.setItem( "MapPositionLatNE", - position?._northEast?.lat || default_LatNE + neLat || default_LatNE ); localStorage.setItem( "MapPositionLngNE", - position?._northEast?.lng || default_LngNE + neLng || default_LngNE ); + localStorage.setItem( "MapPositionLatSW", - position?._southWest?.lat || default_LatSW + swLat || default_LatSW ); localStorage.setItem( "MapPositionLngSW", - position?._southWest?.lng || default_LngSW + swLng || default_LngSW ); }; @@ -399,9 +396,9 @@ function TourMapContainer({ const _tourDetail = await onSelectTour(tourId); const _tour = _tourDetail.data.tour; if (_tour) setSelectedTour(_tour); - if (_tour && _tour.gpx_file) handleGpxTrack(_tour.gpx_file); - if (_tour && _tour.totour_gpx_file) handleTotourGpxTrack(_tour.totour_gpx_file); - if (_tour && _tour.fromtour_gpx_file) handleFromtourGpxTrack(_tour.fromtour_gpx_file); + if (_tour && _tour.gpx_file) await handleGpxTrack(_tour.gpx_file); + if (_tour && _tour.totour_gpx_file) await handleTotourGpxTrack(_tour.totour_gpx_file); + if (_tour && _tour.fromtour_gpx_file) await handleFromtourGpxTrack(_tour.fromtour_gpx_file); } catch (error) { console.error("Error fetching tour details:", error); } finally { @@ -436,15 +433,16 @@ function TourMapContainer({ moveend: () => { //Throws an event whenever the bounds of the map change // if there are markers , fit map to them else use the usual way - let position = null; - if (markers && markers.length > 0 && mapRef.current) { - position = getMarkersBounds(markers); - } else { - position = map.getBounds(); //after moving the map, a position is set and saved + let _bounds = map.getBounds(); + // console.log("L443 mapLoaded", mapLoaded) + // console.log("L444 markers.length", markers.length) + if (markers && markers.length > 0 && mapLoaded) { // replace markers with visibleMarkers + _bounds = getMarkersBounds(markers); + // console.log("L446 _bounds", _bounds) } - assignNewMapPosition(position); + assignNewMapPosition(_bounds); debouncedStoppedMoving(map.getBounds()); - handleMapBounds(map.getBounds()) + handleMapBounds(_bounds) }, }); return null; @@ -471,44 +469,56 @@ function TourMapContainer({ } function stoppedMoving(bounds) { - initiateFilter(bounds); + handleChange(bounds); + } const debouncedStoppedMoving = useMemo(() => makeDebounced(stoppedMoving, 1000), []); //Calls makeDebounce with the function you want to debounce and the debounce time - //Method to load the parameters and the filter call: - const initiateFilter = (bounds) => { + const handleChange = (bounds) => { + + //assignNewMapPosition(bounds); // saves bounds to localStorage + + let swLat = (bounds?._southWest.lat).toFixed(6); + let swLng = (bounds?._southWest.lng).toFixed(6); + let neLat = (bounds?._northEast.lat).toFixed(6); + let neLng = (bounds?._northEast.lng).toFixed(6); + + mapChangeHandler(bounds) const searchTerm = !!searchParams.get('search') ? searchParams.get('search') : null; const filterValues = { //All Values in the URL - coordinatesSouthWest: bounds?._southWest, - coordinatesNorthEast: bounds?._northEast, - singleDayTour: filter.singleDayTour, - multipleDayTour: filter.multipleDayTour, - summerSeason: filter.summerSeason, - winterSeason: filter.winterSeason, - traverse: filter.traverse, - difficulty: filter.difficulty, - minAscent: filter.minAscent, - maxAscent: filter.maxAscent, - minDescent: filter.minDescent, - maxDescent: filter.maxDescent, - minTransportDuration: filter.minTransportDuration, - maxTransportDuration: filter.maxTransportDuration, - minDistance: filter.minDistance, - maxDistance: filter.maxDistance, - ranges: filter.ranges, - types: filter.types, + s: parseFloat(swLat), + w: parseFloat(swLng), + n: parseFloat(neLat), + e: parseFloat(neLng), + singleDayTour: filter?.singleDayTour, + multipleDayTour: filter?.multipleDayTour, + summerSeason: filter?.summerSeason, + winterSeason: filter?.winterSeason, + traverse: filter?.traverse, + difficulty: filter?.difficulty, + minAscent: filter?.minAscent, + maxAscent: filter?.maxAscent, + minDescent: filter?.minDescent, + maxDescent: filter?.maxDescent, + minTransportDuration: filter?.minTransportDuration, + maxTransportDuration: filter?.maxTransportDuration, + minDistance: filter?.minDistance, + maxDistance: filter?.maxDistance, + ranges: filter?.ranges, + types: filter?.types, search: searchTerm }; if (filterValues == null) { searchParams.delete("filter"); setSearchParams(searchParams); + // localStorage.removeItem("filterValues") } else { - //pull filtervalues from localStorage and pass it to params for setting searchParams.set("filter", JSON.stringify(filterValues)); setSearchParams(searchParams); + // localStorage.setItem("filterValues", JSON.stringify(filterValues)) } //pull filtervalues from localStorage and pass it to params for setting localStorage.setItem("MapToggle", true); //The map should stay the same after rendering the page diff --git a/src/components/Search/AutosuggestSearch.js b/src/components/Search/AutosuggestSearch.js index fe2cb31e..a261c34e 100644 --- a/src/components/Search/AutosuggestSearch.js +++ b/src/components/Search/AutosuggestSearch.js @@ -1,48 +1,53 @@ import React, { useState } from "react"; import { loadSuggestions } from "../../actions/crudActions"; import CustomSelect from "./CustomSelect"; +import { isArray } from "lodash"; -const AutosuggestSearchTour = ({ onSearchSuggestion, city, language }) => { - const [options, setOptions] = useState([]); - const urlSearchParams = new URLSearchParams(window.location.search); - let searchParam = urlSearchParams.get("search"); - const [searchPhrase, setSearchPhrase] = useState(searchParam ?? ""); - const handleSelect = (phrase) => { - const value = phrase ? phrase : searchPhrase ? searchPhrase : ""; - onSearchSuggestion(value); - }; +const AutosuggestSearchTour = ({ + onSearchSuggestion, + city, + language, +}) => { - //What the component should do while I type in values - const handleInputChange = (inputValue) => { - if (city !== null) { - setSearchPhrase(inputValue); - loadSuggestions(inputValue, city.value, language) //Call the backend - .then((suggestions) => { - const newOptions = suggestions?.map((suggestion) => ({ - //Get the New suggestions and format them the correct way - label: suggestion.suggestion, - value: suggestion.suggestion, - })); - newOptions && - Array.isArray(newOptions) && - setOptions([...newOptions]); - }) - .catch((err) => { - console.error(err); - }); - } - }; + const [options, setOptions] = useState([]); + const urlSearchParams = new URLSearchParams(window.location.search); + let searchParam = urlSearchParams.get("search"); + const [searchPhrase, setSearchPhrase] = useState(searchParam ?? ""); - return ( -
- -
- ); + const handleSelect = (phrase) => { + const value = phrase ? phrase : searchPhrase ? searchPhrase : ""; + onSearchSuggestion(value); + }; + + //What the component should do while I type in values + const handleInputChange = (inputValue) => { + if (city !== null) { + setSearchPhrase(inputValue); + loadSuggestions(inputValue, city.value, language) //Call the backend + .then((suggestions) => { + const newOptions = suggestions?.map((suggestion) => ({ + //Get the New suggestions and format them the correct way + label: suggestion.suggestion, + value: suggestion.suggestion, + })); + newOptions && isArray(newOptions) && setOptions([...newOptions]); + }) + .catch((err) => { + console.error(err); + }); + } + }; + + return ( +
+ +
+ ); }; export default AutosuggestSearchTour; diff --git a/src/components/Search/Search.js b/src/components/Search/Search.js index 62093975..9d8aadd5 100644 --- a/src/components/Search/Search.js +++ b/src/components/Search/Search.js @@ -1,35 +1,34 @@ /* eslint-disable react-hooks/exhaustive-deps */ -import { Modal, Typography, useMediaQuery } from "@mui/material"; +import * as React from "react"; +import { useRef } from "react"; import Box from "@mui/material/Box"; import Grid from "@mui/material/Grid"; -import IconButton from "@mui/material/IconButton"; -import i18next from "i18next"; -import * as React from "react"; -import { Fragment, useEffect, useRef, useState } from "react"; -import { useTranslation } from "react-i18next"; +import {loadTours } from "../../actions/tourActions"; +import { compose } from "redux"; import { connect } from "react-redux"; +import { Fragment, useEffect, useState } from "react"; +import { useSearchParams, useParams } from "react-router-dom"; +import { + parseIfNeccessary, + setOrRemoveSearchParam, + getTopLevelDomain, +} from "../../utils/globals"; import { useNavigate } from "react-router"; -import { useParams, useSearchParams } from "react-router-dom"; -import { compose } from "redux"; -import { loadCities } from "../../actions/cityActions"; import { hideModal, showModal } from "../../actions/modalActions"; -import { loadFavouriteTours, loadTours } from "../../actions/tourActions"; -import Close from "../../icons/Close"; +import FullScreenCityInput from "./FullScreenCityInput"; +import { useTranslation } from "react-i18next"; +import i18next from "i18next"; import FilterIcon from "../../icons/FilterIcon"; +import IconButton from "@mui/material/IconButton"; import GoIcon from "../../icons/GoIcon"; +import AutosuggestSearchTour from "./AutosuggestSearch"; +import Filter from "../Filter/Filter"; import SearchIcon from "../../icons/SearchIcon"; import TransportTrain from "../../icons/TransportTrain"; -import { - getTopLevelDomain, - parseIfNeccessary, - setOrRemoveSearchParam, -} from "../../utils/globals"; -import Filter from "../Filter/Filter"; -import AutosuggestSearchTour from "./AutosuggestSearch"; -import FullScreenCityInput from "./FullScreenCityInput"; -import "/src/config.js"; - -const capitalize = (str) => str?.charAt(0).toUpperCase() + str?.slice(1); +import { capitalize } from "lodash"; +import { Modal, Typography, useMediaQuery } from "@mui/material"; +import Close from "../../icons/Close"; +import '/src/config.js'; export function Search({ loadTours, @@ -48,8 +47,8 @@ export function Search({ setFilterValues, filterValues, mapBounds, - // idOne, - // cityOne + filterOn, + setFilterOn }) { //navigation const navigate = useNavigate(); @@ -137,7 +136,7 @@ export function Search({ } //setting searchPhrase to the value of the search parameter - + if (!!search) { setSearchPhrase(search); //TODO : do we need to do actual search if search is a city? see line 138 comment @@ -186,7 +185,6 @@ export function Search({ } // flag active filter if count > 0 !!filterCountLocal && setActiveFilter(filterCountLocal > 0); - // filter && setActiveFilter(countFilterActive(searchParams, filter) > 0); const bounds = !!searchParams.get("map") && @@ -209,7 +207,7 @@ export function Search({ }); result.then((res) => { - let importedMarkersArray = res.data.markers; + let importedMarkersArray = res?.data?.markers; if ( !isMasterMarkersSet.current && @@ -249,23 +247,32 @@ export function Search({ localStorage.setItem("filterCount", 0); }; - // Filter modal constructed here + + const openFilter = () => { - showModal("MODAL_COMPONENT", { - CustomComponent: Filter, - title: t("filter.filter"), - page: "main", - modalSize: "lg", - doSubmit: handleFilterSubmit, - resetFilter: handleResetFilter, - onBack: () => { - hideModal(); - }, - searchParams, - setSearchParams, - }); + setFilterOn(true) }; + useEffect(() => { + if (filterOn) { + showModal("MODAL_COMPONENT", { + CustomComponent: Filter, + title: t("filter.filter"), + page: "main", + modalSize: "lg", + doSubmit: handleFilterSubmit, + resetFilter: handleResetFilter, + onBack: () => { + setFilterOn(false); // Reset filterOn when closing the modal + hideModal(); + }, + searchParams, + setSearchParams, + filterOn: filterOn, // Now filterOn is true when the modal opens + }); + } + }, [filterOn]); + //important: // state filterValues(from Main) should be set at submission here // or be set at at handleResetFilter to null @@ -297,6 +304,7 @@ export function Search({ setCounter(0); setFilterValues(null); // reset state in parent Main resetFilterLocalStorage(); + setFilterOn(false) }; const handleFilterChange = (entry) => { @@ -371,39 +379,42 @@ export function Search({ const showCityModal = () => { if (isMobile) { - setShowMobileModal(true); - } else { - showModal("MODAL_COMPONENT", { - CustomComponent: FullScreenCityInput, - searchParams, - initialCity: cityInput, - onSelect: async (city) => { - if (!!city) { - setCityInput(city.label); - setCity(city); - pageKey === "start" && updateCapCity(city.label); - searchParams.set("city", city.value); - setSearchParams(searchParams); - window.location.reload(); - } + setShowMobileModal(true) + }else{ + + showModal("MODAL_COMPONENT", { + CustomComponent: FullScreenCityInput, + searchParams, + initialCity: cityInput, + onSelect: async (city) => { + + if (!!city) { + setCityInput(city.label); + setCity(city); + pageKey === "start" && updateCapCity(city.label); + searchParams.set('city', city.value); + setSearchParams(searchParams) + window.location.reload() + } + + hideModal(); + }, + cityOne: cityOne , + idOne: idOne , + setSearchParams, + title: "", + sourceCall: "city", + page: page, + srhBoxScrollH: document + .querySelector(".main-search-bar") + .getBoundingClientRect().top, + modalSize: "lg", + onBack: () => { + hideModal(); + }, + }); + } - hideModal(); - }, - cityOne: cityOne, - idOne: idOne, - setSearchParams, - title: "", - sourceCall: "city", - page: page, - srhBoxScrollH: document - .querySelector(".main-search-bar") - .getBoundingClientRect().top, - modalSize: "lg", - onBack: () => { - hideModal(); - }, - }); - } }; const showCityModalMobile = () => { showModal("MODAL_COMPONENT", { @@ -411,6 +422,7 @@ export function Search({ searchParams, initialCity: cityInput, onSelect: async (city) => { + if (!!cityOne && !!idOne && pageKey === "detail") { setCityInput(city.label); setCity(city.value); @@ -421,11 +433,12 @@ export function Search({ pageKey === "start" && updateCapCity(city.label); searchParams.set("city", city.value); setSearchParams(searchParams); + } hideModal(); }, - cityOne: cityOne, - idOne: idOne, + cityOne: cityOne , + idOne: idOne , setSearchParams, title: "", sourceCall: "city", @@ -613,11 +626,7 @@ export function Search({ > - {t("start.heimatbahnhof")} + {t("search.dein_heimatbahnhof")} - - {!cityInput && pageKey ? ( - - ) : ( - - )} + {pageKey !== "detail" ? ( - - {cityInput.length > 0 - ? cityInput - : t("start.heimatbahnhof")} - + + <> + {!isMobile && ( + + )} + {cityInput.length > 0 + ? `${t("search.ab_heimatbahnhof")} ${cityInput}` + : t("start.heimatbahnhof")} + + ) : !cityInput && pageKey === "detail" ? ( { - let retrievedTours = res?.data?.tours ? res.data.tours : []; - console.log("L100 retrievedTours[0]", retrievedTours[0]) + // let retrievedTours = res?.data?.tours ? res.data.tours : []; + // console.log("L100 retrievedTours[0]", retrievedTours[0]) }); }; diff --git a/src/icons/provider/logo_alpenvereinaktiv.svg b/src/icons/provider/logo_alpenvereinaktiv.svg new file mode 100644 index 00000000..5329a184 --- /dev/null +++ b/src/icons/provider/logo_alpenvereinaktiv.svg @@ -0,0 +1,4119 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/icons/provider/logo_bahnzumberg.svg b/src/icons/provider/logo_bahnzumberg.svg new file mode 100644 index 00000000..e680236d --- /dev/null +++ b/src/icons/provider/logo_bahnzumberg.svg @@ -0,0 +1,52 @@ + + + + + + + + diff --git a/src/icons/provider/logo_bergfex.svg b/src/icons/provider/logo_bergfex.svg new file mode 100644 index 00000000..5bb0758a --- /dev/null +++ b/src/icons/provider/logo_bergfex.svg @@ -0,0 +1,10 @@ + + + + + + + + + + diff --git a/src/icons/provider/logo_bergfexat.svg b/src/icons/provider/logo_bergfexat.svg new file mode 100644 index 00000000..c2aa458f --- /dev/null +++ b/src/icons/provider/logo_bergfexat.svg @@ -0,0 +1,10 @@ + + + + + + + + + + diff --git a/src/icons/provider/logo_bergfexch.svg b/src/icons/provider/logo_bergfexch.svg new file mode 100644 index 00000000..c2aa458f --- /dev/null +++ b/src/icons/provider/logo_bergfexch.svg @@ -0,0 +1,10 @@ + + + + + + + + + + diff --git a/src/icons/provider/logo_bergfexde.svg b/src/icons/provider/logo_bergfexde.svg new file mode 100644 index 00000000..c2aa458f --- /dev/null +++ b/src/icons/provider/logo_bergfexde.svg @@ -0,0 +1,10 @@ + + + + + + + + + + diff --git a/src/icons/provider/logo_bergfexit.svg b/src/icons/provider/logo_bergfexit.svg new file mode 100644 index 00000000..c2aa458f --- /dev/null +++ b/src/icons/provider/logo_bergfexit.svg @@ -0,0 +1,10 @@ + + + + + + + + + + diff --git a/src/icons/provider/logo_bergfexsi.svg b/src/icons/provider/logo_bergfexsi.svg new file mode 100644 index 00000000..c2aa458f --- /dev/null +++ b/src/icons/provider/logo_bergfexsi.svg @@ -0,0 +1,10 @@ + + + + + + + + + + diff --git a/src/icons/provider/logo_bergsteigen.svg b/src/icons/provider/logo_bergsteigen.svg new file mode 100644 index 00000000..dd1fe30c --- /dev/null +++ b/src/icons/provider/logo_bergsteigen.svg @@ -0,0 +1,45 @@ + + + + + + + diff --git a/src/icons/provider/logo_bergsteigencom.svg b/src/icons/provider/logo_bergsteigencom.svg new file mode 100644 index 00000000..dd1fe30c --- /dev/null +++ b/src/icons/provider/logo_bergsteigencom.svg @@ -0,0 +1,45 @@ + + + + + + + diff --git a/src/icons/provider/logo_bergweltencom.svg b/src/icons/provider/logo_bergweltencom.svg new file mode 100644 index 00000000..b4645a0e --- /dev/null +++ b/src/icons/provider/logo_bergweltencom.svg @@ -0,0 +1,12 @@ + + + + + + + + + + + + diff --git a/src/icons/provider/logo_bzb.svg b/src/icons/provider/logo_bzb.svg new file mode 100644 index 00000000..0465e97b --- /dev/null +++ b/src/icons/provider/logo_bzb.svg @@ -0,0 +1,4 @@ + + + + diff --git a/src/icons/provider/logo_camptocamp.svg b/src/icons/provider/logo_camptocamp.svg new file mode 100644 index 00000000..ba93af47 --- /dev/null +++ b/src/icons/provider/logo_camptocamp.svg @@ -0,0 +1,79 @@ + + + + + + + + + + + + + + + + + + + diff --git a/src/icons/provider/logo_fallback.svg b/src/icons/provider/logo_fallback.svg new file mode 100644 index 00000000..deb5f40b --- /dev/null +++ b/src/icons/provider/logo_fallback.svg @@ -0,0 +1,12 @@ + + + + + + + + + + + + diff --git a/src/icons/provider/logo_gamssteigde.svg b/src/icons/provider/logo_gamssteigde.svg new file mode 100644 index 00000000..5446df5a --- /dev/null +++ b/src/icons/provider/logo_gamssteigde.svg @@ -0,0 +1,46 @@ + + + + + + + + + + diff --git a/src/icons/provider/logo_gulliverit.svg b/src/icons/provider/logo_gulliverit.svg new file mode 100644 index 00000000..6d6c0fae --- /dev/null +++ b/src/icons/provider/logo_gulliverit.svg @@ -0,0 +1,71 @@ + + + + + + + + + + + + + + + + + diff --git a/src/icons/provider/logo_hikrorg.svg b/src/icons/provider/logo_hikrorg.svg new file mode 100644 index 00000000..0dc63dff --- /dev/null +++ b/src/icons/provider/logo_hikrorg.svg @@ -0,0 +1,46 @@ + + + + + + + + + + diff --git a/src/icons/provider/logo_hoehenrausch.svg b/src/icons/provider/logo_hoehenrausch.svg new file mode 100644 index 00000000..d76c0f37 --- /dev/null +++ b/src/icons/provider/logo_hoehenrausch.svg @@ -0,0 +1,58 @@ + + + + + + + + + + + + + + diff --git a/src/icons/provider/logo_mapzssi.svg b/src/icons/provider/logo_mapzssi.svg new file mode 100644 index 00000000..e07ed669 --- /dev/null +++ b/src/icons/provider/logo_mapzssi.svg @@ -0,0 +1,77 @@ + + + + + + + + + + + + + + + + diff --git a/src/icons/provider/logo_oew.svg b/src/icons/provider/logo_oew.svg new file mode 100644 index 00000000..60cf4b93 --- /dev/null +++ b/src/icons/provider/logo_oew.svg @@ -0,0 +1,236 @@ + + + + + + + + + + + + + + + + + + + + + diff --git a/src/icons/provider/logo_outdooractive.svg b/src/icons/provider/logo_outdooractive.svg new file mode 100644 index 00000000..7fe42599 --- /dev/null +++ b/src/icons/provider/logo_outdooractive.svg @@ -0,0 +1,53 @@ + + + + + + + + + + + diff --git a/src/icons/provider/logo_randozone.svg b/src/icons/provider/logo_randozone.svg new file mode 100644 index 00000000..c3215bc4 --- /dev/null +++ b/src/icons/provider/logo_randozone.svg @@ -0,0 +1,94 @@ + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/icons/provider/logo_steiermark.svg b/src/icons/provider/logo_steiermark.svg new file mode 100644 index 00000000..6946d58b --- /dev/null +++ b/src/icons/provider/logo_steiermark.svg @@ -0,0 +1,12 @@ + + + + + + + + + + + + diff --git a/src/icons/provider/logo_visorandocom.svg b/src/icons/provider/logo_visorandocom.svg new file mode 100644 index 00000000..95ed4e9c --- /dev/null +++ b/src/icons/provider/logo_visorandocom.svg @@ -0,0 +1,74 @@ + + + + + + + + + + + + + + + + + + diff --git a/src/icons/provider/logo_wandernsteiermarkat.svg b/src/icons/provider/logo_wandernsteiermarkat.svg new file mode 100644 index 00000000..a2c52a4c --- /dev/null +++ b/src/icons/provider/logo_wandernsteiermarkat.svg @@ -0,0 +1,12 @@ + + + + + + + + + + + + diff --git a/src/index.js b/src/index.js index 100bd020..dc9e5716 100644 --- a/src/index.js +++ b/src/index.js @@ -56,7 +56,6 @@ if (!rootElement) { - { + const { i18n } = useTranslation(); + var resolvedLanguage = i18n.language + const storedLanguage = localStorage.getItem("lang"); + const currLanguage = storedLanguage || resolvedLanguage; + return currLanguage; +} + export const simpleConvertNumToTime = (number)=> { let timeStr = convertNumToTime(number); timeStr = timeStr.replace(/ h/g, '').replace(/ min/g, ''); @@ -94,7 +103,100 @@ export const getDomainText = () => { } } -export const useResponsive = () => useMediaQuery('(max-width:600px)'); + +export const get_meta_data = (page) => { + const { t } = useTranslation(); + + let meta = []; + const _domaintext = getDomainText(); + const host = window.location.hostname; + + meta.currLang = ''; + + if (page === 'Start') { + if (_domaintext === "Zuugle.fr") { + meta.canonical = '' + meta.preconnect_bzb = ''; + } else if (_domaintext === "Zuugle.si") { + meta.canonical = '' + meta.preconnect_bzb = ''; + } else if (_domaintext === "Zuugle.de") { + meta.canonical = '' + meta.preconnect_bzb = ' ' + } else if (_domaintext === "Zuugle.it") { + meta.canonical = '' + meta.preconnect_bzb = ''; + } else if (_domaintext === "Zuugle.ch") { + meta.canonical = '' + meta.preconnect_bzb = ''; + } else if (_domaintext === "Zuugle.li") { + meta.canonical = '' + meta.preconnect_bzb = ''; + } else { + meta.canonical = ''; + meta.preconnect_bzb = ' '; + } + meta.opengraph = ''; + meta.twitter = ''; + } else if (page === 'Impressum') { + meta.preconnect_bzb = ''; + meta.canonical = '' + + '' + + '' + + '' + + '' + + '' + + ''; + meta.opengraph = ''; + meta.twitter = ''; + } else if (page === 'Privacy') { + meta.preconnect_bzb = ''; + meta.canonical = '' + + '' + + '' + + '' + + '' + + '' + + ''; + meta.opengraph = ''; + meta.twitter = ''; + } else if (page === 'Main') { + if (_domaintext === "Zuugle.fr") { + meta.canonical = '' + meta.preconnect_bzb = ''; + } else if (_domaintext === "Zuugle.si") { + meta.canonical = '' + meta.preconnect_bzb = ''; + } else if (_domaintext === "Zuugle.de") { + meta.canonical = '' + meta.preconnect_bzb = ' ' + } else if (_domaintext === "Zuugle.it") { + meta.canonical = '' + meta.preconnect_bzb = ''; + } else if (_domaintext === "Zuugle.ch") { + meta.canonical = '' + meta.preconnect_bzb = ''; + } else if (_domaintext === "Zuugle.li") { + meta.canonical = '' + meta.preconnect_bzb = ''; + } else { + meta.canonical = ''; + meta.preconnect_bzb = ' '; + } + + meta.opengraph = ''; + meta.twitter = ''; + } + + // console.log("meta: ", meta.currLang+meta.canonical+meta.preconnect_bzb+meta.opengraph+meta.twitter) + return meta.currLang+meta.canonical+meta.preconnect_bzb+meta.opengraph+meta.twitter; +} + + +export const useResponsive = () => { + const matches = useMediaQuery('(max-width:600px)'); + return !!matches; +} export function parseIfNeccessary(value) { if(value && value.constructor === "test".constructor){ @@ -104,9 +206,24 @@ export function parseIfNeccessary(value) { }; export const getTopLevelDomain = () => { - let host = window.location.hostname; - host = host.replaceAll('www2.', '').replaceAll('www.', ''); - return host.substring(host.length-2).toLowerCase(); + let domain = window.location.hostname; + let tld = "at"; + + if (domain.indexOf("zuugle.de") > 0) { + tld = "de"; + } else if (domain.indexOf("zuugle.si") > 0) { + tld = "si"; + } else if (domain.indexOf("zuugle.it") > 0) { + tld = "it"; + } else if (domain.indexOf("zuugle.ch") > 0) { + tld = "ch"; + } else if (domain.indexOf("zuugle.li") > 0) { + tld = "li"; + } else if (domain.indexOf("zuugle.fr") > 0) { + tld = "fr"; + } + + return tld; } diff --git a/src/views/Main/DetailReworked.js b/src/views/Main/DetailReworked.js index c5702a34..bcf45b73 100644 --- a/src/views/Main/DetailReworked.js +++ b/src/views/Main/DetailReworked.js @@ -43,8 +43,9 @@ import { import ArrowBefore from "../../icons/ArrowBefore"; import ShareIcon from "../../icons/ShareIcon"; import Close from "../../icons/Close"; -import { shortenText, parseFileName } from "../../utils/globals"; +import { shortenText, parseFileName, get_currLanguage } from "../../utils/globals"; import transformToDescriptionDetail from "../../utils/transformJson"; +import { Helmet } from 'react-helmet'; import '/src/config.js'; @@ -538,13 +539,48 @@ useEffect(() => { ); - return ( + + + const currLanguage = get_currLanguage(); + let page_title = 'Zuugle'; + let imageUrl=""; + let description=""; + let URL = shareUrl() + if (!!tour) { + page_title = 'Zuugle: '+tour.title+' ('+tour.provider_name+')'; + imageUrl = (tour?.image_url && tour?.image_url.length > 0) && tour?.image_url + description = (tour?.description && tour?.description.length > 0) && tour?.description + } + return ( {isTourLoading ? ( ) : ( <> + + {page_title} + + + + + + + + + + + { + (!!tour && validTour && !!tour.canonical && tour.canonical.length > 0) && tour.canonical.map((entry)=>{ + if (entry.canonical_yn === 'y'){ + return + }else{ + return + } + + }) + } + {/* close tab /modal in case no return history available ###### section */} diff --git a/src/views/Main/Main.js b/src/views/Main/Main.js index 420b9fbe..fbf663fb 100644 --- a/src/views/Main/Main.js +++ b/src/views/Main/Main.js @@ -49,28 +49,28 @@ export function Main({ const [activeFilter, setActiveFilter] = useState(false); // State used inside Search and TourCardContainer - const [filterValues, setFilterValues] = useState(null); // pass this to both Search and TourCardContainer + const [filterValues, setFilterValues] = useState(localStorage.getItem("filterValues") ?? null); // pass this to both Search and TourCardContainer +//initial value for filterValues should be +// console.log("L54 filterValues :", filterValues) + const [counter, setCounter] = useState(0); - const [mapInitialized, setMapInitialized] = useState(false); + const [mapInitialized, setMapInitialized] = useState(false); //MAP - const [showMap, setShowMap] = useState(false); - const [mapBounds, setMapBounds] = useState(null); - const [markersChanged, setMarkersChanged] = useState(false); - const [showCardContainer, setShowCardContainer] = useState(true); + const [showMap, setShowMap] = useState(false); //MAP + const [mapBounds, setMapBounds] = useState(null); //MAP + const [markersChanged, setMarkersChanged] = useState(false); //MAP + const [showCardContainer, setShowCardContainer] = useState(true); //MAP const[filterOn, setFilterOn] = useState(false); const isMobile = useMediaQuery("(max-width:678px)"); - // filter values in localStorage: - // let filterCountLocal = !!localStorage.getItem("filterCount") - // ? localStorage.getItem("filterCount") - // : null; let filterValuesLocal = !!localStorage.getItem("filterValues") ? localStorage.getItem("filterValues") : null; + //MAP setting showMap useEffect(() => { setShowMap(searchParams.get("map") === "true" ? true : false); }, [searchParams]); @@ -120,7 +120,7 @@ export function Main({ } }, [allCities]); - //updates the state of activeFilter, filterValues based on the searchParams and filter values whenever there is a change in either searchParams or filter. + //updates the state of the boolean activeFilter based on localStorage values of "filterValues" . useEffect(() => { let _filterCountLocal = getFilterCount(); !!_filterCountLocal && _filterCountLocal > 0 diff --git a/src/views/Start/Header.js b/src/views/Start/Header.js index 43415f0a..cbe2bf33 100644 --- a/src/views/Start/Header.js +++ b/src/views/Start/Header.js @@ -1,12 +1,10 @@ -import { Typography } from "@mui/material"; -import Box from "@mui/material/Box"; -import React, { lazy, useCallback, useEffect, useState } from "react"; +import { getDomainText, useResponsive } from "../../utils/globals"; import { useTranslation } from "react-i18next"; import { useSearchParams } from "react-router-dom"; import { getTotalCityTours } from "../../actions/crudActions"; -import { getDomainText } from "../../utils/globals"; -import BackgroundImageLoader from "./BackgroundImageLoader"; +import { Helmet } from "react-helmet"; import "/src/config.js"; +import BackgroundImageLoader from "./BackgroundImageLoader"; const DomainMenu = lazy(() => import("../../components/DomainMenu")); const LanguageMenu = lazy(() => import("../../components/LanguageMenu")); @@ -37,20 +35,27 @@ export default function Header({ return searchParams.get("city") || localStorage.getItem("city") || null; }, [searchParams]); - useEffect(() => { - const _city = getCity(); - if (_city) { - getTotalCityTours(_city).then((data) => - setTotalToursFromCity(data.tours_city) - ); + useEffect(() => { + let _city = getCity(); + if (!!_city) { + setLoading(true); + getTotalCityTours(city).then((data) => { + setTotalToursFromCity(data.tours_city); + if (!!data.tours_city && data.tours_city > 0) setLoading(false); + }); + } + }, [city]); - const cityObj = allCities.find((e) => e.value === _city); - if (cityObj) { - updateCapCity(cityObj.label); - searchParams.set("city", _city); - } - } - }, [getCity, allCities, searchParams, updateCapCity]); + useEffect(() => { + // city = searchParams.get("city"); + if (!!city && !!allCities && allCities.length > 0) { + const cityObj = allCities.find((e) => e.value === city); // find the city object in array "allCities" + if (!!cityObj) { + updateCapCity(cityObj.label); + searchParams.set("city", city); + } + } + }, [searchParams, city, allCities]); if (totalTours === 0) { return ( diff --git a/src/views/Start/Start.js b/src/views/Start/Start.js index 2af88f9c..a252f911 100644 --- a/src/views/Start/Start.js +++ b/src/views/Start/Start.js @@ -9,17 +9,16 @@ import { compose } from "redux"; import { loadAllCities, loadCities } from "../../actions/cityActions"; import { loadRanges } from "../../actions/rangeActions"; import { + loadTour, loadFavouriteTours, loadTotalTours, - loadTour, - loadTourConnectionsExtended, } from "../../actions/tourActions"; import { useResponsive } from "../../utils/globals"; import { getPageHeader, getTranslatedCountryName, } from "../../utils/seoPageHelper"; -import Header from "./Header"; +import MapBtn from "../../components/Search/MapBtn"; import "/src/config.js"; const RangeCardContainer = lazy(() => @@ -36,7 +35,6 @@ function Start({ loadFavouriteTours, favouriteTours, loadCities, - loadTourConnections, totalTours, loadTour, loadTotalTours, @@ -216,23 +214,60 @@ function Start({ - {getFavouriteToursText()} - - + + {getFavouriteToursText()} + + + + + + + {getRangeText()} + + + + + + +