2013-04-08 15 views
22

JavaScript/jQueryを使用してInfinity-Image-Loop-Sliderを構築するための最良のコンセプト(良い可読性コード、害虫練習コード、再利用性)は何ですか?私はスライドショーをどのようにコードするかを知ることはできませんが、上記の要件に合った青写真は何ですか? 私の質問の主な焦点は、無限ループスライダーの印象を得るために写真をどのように配置するかです。すべての画像のzインデックス-changeInfinityループスライダの概念

次/前の画像が表示されるたびに:私は2つのソリューションに出くわした別のスライダーからのコードを見てすることで

- DOM内の画像の位置を変更します。

しかし、調べて、他の人のコードを理解することは非常に時間がかかるものである - 私は

答えて

49

TL :-)この質問を理由です; - 例DRhttp://jsbin.com/ufoceq/8/


あまりにも多くの労力をかけずに無限のイメージスライダーを作成する簡単な方法は次のとおりです。<n>イメージをループ内でスライドさせるという単純さのために、nth image次の画像は、1st(またはその逆)です。

アイデアは、最後の画像のクローンは最初のものの前に付加され

  • ようにするために、最初と最後の画像のクローンを作成することです。
  • 最後のイメージの後に最初のイメージのクローンが追加されます。

イメージの量は問わず、複製された要素は2つまでしか追加する必要がありません。

また、すべての画像がの幅であり、左右に移動したコンテナに包まれているとします。これは、overflow: hiddenのクリッピングされたマスクに移動します。すると、すべての画像は、display: inline-blockwhite-space: nowrapがコンテナにセットされた行に簡単に揃えることができます(flexboxはさらに簡単です)。

DOM構造はこのようなものになるだろうn = 4について:初めに

offset(px)  0  100  200  300  400  500 
images   | 4c | 1 | 2 | 3 | 4 | 1c 

/*     ^^          ^^ 
     [ Clone of the last image ]    [ Clone of the 1st image ] 
*/ 

、あなたのコンテナはleft: -100px(またはもmargin-left: -100pxor even better (for a matter of performance)transform: translateX(-100px))に配置されるので、スライダーは最初の画像を表示することができます。イメージを別のイメージに切り替えるには、以前選択したものと同じプロパティでJavaScriptアニメーションを適用する必要があります。

あなたのスライダーは番目の画像4 に現在あるとき、あなたは1cに画像4から切り替える必要があり、その考えはすぐに本当であなたのスライダーラッパーを再配置、アニメーションの最後にコールバックを実行することです1 stイメージオフセット(例:あなただけの画像1から4cにアニメーションを実行する必要があるとアニメーションがされていたときに前の画像を表示する:あなたは、スライダーが現在1つのST要素の上に配置されたときにこれが似ている)を容器に

left: -100pxを設定しましたコンテナを移動するだけで完了しました。スライダは、4 thイメージオフセットに配置されています(たとえば、left: -400pxをコンテナに設定します)。


あなたは上記のフィドルに効果を見ることができます。これは私が使用し、最小限のjs/jqueryコードである(アイテムの幅がスクリプトにハードコードされていないので、もちろんコードも最適化することができます)

$(function() { 

    var gallery = $('#gallery ul'), 
     items = gallery.find('li'), 
     len  = items.length, 
     current = 1, /* the item we're currently looking */ 

     first = items.filter(':first'), 
     last = items.filter(':last'), 

     triggers = $('button'); 

    /* 1. Cloning first and last item */ 
    first.before(last.clone(true)); 
    last.after(first.clone(true)); 

    /* 2. Set button handlers */ 
    triggers.on('click', function() { 

    var cycle, delta; 

    if (gallery.is(':not(:animated)')) { 

     cycle = false; 
     delta = (this.id === "prev")? -1 : 1; 
     /* in the example buttons have id "prev" or "next" */ 

     gallery.animate({ left: "+=" + (-100 * delta) }, function() { 

      current += delta; 

      /** 
      * we're cycling the slider when the the value of "current" 
      * variable (after increment/decrement) is 0 or when it exceeds 
      * the initial gallery length 
      */   
      cycle = !!(current === 0 || current > len); 

      if (cycle) { 
       /* we switched from image 1 to 4-cloned or 
        from image 4 to 1-cloned */ 
       current = (current === 0)? len : 1; 
       gallery.css({left: -100 * current }); 
      } 
     }); 
    } 

    }); 
}); 

