[Toy Browser] Layout and Rendering

Jijie Liu
Jijie Liu
Oct 25, 2020 · 5 min read

Introduction: [Toy Browser] Introduction

Previous article: [Toy Browser] HTML parsing and CSS computing

Keywords: CSS, DOM Tree, image rendering

In previous article, the toy browser parsed and tokenized a HTML file. After that, it built a DOM Tree mounted with all the computed CSS rules. A question is remained: How to render a div having a CSS flex: 1 ?

In this article, the last one of toy browser series, I will resolve this problem, and render an image from DOM Tree.

CSS Layout

There are several kinds of CSS layouts:

To make the toy browser simple, I will focus on Flexbox, which is very useful in daily work. There is an awesome article that explains how Flexbox works: A Complete Guide to Flexbox. If you are not familiar with Flexbox, please read it. The code of the function layout will help you to understand this part, too.

The general idea of this part is to translate the rules of Flexbox into 10 properties:

The flex model

They are well explained by MDN. Here, mainSign is a boolean. If the writing mode is from left to right on the main axis, it will be true. mainBase is the starting position of flex item in the flex container of the main axis. It is the same for the cross axis.

Having the general idea, let’s dive deeper to understand how the toy browser deals with Flexbox. In general, it takes 3 steps to calculate Flexbox.

When the HTML Parser is in endTag step during the tokenization, it will call the function layout to translate CSS layout, which is Flexbox in our toy browser. A node of DOM Tree is sent to the function.

When the function layout meets a node with display = flex , it knows that the current node and its children follow the layout of Flexbox. It will start translating.

Before the calculating, it determines the main axis and cross axis by flewDirection .

Calculating of flex container’s size

The flex container is saved in an array, call flexLines . Each item in it is a “line” of flex items. Flexbox is responsive, it will change line automatically when there are too many items in a line. The notion “line” help us deal with changing line.

There are only two cases that Flexbox will not change line:

style of flex container

Calculating of main axis

Once the flex container’s size is calculated, the function layout starts to calculate flex items by main axis. It reads two pieces of information: flex in flex item or justify-content in the flex container. As the result, for row mode, the height and width of each flex item will be calculated.

If the flex items have the attribute flex , the function layout needs to know the total of the flex in the flex container, and split the main axis space by the proportion of space that each flex item has. For example:

<div style="display: flex;">
<div style="flex: 1;">1</div>
<div style="flex: 2;">2</div>
</div>

The first div takes one third of the flex container’s main axis space, while the second takes two third.

style of a flex item with flex:1, its position has been calculated

If the flex container has the attribute justify-content , the function layout calculates the start point of each flex item and the space between 2 flex items on main axis. These 2 variables are depended on the value of justify-content , such as flex-start , flex-end , center , space-between , space-around .

Calculating of cross axis

Once the calculation on the main axis is finished, the function layout starts to calculate flex items by cross axis. This time, the function checks align-self of flex item and align-content of flex content. As the result, for row mode, the top and bottom of each flex item will be calculated.

Similar to justify-content , align-content helps define the start point of each flex item and the space between 2 flex items on cross axis. It has the value, like flex-start , flex-end , center , space-between , space-around, stretch .

With the start point and the space, the function continues calculating using align-self . It has the value, like flex-start , flex-end , center , stretch . Combine align-content and align-self , the cross axis is finally calculated.

An example is as followed. The height, width, top, bottom of a flex container and one of its flex item are calculated.

The height, width, top, bottom of a flex container and one of its flex item are calculated

Rendering

With the information of height , width , top , bottom , the toy browser can render the image easily. I used a package images.

In the demo, the toy browser initialise the viewport with 800px width and 600px height. Its background color is black.

The flex container has the white background color. It has 3 children.

As the result, the width of the blue div is twice as the green one.

the image of demo rendered by the toy browser

Here is the HTML file, and the code of rendering.

Conclusion

In this article, I presented how a toy browser gets the height , width , top , bottom from Flexbox, and renders an image with this information. For now, the toy browser works, but it’s very naive. It can’t deal with many basic layout properties, such as margin , padding , etc.

In this toy browser series, I presented the workflow of a browser:

Hope this series help you understand how the browser works.

Thanks for reading, and see you next time.

The Startup

Get smarter at building your thing. Join The Startup’s +800K followers.

The Startup

Get smarter at building your thing. Follow to join The Startup’s +8 million monthly readers & +800K followers.

Jijie Liu

Written by

Jijie Liu

Developper in Paris, interested in Big Front-end, Full Stack, Explainable AI. Try to introduce AI into Full Stack workflow

The Startup

Get smarter at building your thing. Follow to join The Startup’s +8 million monthly readers & +800K followers.

Medium is an open platform where 170 million readers come to find insightful and dynamic thinking. Here, expert and undiscovered voices alike dive into the heart of any topic and bring new ideas to the surface. Learn more

Follow the writers, publications, and topics that matter to you, and you’ll see them on your homepage and in your inbox. Explore

If you have a story to tell, knowledge to share, or a perspective to offer — welcome home. It’s easy and free to post your thinking on any topic. Write on Medium

Get the Medium app

A button that says 'Download on the App Store', and if clicked it will lead you to the iOS App store
A button that says 'Get it on, Google Play', and if clicked it will lead you to the Google Play store