From f1f2abd0a85a977af1be6104a667bcdcb9ab3630 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?junh=5Feee=28=EC=9D=B4=EC=A4=80=ED=9D=AC=29?= Date: Mon, 21 Nov 2022 14:37:24 +0900 Subject: [PATCH] =?UTF-8?q?=EB=93=9C=EB=A1=A0=EA=B4=80=EC=A0=9C=20?= =?UTF-8?q?=EB=B9=84=ED=96=89=EC=A4=91=EC=9D=B8=20=EA=B8=B0=EC=B2=B4=20?= =?UTF-8?q?=EA=B0=9C=EC=88=98=20=ED=91=9C=EC=B6=9C?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/components/map/naver/dron/DronMarker.js | 64 +++++++++++++++-- .../control/gp/actions/controlGpAction.ts | 18 ++++- .../control/gp/models/controlGpModel.ts | 19 ++++- .../control/gp/reducers/controlGpReducer.ts | 19 ++++- src/modules/control/gp/sagas/controlGpSaga.ts | 12 ++++ src/redux/reducers/rootReducer.ts | 4 +- src/views/control/main/ControlMain.js | 72 ++++++++++++++----- 7 files changed, 181 insertions(+), 27 deletions(-) diff --git a/src/components/map/naver/dron/DronMarker.js b/src/components/map/naver/dron/DronMarker.js index 48198fb..13e2d55 100644 --- a/src/components/map/naver/dron/DronMarker.js +++ b/src/components/map/naver/dron/DronMarker.js @@ -1,21 +1,20 @@ import $ from 'jquery'; -import { useEffect, useState, useLayoutEffect } from 'react'; +import { useEffect, useState } from 'react'; import { useDispatch, useSelector, shallowEqual } from 'react-redux'; import '../../../../assets/css/custom.css'; import FlightIcon from '../../../../assets/images/airplan_org.svg'; import FlightDetailIcon from '../../../../assets/images/airplan_pp.svg'; import DronIcon from '../../../../assets/images/drone-marker-icon.png'; import DronDetailIcon from '../../../../assets/images/drone-marker-icon-pulple.png'; -import { IoMdAirplane } from 'react-icons/io'; import { controlGpDtlAction, - controlGpFlightPlanAction + controlGpFlightPlanAction, + controlGpCountAction } from '../../../../modules/control/gp'; import { objectClickAction, objectUnClickAction } from '../../../../modules/control/map/actions/controlMapActions'; -import { controlGroupAuthAction } from '../../../../modules/control/gp'; import { JOIN_LIST } from '../../../../modules/basis/group/actions/basisGroupAction'; export const DronMarker = props => { @@ -34,12 +33,18 @@ export const DronMarker = props => { const { controlGpArcrftWarnList } = useSelector( state => state.controlGpLogState ); + const { user } = useSelector(state => state.authState); const { joinList } = useSelector(state => state.groupState); const [arrMarkers, setArrMarkers] = useState([]); const [arrInfos, setArrInfos] = useState([]); + const [count, setCount] = useState({ + drone: [], + flight: [] + }); + let naver = props.naver; let map = props.map; let CustomOverlay; @@ -88,6 +93,26 @@ export const DronMarker = props => { // dispatch(controlGroupAuthAction.request()); // }, [controlGpList]); + useEffect(() => { + if (count.drone.length > 0 || count.flight.length > 0) { + dispatch( + controlGpCountAction.request({ + count + }) + ); + } else { + const count = { + drone: [], + flight: [] + }; + dispatch( + controlGpCountAction.request({ + count + }) + ); + } + }, [count]); + useEffect(() => { dispatch( JOIN_LIST.request({ @@ -139,6 +164,11 @@ export const DronMarker = props => { //마커를 그린다. const addMarkers = (position, id, controlId, gps) => { + const gpsCnt = { + gps: gps, + type: '' + }; + const markerOption = {}; if (id.substring(0, 2) === 'PA') { @@ -148,10 +178,12 @@ export const DronMarker = props => { if (pal) { markerOption.url = DronIcon; markerOption.type = 'DRONE'; + gpsCnt.type = 'drone'; } else { if (user.authId === 'SUPER' || user.authId === 'ADMIN') { markerOption.url = FlightIcon; markerOption.type = 'FLIGHT'; + gpsCnt.type = 'flight'; } else { const terminal = joinList?.find(prev => prev.trmnlId === gps.trmnlId); if ( @@ -160,6 +192,7 @@ export const DronMarker = props => { ) { markerOption.url = FlightIcon; markerOption.type = 'FLIGHT'; + gpsCnt.type = 'flight'; } } } @@ -167,6 +200,7 @@ export const DronMarker = props => { if (user.authId === 'SUPER' || user.authId === 'ADMIN') { markerOption.url = FlightIcon; markerOption.type = 'FLIGHT'; + gpsCnt.type = 'flight'; } else { const terminal = joinList?.find(prev => prev.trmnlId === gps.trmnlId); if ( @@ -175,10 +209,23 @@ export const DronMarker = props => { ) { markerOption.url = FlightIcon; markerOption.type = 'FLIGHT'; + gpsCnt.type = 'flight'; } } } + if (gpsCnt.type === 'drone') { + setCount(prev => ({ + ...prev, + drone: [...prev.drone, gpsCnt] + })); + } else if (gpsCnt.type === 'flight') { + setCount(prev => ({ + ...prev, + flight: [...prev.flight, gpsCnt] + })); + } + // if (id.substring(0, 2) === 'PA') { // const pal = controlGroupAuthInfo?.find( // prev => prev.idntfNum === gps.objectId @@ -342,6 +389,15 @@ export const DronMarker = props => { if (!isExists) { removeMarkers(marker); const arrData = arrMarkers.filter(item => item.id != marker.id); + + const drone = count.drone.filter(d => d.gps.objectId != marker.id); + const flight = count.flight.filter(d => d.gps.objectId != marker.id); + + setCount({ + drone: drone, + flight: flight + }); + removeArrMarkers(arrData); if (marker.controlId === objectId) { dispatch(objectUnClickAction()); diff --git a/src/modules/control/gp/actions/controlGpAction.ts b/src/modules/control/gp/actions/controlGpAction.ts index 3c35669..33dc031 100644 --- a/src/modules/control/gp/actions/controlGpAction.ts +++ b/src/modules/control/gp/actions/controlGpAction.ts @@ -17,7 +17,8 @@ import { ControlGpWarnLogList, ControlweatherData, rescontrolweatherData, - ControlGpArcrftWarnRq + ControlGpArcrftWarnRq, + ControlGpCountState } from '../models/controlGpModel'; const CONTROL_GP_REQUEST = 'control/gp/CONTROL_GP_REQUEST'; @@ -78,6 +79,14 @@ const CONTROL_GP_ARCRFT_WARN_SUCCESS = const CONTROL_GP_ARCRFT_WARN_FAILURE = 'control/gp/arcrft/warn/CONTROL_FLIGHT_PLAN_WARN_FAILURE'; +// [관제] 비행중인 기체 수 카운트 +const CONTROL_GP_COUNT_REQUEST = + 'control/gp/flight/count/CONTROL_GP_COUNT_REQUEST'; +const CONTROL_GP_COUNT_SUCCESS = + 'control/gp/flight/count/CONTROL_GP_COUNT_SUCCESS'; +const CONTROL_GP_COUNT_FAILURE = + 'control/gp/flight/count/CONTROL_GP_COUNT_FAILURE'; + export const controlGpAction = createAsyncAction( CONTROL_GP_REQUEST, CONTROL_GP_SUCCESS, @@ -142,6 +151,12 @@ export const controlGpFlightPlanInitAction = createAction( CONTROL_FLIGHT_PLAN_INIT )(); +export const controlGpCountAction = createAsyncAction( + CONTROL_GP_COUNT_REQUEST, + CONTROL_GP_COUNT_SUCCESS, + CONTROL_GP_COUNT_FAILURE +)(); + const actions = { controlGpAction, controlGpHisAction, @@ -154,6 +169,7 @@ const actions = { controlGpArcrftWarnAction, controlGpFlightPlanInitAction, controlweatherAction + // controlGpCountAction }; export type ControlGpAction = ActionType; diff --git a/src/modules/control/gp/models/controlGpModel.ts b/src/modules/control/gp/models/controlGpModel.ts index bbd0f98..3495c8c 100644 --- a/src/modules/control/gp/models/controlGpModel.ts +++ b/src/modules/control/gp/models/controlGpModel.ts @@ -29,10 +29,23 @@ export interface ControlGpDtlState { controlWheather: rescontrolweatherData | undefined; } +export interface ControlGpCountState { + controlGpCountDrone: ControlGpCountData[] | undefined; + controlGpCountFlight: ControlGpCountData[] | undefined; +} + +export interface ControlGpCountData { + gps: ControlGpData | undefined; + type: string; +} + // export interface ControlGroupAuthState { // controlGroupAuthInfo: ControlGroupAuthData[] | undefined; // } - +// const [count, setCount] = useState({ +// drone: [], +// flight: [] +// }); export interface ControlGpHistoryData { objectId: String; lat: number; @@ -238,5 +251,7 @@ export const initiaResponseControlGpData = { controlGpArcrftWarnList: undefined, controlweatherData: undefined, rescontrolweatherData: undefined, - controlWheather: undefined + controlWheather: undefined, + controlGpCountDrone: undefined, + controlGpCountFlight: undefined }; diff --git a/src/modules/control/gp/reducers/controlGpReducer.ts b/src/modules/control/gp/reducers/controlGpReducer.ts index 2513c53..defd823 100644 --- a/src/modules/control/gp/reducers/controlGpReducer.ts +++ b/src/modules/control/gp/reducers/controlGpReducer.ts @@ -12,7 +12,8 @@ import { controlGpRtDtlAction, // controlGroupAuthAction, controlGpArcrftWarnAction, - controlweatherAction + controlweatherAction, + controlGpCountAction } from '../actions/controlGpAction'; import { ControlGpWarnLogData, @@ -24,7 +25,9 @@ import { ControlGpHisState, ControlGpState, // ControlGroupAuthState, - initiaResponseControlGpData + initiaResponseControlGpData, + ControlGpCountState, + ControlGpCountData } from '../models/controlGpModel'; export const controlGpReducer = createReducer( @@ -111,6 +114,18 @@ export const controlGpDtlReducer = createReducer< draft.controlWheather = data; }) ); + +export const controlGpCountReducer = createReducer( + initiaResponseControlGpData +).handleAction(controlGpCountAction.success, (state, action) => + produce(state, draft => { + const drone: ControlGpCountData = action.payload.count.drone; + const flight: ControlGpCountData = action.payload.count.flight; + + draft.controlGpCountDrone = drone; + draft.controlGpCountFlight = flight; + }) +); // export const controlGroupAuthReducer = createReducer< // ControlGroupAuthState, // ControlGpAction diff --git a/src/modules/control/gp/sagas/controlGpSaga.ts b/src/modules/control/gp/sagas/controlGpSaga.ts index 5d2b931..63579fd 100644 --- a/src/modules/control/gp/sagas/controlGpSaga.ts +++ b/src/modules/control/gp/sagas/controlGpSaga.ts @@ -247,6 +247,17 @@ function* controlGpArcrftWarnSaga( } } +function* controlGpCountSaga( + action: ActionType +) { + try { + const data = action.payload; + yield put(Actions.controlGpCountAction.success(data)); + } catch (error) { + yield put(Actions.controlGpCountAction.failure(error)); + } +} + export function* controlGpSaga() { yield takeEvery(Actions.controlGpAction.request, getControlGpSaga); yield takeEvery(Actions.controlGpHisAction.request, getControlGpHistorySaga); @@ -268,4 +279,5 @@ export function* controlGpSaga() { Actions.controlGpArcrftWarnAction.request, controlGpArcrftWarnSaga ); + yield takeEvery(Actions.controlGpCountAction.request, controlGpCountSaga); } diff --git a/src/redux/reducers/rootReducer.ts b/src/redux/reducers/rootReducer.ts index f9f3424..a70db3b 100644 --- a/src/redux/reducers/rootReducer.ts +++ b/src/redux/reducers/rootReducer.ts @@ -29,7 +29,8 @@ import { controlGpFltPlanReducer, controlGpSaga, ControlGpState, - controlGpLogReducer + controlGpLogReducer, + controlGpCountReducer } from '../../modules/control/gp'; import controlMapReducer from '../../modules/control/map/reducers/controlMapReducer'; import { mainDahReducer } from '../../modules/main/dash/reducers/mainDashReducer'; @@ -79,6 +80,7 @@ const rootReducer = combineReducers({ controlGpHisState: controlGpHisReducer, controlGpLogState: controlGpLogReducer, controlGpDtlState: controlGpDtlReducer, + controlGpCountState: controlGpCountReducer, // controlGroupAuthState: controlGroupAuthReducer, controlGpFltPlanState: controlGpFltPlanReducer, menuState: menuReducer, diff --git a/src/views/control/main/ControlMain.js b/src/views/control/main/ControlMain.js index ec0da88..e315c79 100644 --- a/src/views/control/main/ControlMain.js +++ b/src/views/control/main/ControlMain.js @@ -8,9 +8,7 @@ import { Sun, Map, Bell, Navigation2 } from 'react-feather'; import { AiOutlinePoweroff, AiOutlineExclamation } from 'react-icons/ai'; import { IoAlertOutline } from 'react-icons/io5'; import { ReactComponent as DroneMenuIcon } from '../../../assets/images/drone_menu_icon.svg'; -import { - Card -} from 'reactstrap'; +import { Card } from 'reactstrap'; import ControlAlarmNotice from '../alarm/ControlAlarmNotice'; import ControlReportList from '../report/ControlReportList'; import ControlReportDetail from '../report/ControlReportDetail'; @@ -19,7 +17,7 @@ import ControlAlarmList from '../alarm/ControlAlarmList'; import ControlSetting from '../setting/ControlSetting'; import WebsocketClient from '../../../components/websocket/WebsocketClient'; import { useDispatch, useSelector } from 'react-redux'; -import { controlweatherAction } from '../../../modules/control/gp/actions/controlGpAction' +import { controlweatherAction } from '../../../modules/control/gp/actions/controlGpAction'; import * as Actions from '../../../modules/account/login/actions/authAction'; import { objectUnClickAction } from '../../../modules/control/map/actions/controlMapActions'; @@ -27,10 +25,15 @@ const ControlMain = () => { const dispatch = useDispatch(); const { isClickObject } = useSelector(state => state.controlMapReducer); - const { controlGpList, controlGroupAuthInfo } = useSelector(state => state.controlGpState); + const { controlGpList, controlGroupAuthInfo } = useSelector( + state => state.controlGpState + ); const { controlDetail, controlWheather } = useSelector( state => state.controlGpDtlState ); + const { controlGpCountDrone, controlGpCountFlight } = useSelector( + state => state.controlGpCountState + ); const [alarm, setAlarm] = useState(false); const { user } = useSelector(state => state.authState); const [oepnReportList, setOpenReportList] = useState(false); @@ -95,14 +98,14 @@ const ControlMain = () => { setOpenReportList(true); dispatch(objectUnClickAction()); }; - //날씨 API + //날씨 API const rq = { nx: 37.4562557, ny: 126.7052062 - } + }; useEffect(() => { dispatch(controlweatherAction.request(rq)); - }, []) + }, []); function weathericon() { if (controlWheather) { let wheatherDetail = controlWheather.items.item; @@ -163,27 +166,52 @@ const ControlMain = () => { {/* socket_off = 클래스명 변경시 빨간색! 접속이 원할하지않을때 */} -
+
- {!isClickObject ? "인천광역시" : controlDetail?.stAreaNm} + + {!isClickObject ? '인천광역시' : controlDetail?.stAreaNm} + {weathericon()}
기온 - {!isClickObject ? controlWheather?.items.item[12].fcstValue : controlDetail?.items.item[12].fcstValue}℃ + + {!isClickObject + ? controlWheather?.items.item[12].fcstValue + : controlDetail?.items.item[12].fcstValue} + ℃ +
풍향 - + + +
풍속 - {!isClickObject ? controlWheather?.items.item[4].fcstValue : controlDetail?.items.item[4].fcstValue} m/s + + {!isClickObject + ? controlWheather?.items.item[4].fcstValue + : controlDetail?.items.item[4].fcstValue}{' '} + m/s +
@@ -196,11 +224,21 @@ const ControlMain = () => {
드론 - {controlGpList ? controlGpList.length : 0} + {/* {controlGpList ? controlGpList.length : 0} */} + + {controlGpCountDrone?.length > 0 + ? controlGpCountDrone?.length + : 0} +
항공기 - 2147대 + {/* 2147대 */} + + {controlGpCountFlight?.length > 0 + ? controlGpCountFlight?.length + : 0} +