How To Create Masonry And CSS Hybrid Grid Layout

Today’s web design world has become so innovative. Table-based lists with offset pagination are rapidly falling out of favor, while masonry layouts with infinite scroll are now becoming the new trend. You are not aware of it yet? Think Pinterest, Interview Magazine, Windows’ Metro etc. To describe it in words, it’s an almost crazy paving effect whereby variable sized blocks of content are pieced together in an aesthetically pleasing style and often staggered. Masonry style layouts aren’t something new.

How To Create Masonry And CSS Hybrid Grid Layout

So why look at them now? After all there are some great solutions out there that can give you a masonry effect. This is true. However, can we push a pure CSS solution a little further? Can we leverage Flexbox to achieve a more desired effect and push the capabilities a little further?

Well, in this article, we try to provide an in-depth look at masonry layout and its main perks of usage.

Default Situation

Everyone knows that if you want to display a grid of elements (announcement of blog posts, online store goods, galleries, etc.), you’ll face floating and alignment problems where the height of blocks is unspecified.

E.g., indicating the float:left property – even with the same width for all blocks – would lead to the following mess:

How To Create Masonry And CSS Hybrid Grid Layout
Pic. 1 – Default alignment.

Another option is more pleasant to the eye – when the blocks are arranged line-by-line on a vertical grid (frequently used for the goods catalog) or masonry grid with vertical customization of blocks (used for blogs).

How To Create Masonry And CSS Hybrid Grid Layout
Pic. 2 – Line-by-line block layout.
How To Create Masonry And CSS Hybrid Grid Layout
Pic. 3 – Masonry layout.

Responsive grid with line-by-line display of blocks of different heights

Well, it may seem that everything is obvious here. But it isn’t.

Let’s assume we have blocks of the same width, displayed on a 4-column grid and have the float:left property. After every 4th block (the last in line), we use the clear:left property or display each line as a separate block. But for a responsive layout, it’s a doubtful decision to make block-lines with block-columns inside because the layout will be reconstructed and the number of columns will be changed. Moreover, one should be careful when clearing context due to column variability.

How To Create Masonry And CSS Hybrid Grid Layout

Therefore, we proceed as follows. Let’s take a sample layout in which we need to display a maximum of 6 columns and a minimum of one. First, we should ensure that starting from the 7th element, every 6th element is displayed from a new line. Then, due to narrowing of the display area, the rule should be dropped, while another one adopted – every 5th element starting from the 6th one will be placed on a new line and so on, till the layout takes a one-column form.

In the article Responsive Web Design Using Breakpoints, we mostly focused on the principle on which properties of screen size ranges are overlapped. And this is precisely the case when it’s really convenient to use media-queries like "from and to" with properties applied to the strictly specific range.

Before writing the code, let’s denote ranges:

  1. Everything that is more than 1600 pixels – 6 columns.
  2. 1400-1600 – 5 columns.
  3. 1400-1200 – 4 columns.
  4. 1200-900 – 3 columns.
  5. 900-600 – 2 columns.
  6. Less than 600 – 1 column.

When we transform it into CSS, it will look like this:


.element {
    float: left;
    padding: 0 15px;
    margin: 15px 0
}

For definition above 1600 pixels, we need to set a value such that each 6th element starting from number 7 is placed on a new line.

@media screen and (min-width: 1600px) {
    .column:nth-child(6n+7) {
        clear: left
    }
    .column {
        width: 16.666%
    }
}

Our new command works similar to the range of 1400-1600 where every 5th element starting from number 6 is placed on a new line, and so on in descending order.

@media screen and (min-width: 1400px) and (max-width: 1600px) {
    .column:nth-child(5n+6) {
        clear: left
    }
    .column {
        width: 20%
    }
}

Well, the result is as follows:

How To Create Masonry And CSS Hybrid Grid Layout
Pic. 4 – clear:left on every 4th element, starting from the 5th one, we get a four-column grid. The red frame is the border column; the gray color fill is an imitation of the content with unspecified height..

Source 1

At the above layout, we see that the height of the column cells is equal to the height of the content. If you want the height of the columns to be the same (equal to the largest column) in one line, then all you need to do is to indicate the following for the wrap block:


.wrap {
    width: 100%;
    display: -webkit-flex;
    display: -ms-flexbox;;
    display: flex;
    -webkit-flex-wrap: wrap;
    -ms-flex-wrap: wrap;
    flex-wrap: wrap
}

Pseudo-classes: nth-child, mentioned above would be unnecessary in this case (see Source 2).

But this is not quite our topic for discussion because we are most interested in display of brick blocks of different heights (pic.3).

If we want the vertical distances between blocks to be equal, we should use jquery plug-ins instead of css.

Jquery plugins for masonry layouts

There are so many different jquery plugins. They have been there for a long time and have been generally performing well. Masonry, Isotope & Freetile are among the most well-known plugins. Historically, the first and foremost duty of these plugins has been to create galleries. Some of them still don’t go beyond this role, while some acquire more optional features (sorting, animations). If you have a gallery and variegated images by size, then this is the perfect solution you’re looking for. As a rule, it is enough to add a class either to a parent block or to the elements located inside it and then launch the plug-in.

