Реализуйте глобальную тему в React Material-UI

Я немного смущен темой React Material-UI.

Я попытался настроить его как можно проще, но, похоже, мне не удалось заставить его работать как-то.

Ниже вы можете найти мой код:

start.tsx

const theme = createMuiTheme({
    palette: {
        type: 'dark',
        primary: blue,
        secondary: lightGreen
    }
})

ReactDOM.render(
    <ThemeProvider theme={theme}>
        <BrowserRouter>
            <App />
        </BrowserRouter>
    </ThemeProvider>
    ,
    document.getElementById("root")
)

UserInterfaces.scan();

app.tsx

export class App extends React.Component<IProps, IState> {

    constructor(props) {
        super(props);
        this.state = {
            menu: null
        }
    }

    render() {
        if (!this.state.menu) {
            this.login();
            return <div>Loading ... </div>
        } else {
            return <div className="hx-top-frame">
                <div>
                    <MenuBar menuList={this.state.menu} />
                </div>
                <div>
                    Content here
                {/* <Content /> */}
                </div>
            </div>
        }
    }
}

menubar.tsx

export class MenuBar extends React.Component<IMenuProps, IMenuStates> {

    constructor(props) {
        super(props);
        this.state = { expanded: "" };
    }

    private setClose() {
        this.setState({ expanded: "" });
    }

    public render() {
        let menulist: IMenuArray[] = this.props.menuList.map<IMenuArray>(item => {
            return {
                path: item.path,
                icon: item.icon,
                link: Util.hyphenate(item.path)
            }
        })
        return <nav className="hx-menu">
            <Hidden smUp>
                <Drawer variant="temporary" anchor='left' open={this.state.expanded != ""} onClose={this.setClose.bind(this)} className="left-drawer">
                    <SubMenu menu={menulist} />
                </Drawer>
            </Hidden>
            <Hidden xsDown>
                <Drawer variant="permanent" anchor='left' open={this.state.expanded != ""} onClose={this.setClose.bind(this)} className="left-drawer">
                    <SubMenu menu={menulist}></SubMenu>
                </Drawer>
            </Hidden>
        </nav >
    }
}

submenu.tsx

class SubMenu extends React.Component<ISubMenuProps, IMenuStates> {

    constructor(props) {
        super(props);
        this.state = { expanded: "" };
    }

    public render() {
        let submenu: IMenuItems = {};
        let menuitems: IMenuArray[] = [];
        this.props.menu.forEach(menu => {
            let items = menu.path.split("/");
            let parent = items.length > 1;
            let name = items.shift();
            let child = items.join("/");
            if (!parent) {
                menuitems.push({ path: name, icon: menu.icon, link: menu.link });
            } else {
                if (!submenu[name]) submenu[name] = [];
                submenu[name].push({ path: child, icon: menu.icon, link: menu.link });
            }
        })

        return <List>
            {Object.keys(submenu).map(name => {
                let menu = name.split("/").shift();
                return <ListItem button className="hx-submenu" key={"m-" + name}>
                    <span className="hx-nowrap" onClick={() => { this.setState({ expanded: this.state.expanded == name ? "" : name }) }}>
                        <ListItemText primary={name} key={"t-" + name} />{this.state.expanded == name ? <ExpandLess /> : <ExpandMore />}
                    </span>
                    <Collapse in={this.state.expanded == name} timeout="auto" unmountOnExit className="hx-submenu">
                        <SubMenu menu={submenu[name]} />
                    </Collapse>
                </ListItem>
            })}

            {menuitems.map(item => {
                return <ListItem button component={RouterLink} to={item.link} key={"i-" + item.path}>
                    <ListItemText primary={item.path} className="hx-menu" key={"l-" + item.path} />
                </ListItem>
            })}

        </List>
    }
}

И вот результат.

Это когда меню полностью свернуто. Результат

И это когда все расширяется. Меню открыто

