Created
April 10, 2012 12:37
-
-
Save netojoaobatista/2351090 to your computer and use it in GitHub Desktop.
Exemplo de comutação de classes CSS em Javascript
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<!DOCTYPE html> | |
<html> | |
<head> | |
<meta charset="UTF-8" /> | |
<title>Sample</title> | |
<style type="text/css"> | |
html { font-family: Helvetica,sans-serif; } | |
.horizontal > * { | |
float: left; | |
} | |
div.toggle { | |
display: block; | |
width: 200px; | |
height: 200px; | |
border: 1px solid #999999; | |
background-color: #DADADA; | |
margin-top: 10px; | |
transition: all 300ms ease-out; | |
-moz-transition: all 300ms ease-out; | |
-webkit-transition: all 300ms ease-out; | |
} | |
div.toggle:not(:first-child) { | |
margin-left: 10px; | |
} | |
div.toggle.hidden { | |
opacity:0; | |
} | |
.button { | |
display: inline-block; | |
padding: 4px 8px; | |
border: 0px none; | |
text-decoration: none; | |
background-color: #DD3333; | |
color: #FFFFFF; | |
border-radius: 4px; | |
-moz-border-radius: 4px; | |
-webkit-border-radius: 4px; | |
} | |
</style> | |
<script> | |
/** | |
* Anexa, dispara e remove eventos de elementos do documento. | |
* @constructor | |
* @param source Seletor CSS ou o próprio elemento de origem. | |
*/ | |
function EventDispatcher(source) { | |
this.source = { | |
elements: [], | |
listeners: {} | |
}; | |
if (source instanceof Node) { | |
this.source.elements.push(source); | |
} else if (typeof source==="string") { | |
var query = document.querySelectorAll(source); | |
for (var i = 0; i<query.length; ++i) { | |
this.source.elements.push(query.item(i)); | |
} | |
} | |
}; | |
EventDispatcher.prototype = (function(){ | |
var addEvent = function(element,type,handler) { | |
if (element.addEventListener) { | |
element.addEventListener(type,handler,false); | |
} else if (element.attachEvent) { | |
element.attachEvent("on"+type,handler); | |
} else { | |
element["on"+type]=handler; | |
} | |
}; | |
var dispatchEvent = function(element,type,handler) { | |
if (document.createEvent) { | |
var evt = document.createEvent("MouseEvents"); | |
evt.initEvent(type,true,false); | |
element.dispatchEvent(evt); | |
} else if (document.createEventObject) { | |
var evt = document.createEventObject(); | |
element.fireEvent("on"+type,evt); | |
} else if (handler !== undefined && typeof handler == "function") { | |
handler.call(this,{target: element }); | |
} | |
}; | |
var removeEvent = function(element,type,handler) { | |
if (element.removeEventListener) { | |
element.removeEventListener(type,handler,false); | |
} else if (element.detachEvent) { | |
element.detachEvent("on"+type,handler); | |
} else if (element["on"+type] !== undefined) { | |
delete element["on"+type]; | |
} | |
}; | |
return { | |
/** | |
* Adiciona um manipulador para determinado tipo de evento. | |
* @param {String} type O tipo do evento (click, mouseover, etc). | |
* @param {Function} handler O manipulador do evento. | |
* @return {EventDispatcher} Referência ao próprio objeto. | |
*/ | |
addEventListener: function(type,handler) { | |
if (this.source.listeners[type]===undefined) { | |
this.source.listeners[type]=[]; | |
} | |
this.source.listeners[type].push(handler); | |
for ( var i = 0; i<this.source.elements.length;++i ) { | |
addEvent(this.source.elements[i],type,handler); | |
} | |
return this; | |
}, | |
/** | |
* Dispara um tipo evento. | |
* @param {String} type O tipo do evento que será disparado. | |
* @return {EventDispatcher} Referência ao próprio objeto. | |
*/ | |
dispatchEvent: function(type) { | |
if (this.source.listeners[type] !== undefined) { | |
for ( var i = 0; i<this.source.listeners[type].length; ++i ) { | |
for ( var j = 0; j<this.source.elements.length; ++j ) { | |
dispatchEvent(this.source.elements[j],type,this.source.listeners[i]); | |
} | |
} | |
} | |
return this; | |
}, | |
/** | |
* Remove um manipulador de um tipo de evento. | |
* @param {String} type O tipo de evento que terá um manipulador | |
* removido. | |
* @param {Function} handler O manipulador que será removido. | |
* @return {EventDispatcher} Referência ao próprio objeto. | |
*/ | |
removeEventListener: function(type,handler) { | |
if(this.source.listeners[type]!==undefined) { | |
var listeners = []; | |
for ( var i = 0; i<this.source.listeners[type].length ; ++i ) { | |
if (this.source.listeners[type][i]!=handler) { | |
listeners.push(this.source.listeners[type][i]); | |
} else { | |
for ( var j = 0; j <this.source.elements.length; ++j ) { | |
removeEvent(this.source.elements[j],this.source.listeners[type][i]); | |
} | |
} | |
} | |
this.source.listeners[type] = listeners; | |
removeEvent(type,handler); | |
} | |
return this; | |
} | |
} | |
}()); | |
/** | |
* Comutador de classes CSS. | |
* @constructor | |
* @param {String} sourceSelector Seletor CSS dos elementos que serão | |
* observados por um determinado evento. | |
* @param {String} targetSelector Seletor CSS dos elementos que serão | |
* comutados caso determinado evento ocorra. | |
*/ | |
function Toggle(sourceSelector,targetSelector) { | |
EventDispatcher.apply(this,[sourceSelector]); | |
this.target = document.querySelectorAll(targetSelector); | |
} | |
Toggle.prototype = new EventDispatcher(); | |
/** | |
* Método callback que será chamado sempre que o estado de um | |
* elemento for comutado. | |
* @param {HTMLElement} element O elemento que foi comutado. | |
* @param {Event} evt O evento que causou a comutação. | |
*/ | |
Toggle.prototype.change = function(element,evt) {}; | |
/** | |
* Manipulador base de eventos. | |
* @param {String} evt Nome do evento que causará a comutação. | |
* @param {String} toggle Classe CSS que será comutada. | |
*/ | |
Toggle.prototype.handler = function(evt,toggle) { | |
var hasChangeHandler = typeof this.change == "function"; | |
for (var i = 0; i < this.target.length ; ++i ) { | |
var element = this.target.item(i); | |
var classes = (element.getAttribute("class")||""); | |
if (classes.indexOf(toggle) >= 0) { | |
classes = classes.split(toggle).join(""); | |
} else { | |
classes += " " + toggle; | |
} | |
element.setAttribute("class",classes); | |
if (hasChangeHandler) { | |
this.change.apply(this,[element,evt]); | |
} | |
} | |
}; | |
/** | |
* Observa a ocorrência de um evento em um elemento e comuta a classe | |
* CSS defida. | |
* @param {String} evt Nome do evento que causará a comutação. | |
* @param {String} toggle Nome da classe CSS que será comutada. | |
* @return {Toggle} Instância do objeto Toggle. | |
*/ | |
Toggle.prototype.observe = function(evt,toggle) { | |
var instance = this; | |
this.addEventListener(evt,function(evt) { | |
instance.handler.apply(instance,[evt,toggle]); | |
}); | |
return this; | |
}; | |
(new EventDispatcher(document)).addEventListener("DOMContentLoaded",function(){ | |
(new Toggle("#toggle-button",".toggle")).observe("click","hidden"); | |
}); | |
</script> | |
</head> | |
<body> | |
<a id="toggle-button" class="button" href="#">Comutar</a> | |
<div class="horizontal"> | |
<div class="toggle"></div> | |
<div class="toggle"></div> | |
</div> | |
</body> | |
</html> |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment