Heim >Web-Frontend >js-Tutorial >JavaScript-Codebeispiel einer Bildkarussellkomponente

JavaScript-Codebeispiel einer Bildkarussellkomponente

高洛峰
高洛峰Original
2016-12-05 17:14:251300Durchsuche

In diesem Artikel wird JavaScript zur Implementierung der Bildkarussellkomponente vorgestellt. Schauen Sie sich einfach Folgendes an:

Effekt:

JavaScript-Codebeispiel einer Bildkarussellkomponente

Automatische Endlosschleife Spielen Sie das Bild ab. Unten befindet sich eine Schaltfläche, mit der Sie zum entsprechenden Bild wechseln können.

Fügen Sie eine Animation hinzu, um Bilder zu wechseln.

Wenn die Maus auf dem Bild geparkt ist, stoppt das Karussell und links und rechts werden zwei Pfeile angezeigt. Klicken Sie, um das Bild zu wechseln.

Wenn sich die Maus vom Bildbereich entfernt, wird das Karussell an der aktuellen Position fortgesetzt.

Bietet eine Schnittstelle zum Festlegen der Karussellrichtung, der Schleife und des Intervalls.

Anforderungen für HTML und CSS:

<div class="carousel-box">
  <div class="carousel">
    <ul class="clearfix" >
      <li><img src="img/carousel01.jpg" alt=""></li>
      <li><img src="img/carousel02.jpg" alt=""></li>
      <li><img src="img/carousel03.jpg" alt=""></li>
      <li><img src="img/carousel04.jpg" alt=""></li>
      <li><img src="img/carousel05.jpg" alt=""></li>
      <li><img src="img/carousel06.jpg" alt=""></li>
    </ul>
  </div>
</div>

Es müssen zwei verschachtelte Felder vorhanden sein, das innerste Feld muss eine UL haben und das Bild muss in der LI enthalten sein.

Sie können den Klassennamen ändern und den entsprechenden Klassennamen in der CSS-Datei ersetzen. Übergeben Sie einfach das richtige DOM-Element, wenn Sie die Komponente konfigurieren.

Es gibt keine Begrenzung für die Breite und Anzahl der Bilder, ändern Sie einfach die Werte in der CSS-Datei.

/*需要更改的值*/
.carousel img{ 
  width: 600px;
  height: 400px;
}
.carousel,
.carousel-box {
  width: 600px; /*单张图片宽度*/
  height: 400px; /*单张图片高度*/
}
.carousel ul{
  width: 3600px; /*单张图片宽度x图片数量*/
}

Prinzip:

Ordnen Sie alle Bilder horizontal an und legen Sie overflow:hidden auf dem äußersten Behälter und dem Verpackungsbehälter fest. Der äußerste Container dient zur Positionierung von Schaltflächen und Pfeilen. Verwenden Sie die scrollLeft-Eigenschaft des Wrapper-Containers, um zu steuern, welches Bild angezeigt wird.

Idee:

Um diese Funktionen zu erreichen, sollte es folgende Methoden geben:

1. Bildwechselfunktion. Akzeptiert einen Parameter, der die Bildlaufrichtung angibt. Rufen Sie die Easing-Funktion auf, um Bilder zu wechseln. Rufen Sie die Funktion zum Umschalten des Tastensymbols auf, um die entsprechende Taste zum Leuchten zu bringen.

2. Lockerungsfunktion.

3. Beleuchten Sie die Tastenfunktion.

4. Initialisierungsfunktion. Wird verwendet, um Ereignisse zu binden, Schaltflächen und Pfeile zu erstellen und Anfangspositionen zu initialisieren.

5. Erstellen Sie eine Pfeilfunktion.

6. Schaltflächenfunktion erstellen.

7. Starten Sie die Karussellfunktion.

8. Karussellfunktion.

9. Stoppfunktion. Wird verwendet, um das Karussell zu stoppen.

Es gibt auch einige öffentliche Methoden: $(): DOM-Elemente auswählen. addClass(ele,"className"): Fügen Sie dem Element einen Klassennamen hinzu. RemoveClass(ele,"className") entfernt den Klassennamen eines Elements. $.add(ele,"type",fun): Binden Sie ein Ereignis an einen DOM-Knoten. getCSS(ele,"prop"): Ruft den Wert des entsprechenden Attributs des Elements ab. $.delegateTag("selector","tagName","type",fun): Ereignis-Proxy.

