Создал слайдер (блок slider
) с поддержкой входных параметров (this.params
) и слайд-шоу. При установке двух и более экземпляров на страницу, происходит (по-видимому) смешивание их параметров, или их переопределение. Перелистывание слайдов всегда производится с учетом ширины (width
) и скорости перелистывания (duration
) последнего экземпляра. То же касается величины задержки (delay
) при слайд-шоу.
Помогите, пожалуйста, разобраться, в чем таится ошибка.
Проблема была в том, что параметры создавались у прототипа, а не у инстанса.
Отправил pull request с подробными комментариями. Там три коммита: в первом обновил зависимости (это никак не связано с сутью вопроса, но не зря же мы их обновляем ;)), во втором все смысловые изменения и в третьем результат пересборки.
Предлагаю дальше подумать нам тремя направлениями для улучшения:
order
и необходимости заранее запоминать количество слайдов, в пользу использования модификатораcurrent
на текущем активном слайде. Тогда всегда можно будет получить его индекс в общей jQuery-коллекции слайдов.Большое спасибо за PR с подробным разбором ошибок и недочетов.
Касательно п.1: генерация меню с помощью BEMHTML показалась вначале несложной задачей, однако я сел в лужу. Подробнее:
list
в BEMJSON отказался, решил перенести его создание в BEMHTML.elemMatch()
в шаблоне для корневогоslider
, чтобы подписаться на элементыitem
. Безуспешно.item
в кастомныйwrapper
, чтобы опробоватьapplyCtx()
, который наверняка понадобится на следующих шагах. Неудача.Может, следует работать с модой
default
у блокаslider
?Не понимаю, как реализовать задуманное. Подскажите, пожалуйста, в какую сторону копать.
Если я правильно понял, то теперь в BEMJSON ожидается такая структура:
А на выходе хочется
?
Если так, то шаблоны будут выглядеть примерно так:
По поводу неудачных экспериментов с шаблонами предлагаю каждый отдельный момент, который вызывает вопросы, скидывать в виде ссылок на песочницу http://bem.github.io/bem-xjst/ (значения полей сохраняются в урле) с описанием, что хотелось получить в результате, тогда будет понятно, что именно не получается и можно будет внятно ответить.
А
console.log()
таки должен выводить сообщения вgit bash
в момент пересборки шаблонов (enb make
/ рефреш страницы при запущенномenb server
).Все верно, большое спасибо.
order
, убрал прочую лишнюю логикуОб использовании мной
setTimeout()
заместоsetInterval()
: вариант с вызовомsetTimeout()
позволяет убрать первоначальную (длинную) задержку до первого перелистывания при слайдшоу, которая возникает приsetInterval()
и отводится на генерацию события клика на первом переключателе, за что и был выбран (костыль правда). (С логированием действительно все в порядке)А точно ли нужно эту задержку убирать? Пользователь-то должен успеть рассмотреть и первый слайд тоже ;)
В плане примера организации API можно посмотреть на порт карусели из Bootstrap на
bem-core
: https://github.com/tadatuta/bl-carousel/Решил создать внешний блок
remote
, который при клике обращается к слайдеру.В слайдере, в свою очередь, следующие изменения:
В консоли отладчика —
null
для вызоваslider
черезfindBlockOutside()
, хотя структура BEMJSON следующая:В чем дело?
findBlockOutside()
поднимается строго вверх по дереву и не затрагивает сиблингов. Т.е. в данном случае чтобы «добраться» изremote
доslider
, нужноthis.findBlockOutside('content').findBlockInside('slider')
, но в целом практика обращения из блока наружу через DOM не очень хорошая, т.к. вызывает связанность блоков (например, та самая ошибка при попытке выставить модификатор, если слайдера рядом не оказалось).Подробнее про принципы взаимодействия блоков в JS см. https://ru.bem.info/forum/163/
Пробую к
remote
примешать блокslider
.Связь через
this.findBlockOn()
идет только в том случае, если структура BEMJSON такова:Судя по всему, это и есть способ расположения одного js-блока на несколько DOM-узлов. Вопрос: это нормально, так и должно быть? (Почему
remote
не ожидается как блок-микс со специальной декларацией? Ссылка ) Хорошая ли это практика для связи внешних (удаленных) переключателей?Дополнительно: как в таком случае быть с методом
updateWidth()
, который теперь применяет новые стили как для "корневого"slider
, так и для его "переключателя" (там это явно лишнее)? Пока только сильно привязанный к контексту хак:this.domElem.eq(0).css('width', width);
Да, один блок на нескольких DOM-узлах требует совпадающего
id
в js-параметрах. Это необходимо, т.к. на странице может быть несколько разных слайдеров, каждый со своим собственнымremote
, нужно как-то отличать, какой чей. Подробнее про эту связь см. https://ru.bem.info/technology/i-bem/v2/i-bem-js-html-binding/#Один-js-блок-на-нескольких-html-элементахБлоки-миксы — это другая история. Они исключительно о том, чтобы добавить их функциональность другим блокам. Например, есть некоторый метод
doSomething()
, который необходим блокуb1
и блокуb2
, при этомb1
иb2
совершенно разные. Чтобы не копипастить логику проdoSomething()
, ее можно вынести в отдельный блок-микс и примиксовать к каждому. На этом смысл их существования исчерпывается.В данном случае можно просто задавать ширину для
slider__list
. В общем случае, при использовании подхода с разнесением блока на несколько DOM-узлов, можно добавлять некоторый специальный элемент (inner
,main
, etc).Ну и остаются еще варианты: организовать взаимодействие через общего родителя, который подпишется на события от
remote
и вызовет метод наslider
, либо применить глобальный канал событий / модель, храняющую общий стейт и т.п.