cssの背景画像に相当するsrcsetはありますか


91

imgsrcset属性付きは、レスポンシブ画像を作成するための優れた方法のように見えます。cssbackground-imageプロパティで機能する同等の構文はありますか?

HTML

<img src="small.jpg" srcset="medium.jpg 1000w, large.jpg 2000w" alt="yah">

CSS

.mycontainer {
    background: url(?something goes here?);
}

回答:


83

image-set同等のCSS機能です。同等のsrcset機能(ディメンションに従ってリソースを定義する)を仕様に追加する必要があります。

現在、-webkit-プレフィックスが付いたSafari、Chrome、Operaでのみ実装されており、x記述子のみをサポートしています。


1
既知の優雅なフォールバックまたはこれをサポートするポリフィルはありますか?
レイチェルカンター

5
@RachelCantorフォールバックは必要ですか?とにかく、最新のデバイスだけがRetinaスクリーンを備えていると思いますか?
James Kemp

3
x記述子をサポートするだけでは意味がないようです。つまり、2x 'レチナ'デスクトップ(5120w)では背景画像が全幅になる可能性があります。2x(720w)のモバイルでは、あらゆるモバイルデバイスがWebページと見なすのにばかげたサイズの画像です。バックグラウンド。max-widthメディアクエリを使用していくつかの異なるサイズを提供する場合でも、背景コンテナのmax-widthではなく、画面のmax-widthであるため、それほど役に立ちません。
Chris Seufert 2016年

1
したがって、ブラウザがイメージセットをサポートしていない場合、フォールバックは何ですか?
O.MeeKoh

22

かなり確実です:

background: -webkit-image-set( url('path/to/image') 1x, url('path/to/high-res-image') 2x );

同じように機能します。ブラウザは画像を調べて、どれが最適かを確認し、その画像を使用します。


2
2018年でも、これはすべてのブラウザでサポートされているわけではありません。caniuse.com/#search=image-set
BadHorsie

17

率直に言って、より堅牢な別のアプローチは、背景画像の特性とオプションをsrcset属性を持つ画像に適合させることです。

これを行うには、画像を幅:100%に設定します。高さ:100%; およびobject-fit:coverまたはcontain。

次に例を示します。

.pseudo-background-img-container {
  position: relative;
  width:400px;
  height: 200px;
}
.pseudo-background-img {
  position: absolute;
  top: 0;
  left: 0;
  width: 100%;
  height: 100%;
  object-fit: cover;
}
<div class="pseudo-background-img-container">

<img class="pseudo-background-img" src="https://cdn3.tnwcdn.com/wp-content/blogs.dir/1/files/2016/12/Keep.jpg" srcset="https://cdn0.tnwcdn.com/wp-content/blogs.dir/1/files/2016/12/Keep.jpg 640w, https://cdn0.tnwcdn.com/wp-content/blogs.dir/1/files/2016/12/Keep-280x175.jpg 280w, https://cdn0.tnwcdn.com/wp-content/blogs.dir/1/files/2016/12/Keep-432x270.jpg 432w, https://cdn0.tnwcdn.com/wp-content/blogs.dir/1/files/2016/12/Keep-216x135.jpg 216w" sizes="(max-width: 640px) 100vw, 640px">

</div>

これはすべての人にとって最善のアプローチではないかもしれませんが、JavaScriptの回避策なしで最も望ましい結果が得られると思います。


1
src-setは画像の幅を考慮せず、object-fit:coverのコンテナの幅のみを考慮します。つまり、imgタグの幅が50ピクセル、高さが1000ピクセルの場合、50ピクセルの幅を満たす画像が読み込まれ、収まるように引き伸ばされ、240wから1500ピクセルの幅に拡大縮小され、50ピクセルのスライスのみが表示されます。
Chris Seufert 2018

11

ポリフィルの場合、正しい画像サイズをダウンロードするメカニズムとしてsrcsetを使用してimgを使用し、JSを使用してそれを非表示にし、親要素の背景画像を設定できます。

これがフィドルです:http//jsbin.com/garetikubu/edit?html、output

onloadJSをブロックスクリプトとして使用し、配置すること<head>が重要です。スクリプトを後で(たとえば、の最後に<body>)配置すると、ブラウザによってimg.currentSrcがまだ設定されていない競合状態が発生する可能性があります。ロードされるのを待つのが最善です。

この例では、ダウンロードされている元のimgを確認できます。いくつかのCSSで簡単に隠すことができます。


面白い。これを行うと、画像が2回読み込まれると予想していました。ただし、そうではないようです。
ペリー

9

目的に応じてメディアクエリを使用できます。これは簡単です:

.mycontainer {    
    background-image:url("img/image-big.jpg"); // big image   
}

@media(max-width: 768px){
   .mycontainer {
        background-image:url("img/image-sm.jpg"); // small image  
    }
}

そして、私はそれがメディアクエリをサポートするすべてのブラウザで動作すると思います;)


2
画像がコンテナを覆うように設定されている場合、高さに合わせて引き伸ばされる画像は考慮されません。ボックスはネイティブ画像の幅の2〜3倍の高さになる可能性があるため、品質が非常に低くなります。
Chris Seufert 2018

