1 /*
  2 	mooslides-1.0.js by Jean-Nicolas Jolivet (http://www.silverscripting.com)
  3 	Licenced under the MIT license: http://www.opensource.org/licenses/mit-license.php
  4 */
  5 
  6 /**
  7 	Construct a new mooslides object. Make sure that your outterdiv already exists
  8 	and has been inserted in the DOM. (i.e. create a new mooslide in the window.domready
  9 	event.
 10     @class Represents a mooslides object
 11 	@param {String} outterdiv Your main div
 12 	@param {Object} options A set of options (described below)
 13 	
 14 	<dt class="heading">Options</dt>
 15 	@param {bool} [options.customToolbar='false'] Set to true if you plan on using your 
 16 	own toolbar. If you do, you will have to come up with your own Next, Previous, ...,
 17 	buttons. You can use the slideTo(), slideNext(), slidePrevious(), slideFirst() and
 18 	slideLast() functions to help you out.
 19 	
 20 	@param {Fx.Transitions} [options.transitionEffect='Fx.Transitions.Expo.easeOut'] An 
 21 	Fx.Transitions object that will be used when switching panels.
 22 	
 23 	@params {Int} [options.animationDuration='1000'] The duration of the panel switching
 24 	effect.
 25 	
 26 	@param {Int} [options.animationDelay='4000'] Number of milliseconds to wait between 
 27 	panel switching in animation mode.
 28 	
 29 	@param {bool} [options.autoStart='false'] Set to true if you want the animation to 
 30 	start when the page is loaded.
 31 	
 32 	@param {String} [options.buttonClass='toolbar-button'] If you want to use the default toolbar, 
 33 	you can specify a custom class that will be applied to the toolbar's buttons. This is
 34 	only so you can control the styles of the toolbar. Checkout the example abouve, it
 35 	contains a basic style that should get you started.
 36 	
 37 	@example 
 38 	// Creating a new mooslides.
 39 	var myslides = new mooslides('mydiv', {
 40 		customToolbar: false,
 41 		toolbarStyles: myStyles
 42 	});
 43 	
 44 	// an example CSS style that makes a pretty toolbar
 45 	li.toolbar-button {
 46 		display: inline;
 47 		background-color: #262626;
 48 		padding: 2px 5px;
 49 		color: #ddd;
 50 		cursor: pointer;
 51 	}
 52 	
 53  */ 
 54 
 55 var mooslides = new Class({
 56 	/** @lends mooslides.prototype */
 57 	
 58 	Implements: Options,
 59 	options: {
 60 		customToolbar: false,
 61 		transitionEffect: Fx.Transitions.Expo.easeOut,
 62 		animationDelay: 4000,
 63 		animationDuration: 1000,
 64 		autoStart: false,
 65 		buttonClass: 'toolbar-button'
 66 	},
 67 	/**
 68 	@private
 69 	@constructor
 70 	*/
 71 	initialize: function(outterdiv, options) {
 72 		
 73 		this.setOptions(options);
 74 		this.outterdiv = $(outterdiv);
 75 		this.innerdiv = new Element('div', {
 76 			id: 'innerdiv'
 77 		});
 78 		
 79 		this.panels = this.outterdiv.getChildren().filter(".panels");
 80 		if(this.options.customToolbar == false) {
 81 			this.toolbar = this.buildToolbar();
 82 			this.toolbar.inject(this.outterdiv, 'before');
 83 		}
 84 
 85 		
 86 		this.panels.setStyles({
 87 			float: 'left'
 88 		});
 89 		this.size = this.panels[0].getSize();
 90 		this.totalWidth = this.size.x * this.panels.length;
 91 		this.outterdiv.setStyle('width', this.size.x);
 92 		this.innerdiv.setStyle('width', this.totalWidth);
 93 		this.panels.dispose();
 94 		this.panels.inject(this.innerdiv);
 95 		this.innerdiv.inject(this.outterdiv);
 96 		this.outterdiv.setStyle('overflow', 'hidden');
 97 		
 98 		// set the panel's alt to it's id...
 99 		var cnt = 0;
100 		this.panels.each(function(aPanel) {
101 			aPanel.set('alt', cnt + "");
102 			cnt = cnt + 1;
103 			aPanel.addEvent('click', this.panelClicked.bind(this));
104 		}.bind(this));
105 		
106 		this.activePanelId = 0;
107 		this.slideTo(0);
108 
109 		if(this.options.autoStart) {
110 			this.loopStart();
111 		}
112 		
113 	},
114 	
115 	/**
116 	panelClick event. This is mostly for internal use. Note that it fires a "panelClick" event
117 	on the main div each time a panel is clicked. It will send the panel id of the clicked
118 	panel to your callback function.
119 	@event
120 	@returns {Int} The id of the newly selected panel.
121 	*/
122 	panelClicked: function() {
123 		this.outterdiv.fireEvent('panelClick', this.activePanelId);
124 	},
125 	
126 	/**
127 	Builds the toolbar if the user wants to use the default toolbar. *INTERNAL USE*.
128 	@private
129 	*/
130 	buildToolbar: function() {
131 		var newToolbarDiv = new Element('div', {});
132 		
133 		var newToolbarUl = new Element('ul', {
134 			'styles': {
135 				'margin': 0,
136 				'padding': 0
137 			}
138 		});
139 		this.previousButton = new Element('li', {
140 			'class': this.options.buttonClass,
141 			'html' : '<<',
142 			'events': {
143 				'click': function() {
144 					this.slidePrevious();
145 				}.bind(this)
146 			}
147 		});
148 		this.previousButton.inject(newToolbarUl);
149 		var cnt = 1;
150 		this.buttons = [];
151 		this.panels.each(function(aPanel) {
152 			
153 			this.buttons[cnt-1] = new Element('li', {
154 				'html': cnt + "",
155 				'class': this.options.buttonClass,
156 				'title': cnt + ""
157 			});
158 			this.buttons[cnt-1].addEvent('click', function(aButton) {
159 				this.slideTo(aButton.get('title') - 1);
160 			}.bind(this, this.buttons[cnt-1]));
161 			this.buttons[cnt-1].inject(newToolbarUl);
162 			
163 			
164 			cnt = cnt + 1;
165 		
166 		}.bind(this));
167 		this.nextButton = new Element('li', {
168 			'class': this.options.buttonClass,
169 				'html' : '>>',
170 				'events': {
171 					'click': function() {
172 						this.slideNext();
173 					}.bind(this)
174 				}
175 		});
176 		this.nextButton.inject(newToolbarUl);
177 		
178 		newToolbarUl.inject(newToolbarDiv);
179 		return newToolbarDiv;
180 	},
181 	
182 	/**
183 	Slides to the specified panel
184 	@param {Int} panelId The id of the panel to scroll to. (zero-based)
185 	@example
186 	myslides.slideTo(0) // slides to the first panel
187 	*/
188 	slideTo: function(panelId) {
189 		panelId = (panelId < 0) ? 0 : panelId;
190 		panelId = (panelId > this.panels.length - 1) ? this.panels.length - 1 : panelId;
191 		var toX = (panelId ) * this.size.x;
192 		var myFx = new Fx.Scroll(this.outterdiv, {duration: this.options.animationDuration, transition: this.options.transitionEffect}).start(toX, 0);
193 		this.changed(panelId);
194 	},
195 	
196 	/**
197 	Slides to the next panel
198 	@example
199 	myslides.slideNext();
200 	*/
201 	slideNext: function() {
202 		nextPanel =	(this.activePanelId == this.panels.length -1) ? this.activePanelId : this.activePanelId  + 1;
203 		this.slideTo(nextPanel);
204 
205 	},
206 	/**
207 	Slides to the preview panel
208 	@example
209 	myslides.slidePrevious();
210 	*/
211 	slidePrevious: function() {
212 		prevPanel =	(this.activePanelId == 0) ? this.activePanelId : this.activePanelId  - 1;
213 		this.slideTo(prevPanel);
214 	},
215 	
216 	/**
217 	Slides to the first panel
218 	@example
219 	myslides.slideFirst();
220 	*/
221 	slideFirst: function() {
222 		this.slideTo(0);
223 	},
224 	
225 	/**
226 	Slides to the last panel
227 	@example
228 	myslides.slideLast();
229 	*/
230 	slideLast: function() {
231 		this.slideTo(this.panels.length - 1);
232 	},
233 	
234 	/**
235 	Starts the animation. Panels will change at the interval specified
236 	in options. When it reaches the last panel, it will quickly go back
237 	to the first panel.
238 	@example
239 	myslides.loopStart();
240 	*/
241 	loopStart:function () {
242 		this.timer = this.loopNext.periodical(this.options.animationDelay, this);
243 	},
244 	
245 	/**
246 	Stops the animation
247 	@example
248 	myslides.loopStop();
249 	*/
250 	loopStop: function() {
251 		$clear(this.timer);
252 	},
253 	
254 	/**
255 	Do the actual loop. *INTERNAL USE*
256 	@private
257 	*/
258 	loopNext: function() {
259 		if(this.activePanelId == this.panels.length -1) {
260 			var myFx = new Fx.Scroll(this.outterdiv, {duration: 200, transition: this.options.transitionEffect}).start(0, 0);
261 			this.changed(0);
262 		}
263 		else {
264 			this.slideNext();
265 		}
266 	},
267 	
268 	
269 	/**
270 	Similar to slideTo but does it without an animation. This means you will move
271 	instantly to the specified panelId
272 	@param {Int} panelId The id of the panel to warp to. Zero-based.
273 	*/
274 	warpTo: function(panelId) {
275 		panelId = (panelId < 0) ? 0 : panelId;
276 		panelId = (panelId > this.panels.length - 1) ? this.panels.length - 1 : panelId;
277 		var toX = (panelId ) * this.size.x;
278 		var myFx = new Fx.Scroll(this.outterdiv).set(toX, 0);
279 		this.changed(panelId);
280 	},
281 	
282 	/**
283 	Changed event. This is mostly for internal use. Note that it fires a "changed" event
284 	on the main div. You can catch this event. The id of the newly selected panel
285 	will be passed as an argument to your callback function.
286 	@event
287 	@returns {Int} The id of the newly selected panel.
288 	*/
289 	changed: function(newPanel) {
290 		if(this.options.customToolbar == false)
291 		{
292 			
293 			this.buttons[this.activePanelId].removeClass('active');
294 			this.buttons[newPanel].addClass('active');
295 		}
296 		this.activePanelId = newPanel;
297 		this.outterdiv.fireEvent('changed', newPanel);
298 	}
299 });
300