popularVideo.vue 23 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902
  1. <style lang="scss" scoped>
  2. .search-bar {
  3. display: flex;
  4. align-items: center;
  5. }
  6. .search-box p {
  7. display: inline-block;
  8. border: 1px solid #f2f2f2;
  9. border-radius: 5px;
  10. margin-right: 10px;
  11. padding: 5px 10px;
  12. cursor: pointer;
  13. }
  14. </style>
  15. <style>
  16. .showNumBox{
  17. margin: 10px 0;
  18. }
  19. .showNumBox .ant-card-body {
  20. display: flex;
  21. justify-content: center;
  22. }
  23. .showNumBox p,
  24. .showNumBox span {
  25. text-align: center;
  26. line-height: 40px;
  27. font-size: 30px;
  28. font-weight: 600;
  29. color: red;
  30. margin: 0;
  31. }
  32. .search-box .ant-card-body {
  33. padding: 5px 15px;
  34. }
  35. .showNumBox .ant-card-body .styleElse {
  36. line-height: 60px;
  37. height: 40px;
  38. font-size: 16px;
  39. font-weight: 400;
  40. margin-left: 10px;
  41. }
  42. .ant-modal-wrap .yincang .ant-modal-content .ant-modal-footer {
  43. display: none !important;
  44. }
  45. .yincang .ant-col-6 p {
  46. text-align: left;
  47. color: red;
  48. font-size: 16px;
  49. font-weight: 500;
  50. }
  51. .ant-table-thead div {
  52. font-weight: 700;
  53. }
  54. .tool-tip {
  55. position: absolute;
  56. top: 65px;
  57. right: 10px;
  58. }
  59. </style>
  60. <style lang='less'>
  61. .ant-card-head .ant-tabs-bar{
  62. padding: 0;
  63. }
  64. .search-box .ant-card-body {
  65. padding: 5px 15px;
  66. }
  67. .search-box{
  68. padding: 15px 10px;
  69. }
  70. .search-box p {
  71. display: inline-block;
  72. border: 1px solid #f2f2f2;
  73. border-radius: 5px;
  74. margin-right: 10px;
  75. padding: 5px 10px;
  76. cursor: pointer;
  77. }
  78. .statistics .ant-col-6 .ant-card-body .styleElse {
  79. line-height: 60px;
  80. height: 40px;
  81. font-size: 16px;
  82. font-weight: 400;
  83. margin-left: 10px;
  84. }
  85. .ant-modal-wrap .yincang .ant-modal-content .ant-modal-footer {
  86. display: none !important;
  87. }
  88. .yincang .ant-col-6 p {
  89. text-align: left;
  90. color: red;
  91. font-size: 16px;
  92. font-weight: 500;
  93. }
  94. .ant-table-thead div {
  95. font-weight: 700;
  96. }
  97. .tool-tip {
  98. position: absolute;
  99. top: 65px;
  100. right: 10px;
  101. }
  102. .statistics{
  103. .ant-card-bordered {
  104. border: none;
  105. }
  106. .ant-card-head .ant-tabs {
  107. clear: both;
  108. margin-bottom: -13px;
  109. color: rgba(0, 0, 0, 0.65);
  110. font-weight: normal;
  111. font-size: 14px;
  112. }
  113. .duibi{
  114. position: absolute;
  115. right: 24px;
  116. top: 15px;
  117. }
  118. p{
  119. margin-bottom: 0;
  120. }
  121. }
  122. </style>
  123. <style lang="less">
  124. .newPlanStatic{
  125. .divider{
  126. height: 62px;
  127. }
  128. .showNumBox{
  129. background: white;
  130. overflow: hidden;
  131. margin: 15px 0;
  132. padding: 30px 0;
  133. text-align: center;
  134. .ant-card-body{
  135. padding-top: 0;
  136. }
  137. .title{
  138. font-size: 14px;
  139. font-family: PingFangSC-Regular, PingFang SC;
  140. font-weight: 400;
  141. color: #999999;
  142. line-height: 22px;
  143. display: inline-block;
  144. }
  145. }
  146. .tabbody{
  147. background: white;
  148. padding: 0 24px;
  149. margin-bottom: 15px;
  150. .ant-tabs-bar {
  151. margin: 0;
  152. }
  153. }
  154. .chartBox{
  155. background: white;
  156. padding: 20px 0;
  157. }
  158. .tableBody{
  159. background: white;
  160. padding: 20px ;
  161. }
  162. }
  163. </style>
  164. <template>
  165. <div class="newPlanStatic">
  166. <div class="tabbody">
  167. <a-tabs v-model="tabKey" @change="tabChange">
  168. <a-tab-pane :key="1" tab="头条">
  169. </a-tab-pane>
  170. <a-tab-pane :key="2" tab="快手">
  171. </a-tab-pane>
  172. </a-tabs>
  173. </div>
  174. <a-row>
  175. <a-col :span="24">
  176. <a-card :bordered="false" class="search-box">
  177. <div style="margin-bottom:20px">
  178. <span style="margin-left:20px">编导:</span>
  179. <a-select
  180. v-model="planId"
  181. show-search
  182. placeholder="请输入名字"
  183. option-filter-prop="children"
  184. style="width: 200px"
  185. :filter-option="filterOption"
  186. @change="operateChange"
  187. :disabled='operateDisabled'
  188. allowClear
  189. >
  190. <a-select-option v-for="item in designList" :key="item.user_id" :value="item.id">
  191. {{item.realname+'_('+item.roleName+')'}}
  192. </a-select-option>
  193. </a-select>
  194. <span style="margin-left:20px">剪辑:</span>
  195. <a-select
  196. v-model="clipId"
  197. show-search
  198. placeholder="请输入名字"
  199. option-filter-prop="children"
  200. style="width: 200px"
  201. :filter-option="filterOption"
  202. @change="operateChange"
  203. :disabled='operateDisabled'
  204. allowClear
  205. >
  206. <a-select-option v-for="item in designList" :key="item.user_id" :value="item.id">
  207. {{item.realname+'_('+item.roleName+')'}}
  208. </a-select-option>
  209. </a-select>
  210. <span style="margin-left:20px">拍摄:</span>
  211. <a-select
  212. v-model="shotId"
  213. show-search
  214. placeholder="请输入名字"
  215. option-filter-prop="children"
  216. style="width: 200px"
  217. :filter-option="filterOption"
  218. @change="operateChange"
  219. :disabled='operateDisabled'
  220. allowClear
  221. >
  222. <a-select-option v-for="item in designList" :key="item.user_id" :value="item.id">
  223. {{item.realname+'_('+item.roleName+')'}}
  224. </a-select-option>
  225. </a-select>
  226. <a-button type='primary' style="position:absolute;right:20px" @click="search">查询</a-button>
  227. </div>
  228. <div style="margin-bottom:20px">
  229. <span>日期选择:</span>
  230. <a-range-picker
  231. @change="dateChange"
  232. v-model="dateRange"
  233. :disabled-date="disabledDate"
  234. style="width:200px"
  235. />
  236. <span style="margin-left:20px">数据维度:</span>
  237. <a-radio-group v-model="value" @change="dataTypeChange">
  238. <a-radio value="valid">
  239. 有效视频
  240. </a-radio>
  241. <a-radio value="hot">
  242. 爆款视频
  243. </a-radio>
  244. <a-radio value="onlie">
  245. 上线时间
  246. </a-radio>
  247. </a-radio-group>
  248. </div>
  249. <div class="time" >
  250. </div>
  251. </a-card>
  252. </a-col>
  253. </a-row>
  254. <a-row style="margin-bottom:15px;margin-top:12px">
  255. <a-col :span="24">
  256. <div class="tableBody">
  257. <a-button type='primary' class="export" style="margin-bottom:20px" @click="exportExcel" :loading="exportloading">导出报表</a-button>
  258. <a-table :columns="columns" :dataSource="dataTable" :pagination="ipagination" :loading="loading" bordered @change="tableChange">
  259. <span slot="createImg" slot-scope="text,record">
  260. <a-popover placement="right">
  261. <template slot="content">
  262. <video :src="record.url" style="width:250px" controls ></video>
  263. </template>
  264. <template slot="title">
  265. </template>
  266. <img :src="record.coverUrl || noImg" alt="" style="width:80px">
  267. </a-popover>
  268. </span>
  269. <span slot='companyName' slot-scope="text">{{text || '未知'}}</span>
  270. <span slot='planName' slot-scope="text">{{text || '-'}}</span>
  271. <span slot='clipName' slot-scope="text">{{text || '-'}}</span>
  272. <span slot='shotName' slot-scope="text">{{text || '-'}}</span>
  273. <span slot='totalCost' slot-scope="text">{{text |decimalsHandle}}</span>
  274. <span slot='activeNum' slot-scope="text">{{text |formatCurrency}}</span>
  275. <span slot='clickNum' slot-scope="text">{{text |formatCurrency}}</span>
  276. <span slot='convertNum' slot-scope="text">{{text |formatCurrency}}</span>
  277. <span slot='showNum' slot-scope="text">{{text |formatCurrency}}</span>
  278. <span slot='aclick' slot-scope="text">{{text |formatCurrency}}</span>
  279. <span slot='bclick' slot-scope="text">{{text |formatCurrency}}</span>
  280. <span slot='photoClick' slot-scope="text">{{text |formatCurrency}}</span>
  281. <span slot='photoShow' slot-scope="text">{{text |formatCurrency}}</span>
  282. </a-table>
  283. </div>
  284. </a-col>
  285. </a-row>
  286. </div>
  287. </template>
  288. <script>
  289. import { TreeSelect } from 'ant-design-vue';
  290. const SHOW_PARENT = TreeSelect.SHOW_PARENT;
  291. import ARow from 'ant-design-vue/es/grid/Row'
  292. import ACol from 'ant-design-vue/es/grid/Col'
  293. import moment from 'moment'
  294. import { getKsAccountReport, getKsDetail, getReportList } from '@api/video.js'
  295. import {
  296. getAction,
  297. postAction,
  298. downFile,
  299. downFilePost
  300. } from '@/api/manage';
  301. import qs from 'qs'
  302. let TTcolumns=[
  303. {
  304. title: '视频',
  305. dataIndex: 'createImg',
  306. scopedSlots: { customRender: 'createImg' },
  307. align: 'center',
  308. key:'userNcreateImgame'
  309. },
  310. {
  311. title: '视频ID',
  312. dataIndex: 'videoCode',
  313. scopedSlots: { customRender: 'videoCode' },
  314. align: 'center',
  315. key:'videoCode'
  316. },
  317. {
  318. title: '视频上线时间',
  319. dataIndex: 'stateDate',
  320. scopedSlots: { customRender: 'stateDate' },
  321. align: 'center',
  322. key:'stateDate'
  323. },
  324. {
  325. title: '所属公司',
  326. dataIndex: 'companyName',
  327. scopedSlots: { customRender: 'companyName' },
  328. align: 'center',
  329. key:'companyName'
  330. },
  331. {
  332. title: '策划名称',
  333. dataIndex: 'planName',
  334. scopedSlots: { customRender: 'planName' },
  335. align: 'center',
  336. key:'planName'
  337. },
  338. {
  339. title: '剪辑名称',
  340. dataIndex: 'clipName',
  341. scopedSlots: { customRender: 'clipName' },
  342. align: 'center',
  343. key:'clipName'
  344. },
  345. {
  346. title: '拍摄名称',
  347. dataIndex: 'shotName',
  348. scopedSlots: { customRender: 'shotName' },
  349. align: 'center',
  350. key:'shotName'
  351. },
  352. {
  353. title: '总消耗',
  354. dataIndex: 'totalCost',
  355. scopedSlots: { customRender: 'totalCost' },
  356. align: 'center',
  357. key:'totalCost'
  358. },
  359. {
  360. title: '点击数',
  361. dataIndex: 'clickNum',
  362. scopedSlots: { customRender: 'clickNum' },
  363. align: 'center',
  364. key:'clickNum'
  365. },
  366. {
  367. title: '曝光数',
  368. dataIndex: 'showNum',
  369. scopedSlots: { customRender: 'showNum' },
  370. align: 'center',
  371. key:'showNum'
  372. },
  373. {
  374. title: '激活数',
  375. dataIndex: 'activeNum',
  376. scopedSlots: { customRender: 'activeNum' },
  377. align: 'center',
  378. key:'activeNum'
  379. },
  380. {
  381. title: '转化数',
  382. dataIndex: 'convertNum',
  383. scopedSlots: { customRender: 'convertNum' },
  384. align: 'center',
  385. key:'convertNum'
  386. },
  387. // {
  388. // title: '总消耗',
  389. // dataIndex: 'totalCost',
  390. // scopedSlots: { customRender: 'totalCost' },
  391. // align: 'center',
  392. // key:'totalCost'
  393. // },
  394. ]
  395. let KScolumns=[
  396. {
  397. title: '视频',
  398. dataIndex: 'createImg',
  399. scopedSlots: { customRender: 'createImg' },
  400. align: 'center',
  401. key:'userNcreateImgame'
  402. },
  403. {
  404. title: '视频ID',
  405. dataIndex: 'videoCode',
  406. scopedSlots: { customRender: 'videoCode' },
  407. align: 'center',
  408. key:'videoCode'
  409. },
  410. {
  411. title: '视频上线时间',
  412. dataIndex: 'stateDate',
  413. scopedSlots: { customRender: 'stateDate' },
  414. align: 'center',
  415. key:'stateDate'
  416. },
  417. {
  418. title: '所属公司',
  419. dataIndex: 'companyName',
  420. scopedSlots: { customRender: 'companyName' },
  421. align: 'center',
  422. key:'companyName'
  423. },
  424. {
  425. title: '策划名称',
  426. dataIndex: 'planName',
  427. scopedSlots: { customRender: 'planName' },
  428. align: 'center',
  429. key:'planName'
  430. },
  431. {
  432. title: '剪辑名称',
  433. dataIndex: 'clipName',
  434. scopedSlots: { customRender: 'clipName' },
  435. align: 'center',
  436. key:'clipName'
  437. },
  438. {
  439. title: '拍摄名称',
  440. dataIndex: 'shotName',
  441. scopedSlots: { customRender: 'shotName' },
  442. align: 'center',
  443. key:'shotName'
  444. },
  445. {
  446. title: '总消耗',
  447. dataIndex: 'totalCost',
  448. scopedSlots: { customRender: 'totalCost' },
  449. align: 'center',
  450. key:'totalCost'
  451. },
  452. {
  453. title: '封面曝光',
  454. dataIndex: 'photoShow',
  455. scopedSlots: { customRender: 'photoShow' },
  456. align: 'center',
  457. key:'photoShow'
  458. },
  459. {
  460. title: '封面点击',
  461. dataIndex: 'photoClick',
  462. scopedSlots: { customRender: 'photoClick' },
  463. align: 'center',
  464. key:'photoClick'
  465. },
  466. {
  467. title: '素材曝光',
  468. dataIndex: 'aclick',
  469. scopedSlots: { customRender: 'aclick' },
  470. align: 'center',
  471. key:'aclick'
  472. },
  473. {
  474. title: '行为数',
  475. dataIndex: 'bclick',
  476. scopedSlots: { customRender: 'bclick' },
  477. align: 'center',
  478. key:'bclick'
  479. },
  480. ]
  481. export default {
  482. components: {
  483. ACol,
  484. ARow,
  485. },
  486. data() {
  487. return {
  488. exportloading:false,
  489. planId:'',
  490. shotId:'',
  491. clipId:'',
  492. dateRange:[moment().subtract(1,'weeks'),moment()],
  493. noImg:require('@/assets/noImg.png'),
  494. ipagination: {
  495. current: 1,
  496. pageSize: 10,
  497. // pageSizeOptions: ['10', '20', '30'],
  498. showTotal: (total, range) => {
  499. return range[0] + "-" + range[1] + " 共" + total + "条"
  500. },
  501. showQuickJumper: true,
  502. showSizeChanger:true,
  503. pageSizeOptions: ['10', '30', '50'],
  504. total: 0,
  505. onChange: (current, pageSize) => {
  506. // 切换分页时的回调,
  507. // 当在页面定义change事件时,切记要把此处的事件清除,因为这两个事件重叠了,可能到时候会导致一些莫名的bug
  508. this.ipagination.current = current;
  509. this.ipagination.pageSize= pageSize;
  510. }
  511. },
  512. value:'valid',
  513. KSaccountList:[],
  514. TTaccountList:[],
  515. KSdesignList:[],
  516. TTdesignList:[],
  517. operateDisabled:false,
  518. userId:JSON.parse(localStorage.getItem('pro__Login_Userinfo')).value.id,
  519. duration: 1000,
  520. //treeselect的参数
  521. treeValue: [],
  522. treeData: [],
  523. SHOW_PARENT,
  524. type:3,
  525. dateValue:[moment().subtract(7,'days'), moment()],
  526. operate:'',
  527. designList:[],
  528. tabKey:1,
  529. loading: false,
  530. TTcolumns,
  531. KScolumns,
  532. columns:[...TTcolumns],
  533. dataTable: [],
  534. tableTab:1,
  535. newPlan:0,
  536. effectPlan:0,
  537. openOptions:false,
  538. target:'',
  539. order:'desc',
  540. }
  541. },
  542. methods: {
  543. moment,
  544. disabledDate(current) {
  545. return current && current > moment()
  546. },
  547. dateChange(date, dateString) {
  548. // console.log(date,dateString)
  549. },
  550. //导出报表
  551. exportExcel() {
  552. this.exportloading=true;
  553. let url='';
  554. if(this.tabKey==1){
  555. url='/ctop/bytedanceVideoEtlInfo/exportXls';
  556. }else {
  557. url='/ctop/kuaishouVideoEtlInfo/exportXls'
  558. }
  559. let nameType=''
  560. if(this.value=='valid'){
  561. nameType='有效视频'
  562. }else if(this.value=='hot'){
  563. nameType='爆款视频'
  564. }else if(this.value=='online'){
  565. nameType='视频上线时间'
  566. }
  567. downFilePost(url,qs.stringify({
  568. type:this.value,
  569. clipId:this.clipId,
  570. shotId:this.shotId,
  571. planId:this.planId,
  572. startData:this.dateRange[0].format('YYYY-MM-DD'),
  573. endData:this.dateRange[1].format('YYYY-MM-DD'),
  574. })).then(res => {
  575. this.exportloading=false;
  576. let blob = new Blob([res], {
  577. type: 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet'
  578. })
  579. let downloadElement = document.createElement('a')
  580. let href = window.URL.createObjectURL(blob) //创建下载的链接
  581. downloadElement.href = href
  582. downloadElement.download = moment().format('YYYY-MM-DD') + nameType+'.xlsx' //下载后文件名
  583. document.body.appendChild(downloadElement)
  584. downloadElement.click() //点击下载
  585. document.body.removeChild(downloadElement) //下载完成移除元素
  586. window.URL.revokeObjectURL(href) //释放掉blob对象
  587. })
  588. },
  589. dataTypeChange(e){
  590. console.log(e.target.value)
  591. this.getNewPlan()
  592. },
  593. filterOption(input, option){
  594. // console.log(input, option)
  595. return (
  596. option.componentOptions.children[0].text.toLowerCase().indexOf(input.toLowerCase()) >= 0
  597. );
  598. },
  599. // 快手头条的切换
  600. tabChange(key){
  601. console.log(key);
  602. this.treeValue=[];
  603. this.ipagination.current=1
  604. this.columns=this.tabKey==1?[...TTcolumns]:[...KScolumns]
  605. this.getNewPlan()
  606. },
  607. operateChange(value){
  608. console.log(value);
  609. if(value){
  610. this.accountDisabled=true;
  611. this.accountId=''
  612. }else{
  613. this.accountDisabled=false
  614. }
  615. },
  616. tableChange(pagination, filters, sorter, { currentDataSource }){
  617. console.log(pagination)
  618. this.ipagination.current=pagination.current;
  619. this.ipagination.pageSize=pagination.pageSize;
  620. this.getNewPlan()
  621. },
  622. // table区域的tab切换
  623. tableTabChange(key){
  624. if(key==1){
  625. this.columns=this.tabKey==1?[...TTcolumns]:[...KScolumns]
  626. this.target='new'
  627. }else{
  628. this.columns=this.tabKey==1?[...TTcolumnsVaild]:[...KScolumnsVaild]
  629. this.target='valid'
  630. }
  631. this.getNewPlan()
  632. },
  633. // 获取所有运营
  634. getAllOperator(key){
  635. let url='/sys/user/getAllDesigner'
  636. this.designList=[]
  637. getAction(url,{}).then(res=>{
  638. console.log(res);
  639. if(res.success){
  640. this.designList=res.data
  641. }
  642. })
  643. },
  644. // 获取展示数据
  645. getNewPlan(){
  646. let url=''
  647. if(this.tabKey==1){
  648. // 头条
  649. url='/ctop/bytedanceVideoEtlInfo/list'
  650. }else{
  651. // 快手
  652. url='/ctop/kuaishouVideoEtlInfo/list'
  653. }
  654. this.loading=true;
  655. getAction(url,{
  656. type:this.value,
  657. clipId:this.clipId==''?null:this.clipId,
  658. shotId:this.shotId==''?null:this.shotId,
  659. planId:this.planId==''?null:this.planId,
  660. startDate:this.dateRange[0].format('YYYY-MM-DD'),
  661. endDate:this.dateRange[1].format('YYYY-MM-DD'),
  662. pageSize:this.ipagination.pageSize,
  663. pageNo:this.ipagination.current
  664. }).then(res=>{
  665. console.log(res);
  666. this.loading=false;
  667. if(res.success){
  668. if(res.result){
  669. this.dataTable=res.result.records
  670. this.ipagination.total=res.result.total
  671. }
  672. }
  673. })
  674. },
  675. // 查询按钮
  676. search(){
  677. // if(this.accountId || this.operate){
  678. // this.echartSpinning=true;
  679. // this.getNewPlan()
  680. // }else{
  681. // this.$message.error('请选择具体账户或者运营')
  682. // }
  683. this.ipagination.current=1;
  684. this.getNewPlan()
  685. },
  686. },
  687. watch: {
  688. dateValue(newName,oldName){
  689. this.search()
  690. },
  691. },
  692. computed: {
  693. newDate() {
  694. var myDate = new Date()
  695. myDate.getYear() //获取当前年份(2位)
  696. var n = myDate.getFullYear() //获取完整的年份(4位,1970-????)
  697. var m = myDate.getMonth() //获取当前月份(0-11,0代表1月)
  698. var d = myDate.getDate() //获取当前日(1-31)
  699. var day = myDate.getHours()
  700. return day
  701. }
  702. },
  703. mounted() {
  704. this.getNewPlan()
  705. this.getAllOperator()
  706. },
  707. activated: function() {
  708. },
  709. filters: {
  710. toPercentage(val) {
  711. if(typeof val != 'string'){
  712. return (val * 100).toFixed(2) + '%'
  713. }else{
  714. return val
  715. }
  716. },
  717. //保留两位小数并且变成货币格式
  718. decimalsHandle(val){
  719. if(val && typeof val !='string'){
  720. if(val>=0){
  721. val=parseFloat(val).toFixed(2);
  722. let numberStr = val.toString()
  723. let str = numberStr.split('.')
  724. let str0=str[0].split('').reverse();
  725. for (let i = 0; i < str0.length; i++) {
  726. if ((i + 1) % 4 === 0) {
  727. str0.splice(i, 0, ',')
  728. }
  729. }
  730. str0.reverse()
  731. let handleResult = ''
  732. for (let j = 0; j < str0.length; j++) {
  733. handleResult += str0[j]
  734. }
  735. return handleResult+'.'+str[1]
  736. }else{
  737. val=parseFloat(val).toFixed(2);
  738. let numberStr = val.toString()
  739. let str = numberStr.split('.')
  740. let str0=str[0].substr(1).split('').reverse();
  741. for (let i = 0; i < str0.length; i++) {
  742. if ((i + 1) % 4 === 0) {
  743. str0.splice(i, 0, ',')
  744. }
  745. }
  746. str0.reverse()
  747. let handleResult = ''
  748. for (let j = 0; j < str0.length; j++) {
  749. handleResult += str0[j]
  750. }
  751. return '-'+handleResult+'.'+str[1]
  752. }
  753. }else if(typeof val =='string'){
  754. return val
  755. }
  756. else{
  757. return 0
  758. }
  759. },
  760. //变成货币格式
  761. formatCurrency(val){
  762. if(val){
  763. let numberStr = val.toString()
  764. let str = numberStr.split('').reverse()
  765. for (let i = 0; i < str.length; i++) {
  766. if ((i + 1) % 4 === 0) {
  767. str.splice(i, 0, ',')
  768. }
  769. }
  770. str.reverse()
  771. let handleResult = ''
  772. for (let j = 0; j < str.length; j++) {
  773. handleResult += str[j]
  774. }
  775. return handleResult
  776. }else{
  777. return '-'
  778. }
  779. }
  780. }
  781. }
  782. </script>