AngularJS/Isotope вызывает .isotope(reLayout) после загрузки страницы

Я пытаюсь использовать изотоп с AngularJS (для компоновки набора «карточек»). Вместо того, чтобы добавлять элементы в DOM напрямую, я добавляю элементы через изотоп, используя container.isotope('insert',element).

Я делаю все это в функции связывания, но оказывается, что когда я вставляю что-то в DOM в функции связывания, размеры устанавливаются неправильно (в моем случае высота равна 0), поэтому элементы не рисуются должным образом.

Если я изменю размер окна, элементы будут отображаться правильно. Я думал, что мог бы использовать наблюдение за $viewContentLoaded для вызова функции, которая обновляет расположение изотопов (т. е. container.isotope('reLayout')), но событие $viewContentLoaded никогда не срабатывает. Я делаю что-то не так или есть какая-то другая методология, которую я должен использовать?

РЕДАКТИРОВАТЬ: я получил функцию для запуска, выполнив scope.$root.$on('$viewContentLoaded',function(){}); но это не помогло... (похоже, его вызывают рано)

РЕДАКТИРОВАТЬ 2: После того, как вы поиграли намного больше, div правильно добавляется с изотопом, но поскольку его родительский div имеет 0 высоты, размеры дочерних элементов устанавливаются правильно. Если я делаю setTimeout(element.isotope('relayout'),100), он работает нормально. Любой способ имитировать это?

module.directive('tileGrid',function(){
var mytemplate = '<div class="item {{card.class}}">{{card.Title}}</div>';
var original = angular.element(mytemplate);

return {
    restrict: 'A',
    replace: true,
    transclude: true,
    template: '<div id="tileGridContainer"></div>',     
    link: function(scope,element,attrs)
        { 
            element.isotope({itemSelector:'.item',layoutMode:'fitRows'});                               
            var curCards = scope.cards.map(function(a){ return a.nextView;});                                               

            scope.$watch('scope.cards',function()
            {       
//will do this for diff, but for now iterate over all elements
                for(var i=0;i<scope.cards.length;i++)
                {                           
                    var card = scope.cards[i];

                    var childScope = scope.$new();
                    childScope.card = card;


                    scope.compile(original)(childScope,function(clonedElement,childScope){                          
                        element.isotope('insert',clonedElement);                            
                    });


                    scope.$on('$viewContentLoaded', function(){ console.log("view loaded"); });

                }
            }

            );              
        }
    };
});

person user1167650    schedule 16.08.2012    source источник


Ответы (1)


Я не совсем уверен, в этом ли дело или нет. Я столкнулся с проблемой, когда все перепуталось со ссылками, потому что я модифицировал DOM в postLink. В итоге я отложил все манипуляции с DOM с помощью setTimeout.

Однако... теперь, когда я возвращаюсь и пытаюсь воспроизвести проблему, я ее больше не вижу.

В Angular UI упоминается проблема, и мне стало известно, что это помогло мне решить проблему, с которой я столкнулся:

модули/директивы пользовательского интерфейса Angular/ select2/select.js:103 на GitHub

Вы можете попытаться выполнить все манипуляции с DOM в функции компиляции или в вызове setTimeout.

Если вы еще этого не сделали, прочтите AngularJS: директивы о том, когда безопасно выполнять манипуляции с DOM, а когда нет.

person Tim Harper    schedule 07.11.2012