How To Create Masonry And CSS Hybrid Grid Layout

But we are mostly interested in displaying grid tiles of both text and images. Well, yes, they allow to do this indeed, but there is one catch…

At least, all the plugins known to the author are based on the same principle:

With Javascript, a new absolute positioning is set for the elements and coordinates are recalculated. As a result, each of them is assigned with the properties left and top in pixels. When you change the size of the browser window, the absolute values are recalculated.

Although these plugins are of high quality but they sometimes witness some failures in their operations.

1st case: sometimes blocks are placed end-to-end to each other without any margins (probably because the plugin has been triggered just right before all the necessary elements were loaded for correct calculation of position). To overcome this, you can activate plug-in initialization once again after the document has been fully loaded:

$(window).bind("load", function() {
  YourPlugInStart();
});

where pluginStart is the function of plug-in launch.

The second detected trouble stems from the fact that since system resources (all operations occur in the RAM) are required for constant rearrangement of blocks and recalculation of coordinates, the site may hang with high data sufficiency. This almost never happens with desktop versions, but there’s a great chance that it may happen when the site is displayed on an iPhone. Especially if the plugin uses different effects of movement visualizing and block emergence.

Therefore we decided to follow a fundamentally different approach. Although this way is not a universal one but it is less resource-intensive and lightweight in which a simple grid and masonry will be combined. Consequently, positioning issues will be solved by means of CSS instead of JS, which will give additional flexibility to our plugin.

Masonry & Grid Hybrid

As you can see from the title of the chapter, we’ve decided to combine the grid structure of adaptive layout to solve the problems connected with positioning by means of CSS. We’ve also made blocks vertical without changing their coordinates, but placing them in the columns of our layout by using JS.

a) Run

The source code of plugin & sample. Demo.

<link href="anotherbrick.css" rel="stylesheet" type="text/css"/>
<script src="anotherbrick.js"></script>

As in the case with the above-mentioned plugins, we’ve placed tile blocks inside the wrapping block. The parent block is given the the-wall class. Elements which will be further aligned are given another-brick class.

<div class="the-wall">
  <div class="another-brick">...</div>
  <div class="another-brick">...</div>
  ...
  <div class="another-brick">...</div>
</div>

Initialize

AnotherBrick();

b) Operation principle of the plugin & its main perks

After launching JS, the responsive grid is formed with empty columns.

Depending on the width of the display area, the number of columns varies from 12 to 1 by means of CSS (this can be changed. If you have such a need, please, see source).

The borders for transition to a different column number can be changed in the plugin file anotherbrick.css. The whole logic here is:

  • For windows with 2900 pixels, it will be 12 columns (100%: 12 = 8.3333%).

    @media screen and (min-width: 2900px) {
        .brick-col {
            width: 8.3333%
        }
    }

  • If the area is less than 2900 pixels, then we already have 100%: 11 = 9.09% and then the column number 12 should be disabled.

    .brick-col {
        width: 9.09%
    }
    .brick-col:nth-child(12) {
        display: none
    }

  • If the area is less than 2600, similarly, we should define a new column width and remove the column 11.

    .brick-col {
        width: 10%
    }
    .brick-col:nth-child(11) {
        display: none
    }

    And etc. (please, see css-file).

Therefore, we have fully imposed the task of mutual positioning of blocks on css, which means that no calculation of positions of elements is done and extra cpu resources are not used.

How To Create Masonry And CSS Hybrid Grid Layout

We have a grid of empty columns, but we should enter the content in it. Then the plug-in sorts a list of elements alternately arranging them in columns based on the principle: the 1st element in the 1st column, the 2nd element in the 2nd column, etc. When the plug-in reaches the last column, it keeps on filling the elements starting with the 1st again.

But one should keep in mind that the number of columns varies. Therefore, the plugin monitors the situation and as soon as there is transition from one number of columns to another, it rearranges the content in columns.

But one should keep in mind that the number of columns varies. Therefore, the plugin monitors the situation and as soon as there is transition from one number of columns to another, it rearranges the content in columns.

AnotherBrick(N);

where N stands for the number of columns

Summary

Well, our plugin really has no weak point, but rather a technical feature. Due to its focus on the grid structure of layout, it cannot be used for tasks where "bricks" have different width and the layout has no grid.

How To Create Masonry And CSS Hybrid Grid Layout

Questions of this kind are solved using “classic” masonry-plugins. Also one should be realistic: our plugin have no tile customization mechanism with a priority to fill the space as uniformly as possible. It just sorts them (tiles) out by columns. While masonry, isotop and others customize tiles on the priority of maximum density and sometimes can create more visually balanced layout.

Therefore, it’s better to use them in cases when the height of one block is 600 pixels and another is 100 pixels. If the height of blocks doesn’t vary by more than 3 times and there are more than 20 blocks, then the pattern will be the same in all plugins including ours. Major advantages of Another Brick include the css-mechanics, facility, and ability to adapt to user’s needs.

Moreover, there is a chance that the distribution of blog posts with our plugin will be more readable in terms of chronology. Since masonry plugins are placed close to each other, it often occurs that the dates are a bit mixed.

Leave a Reply