Skip to content
New issue

Have a question about this project? # for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “#”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? # to your account

docs(cn): translate content/docs/faq-functions.md into Chinese #136

Merged
merged 5 commits into from
May 24, 2019
Merged
Changes from 3 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
98 changes: 49 additions & 49 deletions content/docs/faq-functions.md
Original file line number Diff line number Diff line change
@@ -1,26 +1,26 @@
---
id: faq-functions
title: Passing Functions to Components
title: 传递函数给组件
permalink: docs/faq-functions.html
layout: docs
category: FAQ
---

### How do I pass an event handler (like onClick) to a component? {#how-do-i-pass-an-event-handler-like-onclick-to-a-component}
### 如何将事件处理器(比如 onClick)传递给组件?{#how-do-i-pass-an-event-handler-like-onclick-to-a-component}

Pass event handlers and other functions as props to child components:
可以将事件处理器和其他函数作为 props 传递给子组件:

```jsx
<button onClick={this.handleClick}>
```

If you need to have access to the parent component in the handler, you also need to bind the function to the component instance (see below).
如果需要在事件处理器中访问父组件,还需要为该函数绑定组件实例(参见下文)。

### How do I bind a function to a component instance? {#how-do-i-bind-a-function-to-a-component-instance}
### 如何为函数绑定组件实例? {#how-do-i-bind-a-function-to-a-component-instance}

There are several ways to make sure functions have access to component attributes like `this.props` and `this.state`, depending on which syntax and build steps you are using.
有以下几种方式可以确保函数可以访问组件属性,比如 `this.props` `this.state`,这取决于使用的语法和构建步骤。

#### Bind in Constructor (ES2015) {#bind-in-constructor-es2015}
#### 在构造函数中绑定(ES2015 {#bind-in-constructor-es2015}

```jsx
class Foo extends Component {
Expand All @@ -37,7 +37,7 @@ class Foo extends Component {
}
```

#### Class Properties (Stage 3 Proposal) {#class-properties-stage-3-proposal}
#### class 属性(第三阶段提案){#class-properties-stage-3-proposal}

```jsx
class Foo extends Component {
Expand All @@ -51,7 +51,7 @@ class Foo extends Component {
}
```

#### Bind in Render {#bind-in-render}
#### Render 中的绑定 {#bind-in-render}

```jsx
class Foo extends Component {
Expand All @@ -64,11 +64,11 @@ class Foo extends Component {
}
```

>**Note:**
>**注意:**
>
>Using `Function.prototype.bind` in render creates a new function each time the component renders, which may have performance implications (see below).
>在 render 方法中使用 `Function.prototype.bind` 会在每次组件渲染时创建一个新的函数,可能会影响性能(参见下文)。

#### Arrow Function in Render {#arrow-function-in-render}
#### Render 中使用箭头函数 {#arrow-function-in-render}

```jsx
class Foo extends Component {
Expand All @@ -81,19 +81,19 @@ class Foo extends Component {
}
```

>**Note:**
>**注意:**
>
>Using an arrow function in render creates a new function each time the component renders, which may have performance implications (see below).
>render 方法中使用箭头函数也会在每次组件渲染时创建一个新的函数,可能会影响性能(参见下文)。

### Is it OK to use arrow functions in render methods? {#is-it-ok-to-use-arrow-functions-in-render-methods}
### 可以在 render 方法中使用箭头函数吗?{#is-it-ok-to-use-arrow-functions-in-render-methods}

Generally speaking, yes, it is OK, and it is often the easiest way to pass parameters to callback functions.
一般来说是可以的,并且直接箭头函数是向回调函数传递参数的最简单的办法。
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

并且直接箭头函数?是不是打错了啊。。

Suggested change
一般来说是可以的,并且直接箭头函数是向回调函数传递参数的最简单的办法
一般来说是可以的,并且使用箭头函数是向回调函数传递参数的最简单的办法


