Skip to content
This repository was archived by the owner on Apr 12, 2024. It is now read-only.

docs(guide/Directives): add info about scope types #12500

Closed
wants to merge 1 commit into from
Closed
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
53 changes: 52 additions & 1 deletion docs/content/guide/directive.ngdoc
Original file line number Diff line number Diff line change
Expand Up @@ -448,7 +448,58 @@ This is clearly not a great solution.

What we want to be able to do is separate the scope inside a directive from the scope
outside, and then map the outer scope to a directive's inner scope. We can do this by creating what
we call an **isolate scope**. To do this, we can use a directive's `scope` option:
we call an **isolate scope**.

To understand this concept we must first explore the directive's **scope** option:

* #### `scope`
* **If set to `true`,** then a new scope will be created for this directive. If multiple directives on the
* same element request a new scope, only one new scope is created. The new scope rule does not
* apply for the root of the template since the root of the template always gets a new scope.
*
* **If set to `{}` (object hash),** then a new "isolate" scope is created. The 'isolate' scope differs from
* normal scope in that it does not prototypically inherit from the parent scope. This is useful
* when creating reusable components, which should not accidentally read or modify data in the
* parent scope.
*
* The 'isolate' scope takes an object hash which defines a set of local scope properties
* derived from the parent scope. These local properties are useful for aliasing values for
* templates. Locals definition is a hash of local scope property to its source:
*
* * `@` or `@attr` - bind a local scope property to the value of DOM attribute. The result is
* always a string since DOM attributes are strings. If no `attr` name is specified then the
* attribute name is assumed to be the same as the local name.
* Given `<widget my-attr="hello {{name}}">` and widget definition
* of `scope: { localName:'@myAttr' }`, then widget scope property `localName` will reflect
* the interpolated value of `hello {{name}}`. As the `name` attribute changes so will the
* `localName` property on the widget scope. The `name` is read from the parent scope (not
* component scope).
*
* * `=` or `=attr` - set up bi-directional binding between a local scope property and the
* parent scope property of name defined via the value of the `attr` attribute. If no `attr`
* name is specified then the attribute name is assumed to be the same as the local name.
* Given `<widget my-attr="parentModel">` and widget definition of
* `scope: { localModel:'=myAttr' }`, then widget scope property `localModel` will reflect the
* value of `parentModel` on the parent scope. Any changes to `parentModel` will be reflected
* in `localModel` and any changes in `localModel` will reflect in `parentModel`. If the parent
* scope property doesn't exist, it will throw a NON_ASSIGNABLE_MODEL_EXPRESSION exception. You
* can avoid this behavior using `=?` or `=?attr` in order to flag the property as optional. If
* you want to shallow watch for changes (i.e. $watchCollection instead of $watch) you can use
* `=*` or `=*attr` (`=*?` or `=*?attr` if the property is optional).
*
* * `&` or `&attr` - provides a way to execute an expression in the context of the parent scope.
* If no `attr` name is specified then the attribute name is assumed to be the same as the
* local name. Given `<widget my-attr="count = count + value">` and widget definition of
* `scope: { localFn:'&myAttr' }`, then isolate scope property `localFn` will point to
* a function wrapper for the `count = count + value` expression. Often it's desirable to
* pass data from the isolated scope via an expression to the parent scope, this can be
* done by passing a map of local variable names and values into the expression wrapper fn.
* For example, if the expression is `increment(amount)` then we can specify the amount value
* by calling the `localFn` as `localFn({amount: 22})`.
*
*

Applying this back to our example, we can use a directive's `scope` option:

<example module="docsIsolateScopeDirective">
<file name="script.js">
Expand Down