CSSのtransform

2023/02/20更新

目次

基本

特長

CSSのtransformは、要素に対して2次元および3次元での拡大・移動・回転などの座標変換を可能にする。

  • 他の要素に影響を及ぼすことなく拡大や回転などの効果を簡単にかけることができる。

  • 2次元だけでなく3次元の効果をかけることもできる。

  • 従来の他のCSSによる方法に比べて高速でスムーズに描画される。

  • transitionなどによるアニメーションにも対応している。

座標軸

transformで使用される座標変換の座標軸は、x軸とy軸については、従来と同じく右がx軸の正、下がy軸の正である。3次元の座標変換で使用されるz軸は、手前が正で奥が負である。

座標の原点は、デフォルトでは要素の中央となる。これはtransform-originプロパティで変更できる。

transformプロパティ

基本

transformプロパティには、以降に示す変形関数(transform-function)を1つ以上並べて指定する。

.box {
    transform: rotateZ(10deg) scaleX(2);
}

2つ以上の変形関数を指定した場合、それぞれの効果が合成されるわけだが、合成は右側に指定したものから左側に指定したものの順番に行なわれる。合成の順番が変わると同じ結果になるとは限らない。なお、perspective()は常に先頭(一番左側)に書かなければならない。

以下は、合成の順序による違いを示す例である。1つ目は「x方向に2倍してから回転」しているが、2つ目は「回転してからx方向に2倍」している。

描画

CSS

transform-rotate-scale.png

.box {
    transform: rotateZ(10deg) scaleX(2);
}

transform-scale-rotate.png

.box {
    transform: scaleX(2) rotateZ(10deg);
}

視点

平面である画面上で3次元の効果(遠近感)を見せるためには、手前にあるものを遠くにあるものより大きく描くことになるが、この効果の度合いを決めるのが視点の位置を定めるperspective(d)である。この関数では、視点位置とz = 0の平面の距離を定義する。

dの値

説明

none

無限遠から見ている状態。
→ 手前のものも奥のものも同じ大きさに見える(=平行投影)。

大きな数値

遠くから見ている状態。
→ 「手前のものが遠くのものより大きく見える度合い」が小さい。

小さな数値

近くから見ている状態。
→ 「手前のものが遠くのものより大きく見える度合い」が大きい。

z座標がdに指定した値より大きい範囲は、視点の後ろにあることになるため、非表示となる。それ以外のz = aの位置にあるものは、z = 0の位置にあるものに比べて大きさがd / (d - a)倍に拡大・縮小されて描画される。

  • z = 0なら常に1倍(本来の大きさ)

  • z ≧ dなら非表示

  • d = ∞none)ならzによらず常に1倍

なお、perspective()は、transformの値の中で最初に書かなければならない。

以下は、perspective()の効果を示す例である。全てY軸を中心に回転しているため、左半分が手前に飛び出ているはずであるが、perspective(none)の場合はその効果が全く見られず、逆に数値が小さくなるとその度合いが大きくなっていくのが分かる。

描画

CSS

transform-perspective-none.png

.box {
    transform: perspective(none) rotateY(10deg);
}

transform-perspective-50.png

.box {
    transform: perspective(50px) rotateY(10deg);
}

transform-perspective-25.png

.box {
    transform: perspective(25px) rotateY(10deg);
}

複数の要素で共通の視点を持たせるためには、後述のperspectiveプロパティを使う。

平行移動

平行移動を行なうにはtranslate()translate3d()を使う。

変形関数

意味

translate(x, y)

x方向、y方向にそれぞれ指定した量だけ平行移動。

  • translate(x)translate(x, 0)と同じ。

translate3d(x, y, z)

x方向、y方向、z方向にそれぞれ指定した量だけ平行移動。

  • perspective()の指定が無いとz方向の移動の効果は全く分からないので注意。

translateX(x)

translate3d(x, 0, 0)と同じ。

translateY(y)

translate3d(0, y, 0)と同じ。

translateZ(z)

translate3d(0, 0, z)と同じ。

回転

回転を行なうにはrotate()rotate3d()を使う。

変形関数

意味

rotate(a)

平面上での回転。

  • aが正の角度なら時計回り。角度はdegradで指定する。

rotate3d(x, y, z, a)

3D空間での回転。

  • {x, y, z}は回転軸ベクトル(自動的に長さ1に正規化される)。

  • aが正の角度なら時計回り。角度はdegradで指定する。

rotateX(a)

rotate3d(1, 0, 0, a)(x軸中心の回転)と同じ。

rotateY(a)

rotate3d(0, 1, 0, a)(y軸中心の回転)と同じ。

rotateZ(a)

rotate3d(0, 0, 1, a)(z軸中心の回転)と同じ。

回転の中心はデフォルトでは要素の中央となるが、transform-originで変更できる。

以下は、回転の効果を示す例である。

描画

CSS

transform-rotate-x.png

.box {
    transform: perspective(80px) rotateX(20deg);
}

transform-rotate-y.png

.box {
    transform: perspective(80px) rotateY(20deg);
}

transform-rotate-z.png

.box {
    transform: perspective(80px) rotateZ(20deg);
}

拡大・縮小

拡大・縮小を行なうにはscale()scale3d()を使う。

変形関数

意味

scale(x, y)

x方向、y方向にそれぞれ指定した倍率だけ拡大または縮小する。

  • scale(x)とした場合はscale(x, x)と同じ。

scale3d(x, y, z)

x方向、y方向、z方向にそれぞれ指定した倍率だけ拡大または縮小する。