前に述べたように、このソリューションは、本当に多くの努力を必要とせず、ループなしで通常のスライダーに、このアプローチを比較すると、パフォーマンスの話、それが唯一のスライダーが初期化されるときに、2つの追加のDOMの挿入を行うことが必要であり、いくつか(かなりtriv ial)後方/前方ループを管理する余分なロジック。

私は、より簡単な方法やより良い方法が存在するかどうかはわかりませんが、これがとにかく役立つことを願っています。

:あなたも応答ギャラリーを持っている必要がある場合は、多分this answerはあまりにも

+0

詳細な説明ありがとうございます! – user1828928

+0

@ user1828928あなたがライブの例に興味があるなら、私は短いフィドルを作成しました – fcalderan

+0

最初の旗は残念です。私はここでウィキの状態についてあなたが正しいので、ワイヤーがそこに横たわったと思う。 –

1

おかげで、この記事の多くを助けるかもしれません! 上記のコードを更新して使用しました。 これが皆に役立つことを願っています。 開発者が不十分です。

<!DOCTYPE html> 
 
<html> 
 
<head lang="en"> 
 
    <meta charset="UTF-8"> 
 
    <title>Directive slider</title> 
 
    <style> 
 
     /* 四联切换焦点图 */ 
 
     .slides-wrapper{ position: relative; width: 100%; margin: 10px 0; } 
 
     .gallery { position: relative; width: 1200px; height: 180px; overflow:hidden; } 
 
     .gallery ul { font-size: 0; white-space: nowrap; position: absolute; top: 0; left: -1200px; margin: 0; padding: 0; } 
 
     .gallery li { display: inline-block; vertical-align: top; width: 1200px; height: 180px; white-space: normal; } 
 
     .gallery li img{ width: 298px; height:180px; padding: 1px; } 
 
     .gallery .arrow { background: url(/shop/templates/default/images/home_bg.png) no-repeat; background-size: 150px 223px; width: 35px; height: 70px; position: absolute; z-index: 2; top: 50px; cursor: pointer; opacity: 0;} 
 
     .gallery .prev { background-position: 1px -92px; left: 0;} 
 
     .gallery .next { background-position: -30px -92px; right: 0px;} 
 
    </style> 
 
    <style type="text/css"> 
 
     .demo_wrapper{ 
 
      margin: 0 auto; 
 
      width: 1200px; 
 
     } 
 
     .demo_wrapper .title{ 
 
      text-align: center; 
 
     } 
 
    </style> 
 
</head> 
 
<body> 
 