3

<picture>要素を使用した同様のソリューション: チュートリアルはこちら

チュートリアルの場合:

同じ画像を小さい画面サイズで使用すると、画像の主要な被写体のサイズが小さくなりすぎる可能性があるのではないかと思います。別の画像(主要な被写体に焦点を当てたもの)を別の画面サイズで表示したいのですが、デバイスのピクセル比に基づいて同じ画像の個別のアセットを表示したいので、高さと幅をカスタマイズしたいビューポートに基づく画像。

コード例:

<picture>

<source media="(max-width: 20em)" srcset="images/small/space-needle.jpg 1x,
images/small/space-needle-2x.jpg 2x, images/small/space-needle-hd.jpg 3x">

<source media="(max-width: 40em)" srcset="images/medium/space-needle.jpg 1x,
images/medium/space-needle-2x.jpg 2x, images/medium/space-needle-hd.jpg 3x">

<img src="space-needle.jpg" alt="Space Needle">

</picture>

'<picture>'要素を 'absolute'または 'fixed'として配置します。セット正しいz屈折率+位置:必要に応じて、そのコンテナの相対
ピョートルŚcigała

gdaniel:Ready JSソリューション:github.com/code-mattclaffey/…テストしたばかりで、うまく機能しています。
ピョートルŚcigała

JS溶液、<画像>要素を介して画像を読み込み、背景画像として表示:github.com/code-mattclaffey/...
ピョートルŚcigała

2

Foundationフレームワーク(https://foundation.zurb.com/)を使用している場合は、そのためにInterchangeプラグインを使用できます。

<div data-interchange="[assets/img/interchange/small.jpg, small], 
                       [assets/img/interchange/medium.jpg, medium], 
                       [assets/img/interchange/large.jpg, large]">
</div>

https://foundation.zurb.com/sites/docs/interchange.html#use-with-background-images


このマルティをありがとう。私はこれをwebpackと一緒にうまく配線しresponsive-loaderて、かなり甘い解決策を見つけました。
fredrivett 2018年

1

@Westonの回答に基づいて、より一般的なjQueryソリューションを構築しました。基本的には、JSとCSSをコピーして貼り付け、HTML部分に焦点を当てることができます;)

TL; DR-フィドル:https//jsfiddle.net/dpaa7oz6/

CSS

...読み込み中に画像がほとんど見えないようにするため

.srcSet{
  position: fixed;
  z-index: 0;
  z-index: -1;
  z-index: -100;
  /* you could probably also add visibility: hidden; */
}

JS / jQuery

このスクリプトは、srcSetクラスとバインドloadイベントを持つすべての画像を調べます。このイベントは、クラスを持つ最も近い親にCSSとして配置されますcurrentSrcsrcサポートされていない場合)。background-imagebgFromSrcSet

それ自体では十分ではありません!そのため、window loadイベントに間隔チェッカーを配置して、ロードイベントが完了したかどうかをテストし、完了していない場合はトリガーします。(img loadイベントは、最初のロード時にのみトリガーされることがよくあります。次のロードでは、イメージソースがキャッシュから取得される可能性があり、その結果、imgロードイベントが発生しません

jQuery(function($){ //ON DOCUMENT READY
  var $window = $(window); //prepare window as jQuery object

  var $srcSets = $('.srcSet'); //get all images with srcSet clas
  $srcSets.each(function(){ //for each .srcSet do...
    var $currImg = $(this); //prepare current srcSet as jQuery object

    $currImg
      .load(function(){ //bind the load event
          var img = $currImg.get(0); //retrieve DOM element from $currImg

          //test currentSrc support, if not supported, use the old src
          var src = img.currentSrc ? img.currentSrc : img.src;

          //To the closest parent with bgFromSrcSet class,
          //set the final src as a background-image CSS
          $currImg.closest('.bgFromSrcSet').css('background-image', "url('"+src+"')");

          //remove processed image from the jQuery set
          //(to update $srcSets.length that is checked in the loadChecker)
          $srcSets = $srcSets.not($currImg);

          $currImg.remove(); //remove the <img ...> itself 
      })
    ;      

  });

  //window's load event is called even on following loads...
  $window.load(function(){    
    //prepare the checker
    var loadChecker = setInterval(function(){
        if( $srcSets.length > 0 ) //if there is still work to do...
            $srcSets.load(); //...do it!
        else
            clearInterval(loadChecker); //if there is nothing to do - stop the checker
    }, 150);  
  });

});

HTML

...次のようになります:

<div class="bgFromSrcSet">
  <img class="srcSet"
       alt=""
       src="http://example.com/something.jpeg" 
       srcset="http://example.com/something.jpeg 5760w, http://example.com/something-300x200.jpeg 300w, http://example.com/something-768x512.jpeg 768w, http://example.com/something-1024x683.jpeg 1024w, http://example.com/something-1000x667.jpeg 1000w"
       sizes="(max-width: 2000px) 100vw, 2000px"
  >
  Something else...
</div>

注:クラスがbgFromSrcSetなければならないに設定することimg自体!imgDOM親ツリーの要素にのみ設定できます。

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.