CSS @functionの作例と落とし穴:カスタム関数プロンプト集

CSS @functionがもたらすパラダイムシフト
2026年5月、CSSにカスタム関数を定義できる@functionルールが主要ブラウザでサポートされ始めた。これにより、従来はプリプロセッサやJavaScriptに頼っていた計算ロジックをCSSだけで完結できるようになる。開発者はSassやPostCSSの関数をネイティブCSSに置き換える選択肢を得た。
重要なのは、この変化が単なるシンタックスシュガーではない点だ。カスタム関数は動的スタイルの生成をCSSレイヤーに閉じ込める。結果として、ランタイムのJavaScript実行を減らし、ブラウザの最適化が効きやすくなる。特にアニメーションやレスポンシブデザインの条件分岐で威力を発揮する。
@functionの基本構文と実例
CSS @functionは以下のように記述する。
@function --clamp-fallback($min, $pref, $max) {
@return clamp($min, $pref, $max);
}
.element {
font-size: --clamp-fallback(1rem, 5vw, 3rem);
}
この例では、clamp()をラップしたカスタム関数を定義している。引数にデフォルト値も設定でき、@returnで値を返す。従来の@mixinと異なり、値そのものを生成するのが関数の役割だ。
実務で役立つユースケースは以下の通り。
- 色変換関数:
--darken($color, $amount)でアクセントカラーを生成 - スケーリング計算:
--fluid-size($min, $max)でビューポートに応じた可変サイズ - グリッド計算:
--columns($count, $gap)で動的カラム幅を算出
Sass関数からの移行コスト
既存のSassプロジェクトをCSS @functionに移行する場合、注意すべき点がある。まず、CSSカスタム関数は全ての演算子や組み込み関数をネイティブで使えるわけではない。特にmath.pow()やリスト操作は未サポート。複雑な計算にはcalc()とmin()/max()/clamp()を組み合わせる必要がある。
また、@function内でvar()を使うと、カスタムプロパティの未定義時はそのままフォールバックされない。代替値は関数呼び出し側でvar(--prop, fallback)として明示しなければならない。この落とし穴は多くの開発者が見落とすポイントだ。
Baselineとブラウザサポート
2026年4月のBaselineダイジェストによれば、@functionはChrome 130以降、Firefox 130以降でサポート。Safariは17.5で一部対応、EdgeはChromeベースのため同様。ただし、全てのCSS関数(例: color-mix()やround())が@function内で使えるわけではない。現時点で@function内で許可されるのは基本演算と一部の数学関数に限られる。
互換性を担保するには、@supportsで機能検出を行い、フォールバックを用意する。
@supports (--custom: @function) {
/* @functionを使用 */
} @else {
/* Sass関数または手動計算 */
}
パフォーマンスと設計上の注意
CSS @functionはブラウザのスタイル計算時に解釈される。再計算の必要があるたびに関数が再評価されるため、頻繁に変化するプロパティ(animation内など)で呼び出すとパフォーマンスが低下する。特にループ処理や再帰的な関数定義は避けるべきだ。
また、関数の入れ子は可能だが、深さによって可読性が急激に落ちる。チーム開発では関数の命名規則とドキュメントを徹底しないと、コードの理解コストが増大する。
これからの展望
CSS @functionが本格的に普及すれば、CSS-in-JSの必要性が減る可能性がある。コンポーネント単位のスタイルロジックをCSSに閉じ込められるからだ。ただし、現状はまだ発展途上。W3Cの仕様策定は進行中で、変数スコープや条件分岐(@if相当)の導入が議論されている。
2026年後半には@function内で@forループや@each相当の機能が追加される見込み。これが実現すれば、CSSは本格的なプログラミング言語の領域に踏み込む。一方で、従来のCSS設計思想(宣言的・静的)からの逸脱を懸念する声もある。
開発者は「使いどころを見極める」ことが求められる。全てをCSS関数で書くのではなく、動的な値はJavaScript、静的なロジックはCSSと役割分担を明確にすべきだ。
