Vu3动态添加行和列表格,支持增删改,复制直接用

![image](https://img2024.cnblogs.com/blog/2686952/202507/2686952-20250722161807535-1232244377.png)

 

<template>
  <div class="info-board">
    <h1>信息看板</h1>
    <el-button type="primary" @click="addRow" size="small" style="margin-bottom: 8px;">添加行</el-button>
    <el-button type="success" @click="openAddColDialog" size="small" style="margin-bottom: 8px; margin-left: 8px;">添加列</el-button>
    <el-button type="success" @click="saveRows" size="small" style="margin-bottom: 8px; margin-left: 8px;">保存</el-button>
    <el-table :data="tableData" border style="width: 100%; margin-top: 12px;">
      <el-table-column
        v-for="col in columns"
        :key="col.key"
        :prop="col.key"
        :label="col.label"
      >
        <template #header="{ column }">
          <span>{{ column.label }}</span>
          <!-- <el-button  size="small" circle icon="el-icon-minus" style="margin-left: 4px;" /> -->
            <el-icon v-if="columns.length > 1" @click.stop="deleteColumn(col.key)" style="margin-left: 10px;cursor: pointer;" ><Remove /></el-icon>
        </template>
        <template #default="scope">
          <el-input v-model="scope.row[col.key]" size="small" />
        </template>
      </el-table-column>
      <!-- 操作列 -->
      <el-table-column label="操作" width="80">
        <template #default="scope">
          <el-button type="danger" size="small" @click="deleteRow(scope.$index)">删除</el-button>
        </template>
      </el-table-column>
    </el-table>
    <!-- 添加列弹窗 -->
    <el-dialog v-model="addColDialogVisible" title="添加新列" width="300px">
      <el-input v-model="newColName" placeholder="请输入表头名称" />
      <template #footer>
        <el-button @click="addColDialogVisible = false">取消</el-button>
        <el-button type="primary" @click="addColumn">确定</el-button>
      </template>
    </el-dialog>
  </div>
</template>

<script setup lang="ts">
import 'element-plus/dist/index.css';
import { ref } from 'vue';
// 引入element-plus组件
import { ElTable, ElTableColumn, ElButton, ElDialog, ElInput, ElMessage } from 'element-plus';
import { Remove } from '@element-plus/icons-vue';

// 表头数据
const columns = ref([
  { label: '系统名称', key: 'sysName' },
  { label: '系统负责人', key: 'sysUser' },
  { label: '负责人电话', key: 'sysUserPhone' },
  { label: '用户部门', key: 'sysUserDept' },
  { label: '系统管理员账号', key: 'sysAdminAccount' },
  { label: '系统管理员密码', key: 'sysAdminPassword' },
  { label: '系统地址', key: 'sysAdminPassword' },

]);

// 表格数据
const tableData = ref<Record<string, string>[]>([
  { col1: '', col2: '' },
]);

// 添加行
function addRow() {
  const newRow: Record<string, string> = {};
  columns.value.forEach(col => {
    newRow[col.key] = '';
  });
  tableData.value.push(newRow);
}

function saveRows() {
  console.log(tableData.value);
}

// 添加列弹窗相关
const addColDialogVisible = ref(false);
const newColName = ref('');

function openAddColDialog() {
  newColName.value = '';
  addColDialogVisible.value = true;
}

function addColumn() {
  const name = newColName.value.trim();
  if (!name) {
    ElMessage.warning('请输入表头名称');
    return;
  }
  // 生成唯一key
  const key = `col${columns.value.length + 1}`;
  columns.value.push({ label: name, key });
  // 给每一行加新字段
  tableData.value.forEach(row => {
    row[key] = '';
  });
  addColDialogVisible.value = false;
}

// 删除行
function deleteRow(idx: number) {
  tableData.value.splice(idx, 1);
}
// 删除列
function deleteColumn(key: string) {
  if (columns.value.length === 1) return;
  columns.value = columns.value.filter(col => col.key !== key);
  tableData.value.forEach(row => {
    delete row[key];
  });
}
</script>

<style scoped lang="scss">
.info-board{
    width: 100%;
    height: 100%;
    background-color: #fff;
    padding: 20px;
    box-sizing: border-box;
    border-radius: 10px;
    box-shadow: 0 0 10px 0 rgba(0, 0, 0, 0.1);
}
.el-table {
  margin-top: 16px;
}
</style>

  

posted on 2025-07-22 16:20  温华从此不练剑  阅读(57)  评论(0)    收藏  举报