为方法加上括号
This commit is contained in:
parent
f5c85b3e82
commit
26ba602922
|
@ -126,7 +126,7 @@ figure.image-display
|
|||
|
||||
Detect and act upon changes to input property values with the `ngOnChanges()` method of the `OnChanges` lifecycle hook interface.
|
||||
|
||||
使用`OnChanges`生命周期钩子接口的`ngOnChanges`方法来监测输入属性值的变化并做出回应。
|
||||
使用`OnChanges`生命周期钩子接口的`ngOnChanges()`方法来监测输入属性值的变化并做出回应。
|
||||
|
||||
.l-sub-section
|
||||
:marked
|
||||
|
|
|
@ -706,7 +706,7 @@ a#committing-changes
|
|||
|
||||
The `onSubmit()` method simply replaces the `hero` object with the combined values of the form:
|
||||
|
||||
`onSubmit`方法直接使用表单的值得合集来替换`hero`对象:
|
||||
`onSubmit()`方法直接使用表单的值得合集来替换`hero`对象:
|
||||
+makeExample('cb-form-validation/ts/src/app/reactive/hero-form-reactive.component.ts','on-submit')(format='.')
|
||||
.l-sub-section
|
||||
:marked
|
||||
|
@ -717,7 +717,7 @@ a#committing-changes
|
|||
:marked
|
||||
The `addHero()` method discards pending changes and creates a brand new `hero` model object.
|
||||
|
||||
`addHero`方法放弃未处理的变化,并创建一个崭新的`hero`模型对象。
|
||||
`addHero()`方法放弃未处理的变化,并创建一个崭新的`hero`模型对象。
|
||||
+makeExample('cb-form-validation/ts/src/app/reactive/hero-form-reactive.component.ts','add-hero')(format='.')
|
||||
:marked
|
||||
Then it calls `buildForm()` again which replaces the previous `heroForm` control model with a new one.
|
||||
|
|
|
@ -759,7 +759,7 @@ a#create-translation-providers
|
|||
1. The `getTranslationsWithSystemJs()` method reads the translation and returns the contents as a string.
|
||||
Notice that it appends `!text` to the filename, telling SystemJS to use the [text plugin](#text-plugin).
|
||||
|
||||
`getTranslationsWithSystemJs`方法读取翻译并以字符串的形式返回其内容。
|
||||
`getTranslationsWithSystemJs()`方法读取翻译并以字符串的形式返回其内容。
|
||||
注意它在文件名上附加`!text`,告诉SystemJS使用[文本插件](#text-plugin)。
|
||||
|
||||
1. The callback composes a providers array with the three translation providers.
|
||||
|
@ -779,7 +779,7 @@ a#bootstrap-the-app
|
|||
The Angular `bootstrapModule()` method has a second _options_ parameter
|
||||
that can influence the behavior of the compiler.
|
||||
|
||||
Angular的`bootstrapModule`方法接受**可选的**第二参数,它可以影响编译器的行为。
|
||||
Angular的`bootstrapModule()`方法接受**可选的**第二参数,它可以影响编译器的行为。
|
||||
|
||||
You'll create an _options_ object with the translation providers from `getTranslationProviders()`
|
||||
and pass it to `bootstrapModule`.
|
||||
|
|
|
@ -271,7 +271,7 @@ a#component
|
|||
the root of filenames (such as `hero-list.component.ts`) are often
|
||||
spelled in dash-case.
|
||||
|
||||
[指令](#directive)的选择器(例如`my-app`)<span if-docs="ts">和文件名(例如`hero-list.component.ts`)</span>通常是用中线命名法来命名。
|
||||
[指令](#directive)的选择器(例如`my-app`)和文件名(例如`hero-list.component.ts`)通常是用中线命名法来命名。
|
||||
|
||||
:marked
|
||||
## Data binding
|
||||
|
@ -301,7 +301,7 @@ a#component
|
|||
|
||||
Read about the following forms of binding in the [Template Syntax](./template-syntax.html) page:
|
||||
|
||||
更多的绑定形式,见[模板语法](!{docsLatest}/guide/template-syntax.html#data-binding):
|
||||
更多的绑定形式,见[模板语法](./template-syntax.html#data-binding):
|
||||
|
||||
* [Interpolation](./template-syntax.html#interpolation)
|
||||
|
||||
|
@ -619,12 +619,12 @@ a#H
|
|||
Data values flow *into* this property from the data source identified
|
||||
in the template expression to the right of the equal sign.
|
||||
|
||||
输入属性是一个指令属性,可以作为[属性绑定 (property binding)](!{docsLatest}/guide/template-syntax.html#property-binding)的目标。
|
||||
输入属性是一个指令属性,可以作为[属性绑定 (property binding)](./template-syntax.html#property-binding)的目标。
|
||||
数据值会从模板表达式等号右侧的数据源流入这个属性。
|
||||
|
||||
See the [Input and output properties](./template-syntax.html#inputs-outputs) section of the [Template Syntax](./template-syntax.html) page.
|
||||
|
||||
见[模板语法](!{docsLatest}/guide/template-syntax.html)中的[输入与输出属性](!{docsLatest}/guide/template-syntax.html#inputs-outputs)。
|
||||
见[模板语法](./template-syntax.html)中的[输入与输出属性](./template-syntax.html#inputs-outputs)。
|
||||
|
||||
:marked
|
||||
## Interpolation
|
||||
|
@ -649,7 +649,7 @@ a#H
|
|||
Read more about [interpolation](./template-syntax.html#interpolation) in the
|
||||
[Template Syntax](./template-syntax.html) page.
|
||||
|
||||
更多信息,见[模板语法](!{docsLatest}/guide/template-syntax.html)中的[插值表达式](!{docsLatest}/guide/template-syntax.html#interpolation)。
|
||||
更多信息,见[模板语法](./template-syntax.html)中的[插值表达式](./template-syntax.html#interpolation)。
|
||||
|
||||
.l-main-section#J
|
||||
|
||||
|
@ -760,7 +760,7 @@ a#jit
|
|||
* [Angular modules](#angular-module).
|
||||
For details and examples, see the [Angular Modules](./ngmodule.html) page.
|
||||
|
||||
[Angular 模块](#angular-module),见[Angular 模块](!{docsLatest}/guide/ngmodule.html)。
|
||||
[Angular 模块](#angular-module),见[Angular 模块](./ngmodule.html)。
|
||||
|
||||
* ES2015 modules, as described in this section.
|
||||
|
||||
|
@ -899,7 +899,7 @@ a#N
|
|||
You can also write your own custom pipes.
|
||||
Read more in the page on [pipes](./pipes.html).
|
||||
|
||||
更多信息,见[管道](!{docsLatest}/guide/pipes.html)。
|
||||
更多信息,见[管道](./pipes.html)。
|
||||
|
||||
:marked
|
||||
## Provider
|
||||
|
@ -973,7 +973,7 @@ a#Q
|
|||
The Angular component router is a richly featured mechanism for configuring and managing the entire view navigation process, including the creation and destruction
|
||||
of views.
|
||||
|
||||
Angular 的[组件路由器 (component router)](!{docsLatest}/guide/router.html)是一个特性丰富的机制,可以配置和管理整个导航过程,包括建立和销毁视图。
|
||||
Angular 的组件路由器是一个特性丰富的机制,可以配置和管理整个导航过程,包括建立和销毁视图。
|
||||
|
||||
In most cases, components become attached to a router by means
|
||||
of a `RouterConfig` that defines routes to views.
|
||||
|
@ -992,7 +992,7 @@ a#Q
|
|||
|
||||
For more information, see the [Routing & Navigation](./router.html) page.
|
||||
|
||||
更多信息,见[路由与导航](!{docsLatest}/guide/router.html)。
|
||||
更多信息,见[路由与导航](./router.html)。
|
||||
|
||||
:marked
|
||||
## Router module
|
||||
|
@ -1007,7 +1007,7 @@ a#Q
|
|||
|
||||
For more information, see the [Routing & Navigation](./router.html) page.
|
||||
|
||||
更多信息,见[路由与导航](!{docsLatest}/guide/router.html)。
|
||||
更多信息,见[路由与导航](./router.html)。
|
||||
|
||||
:marked
|
||||
## Routing component
|
||||
|
@ -1022,7 +1022,7 @@ a#Q
|
|||
|
||||
For more information, see the [Routing & Navigation](./router.html) page.
|
||||
|
||||
更多信息,见[路由与导航](!{docsLatest}/guide/router.html)。
|
||||
更多信息,见[路由与导航](./router.html)。
|
||||
|
||||
.l-main-section#S
|
||||
|
||||
|
@ -1116,7 +1116,7 @@ a#structural-directives
|
|||
|
||||
Read more in the [Structural Directives](./structural-directives.html) page.
|
||||
|
||||
更多信息,见[结构型指令](!{docsLatest}/guide/structural-directives.html)。
|
||||
更多信息,见[结构型指令](./structural-directives.html)。
|
||||
|
||||
// #enddocregion n-s-2
|
||||
|
||||
|
@ -1175,7 +1175,7 @@ a#structural-directives
|
|||
Read about how to build template-driven forms
|
||||
in the [Forms](./forms.html) page.
|
||||
|
||||
更多信息,见[表单](!{docsLatest}/guide/forms.html)。
|
||||
更多信息,见[表单](./forms.html)。
|
||||
|
||||
:marked
|
||||
## Template expression
|
||||
|
@ -1206,7 +1206,9 @@ a#structural-directives
|
|||
The process of transforming code written in one form of JavaScript
|
||||
(such as TypeScript) into another form of JavaScript (such as [ES5](#es5)).
|
||||
|
||||
把一种形式的 JavaScript(例如 TypeScript)转换成另一种形式的 JavaScript(例如 [ES5](#es5))的过程。:marked
|
||||
把一种形式的 JavaScript(例如 TypeScript)转换成另一种形式的 JavaScript(例如 [ES5](#es5))的过程。
|
||||
|
||||
:marked
|
||||
## TypeScript
|
||||
|
||||
.l-sub-section
|
||||
|
|
|
@ -726,7 +726,7 @@ a#service-needs-service
|
|||
You call that property within the `getHeroes()` method when anyone asks for heroes.
|
||||
|
||||
现在,这个构造函数要求注入一个`Logger`类的实例,并把它存到名为`logger`的私有属性中。
|
||||
当别人请求英雄数据时,在`getHeroes`方法中调用这个属性的方法。
|
||||
当别人请求英雄数据时,在`getHeroes()`方法中调用这个属性的方法。
|
||||
|
||||
a#injectable
|
||||
:marked
|
||||
|
@ -1415,7 +1415,7 @@ a#injection-token
|
|||
You can call `get()` with a second parameter, which is the value to return if the service
|
||||
is not found. Angular can't find the service if it's not registered with this or any ancestor injector.
|
||||
|
||||
`get`方法如果不能解析所请求的服务,会抛出异常。
|
||||
`get()`方法如果不能解析所请求的服务,会抛出异常。
|
||||
调用`get`时,还可以使用第二个参数,一旦获取的服务 (`ROUS`) 没有在当前或任何祖先注入器中注册过,
|
||||
就把它作为返回值。
|
||||
.l-sub-section
|
||||
|
|
|
@ -107,7 +107,7 @@ figure.image-display
|
|||
All requests bubble up to the root <code>NgModule</code> injector that you configured with the `bootstrapModule` method.
|
||||
|
||||
如果我们只在顶级(通常是根模块`AppModule`),这三个注入器看起来将是“平面”的。
|
||||
所有的申请都会冒泡到根<span if-docs="ts"><code>NgModule</code></span>进行处理,也就是我们在`!{_bootstrapModule}`方法中配置的那个。
|
||||
所有的申请都会冒泡到根<code>NgModule</code>进行处理,也就是我们在`bootstrapModule`方法中配置的那个。
|
||||
|
||||
.l-main-section
|
||||
:marked
|
||||
|
|
|
@ -49,7 +49,7 @@ table(width="100%")
|
|||
A first taste of Angular<span if-docs="ts"> with zero installation.
|
||||
Run "Hello World" in an online code editor and start playing with live code</span>.
|
||||
|
||||
<span if-docs="ts">零配置第一次尝试 Angular </span><span if-docs="ts">在在线代码编辑器中运行 “Hello World”,并利用在线代码开始体验</span>。
|
||||
零配置第一次尝试 Angular 在在线代码编辑器中运行 “Hello World”,并利用在线代码开始体验。
|
||||
|
||||
tr(style=top)
|
||||
td
|
||||
|
|
|
@ -376,8 +376,9 @@ table(width="100%")
|
|||
Implements an `ngDoCheck()` method with custom change detection.
|
||||
See how often Angular calls this hook and watch it post changes to a log.
|
||||
|
||||
实现了一个`ngDoCheck`方法,通过它可以自定义变更检测逻辑。
|
||||
实现了一个`ngDoCheck()`方法,通过它可以自定义变更检测逻辑。
|
||||
这里将会看到:Angular会用什么频度调用这个钩子,监视它的变化,并把这些变化输出成一条日志。
|
||||
|
||||
tr(style='vertical-align:top')
|
||||
td <a href="#afterview">AfterView</a>
|
||||
td
|
||||
|
@ -548,11 +549,11 @@ figure.image-display
|
|||
|
||||
*Reset*按钮清除了这个`heroes`列表。
|
||||
Angular从DOM中移除了所有英雄的div,并且同时销毁了附加在这些div上的侦探指令。
|
||||
侦探的`ngOnDestroy`方法汇报了它自己的临终时刻。
|
||||
侦探的`ngOnDestroy()`方法汇报了它自己的临终时刻。
|
||||
|
||||
The `ngOnInit()` and `ngOnDestroy()` methods have more vital roles to play in real applications.
|
||||
|
||||
在真实的应用程序中,`ngOnInit`和`ngOnDestroy`方法扮演着更重要的角色。
|
||||
在真实的应用程序中,`ngOnInit()`和`ngOnDestroy()`方法扮演着更重要的角色。
|
||||
|
||||
a#oninit
|
||||
:marked
|
||||
|
@ -612,14 +613,14 @@ a#oninit
|
|||
Angular calls `ngOnChanges()` before `ngOnInit()` and many times after that.
|
||||
It only calls `ngOnInit()` once.
|
||||
|
||||
我们访问这些属性的第一次机会,实际上是`ngOnChanges`方法,Angular会在`ngOnInit`之前调用它。
|
||||
但是在那之后,Angular还会调用`ngOnChanges`很多次。而`ngOnInit`只会被调用一次。
|
||||
我们访问这些属性的第一次机会,实际上是`ngOnChanges()`方法,Angular会在`ngOnInit()`之前调用它。
|
||||
但是在那之后,Angular还会调用`ngOnChanges()`很多次。而`ngOnInit()`只会被调用一次。
|
||||
|
||||
:marked
|
||||
You can count on Angular to call the `ngOnInit()` method _soon_ after creating the component.
|
||||
That's where the heavy initialization logic belongs.
|
||||
|
||||
你可以信任Angular会在创建组件后立刻调用`ngOnInit`方法。
|
||||
你可以信任Angular会在创建组件后立刻调用`ngOnInit()`方法。
|
||||
这里是放置复杂初始化逻辑的好地方。
|
||||
|
||||
a#ondestroy
|
||||
|
@ -651,7 +652,7 @@ a#onchanges
|
|||
Angular calls its `ngOnChanges()` method whenever it detects changes to ***input properties*** of the component (or directive).
|
||||
|
||||
在这个例子中,我们监听了`OnChanges`钩子。
|
||||
一旦检测到该组件(或指令)的***输入属性***发生了变化,Angular就会调用它的`ngOnChanges`方法。
|
||||
一旦检测到该组件(或指令)的***输入属性***发生了变化,Angular就会调用它的`ngOnChanges()`方法。
|
||||
|
||||
This example monitors the `OnChanges` hook.
|
||||
|
||||
|
@ -663,7 +664,7 @@ a#onchanges
|
|||
[SimpleChange](../api/core/index/SimpleChange-class.html) object holding the current and previous property values.
|
||||
This hook iterates over the changed properties and logs them.
|
||||
|
||||
`ngOnChanges`方法获取了一个对象,它把每个发生变化的属性名都映射到了一个[SimpleChange](../api/core/index/SimpleChange-class.html)对象,
|
||||
`ngOnChanges()`方法获取了一个对象,它把每个发生变化的属性名都映射到了一个[SimpleChange](../api/core/index/SimpleChange-class.html)对象,
|
||||
该对象中有属性的当前值和前一个值。我们在这些发生了变化的属性上进行迭代,并记录它们。
|
||||
|
||||
The example component, `OnChangesComponent`, has two input properties: `hero` and `power`.
|
||||
|
@ -801,14 +802,14 @@ a#wait-a-tick
|
|||
|
||||
The `doSomething()` method updates the screen when the hero name exceeds 10 characters.
|
||||
|
||||
当英雄的名字超过10个字符时,`doSomething`方法就会更新屏幕。
|
||||
当英雄的名字超过10个字符时,`doSomething()`方法就会更新屏幕。
|
||||
|
||||
+makeExample('lifecycle-hooks/ts/src/app/after-view.component.ts', 'do-something', 'AfterViewComponent (doSomething)')(format=".")
|
||||
|
||||
:marked
|
||||
Why does the `doSomething()` method wait a tick before updating `comment`?
|
||||
|
||||
为什么在更新`comment`属性之前,`doSomething`方法要等上一拍(tick)?
|
||||
为什么在更新`comment`属性之前,`doSomething()`方法要等上一拍(tick)?
|
||||
|
||||
Angular's unidirectional data flow rule forbids updates to the view *after* it has been composed.
|
||||
Both of these hooks fire _after_ the component's view has been composed.
|
||||
|
@ -949,7 +950,7 @@ a#no-unidirectional-flow-worries
|
|||
This component's `doSomething()` method update's the component's data-bound `comment` property immediately.
|
||||
There's no [need to wait](#wait-a-tick).
|
||||
|
||||
该组件的`doSomething`方法立即更新了组件被绑定的`comment`属性。
|
||||
该组件的`doSomething()`方法立即更新了组件被绑定的`comment`属性。
|
||||
它[不用等](#wait-a-tick)下一回合。
|
||||
|
||||
Recall that Angular calls both *AfterContent* hooks before calling either of the *AfterView* hooks.
|
||||
|
|
|
@ -599,7 +599,7 @@ h3#async-pipe The impure #[i AsyncPipe]
|
|||
|
||||
我们确实得小心点。
|
||||
这个管道只有当所请求的URL发生变化时才会向服务器发起请求。它会缓存服务器的响应。
|
||||
代码如下,<span if-docs="ts">它使用[Angular http](server-communication.html)客户端来接收数据</span>
|
||||
代码如下,它使用[Angular http](server-communication.html)客户端来接收数据
|
||||
|
||||
+makeExample('src/app/fetch-json.pipe.ts')
|
||||
:marked
|
||||
|
|
|
@ -2764,10 +2764,6 @@ a#add-secondary-route
|
|||
|
||||
You are in effect saying, _when the user clicks this link, display the component associated with the `compose` route in the `popup` outlet_.
|
||||
|
||||
要使用`Router`进行相对导航,可以使用`ActivatedRoute`来告诉路由器我们正在*RouterState*中的什么地方,*RouterState*是激活路由组成的树。
|
||||
要做到这一点,我们可以为`router.navigate`方法中*链接参数数组*后的对象型参数指定**relativeTo**属性。
|
||||
只要把这个`relativeTo`属性设置为我们的`ActivatedRoute`,路由器就会把我们的导航信息和当前URL合并在一起。
|
||||
|
||||
.l-sub-section
|
||||
:marked
|
||||
This `outlets` object within an outer object was completely unnecessary
|
||||
|
@ -3369,7 +3365,7 @@ a#CanDeactivate
|
|||
wanted to use this guard for this component and needed to get
|
||||
the component's properties or confirm whether the router should allow navigation away from it.
|
||||
|
||||
另外,我们也可以为`CrisisDetailComponent`创建一个特定的`CanDeactivate`守卫。在需要访问外部信息时,`canDeactivate`方法为提供了组件、`ActivatedRoute`和`RouterStateSnapshot`的当前实例。如果只想为这个组件使用该守卫,并且需要使用该组件属性、或者需要路由器确认是否允许从该组件导航出去时,这个守卫就非常有用。
|
||||
另外,我们也可以为`CrisisDetailComponent`创建一个特定的`CanDeactivate`守卫。在需要访问外部信息时,`canDeactivate()`方法为提供了组件、`ActivatedRoute`和`RouterStateSnapshot`的当前实例。如果只想为这个组件使用该守卫,并且需要使用该组件属性、或者需要路由器确认是否允许从该组件导航出去时,这个守卫就非常有用。
|
||||
|
||||
+makeExcerpt('src/app/can-deactivate-guard.service.1.ts (component-specific)', '')
|
||||
|
||||
|
|
|
@ -442,7 +442,10 @@ code-example(language="typescript").
|
|||
|
||||
参见Dave Smith在<a href="https://www.youtube.com/watch?v=9inczw6qtpY" target="_blank" title="Cross Site Request Funkery Securing Your Angular Apps From Evil Doers">AngularConnect 2016关于XSRF的演讲</a>。
|
||||
|
||||
h3#xssi Cross-site script inclusion (XSSI)h3#xssi 跨站脚本包含(XSSI)
|
||||
h3#xssi Cross-site script inclusion (XSSI)
|
||||
|
||||
h3#xssi 跨站脚本包含(XSSI)
|
||||
|
||||
:marked
|
||||
Cross-site script inclusion, also known as JSON vulnerability, can allow an attacker's website to
|
||||
read data from a JSON API. The attack works on older browsers by overriding native JavaScript
|
||||
|
|
|
@ -432,7 +432,7 @@ a#HeroService
|
|||
In fact, the `http.get` method returns an **Observable** of HTTP Responses (`Observable<Response>`) from the RxJS library
|
||||
and `map()` is one of the RxJS *operators*.
|
||||
|
||||
事实上,`http.get`方法返回了一个 HTTP Response 类型的**可观察对象** (`Observable<Response>`),这个对象来自 RxJS 库,而`map`是 RxJS 的*操作符*之一。
|
||||
事实上,`http.get`方法返回了一个 HTTP Response 类型的**可观察对象** (`Observable<Response>`),这个对象来自 RxJS 库,而`map()`是 RxJS 的*操作符*之一。
|
||||
|
||||
a#rxjs-library
|
||||
.l-main-section
|
||||
|
@ -474,7 +474,7 @@ a#rxjs-library
|
|||
The `getHeroes()` method needs the `map()` and `catch()` operators so it imports them like this.
|
||||
|
||||
每个代码文件都需要把它需要的操作符从RxJS库中导入,并添加进来。
|
||||
`getHeroes`方法需要一个`map`和一个`catch`操作符,那就像这样导入它:
|
||||
`getHeroes()`方法需要一个`map()`和一个`catch()`操作符,那就像这样导入它:
|
||||
|
||||
+makeExample('server-communication/ts/src/app/toh/hero.service.ts', 'rxjs-imports', 'src/app/app.component.ts (import rxjs)')(format=".")
|
||||
|
||||
|
@ -605,7 +605,7 @@ block error-handling
|
|||
The `handleError` method transforms the error into a developer-friendly message,
|
||||
logs it to the console, and returns the message in a new, failed Observable via `Observable.throw`.
|
||||
|
||||
`catch`操作符将错误对象传递给`http`的`handleError`方法。
|
||||
`catch()`操作符将错误对象传递给`http`的`handleError()`方法。
|
||||
服务处理器 (`handleError`) 把响应对象记录到控制台中,
|
||||
把错误转换成对用户友好的消息,并且通过`Observable.throw`来把这个消息放进一个新的、用于表示“失败”的可观察对象。
|
||||
|
||||
|
@ -710,7 +710,7 @@ a#headers
|
|||
|
||||
In the `return` statement, `options` is the *third* argument of the `post()` method, as shown above.
|
||||
|
||||
在`return`声明中,`options`是传给`post`方法的*第三个*参数,就像前面见过的那样。
|
||||
在`return`声明中,`options`是传给`post()`方法的*第三个*参数,就像前面见过的那样。
|
||||
|
||||
a#json-results
|
||||
:marked
|
||||
|
@ -799,7 +799,7 @@ h2#promises 倒退为承诺 (Promise)
|
|||
The only obvious difference is that you call `then()` on the returned Promise instead of `subscribe`.
|
||||
Both methods take the same functional arguments.
|
||||
|
||||
唯一一个比较明显的不同点是我们调用这个返回的承诺的`then`方法,而不再是`subscribe`。
|
||||
唯一一个比较明显的不同点是我们调用这个返回的承诺的`then()`方法,而不再是`subscribe`。
|
||||
我们给了这两个方法完全相同的调用参数。
|
||||
.l-sub-section
|
||||
:marked
|
||||
|
@ -809,14 +809,14 @@ h2#promises 倒退为承诺 (Promise)
|
|||
|
||||
The Promise-based `then()` returns another Promise. You can keep chaining more `then()` and `catch()` calls, getting a new promise each time.
|
||||
|
||||
基于承诺的`then`返回了另一个承诺。我们可以链式调用多个`then`和`catch`方法,每次都返回一个新的承诺。
|
||||
基于承诺的`then()`返回了另一个承诺。我们可以链式调用多个`then()`和`catch()`方法,每次都返回一个新的承诺。
|
||||
|
||||
The `subscribe()` method returns a `Subscription`. A `Subscription` is not another `Observable`.
|
||||
It's the end of the line for Observables. You can't call `map()` on it or call `subscribe()` again.
|
||||
The `Subscription` object has a different purpose, signified by its primary method, `unsubscribe`.
|
||||
|
||||
但`subscribe`方法返回一个`Subscription`对象。但`Subscription`不是另一个`Observable`。
|
||||
它是可观察对象的末端。我们不能在它上面调用`map`函数或再次调用`subscribe`函数。
|
||||
但`subscribe()`方法返回一个`Subscription`对象。但`Subscription`不是另一个`Observable`。
|
||||
它是可观察对象的末端。我们不能在它上面调用`map()`函数或再次调用`subscribe()`函数。
|
||||
`Subscription`对象的设计目的是不同的,这从它的主方法`unsubscribe`就能看出来。
|
||||
|
||||
To understand the implications and consequences of subscriptions, watch [Ben Lesh's talk on Observables](https://www.youtube.com/watch?v=3LKMwkuK0ZE) or his video course on [egghead.io](https://egghead.io/lessons/rxjs-rxjs-observables-vs-promises).
|
||||
|
@ -1112,7 +1112,7 @@ block wikipedia-jsonp+
|
|||
The `search()` method adds each new search box value to that stream via the subject's `next()` method.
|
||||
|
||||
组件创建`searchTermStream`为`string`类型的`Subject`。
|
||||
`search`方法通过`subject`的`next`方法,将每个新搜索框的值添加到数据流中。
|
||||
`search()`方法通过`subject`的`next()`方法,将每个新搜索框的值添加到数据流中。
|
||||
|
||||
+makeExample('server-communication/ts/src/app/wiki/wiki-smart.component.ts', 'subject')(format='.')
|
||||
|
||||
|
@ -1316,7 +1316,7 @@ block redirect-to-web-api
|
|||
The `forRoot()` method name is a strong reminder that you should only call the `InMemoryWebApiModule` _once_,
|
||||
while setting the metadata for the root `AppModule`. Don't call it again.
|
||||
|
||||
`forRoot`方法的名字告诉我们,应该只在设置根模块`AppModule`时调用`InMemoryWebApiModule`*一次*。不要再次调用它。
|
||||
`forRoot()`方法的名字告诉我们,应该只在设置根模块`AppModule`时调用`InMemoryWebApiModule`*一次*。不要再次调用它。
|
||||
|
||||
:marked
|
||||
Here is the final, revised version of <code>src/app/app.module.ts</code>, demonstrating these steps.
|
||||
|
|
|
@ -154,6 +154,7 @@ a#html
|
|||
我们首先看看数据绑定的第一种形式 —— 插值表达式,它展示了模板的 HTML 可以有多丰富。
|
||||
|
||||
a(href="#toc") back to top
|
||||
a(href="#toc") 回到顶部
|
||||
|
||||
.l-hr
|
||||
a#interpolation
|
||||
|
@ -220,6 +221,7 @@ a#interpolation
|
|||
讲解属性绑定之前,先深入了解一下模板表达式和模板语句。
|
||||
|
||||
a(href="#toc") back to top
|
||||
a(href="#toc") 回到顶部
|
||||
|
||||
.l-hr
|
||||
a#template-expressions
|
||||
|
@ -325,6 +327,7 @@ a#expression-context
|
|||
members of the expression context.
|
||||
|
||||
a(href="#toc") back to top
|
||||
a(href="#toc") 回到顶部
|
||||
|
||||
a#no-side-effectsa#expression-guidelines
|
||||
:marked
|
||||
|
@ -429,7 +432,6 @@ a#no-side-effectsa#expression-guidelines
|
|||
如果幂等的表达式返回一个对象(包括`Date`或`Array`),连续调用它两次,也应该返回同一个对象的*引用*。
|
||||
|
||||
a(href="#toc") back to top
|
||||
|
||||
a(href="#toc") 回到顶部
|
||||
|
||||
.l-hr
|
||||
|
@ -554,6 +556,7 @@ a#template-statements
|
|||
除插值表达式外,还有各种各样的数据绑定语法,是学习它们是时候了。
|
||||
|
||||
a(href="#toc") back to top
|
||||
a(href="#toc") 回到顶部
|
||||
|
||||
.l-hr
|
||||
a#binding-syntax
|
||||
|
@ -925,7 +928,6 @@ table(width="100%")
|
|||
放开眼界,我们来看看每种绑定类型的具体情况。
|
||||
|
||||
a(href="#toc") back to top
|
||||
|
||||
a(href="#toc") 回到顶部
|
||||
|
||||
.l-hr
|
||||
|
@ -1643,6 +1645,7 @@ a#custom-event
|
|||
+makeExample('template-syntax/ts/src/app/app.component.html', 'event-binding-propagation')(format=".")
|
||||
|
||||
a(href="#toc") back to top
|
||||
a(href="#toc") 回到顶部
|
||||
|
||||
.l-hr
|
||||
a#two-way
|
||||
|
@ -1741,6 +1744,7 @@ a#two-way
|
|||
幸运的是,Angular 以 [_NgModel_](#ngModel) 指令为桥梁,允许在表单元素上使用双向数据绑定。
|
||||
|
||||
a(href="#toc") back to top
|
||||
a(href="#toc") 回到顶部
|
||||
|
||||
.l-hr
|
||||
a#directives
|
||||
|
@ -1870,6 +1874,7 @@ a#ngClass
|
|||
你既可以在初始化时调用`setCurrentClassess()`,也可以在所依赖的属性变化时调用。
|
||||
|
||||
a(href="#toc") back to top
|
||||
a(href="#toc") 回到顶部
|
||||
|
||||
.l-hr
|
||||
a#ngStyle
|
||||
|
@ -1916,6 +1921,7 @@ a#ngStyle
|
|||
你既可以在初始化时调用`setCurrentStyles()`,也可以在所依赖的属性变化时调用。
|
||||
|
||||
a(href="#toc") back to top
|
||||
a(href="#toc") 回到顶部
|
||||
|
||||
.l-hr
|
||||
a#ngModel
|
||||
|
@ -2007,6 +2013,7 @@ figure.image-display
|
|||
|
||||
p
|
||||
a(href="#toc") back to top
|
||||
a(href="#toc") 回到顶部
|
||||
|
||||
.l-hr
|
||||
a#structural-directives
|
||||
|
@ -2291,6 +2298,7 @@ figure.image-display
|
|||
|
||||
p
|
||||
a(href="#toc") back to top
|
||||
a(href="#toc") 回到顶部
|
||||
|
||||
.l-hr
|
||||
a#ngSwitch
|
||||
|
@ -2336,6 +2344,7 @@ figure.image-display
|
|||
+makeExample('template-syntax/ts/src/app/app.component.html', 'NgSwitch-div')(format=".")
|
||||
|
||||
a(href="#toc") back to top
|
||||
a(href="#toc") 回到顶部
|
||||
|
||||
.l-hr
|
||||
a#template-reference-variable
|
||||
|
@ -2405,6 +2414,7 @@ a#ref-var
|
|||
+makeExample('template-syntax/ts/src/app/app.component.html', 'ref-fax')(format=".")
|
||||
|
||||
a(href="#toc") back to top
|
||||
a(href="#toc") 回到顶部
|
||||
|
||||
.l-hr
|
||||
a#inputs-outputs
|
||||
|
@ -2604,6 +2614,7 @@ h3#aliasing-io
|
|||
+makeExample('template-syntax/ts/src/app/click.directive.ts', 'output-myClick2')(format=".")
|
||||
|
||||
a(href="#toc") back to top
|
||||
a(href="#toc") 回到顶部
|
||||
|
||||
.l-hr
|
||||
a#expression-operators
|
||||
|
@ -2674,6 +2685,7 @@ code-example(language="json").
|
|||
"rate": 325 }
|
||||
|
||||
a(href="#toc") back to top
|
||||
a(href="#toc") 回到顶部
|
||||
|
||||
.l-hr
|
||||
a#safe-navigation-operator
|
||||
|
@ -2785,6 +2797,7 @@ code-example(language="html").
|
|||
在像`a?.b?.c?.d`这样的长属性路径中,它工作得很完美。
|
||||
|
||||
a(href="#toc") back to top
|
||||
a(href="#toc") 回到顶部
|
||||
|
||||
.l-hr
|
||||
:marked
|
||||
|
|
|
@ -591,8 +591,10 @@ a#component-fixture
|
|||
|
||||
The `title` property value is interpolated into the DOM within `<h1>` tags.
|
||||
Use the fixture's `DebugElement` to `query` for the `<h1>` element by CSS selector.
|
||||
|
||||
`title`属性被插值到DOM的`<h1>`标签中。
|
||||
用CSS选择器从fixture的`DebugElement`中`query``<h1>`元素。
|
||||
|
||||
The **`query`** method takes a predicate function and searches the fixture's entire DOM tree for the
|
||||
_first_ element that satisfies the predicate.
|
||||
The result is a _different_ `DebugElement`, one associated with the matching DOM element.
|
||||
|
@ -601,7 +603,9 @@ a#component-fixture
|
|||
.l-sub-section
|
||||
:marked
|
||||
The `queryAll` method returns an array of _all_ `DebugElements` that satisfy the predicate.
|
||||
|
||||
`queryAll`方法返回一列数组,包含所有`DebugElement`中满足predicate的元素。
|
||||
|
||||
A _predicate_ is a function that returns a boolean.
|
||||
A query predicate receives a `DebugElement` and returns `true` if the element meets the selection criteria.
|
||||
**predicate**是返回布尔值的函数。
|
||||
|
@ -1000,9 +1004,11 @@ a#welcome-spec-setup
|
|||
The second parameter to the Jasmine `it` (e.g., `'expected name'`) is an optional addendum.
|
||||
If the expectation fails, Jasmine displays this addendum after the expectation failure message.
|
||||
In a spec with multiple expectations, it can help clarify what went wrong and which expectation failed .
|
||||
|
||||
Jasmine的`it`方法的第二个参数(比如`'expected name'`)是可选附加参数。
|
||||
如果这个期待失败了,Jasmine在期待失败信息后面显示这个附加参数。
|
||||
在拥有多个期待的spec中,它可以帮助澄清发生了什么错误,哪个期待失败了。
|
||||
|
||||
:marked
|
||||
The remaining tests confirm the logic of the component when the service returns different values.
|
||||
The second test validates the effect of changing the user name.
|
||||
|
@ -1144,6 +1150,7 @@ a#when-stable
|
|||
### _whenStable_
|
||||
|
||||
## **whenStable**
|
||||
|
||||
The test must wait for the `getQuote` promise to resolve in the next turn of the JavaScript engine.
|
||||
|
||||
测试程序必须等待`getQuote`在JavaScript引擎的下一回合中被解析。
|
||||
|
@ -1153,9 +1160,13 @@ a#when-stable
|
|||
probes only the component API surface.
|
||||
|
||||
本测试对`twainService.getQuote`返回的承诺没有直接的访问,因为它被埋没在`TwainComponent.ngOnInit`里,
|
||||
所以对于只测试组件API表面的测试来说,它是无法被访问的。Fortunately, the `getQuote` promise is accessible to the _async test zone_ ,
|
||||
所以对于只测试组件API表面的测试来说,它是无法被访问的。
|
||||
|
||||
Fortunately, the `getQuote` promise is accessible to the _async test zone_ ,
|
||||
which intercepts all promises issued within the _async_ method call _no matter where they occur_.
|
||||
|
||||
幸运的是,**异步测试区域**可以访问`getQuote`承诺,因为它拦截所有调用**异步**方法所发出的承诺,不管它们在哪儿。
|
||||
|
||||
The `ComponentFixture.whenStable` method returns its own promise, which resolves when the `getQuote` promise finishes.
|
||||
In fact, the _whenStable_ promise resolves when _all pending asynchronous activities within this test_ complete — the definition of "stable."
|
||||
|
||||
|
@ -1728,22 +1739,28 @@ a#routed-component-w-param
|
|||
`HeroDetailComponent` subscribes to `ActivatedRoute.params` changes in its `ngOnInit` method.
|
||||
|
||||
`HeroDetailComponent`在它的`ngOnInit`方法中监听`ActivatedRoute.params`的变化。
|
||||
|
||||
+makeExample('testing/ts/src/app/hero/hero-detail.component.ts', 'ng-on-init', 'src/app/hero/hero-detail.component.ts (ngOnInit)')(format='.')
|
||||
.l-sub-section
|
||||
:marked
|
||||
The expression after `route.params` chains an _Observable_ operator that _plucks_ the `id` from the `params`
|
||||
and then chains a `forEach` operator to subscribe to `id`-changing events.
|
||||
The `id` changes every time the user navigates to a different hero.
|
||||
|
||||
`route.params`之后的表达式链接了**可观察**操作符,它从`params`中提取`id`,然后链接`forEach`操作符来订阅`id`变化事件。
|
||||
每次`id`变化时,用户被导航到不同的英雄。
|
||||
|
||||
The `forEach` passes the new `id` value to the component's `getHero` method (not shown)
|
||||
which fetches a hero and sets the component's `hero` property.
|
||||
If the`id` parameter is missing, the `pluck` operator fails and the `catch` treats failure as a request to edit a new hero.
|
||||
|
||||
`forEach`将新的`id`值传递到组件的`getHero`方法(这里没有列出来),它获取英雄并将它赋值到组件的`hero`属性。
|
||||
如果`id`参数无效,`pluck`操作符就会失败,`catch`将失败当作创建新英雄来处理。
|
||||
|
||||
The [Router](router.html#route-parameters) guide covers `ActivatedRoute.params` in more detail.
|
||||
|
||||
[路由器](router.html#route-parameters)章更详尽的讲述了`ActivatedRoute.params`。
|
||||
|
||||
:marked
|
||||
A test can explore how the `HeroDetailComponent` responds to different `id` parameter values
|
||||
by manipulating the `ActivatedRoute` injected into the component's constructor.
|
||||
|
@ -1767,10 +1784,12 @@ a#stub-observable
|
|||
This is a cross-application, re-usable _test helper class_.
|
||||
Consider placing such helpers in a `testing` folder sibling to the `app` folder.
|
||||
This sample keeps `ActivatedRouteStub` in `testing/router-stubs.ts`:
|
||||
|
||||
`hero-detail.component.spec.ts`依赖`ActivatedRouteStub`来为每个测试程序设置`ActivatedRoute.params`值。
|
||||
它是跨应用、可复用的**测试辅助类**。
|
||||
我们建议将这样的辅助类放到`app`目录下的名为`testing`的目录。
|
||||
本例把`ActivatedRouteStub`放到`testing/router-stubs.ts`:
|
||||
|
||||
+makeExample('testing/ts/src/testing/router-stubs.ts', 'activated-route-stub', 'testing/router-stubs.ts (ActivatedRouteStub)')(format='.')
|
||||
:marked
|
||||
Notable features of this stub are:
|
||||
|
@ -1922,6 +1941,7 @@ figure.image-display
|
|||
A `createComponent` method creates a `page` objectand fills in the blanks once the `hero` arrives.
|
||||
|
||||
`createComponent`方法创建`page`,在`hero`到来时,自动填补空白。
|
||||
|
||||
+makeExample('testing/ts/src/app/hero/hero-detail.component.spec.ts', 'create-component', 'src/app/hero/hero-detail.component.spec.ts (createComponent)')(format='.')
|
||||
|
||||
:marked
|
||||
|
@ -2126,6 +2146,7 @@ a#override-component-method
|
|||
Focus on the `overrideComponent` method.
|
||||
|
||||
注意这个`overrideComponent`方法。
|
||||
|
||||
+makeExample('testing/ts/src/app/hero/hero-detail.component.spec.ts', 'override-component-method', 'src/app/hero/hero-detail.component.spec.ts (overrideComponent)')(format='.')
|
||||
:marked
|
||||
It takes two arguments: the component type to override (`HeroDetailComponent`) and an override metadata object.
|
||||
|
@ -2197,8 +2218,10 @@ a#more-overrides
|
|||
The `TestBed.overrideComponent` method can be called multiple times for the same or different components.
|
||||
The `TestBed` offers similar `overrideDirective`, `overrideModule`, and `overridePipe` methods
|
||||
for digging into and replacing parts of these other classes.
|
||||
|
||||
`TestBed.overrideComponent`方法可以在相同或不同的组件中被反复调用。
|
||||
`TestBed`还提供了类似的`overrideDirective`、`overrideModule`和`overridePipe`方法,用来深入并重载这些其它类的部件。
|
||||
|
||||
Explore the options and combinations on your own.
|
||||
|
||||
自己探索这些选项和组合。
|
||||
|
@ -3087,6 +3110,7 @@ table
|
|||
(`null` in this example):
|
||||
|
||||
`TestBed.get`方法接受一个可选的第二参数,它是在Angular找不到所需提供商时返回的对象。(在本例中为`null`):
|
||||
|
||||
+makeExample('testing/ts/src/app/bag/bag.spec.ts', 'testbed-get')(format=".")
|
||||
:marked
|
||||
After calling `get`, the `TestBed` configuration is frozen for the duration of the current spec.
|
||||
|
@ -3513,9 +3537,13 @@ a#query-predicate
|
|||
:marked
|
||||
Many custom application directives inject the `Renderer` and call one of its `set...` methods.
|
||||
|
||||
很多制定应用程序指令注入`Renderer`并调用它其中一个方法`set...`。The test environment substitutes the `DebugDomRender` for the runtime `Renderer`.
|
||||
很多制定应用程序指令注入`Renderer`并调用它其中一个方法`set...`。
|
||||
|
||||
The test environment substitutes the `DebugDomRender` for the runtime `Renderer`.
|
||||
The `DebugDomRender` updates additional dictionary properties of the `DebugElement`
|
||||
when something calls a `set...` method.运行时的`Renderer`在测试环境中的替代品为`DebugDomRender`。
|
||||
when something calls a `set...` method.
|
||||
|
||||
运行时的`Renderer`在测试环境中的替代品为`DebugDomRender`。
|
||||
在调用`set...`方法时,`DebugDomRender`更新`DebugElement`额外词典属性。
|
||||
|
||||
These dictionary properties are primarily of interest to authors of Angular DOM inspection tools
|
||||
|
|
|
@ -24,7 +24,7 @@ block qs-src-online-and-local
|
|||
Every component begins with an `@Component` [decorator](glossary.html#decorator '"decorator" explained')
|
||||
function that takes a _metadata_ object. The metadata object describes how the HTML template and component class work together.
|
||||
|
||||
每个组件都以`@Component`[装饰器](glossary.html#!{_decorator} '"!{_decorator}" explained')<span if-docs="ts">函数</span>开始,它<span if-docs="ts">接受一个_元数据_对象参数。该元素对象</span>描述了 HTML 模板和组件类是如何一起工作的。
|
||||
每个组件都以`@Component`[装饰器](glossary.html#!{_decorator} '"!{_decorator}" explained')函数开始,它接受一个_元数据_对象参数。该元素对象描述了 HTML 模板和组件类是如何一起工作的。
|
||||
|
||||
The `selector` property tells Angular to display the component inside a custom `<my-app>` tag in the `index.html`.
|
||||
|
||||
|
|
|
@ -203,9 +203,10 @@ code-example(language="sh" class="code-shell").
|
|||
* Create the file <code>src/app/app.component.ts</code>.
|
||||
|
||||
创建一个名叫<span ngio-ex>src/app/app.component.ts</span>的新文件。
|
||||
|
||||
* Define an exported `AppComponent` class.
|
||||
|
||||
定义一个<span if-docs="ts">导出的</span> `AppComponent`类。
|
||||
定义一个导出的 `AppComponent`类。
|
||||
|
||||
* Add an `@Component` decorator above the class with a `my-app` selector.
|
||||
|
||||
|
@ -642,7 +643,7 @@ a#configure-routes
|
|||
|
||||
In this dashboard you specify four heroes (2nd, 3rd, 4th, and 5th) with the `Array.slice` method.
|
||||
|
||||
在仪表盘中我们<span if-docs="ts">用`Array.slice`方法</span>提取了四个英雄(第2、3、4、5个)。
|
||||
在仪表盘中我们用`Array.slice`方法提取了四个英雄(第2、3、4、5个)。
|
||||
|
||||
Refresh the browser to see four hero names in the new dashboard.
|
||||
|
||||
|
@ -1305,7 +1306,7 @@ figure.image-display
|
|||
|
||||
在`!{_appDir}`目录下添加<span ngio-ex>hero-detail.component.css</span>文件,
|
||||
并且在`styleUrls`数组中引用它 —— 就像之前在`DashboardComponent`中做过的那样。
|
||||
同时删除`hero``@Input`装饰器属性<span if-docs="ts">和它的导入语句</span>。
|
||||
同时删除`hero``@Input`装饰器属性和它的导入语句。
|
||||
|
||||
Here's the content for the component CSS files.
|
||||
|
||||
|
|
|
@ -730,6 +730,8 @@ a#ngoninit
|
|||
Even with a 300ms pause between requests, you could have multiple HTTP requests in flight
|
||||
and they may not return in the order sent.
|
||||
|
||||
借助[switchMap操作符](http://www.learnrxjs.io/operators/transformation/switchmap.html)
|
||||
(正式名称是`flatMapLatest`)
|
||||
每次符合条件的按键事件都会触发一次对`http`方法的调用。即使在发送每个请求前都有 300 毫秒的延迟,
|
||||
我们仍然可能同时拥有多个在途的 HTTP 请求,并且它们返回的顺序未必就是发送时的顺序。
|
||||
|
||||
|
@ -737,7 +739,7 @@ a#ngoninit
|
|||
only the observable from the most recent `http` method call.
|
||||
Results from prior calls are canceled and discarded.
|
||||
|
||||
`switchMap`保留了原始的请求顺序,并且只返回最近一次 `http` 调用返回的可观察对象。
|
||||
`switchMap()`保留了原始的请求顺序,并且只返回最近一次 `http` 调用返回的可观察对象。
|
||||
这是因为以前的调用都被取消或丢弃了。
|
||||
|
||||
If the search text is empty, the `http()` method call is also short circuited
|
||||
|
@ -752,6 +754,7 @@ a#ngoninit
|
|||
注意,_取消_`HeroSearchService`的可观察对象并不会实际中止 (abort) 一个未完成的 HTTP 请求,
|
||||
除非服务支持这个特性,这个问题我们以后再讨论。
|
||||
目前我们的做法只是丢弃不希望的结果。
|
||||
|
||||
:marked
|
||||
* `catch` intercepts a failed observable.
|
||||
The simple example prints the error to the console; a real life app would do better.
|
||||
|
|
Loading…
Reference in New Issue