如何在Material-UI中使用Box组件使用替代按钮? [英] How to use override Button using Box component in Material-UI?

查看:98
本文介绍了如何在Material-UI中使用Box组件使用替代按钮?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我一直试图在material-UI的Box组件上理解和编写代码.(

I've been trying to understand and write code on the Box component in material-UI. (https://material-ui.com/components/box/#box)

I've been trying to override a Button component the two ways it describes in the documentation, but I have no idea how. When I run the code segment using both methods, the button appears but no color change. Then when I try to add an extra Button underneath the clone element code segment I get an error saying 'Cannot read property 'className' of undefined'.

            <Box color="primary" clone>
                <Button>Click</Button>
                <Button>Click</Button>
            </Box>

When I add a Button component underneath in the second render props way, the first button just disappears from the DOM completely.


             <Box color="secondary">
                {props => <Button {...props} > Click </Button>}
                <Button color="secondary">Click</Button>
            </Box> 

Would appreciate an explanation of how overriding underlying DOM elements work.

解决方案

There are a few issues with the code you've shown in your question.

  1. primary and secondary are not valid colors within the palette. They are valid options for the color prop of Button, but here you are trying to reference colors within the theme's palette object. For this purpose, you need primary.main and secondary.main (which is what Button uses when you specify <Button color="primary">).

  2. Box only supports a single child when using the clone property and it only supports a single child when using the render props approach. In both of your examples you have two children.


Here is the Material-UI source code that deals with the clone option:

      if (clone) {
        return React.cloneElement(children, {
          className: clsx(children.props.className, className),
          ...spread,
        });
      }

This is creating a new child element that combines the className generated by Box with any existing class name on the child. It gets at this existing class name via children.props.className, but when there are multiple children then children will be an array of elements and will not have a props property so you get the error:

Cannot read property 'className' of undefined


Here is the Material-UI source code that deals with the render props approach:

      if (typeof children === 'function') {
        return children({ className, ...spread });
      }

When you have more than one child, then typeof children === 'function' will not be true and it won't use the render props approach. In this case, both children just get normal react rendering and trying to render a function doesn't render anything.


Below is a working example that fixes all of these problems by using a single Button child in the clone case and a single function child in the render props case (a function that then renders two Button elements).

import React from "react";
import Button from "@material-ui/core/Button";
import Box from "@material-ui/core/Box";

export default function App() {
  return (
    <>
      <Box color="primary.main" clone>
        <Button>Click</Button>
      </Box>
      <Box color="secondary.main">
        {props => (
          <>
            <Button {...props}> Click </Button>
            <Button color="secondary">Click</Button>
          </>
        )}
      </Box>
    </>
  );
}

这篇关于如何在Material-UI中使用Box组件使用替代按钮?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