Skip to content

Commit

Permalink
Translate Advanced Guides > Forwarding Refs (#260)
Browse files Browse the repository at this point in the history
* Translate Advanced Guides > Forwarding Refs

* Translate Advanced Guides > Forwarding Refs : feedback

Co-authored-by: youngsun.min <[email protected]>
Co-authored-by: Haegul Pyun <[email protected]>
  • Loading branch information
3 people authored Feb 11, 2021
1 parent f1efd13 commit 0004b82
Show file tree
Hide file tree
Showing 6 changed files with 45 additions and 44 deletions.
62 changes: 31 additions & 31 deletions content/docs/forwarding-refs.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,73 +4,73 @@ title: Forwarding Refs
permalink: docs/forwarding-refs.html
---

Ref forwarding is a technique for automatically passing a [ref](/docs/refs-and-the-dom.html) through a component to one of its children. This is typically not necessary for most components in the application. However, it can be useful for some kinds of components, especially in reusable component libraries. The most common scenarios are described below.
ref 전달은 컴포넌트를 통해 자식 중 하나에 [ref](/docs/refs-and-the-dom.html)를 자동으로 전달하는 기법입니다. 일반적으로 애플리케이션 대부분의 컴포넌트에 필요하지는 않습니다. 그렇지만, 특히 재사용 가능한 컴포넌트 라이브러리와 같은 어떤 컴포넌트에서는 유용할 수 있습니다. 가장 보편적인 시나리오를 아래에 설명하겠습니다.

## Forwarding refs to DOM components {#forwarding-refs-to-dom-components}
## DOM 에 refs 전달하기 {#forwarding-refs-to-dom-components}

Consider a `FancyButton` component that renders the native `button` DOM element:
기본 `button` DOM 요소를 렌더링하는 `FancyButton` 컴포넌트를 가정해 봅시다.
`embed:forwarding-refs/fancy-button-simple.js`

React components hide their implementation details, including their rendered output. Other components using `FancyButton` **usually will not need to** [obtain a ref](/docs/refs-and-the-dom.html) to the inner `button` DOM element. This is good because it prevents components from relying on each other's DOM structure too much.
`FancyButton`를 사용하는 다른 컴포넌트들은 **일반적으로** 내부 `button` DOM 요소에 대한 [ref를 얻을](/docs/refs-and-the-dom.html) 필요가 없습니다. 이는 컴포넌트들이 서로의 DOM 구조에 지나치게 의존하지 않기 때문에 괜찮습니다.

Although such encapsulation is desirable for application-level components like `FeedStory` or `Comment`, it can be inconvenient for highly reusable "leaf" components like `FancyButton` or `MyTextInput`. These components tend to be used throughout the application in a similar manner as a regular DOM `button` and `input`, and accessing their DOM nodes may be unavoidable for managing focus, selection, or animations.
이런 캡슐화는 `FeedStory``Comment` 같은 애플리케이션 레벨의 컴포넌트에서는 바람직하지만, `FancyButton`이나 `MyTextInput`과 같은 재사용성이 높은 "말단" 요소에서는 불편할 수도 있습니다. 이런 컴포넌트들은 일반적인 DOM `button`, `input`과 유사한 방볍으로 애플리케이션 전체에 걸쳐 사용되는 경향이 있습니다. 그리고 포커스, 선택, 애니메이션을 관리하기 위해서는 이런 DOM 노드에 접근하는 것이 불가피할 수 있습니다.

**Ref forwarding is an opt-in feature that lets some components take a `ref` they receive, and pass it further down (in other words, "forward" it) to a child.**
**Ref 전달하기는 일부 컴포넌트가 수신한 `ref`를 받아 조금 더 아래로 전달(즉, "전송")할 수 있는 옵트인 기능입니다.**

In the example below, `FancyButton` uses `React.forwardRef` to obtain the `ref` passed to it, and then forward it to the DOM `button` that it renders:
아래의 예에서 `FancyButton``React.forwardRef`를 사용하여 전달된 `ref`를 얻고, 그것을 렌더링 되는 DOM `button`으로 전달합니다.

`embed:forwarding-refs/fancy-button-simple-ref.js`

This way, components using `FancyButton` can get a ref to the underlying `button` DOM node and access it if necessary—just like if they used a DOM `button` directly.
이런 방법으로 `FancyButton`을 사용하는 컴포넌트들은 `button` DOM 노드에 대한 참조를 가져올 수 있고, 필요한 경우 DOM `button`을 직접 사용하는 것처럼 접근할 수 있습니다.

Here is a step-by-step explanation of what happens in the above example:
위의 예제에서 어떤 일이 일어나는지 단계별로 설명하겠습니다.

1. We create a [React ref](/docs/refs-and-the-dom.html) by calling `React.createRef` and assign it to a `ref` variable.
1. We pass our `ref` down to `<FancyButton ref={ref}>` by specifying it as a JSX attribute.
1. React passes the `ref` to the `(props, ref) => ...` function inside `forwardRef` as a second argument.
1. We forward this `ref` argument down to `<button ref={ref}>` by specifying it as a JSX attribute.
1. When the ref is attached, `ref.current` will point to the `<button>` DOM node.
1. `React.createRef`를 호출해서 [React ref](/docs/refs-and-the-dom.html)를 생성하고 `ref` 변수에 할당합니다.
1. `ref`를 JSX 속성으로 지정해서 `<FancyButton ref={ref}>`로 전달합니다.
1. React는 이 `ref``forwardRef` 내부의 `(props, ref) => ...` 함수의 두 번째 인자로 전달합니다.
1. `ref`를 JSX 속성으로 지정해서 `<button ref={ref}>`으로 전달합니다.
1. ref가 첨부되면 `ref.current``<button>` DOM 노드를 가리키게 됩니다.

>Note
>알아두기
>
>The second `ref` argument only exists when you define a component with `React.forwardRef` call. Regular function or class components don't receive the `ref` argument, and ref is not available in props either.
>두 번째 `ref` 인자는 `React.forwardRef`와 같이 호출된 컴포넌트를 정의했을 때에만 생성됩니다. 일반 함수나 클래스 컴포넌트는 `ref` 인자를 받지도 않고 props에서 사용할 수도 없습니다.
>
>Ref forwarding is not limited to DOM components. You can forward refs to class component instances, too.
>Ref 전달은 DOM 컴포넌트에만 한정적이지 않습니다. 클래스 컴포넌트 인스턴스에도 전달할 수 있습니다.
## Note for component library maintainers {#note-for-component-library-maintainers}
## 컴포넌트 라이브러리 유지관리자를 위한 주의사항 {#note-for-component-library-maintainers}

**When you start using `forwardRef` in a component library, you should treat it as a breaking change and release a new major version of your library.** This is because your library likely has an observably different behavior (such as what refs get assigned to, and what types are exported), and this can break apps and other libraries that depend on the old behavior.
**컴포넌트 라이브러리에서 `forwardRef`를 사용하기 시작할 때 이것을 변경사항으로 간주하고 라이브러리의 새로운 중요 버전을 릴리즈 해야 합니다.** 이는 라이브러리에 주목할 만하게 (ref가 할당되는 것이 무엇이며 내보내는 유형은 무엇인가와 같은) 다른 동작을 할 가능성이 높고 이전 동작에 의존하는 앱이나 다른 라이브러리들이 손상될 가능성이 크기 때문입니다.

Conditionally applying `React.forwardRef` when it exists is also not recommended for the same reasons: it changes how your library behaves and can break your users' apps when they upgrade React itself.
조건적으로 `React.forwardRef`가 존재할 때 조건부로 적용하는 것도 같은 이유로 권장하지 않습니다: 라이브러리가 동작하는 방식을 변경하고 React 그 자체를 업데이트할 때 사용자 앱을 손상시킬 수도 있습니다.

## Forwarding refs in higher-order components {#forwarding-refs-in-higher-order-components}
## 고차원 컴포넌트에서의 ref 전달하기 {#forwarding-refs-in-higher-order-components}

This technique can also be particularly useful with [higher-order components](/docs/higher-order-components.html) (also known as HOCs). Let's start with an example HOC that logs component props to the console:
이 기술은 (HOC로 알려진) [고차원 컴포넌트](/docs/higher-order-components.html)에서 부분적으로 유용할 수 있습니다. 콘솔에 컴포넌트 props를 로깅 하는 HOC 예제로 설명을 시작해 보겠습니다.
`embed:forwarding-refs/log-props-before.js`

The "logProps" HOC passes all `props` through to the component it wraps, so the rendered output will be the same. For example, we can use this HOC to log all props that get passed to our "fancy button" component:
"logProps" HOC는 모든 `props`를 래핑하는 컴포넌트로 전달하므로 렌더링 된 결과가 동일하게 됩니다. 예를 들어, 이 HOC를 사용해서 "fancy button" 컴포넌트로 전달하는 모든 props를 기록 할 수 있습니다.
`embed:forwarding-refs/fancy-button.js`

There is one caveat to the above example: refs will not get passed through. That's because `ref` is not a prop. Like `key`, it's handled differently by React. If you add a ref to a HOC, the ref will refer to the outermost container component, not the wrapped component.
위 예제에서 한 가지 주의사항이 있습니다: refs는 전달되지 않는다는 것입니다. 그것은 `ref`는 prop이 아니기 때문입니다. `key`와 마찬가지로 `ref`는 React에서 다르게 처리합니다. 만약 HOC에 ref를 추가하면 ref는 래핑 된 컴포넌트가 아니라 가장 바깥쪽 컨테이너 컴포넌트를 참조합니다.

This means that refs intended for our `FancyButton` component will actually be attached to the `LogProps` component:
`FancyButton` 컴포넌트를 위한 refs가 실제로는 `LogProps` 컴포넌트에 첨부된다는 것을 의미합니다.
`embed:forwarding-refs/fancy-button-ref.js`

Fortunately, we can explicitly forward refs to the inner `FancyButton` component using the `React.forwardRef` API. `React.forwardRef` accepts a render function that receives `props` and `ref` parameters and returns a React node. For example:
다행히도 `React.forwardRef` API를 사용하여 내부 `FancyButton` 컴포넌트에 대한 refs를 명시적으로 전달할 수 있습니다. `React.forwardRef``props``ref` 파라미터를 받아 React 노드를 반환하는 렌더링 함수를 받습니다. 예를 들어:
`embed:forwarding-refs/log-props-after.js`

## Displaying a custom name in DevTools {#displaying-a-custom-name-in-devtools}
## DevTools에 사용자 정의 이름 표시하기 {#displaying-a-custom-name-in-devtools}

`React.forwardRef` accepts a render function. React DevTools uses this function to determine what to display for the ref forwarding component.
`React.forwardRef`는 렌더링 함수를 받습니다. React DevTools는 이 함수를 사용하여 ref 전달 컴포넌트에 대해서 무엇을 표시할 것인지 정의합니다.

For example, the following component will appear as "*ForwardRef*" in the DevTools:
예로, 다음의 컴포넌트는 DevTools에 "*ForwardRef*"로 나타날 것입니다.

`embed:forwarding-refs/wrapped-component.js`

If you name the render function, DevTools will also include its name (e.g. "*ForwardRef(myFunction)*"):
만약 렌더링 함수를 지정하면 DevTools에 해당 이름도 포함됩니다. (예, "*ForwardRef(myFunction)*"):

`embed:forwarding-refs/wrapped-component-with-function-name.js`

You can even set the function's `displayName` property to include the component you're wrapping:
감싸고 있는 컴포넌트를 포함하도록 함수의 `displayName` 속성을 설정할 수도 있습니다.

`embed:forwarding-refs/customized-display-name.js`
4 changes: 2 additions & 2 deletions examples/forwarding-refs/customized-display-name.js
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,8 @@ function logProps(Component) {
return <LogProps {...props} forwardedRef={ref} />;
}

// Give this component a more helpful display name in DevTools.
// e.g. "ForwardRef(logProps(MyComponent))"
// DevTools에서 이 컴포넌트에 조금 더 유용한 표시 이름을 지정하세요.
// 예, "ForwardRef(logProps(MyComponent))"
// highlight-range{1-2}
const name = Component.displayName || Component.name;
forwardRef.displayName = `logProps(${name})`;
Expand Down
9 changes: 5 additions & 4 deletions examples/forwarding-refs/fancy-button-ref.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,10 +3,11 @@ import FancyButton from './FancyButton';
// highlight-next-line
const ref = React.createRef();

// The FancyButton component we imported is the LogProps HOC.
// Even though the rendered output will be the same,
// Our ref will point to LogProps instead of the inner FancyButton component!
// This means we can't call e.g. ref.current.focus()
// 가져온 FancyButton 컴포넌트는 LogProps HOC입니다.
// 렌더링된 결과가 동일하다고 하더라도,
// ref는 내부 FancyButton 컴포넌트 대신 LogProps를 가리킵니다!
// 이것은 우리가 예를 들어 ref.current.focus()를 호출할 수 없다는 것을 의미합니다.

// highlight-range{4}
<FancyButton
label="Click Me"
Expand Down
2 changes: 1 addition & 1 deletion examples/forwarding-refs/fancy-button-simple-ref.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,6 @@ const FancyButton = React.forwardRef((props, ref) => (
</button>
));

// You can now get a ref directly to the DOM button:
// 이제 DOM 버튼으로 ref를 작접 받을 수 있습니다.
const ref = React.createRef();
<FancyButton ref={ref}>Click me!</FancyButton>;
4 changes: 2 additions & 2 deletions examples/forwarding-refs/fancy-button.js
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ class FancyButton extends React.Component {
// ...
}

// Rather than exporting FancyButton, we export LogProps.
// It will render a FancyButton though.
// FancyButton을 내보내는 대신 LogProps를 내보냅니다.
// 그래도 FancyButton을 렌더링합니다.
// highlight-next-line
export default logProps(FancyButton);
8 changes: 4 additions & 4 deletions examples/forwarding-refs/log-props-after.js
Original file line number Diff line number Diff line change
Expand Up @@ -9,15 +9,15 @@ function logProps(Component) {
// highlight-next-line
const {forwardedRef, ...rest} = this.props;

// Assign the custom prop "forwardedRef" as a ref
// 사용자 정의 prop "forwardedRef"를 ref로 할당합니다.
// highlight-next-line
return <Component ref={forwardedRef} {...rest} />;
}
}

// Note the second param "ref" provided by React.forwardRef.
// We can pass it along to LogProps as a regular prop, e.g. "forwardedRef"
// And it can then be attached to the Component.
// React.forwardRef에서 제공하는 두 번째 파라미터 "ref"에 주의하십시오.
// 가령 "forwardedRef"같은 일반 prop으로 LogProps에 전달할 수 있습니다.
// 그 다음 Component에 연결할 수 있습니다.
// highlight-range{1-3}
return React.forwardRef((props, ref) => {
return <LogProps {...props} forwardedRef={ref} />;
Expand Down

0 comments on commit 0004b82

Please sign in to comment.