Тормоза ng-repeat? Нет — просто ngAnimate+transition в css

Не так давно нашел хороший плагин для angularjs для ввода тэгов ngTagEditor (демо на указанной странице). Понравился он мне своим размером — 5 Кб (css+js) — и это, между прочим, без минификации. У него было всё, что мне нужно, а ненужное можно было допилить напильником.

В общем, посмотрел демо на сайте, скачал и добавил его в свой framework велосипед. Начал тестировать и обнаружил неприятный баг — если в поле ввода новой категории нажать клавишу и держать, то категории списка Suggestions начинают дублироваться.



Первое, что пришло в голову — криво «доработал напильником». Тогда взял и запустил исходный пример локально — отлично заработало. После этого скопировал в пример свой доработанный код и он тоже отлично заработал.

Вывел в отладку переменную, которая содержит Suggestions. Стало понятно, что в переменной все нормально. Т.е. проблема именно в выводе. Тогда стал пенять на то, что данный плагин пересекся с чем то другим, подключенным ранее и из-за этого такое поведение. Самое очевидное — классы css пересеклись и на элементы по классам навешиваются какие-то события, которые и приводят к такому поведению. Стал отключать классы. Как только отключил класс tag — неприятный эффект пропал.

<span class="tag alert-info" ng-repeat="tag in suggestions" ng-mousedown="add(tag.id, tag.name)">{{tag.name}}</span>

Я обрадовался, что быстро нашел причину ошибки и тут же переименовал класс tag в framework-tag. Обновил страницу и получил ошибку. Удалил класс — ошибка пропала. Стал внимательно рассматривать класс:

.framework-editor .framework-tag{display:inline-block;height:24px;margin:0 7px 0 0;padding:0 5px;border-radius:2px;font-size:14px;line-height:24px;cursor:default;transition:box-shadow 100ms linear;} 

Тут вспомнил, что при просмотре в консоли отладки видел, как в элементах мелькают классы ng-animate, ng-enter которые относятся к ngAnimate. При чтении описания про ngAnimate попадалось свойство css transition. А при поиске по «ngAnimate»+«ошибка» нашлась страница, где человек жаловался, что пока не отработает одна анимация, другая не начинает работу. Честно говоря, особо не разбирался в сути той ошибки, но transition = 100ms весьма настораживало. Учитывая, что события нажатия клавиши (точнее изменения поля ввода) поступали в большом количестве 100ms могло привести именно к такому эффекту. Убрал из описания класса:

transition:box-shadow 100ms linear

И — УРА неприятный эффект пропал.

Если кто-то может поправить меня с точки зрения теории и терминологии, буду весьма рад. Так как нахождение правильного (?) решения в данном случае больше похоже на удачу, чем на фундаментальные знания.

Если кто-то знает другой хороший компонент для редактирования тэгов — тоже пишите. Я нашел tagger, ngTagsInput. Первый совсем простой, второй хорош, но размер 40 Кб. Да и напильником его допиливать сложнее просто потому, что он больше кода содержит.

P.S. Кстати, небольшие ошибки все-таки нашлись в тесте. Автор подключает файл css как css, а ниже его же подключает как js. Это мелочь и, думаю, в дальнейшем он исправит.
Share post
AdBlock has stolen the banner, but banners are not teeth — they will be back

More
Ads

Comments 2

    0
    стоит использовать track by id при указании способа итерации если постоянно колелкция перетряхивается путем пересоздания элементов
    docs.angularjs.org/error/ngRepeat/dupes
      0
      Насколько я понял, все дело было не в том что тормозит перебор из-за способа итерации (тем более что значений там было всего 4 шт, а при таком количестве не должен тормозить никакой метод перебора), а именно в анимации. Хотя у меня знаний особых нет по css и анимации, но я пришел к выводу что пока анимация ngAnimate не завершится, значения на экране не обновляются, а почему то добавляются в конец уже выведенных. А она не завершается пока не выполнится анимация из css плагина.
      Точнее наверное так: обновленные значения выводятся в конце предыдущих, а предыдущие анимированно исчезают. Но из-за то го что анимация не завершается — анимированного исчезновения не получается. Поэтому и происходит размножение значений. Но это, еще раз повторюсь, мои предположения. Нет у меня знаний по angular чтобы утверждать это на 100%.

    Only users with full accounts can post comments. Log in, please.