2013-08-05 7 views
0

Я столкнулся с ситуацией, которая кажется противоположной любому аналогичному вопросу здесь, на StackOverflow.Доступ к изолированной родительской области из переопределенной директивы

У меня есть директива <scroll>, которая просто обертывает любой контент, который он имеет, с прокручиваемым div. Это выглядит примерно так:

.directive('scroll', ['$document','$parse', function ($document,$parse) { 
return { 
    restrict: 'E', 
    replace: true, 
    transclude: true, 
    scope:false, 
    template: 
     '<div class="scroll">' + 
      '<div class="content" data-ng-transclude>' + 
      '</div>' + 
     '</div>', 
    link: function (scope, element, attr) { 
     // some code here.... 
    } 
}; 
}]); 

Это прекрасно работает само по себе.

Теперь у меня есть еще директиву под названием <editor>, который имеет изолированный объем и использует <scroll> в это шаблон. <editor> выглядит более или менее, как:

.directive('editor', ['$document', function ($document){ 
return { 
    restrict: 'EA', 
    replace: true, 
    transclude: false, 
    scope:true, 
    template: 
     '<div>' + 
      '....<scroll>....</scroll>....' + 
     '</div>', 
    link: function (scope, element, attrs) { 
     ..... 
    } 
}; 
}]); 

Теперь, вот в чем дело: мне нужно, чтобы получить доступ к области видимости s внутри <scroll> '<editor> функции связи с (где он говорит, что „какой-то код здесь“), но по какой-то причине Я не могу. Переменная scope в функции ссылки <scroll> в значительной степени пуста, и scope.$parent дает мне контроллер выше, пропуская <editor>, который должен быть в пути.

Я пытался играть с ng-transclude в разных местах в <editor> и попытался с помощью $emit, и я действительно невежествен об этом - я думаю, что изоляция сферы будет изолировать «меня и все, что ниже меня» от того, что выше, но кажется, что изоляция области просто берет «я» из дерева области ...

Надеюсь, что это достаточно ясно, спасибо.

+0

Посмотрите [видео Джона Линдквист в] (http://www.egghead.io/video/ 2CdivtU5ytY) об общении между директивами. Это может заставить вас идти в правильном направлении. –

+0

Вы должны стараться не делать этого таким образом, потому что теперь вы ограничиваете свою директиву прокрутки жестко закодированной в директиве вашего редактора. Это классический случай «связи» и ограничивает повторное использование ваших директив. При этом есть много способов сделать это. Лучше всего, вероятно, использовать $ emit или $ broadcast для отправки событий. Если вы сделаете это правильно, вы можете оставаться «развязанным» и по-прежнему использовать свой прокрутки в другом месте. –

+0

Это просто поразило меня, почему это происходит, хотя у меня пока нет решения: дело в том, что метод «link» внутренней директивы срабатывает перед родительским, поэтому я вижу, что я не могу получить доступ к области родителя от в функции 'link', но может быть разметкой с' {{}} '. Возможно, решение состоит в том, чтобы иметь внутреннюю директиву '$ watch' для того, чтобы верхняя директива была готова, прежде чем использовать' $ parse (...) (scope) ', чтобы добраться до нее. – motig88

ответ

0

Код, указанный для директивы editor, не создает область изоляции. Вместо этого он создает новую дочернюю область, которая прототипически наследуется от родительской/содержащей области.

Поскольку scroll директива scope: false, он будет использовать сферу ребенка, что создает editor - нет необходимости в $parent.

Да, функция связи для editor будет работать после функции связи для scroll. Тем не менее, функция контроллера для editor (если определить один) будет работать до функции связи для scroll:

app.directive('scroll', ['$document','$parse', function ($document,$parse) { 
return { 
    restrict: 'E', 
    replace: true, 
    transclude: true, 
    scope:false, 
    template: 
     '<div class="scroll">' + 
      '<div class="content" data-ng-transclude>' + 
      '</div>' + 
     '</div>', 
    link: function (scope, element, attr) { 
     // some code here.... 
     console.log('link_editor=',scope.link_editor); // value is "undefined" 
     console.log('ctrl_editor=',scope.ctrl_editor); // value is "true" 
    } 
}; 
}]); 
app.directive('editor', ['$document', function ($document){ 
return { 
    restrict: 'EA', 
    replace: true, 
    transclude: false, 
    scope:true, 
    template: 
     '<div>' + 
      'stuff <scroll>content to scroll</scroll> more stuff' + 
     '</div>', 
    link: function (scope, element, attrs) { 
     scope.link_editor = true; 
    }, 
    controller: function($scope) { 
     $scope.ctrl_editor = true; 
    } 
}; 
}]); 
+0

Спасибо!Похоже, это может быть лучшим решением, чем обходной путь, который я сделал (то есть, если определенное свойство '', которое мне нужно, не определено во время ' -> link' I '$ watch' для свойства' 'Мне нужно, а затем запустить мой код. Я попробую сначала подумать завтра утром, это может упростить код, хотя обходной путь, вероятно, останется, поскольку я не могу полагаться на того, кто использует '' для реализации контроллера. – motig88

+0

Отлично, отлично работает и заставляет меня чувствовать себя идиотом ... – motig88

+0

@Mark Rajcok, простите полу-бок q: зачем редактор.link() запускается после scroll.link(). AJS docs подразумевают, что родительские узлы $ скомпилированы и $ связаны перед детьми, я думал, и здесь у нас есть , так что бы заказ не был: 1) editor.compile(), 2) e.controller(), 3) e.link(), 4) scroll.compile(), 5) scroll.controller; 6) scroll.link()? В этом случае влияют ли заявки на трансляцию или область видимости? – Nikita

Смежные вопросы