It is the received wisdom among software developers, as anyone who has so much as had a conversation with one can testify, that the best way to make progress in learning to programme is to “learn by doing”. I am not here to contest that. On the contrary, as a developer at the beginning of what is clearly going to be a long — possibly life-long — journey of study, I have already experienced first-hand the noticeable acceleration of learning that the project-based education on my Web Development course at allows. Microverse But I have also witnessed how novice web developers, focused only on the end goal of a project, can pick up bad habits and awkward workarounds to problems, becoming over-reliant on familiar but unsuitable techniques while cleaner, stronger and more logical alternatives remain ignored and unused. Simple though it may seem, positioning is one area in which learners of CSS are particularly likely to settle on just one or two preferred methods. As I did with Flexbox positioning, many students become too dependent on one way of placing and moving elements and fail to realise there are other techniques that could make their lives so much easier. And though I will freely admit that it’s not the most glamorous aspect of CSS, I promise you this: if there’s one area of CSS where you want to feel supremely, unassailably confident, it’s positioning. What the skeleton is to the body, CSS positioning properties are to a webpage. All the content, functionality and aesthetics you will ever want to see on your website all depends on that solid structure that your CSS positioning fundamentals provide. So, if you’ve ever found yourself prodding sections of your webpage around pixel by pixel, or wondering if there’s an easier way to fill a responsive navigation bar with equally sized links, then you’re in the right place to fill in the gaps in your knowledge and graduate to true CSS positioning mastery. Let’s begin. Go with the flow Question: How did your page look the last time you forgot to link your HTML and CSS files? In addition to the disappearance of your tastefully selected fonts, backgrounds and borders, you might also have noticed that, in the absence of any CSS positioning properties, a lot of your elements suddenly wanted to queue up along the left-hand side of your screen. Why is that? Well, what you were looking at is something called . It is to a webpage what gravity is to our lives on Earth: a weak force that can very easily be overridden, a force so universal that you would be forgiven for forgetting it’s even there, but in the absence of any interference, it is often the dominant factor in explaining why things move, or why they don’t. “normal flow” How long is a piece of…element? An element is — — only as big as it needs to be. very broadly speaking Contrary to my first impressions, elements don’t just take a random size. Generally, they behave like elastic. First, they wrap tight around their content. Then they conform to any box-model sizing properties they’ve been given, such as width/height and padding. Then they will stop and not ask for a pixel more. Although this is a sound working principle, there are many common exceptions to this elasticity. Elements with defined widths and heights sacrifice their wrapping behaviour, and flexbox and grid items also come to mind as straying very far from this principle. But the first and most obvious exception to this principle of elasticity is block elements. Block vs. Inline: New Kids On The Block and are two types of which is just some jargon that basically means that so-called “block” elements behave and arrange themselves on the page differently to so-called “inline” elements. Block Inline block formatting contexts, Simply put, . In English, each word sits of the previous, while each paragraph sits the paragraph before. That’s because words, like inline elements, can share a horizontal space, while paragraphs and block elements cannot. That explains why, the first time you wrote <h1>Hello World!</h1> and wanted to jazz it up with an aquamarine background, that aquamarine background stretched all the way across the body of the webpage from left to right. block elements behave like paragraphs, while inline elements behave like words to the right underneath As well as demonstrating what a bad choice of colour aquamarine was, this also shows that block elements do wrap around the width of their content but rather, stretch to the width of their parent container. not <h1>, like <p> and <div>, is a block element by default, so despite containing two words, it took the whole width of the container and any subsequent children will, therefore, be forced to sit beneath it. However, don’t forget that even greedy block elements wrap to the of their contents unless instructed otherwise. height Other elements, such as <span> are inline elements by default, shrinking to both the height width of their contents. In fact, inline elements are so “elastic” that their size cannot even be altered with explicit height and width properties! and And although they will grow to accommodate padding, inline elements also ignore top and bottom margins — more on this coming up. Block elements take width and height properties but without them, they will just wrap to the height of their content and stretch to the full width of their container. can However, while <span> is inline by default and <h1>, <p> and <div> are block by default, any element can have its display value defined as either to change its behaviour. Think Inside The Box I’m going to say this once: . Every element is a box Don’t be fooled by the smoke and mirrors of modern web design. If it’s not a box, it’s not an element. If it doesn’t look like a box, it is. This sentence is a box, this paragraph is a box, the images in this article are all boxes, and even the webpage itself is a box. Every one of those boxes is composed of four parts, four sub-boxes, really, sitting one within the other like Russian dolls: the content-box, the padding-box, the border-box and the margin-box. While they are all important, it is margin and padding that we often use when positioning elements. But let’s start at the top. And by that, I mean the middle. The is the heart of the element. When we talk about elements “wrapping” around their content, this is the essential area of content we’re talking about. If it weren’t for padding, this content-area would (normally) be the whole area of the box. What’s padding, you say? Glad you asked. is very simple. It answers the question, “How close should this element wrap to its content?”. The element to take up as little space as it needs to, to wrap as closely to its content as it can. So when padding is 0, there is nothing to stop an element from wrapping right up to its content, and that’s exactly what it will do. But increasing that padding means a distance must be maintained between the content and the element’s border. If an element is wrapped tight and then padding is applied, the total area of the element will be forced to increase, since the content is the same size but now“pushes” the border further from it. But what’s this border, you say? Glad you asked. The separates the “inside” of an element box from the “outside”. It lies on the limits of the element’s area. And, though it is often a very slim area, it’s important to ask: is the border itself inside or outside the box? Glad you asked. The answer is, it can be both. By , the border is considered outside the box, but the box-sizing property can be used to change that, and can make calculations of a box’s true size much easier depending on the situation. content-box Padding wants border default The Margin: No-One’s-Land is the fourth piece of the box model puzzle, and it is possibly the most likely of the four to be used as a positioning tool. Why’s that? Margin In the normal flow context, margin does a similar job to padding, but instead of maintaining a distance between the content and the edges of the box, margin lies the box, keeping boxes at a distance. In order to accommodate this distance that margin demands, elements on the page will shuffle left, right, or whatever direction they need to, to make sure those no-one’s-land distances are maintained. outside other Margins are not collapsable, which means that two margins overlap. If one element’s margin demands that it stay 10px from any other element, while the next element’s margin demands that it stay 15px away from any other element, those two elements will refuse to sit any closer than 25px apart. cannot Position, position, position Now that we’re clear that elements are boxes and that they generally follow this force called “the normal flow”, let’s look at when they don’t. The position property has five possible values, one of which we actually already know: static. is the default value for the position property. It means “just follow the normal flow”. Statically positioned elements are the most obedient of them all. Static The next value is . Relatively positioned elements are also very obedient, but they can be persuaded to break the rules using offset properties like top, right, bottom and left. relative Relatively positioned elements first sit where they should according to normal flow, but from there they will then translate in other directions according to any offset properties it has been given. The first of the truly mischievous position values is . absolute These elements obey offset properties and are . Absolutely positioned elements can’t “see” normal-flow elements at all and their margins won’t push any other elements away (apart from their parent element). only outside the normal flow But if relatively positioned elements take their “normal flow” position as the starting point for offset, ? what do absolutely positioned elements offset from Well, from their closest “non-static ancestor”. That could be their parent element, or it could just be the body. Whichever it is, they act as if they’re the first and only child element of that container and place themselves in its top-left corner and then offset from there as instructed. The fourth position value is . These elements, like their absolutely-positioned cousins, are also out of the normal flow. But while absolute elements position themselves relative to their immediate ancestor, fixed elements position themselves relative to . That’s right. Scrolling around a webpage means nothing to a fixed element. Tell it to sit on the left-hand side of the screen and it will be there. fixed the viewport always The final option for the position property is the youngster of the group. Only arriving on the scene with CSS3, positioning combined the behaviour of relative and fixed positioning. It will remain in its relatively-positioned location, until the user’s scrolling would move it beyond its “permitted” offset (e.g. top: 0px), at which points it “sticks” to the viewport in order to obey that offset rule. sticky So far, our positioning options have been either “in-flow” with margins and padding or “out-of-flow” with non-static positioning and offsets. And that basic information about the natural behaviour of elements . But websites built using only these somewhat awkward positioning methods tend to come out looking a bit…’90s. In case you've forgotten what that looks like, here's the US Geographical Survey's groundbreaking 1994 website: is an absolute must-know Luckily for us, there are now a couple of other major, well-supported positioning techniques that are about as far from “normal flow” and ’90s websites as you can get. Let’s start with grid. Grid and Square It are pretty much the most powerful 2-dimensional positioning system available to a novice web developer. With a grid, you can divide a container into grid rows, grid columns and grid cells of whatever size you choose, and then just tell the child elements which areas to occupy! Grids The other strengths that grid layouts can boast of include their excellent capacity for responsiveness to screen sizes. They can use to define the breadth of rows and columns in terms of the width/height of the container. Or they can use , unique to grids, which are “units of free space” and basically instruct the grid to divide space proportionally between rows and columns that are in fr units. percentage distance units the fr unit untaken The power of grids is in the macro-structure. Many smaller containers don’t need grid positioning when flexbox or normal-flow positioning are quite up to the job. But laying out an entire webpage with margins, offsets, floats, even flexbox, can become insanely complicated, like building a log cabin with matchsticks. By allowing grids to control the large-scale and then fine-tuning positions with padding, margin, offsets, etc., you can play to the strengths of each method and keep your code clean and dependable. Flexbox While grid is a 2-dimensional layout system, positioning is best suited to one-dimensional contexts. flexbox Flexbox containers have a main axis and a cross axis. In a horizontal navigation bar, for example, the main axis would be from left to right, while the cross axis would be from top to bottom. Flex items automatically consume all of the space available to them in the . How the space on the is distributed can be controlled quite precisely with properties like flex-basis and flex-grow, which instruct the flex item how much they should expand to fill empty space. Or the space can be left empty and distributed in gaps between the items, using the justify-content property. With flexbox, an item’s size is less important than its size relative to the space it’s in and to the other items it shares the space with. cross axis main axis Flexbox is brilliant. Combined with media queries, responsive units of measurement, and the flex-wrap property, flexbox layout can give navigation bars and other containers an ability to seamlessly adapt whenever they are stretched or shrunk. However, they really come into their own in one-dimensional layout contexts, between the large-scale structuring that grids excel at and the “finishing touches” shuffling that padding and margin provide. Conclusion I believe the contents of this article represent some of the most important concepts and tools when it comes to CSS positioning, even without going into floats, z-index, or the million little ways that different positioning rules interact — and I am currently discovering at least a handful of these every day. But, even more important than understanding the concepts and tools at your disposal is the instinct for when different positioning methods are appropriate. There are no such things as “good” and “bad” positioning methods, just “good for this” and “bad for that”. Newcomers to web development — and I speak here from first-hand experience — can so easily get carried away by the flashier aspects of CSS, its colours and backgrounds, its videos and images, its fonts and borders, that they neglect to really take the time to understand the positioning mechanics that are at work on every webpage they build. And I think they should. Mastering positioning fundamentals means knowing what your tools are and when to use them. Some of the techniques covered in this article may be totally familiar to you, but I believe that avoiding over-reliance on your most confident areas means diversifying your toolkit, which can only improve the quality of the websites you create and the enjoyment you feel while creating them. I started this piece by invoking that sacred phrase: “learn by doing” and I will conclude by once again saying that I have enormous faith in this idea. Get stuck in. Think of something that you wish existed and be the one to bring it to life. There really is no better way to learn. But to that advice, I would add: Instead of getting stuck in your ways, be curious about other ways. Instead of keeping to what’s comfortable, get comfortable in something else. Don’t negotiate with your weak areas, run right at them! Because in a field like development, there’s always a better way. So go find it. do by learning. Further Reading deserves some kind of award for graphical explanations of flexbox rules. It’s so good. This graphical explanation of flex-box rules CSS-Tricks Thought not “further reading” as such, has been an absolute game-changer for my positioning game. At the click of a button, this browser extension lets you see the outlines of every element on the page your viewing. Thank me later. Pesticide for Chrome These freely available lessons are an excellent resource for more details on , and . Odin Project grids flexbox floats I can also strongly recommend sticking on some good music and playing around with different positioning methods concepts on . Codepen And last but not least, some independent project-work on is a great way to put all that positioning to work. ’s Responsive Web Design Certificate freeCodeCamp Happy Positioning! Previously published at https://medium.com/@__joeburke/the-bare-bones-of-it-mastering-css-positioning-fundamentals-43077f27cbc4