Ответ 1
Чтобы получить более подробные ответы, мы можем/должны соблюдать исходный код и проверить документацию . Позвольте мне попытаться объяснить все три вопроса (а также привести из кода и документа).
1. Когда создаются экземпляры контроллеров?
Здесь мы можем наблюдать код директивы ui-view
:
[$ViewDirective.$inject = \['$state', '$injector', '$uiViewScroll', '$interpolate'\];][1]
Контроллеры связаны с видами. Те views
, которые определены внутри .state()
как объект views
:
.state('...', {
// The view definition
views : {
'' : {
template: ...
controller: ...
resolve: ..
}
},
resolve: ...
}
Итак, всякий раз, когда view (the ui-view
) заполняется настройками, определенными внутри представления состояния, он действует почти как стандартная , но расширенная директива.
1) Шаблон найден,
2) Решения разрешены
...
x) Создан контроллер...
Просмотр целей (директивы ui-view
) могут использовать имена и могут быть заполнены разными состояниями в иерархии.
Это может означать, что внутри одного представления может быть содержимое (например, title), определяемое parent, а также замененное на дочерний strong >
// parent
.state('parent', {
views : {
'' : {...} // the main parent view, with ui-view="title"
'[email protected]' : { ...} // here we go and fill parent ui-view="title"
},
...
}
// child
.state('parent.child', {
views : {
'title' : { ...} // here we change the parent target ui-view="title"
},
...
}
Вышеуказанное определение состояния будет (всякий раз, когда мы переходим из этих двух состояний):
-
$state.go('parent')
- представление (шаблон, контроллер...), определенное в'[email protected]' : { ...}
, будет введено в целевойui-view="title"
и создаваться как описано выше -
$state.go('parent.child')
- почти то же самое, только представление будет взято из состояния child/view defintion'title' : { ...}
. Это заменит содержимоеui-view="title"
и будет создано таким образом, как описано выше.
Это будет происходить каждый раз, когда мы переходим от родителя к дочернему и от дочернего к родительскому.
2. Под вложенными маршрутами все представления совместно используют один контроллер и область видимости?
Простой ответ НЕТ, существует общий не общий доступ.
Фактически, каждый контроллер имеет собственную область, созданную из области представления родительского представления. Во-первых, документация:
Что наследуют дочерние государства из родительских состояний?
...
Наследование наследования по только иерархии просмотров
Имейте в виду, что свойства области только наследуют цепочку состояний, если представления ваших состояний вложены. Наследование свойств области не имеет ничего общего с вложением ваших состояний и всего, что связано с вложением ваших представлений (шаблонов).
Вполне возможно, что у вас есть вложенные состояния, шаблоны которых заполняют u-views в разных не-вложенных местах на вашем сайте. В этом случае вы не можете ожидать доступа к переменным области представлений родительского состояния в представлениях дочерних состояний.
Итак, всякий раз, когда есть наш controller
(ну представление с шаблоном, контроллер...), введенный в родительскую цель ui-view="..."
, он получает наследуемую область:
newScope = scope.$new();
Это в двух словах означает, что объекты JS (например, scope.Model = {}
) могут совместно использоваться дочерними и родительскими.
$scope.Model.id = 1; // will refer to the same id in both parent & child
Однако, основные типы Javascript не передаются по ссылке, поэтому их значения автоматически не синхронизируются между областями:
// set in parent
$scope.id = 1;
// in child after inherted still === 1
$scope.id = 2; // now 2 for a child, different value in parent - still === 1
Здесь стоит прочитать больше о прототипическом наследовании:
Каковы нюансы объема прототипа/прототипного наследования в AngularJS?
3. Что происходит, когда я переключаю состояния и возвращаюсь в состояние - создается ли еще один контроллер?
Это зависит.
Если родительский под просмотр (помните ui-view="title"
выше) заменяется дочерним видом, а затем он заново создается (переход от дочернего к родительскому) - такой контроллер будет повторно инициализирован (обсуждается выше).
Но когда мы говорим о основном родительском представлении (обычно без имени), который представляет родительский (например, неназванное представление ниже с контроллером ParentMainCtrl)
.state('parent', {
views : {
'' : { // // the main parent view
controller: 'ParentMainCtrl',
}
'[email protected]'
'[email protected]'
},
Тогда мы можем быть уверены, что такой контроллер НЕ повторно создан. Он живет во время жизни всех его детей, плюс родительский (не выбрано дочернее состояние).
Чтобы повторно загрузить этот просмотр/контроллер, мы должны использовать опцию reload
$state.go(to, params, options)
... Параметры Опция объекта. Возможные варианты:
- ...
- перезагрузить -
{boolean=false}
. Если значение true приведет к переходу, даже если состояние или параметры не изменились, то есть перезагрузка того же состояния. Он отличается от reloadOnSearch, потому что вы будете использовать его, когда хотите принудительно перезагрузить, когда все будет одинаково, включая параметры поиска.
Надеюсь, что это поможет. Для получения дополнительной информации ознакомьтесь с этими ресурсами:
- Вложенные состояния и вложенные представления
- Несколько именованных видов
- Ссылка на API
- State.js пример приложения - Я бы сказал, что наиболее документированный фрагмент кода никогда