|
@@ -11,32 +11,34 @@
|
|
|
<el-button class="btn" @click="handleCancel">取消</el-button>
|
|
|
</div>
|
|
|
</div>
|
|
|
- <div class="section-box">
|
|
|
- <div class="title2">路径列表</div>
|
|
|
- <div style="display: flex; align-content: center">
|
|
|
- <span style="margin-right: 10px; white-space: nowrap; font-size: 40px; height: 100px">选择台风:</span>
|
|
|
- <el-select
|
|
|
- v-model="selectedYear"
|
|
|
- placeholder="请选择年份"
|
|
|
- class="custom-select"
|
|
|
- popper-class="custom-select-popper"
|
|
|
- :teleported="false"
|
|
|
- style="width: 1200px; margin-left: 30px"
|
|
|
- >
|
|
|
- <el-option v-for="year in yearList" :key="year" :label="year" :value="year"></el-option>
|
|
|
- </el-select>
|
|
|
- <el-select
|
|
|
- v-model="selectedTyphoon"
|
|
|
- placeholder="请选择台风名称"
|
|
|
- class="custom-select"
|
|
|
- popper-class="custom-select-popper"
|
|
|
- :teleported="false"
|
|
|
- style="width: 1200px; margin-left: 30px"
|
|
|
- >
|
|
|
- <el-option v-for="typhoon in availableTyphoons" :key="typhoon.id" :label="typhoon.name" :value="typhoon.id"></el-option>
|
|
|
- </el-select>
|
|
|
- </div>
|
|
|
+ <!-- <div class="section-box">-->
|
|
|
+ <div class="title2">路径列表</div>
|
|
|
+ <div style="display: flex; align-content: center; justify-content: flex-start">
|
|
|
+ <span style="margin-right: 15px; white-space: nowrap; font-size: 38px; height: 100px">选择台风:</span>
|
|
|
+ <el-select
|
|
|
+ v-model="selectedYear"
|
|
|
+ placeholder="请选择年份"
|
|
|
+ class="custom-select"
|
|
|
+ popper-class="custom-select-popper"
|
|
|
+ :teleported="false"
|
|
|
+ style="width: 1200px; margin-left: 30px"
|
|
|
+ @change="handleYearChange"
|
|
|
+ >
|
|
|
+ <el-option v-for="year in yearList" :key="year" :label="year" :value="year"></el-option>
|
|
|
+ </el-select>
|
|
|
+ <el-select
|
|
|
+ v-model="selectedTyphoon"
|
|
|
+ placeholder="请选择台风名称"
|
|
|
+ class="custom-select"
|
|
|
+ popper-class="custom-select-popper"
|
|
|
+ :teleported="false"
|
|
|
+ style="width: 1200px; margin-left: 30px"
|
|
|
+ @change="handleTyphoonChange"
|
|
|
+ >
|
|
|
+ <el-option v-for="typhoon in TyphoonList" :key="typhoon.id" :label="typhoon.typhoon_name" :value="typhoon.typhoon_name"></el-option>
|
|
|
+ </el-select>
|
|
|
</div>
|
|
|
+
|
|
|
<div class="custom-table">
|
|
|
<div class="th">
|
|
|
<div class="td">过去时间</div>
|
|
@@ -46,9 +48,9 @@
|
|
|
</div>
|
|
|
<div class="table-content">
|
|
|
<div v-for="(item, index) in dataList" :key="item.id" class="tr">
|
|
|
- <div class="td">{{ item.name }}</div>
|
|
|
- <div class="td">{{ item.work_unit }}</div>
|
|
|
- <div class="td">{{ item.position }}</div>
|
|
|
+ <div class="td">{{ item.record_time }}</div>
|
|
|
+ <div class="td">{{ item.longitude }},{{ item.latitude }}</div>
|
|
|
+ <div class="td">{{ item.record_address }}</div>
|
|
|
<div class="td">
|
|
|
<div class="text" @click="handleConnect(index, item)">周边视频</div>
|
|
|
</div>
|
|
@@ -57,48 +59,109 @@
|
|
|
</div>
|
|
|
</div>
|
|
|
</template>
|
|
|
+
|
|
|
<script setup lang="ts">
|
|
|
-import { ref, reactive, onMounted, watch } from 'vue';
|
|
|
-import { getTyphoonTrajectory, getTyphoonYearList } from '@/api/globalMap/TyphoonVideo';
|
|
|
+import { ref, reactive, onMounted } from 'vue';
|
|
|
+import { getTyphoonList, getTyphoonTrajectory, getTyphoonYearList } from '@/api/globalMap/TyphoonVideo';
|
|
|
|
|
|
-const selectedYear = ref(''); //selectedYear 用于存储用户选择的年份
|
|
|
+const selectedYear = ref(''); // selectedYear 用于存储用户选择的年份
|
|
|
const yearList = ref([]); // yearList 用于存储从 getTyphoonYearList 获取的年份列表
|
|
|
-//入参
|
|
|
+const TyphoonList = ref([]);
|
|
|
+const selectedTyphoon = ref('');
|
|
|
+const dataList = reactive([]); // 数据列表
|
|
|
const queryParams = reactive({
|
|
|
- typhoon_code: ''
|
|
|
+ typhoon_code: '',
|
|
|
+ year_n: ''
|
|
|
});
|
|
|
|
|
|
-//调用函数
|
|
|
+// 调用函数
|
|
|
onMounted(() => {
|
|
|
initData();
|
|
|
});
|
|
|
|
|
|
-//调接口在 initData 函数中,首先调用 getTyphoonYearList 并处理返回的数据,将其赋值给 yearList。
|
|
|
-const initData = () => {
|
|
|
- getTyphoonYearList().then((res) => {
|
|
|
- if (res.code === 0) {
|
|
|
- yearList.value.splice(0, yearList.value.length, ...res.rows.map(item => item.year_n)); // 更新年份列表
|
|
|
- } else {
|
|
|
- console.error('Failed to fetch typhoon year list:', res);
|
|
|
+const handleYearChange = async () => {
|
|
|
+ if (selectedYear.value) {
|
|
|
+ try {
|
|
|
+ const typhoons = await getTyphoonList({ query: { year_n: selectedYear.value } });
|
|
|
+ if (typhoons.code === 0) {
|
|
|
+ TyphoonList.value = typhoons.rows;
|
|
|
+ selectedTyphoon.value = typhoons.rows[0]?.typhoon_name || '';
|
|
|
+ initDataByTyphoon();
|
|
|
+ } else {
|
|
|
+ console.error('Failed to fetch typhoon list:', typhoons);
|
|
|
+ }
|
|
|
+ } catch (error) {
|
|
|
+ console.error('Error fetching typhoon list:', error);
|
|
|
+ }
|
|
|
+ }
|
|
|
+};
|
|
|
+
|
|
|
+const handleTyphoonChange = async () => {
|
|
|
+ if (selectedTyphoon.value && selectedYear.value) {
|
|
|
+ initDataByTyphoon();
|
|
|
+ }
|
|
|
+};
|
|
|
+
|
|
|
+const initDataByTyphoon = async () => {
|
|
|
+ const typhoonCode = TyphoonList.value.find((t) => t.typhoon_name === selectedTyphoon.value)?.typhoon_code;
|
|
|
+ if (typhoonCode) {
|
|
|
+ try {
|
|
|
+ const trajectory = await getTyphoonTrajectory({ query: { typhoon_code: typhoonCode } });
|
|
|
+ if (trajectory.code === 0 && Array.isArray(trajectory.rows)) {
|
|
|
+ dataList.splice(0, dataList.length, ...trajectory.rows);
|
|
|
+ } else {
|
|
|
+ console.error('Invalid response from server:', trajectory);
|
|
|
+ dataList.splice(0, dataList.length); // 清空数据列表
|
|
|
+ }
|
|
|
+ } catch (error) {
|
|
|
+ console.error('Error fetching typhoon trajectory:', error);
|
|
|
}
|
|
|
- });
|
|
|
- getTyphoonTrajectory({
|
|
|
- query: {
|
|
|
- typhoon_code: queryParams.typhoon_code
|
|
|
+ } else {
|
|
|
+ console.error('No typhoon code found for selected typhoon name');
|
|
|
+ }
|
|
|
+};
|
|
|
+
|
|
|
+const fetchData = async (apiFunction, params) => {
|
|
|
+ try {
|
|
|
+ const response = await apiFunction(params);
|
|
|
+ if (response.code !== 0) {
|
|
|
+ throw new Error('Invalid response from server');
|
|
|
}
|
|
|
- }).then((res) => {
|
|
|
- if (res.code === 0 && Array.isArray(res.rows)) {
|
|
|
- dataList.splice(0, dataList.length, ...res.rows); // 使用 splice 替换数组内容,保持响应性
|
|
|
+ return response.rows;
|
|
|
+ } catch (error) {
|
|
|
+ console.error('Error fetching data:', error);
|
|
|
+ return [];
|
|
|
+ }
|
|
|
+};
|
|
|
+
|
|
|
+const initData = async () => {
|
|
|
+ try {
|
|
|
+ const years = await fetchData(getTyphoonYearList, {});
|
|
|
+ yearList.value = years.map((item) => item.year_n);
|
|
|
+ const year = years[0]?.year_n;
|
|
|
+ if (year) {
|
|
|
+ const typhoons = await fetchData(getTyphoonList, { query: { year_n: year } });
|
|
|
+ TyphoonList.value = typhoons;
|
|
|
+ const typhoonCode = typhoons[0]?.typhoon_code;
|
|
|
+ if (typhoonCode) {
|
|
|
+ const trajectory = await fetchData(getTyphoonTrajectory, { query: { typhoon_code: typhoonCode } });
|
|
|
+ dataList.splice(0, dataList.length, ...trajectory);
|
|
|
+ } else {
|
|
|
+ console.error('No typhoon code found in the list');
|
|
|
+ }
|
|
|
} else {
|
|
|
- console.error('Invalid response from server:', res);
|
|
|
- // 可以选择清空数据列表或显示错误消息
|
|
|
- dataList.splice(0, dataList.length); // 清空数据列表
|
|
|
+ console.error('No year found in the list');
|
|
|
}
|
|
|
- });
|
|
|
+ } catch (error) {
|
|
|
+ console.error('Error initializing data:', error);
|
|
|
+ }
|
|
|
};
|
|
|
|
|
|
-// 数据列表,直接定义为数组
|
|
|
-const dataList = reactive([]);
|
|
|
+const handleCancel = () => {
|
|
|
+ queryParams.typhoon_code = '';
|
|
|
+ queryParams.year_n = '';
|
|
|
+ initData();
|
|
|
+};
|
|
|
</script>
|
|
|
|
|
|
<style lang="scss" scoped>
|
|
@@ -112,6 +175,11 @@ const dataList = reactive([]);
|
|
|
color: #ffffff;
|
|
|
}
|
|
|
|
|
|
+.custom-input {
|
|
|
+ height: 60px;
|
|
|
+ line-height: 40px;
|
|
|
+}
|
|
|
+
|
|
|
.box-left {
|
|
|
display: flex;
|
|
|
margin-top: 30px;
|
|
@@ -190,7 +258,18 @@ const dataList = reactive([]);
|
|
|
}
|
|
|
|
|
|
.title2 {
|
|
|
- font-size: 48px;
|
|
|
- height: 100px;
|
|
|
+ font-size: 36px;
|
|
|
+ height: 80px;
|
|
|
+}
|
|
|
+
|
|
|
+.title {
|
|
|
+ font-size: 60px;
|
|
|
+ position: absolute;
|
|
|
+ top: 30px;
|
|
|
+ left: 160px;
|
|
|
+}
|
|
|
+
|
|
|
+.text {
|
|
|
+ cursor: pointer;
|
|
|
}
|
|
|
</style>
|