Network Security Internet Technology Development Database Servers Mobile Phone Android Software Apple Software Computer Software News IT Information

In addition to Weibo, there is also WeChat

Please pay attention

WeChat public account

Shulou

How to modularize CSS preprocessing language

2025-01-17 Update From: SLTechnology News&Howtos shulou NAV: SLTechnology News&Howtos > Development >

Share

Shulou(Shulou.com)06/02 Report--

This article introduces you how to carry out the modularization of CSS preprocessing language, the content is very detailed, interested friends can refer to, hope to be helpful to you.

Writing css is a common and frequent work in the front-end work. Because css is not a language, it is somewhat crude in program design. For small projects, the amount of css is not large, the problem is not highlighted, and if you want to develop and maintain a larger project, you need to manage and regulate css, otherwise there will be irreparable consequences.

Background

redundancy. Although we euphemistically share the volume of common by defining public and private modules, the volume of common is still too large, and from a design point of view, we should refine as many public modules as possible in order to better achieve reuse. Ideally, all modules are stored in a common library and transferred directly from the library where they are needed. This good wish is not impossible, with the help of preprocessing language, we can easily do it.

Preprocessing language is a css-like language, we know that css itself is not a language, and the birth of preprocessing language is to fill this part of the language function. It realizes the definition of variables, functions and mixtures, as well as the functions of file reference, merging and compression, so that css can also be object-oriented and cope with complex and huge business.

At present, there are two popular preprocessing languages: less and sass. As a study, you can get started with both, and as a job, try to be familiar with one. I often use sass, so the following content is introduced in sass as the basic language, and there are a lot of similarities in features, so you don't have to worry about the differences in implementation.

Sass

You can go to the official website (English) or w3cplus sass guide (Chinese) to check and learn the basic grammar. We will simply go through it here and talk about some of the contents we need to use.

Sass has two suffix files: one suffix is sass, without braces and semicolons; the other is the scss file we use here, which is similar to the css file format we usually write, using braces and semicolons. All the sass files mentioned in this tutorial refer to files with the suffix scss. It is also recommended to use a file with the suffix name scss to avoid errors in the strict format of the sass suffix name. -- extracted from w3cplus sass guide

1. Nesting (a very important feature)

There are two kinds of nesting of sass: one is the nesting of selectors, and the other is the nesting of attributes. We usually talk about or use the nesting of selectors. -- extracted from w3cplus sass guide

Selector nesting refers to nesting one selector in another to implement inheritance, thereby enhancing the structure and readability of the sass file. In selector nesting, you can use & to represent the parent element selector. -- extracted from w3cplus sass guide

