
最近工作中遇到一个这样的需求, 后台给出宽度和高度, 然后前端展示成上面的样子 , 颜色随便给的
灰色: 超出边缘的不用分 , 无法被选中
绿色: 已经被占用的 , 无法被选中
白色 : 可以选择的区域 , 点击会变成 红色 再次单击 会取消
最终需求: 在白色区域 选择一个 ‘ 坐标 ‘
代码如下 vue 项目
<template>
<div>
<el-button @click="openDialog" type="primary" size="mini"
>打开dialog</el-button
>
<el-dialog title="外层 Dialog" :visible.sync="dialog1">
<el-dialog
width="900px"
title="内层 Dialog"
:visible.sync="dialog2"
append-to-body
>
<div class="dialog_container">
<div class="index">
<div class="header">
<div class="block"></div>
<div v-for="(i, k) in 10" :key="k" class="box">
{{ k + 1 }}
</div>
</div>
<div class="body">
<div class="left">
<div v-for="(i, k) in 10" :key="k" class="box">{{ k + 1 }}</div>
</div>
<div class="main">
<div
@click="choosed(k)"
:class="[getColor(k), chooseIndex === k ? ‘red‘ : ‘‘]"
v-for="(i, k) in 100"
:key="k"
class="box"
></div>
</div>
</div>
</div>
<div class="img">
<img src="../assets/timg.jpg" />
</div>
</div>
</el-dialog>
<div slot="footer" class="dialog-footer">
<el-button @click="dialog1 = false">取 消</el-button>
<el-button type="primary" @click="dialog2 = true"
>打开内层 Dialog</el-button
>
</div>
</el-dialog>
</div>
</template>
<script>
export default {
data: function () {
return {
dialog1: false,
dialog2: false,
// 假设五行四列
row: 5,
col: 4,
// 占用
used: [12, 33],
chooseIndex: ‘‘,
}
},
methods: {
openDialog() {
this.dialog1 = true
},
choosed(k) {
const index = k + 1
// 不超过边缘
if (
index % 10 > this.col ||
index > this.row * 10 ||
(this.col < 10 && index % 10 === 0)
)
return
// 判断是否被占用
if (this.used.includes(index)) return
// 判断是否和之前选中的为同一个
console.log(‘能选中‘)
if (this.chooseIndex === index - 1) {
return (this.chooseIndex = ‘‘)
}
// 不一样
this.chooseIndex = index - 1
},
getColor(k) {
const index = k + 1
if (
parseInt(index % 10) > this.col ||
index > this.row * 10 ||
(this.row < 10 && index % 10 === 0)
) {
return ‘gray‘
} else {
if (this.used.includes(index)) {
return ‘green‘
} else {
return ‘‘
}
}
// 1 空
// 2 占用
// 3 不在选择范围内
},
},
created() {},
}
</script>
<style lang=‘scss‘ scoped>
* {
box-sizing: border-box;
}
.dialog_container {
width: 100%;
display: flex;
.index {
flex: 1;
width: 10%;
box-sizing: border-box;
.header {
height: 40px;
width: 100%;
display: flex;
.block {
width: 40px;
height: 100%;
border: 1px solid orange;
}
.box {
flex: 1;
text-align: center;
line-height: 40px;
border: 1px solid orange;
border-left: none;
background-color: #eee;
}
}
.body {
display: flex;
.left {
width: 40px;
.box {
height: 40px;
border: 1px solid orange;
border-top: none;
text-align: center;
line-height: 40px;
background-color: #eee;
}
}
.main {
flex: 1;
display: flex;
flex-wrap: wrap;
.box {
flex: 10%;
height: 40px;
border-right: 1px solid orange;
border-bottom: 1px solid orange;
}
}
}
}
.img {
width: 300px;
img {
width: 100%;
height: auto;
}
}
}
// 绿色 占用
.green {
background-color: green;
}
// 红色 选中项
.red {
background-color: red;
}
// 灰色 不能选中的区域
.gray {
background-color: gray;
}
// .current {
// }
</style>
原文:https://www.cnblogs.com/liuyuexue520/p/13881380.html