Implementierung:

Angenommen, es gibt 6 Bilder, jedes Bild hat eine Breite von 600 Pixel. Vervollständigen Sie entsprechend der Unabhängigkeit der Funktionen:

1. Beschleunigungsfunktionsliner

Die Funktion der Beschleunigungsfunktion besteht darin, den Attributwert des Zielelements Stück für Stück zu ändern, bis das Ziel erreicht ist erreichter Wert ist. Das Element, das es verwendet, kann ein horizontal gedrehtes Bild, ein vertikal gedrehtes Bild oder ein kleiner Kasten sein, der vom linken Ende der Seite bis zum rechten Ende der Seite reichen soll. Es sollte also vier Parameter erhalten (Zielelement, zu ändernder Attributwert, Zielwert, Anzahl der Züge).

liner=function(ele,prop,next,num){
  var speed=(next-ele[prop])/num,
    i=0;
  (function(){
    ele[prop]+=speed;
    i++;
    if (i<num) {
      setTimeout(arguments.callee,30);
    }
  })();  
},

2. Licht der Tastenfunktion

Das Aufleuchten der Taste bedeutet im Wesentlichen das Hinzufügen einer aktiven Klasse zur Taste, und das Ausschalten der Taste bedeutet, die aktive Klasse aus der Taste zu entfernen Taste.

Woher wissen Sie also, welche Schaltfläche die aktuelle ist?

Die einfachste Methode besteht darin, es direkt abzurufen, sodass Sie jeder Schaltfläche ein Indexattribut hinzufügen können. Wenn Sie die Schaltfläche beleuchten müssen, übergeben Sie den Index der zu beleuchtenden Schaltfläche an diese Funktion.

Woher wissen Sie also, welche Taste Sie ausschalten müssen?

Die einfachste Methode besteht darin, sie direkt abzurufen. Sie können also eine aktive Variable am Ende der Bereichskette hinzufügen, sich die aktuell leuchtende Schaltfläche merken und diese Funktion direkt ausschalten.

light=function(index){
  removeClass(active,"active");
  active=$(this.wrapSelec+" "+"[index="+index+"]");
  addClass(active,"active");
}

3. Die Bildwechselfunktion go

muss den Wert des nächsten scrollLeft berechnen:

Wenn es sich nach links bewegt, sollte scrollLeft -600 sein , wenn es bereits 0 ist, wechseln Sie zu 3000. Es ist also ele.scrollLeft===0?width*(len-1):ele.scrollLeft-width;

Wenn es sich bewegt rechts sollte scrollLeft +600 sein, das heißt 0——>600, 600——>1200,..., 3000——>0. Hier können Sie die oben beschriebene Beurteilung verwenden oder die Formel next=(cur+distance)%(distance*num) verwenden. Das heißt, (ele.scrollLeft+width)%(width*len)

muss den Index der nächsten Schaltfläche abrufen, die beleuchtet werden soll:

Die gleiche Idee wie bei der Berechnung von scrollLeft, gehe zu links: index===0? len-1:index-1; Nach rechts verschieben: (index+1)%len

go=function(dire){
  var index=active.getAttribute("index")-0,
    nextIndex,
    nextPosition;
  if (dire==="next") {
    nextIndex=(index+1)%len;
    nextPosition=(ele.scrollLeft+width)%(width*len);
  }else{
    nextIndex=index===0? len-1:index-1,
    nextPosition=ele.scrollLeft===0?width*len:ele.scrollLeft-width;
  }
  light(nextIndex);
  animate.liner(ele,"scrollLeft",nextPosition);  
}

wobei len (Gesamtzahl der Bilder), width (Bildbreite) Auf ele (Wrapping-Container) wird auch von anderen Funktionen zugegriffen, daher wird es auch am Ende der Bereichskette hinzugefügt.

len=ele.getElementsByTagName("img").length

