Получить имя компонента в React

Я разрабатываю приложение React. У меня есть компонент загрузки, который представляет собой небольшую анимацию для ожидания. Я хочу добавить сообщение в этот компонент Загрузка в соответствии с компонентом, который его вызвал.

Вот как я называю свой компонент загрузки (с this.state.displayLoading с истинным или ложным):

class LoginForm extends React.Component {
    render() {   
        return (
            <div className="login-form-root">
                 {this.state.displayLoading && <Loading loadingFrom={?}/>}
            </div>
        );
    }
}

Я хочу получить "LoginForm" в моей переменной loadingFrom, которая является именем класса. Возможно, это не правильный способ сделать это.

Ответ 1

Вам не нужно, чтобы он был динамическим, поскольку вы сами пишете компонент и можете передать его в виде строки

class LoginForm extends React.Component {
    render() {   
        return (
            <div className="login-form-root">
                 {this.state.displayLoading && <Loading loadingFrom="LoginForm "/>}
            </div>
        );
    }
}

Однако если вам все еще нужно получить доступ к имени компонента, вы можете определить свойство displayName для компонента

class LoginForm extends React.Component {
   static displayName = 'LoginForm';
    render() {   
        return (
            <div className="login-form-root">
                 {this.state.displayLoading && <Loading loadingFrom="LoginForm "/>}
            </div>
        );
    }
}

и получить к нему доступ как Component.displayName.

Ответ 2

Вы можете использовать this.constructor.name для получения имени вашего компонента.

(Используя React 16.x на момент написания этой статьи)

Caveat: Это не сработает, если вы собираетесь использовать программу Webpack.

Ответ 3

Каждый React.Component имеет свойство displayName которое JSX устанавливает автоматически, поэтому теоретически вы можете использовать это свойство

class LoginForm extends React.Component {
    render() {   
        return (
            <div className="login-form-root">
                {this.state.displayLoading && <Loading loadingFrom={this.displayName}/>}
            </div>
        );
    }
}

ОБНОВЛЕНИЕ (после нескольких комментариев, говорящих, что это не работает)

В соответствии с соглашением, Response предлагает фрагмент кода для переноса получения имени компонента в их документации, а именно:

function withSubscription(WrappedComponent) {
  class WithSubscription extends React.Component {/* ... */}
  WithSubscription.displayName = 'WithSubscription(${getDisplayName(WrappedComponent)})';
  return WithSubscription;
}

function getDisplayName(WrappedComponent) {
  return WrappedComponent.displayName || WrappedComponent.name || 'Component';
}

Как видно, они сначала проверяют отображаемое имя, затем имя компонента, и если все не удается, то это будет просто 'Component'

Ответ 4

Это было немного спрятано, но, играя с отладчиком, мне удалось выяснить, что this._reactInternalInstance.getName() возвращает имя компонента во время выполнения.

Например:

componentDidMount() {
    console.log('mount ' + this._reactInternalInstance.getName());
}

Ответ 5

После поиска с помощью отладчика, в более новых версиях вы должны использовать this._reactInternalFiber.elementType.name вместо this._reactInternalInstance.getName()