//this module's functionality is to create instances of slide, |
//different instances will be easy to control, because everyone has different scope |
//it's a good practise to write maintainable js code |
//please refer: https://www.youtube.com/watch?v=OzjogCFO4Zo |
var SlideModule = ( function () { |
var Slide = function (settings) { |
this .btns = settings.btns; |
this .pics = settings.pics; |
this .picWidth = settings.picWidth; |
this .container = settings.container; |
//to set the default value |
this .span = settings.span || 1000; |
this .currentIndex = 0; |
//I call the init function here to make sure the instances work immediately after initialization |
//but I can also let clients to call this method, if they want to control the behavior, it all depends. |
this .Init(); |
} |
Slide.prototype.Init = function () { |
$( this .btns[0]).css({ "background" : "pink" }) |
//to change the context because of the closure |
var that = this ; |
//to bind the callback functions according to the events |
$.each( this .btns, function (i, btn) { |
//to bind every button with the corresponding picture |
$(btn).on( "mouseover" , function () { |
that.interval && clearInterval(that.interval); |
that.currentIndex = i; |
that.Run(that.currentIndex); |
}); |
$(btn).on( "mouseout" , function () { |
that.GetNextIndex() |
}) |
}); |
this .GetNextIndex(); |
} |
//this function is only responsible to find out the next index of pictures to show |
Slide.prototype.GetNextIndex = function () { |
//clear the interval if it exists |
this .interval && clearInterval( this .interval); |
//to change the context because of the closure |
var that = this ; |
this .interval = setInterval( function () { |
//to ensure the index should be smaller than the length of the buttons(the amount of the buttons and pictures are same) |
that.currentIndex = ++that.currentIndex >= that.btns.length ? 0 : that.currentIndex; |
//call the Run function of the current instance |
that.Run(that.currentIndex); |
}, this .span) |
} |
//this function is the true one to set the layout of the slide. |
Slide.prototype.Run = function (index) { |
//to compute the right position every time |
this .container.css({ "left" : -1 * this .picWidth * index + "px" }); |
//to change the buttons' style |
this .btns.css({ "background" : "white" }) |
$( this .btns[index]).css({ "background" : "pink" }) |
} |
return Slide; |
}()) |
//this class is to demostrate inheritance and polymorphism |
var DerivedSlideModule = ( function (){ |
if (SlideModule.constructor === Function){ |
var DerivedSlide = function (){ |
SlideModule.apply( this , arguments) |
} |
|
DerivedSlide.prototype = Object.create(SlideModule.prototype) |
//to override the same function of the base class |
DerivedSlide.prototype.GetNextIndex = function (){ |
this .interval && clearInterval( this .interval); |
//to change the context because of the closure |
var that = this ; |
this .interval = setInterval( function () { |
//to set the every second picture's index |
that.currentIndex+=2; |
//to ensure the index should be smaller than the length of the buttons(the amount of the buttons and pictures are same) |
that.currentIndex = that.currentIndex >= that.btns.length ? 0 : that.currentIndex; |
//call the Run function of the current instance |
that.Run(that.currentIndex); |
}, this .span) |
}; |
return DerivedSlide; |
} |
return ; |
}()) |
//in order to write testable and maintainable js code, |
//I tried to apply OOP principles to JS |
//abstract the relative class by using function |
//encapsulate properties in constructor function and inheritable functions to prototype chain |
//for polymorphism, I overrided the specific function on the prototype chain. |
$( function () { |
//to call this function, please make sure the amount of the buttons and pictures are same |
var slideModule = new SlideModule({ |
btns: $( "#btns > input[type=button]" ), |
pics: $( "#container > img" ), |
picWidth: 250, |
container: $( "#container" ) |
}); |
|
//create an instance of the derived class |
var slideModule1 = new DerivedSlideModule({ |
btns: $( "#btns1 > input[type=button]" ), |
pics: $( "#container1 > img" ), |
picWidth: 250, |
container: $( "#container1" ) |
}); |
}) |