CSS formatting and compression with native JS

Posted by ytse on Thu, 27 Jan 2022 15:17:42 +0100

preface

I've always liked collecting web page special effects. I often encounter the situation that CSS has been compressed. At this time, it will be very inconvenient to check. Sometimes I will compress my CSS in order to reduce the file size. Many such services are provided online, but they are not as human as I want. Therefore, I plan to write a JS to format and compress CSS myself

principle

The structure of CSS is as follows:

selector{
  css Attribute declarations: Values;
}

Therefore, CSS formatting is relatively simple, which can be roughly divided into the following steps;

1. Combine multiple spaces into one and remove the newline

2. Group the processed strings by "{"

3. Traverse the grouping and group the parts containing "}" with "}" again

4. Processing the grouped data, mainly adding spaces and line breaks

CSS compression is relatively simple. Merge the spaces and remove the newline

format

The above steps are implemented step by step below.

initialization:

function formathtmljscss(source, spaceWidth, formatType) {
this.source = source;
this.spaceStr = " ";
if (!isNaN(spaceWidth)) {
if (spaceWidth > 1) {
this.spaceStr = "";
for (var i = 0; i < spaceWidth; i++) {
this.spaceStr += " ";
}
}
else {
this.spaceStr = "\t";
}
}
this.formatType = formatType;
this.output = [];
}

The parameters here are the CSS code to be formatted, the space width before CSS attribute declaration, and the type (format / compression)

1. Combine multiple spaces into one and remove the newline:

formathtmljscss.prototype.removeSpace = function () {
this.source = this.source.replace(/\s+|\n/g, " ")
.replace(/\s*{\s*/g, "{")
.replace(/\s*}\s*/g, "}")
.replace(/\s*:\s*/g, ":")
.replace(/\s*;\s*/g, ";");
}

2. Group the processed strings by "{"

formathtmljscss.prototype.split = function () {
var bigqleft = this.source.split("{");
}

3. Traverse the grouping and group the parts containing "}" with "}" again

formathtmljscss.prototype.split = function () {
var bigqleft = this.source.split("{");
var bigqright;
for (var i = 0; i < bigqleft.length; i++) {
if (bigqleft[i].indexOf("}") != -1) {
bigqright = bigqleft[i].split("}");
}
else {

}
}
}

4. Processing the grouped data, mainly adding spaces and line breaks

The processing here is mainly divided into taking out the CSS attribute declaration and value part, and then adding spaces and line breaks:

formathtmljscss.prototype.split = function () {
var bigqleft = this.source.split("{");
var bigqright;
for (var i = 0; i < bigqleft.length; i++) {
if (bigqleft[i].indexOf("}") != -1) {
bigqright = bigqleft[i].split("}");
var pv = bigqright[0].split(";");
for (var j = 0; j < pv.length; j++) {
pv[j] = this.formatStatement(this.trim(pv[j]),true);
if (pv[j].length > 0) {
this.output.push(this.spaceStr + pv[j] + ";\n");
}
}
this.output.push("}\n");
bigqright[1] = this.trim(this.formatSelect(bigqright[1]));
if (bigqright[1].length > 0) {
this.output.push(bigqright[1], " {\n");
}
}
else {
this.output.push(this.trim(this.formatSelect(bigqleft[i])), " {\n");
}
}
}

Several methods are called here: trim, formatSelect and formatStatement, which are described below.

trim: it can be seen from the naming that the first and last spaces are removed;

formathtmljscss.prototype.trim = function (str) {
return str.replace(/(^\s*)|(\s*$)/g, "");
}

formatSelect: it deals with the syntax of the selector part by giving "." Add a space in front, remove the space before and after "," and combine multiple spaces into one:

formathtmljscss.prototype.formatSelect = function (str) {
return str.replace(/\./g, " .")
.replace(/\s+/g, " ")
.replace(/\. /g, ".")
.replace(/\s*,\s*/g, ",");
}

formatStatement: handle "css attribute declaration: value" Part of the syntax is to add spaces after ":, combine multiple spaces into one, remove the spaces after" # ", the spaces before" px ", the spaces on both sides of" - "and the spaces before"::

formathtmljscss.prototype.formatStatement = function (str, autoCorrect) {
str = str.replace(/:/g, " : ")
.replace(/\s+/g, " ")
.replace("# ", "#")
.replace(/\s*px/ig, "px")
.replace(/\s*-\s*/g, "-")
.replace(/\s*:/g, ":");

return str;
}

call

The calling part is relatively simple. For formatting, it is to remove spaces and line breaks, and then group processing. For compression, it is to remove spaces and line breaks:

formathtmljscss.prototype.formatcss = function () {
if (this.formatType == "compress") {
this.removeSpace();
}
else {
this.removeSpace();
this.split();
this.source = this.output.join("");
}
}

Interface HTML code:

Events bound to page element buttons: