CSS でインライン SVG 定義を使用することは可能ですか?
私は次のようなことを意味します:
.my-class {
background-image: <svg>...</svg>;
}
はい、可能です。これを試して:
body { background-image:
url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' width='10' height='10'><linearGradient id='gradient'><stop offset='10%' stop-color='%23F00'/><stop offset='90%' stop-color='%23fcc'/> </linearGradient><rect fill='url(%23gradient)' x='0' y='0' width='100%' height='100%'/></svg>");
}
(これを機能させるには、SVG コンテンツを URL エスケープする必要があることに注意してください。たとえば#
、 に置き換えられ%23
ます。)
これは IE 9 (SVG をサポート) で機能します。データ URL は IE の古いバージョンでも (制限付きで) 動作しますが、ネイティブでは SVG をサポートしていません。
少し遅れましたが、インライン SVG を background として使用しようとして夢中になっている人がいる場合、上記のエスケープの提案はうまく機能しません。1 つには、IE では機能せず、SVG のコンテンツによっては、FF などの他のブラウザーでこの手法が問題を引き起こす可能性があります。
svg を base64 でエンコードすると (URL 全体ではなく、svg タグとそのコンテンツだけです!)、すべてのブラウザーで動作します。base64 での同じ jsfiddle の例を次に示します: http://jsfiddle.net/vPA9z/3/
CSS は次のようになります。
body { background-image:
url("data:image/svg+xml;base64,PHN2ZyB4bWxucz0naHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmcnIHdpZHRoPScxMCcgaGVpZ2h0PScxMCc+PGxpbmVhckdyYWRpZW50IGlkPSdncmFkaWVudCc+PHN0b3Agb2Zmc2V0PScxMCUnIHN0b3AtY29sb3I9JyNGMDAnLz48c3RvcCBvZmZzZXQ9JzkwJScgc3RvcC1jb2xvcj0nI2ZjYycvPiA8L2xpbmVhckdyYWRpZW50PjxyZWN0IGZpbGw9J3VybCgjZ3JhZGllbnQpJyB4PScwJyB5PScwJyB3aWR0aD0nMTAwJScgaGVpZ2h0PScxMDAlJy8+PC9zdmc+");
base64 に変換する前に、URL エスケープを必ず削除してください。つまり、上記の例では、color='#fcc' が color='%23fcc' に変換されたことを示しています。# に戻る必要があります。
base64 がうまく機能する理由は、一重引用符と二重引用符、および URL エスケープに関するすべての問題が解消されるためです。
JS を使用している場合はwindow.btoa()
、base64 svg を生成するために使用できます。うまくいかない場合 (文字列に無効な文字が含まれている可能性があります)、単純にhttps://www.base64encode.org/を使用できます。
div の背景を設定する例:
var mySVG = "<svg xmlns='http://www.w3.org/2000/svg' width='10' height='10'><linearGradient id='gradient'><stop offset='10%' stop-color='#F00'/><stop offset='90%' stop-color='#fcc'/> </linearGradient><rect fill='url(#gradient)' x='0' y='0' width='100%' height='100%'/></svg>";
var mySVG64 = window.btoa(mySVG);
document.getElementById('myDiv').style.backgroundImage = "url('data:image/svg+xml;base64," + mySVG64 + "')";
html, body, #myDiv {
width: 100%;
height: 100%;
margin: 0;
}
<div id="myDiv"></div>
JS を使用すると、パラメーターを変更しても、オンザフライで SVG を生成できます。
SVG の使用に関する優れた記事の 1 つがここにあります: http://dbushell.com/2013/02/04/a-primer-to-front-end-svg-hacking/
お役に立てれば
マイク
まだ苦労している人のために、IE11以降の最新のすべてのブラウザでこれを機能させることができました.
SASSを使用して、特定の色に基づいてSVGアイコンを生成したかったため、base64は私にとって選択肢ではありませんでした。例:@include svg_icon(heart, #FF0000);
この方法では、特定のアイコンを任意の色で作成でき、SVG 形状を CSS に 1 回埋め込むだけで済みます。(base64 では、使用するすべての色に SVG を埋め込む必要があります)
次の 3 つの点に注意してください。
SVG
を URL エンコードする 他の人が示唆しているように、SVG 文字列全体を IE11 で動作させるには、SVG 文字列全体を URL エンコードする必要があります。私の場合、fill="#00FF00"
やなどのフィールドの色の値をstroke="#FF0000"
省略し、それらを SASS 変数fill="#{$color-rgb}"
に置き換えて、これらを必要な色に置き換えることができるようにしました。任意のオンライン コンバーターを使用して、残りの文字列を URL エンコードできます。次のような SVG 文字列になります。
%3Csvg%20xmlns%3D%27http%3A%2F%2Fwww.w3.org%2F2000%2Fsvg%27%20viewBox%3D%270%200%20494.572%20494.572%27%20width%3D%27512%27%20height%3D %27512%27%3E%0A%20%20%3CPATH%20D%3D%3D%27M257.063%200C127.136%200%2021.808%20105.33%2021.808%20235.266C0%2041.012% %20464.586c345%2012.797%2041.813%2012.797%2015.467%200%2029.872-4.721%2041.813-12.797v158.184z%27%20fill%3D%27# {$color-rgb} %27%2%C%23FEs%g3 3E
データ URL でUTF8文字セットを省略する データ URL を作成するときは、IE11 で機能するように文字セットを省略する必要があります。
背景画像: url( data:image/svg+xml;utf-8,%3Csvg%2....) ではありませんが、背景画像: url( data:image/svg+xml,%
3Csvg %2...)ではありません。 .)
16 進数の色の代わりに RGB()を使用 する Firefox は SVG コードの # を好みません。したがって、色の 16 進値を RGB 値に置き換える必要があります。
fill ="#FF0000" では
なく、fill="rgb(255,0,0)"
私の場合、SASS を使用して、指定された 16 進数を有効な RGB 値に変換します。コメントで指摘されているように、RGB 文字列も URL エンコードすることをお勧めします (コンマは %2C になります)。
@mixin svg_icon($id, $color) {
$color-rgb: "rgb(" + red($color) + "%2C" + green($color) + "%2C" + blue($color) + ")";
@if $id == heart {
background-image: url('data:image/svg+xml,%3Csvg%20xmlns%3D%27http%3A%2F%2Fwww.w3.org%2F2000%2Fsvg%27%20viewBox%3D%270%200%20494.572%20494.572%27%20width%3D%27512%27%20height%3D%27512%27%3E%0A%20%20%3Cpath%20d%3D%27M257.063%200C127.136%200%2021.808%20105.33%2021.808%20235.266c0%204%27%20fill%3D%27#{$color-rgb}%27%2F%3E%3C%2Fsvg%3E');
}
}
これは非常に複雑な SVG (インライン SVG は決してそうではありません) には最適なソリューションではないかもしれませんが、2、3 色しかないフラット アイコンの場合、これは非常にうまく機能します。
CSS でスプライト ビットマップ全体を省略してインライン SVG に置き換えることができましたが、圧縮後は約 25kb しかありませんでした。したがって、CSS ファイルを肥大化させることなく、サイトが行う必要があるリクエストの量を制限する優れた方法です。
Mac/Linux では、次の単純な bash コマンドを使用して、SVG ファイルを CSS 背景属性の base64 でエンコードされた値に簡単に変換できます。
echo "background: transparent url('data:image/svg+xml;base64,"$(openssl base64 < path/to/file.svg)"') no-repeat center center;"
Mac OS X でテスト済み。これにより、URL エスケープの混乱も回避できます。
SVG ファイルを base64 でエンコードするとサイズが大きくなることに注意してください。 css-tricks.com ブログ投稿を参照してください。
インライン SVG を CSS に埋め込む際に同じ問題が発生した CodePen デモをフォークしました。SCSS で動作するソリューションは、単純な URL エンコード関数を作成することです。
文字列置換関数は、組み込みの str-slice 関数、str-index 関数から作成できます ( Hugo Giraudel のおかげでcss-tricksを参照してください)。
次に、、、、、、、%
をコード<
に置き換えます。>
"
'
%xx
@function svg-inline($string){
$result: str-replace($string, "<svg", "<svg xmlns='http://www.w3.org/2000/svg'");
$result: str-replace($result, '%', '%25');
$result: str-replace($result, '"', '%22');
$result: str-replace($result, "'", '%27');
$result: str-replace($result, ' ', '%20');
$result: str-replace($result, '<', '%3C');
$result: str-replace($result, '>', '%3E');
@return "data:image/svg+xml;utf8," + $result;
}
$mySVG: svg-inline("<svg>...</svg>");
html {
height: 100vh;
background: url($mySVG) 50% no-repeat;
}
Compass にもimage-inline
ヘルパー関数がありますが、CodePen ではサポートされていないため、このソリューションが役立つ可能性があります。
CodePen のデモ: http://codepen.io/terabaud/details/PZdaJo/
サードパーティのソース (Google チャートなど) からのインライン SVG にはxmlns="http://www.w3.org/2000/svg"
、SVG 要素に XML 名前空間属性 ( ) が含まれていない可能性があります (または、SVG がレンダリングされると削除される可能性があります。ブラウザー インスペクターも、ブラウザー コンソールからの jQuery コマンドも、SVG 要素の名前空間を表示しません)。
これらの svg スニペットを他のニーズ (CSS の background-image または HTML の img 要素) に再利用する必要がある場合は、欠落している名前空間に注意してください。名前空間がないと、ブラウザーは SVG の表示を拒否する場合があります (エンコーディングが utf8 または base64 に関係なく)。