西藏巴青项目

SelfConsumptionDialog.vue 7.7KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271
  1. <script setup>
  2. import { computed, reactive, ref, toRef, watch } from 'vue'
  3. import ScreenModal from '@/components/ScreenModal.vue'
  4. import { getYakOutboundReports } from '@/api/home'
  5. import { displayEmpty } from '@/utils/displayEmpty'
  6. import { buildScreenYearOptions } from '@/utils/screenYearOptions'
  7. import { useDialogStatYearSync } from '@/utils/useDialogStatYearSync'
  8. import { useScreenTownVillageOptions } from '@/utils/screenTownVillage'
  9. const props = defineProps({
  10. modelValue: { type: Boolean, default: false }
  11. })
  12. const emit = defineEmits(['update:modelValue'])
  13. const visible = computed({
  14. get: () => props.modelValue,
  15. set: (v) => emit('update:modelValue', v)
  16. })
  17. const query = reactive({
  18. statYear: undefined,
  19. statMonth: undefined,
  20. townDeptId: undefined,
  21. villageDeptId: undefined
  22. })
  23. const { townOptions, villageOptions, loadTownVillageOptions } = useScreenTownVillageOptions(
  24. toRef(query, 'townDeptId')
  25. )
  26. const loading = ref(false)
  27. const tableRows = ref([])
  28. const total = ref(0)
  29. const pageNum = ref(1)
  30. const pageSize = ref(10)
  31. const yearSelectOptions = buildScreenYearOptions()
  32. const { syncDialogYearFromGlobal } = useDialogStatYearSync(query, {
  33. visible,
  34. onSynced: () => {
  35. pageNum.value = 1
  36. fetchList()
  37. }
  38. })
  39. const monthOptions = Array.from({ length: 12 }, (_, i) => i + 1)
  40. function toNum(val) {
  41. if (val === null || val === undefined || val === '') {
  42. return null
  43. }
  44. const n = Number(val)
  45. return Number.isNaN(n) ? null : n
  46. }
  47. /** 自食合计 = 牛 + 绵羊 + 山羊;全空则展示 -- */
  48. function selfConsumptionTotal(row) {
  49. const cattle = toNum(row?.selfConsumptionCattleCount)
  50. const sheep = toNum(row?.selfConsumptionSheepCount)
  51. const goat = toNum(row?.selfConsumptionGoatCount)
  52. if (cattle === null && sheep === null && goat === null) {
  53. return displayEmpty(null)
  54. }
  55. return (cattle || 0) + (sheep || 0) + (goat || 0)
  56. }
  57. async function fetchList() {
  58. loading.value = true
  59. try {
  60. const params = {
  61. pageNum: pageNum.value,
  62. pageSize: pageSize.value,
  63. statYear: query.statYear,
  64. statMonth: query.statMonth
  65. }
  66. if (query.townDeptId != null && query.townDeptId !== '') {
  67. params.townDeptId = query.townDeptId
  68. }
  69. if (query.villageDeptId != null && query.villageDeptId !== '') {
  70. params.villageDeptId = query.villageDeptId
  71. }
  72. const res = await getYakOutboundReports(params)
  73. tableRows.value = res.rows || []
  74. total.value = Number(res.total) || 0
  75. } catch {
  76. tableRows.value = []
  77. total.value = 0
  78. } finally {
  79. loading.value = false
  80. }
  81. }
  82. function handleSearch() {
  83. pageNum.value = 1
  84. fetchList()
  85. }
  86. function handleReset() {
  87. syncDialogYearFromGlobal()
  88. query.statMonth = undefined
  89. query.townDeptId = undefined
  90. query.villageDeptId = undefined
  91. pageNum.value = 1
  92. fetchList()
  93. }
  94. function onTownChange() {
  95. query.villageDeptId = undefined
  96. }
  97. function onOpen() {
  98. syncDialogYearFromGlobal()
  99. query.statMonth = undefined
  100. query.townDeptId = undefined
  101. query.villageDeptId = undefined
  102. pageNum.value = 1
  103. loadTownVillageOptions().then(() => fetchList())
  104. }
  105. function onClose() {
  106. tableRows.value = []
  107. total.value = 0
  108. }
  109. watch([pageNum, pageSize], () => {
  110. if (visible.value) {
  111. fetchList()
  112. }
  113. })
  114. </script>
  115. <template>
  116. <ScreenModal
  117. v-model="visible"
  118. title="牲畜自食情况明细"
  119. width="1480px"
  120. height="780px"
  121. max-width="98vw"
  122. max-height="94vh"
  123. @open="onOpen"
  124. @close="onClose"
  125. >
  126. <el-form :inline="true" :model="query" class="sc-form" @submit.prevent>
  127. <el-form-item label="年份">
  128. <el-select v-model="query.statYear" clearable placeholder="年份" style="width: 110px">
  129. <el-option v-for="y in yearSelectOptions" :key="y" :label="`${y}年`" :value="y" />
  130. </el-select>
  131. </el-form-item>
  132. <el-form-item label="月份">
  133. <el-select v-model="query.statMonth" clearable placeholder="月份" style="width: 100px">
  134. <el-option v-for="m in monthOptions" :key="m" :label="`${m}月`" :value="m" />
  135. </el-select>
  136. </el-form-item>
  137. <el-form-item label="乡镇">
  138. <el-select
  139. v-model="query.townDeptId"
  140. placeholder="全部乡镇"
  141. clearable
  142. filterable
  143. style="width: 160px"
  144. @change="onTownChange"
  145. >
  146. <el-option
  147. v-for="t in townOptions"
  148. :key="t.deptId"
  149. :label="t.deptName"
  150. :value="t.deptId"
  151. />
  152. </el-select>
  153. </el-form-item>
  154. <el-form-item label="村">
  155. <el-select
  156. v-model="query.villageDeptId"
  157. placeholder="全部村"
  158. clearable
  159. filterable
  160. style="width: 160px"
  161. >
  162. <el-option
  163. v-for="v in villageOptions"
  164. :key="v.deptId"
  165. :label="v.deptName"
  166. :value="v.deptId"
  167. />
  168. </el-select>
  169. </el-form-item>
  170. <el-form-item>
  171. <el-button type="primary" @click="handleSearch">搜索</el-button>
  172. <el-button @click="handleReset">重置</el-button>
  173. </el-form-item>
  174. </el-form>
  175. <el-table
  176. v-loading="loading"
  177. :data="tableRows"
  178. border
  179. stripe
  180. height="100%"
  181. class="sc-table"
  182. empty-text="暂无数据"
  183. >
  184. <el-table-column prop="statYear" label="年份" width="80" align="center">
  185. <template #default="{ row }">{{ displayEmpty(row.statYear) }}</template>
  186. </el-table-column>
  187. <el-table-column prop="statMonth" label="月份" width="70" align="center">
  188. <template #default="{ row }">{{ displayEmpty(row.statMonth) }}</template>
  189. </el-table-column>
  190. <el-table-column prop="townName" label="乡镇" min-width="100" show-overflow-tooltip>
  191. <template #default="{ row }">{{ displayEmpty(row.townName) }}</template>
  192. </el-table-column>
  193. <el-table-column prop="villageName" label="村" min-width="100" show-overflow-tooltip>
  194. <template #default="{ row }">{{ displayEmpty(row.villageName) }}</template>
  195. </el-table-column>
  196. <el-table-column label="户数(户)" min-width="100" align="right">
  197. <template #default="{ row }">{{ displayEmpty(row.farmerHouseholdCount) }}</template>
  198. </el-table-column>
  199. <el-table-column label="人数(人)" min-width="100" align="right">
  200. <template #default="{ row }">{{ displayEmpty(row.farmerPopulationCount) }}</template>
  201. </el-table-column>
  202. <el-table-column label="牛(头)" min-width="90" align="right">
  203. <template #default="{ row }">{{ displayEmpty(row.selfConsumptionCattleCount) }}</template>
  204. </el-table-column>
  205. <el-table-column label="绵羊(只)" min-width="90" align="right">
  206. <template #default="{ row }">{{ displayEmpty(row.selfConsumptionSheepCount) }}</template>
  207. </el-table-column>
  208. <el-table-column label="山羊(只)" min-width="90" align="right">
  209. <template #default="{ row }">{{ displayEmpty(row.selfConsumptionGoatCount) }}</template>
  210. </el-table-column>
  211. <el-table-column label="合计(头只匹)" min-width="120" align="right">
  212. <template #default="{ row }">{{ selfConsumptionTotal(row) }}</template>
  213. </el-table-column>
  214. </el-table>
  215. <div class="sc-pager">
  216. <el-pagination
  217. v-model:current-page="pageNum"
  218. v-model:page-size="pageSize"
  219. background
  220. layout="total, sizes, prev, pager, next"
  221. :total="total"
  222. :page-sizes="[10, 20, 50]"
  223. />
  224. </div>
  225. </ScreenModal>
  226. </template>
  227. <style scoped>
  228. .sc-form {
  229. flex-shrink: 0;
  230. margin-bottom: 8px;
  231. }
  232. .sc-form :deep(.el-form-item__label) {
  233. color: #a8d4c8;
  234. }
  235. .sc-table {
  236. width: 100%;
  237. flex: 1;
  238. min-height: 0;
  239. }
  240. .sc-pager {
  241. flex-shrink: 0;
  242. display: flex;
  243. justify-content: flex-end;
  244. margin-top: 12px;
  245. }
  246. </style>