mui / material-ui

Material UI: Comprehensive React component library that implements Google's Material Design. Free forever.
https://mui.com/material-ui/
MIT License
93.96k stars 32.27k forks source link

[material-ui][Masonry] layout forms a single column when the first item is hidden #42611

Open Fanzzzd opened 5 months ago

Fanzzzd commented 5 months ago

Steps to reproduce

Link to live example: https://react-nxweja.stackblitz.io/

Steps:

  1. Create a Masonry layout using Material UI.
  2. Hide the first item in the Masonry layout using CSS or JavaScript.
  3. Observe the behavior of the remaining items in the layout.

Current behavior

When the first item in the Masonry layout is hidden, all the remaining items are forced into a single column instead of distributing evenly across the available space.

Expected behavior

The remaining items should adjust and distribute evenly across the columns, maintaining the Masonry layout even if the first item is hidden.

Context

I am using the Masonry component to create a visually appealing grid layout for a photo gallery. The layout should remain balanced and distribute items evenly across columns. However, when the first item is hidden, it disrupts the entire layout, forming a single column, which is not the intended behavior and affects the gallery's visual consistency.

Your environment

System: OS: macOS 14.1.1 Binaries: Node: 19.8.1 - /usr/local/bin/node npm: 9.5.1 - /usr/local/bin/npm pnpm: 9.1.2 - /usr/local/bin/pnpm Browsers: Chrome: 125.0.6422.142 Edge: Not Found Safari: 17.1 npmPackages: @emotion/react: ^11.11.4 => 11.11.4 @emotion/styled: ^11.11.5 => 11.11.5 @mui/base: 5.0.0-beta.40 @mui/core-downloads-tracker: 5.15.19 @mui/icons-material: ^5.15.19 => 5.15.19 @mui/lab: ^5.0.0-alpha.170 => 5.0.0-alpha.170 @mui/material: ^5.15.19 => 5.15.19 @mui/private-theming: 5.15.14 @mui/styled-engine: 5.15.14 @mui/system: 5.15.15 @mui/types: 7.2.14 @mui/utils: 5.15.14 @types/react: 18.2.8 => 18.2.8 react: ^18.3.1 => 18.3.1 react-dom: ^18.3.1 => 18.3.1 typescript: 4.8.4 => 4.8.4

Search keywords: Masonry layout, single column, hidden item, layout issue

DiegoAndai commented 5 months ago

Hey @Fanzzzd, thanks for the report!

May I ask you to share the code of the live example? If you could share the stackblitz in editor mode, that would be great. This will help us understand the issue better.

mbrookes commented 5 months ago

Interestingly it only affects the initial layout. It's fine if it's hidden after it's rendered. (Literally "turn it off and on again" in dev-tools.)

https://stackblitz.com/edit/react-hhacxp?file=Demo.tsx

Fanzzzd commented 5 months ago

Hi @DiegoAndai ,

Here is the editor link to the live example: https://stackblitz.com/edit/react-nxweja?file=Demo.tsx

I observed the same behavior as @mbrookes mentioned. Once the Masonry layout is loaded, setting any element to display: none does not affect the layout.

Issue Analysis: The issue where the Masonry layout forms a single column when the first item is hidden initially occurs because the layout calculations are based on the first child element. If this element is hidden, its height is zero, which triggers the skip condition. This condition is intended to handle cases where images haven’t loaded yet but also inadvertently causes problems when the first element is simply hidden.

Solution: I modified the code to identify the first visible child instead of assuming the first child is visible. This ensures that the layout calculations use a visible element, avoiding the height zero issue. Additionally, I added checks to skip any children that are not visible during layout calculations, preventing them from affecting the layout logic.

With these changes, the Masonry layout should initialize correctly even if the initial item is hidden. If you like you can give it a try and plz let me know if it works!

DiegoAndai commented 5 months ago

Thanks for the live example @Fanzzzd. Accepted as a bug.