details.vue 9.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261
  1. <template>
  2. <u-navbar :titleStyle="{ color: '#000' }" :autoBack="true" :title="dataList[0]?.createBy + '的日报'" :placeholder="true" :safeAreaInsetTop="true" bgColor="#fff">
  3. <template #left>
  4. <view class="u-navbar__content__left__item">
  5. <u-icon name="arrow-left" size="20" color="#000"></u-icon>
  6. </view>
  7. </template>
  8. </u-navbar>
  9. <oa-scroll
  10. customClass="record-details-container scroll-height"
  11. :style="{
  12. //#ifdef APP-PLUS || MP-WEIXIN
  13. height: `calc(100vh - (44px + ${proxy.$settingStore.StatusBarHeight}))`,
  14. //#endif
  15. //#ifdef H5
  16. height: 'calc(100vh - (44px))',
  17. //#endif
  18. }"
  19. :refresherLoad="false"
  20. :refresherEnabled="false"
  21. :refresherEnabledTitle="false"
  22. :refresherDefaultStyle="'none'"
  23. :refresherThreshold="44"
  24. :refresherBackground="'#f5f6f7'"
  25. :data-theme="'theme-' + proxy.$settingStore.themeColor.name"
  26. >
  27. <template #default>
  28. <view class="content-area radius bg-white" v-for="(item, index) in dataList" :key="index">
  29. <view class="content-area-header flex mb10">
  30. <img :src="item.avatar" class="content-area-header-avatarImg mr10" v-if="item.avatar" />
  31. <u-avatar
  32. v-if="!item.avatar"
  33. class="content-area-header-avatar mr10"
  34. :text="item.createBy.length > 2 ? item.createBy.slice(1, 3) : item.createBy"
  35. shape="square"
  36. size="40"
  37. fontSize="12"
  38. color="#ffffff"
  39. :bgColor="proxy.$settingStore.themeColor.color"
  40. ></u-avatar>
  41. <view>
  42. <view class="content-area-header-title font16 mb5">{{ item.createBy ? item.createBy : " " }}</view>
  43. <view class="content-area-header-time font14">{{ item.submitDate ? item.submitDate.replace("T", " ") : " " }}</view>
  44. </view>
  45. </view>
  46. <view class="content-area-center mb10" v-for="child in item.workContents" :key="child">
  47. <view class="content-area-center-top flex">
  48. <view class="content-area-center-top-title mr10" style="color: #559aff" @click="toProjectMange(child.projectId)">{{ child.projectName ? child.projectName : " " }}</view>
  49. <view class="content-area-center-top-time" :style="{ color: proxy.$settingStore.themeColor.color }">{{ child.workTime }}h</view>
  50. </view>
  51. <u-text :text="child.workContent" color="#000000" size="14"></u-text>
  52. </view>
  53. <view class="content-area-center mb10">
  54. <view class="content-area-center-top"> 明日计划 </view>
  55. <u-text :text="item.tomorrowPlan ? item.tomorrowPlan : '无'" color="#000000" size="14"></u-text>
  56. </view>
  57. <view class="content-area-center mb10">
  58. <view class="content-area-center-top"> 工作协调 </view>
  59. <u-text :text="item.coordinateWork ? item.coordinateWork : '无'" color="#000000" size="14"></u-text>
  60. </view>
  61. <view class="content-area-center mb10">
  62. <view class="content-area-center-top">图片</view>
  63. <view class="imageBox" v-if="JSON.parse(item.reportImage)&&JSON.parse(item.reportImage).length>0">
  64. <image class="image m5" style="width: 50px" mode="widthFix" v-for="(a, index) in JSON.parse(item.reportImage)" :key="index" :src="a.url" @click="previewImage(index)" />
  65. </view>
  66. <view class="imageBox" v-else>无</view>
  67. </view>
  68. <view class="content-area-center mb10">
  69. <view class="content-area-center-top">附件 </view>
  70. <view v-if="JSON.parse(item.reportFile)&&JSON.parse(item.reportFile).length>0">
  71. <uni-link v-for="(file, index) in JSON.parse(item.reportFile)" :key="index" :href="file.url" text="file.url" style="color: rgba(0, 0, 0, 0.7)">{{ file.name }}</uni-link>
  72. </view>
  73. <view v-else>无</view>
  74. </view>
  75. <view class="content-area-center mb10" style="display: flex; flex-wrap: wrap">
  76. <u-tabs
  77. :list="tabsList"
  78. :current="tabsCurrent"
  79. @click="tabsClick"
  80. lineColor="#333"
  81. :activeStyle="{ color: '#333', fontSize: '14px' }"
  82. :inactiveStyle="{ color: '#909399', fontSize: '14px' }"
  83. :scrollable="false"
  84. style="width: 100%"
  85. ></u-tabs>
  86. <view class="content-area-header mt20 mb10 text-center" style="display: inline-block" v-for="(item, index) in reportDetailData.treeSelectNodes" :key="index">
  87. <img v-if="item.avatar" class="content-area-header-avatarImg mlr5" :src="item.avatar" style="display: block; width: 40px; height: 40px" />
  88. <u-avatar
  89. v-if="!item.avatar"
  90. class="content-area-header-avatar mlr5"
  91. :text="item.nickName.length > 2 ? item.nickName.slice(1, 3) : item.nickName"
  92. shape="square"
  93. size="40"
  94. fontSize="12"
  95. color="#ffffff"
  96. :bgColor="proxy.$settingStore.themeColor.color"
  97. ></u-avatar>
  98. <u-text :text="item.nickName" color="#000000" size="14" align="center"></u-text>
  99. </view>
  100. </view>
  101. </view>
  102. </template>
  103. </oa-scroll>
  104. </template>
  105. <script setup>
  106. /*----------------------------------依赖引入-----------------------------------*/
  107. import { onLoad, onShow, onReady, onHide, onLaunch, onBackPress, onUnload, onNavigationBarButtonTap, onPageScroll } from "@dcloudio/uni-app";
  108. import { ref, reactive, computed, getCurrentInstance, toRefs, inject } from "vue";
  109. /*----------------------------------接口引入-----------------------------------*/
  110. import { projectApi } from "@/api/business/project.js";
  111. import { dUserList } from "@/api/system/user.js";
  112. import { deptUserTreeSelect } from "@/api/system/user.js";
  113. /*----------------------------------组件引入-----------------------------------*/
  114. /*----------------------------------store引入-----------------------------------*/
  115. /*----------------------------------公共方法引入-----------------------------------*/
  116. /*----------------------------------公共变量-----------------------------------*/
  117. const { proxy } = getCurrentInstance();
  118. /*----------------------------------变量声明-----------------------------------*/
  119. const tree = ref({
  120. value: "tree_root",
  121. label: "Root",
  122. children: [],
  123. });
  124. const reportDetailData = ref([]);
  125. const pmReportReaders = ref([]); //已读未读集合
  126. const state = reactive({
  127. loading: true,
  128. dataList: [], //日报列表
  129. options: {
  130. //日报详情参数
  131. reportId: "",
  132. },
  133. userData: [], //用户列表
  134. images: [], //图片列表
  135. files: [], //附件列表
  136. tabsList: [
  137. { name: "已读", value: 0 },
  138. { name: "未读", value: 1 },
  139. ],
  140. tabsCurrent: 0,
  141. });
  142. const { dataList, userData, tabsList, tabsCurrent } = toRefs(state);
  143. /**
  144. * @tabs点击事件
  145. */
  146. function tabsClick(e) {
  147. state.tabsCurrent = e.index;
  148. reportDetailData.value.treeSelectNodes = proxy.$common.findTreeNodes(tree.value, state.tabsCurrent == 0 ? pmReportReaders.value.readAlready : pmReportReaders.value.readNotAlready);
  149. }
  150. function previewImage(index) {
  151. uni.previewImage({
  152. current: index, // 当前显示图片索引
  153. urls: state.images, // 需要预览的图片http链接列表
  154. });
  155. }
  156. /**
  157. * @初始化
  158. */
  159. function init() {
  160. dataList.value = [];
  161. state.loading = true;
  162. /** 查询树结构用户列表 回显抄送人*/
  163. deptUserTreeSelect({ pageNum: "1", pageSize: "1000" }).then((res) => {
  164. tree.value = res.data;
  165. projectApi()
  166. .ReportRecord({
  167. reportId: state.options.reportId,
  168. pageNum: 1,
  169. pageSize: 1,
  170. })
  171. .then((requset) => {
  172. dataList.value = requset.data.records;
  173. state.loading = false;
  174. pmReportReaders.value = requset.data.records[0].pmReportReaders;
  175. state.tabsList[0].name=state.tabsList[0].name+'('+pmReportReaders.value.read+')';
  176. state.tabsList[1].name=state.tabsList[1].name+'('+pmReportReaders.value.unRead+')';
  177. reportDetailData.value.treeSelectNodes = proxy.$common.findTreeNodes(tree.value, tabsCurrent.value == 0 ? pmReportReaders.value.readAlready : pmReportReaders.value.readNotAlready);
  178. var imgs = JSON.parse(dataList.value[0].reportImage);
  179. var files = JSON.parse(dataList.value[0].reportFile);
  180. imgs.forEach(function (item) {
  181. state.images.push(item.url);
  182. });
  183. files.forEach(function (item) {
  184. state.files.push(item.url);
  185. });
  186. })
  187. .catch((err) => {
  188. state.loading = false;
  189. });
  190. });
  191. }
  192. /**
  193. * 跳转项目概览
  194. * @param id 项目id
  195. */
  196. function toProjectMange(id) {
  197. proxy.$tab.navigateTo(`/pages/business/common/projectMange/overview/index?id=${id}`);
  198. }
  199. onReady(() => {});
  200. onShow(() => {
  201. //调用系统主题颜色
  202. proxy.$settingStore.systemThemeColor([1]);
  203. });
  204. onLoad((options) => {
  205. state.options.reportId = options?.reportId;
  206. init();
  207. });
  208. onUnload(() => {
  209. projectApi()
  210. .ReportRecordReadFlag({ reportId: state.options.reportId })
  211. .then((requset) => {
  212. uni.$emit("projectMange_record", true); //监听器
  213. })
  214. .catch((err) => {
  215. uni.$emit("projectMange_record", true); //监听器
  216. });
  217. });
  218. </script>
  219. <style lang="scss" scoped>
  220. .content-area {
  221. margin: 0;
  222. padding: 15px 20px;
  223. overflow: hidden;
  224. &-header {
  225. &-avatar {
  226. margin: auto 0;
  227. }
  228. &-avatarImg {
  229. width: 35px;
  230. height: 35px;
  231. border-radius: 4px;
  232. }
  233. &-title {
  234. margin: 0 0 15px 0;
  235. font-weight: 600;
  236. color: #000000;
  237. }
  238. }
  239. &-center {
  240. line-height: 25px;
  241. &-top {
  242. color: #000000;
  243. font-weight: 600;
  244. }
  245. }
  246. }
  247. </style>