toutiaoTime.vue 8.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314
  1. <template>
  2. <div class="calendar">
  3. <table class="time_table table" v-on:mouseleave="mouseleave">
  4. <thead>
  5. <tr>
  6. <th rowspan="2" style="width: 120px">日期/时间</th>
  7. </tr>
  8. <tr>
  9. <th class="unselectable" v-for="(num, index) in numData" :key="index" style="width: 30px">{{ num }}</th>
  10. </tr>
  11. </thead>
  12. <tbody>
  13. <tr v-for="(options, index) in timeData" :key="index">
  14. <th scope="row">{{ options.date }}</th>
  15. <td
  16. v-for="(timeItem, key) in options.time"
  17. :key="key"
  18. :class="[{ active_select: timeItem.isSelected, active_select_move: timeItem.show }]"
  19. v-on:mousedown="mousedown(index, key)"
  20. v-on:mouseover="mouseover(index, key)"
  21. v-on:mouseup="mouseup(index, key)"
  22. @click="showOne(index, key)"
  23. ></td>
  24. </tr>
  25. </tbody>
  26. </table>
  27. <!-- <div style="height:200px;overflow:auto">
  28. <span v-for="(item, index) of dataString" :key="index">
  29. <a-tag v-if="item" closable :afterClose="() => handleClose(index)">
  30. {{ setItemDate(index) }}
  31. </a-tag>
  32. </span>
  33. </div> -->
  34. </div>
  35. </template>
  36. <script>
  37. export default {
  38. name: 'calendar-table',
  39. props: {
  40. scheduleTime: {
  41. type: String,
  42. default() {
  43. return '000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000'
  44. },
  45. },
  46. },
  47. data() {
  48. return {
  49. changeDataElse: ['1'],
  50. show: false,
  51. numData: [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23],
  52. dateTime: ['周一', '周二', '周三', '周四', '周五', '周六', '周日'],
  53. timeData: [
  54. {
  55. date: '周一',
  56. time: [],
  57. },
  58. {
  59. date: '周二',
  60. time: [],
  61. },
  62. {
  63. date: '周三',
  64. time: [],
  65. },
  66. {
  67. date: '周四',
  68. time: [],
  69. },
  70. {
  71. date: '周五',
  72. time: [],
  73. },
  74. {
  75. date: '周六',
  76. time: [],
  77. },
  78. {
  79. date: '周日',
  80. time: [],
  81. },
  82. ],
  83. selectFlag: false,
  84. max: {
  85. x: 0,
  86. y: 0,
  87. },
  88. dataString: '',
  89. }
  90. },
  91. methods: {
  92. // handleClose(item) {
  93. // var index = Math.floor(item / 24)
  94. // var key = item % 7
  95. // if (this.timeData[index].time[key].value == false) {
  96. // if (this.timeData[index].time[key].isSelected) {
  97. // this.timeData[index].time[key].isSelected = false
  98. // } else {
  99. // this.$set(this.timeData[index].time[key], 'isSelected', true)
  100. // }
  101. // }
  102. // },
  103. showOne(index, key) {
  104. // this.timeData[index].time[key].isSelected = !this.timeData[index].time[key].isSelected
  105. },
  106. mousedown: function (index, key) {
  107. this.selectStart = []
  108. this.selectFlag = true
  109. if (this.timeData[index].time[key].value == false) {
  110. if (this.timeData[index].time[key].isSelected) {
  111. this.timeData[index].time[key].isSelected = false
  112. } else {
  113. this.$set(this.timeData[index].time[key], 'isSelected', true)
  114. }
  115. }
  116. this.selectStart.push({
  117. index: index,
  118. key: key,
  119. })
  120. },
  121. mouseover: function (index, key) {
  122. // x 垂直方向 y 水平方向
  123. if (this.selectFlag) {
  124. if (index >= this.max.x) {
  125. this.max.x = index
  126. }
  127. if (key >= this.max.y) {
  128. this.max.y = key
  129. }
  130. var start = {
  131. x: this.selectStart[0].index,
  132. y: this.selectStart[0].key,
  133. }
  134. var end = {
  135. x: index,
  136. y: key,
  137. }
  138. for (var i = end.x; i <= this.max.x; i++) {
  139. for (var j = end.y; j <= this.max.y; j++) {
  140. this.$set(this.timeData[i].time[j], 'isSelected', false)
  141. }
  142. }
  143. /* 渲染选中的区域 */
  144. // for (var i = start.x; i <= end.x; i++) {
  145. // for (var j = start.y; j <= end.y; j++) {
  146. // // this.$set(this.timeData[i].time[j], 'isSelected', true)
  147. // this.$set(this.timeData[i].time[j], 'show', true)
  148. // }
  149. // }
  150. for (var i = start.x; i <= end.x; i++) {
  151. for (var j = start.y; j <= end.y; j++) {
  152. this.$set(this.timeData[i].time[j], 'isSelected', true)
  153. }
  154. }
  155. }
  156. },
  157. mouseup: function (index, key) {
  158. var start = {
  159. x: this.selectStart[0].index,
  160. y: this.selectStart[0].key,
  161. }
  162. var end = {
  163. x: index,
  164. y: key,
  165. }
  166. /* 渲染选中的区域 */
  167. var data = []
  168. var arr = []
  169. // for (let i = 0; i < this.timeData.length; i++) {
  170. // for (let j = 0; j < this.timeData[i].time.length; j++) {
  171. // this.timeData[i].time[j].show = false
  172. // }
  173. // }
  174. arr = data.concat(
  175. this.timeData[0].time,
  176. this.timeData[1].time,
  177. this.timeData[2].time,
  178. this.timeData[3].time,
  179. this.timeData[4].time,
  180. this.timeData[5].time,
  181. this.timeData[6].time
  182. )
  183. this.dataString = arr.map((item) => {
  184. if (item.isSelected) {
  185. return 1
  186. } else {
  187. return 0
  188. }
  189. })
  190. console.log(this.dataString.join(''))
  191. this.$emit('update:scheduleTime', this.dataString.join(''))
  192. this.selectFlag = false
  193. this.max = {
  194. x: 0,
  195. y: 0,
  196. }
  197. },
  198. mouseleave: function () {
  199. this.selectFlag = false
  200. },
  201. setItemDate(sum) {
  202. let i = sum
  203. if (i < 24) {
  204. return '周一' + i + ':00~' + (i + 1) + ':00'
  205. } else if (i < 48 && i >= 24) {
  206. return '周二' + (i - 24) + ':00~' + (i - 23) + ':00'
  207. } else if (i < 72 && i >= 48) {
  208. return '周三' + (i - 48) + ':00~' + (i - 47) + ':00'
  209. } else if (i < 96 && i >= 72) {
  210. return '周四' + (i - 72) + ':00~' + (i - 71) + ':00'
  211. } else if (i < 120 && i >= 96) {
  212. return '周五' + (i - 96) + ':00~' + (i - 95) + ':00'
  213. } else if (i < 144 && i >= 120) {
  214. return '周六' + (i - 120) + ':00~' + (i - 119) + ':00'
  215. } else {
  216. return '周日' + (i - 144) + ':00~' + (i - 143) + ':00'
  217. }
  218. },
  219. init() {
  220. var str = this.scheduleTime
  221. var arr = str.split('')
  222. this.timeData = [
  223. {
  224. date: '周一',
  225. time: [],
  226. },
  227. {
  228. date: '周二',
  229. time: [],
  230. },
  231. {
  232. date: '周三',
  233. time: [],
  234. },
  235. {
  236. date: '周四',
  237. time: [],
  238. },
  239. {
  240. date: '周五',
  241. time: [],
  242. },
  243. {
  244. date: '周六',
  245. time: [],
  246. },
  247. {
  248. date: '周日',
  249. time: [],
  250. },
  251. ]
  252. for (let i = 0; i < arr.length; i++) {
  253. if (i < 24) {
  254. this.timeData[0].time.push({ isSelected: arr[i] == 1 ? true : false, move: false, value: false })
  255. } else if (i < 48 && i >= 24) {
  256. this.timeData[1].time.push({ isSelected: arr[i] == 1 ? true : false, move: false, value: false })
  257. } else if (i < 72 && i >= 48) {
  258. this.timeData[2].time.push({ isSelected: arr[i] == 1 ? true : false, move: false, value: false })
  259. } else if (i < 96 && i >= 72) {
  260. this.timeData[3].time.push({ isSelected: arr[i] == 1 ? true : false, move: false, value: false })
  261. } else if (i < 120 && i >= 96) {
  262. this.timeData[4].time.push({ isSelected: arr[i] == 1 ? true : false, move: false, value: false })
  263. } else if (i < 144 && i >= 120) {
  264. this.timeData[5].time.push({ isSelected: arr[i] == 1 ? true : false, move: false, value: false })
  265. } else {
  266. this.timeData[6].time.push({ isSelected: arr[i] == 1 ? true : false, move: false, value: false })
  267. }
  268. }
  269. },
  270. },
  271. watch: {
  272. scheduleTime: {
  273. immediate: true, // immediate选项可以开启首次赋值监听
  274. handler(newVal, oldVal) {
  275. if (newVal == '' || newVal == null || newVal == undefined) {
  276. // this.scheduleTime=oldVal
  277. this.$emit('update:scheduleTime', oldVal)
  278. } else {
  279. this.init()
  280. }
  281. },
  282. },
  283. },
  284. }
  285. </script>
  286. <style lang="scss" scoped>
  287. .time_table {
  288. border: 1px solid #ccc;
  289. border-collapse: collapse;
  290. }
  291. .time_table th,
  292. .time_table td {
  293. border: 1px solid #ccc;
  294. text-align: center;
  295. }
  296. .time_table .unselectable {
  297. // width: 30px !important;
  298. height: 20px;
  299. }
  300. .active_select {
  301. background: cornflowerblue;
  302. }
  303. .active_select_move {
  304. background: aqua;
  305. }
  306. * {
  307. -webkit-touch-callout: none !important;
  308. -webkit-user-select: none !important;
  309. -moz-user-select: none !important;
  310. -ms-user-select: none !important;
  311. user-select: none !important;
  312. }
  313. </style>