scaleX(x)

scale3d(x, 1, 1)と同じ。

scaleY(y)

scale3d(1, y, 1)と同じ。

scaleZ(z)

scale3d(1, 1, z)と同じ。

拡大・縮小の中心はデフォルトでは要素の中央となるが、transform-originで変更できる。

せん断変形

平面上でのせん断変形を行なうにはskew()を使う。

変形関数

意味

skew(ax, ay)

x方向に角度ax、y方向に角度ayのせん断変形を行なう。

  • skew(ax)とした場合はskew(ax, 0)と同じ。

その他の関連プロパティ

transform-origin

transform-originは、回転拡大・縮小を行なうときの座標変換の原点を指定する。指定しない場合は、要素の中央(transform-origin: center center;)となる。

CSS

意味

transform-origin: left top;

要素の左上を原点とする。

  • leftの代わりにcenterまたはrighttopの代わりにcenterまたはbottomが使える。

transform-origin: 10px 20px;

要素の左上からx=10px、y=20pxの位置を原点とする。

transform-origin: 20% 30%;

要素の幅の20%、高さの30%の位置を原点とする。

transform-origin: 10px 20px 30px;

要素の左上からx=10px、y=20px、かつ、z=30pxの位置を原点とする。

  • z座標は%やキーワードでは指定できない。

以下は、拡大・縮小におけるtransform-originの効果を示す例である。拡大の中心が変わっていることが分かる。

描画

CSS

transform-origin-center-scale.png

.box {
    transform: scale(1.33);
}

transform-origin-topleft-scale.png

.box {
    transform: scale(1.33);
    transform-origin: left top;
}

以下は、回転におけるtransform-originの効果を示す例である。回転の中心が変わっていることが分かる。

描画

CSS

transform-origin-center-rotate.png

.box {
    transform: rotateZ(30deg);
}

transform-origin-topleft-rotate.png

.box {
    transform: rotateZ(30deg);
    transform-origin: left top;
}

transform-style

transform-styleは、親要素と子要素ともにtransformで変形の指定がなされている場合にどのように描画するかを決定するプロパティである。このプロパティ自体は親要素に指定する。

CSS

意味

transform-style: flat;
(デフォルト値)

子要素の3D変形が描画された親要素(=この時点で平面)だけが3D空間で変形する。

transform-style: preserve-3d;

子要素が3D空間に配置された親要素(=この時点で3D)がさらに3D空間で変形する。

以下は、transform-styleの効果を示す例である。

親要素(緑色の要素)でflat(デフォルト)が指定された場合は、子要素(青色の要素)の変形の効果がまず親要素の平面に描画され、その平面の親要素だけが変形している。一方で、preserve-3dが指定された場合は、子要素の変形が親要素に投影されることなく3D空間で維持され、親要素とともにさらに変形しているのが分かる。なお、preserve-3dの場合に子要素にperspective()を指定すると予期しない形に変形されるため、perspective()は親要素だけにすると良いようである。

描画

CSS

transform-style-flat.png

/* 親要素(下辺を軸に手前に60度回転) */
.box {
    transform: perspective(200px) translate3d(0px, 50px, 0px) rotateX(-60deg) translate3d(0px, -50px, -0px);
    transform-style: flat;
}
/* 子要素(右辺を軸に奥に45度回転) */
.child_box {
    transform: translate3d(50px, 0px, 0px) rotateX(-45deg) translate3d(-50px, 0px, 0px);
}

transform-style-preserve3d.png

/* 親要素(下辺を軸に手前に60度回転) */
.box {
    transform: perspective(200px) translate3d(0px, 50px, 0px) rotateX(-60deg) translate3d(0px, -50px, -0px);
    transform-style: preserve-3d;
}
/* 子要素(右辺を軸に奥に45度回転) */
.child_box {
    transform: translate3d(50px, 0px, 0px) rotateX(-45deg) translate3d(-50px, 0px, 0px);
}

perspective

perspectiveプロパティは、transformプロパティのperspective()関数と同様に視点位置を指定する。perspective()関数はtransformする要素自身の単独の視点を決めるのに対し、perspectiveプロパティは指定した要素の子要素に共通の視点を決定する。

以下は、perspectiveプロパティとperspective()関数の効果の違いを示す例である。

1つ目はperspective()関数を要素それぞれに指定した場合である。要素一つずつで見ると奥行きの効果が出て描画されているが、それぞれ独立した視点が設定されているため、3つの要素が共通の空間にあるようには見えない。

一方で2つ目はperspectiveプロパティを3つの要素の共通の親要素に指定した場合である。要素に共通の視点が設定されているため、3つの要素がそれぞれ異なる見え方で描画され、同じ空間で並んでいるかのように描画されているのが分かる。

描画

CSS

perspective-func.png

/* 緑色の要素 */
.box {
    transform: perspective(200px) rotateX(45deg);
}

perspective-prop.png

/* 緑色の要素に共通の親要素 */
.parent {
    perspective: 200px;
}
/* 緑色の要素 */
.box {
    transform: rotateX(45deg);
}

perspectiveを指定した要素でoverflow: scrollを指定すると、視点を親要素上で固定したまま子要素を動かすことができるため、スクロールに応じて子要素の見え方が変化する効果が得られる。

perspective-origin

perspectiveプロパティを指定したときに、消失点を親要素のどこにするかを指定する。transform-originと同様に、leftcenterなどのキーワード、%値、px値で指定できる。デフォルトは親要素の中央である。

外部リンク