[Перевод] Vue.js для начинающих, урок 5: обработка событий
Сегодня, в пятом уроке курса по Vue.js для начинающих, речь пойдёт о том, как обрабатывать события.

→ Vue.js для начинающих, урок 1: экземпляр Vue
→ Vue.js для начинающих, урок 2: привязка атрибутов
→ Vue.js для начинающих, урок 3: условный рендеринг
→ Vue.js для начинающих, урок 4: рендеринг списков
Цель урока
Первая цель урока заключается в том, чтобы в карточке товара появилась бы кнопка, нажатия на которую увеличивают количество товара в корзине.
Вторая цель заключается в том, чтобы при наведении мыши на названия цветов вариантов товара менялось бы изображение товара.
Начальный вариант кода
В файле проекта index.html будет присутствовать следующий код:
{{ product }}
In stock
Out of Stock
- {{ detail }}
{{ variant.variantColor }}
Вот содержимое main.js:
var app = new Vue({
el: '#app',
data: {
product: "Socks",
image: "./assets/vmSocks-green.jpg",
inStock: true,
details: ['80% cotton', '20% polyester', 'Gender-neutral'],
variants: [
{
variantId: 2234,
variantColor: "green"
},
{
variantId: 2235,
variantColor: "blue"
}
]
}
})
Задача
Нам нужна кнопка, которой будет назначен прослушиватель события, реагирующий на щелчок по ней. По щелчку должен запускаться метод, который и выполняет увеличение количества товара в корзине.
Решение
Для начала — добавим, в main.js, в объект data, новое свойство, которое будет символизировать количество товара в корзине:
cart: 0
Cart({{ cart }}) Если теперь нажать на кнопку — количество товара в корзине увеличится на 1. Как всё это работает? Давайте разберёмся в представленной здесь конструкции. Использование директивы Это — простой, но не вполне реалистичный пример. Вместо того, чтобы указывать в кавычках выражение Тут используется механизм, очень похожий на тот, который мы уже применяем для хранения данных. А именно, речь идёт о том, что у объекта с опциями, используемого при создании экземпляра Vue, может быть необязательное свойство, носящее имя Продолжим разбор того, что здесь происходит. Кнопка прослушивает события Если бы мы просто написали бы в теле функции что-то вроде Возможно, вы сейчас задаётесь вопросом о том, что сейчас мы просто увеличиваем количество товаров в корзине, но самого товара в корзину не добавляем. Может, мы что-то делаем не так? Это — правильный вопрос. Мы реализуем соответствующий функционал позже, в одном из следующих уроков. Итак, теперь, когда мы изучили основы обработки событий во Vue, взглянем на более сложный пример. Для начала — давайте расширим объекты массива Вот соответствующий код в
{{ variant.variantColor }}
Создадим этот метод в Но тут мы обновляем значение, хранящееся в
Когда вызывается этот метод, → Вот заготовка, которую вы можете использовать для решения этой задачи. → Вот решение задачи. → Vue.js для начинающих, урок 1: экземпляр Vue
Теперь, в index.html, добавим элемент , с помощью которого на страницу будет выводиться число, хранящееся в свойстве cart:
Ещё мы создадим в коде index.html кнопку, которая позволяет добавлять товар в корзину:
Здесь обратите внимание на то, что для инкрементирования значения, хранящегося в cart, мы используем директиву v-on.
Страница с корзиной и с кнопкой для добавления товара в корзину v-on сообщает Vue о том, что мы хотим прослушивать события, происходящие с кнопкой. Потом идёт двоеточие, после которого указывается то, какое конкретно событие нас интересует. В данном случае это — событие click. В кавычках записано выражение, которое добавляет 1 к значению, хранящемуся в cart. Это происходит при каждом щелчке по кнопке.cart += 1, давайте сделаем так, чтобы щелчок по кнопке вызывал бы метод, который будет увеличивать значение, хранящееся в cart. Вот как это выглядит:
Как видите, здесь addToCart — это имя метода, который будет вызван при возникновении события click. Но сам метод мы пока не объявили, поэтому давайте сделаем это прямо сейчас, оснастив им наш экземпляр Vue.methods, в котором содержится объект с методами. В нашем случае это будет всего один метод — addToCart: methods: {
addToCart() {
this.cart += 1
}
}
Теперь, когда мы щёлкаем по кнопке, вызывается метод addToCart, который и увеличивает значение cart, выводящееся в теге .click благодаря директиве v-on, которая вызывает метод addToCart. Этот метод находится в свойстве methods экземпляра Vue. В теле функции содержится инструкция, добавляющая 1 к значению this.cart. Так как this хранит ссылку на то место, где хранятся данные экземпляра Vue, в котором мы находимся, функция добавляет 1 к значению cart. А this.cart — это то же самое, что и свойство cart, объявленное в свойстве data объекта с опциями.cart += 1, то мы столкнулись бы с сообщением об ошибке cart is not defined. Именно поэтому мы используем конструкцию this.cart и обращаемся к cart из экземпляра Vue, используя this.variants из объекта data, добавив туда свойство variantImage, хранящее путь к изображению нужного варианта товара. Приведём соответствующий раздел файла main.js к такому виду: variants: [
{
variantId: 2234,
variantColor: "green",
variantImage: "./assets/vmSocks-green.jpg"
},
{
variantId: 2235,
variantColor: "blue",
variantImage: "./assets/vmSocks-blue.jpg"
}
],
Теперь каждому варианту товара, зелёным и синим носкам, назначено собственное изображение.Задача
Нужно, чтобы, по наведению мыши на название цвета варианта носков, в поле, где выводится изображение товара, вывелось бы изображение variantImage для соответствующего цвета.Решение
Тут нам снова пригодится директива v-on. Но в этот раз мы воспользуемся сокращённым вариантом её записи, который выглядит как @. А прослушивать будем событие mouseover.index.html:
Обратите внимание на то, что мы передаём методу updateProduct, в виде аргумента, variant.variantImage.main.js: updateProduct(variantImage) {
this.image = variantImage
}
Этот метод очень похож на тот, который мы недавно создавали для увеличения значения cart.image. А именно, в image записывается то, что хранится в variantImage того варианта товара, на который наведён указатель мыши. Соответствующее значение передаётся функции updateProduct из самого обработчика события, находящегося в index.html:
Другими словами, теперь метод updateProduct готов к вызову с параметром variantImage.variant.variantImage передаётся ему в виде variantImage и используется для обновления значения, хранящегося в this.image. Мы, по аналогии с ранее рассмотренной конструкцией this.cart, можем сказать, что this.image — это то же самое, что image. В результате значение, хранящееся в image, теперь динамически обновляется в соответствии с данными варианта товара, на который наведён указатель мыши.Синтаксис ES6
Здесь мы, создавая методы, пользовались такими конструкциями: updateProduct(variantImage) {
this.image = variantImage
}
Это сокращённый вариант описания методов, который появился в ES6. Более старый вариант записи подобных конструкций выглядит так: updateProduct: function(variantImage) {
this.image = variantImage
}
Практикум
Создайте кнопку и соответствующий метод, которые позволят уменьшать значение, хранящееся в cart.Итоги
Подведём итоги сегодняшнего занятия: v-on.v-on выглядит как @.v-on можно указать тип прослушиваемого события: v-on может вызывать методы.v-on, может принимать аргументы.this содержит ссылку на то место, где хранятся данные текущего экземпляра Vue. Его использование позволяет работать с данными экземпляра, а так же с методами, объявленными в экземпляре.
Получилось ли у вас домашнее задание к этому уроку?
→ Vue.js для начинающих, урок 2: привязка атрибутов
→ Vue.js для начинающих, урок 3: условный рендеринг
→ Vue.js для начинающих, урок 4: рендеринг списков