width=parseInt(getCSS(ele.getElementsByTagName("img")[0],"width");

ele=$(eleSelec), eleSelec ist der Selektor des Verpackungscontainers, z. B. .carousel

4. Erstellen Sie die Pfeilfunktion createArrow

, um einen Pfeil nach links zu erstellen und binden Sie den Ereignishandler, um ihn nach links zu verschieben. Erstellen Sie einen Rechtspfeil und binden Sie den Ereignishandler, um ihn nach rechts zu verschieben.

createArrow=function(){
  var prev=document.createElement("div"),
    next=document.createElement("div");
  prev.appendChild(document.createTextNode("<"));
  next.appendChild(document.createTextNode(">"));
  prev.className="arrow prev";
  next.className="arrow next";  
  container.appendChild(prev);
  container.appendChild(next);
  addClass(container,"hide");
  $.add(next,"click",function(){
    go("next");
  });
  $.add(prev,"click",function(){
    go("prev");
  });
}

Der Container stellt den äußersten Container dar und wird auch von anderen verwendet Funktionen. Zugriff, daher wird es auch am Ende der Bereichskette

container=$(wrapSelec) hinzugefügt. WrapSelec ist der Selektor des äußersten Containers, z. B. .carousel-box

5. Erstellen Sie die Schaltflächenfunktion createBtn

给每个按钮添加一个index用于点亮和熄灭,给按钮组添加一个类名用于设置样式和获取它:

createBtn=function(){
  var div=document.createElement("div"),
    btns=&#39;&#39;;
  for(var i=0;i<len;i++){
    btns+=&#39;<a href="#" index="&#39;+i+&#39;"></a>&#39;;
  }
  div.innerHTML=btns;
  addClass(div,"carousel-btn");
  container.appendChild(div);
}

6.轮播函数

根据要求(顺时针、逆时针)判断要调用go("prev")还是go("next")。

如果要求循环,则再次调用自己。如果不循环,则在轮播一轮后停止。

所以这里需要一个变量来判断方向,一个变量来判断是否循环,一个变量来计数。

所以又有四个变量被加到作用域链末端。direction、loop、count、begin用于清除定时器。

circle=function(){
  count++;
  if (loop||count<len) {
    if (direction==="forward") {
      go("next");
    }else{
      go("prev");
    }
  }
  begin=setTimeout(arguments.callee,t);
}

7.停止函数 stop

stop=function(){
  clearTimeout(begin);
}

8.初始化函数 init

如果是第一次使用轮播,则创建按钮和箭头,并给按钮绑定click事件处理程序(获取点击的按扭index点亮它,切换到相应图片),然后根据顺时针或逆时针来展示相应的图片和按钮。

所以这里又需要有一个变量加在作用域链末端,用于表示是否已经初始化。

init=function(){
  createBtn();
  createArrow();
  $.delegateTag(wrapSelec+" "+".carousel-btn","a","click",function(e,target){
    $.prevent(e);
    light(target.getAttribute("index"));
    animate.liner(ele,"scrollLeft",target.getAttribute("index")*width);
  });
  $.add(container,"mouseenter",function(){
    stop();
    removeClass(container,"hide");
  });
  $.add(container,"mouseleave",function(){
    addClass(container,"hide");
    begin=setTimeout(circle,t); 
  });if (direction==="forward") {
    light(0);
  }else{
    light(len-1);
    ele.scrollLeft=width*(len-1);
  }
  haveStart=true;
}

9.开始轮播函数 start

这个函数当做接口,用于控制轮播方向,间隔时间,和是否循环。计数器归零。

因为可能重复的开始轮播,所以每次开始之前都需要清除定时器。

start=function(dir,th,lo){
  stop();
  count=0;
  direction=dir;
  t=th*1000;
  loop=lo;
  if (!haveStart) {
    init();
  }
  begin=setTimeout(circle,t);
}

到这里,所有需要用到的函数已经写完了,如果把这些函数和那些需要的变量扔到一个函数里,把外层容器盒包裹容器的类名或ID传给它,这个函数返回一个包含start和stop方法的对象,这个组件就可以使用了。

但是有一个问题,这个函数只有一个,也就是说,一个页面只能有一个轮播实例。所以,如果想要一个页面能有两个轮播实例都用这个组件的话,就不能把它们扔到一个函数里。那么就只能放到对象里。每个对象有自己的变量,他们共用一组方法。

那么,这些变量就不能直接访问了,需要通过对象的属性访问,即this。

这时候就会出现问题,this是会指向调用它的那个环境,所以当那些变量在事件处理程序中,或是在定时器中被访问的时候,就不能用this,而是要创建一个闭包。

即,在能获取到this时,将this赋值给一个变量,然后在事件处理程序或是定时器中访问这个变量,就会获取到正确的对象。

以init函数为例来改装:

carouselProto.init=function(){
  var that=this;
  this.createBtn();
  this.createArrow();
  $.delegateTag(this.wrapSelec+" "+".carousel-btn","a","click",function(e,target){
    $.prevent(e);
    that.light(target.getAttribute("index"));
    animate.liner(that.ele,"scrollLeft",target.getAttribute("index")*that.width);
  });
  $.add(this.container,"mouseenter",function(){
    that.stop();
    removeClass(that.container,"hide");
  });
  $.add(this.container,"mouseleave",function(){
    addClass(that.container,"hide");
    that.begin=setTimeout(function(){
      that.circle();
    },that.t); 
  });if (this.direction==="forward") {
    this.light(0);
  }else{
    this.light(this.len-1);
    this.ele.scrollLeft=this.width*(this.len-1);
  }
  this.haveStart=true;
};

这样改装完之后,就可以创建实例了,每个实例都会有自己的属性用于记录状态,他们都共用原型中的方法。

如果采用原型继承的方式的话,可以创建一个对象作为实例的原型对象,然后创建一个函数来生产实例:

var carouselProto={};
 
//把上面那些方法给这个对象
carouselProto.light=...
carouselProto.go=...
carouselProto.stop=...
 
//创建实例对象函数
var carousel=function(eleSelec,wrapSelec){
  var that=Object.create(carouselProto);
  that.wrapSelec=wrapSelec;
  that.ele=$(eleSelec);
  that.container=$(wrapSelec);
  that.len=that.ele.getElementsByTagName("img").length;
  that.width=parseInt(getCSS(that.ele.getElementsByTagName("img")[0],"width"));
  return that;
}
 
//创建实例,使用组件
var carousel1=carousel(".carousel",".carousel-box");
   carousel1.start("forward",3,true);
var carousel2=carousel(".carousel2",".carousel-box2");
   carousel2.start("backward",2,true);

性能优化:

1.当点击的按钮刚好是当前被点亮的按钮时,依然会调用一次light和animate.liner。所以可以添加一个判断语句,如果点击的按钮刚好是正确的,就不要执行下面的了。

$.delegateTag(this.wrapSelec+" "+".carousel-btn","a","click",function(e,target){
  $.prevent(e);
  var index=target.getAttribute("index");
  if (index===that.active.getAttribute("index")) {
    return
  }
  that.light(index);
  animate.liner(that.ele,"scrollLeft",target.getAttribute("index")*that.width);
});

2.当图片切换的时候,缓动动画正在执行。如果在缓动动画还没执行完时就点击按钮或者箭头,就会进入下一次动画,于是就会出现混乱,图片错位。性能也会受到影响。为了防止这种情况发生,可以使用一个变量,用于记录缓动动画是否正在执行,没有执行的话点击按钮或箭头才会执行函数。

liner=function(ele,prop,next){
  var speed=(next-ele[prop])/10,
    i=0;
  ele.animating=true;
  (function(){
    ele[prop]+=speed;
    i++;
    if (i<10) {
      setTimeout(arguments.callee,60);
    }else{
      ele.animating=false;
    }
  })();  
}
if (!this.ele.animating) {
  this.light(nextIndex);
    animate.liner(this.ele,"scrollLeft",nextPosition);
}


Stellungnahme:
Der Inhalt dieses Artikels wird freiwillig von Internetnutzern beigesteuert und das Urheberrecht liegt beim ursprünglichen Autor. Diese Website übernimmt keine entsprechende rechtliche Verantwortung. Wenn Sie Inhalte finden, bei denen der Verdacht eines Plagiats oder einer Rechtsverletzung besteht, wenden Sie sich bitte an admin@php.cn