javascript - 将 css transition 应用于元素的宽度,使其覆盖其容器 div [ReactJS] 的 100% 宽度

标签 javascript css reactjs material-ui

import React from 'react';
import PropTypes from 'prop-types';
import SearchIcon from '@material-ui/icons/Search';
import InputBase from '@material-ui/core/InputBase';
import { AccountCircle } from '@material-ui/icons';
import { withStyles, AppBar, Toolbar, Paper, Typography, IconButton } from '@material-ui/core';

const styles = (theme) => ({

    root: {
        borderRadius: theme.shape.borderRadius * 0.5,
        backgroundColor: theme.palette.primary.main,
        display: 'flex',
    },

    logo: {
        borderRadius: theme.shape.borderRadius * 0.5,
        backgroundColor: theme.palette.secondary.main,
        marginTop: theme.spacing.unit * 2,
        marginBottom: theme.spacing.unit * 2,
        marginLeft: theme.spacing.unit * 3,
        marginRight: theme.spacing.unit * 5,
        flex: 0.5,
    },

    logoFont: {
        color: theme.palette.primary.main,
        fontWeight: 'bolder',
        paddingTop: theme.spacing.unit * 0.5,
        paddingBottom: theme.spacing.unit * 0.5,
        paddingLeft: theme.spacing.unit * 2,
        paddingRight: theme.spacing.unit * 2,
    },

    headerPads: {
        paddingTop: theme.spacing.unit * 3,
        paddingBottom: theme.spacing.unit * 2,
        paddingRight: theme.spacing.unit * 10,
        paddingLeft: theme.spacing.unit * 10,
    },

    containerHorizontalAlignment: {
        display: 'flex',
        flexDirection: 'row',
        justifyContent: 'end',
        paddingTop: theme.spacing.unit,
        paddingBottom: theme.spacing.unit,
        flex: 10,
    },

    searchBar: {
        marginTop: theme.spacing.unit,
        marginBottom: theme.spacing.unit,
        marginLeft: theme.spacing.unit,
        marginRight: theme.spacing.unit * 5,
        borderRadius: theme.shape.borderRadius * 0.5,
        backgroundColor: theme.palette.secondary.main,
        width: 'auto',
        /* [theme.breakpoints.up('sm')]: {
            marginLeft: theme.spacing.unit,
            width: 'auto',
        }, */
        display: 'flex',
        flexDirection: 'row',
    },

    searchIcon: {
        color: theme.palette.primary.main,
        display: 'flex',
        alignItems: 'center',
        justifyContent: 'space-between',
        marginLeft: 20,
        height: '100%',
        width: theme.spacing.unit * 7,
    },

    inputRoot: {
        color: theme.palette.primary.main,
        width: '100%',
    },

    inputInput: {
        transition: theme.transitions.create('width'),
        width: 'auto',
        [theme.breakpoints.up('sm')]: {
            width: '25%', //change it to 250(number)
            '&:focus': {
                width: '100%', //change it to 1000(number), it will work fine, but I need percentages. 
            },
        },
    },

    loginButtonContainer: {
         flex: 1,
    },

    loginButton: {
        justifyContent: 'right',
        marginTop: theme.spacing.unit * 0.5,
        color: theme.palette.secondary.main,
    },
});

function ExpandingSearchBar(props) {

    const { classes} = props;

    return (
        <div className={classes.headerPads}>
            <Paper square className={ classes.root }>
                    <div className={classes.logo}>
                        <Typography variant="h5" className={classes.logoFont}>
                            PlaceHolder
                        </Typography>
                    </div>
//Problematic div: the search bar
                    <div style={{border: '1px solid white'}} className={ classes.containerHorizontalAlignment }>
                        <div className={classes.searchBar}>
                            <div className={classes.searchIcon}>
                                <SearchIcon />
                            </div>
                            <InputBase 
                                placeholder='Search'
                                classes={{
                                    root: classes.inputRoot,
                                    input: classes.inputInput,
                                }}
                            />
                        </div>
                    </div>
                    <div className={classes.loginButton}>
                        <IconButton className={classes.loginButton}>
                            <AccountCircle fontSize='large'/>
                        </IconButton>
                    </div>
            </Paper>
        </div>
    );
}

ExpandingSearchBar.propTypes = {
    classes: PropTypes.object.isRequired,
}

export default withStyles(styles)(ExpandingSearchBar);

问题:

  1. styles.inputInput 我已经使用 material-ui 的 theme.transition.create 创建了一个转换,问题是,如果宽度是固定的数字工作正常,如果我将百分比传递给它,组件只有固定宽度,根本没有扩展或过渡。

  2. 还有一个问题是,如果 searchBar 的宽度超过它的父级可以容纳的宽度,它不会将“PlaceHolder”推出 Paper,但会将末尾的按钮推出Paper 元素及其自身会将自身推过右边界。

我使用了 material-ui 中的 theme.create.transitions(),但请建议任何仅使用 CSS 的解决方案。

试一试 here在沙盒中,将沙盒的浏览器窗口切换到全屏。

谢谢

最佳答案

主要问题是您的“searchBar”div 限制了您输入的“100%”的含义。关键是对整个搜索输入使用 InputBase,这意味着对搜索图标使用 startAdornment:

      <div className={classes.searchBar}>
        <InputBase
          startAdornment={<SearchIcon />}
          placeholder="Search"
          classes={{
            root: classes.inputRoot,
            focused: classes.inputFocused
          }}
        />
      </div>

然后对样式进行了一些必要的调整(将一些样式从 searchBar 移动到 inputRoot 以及从 inputInput 移动到 inputRoot):

  searchBar: {
    width: "100%",
    display: "flex",
    flexDirection: "row"
  },
  inputRoot: {
    marginTop: theme.spacing.unit,
    marginBottom: theme.spacing.unit,
    marginLeft: theme.spacing.unit,
    marginRight: theme.spacing.unit * 5,
    borderRadius: theme.shape.borderRadius * 0.5,
    backgroundColor: theme.palette.secondary.main,
    color: theme.palette.primary.main,
    transition: theme.transitions.create("width"),
    width: "auto",
    [theme.breakpoints.up("sm")]: {
      width: "25%" //change it to 250(number)
    },
    "&$inputFocused": {
      [theme.breakpoints.up("sm")]: {
        width: "100%" //change it to 1000(number), it will work fine, but I need percentages.
      }
    }
  },
  inputFocused: {},

这是对沙箱的有效修改:

Edit Search Grow on Focus

关于javascript - 将 css transition 应用于元素的宽度,使其覆盖其容器 div [ReactJS] 的 100% 宽度,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/54957126/

相关文章:

reactjs - 类型 'Promise<(string[] | undefined)[]>' 缺少类型 'Etablissement[]' : length, pop、push、concat 等 29 个属性

javascript - 如何加速 javascript 表格渲染?

javascript - Yeoman 使用 args 通过代码调用生成器

css - body 和 child 身上带有 flexbox 的粘性页脚

html - 在 HTML 中呈现字符串并保留空格和换行符

reactjs - 为什么 select() 不能在 Safari 上使用 ReactJS 工作?

javascript - 使用浏览器后退按钮返回时如何将对象作为 Prop 传递给先前的 react 组件( react , react 路由器)

javascript - 为什么 d3 在第二次更新时删除数据

javascript - 从 KnockoutJS 中动态生成的输入中获取值

asp.net - 右对齐 statictextfield 控件的问题