简体   繁体   中英

Hide and show table column based on user selection

I am trying to hide and show a table column based on user selection. But it is not working as expected. Here is the link to the codepen file.

https://codepen.io/nigel1995/pen/XWKbqoe?editors=1111

<div id="app">
  <div v-for="item in columnHeaders">
    <label>
      <input type='checkbox' :value='item.value' v-model="selectedType"> {{ item.text }}
    </label>
  </div>

  <table class="selection-div">
    <tr>
      <template v-for="item in columnHeaders">
        <th v-if="showHeader(item)">{{ item.text }}</th>
      </template>
    </tr>
     <tr v-for="desert in deserts">
        <td v-if="!hideCol(desert)">{{ desert.name }}</td>
       <td v-if="!hideCol(desert)">{{ desert.fat }}</td>
    </tr>
  </table>
</div>
new Vue({
  el: '#app',
  data: {
    selectedType: [],
     columnHeaders: [
        { text: 'Name', value: 'name', show: true },
        { text: 'Fat (g)', value: 'fat', show:true },
      ],
      deserts: [
        {
          name: 'Frozen Yogurt',
          fat: 6.0,
        },
        {
           name: 'Golden Yogurt',
           fat: 6.0,
        },
        {
           name: 'Tasty Yogurt',
           fat: 6.0,
        }
      ]
  },
  
  
  methods: {
    hideCol(row){
      const t = Object.keys(row)[0];
      return this.selectedType.includes(t);
    },
    
    showHeader(val){
     return (val.show && !this.selectedType.includes(val.value));       
    } 
  },
});

What I want to do is making the display of table columns dynamic and not check it in each column as table headers will be dynamic in the future. Any direction would be appreciated.

By using a computed method, we can automatically create the visibleColumns data element. It defaults to all columns when there's no selected column, otherwise it returns only the selected columns.

The vue template then checks if the column is in visibleColumns . It also automatically creates data columns based on visibleColumns .

<div id="app">
  <div v-for="item in columnHeaders">
    <label>
      <input type='checkbox' :value='item.value' v-model="selectedType"> {{ item.text }}
    </label>
  </div>

  <table class="selection-div">
    <tr>
      <th 
        v-for="item in columnHeaders"
        v-if="visibleColumns.includes(item.value)">
        {{ item.text }}
      </th>
    </tr>
     <tr v-for="desert in deserts">
       <td v-for="column in visibleColumns">{{ desert[column] }}</td>
    </tr>
  </table>
</div>
new Vue({
  el: '#app',
  data: {
     selectedType: [],
     columnHeaders: [
        { text: 'Name', value: 'name' },
        { text: 'Fat (g)', value: 'fat' },
      ],
      deserts: [
        {
          name: 'Frozen Yogurt',
          fat: 6.0,
        },
        {
           name: 'Golden Yogurt',
           fat: 6.0,
        },
        {
           name: 'Tasty Yogurt',
           fat: 6.0,
        }
      ]
  },
  
  computed: {
    visibleColumns() {
      if(this.selectedType.length === 0) {
        return this.columnHeaders.map(c => c.value);
      }
      
      return this.selectedType;
    }
  },

});

View Codepen

You need to pass the object key you want to hide:

 <tr v-for="desert in deserts">
    <td v-if="!hideCol('name')">{{ desert.name }}</td>
   <td v-if="!hideCol('fat')">{{ desert.fat }}</td>
</tr>

then check if that key should be visible or not:

hideCol(key){
  return this.selectedType.includes(key);
},

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM