index.vue 8.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434
  1. <script setup>
  2. import {
  3. ref
  4. } from 'vue'
  5. import {
  6. onLoad,
  7. onUnload
  8. } from "@dcloudio/uni-app"
  9. import {
  10. getfundPlanUse,
  11. } from "@/api/work/countAnalysis.js"
  12. function backToBefore() {
  13. uni.reLaunch({
  14. url: "/pages/index"
  15. });
  16. };
  17. function goToPage(url) {
  18. uni.navigateTo({
  19. url
  20. })
  21. }
  22. function searchClick() {
  23. goToPage('/pages/countAnalysis/search/index?page=fundUseSearch')
  24. }
  25. let projectYear = ref(null);
  26. let yearShow = ref(false);
  27. let defaultIndex = ref([0]);
  28. let yearColumns = ref([
  29. ["2000", "2001", "2002", "2003", "2004", "2005", "2006", "2007", "2008", "2009", "2010", "2011", "2012",
  30. "2013",
  31. "2014", "2015", "2016", "2017", "2018", "2019", "2020", "2021", "2022", "2023", "2024", "2025", "2026",
  32. "2027", "2028", "2029", "2030", "2031", "2032", "2033"
  33. ]
  34. ])
  35. const yearShowChoose = () => {
  36. yearShow.value = true;
  37. }
  38. const yearClose = e => {
  39. if (e) {
  40. projectYear.value = e.value[0];
  41. getPageDate();
  42. }
  43. yearShow.value = false;
  44. }
  45. const getPageDate = () => {
  46. let params = Object.assign({}, searchObj, {
  47. year: projectYear.value
  48. })
  49. getfundPlanUse(params).then(res => {
  50. filterData(res.data)
  51. });
  52. }
  53. let dataList = ref([{
  54. name: '项目总数(个)',
  55. key: "num",
  56. count: ""
  57. }, {
  58. name: '项目计划总金额(万元)',
  59. key: "totalAmt",
  60. count: ""
  61. }, {
  62. name: '项目年度计划总金额(万元)',
  63. key: "yearAmt",
  64. count: ""
  65. }, {
  66. name: '年度实际投入金额(万元)',
  67. key: "compAmt",
  68. count: ""
  69. }])
  70. let pieOpts = ref({
  71. color: ["#90B5F4", "#6497EE", "#1869F6", "#FF8229", "#FFAC71"],
  72. padding: [5, 5, 5, 5],
  73. enableScroll: false,
  74. legend: {
  75. show: false
  76. },
  77. extra: {
  78. pie: {
  79. activeOpacity: 0.5,
  80. activeRadius: 10,
  81. offsetAngle: 0,
  82. customRadius: 70,
  83. labelWidth: 15,
  84. border: false,
  85. offsetAngle: -90
  86. }
  87. }
  88. })
  89. let pieChartDataText = ref([]);
  90. let pieChartData = ref({
  91. series: [{
  92. data: []
  93. }]
  94. })
  95. let barOpts = {
  96. color: ["#1869F6", "#90B5F4"],
  97. touchMoveLimit: 24,
  98. enableScroll: true,
  99. dataLabel: false,
  100. legend: {
  101. show: false
  102. },
  103. xAxis: {
  104. disableGrid: true,
  105. scrollShow: true,
  106. itemCount: 8,
  107. },
  108. yAxis: {
  109. showTitle: true,
  110. data: [{
  111. min: 0,
  112. title: "单位:万元",
  113. // titleOffsetX: -30,
  114. }]
  115. },
  116. extra: {
  117. column: {
  118. type: "group",
  119. width: 14,
  120. barBorderRadius: [12, 12, 12, 12],
  121. activeBgColor: "#000000",
  122. activeBgOpacity: 0.08,
  123. }
  124. }
  125. }
  126. let barChartData = ref({
  127. categories: [],
  128. series: [{
  129. name: "月统计金额",
  130. data: []
  131. }]
  132. })
  133. let showBar = ref(false)
  134. let showPie = ref(false)
  135. function filterData(data) {
  136. // 上面四个数
  137. for (let i in dataList.value) {
  138. dataList.value[i].count = data[dataList.value[i].key] ?? "0"
  139. }
  140. // 饼状图数据
  141. let pieList = []
  142. for (let i in data.listIndusKind) {
  143. pieList.push({
  144. "name": data.listIndusKind[i].title,
  145. "value": data.listIndusKind[i].num || 0,
  146. "labelShow": false
  147. })
  148. }
  149. pieList.sort(sortByValue('value', -1))
  150. pieChartDataText.value = pieChartData.value.series[0].data = pieList;
  151. showPie.value = true
  152. // 柱状图数据
  153. let categoriesList = []
  154. let seriesList = []
  155. for (let i in data.listMonthAmt) {
  156. categoriesList.push(data.listMonthAmt[i].month + "月")
  157. seriesList.push(data.listMonthAmt[i].amtYear)
  158. }
  159. barChartData.value.categories = categoriesList.length > 0 ? categoriesList : ["无数据"]
  160. barChartData.value.series[0].data = seriesList
  161. showBar.value = true
  162. }
  163. const sortByValue = (attr, rev) => {
  164. if (rev == undefined) {
  165. rev = 1
  166. } else {
  167. (rev) ? 1: -1;
  168. }
  169. return function(a, b) {
  170. a = a[attr];
  171. b = b[attr];
  172. if (a < b) {
  173. return rev * -1
  174. }
  175. if (a > b) {
  176. return rev * 1
  177. }
  178. return 0;
  179. }
  180. }
  181. let searchObj = [];
  182. const goToThrough = function(key) {
  183. let url = "/pages/countAnalysis/through/index?key=" + key + "&";
  184. for (let i in searchObj) {
  185. let item = null
  186. if (!((searchObj[i] ?? "") === "")) {
  187. item = `${i}=${searchObj[i]}&`;
  188. } else {
  189. item = `${i}=&`;
  190. }
  191. url = url += item;
  192. }
  193. if (key === "num" || key === "totalAmt") {
  194. let beginDateStart = projectYear.value + "/01/01";
  195. let beginDateEnd = projectYear.value + "/12/31";
  196. url = `${url}beginDateStart=${beginDateStart}&beginDateEnd=${beginDateEnd}`
  197. } else {
  198. url = `${url}year=${projectYear.value}`
  199. }
  200. uni.navigateTo({
  201. url
  202. })
  203. }
  204. const barClick = function(e) {
  205. let index = e.currentIndex.index;
  206. let clickMonth = barChartData.value.categories[index];
  207. clickMonth = clickMonth ? clickMonth.slice(0, clickMonth.length - 1) : clickMonth;
  208. let url = "/pages/countAnalysis/through/index?key=compAmt&month=" + clickMonth + "&";
  209. let params = Object.assign({}, searchObj, {
  210. year: projectYear.value
  211. })
  212. for (let i in params) {
  213. let item = null
  214. if (!(params[i] ?? "") === "") {
  215. item = `${i}=${params[i]}&`;
  216. } else {
  217. item = `${i}=&`;
  218. }
  219. url = url += item;
  220. }
  221. uni.navigateTo({
  222. url
  223. })
  224. }
  225. onLoad(() => {
  226. uni.$on("fundUseSearch", resolve => {
  227. let optionFilter = Object.assign({}, resolve);
  228. let filterArr = ["null", "undefined", ""];
  229. for (let i in optionFilter) {
  230. if (filterArr.includes(optionFilter[i])) {
  231. optionFilter[i] = null;
  232. };
  233. };
  234. if (optionFilter.year) {
  235. projectYear.value = optionFilter.year;
  236. defaultIndex.value = [projectYear.value - 2000];
  237. }
  238. searchObj = optionFilter;
  239. getfundPlanUse(optionFilter).then(res => {
  240. filterData(res.data);
  241. });
  242. });
  243. projectYear.value = new Date().getFullYear();
  244. defaultIndex.value = [projectYear.value - 2000];
  245. getPageDate();
  246. });
  247. onUnload(() => {
  248. uni.$off('fundUseSearch');
  249. })
  250. </script>
  251. <template>
  252. <view class="container">
  253. <page-title @searchClick='searchClick' showSearch>资金使用</page-title>
  254. <view class="main">
  255. <view class="choose-year" @click="yearShowChoose()">
  256. 年度:{{projectYear}}
  257. <u-icon name="arrow-right" color="#000" size="14" customStyle="margin-left:5rpx"></u-icon>
  258. </view>
  259. <view class="count">
  260. <u-grid :border="false" col="2">
  261. <u-grid-item v-for="(item,index) in dataList" :key="index" @click="goToThrough(item.key)">
  262. <view class="count-item">
  263. <view class="count-item-num">{{item.count}}</view>
  264. <view class="count-item-name">{{item.name}}</view>
  265. </view>
  266. </u-grid-item>
  267. </u-grid>
  268. </view>
  269. <view class="pie" v-if="showPie">
  270. <view class="pie-area">
  271. <qiun-data-charts type="pie" :opts="pieOpts" :chartData="pieChartData" />
  272. </view>
  273. <view class="pie-text">
  274. <view class="pie-item" v-for="(item,index) in pieChartDataText" :key="index">
  275. <view class="pie-item-name">{{item.name}}</view>
  276. <view class="pie-item-value">{{item.value}}</view>
  277. </view>
  278. </view>
  279. </view>
  280. <view class="charts" v-if="showBar">
  281. <qiun-data-charts type="line" :opts="barOpts" :ontouch="true" :chartData="barChartData" @getIndex="barClick" />
  282. </view>
  283. <view class="charts-description">月度实际投资情况</view>
  284. <view class="gap-bottom"></view>
  285. </view>
  286. <!-- 年度选择 -->
  287. <u-picker :show="yearShow" :defaultIndex="defaultIndex" :columns="yearColumns" @confirm="yearClose"
  288. @cancel="yearClose" @close="yearClose" closeOnClickOverlay></u-picker>
  289. </view>
  290. </template>
  291. <style lang="scss" scoped>
  292. page {
  293. background: #fff;
  294. }
  295. .container {
  296. background: #fff;
  297. }
  298. .main {
  299. position: absolute;
  300. top: 10%;
  301. left: 0;
  302. width: 100%;
  303. height: 95%;
  304. padding: 40rpx 4%;
  305. background-color: #fff;
  306. }
  307. .count {
  308. width: 100%;
  309. height: 300rpx;
  310. .count-item {
  311. display: flex;
  312. flex-direction: column;
  313. justify-content: space-evenly;
  314. width: 100%;
  315. height: 150rpx;
  316. text-align: center;
  317. .count-item-num {
  318. font-size: 40rpx;
  319. font-weight: 500;
  320. color: #343437;
  321. }
  322. .count-item-name {
  323. font-size: 26rpx;
  324. color: #9E9E9E;
  325. }
  326. }
  327. }
  328. .choose-year {
  329. display: flex;
  330. align-items: center;
  331. justify-content: flex-end;
  332. font-size: 32rpx;
  333. font-weight: 500;
  334. color: #000;
  335. }
  336. .pie {
  337. display: flex;
  338. min-height: 400rpx;
  339. margin-top: 68rpx;
  340. background: #EAF0FA;
  341. border-radius: 40rpx;
  342. .pie-area {
  343. width: 50%;
  344. }
  345. .pie-text {
  346. display: flex;
  347. flex-direction: column;
  348. justify-content: center;
  349. min-height: 400rpx;
  350. width: 50%;
  351. padding: 20rpx;
  352. box-sizing: border-box;
  353. .pie-item {
  354. display: flex;
  355. justify-content: space-between;
  356. align-items: center;
  357. width: 100%;
  358. margin-bottom: 10rpx;
  359. }
  360. }
  361. }
  362. .charts {
  363. width: 100%;
  364. height: 508rpx;
  365. margin-top: 40rpx;
  366. }
  367. .charts-description {
  368. width: 100%;
  369. margin-top: 34rpx;
  370. text-align: center;
  371. font-size: 32rpx;
  372. font-weight: 500;
  373. color: #343437;
  374. }
  375. </style>