If you do have performance issues, by all means, optimize!
但是如果遇到了性能问题,一定要进行优化!

### Why is binding necessary at all? {#why-is-binding-necessary-at-all}
### 为什么绑定是必要的?{#why-is-binding-necessary-at-all}

In JavaScript, these two code snippets are **not** equivalent:
在JavaScript中,以下两种写法是**不**等价的:

```js
obj.method();
Expand All @@ -104,15 +104,15 @@ var method = obj.method;
method();
```

Binding methods helps ensure that the second snippet works the same way as the first one.
bind 方法确保了第二种写法与第一种写法相同。
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

第 94 行翻译成了绑定,所以这里也翻译成“绑定”吧,统一一下。

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

这个就 bind 吧~


With React, typically you only need to bind the methods you *pass* to other components. For example, `<button onClick={this.handleClick}>` passes `this.handleClick` so you want to bind it. However, it is unnecessary to bind the `render` method or the lifecycle methods: we don't pass them to other components.
使用 React,通常只需要绑定*传递*给其他组件的方法。例如,`<button onClick={this.handleClick}>` 是在传递 `this.handleClick` ,所以需要绑定它。但是,没有必要绑定 `render` 方法或生命周期方法:我们并没有将它们传递给其他的组件。

[This post by Yehuda Katz](https://yehudakatz.com/2011/08/11/understanding-javascript-function-invocation-and-this/) explains what binding is, and how functions work in JavaScript, in detail.
[This post by Yehuda Katz](https://yehudakatz.com/2011/08/11/understanding-javascript-function-invocation-and-this/) 详细解释了什么是绑定,和函数在 JavaScript 中怎么起作用。
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

个人看法:“和”用来连接两个名词短语好一点,连接两个分句感觉用“以及”通顺一点。

Suggested change
[This post by Yehuda Katz](https://yehudakatz.com/2011/08/11/understanding-javascript-function-invocation-and-this/) 详细解释了什么是绑定,和函数在 JavaScript 中怎么起作用。
[This post by Yehuda Katz](https://yehudakatz.com/2011/08/11/understanding-javascript-function-invocation-and-this/) 详细解释了什么是绑定,以及函数在 JavaScript 中怎么起作用。


### Why is my function being called every time the component renders? {#why-is-my-function-being-called-every-time-the-component-renders}
### 为什么我的函数每次组件渲染时都会被调用?{#why-is-my-function-being-called-every-time-the-component-renders}

Make sure you aren't _calling the function_ when you pass it to the component:
确保你没有*调用函数*,在你传递函数给组件时:
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
确保你没有*调用函数*,在你传递函数给组件时
确保你在传递一个函数给组件时,没有*调用这个函数*


```jsx
render() {
Expand All @@ -121,7 +121,7 @@ render() {
}
```

Instead, *pass the function itself* (without parens):
正确做法是,*传递函数本身*(不带括号):

```jsx
render() {
Expand All @@ -130,21 +130,21 @@ render() {
}
```

### How do I pass a parameter to an event handler or callback? {#how-do-i-pass-a-parameter-to-an-event-handler-or-callback}
### 如何传递参数给事件处理器或回调? {#how-do-i-pass-a-parameter-to-an-event-handler-or-callback}

You can use an arrow function to wrap around an event handler and pass parameters:
可以使用箭头函数包裹事件处理器,并传递参数:

```jsx
<button onClick={() => this.handleClick(id)} />
```

This is equivalent to calling `.bind`:
以上代码和调用 `.bind` 是等价的:

```jsx
<button onClick={this.handleClick.bind(this, id)} />
```

#### Example: Passing params using arrow functions {#example-passing-params-using-arrow-functions}
#### 示例:通过箭头函数传递参数 {#example-passing-params-using-arrow-functions}

```jsx
const A = 65 // ASCII character code
Expand Down Expand Up @@ -178,9 +178,9 @@ class Alphabet extends React.Component {
}
```

#### Example: Passing params using data-attributes {#example-passing-params-using-data-attributes}
#### 示例:通过 data-attributes 传递参数 {#example-passing-params-using-data-attributes}

Alternately, you can use DOM APIs to store data needed for event handlers. Consider this approach if you need to optimize a large number of elements or have a render tree that relies on React.PureComponent equality checks.
同样的,也可以使用DOM API来存储事件处理器需要的数据。如果需要优化大量元素或使用依赖于 `React.PureComponent` 相等性检查的渲染树,请考虑使用此方法。
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
同样的,也可以使用DOM API来存储事件处理器需要的数据。如果需要优化大量元素或使用依赖于 `React.PureComponent` 相等性检查的渲染树,请考虑使用此方法。
同样的,也可以使用 DOM API 来存储事件处理器需要的数据。如果需要优化大量元素或使用依赖于 `React.PureComponent` 相等性检查的渲染树,请考虑使用此方法。


```jsx
const A = 65 // ASCII character code
Expand Down Expand Up @@ -218,23 +218,23 @@ class Alphabet extends React.Component {
}
```

### How can I prevent a function from being called too quickly or too many times in a row? {#how-can-i-prevent-a-function-from-being-called-too-quickly-or-too-many-times-in-a-row}
### 怎样阻止函数被调用太快或者太多次?{#how-can-i-prevent-a-function-from-being-called-too-quickly-or-too-many-times-in-a-row}

If you have an event handler such as `onClick` or `onScroll` and want to prevent the callback from being fired too quickly, then you can limit the rate at which callback is executed. This can be done by using:
如果你有一个 `onClick` 或者 `onScroll` 这样的事件处理器,想要阻止回调被触发的太快,那么可以限制执行回调的速度,可以通过以下几种方式做到这点:

- **throttling**: sample changes based on a time based frequency (eg [`_.throttle`](https://lodash.com/docs#throttle))
- **debouncing**: publish changes after a period of inactivity (eg [`_.debounce`](https://lodash.com/docs#debounce))
- **`requestAnimationFrame` throttling**: sample changes based on [`requestAnimationFrame`](https://developer.mozilla.org/en-US/docs/Web/API/window/requestAnimationFrame) (eg [`raf-schd`](https://github.com/alexreardon/raf-schd))
- **节流**:基于时间的频率来进行抽样更改 (例如 [`_.throttle`](https://lodash.com/docs#throttle))
- **防抖**:一段时间的不活动之后发布更改 (例如 [`_.debounce`](https://lodash.com/docs#debounce))
- **`requestAnimationFrame` 节流**:基于 requestAnimationFrame 的抽样更改 (例如 [raf-schd]([`raf-schd`](https://github.com/alexreardon/raf-schd)))

See [this visualization](http://demo.nimius.net/debounce_throttle/) for a comparison of `throttle` and `debounce` functions.
可以看这个比较 throttle 和 debounce 的[可视化页面](http://demo.nimius.net/debounce_throttle/)

> Note:
> **注意:**
>
> `_.debounce`, `_.throttle` and `raf-schd` provide a `cancel` method to cancel delayed callbacks. You should either call this method from `componentWillUnmount` _or_ check to ensure that the component is still mounted within the delayed function.
> `_.debounce` , `_.throttle` `raf-schd` 都提供了一个 `cancel` 方法来取消延迟回调。 所以要么调用 `componentWillUnmount`,否则需要对代码进行检查来保证在延迟函数有效期间内组件始终挂载。
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
> `_.debounce` , `_.throttle``raf-schd` 都提供了一个 `cancel` 方法来取消延迟回调。 所以要么调用 `componentWillUnmount`,否则需要对代码进行检查来保证在延迟函数有效期间内组件始终挂载
> `_.debounce``_.throttle``raf-schd` 都提供了一个 `cancel` 方法来取消延迟回调。 你需要在 `componentWillUnmount` 中调用该方法,或者对代码进行检查来保证在延迟函数有效期间内组件始终挂载


#### Throttle {#throttle}
#### 节流 {#throttle}

Throttling prevents a function from being called more than once in a given window of time. The example below throttles a "click" handler to prevent calling it more than once per second.
节流阻止函数在给定时间窗口内被调不能超过一次。下面这个例子会节流 “click” 事件处理器每秒钟的只能调用一次。
Copy link
Member

@yuqingc yuqingc Apr 3, 2019

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
节流阻止函数在给定时间窗口内被调不能超过一次。下面这个例子会节流 “click” 事件处理器每秒钟的只能调用一次
节流阻止函数在给定时间窗口内被调不能超过一次。下面这个例子会节流 “click” 事件处理器,使其每秒钟的只能调用一次


```jsx
import throttle from 'lodash.throttle';
Expand All @@ -260,9 +260,9 @@ class LoadMoreButton extends React.Component {
}
```

#### Debounce {#debounce}
#### 防抖 {#debounce}

Debouncing ensures that a function will not be executed until after a certain amount of time has passed since it was last called. This can be useful when you have to perform some expensive calculation in response to an event that might dispatch rapidly (eg scroll or keyboard events). The example below debounces text input with a 250ms delay.
防抖确保函数不会在上一次被调用之后一定量的时间内被执行。当必须进行一些费时的计算来响应快速派发的事件时(比如鼠标滚动或键盘事件时),防抖是非常有用的。下面这个例子以 250ms 的延迟来改变文本输入。

```jsx
import debounce from 'lodash.debounce';
Expand Down Expand Up @@ -302,13 +302,13 @@ class Searchbox extends React.Component {
}
```

#### `requestAnimationFrame` throttling {#requestanimationframe-throttling}
#### `requestAnimationFrame` 节流 {#requestanimationframe-throttling}

[`requestAnimationFrame`](https://developer.mozilla.org/en-US/docs/Web/API/window/requestAnimationFrame) is a way of queuing a function to be executed in the browser at the optimal time for rendering performance. A function that is queued with `requestAnimationFrame` will fire in the next frame. The browser will work hard to ensure that there are 60 frames per second (60 fps). However, if the browser is unable to it will naturally *limit* the amount of frames in a second. For example, a device might only be able to handle 30 fps and so you will only get 30 frames in that second. Using `requestAnimationFrame` for throttling is a useful technique in that it prevents you from doing more than 60 updates in a second. If you are doing 100 updates in a second this creates additional work for the browser that the user will not see anyway.
[`requestAnimationFrame`](https://developer.mozilla.org/en-US/docs/Web/API/window/requestAnimationFrame) 是在浏览器中排队等待执行的一种方法,它可以在呈现性能的最佳时间执行。一个函数被 `requestAnimationFrame` 放入队列后将会在下一帧触发。浏览器会努力确保每秒 60 帧(60fps)。然而,如果浏览器无法确保,那么自然会*限制*每秒的帧数。例如,某个设备可能只能处理每秒 30 帧,所以每秒只能得到 30 帧。使用 `requestAnimationFrame` 来节流是一种有用的技术,它可以防止在一秒中进行 60 帧以上的更新。如果要求一秒钟内完成100次更新,则会为浏览器创建额外的负担,而用户无法看到这些工作。
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
[`requestAnimationFrame`](https://developer.mozilla.org/en-US/docs/Web/API/window/requestAnimationFrame) 是在浏览器中排队等待执行的一种方法,它可以在呈现性能的最佳时间执行。一个函数被 `requestAnimationFrame` 放入队列后将会在下一帧触发。浏览器会努力确保每秒 60 帧(60fps)。然而,如果浏览器无法确保,那么自然会*限制*每秒的帧数。例如,某个设备可能只能处理每秒 30 帧,所以每秒只能得到 30 帧。使用 `requestAnimationFrame` 来节流是一种有用的技术,它可以防止在一秒中进行 60 帧以上的更新。如果要求一秒钟内完成100次更新,则会为浏览器创建额外的负担,而用户无法看到这些工作
[`requestAnimationFrame`](https://developer.mozilla.org/en-US/docs/Web/API/window/requestAnimationFrame) 是在浏览器中排队等待执行的一种方法,它可以在呈现性能的最佳时间执行。一个函数被 `requestAnimationFrame` 放入队列后将会在下一帧触发。浏览器会努力确保每秒 60 帧(60fps)。然而,如果浏览器无法确保,那么自然会*限制*每秒的帧数。例如,某个设备可能只能处理每秒 30 帧,所以每秒只能得到 30 帧。使用 `requestAnimationFrame` 来节流是一种有用的技术,它可以防止在一秒中进行 60 帧以上的更新。如果一秒钟内完成 100 次更新,则会为浏览器带来额外的负担,而用却户无法感知到这些工作


>**Note:**
>**注意:**
>
>Using this technique will only capture the last published value in a frame. You can see an example of how this optimization works on [`MDN`](https://developer.mozilla.org/en-US/docs/Web/Events/scroll)
>使用这个方法时只能获取帧中最后发布的值。也可以在 [`MDN`](https://developer.mozilla.org/en-US/docs/Web/Events/scroll) 中看优化的示例。
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
>使用这个方法时只能获取帧中最后发布的值。也可以在 [`MDN`](https://developer.mozilla.org/en-US/docs/Web/Events/scroll) 中看优化的示例。
>使用这个方法时只能获取某一帧中最后发布的值。也可以在 [`MDN`](https://developer.mozilla.org/en-US/docs/Web/Events/scroll) 中看优化的示例。


```jsx
import rafSchedule from 'raf-schd';
Expand Down Expand Up @@ -349,6 +349,6 @@ class ScrollListener extends React.Component {
}
```

#### Testing your rate limiting {#testing-your-rate-limiting}
#### 测试速率限制 {#testing-your-rate-limiting}

When testing your rate limiting code works correctly it is helpful to have the ability to fast forward time. If you are using [`jest`](https://facebook.github.io/jest/) then you can use [`mock timers`](https://facebook.github.io/jest/docs/en/timer-mocks.html) to fast forward time. If you are using `requestAnimationFrame` throttling then you may find [`raf-stub`](https://github.com/alexreardon/raf-stub) to be a useful tool to control the ticking of animation frames.
在测试速率限制的代码是否正确工作的时候,如果可以(对动画或操作)进行快进将会很有帮助。如果正在使用 [`jest`](https://facebook.github.io/jest/) ,那么可以使用 [`mock timers`](https://facebook.github.io/jest/docs/en/timer-mocks.html) 来快进。如果正在使用 `requestAnimationFrame` 节流,那么就会发现 [raf-stub]([`raf-stub`](https://github.com/alexreardon/raf-stub)) 是一个控制动画帧的十分有用的工具。
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
在测试速率限制的代码是否正确工作的时候,如果可以(对动画或操作)进行快进将会很有帮助。如果正在使用 [`jest`](https://facebook.github.io/jest/) ,那么可以使用 [`mock timers`](https://facebook.github.io/jest/docs/en/timer-mocks.html) 来快进。如果正在使用 `requestAnimationFrame` 节流,那么就会发现 [raf-stub]([`raf-stub`](https://github.com/alexreardon/raf-stub)) 是一个控制动画帧的十分有用的工具。
在测试速率限制的代码是否正确工作的时候,如果可以(对动画或操作)进行快进将会很有帮助。如果正在使用 [`jest`](https://facebook.github.io/jest/) ,那么可以使用 [`mock timers`](https://facebook.github.io/jest/docs/en/timer-mocks.html) 来快进。如果正在使用 `requestAnimationFrame` 节流,那么就会发现 [`raf-stub`](https://github.com/alexreardon/raf-stub) 是一个控制动画帧的十分有用的工具。