diff --git a/src/frontend/src/components/MapComponent/OpenLayersComponent/LayerSwitcher/index.js b/src/frontend/src/components/MapComponent/OpenLayersComponent/LayerSwitcher/index.js index a574f4f5d7..1e5ca13fac 100644 --- a/src/frontend/src/components/MapComponent/OpenLayersComponent/LayerSwitcher/index.js +++ b/src/frontend/src/components/MapComponent/OpenLayersComponent/LayerSwitcher/index.js @@ -161,12 +161,18 @@ const LayerSwitcherControl = ({ map, visible = 'osm' }) => { layerSwitcher.style.justifyContent = 'center'; layerSwitcher.style.alignItems = 'center'; } - if (location.pathname.includes('project_details')) { + if ( + location.pathname.includes('project_details') || + location.pathname.includes('upload-area') || + location.pathname.includes('select-form') || + location.pathname.includes('data-extract') || + location.pathname.includes('split-tasks') + ) { const olZoom = document.querySelector('.ol-zoom'); if (olZoom) { olZoom.style.display = 'none'; } - if (layerSwitcher) { + if (layerSwitcher && location.pathname.includes('project_details')) { layerSwitcher.style.right = '19px'; layerSwitcher.style.top = '250px'; layerSwitcher.style.zIndex = '1000'; diff --git a/src/frontend/src/components/MapComponent/OpenLayersComponent/Layers/VectorLayer.js b/src/frontend/src/components/MapComponent/OpenLayersComponent/Layers/VectorLayer.js index e3cb4c26d7..3ed0cc9a7f 100644 --- a/src/frontend/src/components/MapComponent/OpenLayersComponent/Layers/VectorLayer.js +++ b/src/frontend/src/components/MapComponent/OpenLayersComponent/Layers/VectorLayer.js @@ -83,7 +83,9 @@ const VectorLayer = ({ map.addInteraction(select); return () => { - // map.removeInteraction(defaultInteractions().extend([select, modify])) + // map.removeInteraction(defaultInteractions().extend([select, modify])); + map.removeInteraction(modify); + map.removeInteraction(select); }; }, [map, vectorLayer, onModify]); @@ -213,7 +215,7 @@ const VectorLayer = ({ ] : [getStyles({ style, feature, resolution })]; }); - }, [vectorLayer, style, setStyle]); + }, [vectorLayer, style, setStyle, onModify]); useEffect(() => { if (!vectorLayer) return; diff --git a/src/frontend/src/components/createnewproject/MapControlComponent.tsx b/src/frontend/src/components/createnewproject/MapControlComponent.tsx new file mode 100644 index 0000000000..93917ab5a5 --- /dev/null +++ b/src/frontend/src/components/createnewproject/MapControlComponent.tsx @@ -0,0 +1,68 @@ +import React, { useState } from 'react'; +import AssetModules from '../../shared/AssetModules'; +import VectorLayer from 'ol/layer/Vector'; +import CoreModules from '../../shared/CoreModules.js'; +import { CreateProjectActions } from '../../store/slices/CreateProjectSlice'; + +const MapControlComponent = ({ map, hasEditUndo }) => { + const dispatch = CoreModules.useAppDispatch(); + const toggleSplittedGeojsonEdit = CoreModules.useAppSelector( + (state) => state.createproject.toggleSplittedGeojsonEdit, + ); + const btnList = [ + { + id: 'Add', + icon: , + }, + { + id: 'Minus', + icon: , + }, + { + id: 'Edit', + icon: ( + + ), + }, + ]; + + const handleOnClick = (btnId) => { + if (btnId === 'Add') { + const actualZoom = map.getView().getZoom(); + map.getView().setZoom(actualZoom + 1); + } else if (btnId === 'Minus') { + const actualZoom = map.getView().getZoom(); + map.getView().setZoom(actualZoom - 1); + } else if (btnId === 'Edit') { + dispatch(CreateProjectActions.SetToggleSplittedGeojsonEdit(!toggleSplittedGeojsonEdit)); + } + }; + + return ( +
+ {btnList.map((btn) => { + return ( +
+ {((btn.id !== 'Edit' && btn.id !== 'Undo') || (btn.id === 'Edit' && hasEditUndo)) && ( +
handleOnClick(btn.id)} + > + {btn.icon} +
+ )} +
+ ); + })} +
+ ); +}; + +export default MapControlComponent; diff --git a/src/frontend/src/components/createnewproject/SplitTasks.tsx b/src/frontend/src/components/createnewproject/SplitTasks.tsx index 55e92b5ff6..d8915bc6a4 100644 --- a/src/frontend/src/components/createnewproject/SplitTasks.tsx +++ b/src/frontend/src/components/createnewproject/SplitTasks.tsx @@ -62,6 +62,9 @@ const SplitTasks = ({ flag, geojsonFile, setGeojsonFile, customLineUpload, custo ); const isTasksGenerated = CoreModules.useAppSelector((state) => state.createproject.isTasksGenerated); const isFgbFetching = CoreModules.useAppSelector((state) => state.createproject.isFgbFetching); + const toggleSplittedGeojsonEdit = CoreModules.useAppSelector( + (state) => state.createproject.toggleSplittedGeojsonEdit, + ); const toggleStep = (step, url) => { dispatch(CommonActions.SetCurrentStepFormStep({ flag: flag, step: step })); @@ -427,11 +430,17 @@ const SplitTasks = ({ flag, geojsonFile, setGeojsonFile, customLineUpload, custo splittedGeojson={dividedTaskGeojson} uploadedOrDrawnGeojsonFile={drawnGeojson} buildingExtractedGeojson={dataExtractGeojson} - onModify={(geojson) => { - handleCustomChange('drawnGeojson', geojson); - dispatch(CreateProjectActions.SetDividedTaskGeojson(JSON.parse(geojson))); - setGeojsonFile(null); - }} + onModify={ + toggleSplittedGeojsonEdit + ? (geojson) => { + handleCustomChange('drawnGeojson', geojson); + dispatch(CreateProjectActions.SetDividedTaskGeojson(JSON.parse(geojson))); + setGeojsonFile(null); + } + : null + } + // toggleSplittedGeojsonEdit + hasEditUndo /> {generateProjectLog ? ( diff --git a/src/frontend/src/components/createnewproject/validation/DataExtractValidation.tsx b/src/frontend/src/components/createnewproject/validation/DataExtractValidation.tsx index 3a72dfdc88..c913144e34 100644 --- a/src/frontend/src/components/createnewproject/validation/DataExtractValidation.tsx +++ b/src/frontend/src/components/createnewproject/validation/DataExtractValidation.tsx @@ -36,7 +36,6 @@ function DataExtractValidation(values: ProjectValues) { errors.customPolygonUpload = 'A GeoJSON file is required.'; } - console.log(errors); return errors; } diff --git a/src/frontend/src/hooks/Prompt.tsx b/src/frontend/src/hooks/Prompt.tsx index 79915cc18a..b61748154e 100644 --- a/src/frontend/src/hooks/Prompt.tsx +++ b/src/frontend/src/hooks/Prompt.tsx @@ -5,7 +5,6 @@ import { unstable_useBlocker as useBlocker } from 'react-router-dom'; function Prompt(props) { const block = props.when; useBlocker(({ nextLocation }) => { - console.log(nextLocation, 'next'); if (block && !pathNotToBlock.includes(nextLocation.pathname)) { return !window.confirm(props.message); } diff --git a/src/frontend/src/shared/AssetModules.js b/src/frontend/src/shared/AssetModules.js index adf038da20..4baba51804 100755 --- a/src/frontend/src/shared/AssetModules.js +++ b/src/frontend/src/shared/AssetModules.js @@ -56,6 +56,8 @@ import { AccessTime as AccessTimeIcon, ImportExport as ImportExportIcon, Check as CheckIcon, + Undo as UndoIcon, + Timeline as TimelineIcon, } from '@mui/icons-material'; import LockPng from '../assets/images/lock.png'; import RedLockPng from '../assets/images/red-lock.png'; @@ -122,4 +124,6 @@ export default { AccessTimeIcon, ImportExportIcon, CheckIcon, + UndoIcon, + TimelineIcon, }; diff --git a/src/frontend/src/store/slices/CreateProjectSlice.ts b/src/frontend/src/store/slices/CreateProjectSlice.ts index b8e677609d..ecdf7b33b9 100755 --- a/src/frontend/src/store/slices/CreateProjectSlice.ts +++ b/src/frontend/src/store/slices/CreateProjectSlice.ts @@ -49,6 +49,7 @@ export const initialState: CreateProjectStateTypes = { canSwitchCreateProjectSteps: false, isTasksGenerated: { divide_on_square: false, task_splitting_algorithm: false }, isFgbFetching: false, + toggleSplittedGeojsonEdit: false, }; const CreateProject = createSlice({ @@ -225,6 +226,9 @@ const CreateProject = createSlice({ state.dataExtractGeojson = null; state.projectDetails = { ...action.payload, customLineUpload: null, customPolygonUpload: null }; }, + SetToggleSplittedGeojsonEdit(state, action) { + state.toggleSplittedGeojsonEdit = action.payload; + }, }, }); diff --git a/src/frontend/src/store/types/ICreateProject.ts b/src/frontend/src/store/types/ICreateProject.ts index 2ce4a158a6..adfd719988 100644 --- a/src/frontend/src/store/types/ICreateProject.ts +++ b/src/frontend/src/store/types/ICreateProject.ts @@ -35,6 +35,7 @@ export type CreateProjectStateTypes = { canSwitchCreateProjectSteps: boolean; isTasksGenerated: {}; isFgbFetching: boolean; + toggleSplittedGeojsonEdit: boolean; }; export type ValidateCustomFormResponse = { detail: { message: string; possible_reason: string }; diff --git a/src/frontend/src/views/NewDefineAreaMap.tsx b/src/frontend/src/views/NewDefineAreaMap.tsx index 15364b012e..db465efe80 100644 --- a/src/frontend/src/views/NewDefineAreaMap.tsx +++ b/src/frontend/src/views/NewDefineAreaMap.tsx @@ -4,6 +4,7 @@ import { MapContainer as MapComponent } from '../components/MapComponent/OpenLay import LayerSwitcherControl from '../components/MapComponent/OpenLayersComponent/LayerSwitcher/index.js'; import { VectorLayer } from '../components/MapComponent/OpenLayersComponent/Layers'; import { GeoJSONFeatureTypes } from '../store/types/ICreateProject'; +import MapControlComponent from '../components/createnewproject/MapControlComponent'; type NewDefineAreaMapProps = { drawToggle?: boolean; @@ -12,7 +13,8 @@ type NewDefineAreaMapProps = { buildingExtractedGeojson?: GeoJSONFeatureTypes; lineExtractedGeojson?: GeoJSONFeatureTypes; onDraw?: (geojson: any, area: number) => void; - onModify?: (geojson: any, area?: number) => void; + onModify?: ((geojson: any, area?: number) => void) | null; + hasEditUndo?: boolean; }; const NewDefineAreaMap = ({ drawToggle, @@ -22,6 +24,7 @@ const NewDefineAreaMap = ({ lineExtractedGeojson, onDraw, onModify, + hasEditUndo, }: NewDefineAreaMapProps) => { const { mapRef, map } = useOLMap({ // center: fromLonLat([85.3, 27.7]), @@ -43,6 +46,7 @@ const NewDefineAreaMap = ({ }} > + {splittedGeojson && (