index.vue 23 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881
  1. <template>
  2. <view class="warning-center">
  3. <!-- 顶部导航栏 -->
  4. <custom-card>
  5. <block slot="backText">预警中心</block>
  6. </custom-card>
  7. <!-- 主要内容 -->
  8. <view class="content">
  9. <!-- 宣传语区域 -->
  10. <view class="banner">
  11. <view class="banner-text">
  12. <text class="banner-title">天灾虫害,预警在先</text>
  13. <text class="banner-subtitle">全天候监测,风险早知晓</text>
  14. </view>
  15. <view class="warning-icon">
  16. <view class="icon-triangle">
  17. <image :src="exclamation" class="icon-image" />
  18. </view>
  19. </view>
  20. </view>
  21. <!-- 日期选择器 -->
  22. <view class="date-picker">
  23. <view class="date-inputs" @click="showDatePickerHandle()">
  24. <text class="date-label">{{ startTime }}</text>
  25. <text class="date-separator">-</text>
  26. <text class="date-label">{{ endTime }}</text>
  27. <u-icon name="calendar" size="28rpx" color="#999" />
  28. </view>
  29. <view class="date-icons">
  30. <image :src="warning" class="icon-image" />
  31. </view>
  32. </view>
  33. <!-- 标签导航 -->
  34. <view class="tab-nav">
  35. <view
  36. v-for="(tab, index) in tabs"
  37. :key="index"
  38. class="tab-item"
  39. :class="{ active: activeTab === index }"
  40. @click="activeTabHandler(index)"
  41. >
  42. {{ tab }}
  43. </view>
  44. </view>
  45. <!-- 预警列表 -->
  46. <scroll-view
  47. v-if="activeTab == 0"
  48. class="warning-list"
  49. scroll-y
  50. :scroll-top="listScrollTop"
  51. scroll-with-animation
  52. @scrolltolower="loadMore"
  53. @scrolltoupper="refresh"
  54. >
  55. <view
  56. v-for="(warning, index) in warningList"
  57. :key="index"
  58. class="warning-item"
  59. @click="popupShowHandler(warning)"
  60. >
  61. <view class="warning-header">
  62. <view class="warning-type">
  63. <view class="type-icon" :class="warning.status == '0' ? 'type-blue' : 'type-gray'">
  64. <image :src="weather" class="icon-image" />
  65. </view>
  66. <text class="type-text">{{ warning.warning_title }}</text>
  67. <text class="device-type">{{ warning.device_type }}</text>
  68. </view>
  69. <view class="warning-level"
  70. :class="
  71. warning.level == '0' ? (warning.status != '0' ? 'level-normal-gray' : 'level-normal') :
  72. warning.level == '1'? (warning.status != '0' ? 'level-important-gray' : 'level-important'):
  73. (warning.status != '0' ? 'level-urgent-gray' : 'level-urgent')
  74. ">
  75. </view>
  76. </view>
  77. <view class="warning-content">
  78. {{ warning.warning_content }}
  79. </view>
  80. <view class="warning-footer">
  81. <text class="warning-time">{{ formatTime(warning.upl_time) }}</text>
  82. <view class="warning-location">
  83. <u-icon name="location" size="20rpx" color="#999" />
  84. </view>
  85. </view>
  86. <view class="location-text">
  87. <u-icon name="map" size="28"></u-icon>
  88. <text style="margin-left: 10rpx">{{ warning.address || '-' }}</text>
  89. </view>
  90. </view>
  91. <!-- 加载更多提示 -->
  92. <view class="loading-more">
  93. <text v-if="loading">加载中...</text>
  94. <text v-else-if="finished">没有更多数据了</text>
  95. <text v-else>上拉加载更多</text>
  96. </view>
  97. </scroll-view>
  98. <scroll-view
  99. v-if="activeTab == 1"
  100. class="warning-list"
  101. scroll-y
  102. :scroll-top="listScrollTop"
  103. scroll-with-animation
  104. @scrolltolower="loadMore"
  105. @scrolltoupper="refresh"
  106. >
  107. <view
  108. v-for="(warning, index) in manualWarningList"
  109. :key="index"
  110. class="warning-item"
  111. @click="popupManualShowHandler(warning)"
  112. >
  113. <view class="warning-content">
  114. {{ warning.conf }}
  115. </view>
  116. <view class="warning-footer">
  117. <text class="warning-time">{{ formatTime(warning.create_time) }}</text>
  118. <view class="warning-location">
  119. <u-icon name="location" size="20rpx" color="#999" />
  120. </view>
  121. </view>
  122. </view>
  123. <!-- 加载更多提示 -->
  124. <view class="loading-more">
  125. <text v-if="loading">加载中...</text>
  126. <text v-else-if="finished">没有更多数据了</text>
  127. <text v-else>上拉加载更多</text>
  128. </view>
  129. </scroll-view>
  130. <!-- 回到顶部 -->
  131. <view class="back-to-top" @click="scrollToTop">
  132. <u-icon name="arrow-up" size="28rpx" color="#999" />
  133. </view>
  134. </view>
  135. <u-calendar v-model="showDatePicker" :mode="mode" @change="changeCalendar"></u-calendar>
  136. <u-popup v-model="popupShow" mode="bottom" height="50%" border-radius="20">
  137. <view class="popup-container">
  138. <view class="popup-icon" :class="
  139. current.level == '0' ? (current.status != '0' ? 'popup-level-normal-gray' : 'popup-level-normal') :
  140. current.level == '1'? (current.status != '0' ? 'popup-level-important-gray' : 'popup-level-important'):
  141. (current.status != '0' ? 'popup-level-urgent-gray' : 'popup-level-urgent')
  142. ">
  143. </view>
  144. <view class="popup-header">{{ current.warning_title }}</view>
  145. <view class="popup-type">
  146. <text class="type-text">{{ current.device_type }}</text>
  147. </view>
  148. <view class="popup-content">{{ current.warning_content }}</view>
  149. <view class="popup-time">{{ formatTime(current.upl_time) }}</view>
  150. <view class="popup-text">
  151. <u-icon name="map" size="28"></u-icon>
  152. <text style="margin-left: 10rpx">{{ warning.address || '-' }}</text>
  153. </view>
  154. </view>
  155. </u-popup>
  156. <u-popup v-model="popupManualShow" mode="bottom" height="50%" border-radius="20">
  157. <view class="popup-container" style="margin-top:40rpx">
  158. <view class="popup-content">{{ currentManual.conf }}</view>
  159. <view class="popup-time">{{ formatTime(currentManual.create_time) }}</view>
  160. </view>
  161. </u-popup>
  162. </view>
  163. </template>
  164. <script>
  165. import exclamation from './assets/exclamation.png';
  166. import warning from './assets/warning.png';
  167. import pest from './assets/pest.png';
  168. import weather from './assets/weather.png';
  169. import offline from './assets/offline.png';
  170. export default {
  171. data() {
  172. return {
  173. current:{},
  174. currentManual:{},
  175. popupShow: false,
  176. popupManualShow: false,
  177. exclamation,
  178. warning,
  179. pest,
  180. weather,
  181. offline,
  182. showDatePicker: false,
  183. mode: 'range',
  184. activeTab: 0,
  185. listScrollTop: 0,
  186. tabs: ['环境监测','手动预警'],
  187. warningList: [],
  188. manualWarningList: [],
  189. page_size: 10,
  190. page: 1,
  191. // 获取7天前的日期
  192. startTime: this.getSevenDaysAgo() || '开始日期',
  193. endTime: this.getCurrentDate() || '结束日期',
  194. deviceId: '',
  195. device_type_id:'',
  196. total: 0,
  197. loading: false,
  198. finished: false,
  199. refreshing: false,
  200. };
  201. },
  202. onLoad() {
  203. this.getWarningList();
  204. },
  205. methods: {
  206. activeTabHandler(index){
  207. this.activeTab = index;
  208. this.page = 1;
  209. if(index == 0){
  210. this.getWarningList();
  211. }else if(index == 1){
  212. this.getWarningManualList();
  213. }
  214. },
  215. popupManualShowHandler(warning){
  216. this.currentManual = warning;
  217. this.popupManualShow = true;
  218. },
  219. popupShowHandler(warning){
  220. this.current = warning;
  221. const params = {
  222. record_ids: warning.id,
  223. };
  224. this.readHandler(params)
  225. this.popupShow = true;
  226. },
  227. changeCalendar(e){
  228. this.startTime = e.startDate;
  229. this.endTime = e.endDate;
  230. // 重置分页参数
  231. this.page = 1;
  232. this.loading = false;
  233. this.finished = false;
  234. if(this.activeTab == 0){
  235. this.getWarningList();
  236. }else if(this.activeTab == 1){
  237. this.getWarningManualList();
  238. }
  239. },
  240. // 加载更多
  241. loadMore() {
  242. if (this.finished) return;
  243. if(this.activeTab == 0){
  244. this.getWarningList();
  245. }else if(this.activeTab == 1){
  246. this.getWarningManualList();
  247. }
  248. },
  249. // 下拉刷新
  250. refresh() {
  251. if (this.loading) return;
  252. // 重置分页参数
  253. this.page = 1;
  254. this.loading = false;
  255. this.finished = false;
  256. this.refreshing = true;
  257. if(this.activeTab == 0){
  258. this.getWarningList();
  259. }else if(this.activeTab == 1){
  260. this.getWarningManualList();
  261. }
  262. },
  263. // 已读
  264. async readHandler(params){
  265. await this.$myRequest({
  266. url:'/api/api_gateway?method=device.env_sec_alert.update_env_sec_alert_record',
  267. method:'POST',
  268. data: params,
  269. })
  270. this.page = 1;
  271. if(this.activeTab == 0){
  272. this.getWarningList();
  273. }
  274. },
  275. formatTime(time){
  276. if(!time){
  277. return '';
  278. }
  279. const date = new Date(time * 1000);
  280. const year = date.getFullYear();
  281. const month = String(date.getMonth() + 1).padStart(2, '0');
  282. const day = String(date.getDate()).padStart(2, '0');
  283. const hour = String(date.getHours()).padStart(2, '0');
  284. const minute = String(date.getMinutes()).padStart(2, '0');
  285. const second = String(date.getSeconds()).padStart(2, '0');
  286. return `${year}-${month}-${day} ${hour}:${minute}:${second}`;
  287. },
  288. // 获取7天前的日期
  289. getSevenDaysAgo() {
  290. const today = new Date();
  291. const sevenDaysAgo = new Date(today);
  292. sevenDaysAgo.setDate(today.getDate() - 7);
  293. const year = sevenDaysAgo.getFullYear();
  294. const month = String(sevenDaysAgo.getMonth() + 1).padStart(2, '0');
  295. const day = String(sevenDaysAgo.getDate()).padStart(2, '0');
  296. return `${year}-${month}-${day}`;
  297. },
  298. // 获取当前日期
  299. getCurrentDate() {
  300. const today = new Date();
  301. const year = today.getFullYear();
  302. const month = String(today.getMonth() + 1).padStart(2, '0');
  303. const day = String(today.getDate()).padStart(2, '0');
  304. return `${year}-${month}-${day}`;
  305. },
  306. showDatePickerHandle(){
  307. this.showDatePicker = true;
  308. },
  309. // 把日期转成秒数
  310. dateToTimestamp(date) {
  311. return Math.floor(new Date(date).getTime() / 1000);
  312. },
  313. async getWarningManualList(){
  314. if (this.loading) return;
  315. this.loading = true;
  316. const start = this.dateToTimestamp(this.startTime + ' 00:00:00');
  317. const end = this.dateToTimestamp(this.endTime + ' 23:59:59');
  318. const params = {
  319. start,
  320. end,
  321. page: this.page,
  322. page_size: this.page_size,
  323. device_id: this.deviceId,
  324. device_type_id: this.device_type_id
  325. }
  326. try {
  327. const res = await this.$myRequest({
  328. url:'/api/api_gateway?method=device.env_sec_alert.get_manual_env_sec_alert_record',
  329. method:'POST',
  330. data: params,
  331. })
  332. const resData = res?.data || [];
  333. const list = resData || [];
  334. if (this.page === 1) {
  335. this.manualWarningList = list;
  336. } else {
  337. this.manualWarningList = [...this.manualWarningList, ...list];
  338. }
  339. this.total = res?.total || 0;
  340. this.loading = false;
  341. // 计算是否还有更多数据
  342. if (this.manualWarningList.length >= this.total) {
  343. this.finished = true;
  344. } else {
  345. this.page++;
  346. }
  347. // 结束刷新状态
  348. if (this.refreshing) {
  349. this.refreshing = false;
  350. }
  351. } catch (error) {
  352. console.error('获取预警列表失败:', error);
  353. this.loading = false;
  354. if (this.refreshing) {
  355. this.refreshing = false;
  356. }
  357. }
  358. },
  359. async getWarningList(){
  360. if (this.loading) return;
  361. this.loading = true;
  362. const start = this.dateToTimestamp(this.startTime + ' 00:00:00');
  363. const end = this.dateToTimestamp(this.endTime + ' 23:59:59');
  364. const params = {
  365. start,
  366. end,
  367. page: this.page,
  368. page_size: this.page_size,
  369. device_id: this.deviceId,
  370. device_type_id: this.device_type_id
  371. }
  372. try {
  373. const res = await this.$myRequest({
  374. url:'/api/api_gateway?method=device.env_sec_alert.get_env_sec_alert',
  375. method:'POST',
  376. data: params,
  377. })
  378. const resData = res?.data || [];
  379. const list = resData || [];
  380. if (this.page === 1) {
  381. this.warningList = list;
  382. } else {
  383. this.warningList = [...this.warningList, ...list];
  384. }
  385. this.total = res?.total_num || 0;
  386. this.loading = false;
  387. // 计算是否还有更多数据
  388. if (this.warningList.length >= this.total) {
  389. this.finished = true;
  390. } else {
  391. this.page++;
  392. }
  393. // 结束刷新状态
  394. if (this.refreshing) {
  395. this.refreshing = false;
  396. }
  397. } catch (error) {
  398. console.error('获取预警列表失败:', error);
  399. this.loading = false;
  400. if (this.refreshing) {
  401. this.refreshing = false;
  402. }
  403. }
  404. },
  405. // 回到顶部
  406. scrollToTop() {
  407. this.listScrollTop = 0;
  408. }
  409. }
  410. };
  411. </script>
  412. <style scoped lang="scss">
  413. .warning-center {
  414. min-height: 100vh;
  415. font-family: 'Source Han Sans CN';
  416. background: linear-gradient(0deg, #F5F6FA 79.64%, #FFEEEC 99.35%);
  417. }
  418. ::v-deep .u-calendar__action{
  419. display:flex;
  420. }
  421. ::v-deep .u-calendar__action__icon{
  422. width: 40rpx;
  423. }
  424. ::v-deep .u-calendar__action__text{
  425. width: calc(100% - 160rpx);
  426. text-align: center;
  427. }
  428. .content {
  429. padding: 0 32rpx;
  430. }
  431. /* 宣传语区域 */
  432. .banner {
  433. display: flex;
  434. align-items: center;
  435. justify-content: space-between;
  436. margin: 32rpx 0;
  437. margin-bottom: 0rpx;
  438. padding: 24rpx;
  439. .banner-text {
  440. flex: 1;
  441. .banner-title {
  442. font-style: italic;
  443. display: block;
  444. color: #303133;
  445. font-family: "Source Han Sans CN VF";
  446. font-size: 40rpx;
  447. font-weight: 700;
  448. margin-bottom: 8rpx;
  449. }
  450. .banner-subtitle {
  451. display: block;
  452. font-size: 24rpx;
  453. color: #666666;
  454. }
  455. }
  456. .warning-icon {
  457. .icon-triangle {
  458. width: 130rpx;
  459. height: 130rpx;
  460. position: relative;
  461. .icon-image{
  462. width: 100%;
  463. height: 100%;
  464. }
  465. }
  466. }
  467. }
  468. .popup-container{
  469. position:relative;
  470. .popup-icon {
  471. position: absolute;
  472. top:0;
  473. right:0;
  474. margin-left: 12rpx;
  475. width: 112rpx;
  476. height: 48rpx;
  477. background: url('./assets/normal-gray.png');
  478. background-repeat: no-repeat;
  479. background-size: 100%;
  480. &.popup-level-normal {
  481. background: url('./assets/normal.png');
  482. background-repeat: no-repeat;
  483. background-size: 100%;
  484. }
  485. &.popup-level-normal-gray {
  486. background: url('./assets/normal-gray.png');
  487. background-repeat: no-repeat;
  488. background-size: 100%;
  489. }
  490. &.popup-level-important-gray {
  491. background: url('./assets/important-gray.png');
  492. background-repeat: no-repeat;
  493. background-size: 100%;
  494. }
  495. &.popup-level-important {
  496. background: url('./assets/important.png');
  497. background-repeat: no-repeat;
  498. background-size: 100%;
  499. }
  500. &.popup-level-urgent-gray {
  501. background: url('./assets/urgent-gray.png');
  502. background-repeat: no-repeat;
  503. background-size: 100%;
  504. }
  505. &.popup-level-urgent {
  506. background: url('./assets/urgent.png');
  507. background-repeat: no-repeat;
  508. background-size: 100%;
  509. }
  510. }
  511. }
  512. .popup-header{
  513. padding: 20rpx 32rpx;
  514. width: 100%;
  515. text-align: left;
  516. color: #303133;
  517. font-family: "Source Han Sans CN VF";
  518. font-size: 32rx;
  519. font-weight: 700;
  520. }
  521. .popup-type{
  522. border-radius:32rpx;
  523. margin-left: 32rpx;
  524. display:inline-block;
  525. border: 2rpx solid #E4E7ED;
  526. padding: 2rpx 12rpx;
  527. color: #666666;
  528. font-family: "Source Han Sans CN VF";
  529. font-size: 24rpx;
  530. font-weight: 400;
  531. margin-bottom: 24rpx;
  532. }
  533. .popup-content{
  534. padding: 0 32rpx;
  535. line-height: 50rpx;
  536. }
  537. .popup-time{
  538. padding:0 32rpx;
  539. margin-top: 36rpx;
  540. color:#999999;
  541. font-size: 24rpx;
  542. text-align: left;
  543. color: #bdbdbd;
  544. font-family: "Source Han Sans CN VF";
  545. font-style: normal;
  546. font-weight: 400;
  547. }
  548. .popup-location{
  549. font-size: 24rpx;
  550. margin-top: 16rpx;
  551. padding-top: 16rpx;
  552. font-family: "Source Han Sans CN VF";
  553. color: #999999;
  554. display:flex;
  555. align-items: center;
  556. }
  557. .popup-text {
  558. padding: 0 32rpx;
  559. font-size: 24rpx;
  560. margin-top: 16rpx;
  561. padding-top: 16rpx;
  562. font-family: "Source Han Sans CN VF";
  563. color: #999999;
  564. display:flex;
  565. align-items: center;
  566. }
  567. /* 日期选择器 */
  568. .date-picker {
  569. display: flex;
  570. align-items: center;
  571. justify-content: space-between;
  572. margin-bottom: 32rpx;
  573. .date-inputs {
  574. display: flex;
  575. align-items: center;
  576. background: #ffffff;
  577. border-radius: 48rpx;
  578. padding: 14rpx;
  579. box-shadow: 0 2rpx 8rpx rgba(0, 0, 0, 0.05);
  580. .date-label {
  581. width:250rpx;
  582. font-size: 26rpx;
  583. color: #999999;
  584. text-align: center;
  585. }
  586. .date-separator {
  587. margin: 0 24rpx;
  588. font-size: 26rpx;
  589. color: #999999;
  590. }
  591. }
  592. .date-icons {
  593. display: flex;
  594. align-items: center;
  595. justify-content: center;
  596. width: 60rpx ;
  597. height: 60rpx;
  598. border-radius: 50%;
  599. background:#ffffff;
  600. .icon-image{
  601. width: 32rpx;
  602. height: 32rpx;
  603. }
  604. }
  605. }
  606. /* 标签导航 */
  607. .tab-nav {
  608. display: flex;
  609. margin-bottom: 24rpx;
  610. border-bottom: 1rpx solid #e5e5e5;
  611. .tab-item {
  612. padding: 20rpx 0;
  613. font-size: 28rpx;
  614. color: #666666;
  615. position: relative;
  616. margin-right: 30rpx;
  617. &.active {
  618. color: #333333;
  619. font-weight: 500;
  620. &::after {
  621. content: '';
  622. position: absolute;
  623. bottom: 0;
  624. left: 50%;
  625. transform: translateX(-50%);
  626. width: 100%;
  627. height: 4rpx;
  628. background: #515153;
  629. border-radius: 2rpx;
  630. }
  631. }
  632. }
  633. }
  634. /* 预警列表 */
  635. .warning-list {
  636. margin-bottom: 100rpx;
  637. height: calc(100vh - 600rpx);
  638. overflow-y: auto;
  639. .warning-item {
  640. position: relative;
  641. padding: 28rpx 24rpx;
  642. margin-bottom: 24rpx;
  643. background: #ffffff;
  644. border-radius: 16rpx;
  645. box-shadow: 0 2rpx 12rpx rgba(0, 0, 0, 0.06);
  646. .warning-header {
  647. display: flex;
  648. align-items: center;
  649. justify-content: space-between;
  650. margin-bottom: 16rpx;
  651. .warning-type {
  652. display: flex;
  653. align-items: center;
  654. flex: 1;
  655. min-width: 0;
  656. .type-icon {
  657. width: 48rpx;
  658. height: 48rpx;
  659. border-radius: 50%;
  660. margin-right: 12rpx;
  661. flex-shrink: 0;
  662. display:flex;
  663. align-items: center;
  664. justify-content: center;
  665. &.type-red {
  666. background: linear-gradient(180deg, #FFA9A5 0%, #FF716A 100%);
  667. }
  668. &.type-blue {
  669. background: linear-gradient(180deg, #83D2FF 0%, #09A5FC 100%);
  670. }
  671. &.type-yellow {
  672. background: linear-gradient(180deg, #FED057 0%, #FFAF40 100%);
  673. }
  674. &.type-gray {
  675. background: #DDDFE6;
  676. }
  677. .icon-image{
  678. width: 28rpx;
  679. height: 28rpx;
  680. }
  681. }
  682. .type-text {
  683. font-size: 26rpx;
  684. font-weight: 500;
  685. color: #333333;
  686. margin-right: 12rpx;
  687. flex-shrink: 0;
  688. }
  689. .device-type {
  690. font-size: 22rpx;
  691. color: #515153;
  692. font-family: "Source Han Sans CN VF";
  693. font-style: normal;
  694. font-weight: 400;
  695. border: 2rpx solid #E4E7ED;
  696. padding: 2rpx 12rpx;
  697. border-radius: 32rpx;
  698. margin-left: 8rpx;
  699. flex-shrink: 0;
  700. }
  701. }
  702. .warning-level {
  703. position: absolute;
  704. top:0;
  705. right:0;
  706. margin-left: 12rpx;
  707. width: 112rpx;
  708. height: 48rpx;
  709. background: url('./assets/normal-gray.png');
  710. background-repeat: no-repeat;
  711. background-size: 100%;
  712. &.level-normal {
  713. background: url('./assets/normal.png');
  714. background-repeat: no-repeat;
  715. background-size: 100%;
  716. }
  717. &.level-normal-gray {
  718. background: url('./assets/normal-gray.png');
  719. background-repeat: no-repeat;
  720. background-size: 100%;
  721. }
  722. &.level-important {
  723. background: url('./assets/important.png');
  724. background-repeat: no-repeat;
  725. background-size: 100%;
  726. }
  727. &.level-important-gray {
  728. background: url('./assets/important-gray.png');
  729. background-repeat: no-repeat;
  730. background-size: 100%;
  731. }
  732. &.level-urgent-gray {
  733. background: url('./assets/urgent-gray.png');
  734. background-repeat: no-repeat;
  735. background-size: 100%;
  736. }
  737. &.level-urgent {
  738. background: url('./assets/urgent.png');
  739. background-repeat: no-repeat;
  740. background-size: 100%;
  741. }
  742. }
  743. }
  744. .warning-content {
  745. font-size: 28rpx;
  746. color: #333333;
  747. line-height: 40rpx;
  748. margin-bottom: 20rpx;
  749. //最多显示2行
  750. overflow: hidden;
  751. text-overflow: ellipsis;
  752. display: -webkit-box;
  753. -webkit-line-clamp: 2;
  754. -webkit-box-orient: vertical;
  755. }
  756. .warning-footer {
  757. display: flex;
  758. align-items: center;
  759. justify-content: space-between;
  760. .warning-time {
  761. font-size: 24rpx;
  762. color: #999999;
  763. }
  764. .warning-location {
  765. display: flex;
  766. align-items: center;
  767. }
  768. }
  769. .location-text {
  770. font-size: 24rpx;
  771. margin-top: 16rpx;
  772. padding-top: 16rpx;
  773. border-top: 1rpx solid #f0f0f0;
  774. font-family: "Source Han Sans CN VF";
  775. color: #999999;
  776. display:flex;
  777. align-items: center;
  778. }
  779. }
  780. }
  781. /* 加载更多提示 */
  782. .loading-more {
  783. text-align: center;
  784. padding: 32rpx 0;
  785. font-size: 24rpx;
  786. color: #999999;
  787. }
  788. /* 回到顶部 */
  789. .back-to-top {
  790. position: fixed;
  791. bottom: 80rpx;
  792. right: 32rpx;
  793. width: 64rpx;
  794. height: 64rpx;
  795. background: #ffffff;
  796. border-radius: 50%;
  797. display: flex;
  798. align-items: center;
  799. justify-content: center;
  800. box-shadow: 0 2rpx 12rpx rgba(0, 0, 0, 0.1);
  801. z-index: 99;
  802. }
  803. /* 顶部导航栏右侧图标 */
  804. .header-right {
  805. display: flex;
  806. align-items: center;
  807. .notification-icon {
  808. position: relative;
  809. margin-right: 32rpx;
  810. .badge {
  811. position: absolute;
  812. top: -4rpx;
  813. right: -4rpx;
  814. width: 12rpx;
  815. height: 12rpx;
  816. background: #ff6b6b;
  817. border-radius: 50%;
  818. }
  819. }
  820. }
  821. </style>