提问者:小点点

根据列计数更改表列宽


我正在使用Vue,我想要一个表改变它的列宽度取决于列的数量。详细规范如下:

  • 第一列是索引列(如日期或序列号),它始终存在。宽度为200px.
  • 从第二列开始,每个列的宽度通过平均分配剩余宽度来确定,即(表宽-200px)/#列。宽度不能小于150px或大于300px。因此,如果计算的宽度小于150px,则最终宽度为150px。同样,如果宽度大于300px,则最终宽度为300px.
  • 如果表格不够宽,无法显示所有列,则必须添加滚动条才能查看其余内容。

基本上,我将width:max(150px,min(300px,calc((100%-200px)/${this.columnCount})))应用于所有标记,除了第一个标记。然而,当列#大时,列宽度变得小于150px。我做错了什么?

复制代码见https://codepen.io/hitochan777/pen/mdrwxwy


共1个答案

匿名用户

问题似乎是100%实际上引用的不是表的宽度,而是导致CSS失败的TH。

相反,您必须获取width width JavaScript。您可以通过使用ref,然后使用隐式宽度而不是100%来实现这一点。

另一个问题是,您希望该表是可滚动的,但是通过对该表应用overflow-x:[scroll/auto]无法直接实现这一点。相反,您必须将表包装在div中,并向该元素添加overflow-x:[scroll/auto]

这个包装器也是您在计算th宽度时要使用的元素,因为表的大小将根据th的大小不断动态调整,因此是不可靠的。

null

const HelloVueApp = {
  data() {
    return {
      rowCount: 5,
      columnCount: 50,
      indexColumnStyle: {
        width: "200px",
        textAlign: "left"
      },
      tableWidth: 1980
    };
  },
  mounted() {
    // Should add a debounce to the event method 
    window.addEventListener("resize", this.onResize);
    // Run once on mounted to get table width
    this.onResize();
  },
  beforeDestroy() {
    // Remember to remove the event listener when the component is destroyed to
    // avoid memory leaks
    window.removeEventListener("resize", this.onResize);
  },
  methods: {
    onResize() {
      this.tableWidth = this.$refs['my-table-container'].clientWidth
    }
  },
  computed: {
    dataColumnStyle() {
      return {
        width: `max(150px, min(300px, calc((${this.tableWidth}px - ${this.indexColumnStyle.width}) / ${this.columnCount})))`,
        textAlign: "left"
      };
    }
  }
};

Vue.createApp(HelloVueApp).mount("#hello-vue");
table, th, td {
  border: 1px solid black;
  border-collapse: collapse;
}

.table {
  table-layout: fixed;
  width: 100%;
}

.table-responsive {
  overflow-x: auto;
}
<script src="https://unpkg.com/vue@next"></script>

<div id="hello-vue">
  <div class="table-responsive" ref="my-table-container">
    <table class="table">
      <thead>
        <tr>
          <th :style="indexColumnStyle">date</th>
          <th v-for="c in columnCount" :style="dataColumnStyle">
            {{c}}
          </th>
        </tr>
      </thead>
      <tbody>
        <tr v-for="r in rowCount">
          <td>{{r}}</td>
          <td v-for="c in columnCount">{{c * 10}}</td>
        </tr>
      </tbody>
    </table>
  </div>
</div>