<div class="demo_wrapper"> 
 
    <div class="title"> 
 
     <h1>Directive slider (Published by fenmingyu)</h1> 
 
    </div> 
 
    <!-- demo content --> 
 
    <div class="slides-wrapper"> 
 
     <div class="gallery" id="top_sale_gallery"> 
 
      <ul> 
 
       <li> 
 
        <a href="" target="_blank" title="" style="opacity: 1;"><img src="http://imgserv.5thmedia.cn/upload_test/shop/editor/web-102-104-1-1.jpg?234" alt=""></a> 
 
        <a href="" target="_blank" title="" style="opacity: 1;"><img src="http://imgserv.5thmedia.cn/upload_test/shop/editor/web-102-104-1-2.jpg?752" alt=""></a> 
 
        <a href="" target="_blank" title="" style="opacity: 1;"><img src="http://imgserv.5thmedia.cn/upload_test/shop/editor/web-102-104-1-3.jpg?320" alt=""></a> 
 
        <a href="" target="_blank" title="" style="opacity: 1;"><img src="http://imgserv.5thmedia.cn/upload_test/shop/editor/web-102-104-1-4.jpg?365" alt=""></a> 
 
       </li> 
 
       <li> 
 
        <a href="" target="_blank" title="" style="opacity: 1;"><img src="http://imgserv.5thmedia.cn/upload_test/shop/editor/web-102-104-2-1.jpg?852" alt=""></a> 
 
        <a href="" target="_blank" title="" style="opacity: 1;"><img src="http://imgserv.5thmedia.cn/upload_test/shop/editor/web-102-104-2-2.jpg?746" alt=""></a> 
 
        <a href="" target="_blank" title="" style="opacity: 1;"><img src="http://imgserv.5thmedia.cn/upload_test/shop/editor/web-102-104-2-3.jpg?525" alt=""></a> 
 
        <a href="" target="_blank" title="" style="opacity: 1;"><img src="http://imgserv.5thmedia.cn/upload_test/shop/editor/web-102-104-2-4.jpg?550" alt=""></a> 
 
       </li> 
 
      </ul> 
 
      <div class='arrow prev'></div> 
 
      <div class='arrow next'></div> 
 
     </div> 
 
     <div class="gallery" id="top_goods_gallery"> 
 
      <ul> 
 
       <li> 
 
        <a href="" target="_blank" title="" style="opacity: 1;"><img src="http://imgserv.5thmedia.cn/upload_test/shop/editor/web-102-104-3-1.jpg?793" alt=""></a> 
 
        <a href="" target="_blank" title="" style="opacity: 1;"><img src="http://imgserv.5thmedia.cn/upload_test/shop/editor/web-102-104-3-2.jpg?180" alt=""></a> 
 
        <a href="" target="_blank" title="" style="opacity: 1;"><img src="http://imgserv.5thmedia.cn/upload_test/shop/editor/web-102-104-3-3.jpg?550" alt=""></a> 
 
        <a href="" target="_blank" title="" style="opacity: 1;"><img src="http://imgserv.5thmedia.cn/upload_test/shop/editor/web-102-104-3-4.jpg?851" alt=""></a> 
 
       </li> 
 
       <li> 
 
        <a href="" target="_blank" title="" style="opacity: 1;"><img src="http://imgserv.5thmedia.cn/upload_test/shop/editor/web-102-104-1-1.jpg?234" alt=""></a> 
 
        <a href="" target="_blank" title="" style="opacity: 1;"><img src="http://imgserv.5thmedia.cn/upload_test/shop/editor/web-102-104-1-2.jpg?752" alt=""></a> 
 
        <a href="" target="_blank" title="" style="opacity: 1;"><img src="http://imgserv.5thmedia.cn/upload_test/shop/editor/web-102-104-1-3.jpg?320" alt=""></a> 
 
        <a href="" target="_blank" title="" style="opacity: 1;"><img src="http://imgserv.5thmedia.cn/upload_test/shop/editor/web-102-104-1-4.jpg?365" alt=""></a> 
 
       </li> 
 
       <li> 
 
        <a href="" target="_blank" title="" style="opacity: 1;"><img src="http://imgserv.5thmedia.cn/upload_test/shop/editor/web-102-104-2-1.jpg?852" alt=""></a> 
 
        <a href="" target="_blank" title="" style="opacity: 1;"><img src="http://imgserv.5thmedia.cn/upload_test/shop/editor/web-102-104-2-2.jpg?746" alt=""></a> 
 
        <a href="" target="_blank" title="" style="opacity: 1;"><img src="http://imgserv.5thmedia.cn/upload_test/shop/editor/web-102-104-2-3.jpg?525" alt=""></a> 
 
        <a href="" target="_blank" title="" style="opacity: 1;"><img src="http://imgserv.5thmedia.cn/upload_test/shop/editor/web-102-104-2-4.jpg?550" alt=""></a> 
 
       </li> 
 
      </ul> 
 
      <div class='arrow prev'></div> 
 
      <div class='arrow next'></div> 
 
     </div> 
 
     <div style="clear: both;"></div> 
 
    </div> 
 
</div> 
 

 
</body> 
 
<script src="http://code.jquery.com/jquery-1.9.1.min.js"></script> 
 
