JSFiddle - React, Tailwind, and code Playground
HTML
<script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.6.14/vue.js"></script>
<div id="app">
<select v-model="column">
<option v-for="n in filterColumns" :value="n[0]">{{ n[1] }}</option>
</select>
<select v-model="operation">
<option v-for="n in operations" :value="n[0]">{{ n[1] }}</option>
</select>
<input type="text" v-model="filterVal">
<ul>
<li v-for="n in filteredItems">{{ n }}</li>
</ul>
</div>
JavaScript
new Vue({
el: '#app',
data: () => ({
items: [
{ id: 1, name: 'Утренний марафон', count: 69, distance: 1500 },
{ id: 2, name: 'Дневной марафон', count: 187, distance: 4500 },
{ id: 3, name: 'Вечерний марафон', count: 666, distance: 3000 },
],
types: {
string: {
equal: (a, b) => a.toLowerCase() === b,
contains: (a, b) => a.toLowerCase().includes(b),
greater: (a, b) => a.toLowerCase() > b,
less: (a, b) => a.toLowerCase() < b,
},
number: {
equal: (a, b) => a === +b,
contains: (a, b) => `${a}`.includes(b),
greater: (a, b) => a > +b,
less: (a, b) => a < +b,
},
},
filterColumns: [
[ 'name', 'имя', 'string' ],
[ 'count', 'количество', 'number' ],
[ 'distance', 'расстояние', 'number' ],
],
operations: [
[ 'equal', 'равно' ],
[ 'contains', 'содержит' ],
[ 'greater', 'больше' ],
[ 'less', 'меньше' ],
],
column: '',
operation: '',
filterVal: '',
}),
computed: {
filteredItems() {
const { items, column } = this;
const type = this.filterColumns.find(n => n[0] === column)?.[2];
const filterFn = this.types[type]?.[this.operation];
const filterVal = this.filterVal.toLowerCase();
return filterFn && filterVal
? items.filter(n => filterFn(n[column], filterVal))
: items;
},
},
});