Есть переменная, содержащая в себе массив объектов. При клике на checkbox
, объекты сортируются в зависимости от первой буквы в значении одного из ключей. То есть, сортируются по алфавиту.
НО. Как сделать так, чтобы при повторном клике (когда чекбокс принимает false
), массив объектов приходил к исходному виду?
new Vue({
el: '.townsProject',
data: {
towns: [{
town: Moscow,
yearvisited: 2015
},
{
town: Saint - Petersburg,
yearvisited: 2019
},
{
town: Novorossiisk,
yearvisited: 2016
}
]
},
methods: sort: function() {
this.towns.sort(function(a, b) {
if (a.town > b.town) {
return 1;
}
if (a.town < b.town) {
return -1;
}
return 0;
})
}
<div class="townsProject">
<input class="container__movieList__seen" type='checkbox' id='sort2' v-on:click="sort()">
<label for='sort2'>Отсортировать по алфавиту</label>
</div>
Не нужно изменять исходный массив. Для этого лучше использовать computed
свойство. И не забудьте клонировать исходный массив прежде чем сортировать, например, с помощью [].concat()
new Vue({
el: '.townsProject',
data() {
return {
sort: false,
towns: [
{
town: "Moscow",
yearvisited: 2015
},
{
town: "Saint - Petersburg",
yearvisited: 2019
},
{
town: "Novorossiisk",
yearvisited: 2016
}
]
}
},
computed: {
sorted_list() {
if (this.sort) {
return [].concat(this.towns).sort(function(a, b) {
if (a.town > b.town) {
return 1;
}
if (a.town < b.town) {
return -1;
}
return 0;
})
}
return this.towns
}
}
})
<script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.5.17/vue.js"></script>
<div class="townsProject">
<input class="container__movieList__seen" type='checkbox' id='sort2' v-model="sort">
<label for='sort2'>Отсортировать по алфавиту</label>
<ul>
<li v-for="town in sorted_list" :key="town.town">{{ town.town }}</li>
</ul>
</div>
PS: Всегда инициализируйте объект data
c помощью функции:
data() {
return {
...
}
}
иначе, если компонент будет использоваться несколько раз на странице, они будут ссылаться на один объект и доставят много неприятностей. В варианте с функцией - при инициализации компонента будет создан обособленный объект
Вам необходимо сохранять изначальный порядок элементов. Для этого можно добавить свойство к объектам массива towns
, к примеру orderIndex
. При клике Вы можете передавать в метод событие и определять отмечен ли чекбокс или нет. Если "да", то можно брать значение value из чекбокса и использовать его для сортировки, если "нет", то использовать значение по-умолчанию. Выглядеть это может примерно так:
<input type='checkbox' value="town" v-on:click="sort($event)" />
new Vue({
el: '.townsProject',
data: {
towns: [
{ town: "Moscow", orderIndex: 0},
{ town: "Saint-Petersburg", orderIndex: 1 },
{ town: "Novorossiisk", orderIndex: 2}
]
},
methods: {
sort: function (ev) {
var isChecked = ev.target.checked;
var sortProp = isChecked ? ev.target.value : 'orderIndex';
this.towns.sort(function (a, b) {
if (a[sortProp] > b[sortProp]) {
return 1;
}
if (a[sortProp] < b[sortProp]) {
return -1;
}
return 0;
});
}
}
});
По этому принципу можно построить сортировку по другим свойствам, но это будет удобней сделать с радио-кнопками, т.к. отмечен будет лишь один элемент, в отличии от чекбоксов, где пользователь может создать любую комбинацию из отмеченных и не отмеченных элементов.
Айфон мало держит заряд, разбираемся с проблемой вместе с AppLab
По клику на мою цель в консоли выводится сообщение, значит делегирование правильно работает, но тогда почему не удаляется класс?