/ / index.scss. G-index {.... G-hd {.... M-nav {...}}. G-bd {.... M-news {...}}. G-ft {.... M-copy_right {...}}. M-dialog {display: none & .z-active {/ / pay attention to the usage of & here display: block;}}

After compilation:

/ * index.css * / .g-index {...}. G-index. G-hd {.}. G-index. G-hd. M-nav {.}. G-index. G-bd {...}. G-index. G-bd. M-news {. G-index. G-ft {. G-index. G-ft. M-copy _ right {...}. G-index. M-dialog {display: none } .g-index .m-dialog.z-active {/ / notice the compilation result of & here display: block;}

Isn't it awesome? You don't have to copy and modify a lot of selectors over and over again, and you don't need to sort out the relationships between them, you just need to nest them, and all the relationships are as straightforward as looking at dom! Liberate the hands and eyes, and improve efficiency at the same time. It is worth noting that when we write sass, we should try to keep the nesting order of sass consistent with dom. Note that the nesting order is consistent, not hierarchical, because not all elements in dom need to be styled.

Let's mention another scenario to show that the nested writing of sass is good for maintenance. Suppose there was a module m-article_box under g-bd, but now we want to migrate m-article_box from g-bd to g-hd (of course, this requirement is unreasonable). Let's take a look at the original code:

Index * * article

Article title A brief introduction to 1 2 3 4. G-bd {...} .g- Bd. M-article_box {...}. G-bd. M-article_box .hd {...}. G-bd. M-article_box .bd {...}. G-bd. M-article_box .bd .list {...}. G-bd. M-article_box .bd .list .item {...}. G-bd. M-article_box .b d .list .item .cover { ...}. G-bd. M-article_box .bd .list .item .info {...}. G-bd. M-article_box .bd .list .item .info .title {...}. G-bd. M-article_box .bd .list .item .info .desc {...}. G-bd. M-article_box .ft {...}. G-bd. M-article_box. Ft .page {...}. G-bd. M-article_box .ft .page .pg {...}

In css's way, we have to copy all the parts related to m-article_box from g-bd to g-hd. This is still under the condition that the writing of the module conforms to the specification, and if the writing of this module does not conform to the specification and does not hang all the structures under the m-article_box class, it will be a disaster ~ and now using sass, we only need to cut the whole block of m-article_box from g-bd to g-hd (here is a large amount of work to highlight the modification. I specially wrote the whole module structure-- not to make up the word count. ):

/ / before modification. G-hd {...}. G-bd {.m-article_box {.hd {...} .bd {.list {.item {.cover {...} .info {.title {. .desc {...} .ft {.page {.pg {...}} / / modified .desc {.m- Article_box {.hd {...} .bd {.list {.item {.cover {...} .info {.title {...} .desc {. ..} .ft {.page {.pg {...}. G-bd {...}

It is very convenient and not easy to make mistakes.

2. Variable (variable)

Let's go straight to the code:

/ / index.scss $fontSize: 16px; $grey: # ccc;. M-nav {font-size: $fontSize; color: $grey;}

Compilation result:

/ * index.css * / .m-nav {font-size: 16px; color: # ccc;}

People who have written code are familiar with the use of parameters, too simple and straightforward do not want to say too much, they understand it.

3. Function (function)

/ / pixels to rems @ function rem ($px) {@ return $px / 640 * 16remr;}

It's too simple. I don't want to say too much. I know it.

4. Mix (mixin)

Mixing, as the name implies, means mixing. That is, we can define a block of code in advance and include it where it is needed, and this code will not appear in the compilation file before the reference, that is, nothing will be generated.

This is also a very important feature! We know that common is very large, and the fundamental reason for its large size is that it stores a lot of modules. Let's imagine that if every module is packaged into mixin, won't common lose weight successfully? After years of stubborn illness, there is nothing more surprising than to see hope. Let's get in the car:

/ * common.css * / .m-nav {...}. M-news {...}. M-copy_right {...}

After transformation

/ / common.scss @ mixin m-nav {. M-nav {...}} @ mixin m-news {. M-news {.}} @ mixin m-copy_right {. M-copy_right {...}} / / index.scss. G-index {@ include; nav@ include MMI newsletter; @ include Mcopycopyrights;}

5 、 import

Does this attribute look familiar? Yes, in fact, css itself has this property implementation, and we can use import directly in the css file to introduce other files. So what's the difference between css's import and sass's import? In terms of meaning and usage, there is no difference, but the difference lies in the working principle. Css's import is blocked, while sass's import is actually merging files after compilation. * only produces one css file, while css does not merge, so there are as many files as you want.

Note:

The suffix can be omitted only when import is a .sass / .scss file. If you are directly import a .css file, complete the filename.

The semicolon after import; don't leave it out, it will make an error.

Sass if the import is a .css file, then its function is the same as the css native import function, only when import a sass file, is the merge file.

As follows:

/ / index.scss @ import 'common'; @ import' a.css'

Compilation result:

/ * index.scss * / .m-nav {...}. M-news {.}. M-copy_right {...} @ import url ('a.css')

There is a reason why css's import is not widely used. We can guess how it works: after a.css import b.css, when the browser loads the a.css in the page, it is ready to render the page according to the contents of a.css. Just parsed to the * line, it found that a.css also import a b.css, so it had to put down a.css (both blocking a.css) and load b.css until b.css loaded, and parsed it first. And then I started to come back to parse a.cssmurf-God knows if b.css will import c.css again. This directly leads to the lag of rendering work and leads to performance problems.

To be honest, I might as well use two link tags to load a.css and b.css synchronously, which will be more efficient.

So css's import is basically an abandoned attribute.

The main benefit of sass's import is that it merges files and reduces requests. Pages that used to require several css files for link are now needed only one.

Modularization

Finally, let's get down to business. First of all, let's review what problems we left behind from the modular project we built on the basis of specifications in the previous section.

Redundant and bulky common

Using cm- module to distinguish m-module makes the transition from m-module to cm- module more tedious in the later development process.

……

It seems that there are not many problems, and we can solve them one by one.

For convenience, here we call the scss file corresponding to each page page scss; and the code that compiles variables, functions, mixtures, etc. (without being referenced or executed) that does not produce actual content is called definition class code, then the corresponding other content is the actual content code.

1 、 mixin.scss

We know that, on the one hand, adding too many modules to common will eventually lead to excessive volume of common and make resources redundant, on the other hand, in order to facilitate maintenance, we hope to publicize as many modules as possible.

This is a contradiction that cannot be solved by css alone, but sass can! If we use mixin instead of writing modules, because mixin does not generate code directly, but through active references to generate the corresponding content, then in theory, common can store more modules without taking up any space!

Note that in theory, in practice, if the file is too large, it will inevitably be limited by naming conflicts, but this is not a big problem. )

Just do it, let's package all the modules in common into mixin:

/ * common.css * / .m-nav {...}. M-news {...}. M-copy_right {...}

After transformation

/ / common.scss @ mixin m-nav {.m-nav {...}} @ mixin m-news {.m-news {...}} @ mixin m-copy_right {.m-copy_right {...}}

The calling method is as follows:

/ / index.scss @ import 'common'; / / remember to introduce common. G-index {@ include Mmurnave; @ include Mmuri newsletter; @ include Mcopycopyright newsletter;}

Originally, we would have referenced common first and then page css in every page that needed a common module, but now we just need to directly @ import common; in the page scss.

Use common:

Index...

After the transformation:

/ / index.scss @ import 'common'; index...

Very *

At least so far.

Let's think about a question: does common have anything other than storage modules? The answer is yes, you must know that there is something called css reset (or normalize.css), which must be global; in addition, if it is a background management system, there may be Bootstrap. Of course, there are also some custom global styles, such as the common .clearfix, and so on.

These things are also stacked in common at the moment, and it makes sense because they are all global styles. But compared to mixin, the actual content code is very small, there is a sense of drowning, making the whole common look like there is only mixin. But the role of these actual content codes is very important. In order to make the composition of common more intuitive, we extract all the mixin, store it separately in a file called mixin.scss, and then reference it in common, so that the management of mixin is more standardized, and the structure of common is clearer.

There is another important reason for pulling away from mixin, and as we'll talk about later, we want mixin to be a purely defined class code file that can be referenced anywhere without generating redundant code.

Originally, we would have referenced common first and then page css in every page that needed a common module, but now we just need to directly @ import mixin; in the page scss.

Use mixin:

/ / index.scss @ import 'common'; / / introduce common. If necessary, you can also introduce mixin @ import' mixin'; / / mixin. G-index {...} index in common.

2 、 common.scss

OK, now that we have removed the mixin, let's go back to what it should be like in the common,common. We mentioned a little bit about the above, let's expand it.

2.1css reset (normalize)

We know that browsers vary from browser to browser, and the default styles vary from browser to browser, such as the default inner margin of body, the default inner margin of p tag, and ul/ol, etc. These inconsistent default styles often give us a headache, so someone came up with the idea of eliminating them as soon as we started writing styles, which led to the very popular reset.css.

The original reset.css was simple, something like this:

Html, body, H2, h3, h4, h5, h6, H7, div, dl, dt, dd, ul, ol, li, p {margin: 0; padding: 0;}

Yes, almost all the tags that can be used are given the inner and outer margins, which is simple and rough, so that all the tags are unified, and they are uniform in different browsers.

Everyone has their own additions to the other parts, for example, someone will define all the font sizes of h2~h7 to ensure that they have a uniform size in different browsers, someone will set a uniform font color and hover effect for the a tag, and so on.

Good, nothing wrong with it. We collectively call these css reset, then uniformly encapsulate them into a file called reset.css, and then refer to each page.

This method has always been very practical, and everyone uses it in the same way, and there has been no problem. It's just that someone later suggested that this method was too rude (even distressed by the browser). No, no, no. And it will reduce the performance of page rendering, and most importantly, it makes the tags that we originally designed to express all kinds of meanings become meaningless.

That makes sense. What's the point if everyone in your family has different names but looks the same?

As a result, the purpose of normalize.css,normalize is also to unify the different default styles under each browser, but it is not simply to rudely wipe them all, but according to the specification, to artificially "righten" those default styles that do not conform to the specification, so as to achieve the purpose of unifying the default style of each browser while retaining the original characteristics of each tag.

We cannot say whether reset and normalize are good or bad, we can only say that each has its own characteristics and functions, and they both exist to solve the same problem.

2.2, plug-in

Generally speaking, a ui plug-in will include at least one css file, such as bootstrap, datepicker, and so on. Assuming that our project needs to use bootstrap as the basic framework for rapid development, then we need to introduce bootstrap.min.css and, of course, bootstrap.min.js into the project globally. When it comes to global exposure, we think of common in our time, and yes, we can introduce it in common.

Someone asked, how to import the .css file of the plug-in? Well, just change the extension to .scss. Scss is compatible with native css syntax.

So in the end, our common looks something like this:

/ / common.scss @ import'. / reset'; @ import'. / bootstrap.min'; @ import'. / mixin'

In fact, if we don't need to use the variables and mixin in mixin.scss, we don't have to refer to it.

Then our page scss should look like this:

/ / index.scss @ import'. / common'; @ import'. / mixin';. G-index {...}

Clean and tidy.

3. Mixin writing specification

Every time we add a new role, we have to set specifications for it in time so that it doesn't mess up according to our expectations. Let's next summarize the writing specifications of mixin.

Scenario 1: there are three files in the project: mixin.scss, a.scss (assuming this is a function file) and index.scss. A variable $fontSize is defined in mixin and a variable $color: # ccc is defined in 16pxposition hand.a We reference both files in index, so we can use the variables $fontSize and $color directly in index-- I mean, although we don't see the declaration and definition of these two variables in index, they just exist.

Is this a good thing or a bad thing? My gut tells me there might be a problem. Yes, is this very similar to the pollution we discussed before? It's just that after we referenced common, index has already taken up a lot of module names without writing anything, but now it takes up a lot of variable names of index because of referencing other files. In addition, from a maintenance point of view, this is also problematic. If I don't tell you in advance, or if you haven't seen mixin and an in advance, do you know where the $color in index comes from? Suppose we need font size, do you know which file to modify? In addition, how can you ensure that there is a variable with the same name between mixin and a when they are referenced at the same time? So who covers who? These problems may seem small, but when your project is large, it can be an irreparable disaster (scare who? ).

Scene 2: suppose our project has a theme color, border, tab background, navigation bar background, and font color, etc., are all this theme color, in order to facilitate use, do not want to always use the color picker to take the value, so we define a global variable $color: # ff9900 in mixin, and then we can happily use it everywhere!

The whole website has been developed, and a month later, the designer suddenly came to you and said: "the boss said that this theme color should be changed, it's a little corny, let's change it to a big red." So you open mixin reluctantly but happily inside, change the value of $color to bright red, and then ostentatiously say to the designer, "it's a good thing I'm prepared. Take a look." Save, open the page, the designer and your face are green, the page is so ugly, some words were originally the theme color, but the background is red, but now a change, the whole block has become red, the content is not clear, some borders were originally red, but the font is the original theme color, but now a change, the border and the font have become red.

Designer: "No, I just want to change the background color."

You: "didn't you say change the theme color? that's all the places."

Designer: "No, just change the background."

You: "No way." no, no, no. "

Designer: "Why not, isn't it just to change the background color? you can change it back as you set it."

You: "it's not as simple as you think." no, no, no. "

……

Well, I'm just trying to scare you, and it doesn't matter if you're good at it.

So we need to manage (global) variables, just as we used to manage mixin, we can't define where we want to, and we can't modify a global variable all the time:

Global variables are only defined in mixin, and variables defined by other scss files (whether exposed globally or locally) are treated only as local variables and are not used outside the current file (even if they can be referenced).

Direct import mixin where you need to use global variables

Generally speaking, global variables should be defined cautiously, and the number of global variables should be as small as possible.

Do not change as much as possible, if the requirements change, unless you are sure of the use, add a global variable to gradually replace the areas that need to be modified.

Do not use too general nouns as global variables, such as color, it is recommended to directly use the description of the color value, such as $orange: # ff9900, which makes it easier for us to expand in maintenance. If the color value needs to be modified, but not everything needs to be modified, then we can define a new variable to extend it, such as $red: red.

These points are a bit erratic, in fact, it is really difficult to understand why to do so, after all, it is a summary of experience, so you might as well be familiar with the use of sass for a period of time, and then think about these issues carefully.

Note that none of the above is a dead rule. At some point, the specification needs to be adjusted according to the actual project, such as SPA, which we will talk about later. Perfect projects do not exist, and there is no development model that can be applied to all projects. Only by adjusting measures to local conditions can we better solve the problem. And none of the problems we have mentioned so far are fatal, which were avoided in the last section when we were setting the specification.

Call module

Question, where do I call the module?

Answer, page scss.

It is a good habit to call modules in the page scss, which makes the modules we use on each page consistent and isolated from each other, unlike referencing modules directly in common, so that a page scss has been contaminated by many module names before it has any content.

One more question, where can I call the module on the page scss?

Example 1, outside the root class:

/ / index.scss @ import'. / common'; @ import'. / mixin'; @ include MMI navy; @ include MMI newsletter; @ include MMI copywriting right; .g-index {...}

Example 2, within the root class:

/ / index.scss @ import'. / common'; @ import'. / mixin';. G-index {@ include; @ include Mmuri newsletter; @ include Mlysee copyrights;...}

So far, both of these ways are fine, and as for why I use the word "so far", it is because of SPA, which we will talk about later, if there is a problem with the use case 1 approach. So I encourage the use of example 2. Of course, as I said, example 1 is fine so far.

Performance optimization

So far, our modularization work has been completed, in fact, we can finish the work. But we can still optimize it a little bit.

1. Caching

We need to consider one problem: caching.

Caching is one of the most common situations in our web development, and most of the time we need to deal with caching, especially when doing performance optimization.

In general, after a static resource is loaded into a browser, the browser caches it locally so that it can respond quickly the next time the same resource is requested, without having to load it on a remote server.

As far as css is concerned, suppose we use multiple link to load reset, bootstrap, common and index files in the original way, these files will be cached so that the next time we visit this page, the loading speed of this page will be much faster.

What if you jump from an index page to an about page? You will find that it is also very fast, because the global css (reset, bootstrap, common) of about pages is the same as index pages, and they have already been loaded when you visit index, and thanks to the cache, subsequent pages open quickly.

The way we do now is that all the css files used on a page are merged into one, so there is no advantage that the same file can take advantage of caching.

Is there any way we can improve it? Yes, there is! We just need to separate the common so that the common can be used as a cached public file. In the end, we changed from one page referencing only one file to one page referencing two files, namely common and page css:

/ / common.scss @ import'. / reset'; @ import'. / bootstrap.min'; @ import'. / mixin';// index.scss @ import'. / mixin';. G-index {.}

Note that unlike before, our index.scss no longer introduces common.scss, so we end up with two css files, while common.css is introduced through the link tag on all pages.

In this way, we can not only merge files and reduce the number of requests, but also use caching to improve loading speed.

2. Compression

Code compression is the most basic step in optimization work, css compression space is very large, especially our vertical writing method, compression is quite efficient.

This is very simple in sass. Sass provides several modes when compiling, of which compressed mode is * * efficient compression mode. Remember to choose compressed mode when compiling and packaging.

Generally speaking, the preprocessing language not only makes our programming better, but also makes the specification more perfect. In the case that css itself can not be implemented, we use tools to complete modular development.

I will not talk about how to install and configure the sass environment, because these w3cplus sass guide are described in detail, it is recommended to use the nodejs way, will not tamper with the front end of nodejs/npm is not a good front end.

Let's go back to the question we mentioned at the beginning-- why modularization? Now we can answer from the work of css, in a sense, modularization improves our programming ability and problem-solving ability, makes it possible to build a large, scalable and maintainable project, and enables us to build the whole project with architectural thinking and vision.

On how to carry out the modularization of CSS preprocessing language to share here, I hope the above content can be of some help to you, can learn more knowledge. If you think the article is good, you can share it for more people to see.

Welcome to subscribe "Shulou Technology Information " to get latest news, interesting things and hot topics in the IT industry, and controls the hottest and latest Internet news, technology news and IT industry trends.

Views: 0

*The comments in the above article only represent the author's personal views and do not represent the views and positions of this website. If you have more insights, please feel free to contribute and share.

Share To

Development

Wechat

© 2024 shulou.com SLNews company. All rights reserved.

12
Report