#9 React中的条件渲染

React 中的条件渲染有以下几种方式:

  • if 语句
  • 三元操作符(ternary operator)
  • 逻辑 && 操作符
  • switch.. case.. 语句
  • 枚举(enums)
  • 多层条件渲染(multi-level conditional reandering)
  • 使用高阶组件

1.if 语句

在React中使用if语句条件渲染是最简单的。比如List组件如果没有任何items,可以提前return

function List({ list }) {
  if (!list) {
    return null;
  }
  return (
    
{list.map(item => )}
); }

一个组件如果return null,将不会被渲染出来。如果你想给用户一些反馈,当list为空时,可以采用下面方式:

function List({ list }) {
  // list 为null的情况
  if (!list) {
    return null;
  }

  // list 为空的情况
  if (!list.length) {
    return 

sorry, the list is empty

} else { return (
{list.map(item => )}
); } }

if...else 是最基本的条件渲染方式。

2.三元操作符

可以使用三元运算符来代替上面的if...else... 条件渲染。

例如,你想从2种模式(edit, view)中切换,可以使用布尔值来决定那个组件被渲染:

function Item({ item, mode }) {
  const isEditMode = mode === 'EDIT';

  return (
    
{ isEditMode ? : }
); }

三元运算符使条件渲染更加的简洁,使得代码可以采用内联(inline)的方式表达出来

3.逻辑 '&&' 操作符

这个是当你想渲染一个组件或者什么也不渲染的情况

例如,有一个 LoadingIndicator 组件,返回加载文字或者什么也没有。当然可以使用if...else或者三元运算符,如下:

function LoadingIndicator({ isLoading }) {
  if (isLoading) {
    return (
      

Loading...

); } else { return null; } } function LoadingIndicator({ isLoading }) { return (
{ isLoading ?

Loading...

: null }
); }

使用 && 可以使返回 null 的情况的条件渲染更加的简洁

function LoadingIndicator({ isLoading }) {
  return (
    
{ isLoading &&

Loading...

}
); }

4.switch...case语句

我们有可能遇到多种条件渲染的情况,例如依据不同的state渲染不同的Component.

例如,Notification 组件根据输入状态可能渲染Error,Warning,Info三种不同的组件。这个时候可以使用switch...case来进行多种条件渲染:

function Notification({ text, state }) {
  switch (state) {
    case 'info':
      return ;
    case 'warning':
      return ;
    case 'info':
      return ;
    default:
      return null;
  }
}

注意switch...case语句永远要加上default情况,因为React组件要么返回元素,要么返回null

另外值得注意的是,如果组件依据 state 属性 渲染时,最后添加上 React.PropTypes,即上面的组件后面添加:

Notification.propTypes = {
  text: React.PropTypes.string,
  state: React.PropTypes.oneOf(['info', 'warning', 'error'])
}

另一种将条件渲染结果内联在switch...case中的方法是,使用立即调用函数

function Notification({ text, state }) {
  return (
    
{(() => { switch (state) { case 'info': return ; case 'warning': return ; case 'info': return ; default: return null; } })()}
); }

switch...case帮助我们在多种条件中渲染中使用,但是多种条件渲染最好的方式是枚举

5.枚举(Enums)

在javascript中,对象的键值对可以用作枚举:

const ENUM = {
  a: '1',
  b: '2',
  c: '3'
};

枚举是多种条件渲染中很好的一种方式,上面的 Notification 组件可以写为:

function Notification({ text, state }) {
  return (
    
{{ info: , warning: , error: }[state]}
) }

上面的 state 属性用于取回对象中的值,这比switch...case可读性更强。

因为对象的值依赖 text 属性,所以我们必须使用内联对象。如果我们不需要text属性,我们可以使用外部静态枚举:

const NOTIFICATION_STATES = {
  info: ,
  warning: ,
  error: ,
};

function Notification({ state }) {
  return (
    
{NOTIFICATION_STATES[state]}
) }

如果我们需要text属性,我们可以使用函数取回对象的值

const getSpecificNotification = (text) => ({
  info: ,
  warning: ,
  error: ,
});

function Notification({ state, text }) {
  return (
    
{getSpecificNotification(text)[state]}
) }

对象用作枚举,使用场景很灵活,下面例子:

function FooBarOrFooOrBar({ isFoo, isBar }) {
  const key = `${isFoo}-${isBar}`;
  return (
    
{{ ['true-true']: , ['true-false']: , ['false-true']: , ['false-false']: null, }[key]}
); } FooBarOrFooOrBar.propTypes = { isFoo: React.PropTypes.boolean.isRequired, isBar: React.PropTypes.boolean.isRequired }

6.多层条件渲染

我们有时候可能碰到嵌套条件选择渲染的情况。

例如,List组件可能显示一个list,或者一个empty text提示,或者什么多没有:

function List({ list }) {
  const isNull = !list;
  const isEmpty = !isNull && !list.length;

  return (
    
{ isNull ? null : ( isEmpty ?

Sorry, the list is empty

:
{list.map(item => )}
) }
); } // 实例 //
//

Sorry, the list is empty

//
a
b
c

但是最好保持嵌套的层数最小化,这样代码可读性更强。可以将组件划分成更小的组件的方式

function List({ list }) {
  const isList = list && list.length;

  return (
    
{ isList ?
{list.map(item => )}
: }
); } function NoList({ isNull, isEmpty }) { return (!isNull && isEmpty) &&

Sorry, the list is empty

}

7.高阶组件用作条件渲染

HOCs 在React中很适合条件渲染。HOCs的一种使用方式就是改变组件的外观。

例如使用高阶组件来展示一个加载显示器或者一个想要的组件:

function withLoadingIndicator(Component) {
  return function EnhancedComponent({ isLoading, ...props }) {
    if (!isLoading) {
      return ;
    }

    return 

Loading...

; } } // 使用 const ListWithLoadingIndicator = withLoadingIndicator(List);

这个示例中,List组件能关注渲染list上,而不必担心loading状态,另外,HOCs可以屏蔽list为null或empty的情况。

总结

使用上面的哪一种条件渲染可以根据下面的一些情况而定:

  • if-else

    • 最简单的条件渲染
    • 适用于新手
    • 使用if,从渲染方法中返回null提前退出函数
  • 三元操作符

    • 比if-else更好,优先使用
    • 比if-else更加简洁
  • 逻辑 '&&' 操作符

    • 不返回元素就返回null时使用
  • switch...case

    • 比较冗长
    • 可以通过立即调用函数内联使用
    • 使用枚举的方式代替这种方式更好
  • 枚举(enums)

    • 使用于不同的状态使用
    • 超过一种条件选择时使用
  • 多层次条件选择渲染

    • 避免使用这种方式对可读性的影响
    • 将组件划分为更小的组件,小组件自身带有条件选择
    • 偏向于使用高阶组件(HOCs)
  • HOCs

    • 使用高阶组件而屏蔽条件渲染
    • 组件能关注主要的逻辑目的

你可能感兴趣的:(#9 React中的条件渲染)