<script type="text/javascript"> 
 
    $(function() { 
 
     $.fn.gallery = function(settings) { 
 
      var defaults = { 
 
       time: 3000, 
 
       direction:1 
 
      }; 
 
      var settings = $.extend(defaults, settings); 
 
      var gallery_wrapper = $(this), 
 
       gallery = gallery_wrapper.find('ul'), 
 
       items = gallery.find('li'), 
 
       len  = items.length, 
 
       current = 1, /* the current item we're looking */ 
 
       first = items.filter(':first'), 
 
       last = items.filter(':last'), 
 
       w = gallery.find('li').width(), 
 
       triggers = gallery_wrapper.find('.arrow'); 
 
      var show_slide = function(direction,w){ 
 
       gallery.animate({ left: "+=" + (-w * direction) }, function() { 
 

 
        current += direction; 
 

 
        /** 
 
        * we're cycling the slider when the the value of "current" 
 
        * variable (after increment/decrement) is 0 or when it exceeds 
 
        * the initial gallery length 
 
        */ 
 
        cycle = !!(current === 0 || current > len); 
 

 
        if (cycle) { 
 
         /* we switched from image 1 to 4-cloned or 
 
         from image 4 to 1-cloned */ 
 
         current = (current === 0)? len : 1; 
 
         gallery.css({left: -w * current }); 
 
        } 
 
       }); 
 
      }; 
 
      var picTimer = setInterval(function() { 
 
         show_slide(settings.direction,w); 
 
        }, 
 
        settings.time); 
 
      return this.each(function(){ 
 

 
       /* 1. Cloning first and last item */ 
 
       first.before(last.clone(true)); 
 
       last.after(first.clone(true)); 
 
       /* 2. Set button handlers */ 
 
       triggers.on('click', function() { 
 
        if (gallery.is(':not(:animated)')) { 
 

 
         var cycle = false; 
 
         settings.direction = ($(this).hasClass('prev'))? -1 : 1; 
 
         /* in the example buttons have id "prev" or "next" */ 
 
         show_slide(settings.direction,w); 
 
        } 
 
        clearInterval(picTimer); 
 
        picTimer = setInterval(function() { 
 
           show_slide(settings.direction,w); 
 
          }, 
 
          settings.time); 
 
       }); 
 
       /* hover show arrows*/ 
 
       show_slide(settings.direction,w); 
 

 
       gallery_wrapper.hover(function() { 
 
        $(this).find(".arrow").css("opacity", 0.0).stop(true, false).animate({ 
 
           "opacity": "0.3" 
 
          }, 
 
          300); 
 
       },function(){ 
 
        $(this).find(".arrow").css("opacity", 0.3).stop(true, false).animate({ 
 
           "opacity": "0" 
 
          }, 
 
          300); 
 
       }); 
 
      }); 
 
     }; 
 
     $('#top_goods_gallery.gallery').gallery(); 
 
     $('#top_sale_gallery.gallery').gallery({ 
 
      time: 5000, 
 
      direction:-1 
 
     }); 
 
    }); 
 
</script> 
 
</html>

TEと私のプロジェクトでこれを使用しています。

2

私はちょうど項目のスライダーを作成しました:それをチェックアウト: それはコードの600行だhttps://github.com/lingtalfi/jItemSlider/blob/master/README.md

、多分あなたは単にそれを閲覧することができます。

アイデアは、ネットフリックススライダ(2016-02-24現在)からインスピレーションを受けています。

基本的には、ブラウザで最も速く/滑らかであるため、CSS変換を使用しています。今

http://eng.wealthfront.com/2015/05/19/performant-css-animations/

スライド運動の背後にある基本的な概念、あなただけの現在の表示のスライス、 を表示していますが、一つ左の目に見えないスライス、右側に別の見えないのスライスを持っているということです。

そして、あなたの項目は次のようになりように、あなたはまた、2つの追加項目、各側に1つを持っている:

前の項目 - 前の余分なアイテム - 主な項目 - 次の余分な項目 - 次の項目を

メインアイテムのみが表示されます。 余分な項目は部分的に表示されます。 前と次の項目は見えません。

ここ

詳細:あなたは(例えば)右にスライドさせたときに https://github.com/lingtalfi/jItemSlider/blob/master/doc/conception.md

さて、あなたは基本的に右側に複数の項目を追加し、 た後、左側からそれらを削除します。

このテクニックは、目に見えないアイテムを削除せずに クローンを使用してアイテムの長いリストを処理しないため、これまでに遭遇したことが最大です。

注:このスライダの私の最初の試みは、実際に削除せずにクローニングされた、それは動作しますが、私はそれを好きではない: https://github.com/lingtalfi/jInfiniteSlider

また、それはアイテムベースの(というよりもピクセルベース)だ、とでこれは、ユーザーが期待しているのは、 であるため、すべてが常に整列しているためです。