15
7

More than 5 years have passed since last update.

PostCSSのASTを操作する

Posted at

PostCSSには2日目で説明した、ASTを簡単に操作するためのAPIが用意されています。ASTはJavaScriptのオブジェクトなので、JavaScriptの構文で直接変換させることもできますが、より便利に、そして効率の良い処理をするためにも提供されているAPIを使います。

また、PostCSSの全てのAPIはAPIドキュメントで確認することができます。

ノードの種類

まずはASTのノードの種類です。PostCSSのASTのノードは以下の5つです。

  • Rootノード: ASTの1番上のノード(Rootノードは親ノードがない)
  • Ruleノード: 1つのルールセット
  • AtRuleノード: 1つの@ルール
  • Declarationノード: 1プロパティ宣言
  • Comment: 1つのコメント

これらは実装的には PostCSSの Node クラスを継承したもので、Node.type を参照することで、それが何のノードかを知ることができます。

ノードの探索

次にノードを探索するAPIを見てみましょう。以下の input.css を入力としたときの例を挙げます。

.foo {
  font-size: 1.2rem;
}

.bar {
  color: pink;
}

@media (max-width: 415px) {
  .foo {
    font-size: 1rem;
  }
}

Ruleノードの探索

Ruleノードは container.walkRules([selector], callback) というAPIを使って探索することができます。 container というのは「子ノードを持つことができる(親ノードになることができる)ノード」である Container クラスのインスタンスです。Root ノード、Rule ノード、AtRuleノードがそれに当たります。

var css = fs.readFileSync('./input.css');
var root = postcss.parse(css); // `input.css`をパースしてASTを返す

root.walkRule(function (rule) {
  // 全てのルールセットを探索
});

walkRules() は第一引数にセレクタ名を文字列(または正規表現)で指定することもできます。

root.walkRules('.foo', function (rule) {
  // 全て`.foo`セレクタのルールセットを探索
});

AtRuleノードの探索

AtRuleノードは container.walkAtRules([name], callback) というAPIを使って探索することができます。第一引数に@ルール名を指定することもできます。

root.walkAtRules('media', function (atrule) {
  // `@media` の@ルールを探索
});

Declarationノードの探索

AtRuleノードは container.walkAtRules([prop], callback) というAPIを使って探索することができます。第一引数にプロパティ名を指定することもできます。

root.walkDecls('font-size', function (decl) {
  // `font-size`プロパティのプロパティ宣言を探索
});

Commentノードの探索

AtRuleノードは container.walkAtRules([prop], callback) というAPIを使って探索することができます。

root.walkComments(function (comment) {
  // 全てのコメントを探索
});

ノードの挿入・移動・削除

container.insertBefore(exist, add), container.insertAfter(exist, add) はそれぞれ、ノードの指定した子ノードの直前と直後に新しくノード(add)を追加するためのAPIです。

rule.insertBefore(decl, { prop: 'color', value: 'pink' }));

node.moveTo(newParent) は、そのノードを削除し、指定したノードの子要素に追加するものです。

atrule.moveTo(atrule.root());

node.remove() はノードを削除するためのAPIです。

if ( decl.prop.match(/^-webkit-/) ) {
  decl.remove();
}

今日はPostCSSのASTを操作するためのAPIをいくつか紹介しました。これらのAPIを使って、ASTを変換するプラグラムがPostCSSのプラグインです。簡単なプラグインの実装を読んでみると、さらに理解が深まると思います。

明日は、これらのAPIを使って実際にPostCSSのプラグインの書き方を説明します。

15
7
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
15
7