timeDivSelect.vue 8.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292
  1. <style scoped>
  2. .timecontainer {
  3. width: 780px;
  4. overflow: hidden;
  5. padding-top: 30px;
  6. }
  7. .swrap {
  8. width: 780px;
  9. overflow: hidden;
  10. }
  11. .leftweek {
  12. display: inline-block;
  13. width: 50px;
  14. vertical-align: top;
  15. margin-top: 5px;
  16. }
  17. .leftweek .weekname {
  18. display: inline-block;
  19. width: 50px;
  20. height: 29px;
  21. line-height: 29px;
  22. text-align: center;
  23. font-size: 12px;
  24. }
  25. .mainbox {
  26. display: inline-block;
  27. vertical-align: middle;
  28. padding: 10px 0px 2px 10px;
  29. width: 710px;
  30. overflow: hidden;
  31. background-color: #eee;
  32. }
  33. .boxlist {
  34. overflow: hidden;
  35. }
  36. .boxlist .list {
  37. float: left;
  38. height: 20px;
  39. width: 10px;
  40. border: 1px solid #999;
  41. border-radius: 2px;
  42. margin: 0 1px 7px;
  43. cursor: pointer;
  44. background-color: #fff;
  45. }
  46. .boxlist .list:nth-of-type(12n) {
  47. margin-right: 10px;
  48. }
  49. .boxlist .list.selected {
  50. background-color: #0099ff;
  51. border-color: #0099ff;
  52. }
  53. .selectall {
  54. float: left;
  55. font-size: 12px;
  56. margin-left: 50px;
  57. }
  58. .righttips {
  59. font-size: 12px;
  60. float: right;
  61. }
  62. .righttips .tiplist {
  63. display: inline-block;
  64. margin-right: 10px;
  65. }
  66. .righttips .tiplist span {
  67. display: inline-block;
  68. width: 20px;
  69. height: 10px;
  70. border: 1px solid #999;
  71. margin-right: 3px;
  72. }
  73. .righttips .tiplist span.current {
  74. background: #43a9ed;
  75. border-color: #43a9ed;
  76. }
  77. .timeList {
  78. display: inline-block;
  79. vertical-align: middle;
  80. font-size: 12px;
  81. width: 175px;
  82. text-align: center;
  83. }
  84. </style>
  85. <template>
  86. <div>
  87. <div class="timecontainer" id="timecontainer" @mousedown="mousedownfn">
  88. <div class="selectall">
  89. <input type="checkbox" id="selectAllid" @click="selectAllornot" /><label
  90. for="selectAllid"
  91. style="cursor:pointer;padding-left:5px;"
  92. >全选</label
  93. >
  94. </div>
  95. <div class="righttips">
  96. <div class="tiplist"><span class="current"></span>投放</div>
  97. <div class="tiplist"><span></span>不投放</div>
  98. </div>
  99. <div class="swrap">
  100. <div class="leftweek">
  101. <div class="weekname" v-for="(item, index) in weekName" :key="index">{{ item }}</div>
  102. </div>
  103. <div class="mainbox">
  104. <div class="boxlist">
  105. <div
  106. class="list"
  107. :title="`${timeSetp}小时`"
  108. v-for="(item, index) in timeList"
  109. :class="{ selected: item == 1 }"
  110. @click="setcurrent(item, index)"
  111. :key="index"
  112. ></div>
  113. </div>
  114. <div class="bottomtime">
  115. <div class="timeList" v-for="(item, index) in timeName" :key="index">{{ item }}</div>
  116. </div>
  117. </div>
  118. </div>
  119. </div>
  120. </div>
  121. </template>
  122. <script>
  123. export default {
  124. data() {
  125. return {
  126. weekName: ['星期一', '星期二', '星期三', '星期四', '星期五', '星期六', '星期日'],
  127. timeName: ['00:00~06:00', '06:00~12:00', '12:00~18:00', '18:00~24:00'],
  128. timeList: this.timeString.split(''),
  129. isSelect: true,
  130. selectBoxDashed: null,
  131. startX: null,
  132. startY: null,
  133. initx: null,
  134. scrollX: null,
  135. scrollY: null,
  136. inity: null
  137. }
  138. },
  139. props: {
  140. timeSetp: {
  141. type: Number,
  142. default() {
  143. return 0.5
  144. }
  145. },
  146. timeString: {
  147. type: String,
  148. default() {
  149. let _timeArray = []
  150. for (let i = 0; i < (24 / this.timeSetp) * 7; i++) {
  151. _timeArray.push('0')
  152. }
  153. return _timeArray.join('')
  154. }
  155. }
  156. },
  157. model: {
  158. prop: 'timeString',
  159. event: 'triggertime'
  160. },
  161. mounted() {},
  162. methods: {
  163. clearBubble(e) {
  164. if (e.stopPropagation) {
  165. e.stopPropagation()
  166. } else {
  167. e.cancelBubble = true
  168. }
  169. if (e.preventDefault) {
  170. e.preventDefault()
  171. } else {
  172. e.returnValue = false
  173. }
  174. },
  175. mousedownfn(e) {
  176. // 创建选框节点
  177. this.$nextTick(() => {
  178. this.selectBoxDashed = document.createElement('div')
  179. this.selectBoxDashed.className = 'select-box-dashed'
  180. document.body.appendChild(this.selectBoxDashed)
  181. this.scrollX = document.documentElement.scrollLeft || document.body.scrollLeft
  182. this.scrollY = document.documentElement.scrollTop || document.body.scrollTop
  183. // 设置选框的初始位置
  184. this.startX = e.x + this.scrollX || e.clientX + this.scrollX
  185. this.startY = e.y + this.scrollY || e.clientY + this.scrollY
  186. this.selectBoxDashed.style.cssText = `left:${this.startX}px;top:${this.startY}px`
  187. // 清除事件冒泡、捕获
  188. console.log(this.startX ,this.startY)
  189. this.clearBubble(e)
  190. document.getElementById('timecontainer').addEventListener('mousemove', this.mousemovefn)
  191. document.body.addEventListener('mouseup', this.mouseUpfn)
  192. })
  193. },
  194. mousemovefn(e) {
  195. this.$nextTick(() => {
  196. // 设置选框可见
  197. this.selectBoxDashed.style.display = 'block'
  198. // 根据鼠标移动,设置选框的位置、宽高
  199. this.initx = e.x + this.scrollX || e.clientX + this.scrollX
  200. this.inity = e.y + this.scrollY || e.clientY + this.scrollY
  201. // 暂存选框的位置及宽高,用于将 select-item 选中
  202. this.left = Math.min(this.initx, this.startX)
  203. this.top = Math.min(this.inity, this.startY)
  204. this.width = Math.abs(this.initx - this.startX)
  205. this.height = Math.abs(this.inity - this.startY)
  206. this.selectBoxDashed.style.left = `${this.left}px`
  207. this.selectBoxDashed.style.top = `${this.top}px`
  208. this.selectBoxDashed.style.width = `${this.width}px`
  209. this.selectBoxDashed.style.height = `${this.height}px`
  210. let fileDivs = document.getElementsByClassName('list')
  211. for (let i = 0; i < fileDivs.length; i++) {
  212. let itemX_pos = fileDivs[i].offsetWidth + fileDivs[i].offsetLeft
  213. let itemY_pos = fileDivs[i].offsetHeight + fileDivs[i].offsetTop
  214. let condition1 = itemX_pos > this.left
  215. let condition2 = itemY_pos > this.top
  216. let condition3 = fileDivs[i].offsetLeft < this.left + this.width
  217. let condition4 = fileDivs[i].offsetTop < this.top + this.height
  218. if (condition1 && condition2 && condition3 && condition4) {
  219. fileDivs[i].classList.add('temp-selected')
  220. } else {
  221. fileDivs[i].classList.remove('temp-selected')
  222. }
  223. }
  224. this.clearBubble(e)
  225. })
  226. },
  227. mouseUpfn(e) {
  228. this.$nextTick(() => {
  229. document.getElementById('timecontainer').removeEventListener('mousemove', this.mousemovefn)
  230. let selectDom = document.getElementsByClassName('temp-selected')
  231. ;[].slice.call(selectDom).forEach(item => {
  232. if (item.classList.contains('selected')) {
  233. item.classList.remove('selected')
  234. } else {
  235. item.classList.add('selected')
  236. }
  237. item.classList.remove('temp-selected')
  238. })
  239. if (this.selectBoxDashed) {
  240. try {
  241. this.selectBoxDashed.parentNode.removeChild(this.selectBoxDashed)
  242. } catch (err) {
  243. // console.log(err)
  244. }
  245. }
  246. let fileDivs = document.getElementsByClassName('list')
  247. for (let i = 0; i < fileDivs.length; i++) {
  248. if (fileDivs[i].classList.contains('selected')) {
  249. this.timeList[i] = '1'
  250. } else {
  251. this.timeList[i] = '0'
  252. }
  253. }
  254. this.$emit('triggertime', this.timeList.join(''))
  255. this.clearBubble(e)
  256. })
  257. },
  258. setcurrent(item, index) {
  259. if (item == 0) {
  260. this.timeList.splice(index, 1, '1')
  261. } else {
  262. this.timeList.splice(index, 1, '0')
  263. }
  264. },
  265. selectAllornot(e) {
  266. this.timeList.forEach((item, index) => {
  267. this.timeList.splice(index, 1, Number(e.target.checked))
  268. })
  269. this.$emit('triggertime', this.timeList.join(''))
  270. }
  271. }
  272. }
  273. </script>
  274. <style>
  275. .select-box-dashed {
  276. position: absolute;
  277. display: none;
  278. width: 0px;
  279. height: 0px;
  280. padding: 0px;
  281. margin: 0px;
  282. border: 1px dashed #0099ff;
  283. background-color: #c3d5ed;
  284. opacity: 0.5;
  285. filter: alpha(opacity=50);
  286. font-size: 0px;
  287. z-index: 99999;
  288. }
  289. </style>