junh_eee(이준희)
10 months ago
7 changed files with 271 additions and 555 deletions
@ -1,56 +1,56 @@
|
||||
import { useState, useEffect } from 'react'; |
||||
import { Button, Modal, ModalHeader, ModalBody, ModalFooter, Card } from 'reactstrap' |
||||
import { Button, Modal, ModalHeader, ModalBody, ModalFooter } from 'reactstrap'; |
||||
|
||||
const ControlAlarmDetail = ({ historyModal, setHistoryModal, controlGpWarnLog }) => { |
||||
return ( |
||||
<Modal |
||||
isOpen={historyModal} |
||||
toggle={() => setHistoryModal(!historyModal)} |
||||
className='modal-dialog-centered historyModal' |
||||
> |
||||
<ModalHeader toggle={() => setHistoryModal(!historyModal)}> |
||||
<div className='drone-ti'> |
||||
<span className="drone-name">{controlGpWarnLog?.idntfNum}</span> |
||||
<span>알림내역</span> |
||||
</div> |
||||
</ModalHeader> |
||||
const ControlAlarmDetail = ({ |
||||
historyModal, |
||||
setHistoryModal, |
||||
controlGpWarnLog |
||||
}) => { |
||||
return ( |
||||
<Modal |
||||
isOpen={historyModal} |
||||
toggle={() => setHistoryModal(!historyModal)} |
||||
className='modal-dialog-centered historyModal' |
||||
> |
||||
<ModalHeader toggle={() => setHistoryModal(!historyModal)}> |
||||
<div className='drone-ti'> |
||||
<span className='drone-name'>{controlGpWarnLog?.idntfNum}</span> |
||||
<span>알림내역</span> |
||||
</div> |
||||
</ModalHeader> |
||||
|
||||
<ModalBody> |
||||
<table className='table pal-table'> |
||||
<tr> |
||||
<th>번호</th> |
||||
<th>식별번호</th> |
||||
<th>날짜</th> |
||||
<th>내용</th> |
||||
</tr> |
||||
{controlGpWarnLog ? |
||||
controlGpWarnLog.map((p, i) => { |
||||
return ( |
||||
<tr key={i}> |
||||
<th>{i + 1}</th> |
||||
<th>{p.idntfNum}</th> |
||||
<th>{p.createDt}</th> |
||||
<th>{p.warnType}</th> |
||||
</tr> |
||||
) |
||||
}) |
||||
: |
||||
<tr> |
||||
<th colSpan={3}>데이터가 없습니다.</th> |
||||
</tr> |
||||
} |
||||
</table> |
||||
</ModalBody> |
||||
<ModalFooter> |
||||
<Button |
||||
color='info' |
||||
onClick={() => setHistoryModal(!historyModal)} |
||||
> |
||||
확인 |
||||
</Button> |
||||
</ModalFooter> |
||||
</Modal> |
||||
) |
||||
} |
||||
<ModalBody> |
||||
<table className='table pal-table'> |
||||
<tr> |
||||
<th>번호</th> |
||||
<th>식별번호</th> |
||||
<th>날짜</th> |
||||
<th>내용</th> |
||||
</tr> |
||||
{controlGpWarnLog ? ( |
||||
controlGpWarnLog.map((p, i) => { |
||||
return ( |
||||
<tr key={i}> |
||||
<th>{i + 1}</th> |
||||
<th>{p.idntfNum}</th> |
||||
<th>{p.createDt}</th> |
||||
<th>{p.warnType}</th> |
||||
</tr> |
||||
); |
||||
}) |
||||
) : ( |
||||
<tr> |
||||
<th colSpan={3}>데이터가 없습니다.</th> |
||||
</tr> |
||||
)} |
||||
</table> |
||||
</ModalBody> |
||||
<ModalFooter> |
||||
<Button color='info' onClick={() => setHistoryModal(!historyModal)}> |
||||
확인 |
||||
</Button> |
||||
</ModalFooter> |
||||
</Modal> |
||||
); |
||||
}; |
||||
|
||||
export default ControlAlarmDetail; |
@ -1,175 +1,151 @@
|
||||
import { useEffect, useState } from 'react'; |
||||
import { X } from 'react-feather'; |
||||
import { useDispatch, useSelector } from 'react-redux'; |
||||
import { controlGpArcrftWarnAction, controlGpLogAction } from '../../../modules/control/gp/actions/controlGpAction'; |
||||
import { controlGpLogAction } from '../../../modules/control/gp/actions/controlGpAction'; |
||||
import ControlAlarmDetail from './ControlAlarmDetail'; |
||||
import { Badge } from 'reactstrap'; |
||||
|
||||
const ControlAlarmList = props => { |
||||
const dispatch = useDispatch(); |
||||
|
||||
const [historyModal, setHistoryModal] = useState(false); |
||||
|
||||
const { controlGpList } = useSelector(state => state.controlGpState); |
||||
const { controlGpArcrftWarnList } = useSelector(state => state.controlGpLogState);
|
||||
const { controlGpWarnLog } = useSelector(state => state.controlGpLogState); |
||||
const { objectId, isClickObject } = useSelector(state => state.controlMapReducer); |
||||
|
||||
|
||||
const [total, setTotal] = useState({ |
||||
totalDroneCnt: 0, |
||||
totalWarnCnt: 0, |
||||
warnList: [] |
||||
});
|
||||
|
||||
const handleWarnDetail = (cntrlId) => { |
||||
setHistoryModal(prev => !prev); |
||||
|
||||
dispatch(controlGpLogAction.request({id : cntrlId})); |
||||
const dispatch = useDispatch(); |
||||
// 비정상상황 상세 히스토리 모달
|
||||
const [historyModal, setHistoryModal] = useState(false); |
||||
|
||||
// 비정상상황 상세 히스토리
|
||||
const { controlGpWarnLog } = useSelector(state => state.controlGpLogState); |
||||
|
||||
// 비정상상황 기체 목록
|
||||
const { controlGpArcrftWarnList } = useSelector( |
||||
state => state.controlGpLogState |
||||
); |
||||
|
||||
// 클릭한 기체 Id, 비행중인 기체 클릭 여부
|
||||
const { objectId, isClickObject } = useSelector( |
||||
state => state.controlMapReducer |
||||
); |
||||
|
||||
// 전체 드론, 비정상 드론 개수
|
||||
const [total, setTotal] = useState({ |
||||
totalDroneCnt: 0, |
||||
totalWarnCnt: 0, |
||||
warnList: [] |
||||
}); |
||||
|
||||
// 비정상상황 상세 히스토리 모달 표출
|
||||
const handleWarnDetail = cntrlId => { |
||||
setHistoryModal(prev => !prev); |
||||
dispatch(controlGpLogAction.request({ id: cntrlId })); |
||||
}; |
||||
|
||||
// 비행중인 기체 클릭 시 비정상상황 사이드메뉴 닫힘
|
||||
useEffect(() => { |
||||
if (isClickObject) { |
||||
props.setOpenAlarmList(false); |
||||
} |
||||
|
||||
useEffect(() => { |
||||
if(isClickObject) {
|
||||
props.setOpenAlarmList(false); |
||||
} |
||||
|
||||
}, [objectId, isClickObject]) |
||||
|
||||
useEffect(() => { |
||||
if(controlGpArcrftWarnList) { |
||||
let totalWarnCnt = 0; |
||||
|
||||
if(controlGpArcrftWarnList.length > 0) { |
||||
controlGpArcrftWarnList.forEach(warn => { |
||||
totalWarnCnt += warn.warnCount; |
||||
}); |
||||
}
|
||||
|
||||
setTotal(total => { |
||||
return { |
||||
totalDroneCnt : controlGpArcrftWarnList.length, |
||||
totalWarnCnt : totalWarnCnt, |
||||
warnList : controlGpArcrftWarnList |
||||
}
|
||||
}) |
||||
} |
||||
|
||||
}, [controlGpArcrftWarnList]); |
||||
|
||||
return ( |
||||
<div className='left-layer'> |
||||
<div className='layer-content'> |
||||
<div className='layer-ti'> |
||||
<h4>실시간 비정상 알림 정보</h4> |
||||
<button |
||||
className='btn-icon' |
||||
// outline
|
||||
color='primary' |
||||
onClick={() => props.setOpenAlarmList(false)} |
||||
> |
||||
<X size={20} /> |
||||
</button> |
||||
</div> |
||||
<div className='layer-content-list'> |
||||
<dl className='notice-list'> |
||||
<dt> |
||||
<div className='list-ti'> |
||||
<div className='list-left-txt'>드론 현황</div> |
||||
<div className='list-right-txt'>
|
||||
<Badge color='light-primary'> |
||||
{total? total.totalDroneCnt: 0}대 비행 중 |
||||
</Badge> |
||||
</div> |
||||
</div> |
||||
</dt> |
||||
<dt> |
||||
<div className='list-ti'>
|
||||
<div className='list-left-txt'>비정상 알림 전체</div> |
||||
<div className='list-right-txt'> |
||||
<Badge color='light-primary'> |
||||
{total? total.totalWarnCnt : 0}건 |
||||
</Badge> |
||||
</div> |
||||
</div> |
||||
</dt> |
||||
</dl> |
||||
</div> |
||||
</div> |
||||
<div className='layer-content'> |
||||
<div className='layer-ti'> |
||||
<h4>알림 목록</h4> |
||||
</div> |
||||
{total?.warnList.map((warn, i) => { |
||||
const warnContent = warn.warnType === 'PLAN' ? '비행 경로 이탈' : '비정상 상황 발생' |
||||
|
||||
return ( |
||||
<div className='layer-content-list' key={i} onClick={() => handleWarnDetail(warn.cntrlId)}> |
||||
<dl className='notice-list'> |
||||
<dt> |
||||
<div className='list-ti'> |
||||
<div className='list-left-txt'>{warn.idntfNum}</div> |
||||
<div className='list-right-txt'>{warn.occurDt ? warn.occurDt : '-'}</div> |
||||
</div> |
||||
<div className='list-ti'> |
||||
<div className='list-left-txt'>{warnContent ? warnContent : '-'}</div> |
||||
<div className='list-right-txt'>{warn.warnCount ? warn.warnCount : '-'}건</div> |
||||
</div> |
||||
</dt> |
||||
</dl> |
||||
</div> |
||||
) |
||||
})} |
||||
{/* <div className='layer-content-list'> |
||||
<dl className='notice-list'> |
||||
<dt> |
||||
<div className='list-ti'> |
||||
<div className='list-left-txt'>PAV-001</div> |
||||
<div className='list-right-txt'>2022. 09. 02 10:00:30</div> |
||||
</div> |
||||
<div className='list-ti'> |
||||
<div className='list-left-txt'>비행 경로 이탈</div> |
||||
<div className='list-right-txt'>22건</div> |
||||
</div> |
||||
</dt> |
||||
</dl> |
||||
}, [objectId, isClickObject]); |
||||
|
||||
// 비정상상황 기체 개수 계산
|
||||
useEffect(() => { |
||||
if (controlGpArcrftWarnList) { |
||||
let totalWarnCnt = 0; |
||||
|
||||
if (controlGpArcrftWarnList.length > 0) { |
||||
controlGpArcrftWarnList.forEach(warn => { |
||||
totalWarnCnt += warn.warnCount; |
||||
}); |
||||
} |
||||
|
||||
setTotal(total => { |
||||
return { |
||||
totalDroneCnt: controlGpArcrftWarnList.length, |
||||
totalWarnCnt: totalWarnCnt, |
||||
warnList: controlGpArcrftWarnList |
||||
}; |
||||
}); |
||||
} |
||||
}, [controlGpArcrftWarnList]); |
||||
|
||||
return ( |
||||
<div className='left-layer'> |
||||
<div className='layer-content'> |
||||
<div className='layer-ti'> |
||||
<h4>실시간 비정상 알림 정보</h4> |
||||
<button |
||||
className='btn-icon' |
||||
color='primary' |
||||
onClick={() => props.setOpenAlarmList(false)} |
||||
> |
||||
<X size={20} /> |
||||
</button> |
||||
</div> |
||||
<div className='layer-content-list'> |
||||
<dl className='notice-list'> |
||||
<dt> |
||||
<div className='list-ti'> |
||||
<div className='list-left-txt'>드론 현황</div> |
||||
<div className='list-right-txt'> |
||||
<Badge color='light-primary'> |
||||
{total ? total.totalDroneCnt : 0}대 비행 중 |
||||
</Badge> |
||||
</div> |
||||
<div className='layer-content-list'> |
||||
<dl className='notice-list'> |
||||
<dt> |
||||
<div className='list-ti'> |
||||
<div className='list-left-txt'>PAV-002</div> |
||||
<div className='list-right-txt'>2022. 09. 02 11:23:52</div> |
||||
</div> |
||||
<div className='list-ti'> |
||||
<div className='list-left-txt'>비행 경로 이탈</div> |
||||
<div className='list-right-txt'>10건</div> |
||||
</div> |
||||
</dt> |
||||
</dl> |
||||
</div> |
||||
</dt> |
||||
<dt> |
||||
<div className='list-ti'> |
||||
<div className='list-left-txt'>비정상 알림 전체</div> |
||||
<div className='list-right-txt'> |
||||
<Badge color='light-primary'> |
||||
{total ? total.totalWarnCnt : 0}건 |
||||
</Badge> |
||||
</div> |
||||
<div className='layer-content-list'> |
||||
<dl className='notice-list'> |
||||
<dt> |
||||
<div className='list-ti'> |
||||
<div className='list-left-txt'>PAV-003</div> |
||||
<div className='list-right-txt'>-</div> |
||||
</div> |
||||
<div className='list-ti'> |
||||
<div className='list-left-txt'>-</div> |
||||
<div className='list-right-txt'>0건</div> |
||||
</div> |
||||
</dt> |
||||
</dl> |
||||
</div> */} |
||||
</div> |
||||
|
||||
<ControlAlarmDetail
|
||||
historyModal={historyModal} |
||||
setHistoryModal={setHistoryModal} |
||||
controlGpWarnLog={controlGpWarnLog} |
||||
/> |
||||
</div> |
||||
</dt> |
||||
</dl> |
||||
</div> |
||||
</div> |
||||
<div className='layer-content'> |
||||
<div className='layer-ti'> |
||||
<h4>알림 목록</h4> |
||||
</div> |
||||
); |
||||
{total?.warnList.map((warn, i) => { |
||||
const warnContent = |
||||
warn.warnType === 'PLAN' ? '비행 경로 이탈' : '비정상 상황 발생'; |
||||
|
||||
return ( |
||||
<div |
||||
className='layer-content-list' |
||||
key={i} |
||||
onClick={() => handleWarnDetail(warn.cntrlId)} |
||||
> |
||||
<dl className='notice-list'> |
||||
<dt> |
||||
<div className='list-ti'> |
||||
<div className='list-left-txt'>{warn.idntfNum}</div> |
||||
<div className='list-right-txt'> |
||||
{warn.occurDt ? warn.occurDt : '-'} |
||||
</div> |
||||
</div> |
||||
<div className='list-ti'> |
||||
<div className='list-left-txt'> |
||||
{warnContent ? warnContent : '-'} |
||||
</div> |
||||
<div className='list-right-txt'> |
||||
{warn.warnCount ? warn.warnCount : '-'}건 |
||||
</div> |
||||
</div> |
||||
</dt> |
||||
</dl> |
||||
</div> |
||||
); |
||||
})} |
||||
</div> |
||||
|
||||
<ControlAlarmDetail |
||||
historyModal={historyModal} |
||||
setHistoryModal={setHistoryModal} |
||||
controlGpWarnLog={controlGpWarnLog} |
||||
/> |
||||
</div> |
||||
); |
||||
}; |
||||
|
||||
export default ControlAlarmList; |
||||
|
@ -1,45 +0,0 @@
|
||||
import { Bell, ChevronDown, ChevronUp } from "react-feather"; |
||||
import { ReactComponent as DroneMenuIcon } from '../../../assets/images/drone_menu_icon.svg'; |
||||
|
||||
const ControlAlarmNotice = () => { |
||||
{} |
||||
return( |
||||
|
||||
<div> |
||||
{/* <div className='notice'> |
||||
<div className='notice-icon'> |
||||
<Bell size={20} /> |
||||
</div> |
||||
<div className='notice-txt'> |
||||
<dl> |
||||
<dt> |
||||
<span className='time'>2021-06-17 12:00:00</span>AVSF123 장애물 |
||||
지역에 접근하였습니다111. |
||||
</dt> |
||||
<dt> |
||||
<span className='time'>2021-06-30 13:00:00</span>AVSF123 |
||||
비행금지구역에 접근하였습니다. |
||||
</dt> |
||||
<dt> |
||||
<span className='time'>2021-08-20 14:00:00</span>AVSF123 |
||||
국립공원구역에 접근하였습니다. |
||||
</dt> |
||||
</dl> |
||||
</div> |
||||
<div className='notice-btn'> |
||||
<button> |
||||
<ChevronUp size={15} /> |
||||
</button> |
||||
<button> |
||||
<ChevronDown size={15} /> |
||||
</button> |
||||
</div> |
||||
</div> */} |
||||
|
||||
</div> |
||||
|
||||
|
||||
) |
||||
} |
||||
|
||||
export default ControlAlarmNotice; |
Loading…
Reference in new issue