ボックスの右上にSVG画像を背景に使用。
スタイルシートに下記のように指定して配置。
background-position : right top;
実際には位置を細かく調整して
background-position : top -20px right -120px;
のように指定。
モダンブラウザでは問題なく意図どおりに配置されるものの、IE11の場合は、要素の中央に・・・
調べていくと、SVGのレンダリングに違いがあるようで。
IE11の仕様書的なものは調べるまでもないなと判断したので、違いについては「いつものアレだ」とだけ理解して、解決策と簡単なメモだけ備忘録的に残しておきます。
対処法「SVGタグにpreserveAspectRatio属性を付与」する
svgタグにpreserveAspectRatio属性を追加すれば今回のような場合は意図した形で表示されるようになりました。
属性値ですが、使用しているSVG画像のビューポートが持つ余白の方向によって使い分けが必要です。
詳しくは後述しますが、各属性の詳細はSVGの仕様書「7.8 preserveAspectRatio 属性」を確認してください。
今回は、左右いっぱい、上下に余白のあるSVGだった
今回、背景に使用してIE11でズレが生じたのは、ビューポート自体は正方形であるものの、パス図形がビューポートの縦幅よりも短いSVG画像でした。
このため、ビューポートには自然と余白ができるわけですが、この余白の描画が(背景への利用時)IE11のみ解釈が異なったことがずれの原因でした。
一番左のA.が今回の原因となったSVGの描画エリアとパス図形の組み合わせです。
PreserveAspectRatioAttribute属性自体を記述していなかったので、規定値である「xMidYMid」が指定されている場合と同じ描画となり、上下に余白が生じています。
他のブラウザでは、パス図形がぴったりビューポートの上部にくっついている、Bの解釈をしていたため、IE11だけ余白分、背景が下に下がってしまっていました。
C.については参考程度に画像に含めています。xMidYMaxを指定すると、xMidYMinとは逆に下辺に張り付く形になるということがわかります。
解決に至れる属性値はSVGのビューポートサイズによる
preserveAspectRatio属性には様々な値があり、一見して、その値と、動作を理解するのは少し難しく感じます。
SVGの仕様書「7.8 preserveAspectRatio 属性」を見てもらえると大体なんとなく理解できるのではないかと思います。
とにかく背景を真ん中に持ってきたければ「xMidYMid」
規定値「xMidYMid」
preserveAspectRatio属性の指定をしていない状態で、規定値では「xMidYMid」となります。
「xMidYMid」は、 X(Y)の中央値をビューポートのX(Y)の中央値に揃える。
という指定なので、パス図形よりビューポート(描画エリア)が縦に大きければ垂直方向の中央に表示され、パス図形よりビューポート(描画エリア)が横に大きければ水平方向の中央に表示されます。
そもそも、この規定値が原因で今回のズレが発生しているので、対処としてこの指定をすることなんてないか・・・。
縦方向に余白のあるビューポートを持つSVGの場合の対処
今回のように、縦方向に余白がある場合の調整方法は「xMidY*」で行います。
「*」には「Mid(ミドル)」「Min(最小)」「Max(最大)」のいずれかが入ります。
上の余白をなくすときは「Min(最小)」、下の余白をなくすときは「Max(最大)」。
これだけでなんとなくイメージできますよね。
background-position:topにはxMidYMin
要素の viewBox の <min-x> + <width> の値をビューポートの X の最大値に揃える。
要素の viewBox の <min-y> の値をビューポートの Y の最小値に揃える。
ちょっとわかりにくい表現で混乱しましたが、実際のSVGで見てみるとこんな感じです。
背景画像をtop方向にposition指定する場合、これで対処可能です。
今回のわたしの事例は、このxMidYMinで対処することで、ズレを回避することができました。
background-position:bottomにはxMidYMax
均等な拡縮を強制する。
要素の viewBox の X の中央値をビューポートの X の中央値に揃える。
要素の viewBox の <min-y> + <height> の値をビューポートの Y の最大値に揃える。
実際のSVGで見るとこんな感じです。
背景画像をbottom方向にposition指定する場合、これで対処可能です。
横方向に余白のあるビューポートを持つSVGの場合の対処
今回の事例とは異なり、横方向に余白がある場合の調整方法は「x*YMin」で行います。
「*」には「Mid(ミドル)」「Min(最小)」「Max(最大)」のいずれかが入ります。
左の余白をなくすときは「Min(最小)」、右の余白をなくすときは「Max(最大)」を使う。
属性値の命名の流れでなんとなくイメージが付いてきたのではないでしょうか?
background-position:leftにはxMinYMin
均等な拡縮を強制する。
要素の viewBox の <min-x> の値をビューポートの X の最小値に揃える。
要素の viewBox の <min-y> の値をビューポートの Y の最小値に揃える。
図形が左に寄りました。
background-position:rightにはxMaxYMin
均等な拡縮を強制する。
要素の viewBox の <min-x> + <width> の値をビューポートの X の最大値に揃える。
要素の viewBox の <min-y> の値をビューポートの Y の最小値に揃える。
図形が右に寄りました。
今回の事例の場合、この値でも思うような表示になります。
状況に合わせて属性値を変えるべし
SVG画像の状態によって思うような表示になる属性値が複数あるため、SVGに合わせて仕様書を見ながら最適なものを設定してみてください。
SVG画像を背景で指定した場合のみ影響があり、画像として表示の場合は影響なし
2021/4/7時点でのChirome、Firefox、Safari(mac)、IE11最新版では、背景ではなく、画像として表示させる場合は、どのブラウザでも同じようにpreserveAspectRatioの指定値が反映されています。
今回の現象は、SVG画像を背景としてスタイルシートで指定した場合のみ起こる現象のようです。
背景画像にSVG画像を用いて、backgroundのposition指定をした場合、preserveAspectRatioを指定していないときはモダンブラウザでは余白が空くことなく、cssで指定した通りのbackground-positionで表示されますが、IE11のみpreserveAspectRatioでの調整が必要でした。
preserveAspectRatioを指定した場合、モダンブラウザので余白に変化はなく、IE11のみ、ずれていたものが思い通りの表示になりました。
SVG画像を背景に用いる際にIE11はpreserveAspectRatioの値を参照している、ということしかわかりませんが、深く調べることをせず、対処法はpreserveAspectRatio属性で調整をすればヨシということで、メモ完了としておきます。
コメントを残す