diagnosisReportPopup.vue 4.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178
  1. <template>
  2. <popup
  3. v-model:show="visible"
  4. round
  5. teleport="body"
  6. class="diagnosis-report-popup"
  7. :z-index="20000"
  8. :close-on-click-overlay="true"
  9. >
  10. <img class="diagnosis-report-popup__image" src="@/assets/img/agricultural/report.png" alt="" />
  11. <div class="diagnosis-report-popup__title">
  12. <div>{{ t("agriFile.plantingDiagnosisReport") }}</div>
  13. <div>{{ t("agriFile.reportGenerated") }}</div>
  14. </div>
  15. <div class="diagnosis-report-popup__btn" @click="handleView">{{ t("agriFile.clickToView") }}</div>
  16. <div class="diagnosis-report-popup__hint">{{ t("agriFile.viewInDiagnosisHint") }}</div>
  17. </popup>
  18. </template>
  19. <script setup>
  20. import { onActivated, onMounted, ref, watch } from "vue";
  21. import { useRouter } from "vue-router";
  22. import { Popup } from "vant";
  23. import { useI18n } from "@/i18n";
  24. const { t } = useI18n();
  25. const router = useRouter();
  26. const SHOWN_CACHE_PREFIX = "DIAGNOSIS_REPORT_POPUP_SHOWN_";
  27. /** 弹窗显隐由组件内接口控制,默认不展示 */
  28. const visible = ref(false);
  29. /** 当前缓存中选中的农场 / 分区 id */
  30. const getSelectedFarmId = () => {
  31. try {
  32. const farm = JSON.parse(localStorage.getItem("selectedFarmData") || "{}");
  33. return String(
  34. localStorage.getItem("selectedFarmId") || farm.farm_id || farm.id || ""
  35. );
  36. } catch {
  37. return String(localStorage.getItem("selectedFarmId") || "");
  38. }
  39. };
  40. const getSelectedZoneId = () => {
  41. try {
  42. const farm = JSON.parse(localStorage.getItem("selectedFarmData") || "{}");
  43. const zoneId = farm.zone_id ?? farm.zoneId ?? "";
  44. return zoneId === "" || zoneId == null ? "" : String(zoneId);
  45. } catch {
  46. return "";
  47. }
  48. };
  49. const getShownCacheKey = (farmId, zoneId) =>
  50. `${SHOWN_CACHE_PREFIX}${farmId}_${zoneId || ""}`;
  51. const hasShownPopup = (farmId, zoneId) =>
  52. !!localStorage.getItem(getShownCacheKey(farmId, zoneId));
  53. const markPopupShown = (farmId, zoneId) => {
  54. if (!farmId) return;
  55. localStorage.setItem(getShownCacheKey(farmId, zoneId), "1");
  56. };
  57. /** 当前选中农场;接口必传 farm_id / zone_id */
  58. const readSelectedFarm = () => {
  59. try {
  60. return JSON.parse(localStorage.getItem("selectedFarmData") || "null") || {};
  61. } catch {
  62. return {};
  63. }
  64. };
  65. const readFarmId = () => {
  66. const farm = readSelectedFarm();
  67. const id = farm.farm_id ?? farm.id;
  68. if (id != null && id !== "") return id;
  69. return localStorage.getItem("selectedFarmId") || "";
  70. };
  71. const readZoneId = () => {
  72. const farm = readSelectedFarm();
  73. const id = farm.zone_id ?? farm.zoneId;
  74. return id != null && id !== "" ? id : "";
  75. };
  76. let checking = false;
  77. /** exists=2 且本地未展示过时弹窗(不依赖物候确认) */
  78. const checkShouldShow = async () => {
  79. const farmId = getSelectedFarmId();
  80. const zoneId = getSelectedZoneId();
  81. if (!farmId || hasShownPopup(farmId, zoneId)) {
  82. visible.value = false;
  83. return;
  84. }
  85. checking = true;
  86. try {
  87. const res = await VE_API.questionnaire.checkReportGenerated({
  88. farm_id: farmId,
  89. zone_id: zoneId,
  90. });
  91. const shouldShow = res?.code === 200 && Number(res?.data?.exists) === 1;
  92. visible.value = shouldShow;
  93. if (shouldShow) markPopupShown(farmId, zoneId);
  94. } catch {
  95. visible.value = false;
  96. } finally {
  97. checking = false;
  98. }
  99. };
  100. const handleView = () => {
  101. const farmId = getSelectedFarmId();
  102. const zoneId = getSelectedZoneId();
  103. markPopupShown(farmId, zoneId);
  104. visible.value = false;
  105. router.push("/diagnosis_report");
  106. };
  107. // 用户点遮罩关闭时也记为已展示,避免反复弹出
  108. watch(visible, (val, oldVal) => {
  109. if (oldVal && !val) markPopupShown(getSelectedFarmId(), getSelectedZoneId());
  110. });
  111. onActivated(() => {
  112. checkShouldShow();
  113. });
  114. defineExpose({
  115. checkShouldShow,
  116. });
  117. </script>
  118. <style scoped lang="scss">
  119. .diagnosis-report-popup {
  120. width: 78%;
  121. padding: 90px 20px 22px;
  122. text-align: center;
  123. overflow: visible;
  124. background: linear-gradient(360deg, #FFFFFF 0%, #D3EBFF 100%);
  125. &__image {
  126. display: block;
  127. width: 138px;
  128. height: 138px;
  129. margin: 0 auto 16px;
  130. position: absolute;
  131. top: -54px;
  132. left: 50%;
  133. transform: translateX(-50%);
  134. }
  135. &__title {
  136. font-size: 30px;
  137. color: #010101;
  138. line-height: 32px;
  139. div{
  140. font-family: "pangmenzhengdao";
  141. }
  142. }
  143. &__btn {
  144. width: 162px;
  145. margin: 18px auto 10px;
  146. padding: 8px 0;
  147. border-radius: 25px;
  148. background: linear-gradient(180deg, #96D1FF 0%, #2199F8 100%);
  149. color: #fff;
  150. font-size: 16px;
  151. }
  152. &__hint {
  153. color: #1D1919;
  154. }
  155. }
  156. </style>