Теперь мои вопросы:

  1. Почему правая панель светло-серая? Как изменить панель меню на синий цвет?
  2. Мне нужно, чтобы ящик был открыт всякий раз, когда у окна достаточно ширины. Я могу сделать скрытую часть, но почему она отображается поверх моей части контента? Как сделать стойким слева?
  3. Почему меню расширяется по горизонтали? Как заставить его расширяться по вертикали?
  4. Я не хочу делать макет для каждого компонента, и поэтому мне не нужен стилизованный компонент. Только одна глобальная тема, которую я буду использовать в своем проекте. Как это сделать? Я следовал примеру документации, но он все еще был похож на приведенные выше примеры. Я, кстати, не совсем понимаю этот документ, так как он имеет тенденцию использовать функции, а все мои проекты основаны на классах.

Песочница кода: https://codesandbox.io/embed/theme-test-gwutc

Спасибо.


person Magician    schedule 19.08.2019    source источник
comment
Помимо вопросов по глобальной теме. Я думаю, что вопросы по ящику должны быть отдельными. Не входит в тот же вопрос.   -  person minus.273    schedule 19.08.2019
comment
@ minus.273 Думаю, дело в том, что код не правильно реализует? Или я должен сделать другую тему для ящика, чем те, которые используются по умолчанию?   -  person Magician    schedule 19.08.2019
comment
Можете ли вы предоставить ссылку codeandbox с кодом?   -  person Ido    schedule 19.08.2019
comment
@Ido попытается переписать код. Я отправлю ссылку, когда закончишь   -  person Magician    schedule 19.08.2019
comment
Добавлена ​​песочница @Ido   -  person Magician    schedule 19.08.2019


Ответы (2)


Я отвечу 1 и 4, так как пока я не знаю ответов на 2, 3.

  1. Панель светло-серая, потому что это цвет бумаги по умолчанию (кассета использует бумагу под капотом).
    palette.primary не влияет на бумагу
    Чтобы изменить цвет фона бумаги глобально, вы можете сделать следующее:

    const theme = createMuiTheme({
      palette: {
        type: "dark",
        primary: blue,
        secondary: lightGreen,
        background: {
          paper: "blue" // drawers (and papers) will be blue because of this line.
        }
      }
    });
    
  2. Вы можете очень легко применить глобальную тему ко всем компонентам пользовательского интерфейса материала. Вы уже делаете это, обертывая свое приложение с помощью ThemeProvider, все, что вам нужно сделать, это правильно отредактировать свою тему.
    например: если вы хотите переопределить цвет фона ящиков по умолчанию, вы также можете сделать это так (лучше, чем вариант 1 выше, потому что он не применяется для бумажных компонентов):

    const theme = createMuiTheme({
      overrides: { // you declare you override default material-ui styles
       MuiDrawer: {
         paper: {
           backgroundColor: 'blue',
         }
       }
      }
    });
    
person Ido    schedule 19.08.2019
comment
Я имел в виду правую панель. Не темно-серый, а светло-серый. - person Magician; 20.08.2019
comment
Не могли бы вы пояснить, о какой панели вы имеете в виду? в вашемcodeandbox я вижу только одну панель, закрепленную слева. только когда я нахожу или нажимаю на нее, она становится светло-серой - person Ido; 20.08.2019
comment
Тот, что за левой панелью. - person Magician; 20.08.2019

Я решил их все. Номер 1 и 4, как ответил @ido.

Ответ номер 2, использующий решение @ido, заключается в том, чтобы поставить display:flex и установить фиксированное значение ширины бумаги.

И это ниже ответ на номер 3.

submenu.tsx

.
.
<li>
    <ListItem button className="hx-submenu" key={"m-" + name}>
        <ListItemText primary={name} key={"t-" + name} onClick={() => {
            this.setState({
                expanded: this.state.expanded == name ? "" : name
            });
        }}
        />
        {this.state.expanded == name ? <ExpandLess /> : <ExpandMore />}
    </ListItem>
    <Collapse
        in={this.state.expanded == name}
        timeout="auto"
        unmountOnExit
        className="hx-submenu"
    >
        <SubMenu menu={submenu[name]} />
    </Collapse>
</li>
.
.

Проблема была в том, что я поместил <Collapse> внутрь <ListItem>. Поэтому я не вижу необходимости в <span>, и я удалил его.

Кодовый код обновлен на исправленный.

person Magician    schedule 26.08.2019