PageSourceSearch

http://togo-media.com/schooltogo/files/lightbox_files/event_mixins.js

js togo-media.com collected 2026-10-05 09:36:18 UTC 8,130 bytes, 289 lines download raw bytes

1/**
2  *  Event Mixins
3  *  (c) 2006 Seth Dillingham <[email protected]>
4  *
5  *  This software is hereby released into the public domain. Do with it as
6  *  you please, but with the understanding that it is provided "AS IS" and 
7  *  without any warranty of any kind.
8  *  
9  *  (But I'd love to be told about where and how this code is being used.)
10  **/
11  
12/**
13  *  Description:
14  *    add support (to any object or class) by mixing this class into your own
15  *  
16  *  Requires prototype.js
17  *  
18  *  Usage:
19  *    To publish custom events:
20  *      1. mix this class with your own via
21  *         Object.extend( [your class or prototype], Event.Publisher )
22  *      2. post events by calling
23  *         this.dispatchEvent( [event name], [data for event] )
24  *   
25  *    To activate and deactivate the event-tracing feature, just call 
26  *      this.toggleEventsTrace()
27  **/
28
29Event.Publisher = Class.create();
30Object.extend( Event.Publisher, {
31	_ls_event_targets: null,
32	
33	_event_source_id: null,
34	
35	_fl_trace_events: false,
36	
37	getEventSourceId: function() {
38		if ( typeof this._event_source_id == 'function' )
39			return this._event_source_id();
40		else
41			return this._event_source_id;
42	},
43	
44	getEventTarget: function( event_name ) {
45		if ( ! this._ls_event_targets )
46			this._ls_event_targets = new Array();
47		
48		if ( ! this._ls_event_targets[ event_name ] )
49			document.body.appendChild(
50				this._ls_event_targets[ event_name ] = document.createElement( 'A' )
51			);
52		
53		return this._ls_event_targets[ event_name ];
54	},
55	
56	addEventListener: function( event_name, callback_func, capturing ) {
57		var targ = this.getEventTarget( event_name );
58		
59		Event.observe( targ, 'click', callback_func, capturing );
60		
61		if ( this._fl_trace_events ) {
62			var data =  {
63				publisher: this.getEventSourceId(),
64				event_name: event_name,
65				listener: callback_func,
66				capturing: capturing,
67				event_source_proxy: targ
68			};
69			
70			this.dispatchEvent( 'eventListenerAdded', data, true, true );
71		}
72	},
73	
74	removeEventListener: function( event_name, callback_func, capturing ) {
75		var targ = this.getEventTarget( event_name );
76		
77		Event.stopObserving( targ, 'click', callback_func, capturing );
78		
79		if ( this._fl_trace_events ) {
80			var data =  {
81				publisher: this.getEventSourceId(),
82				event_name: event_name,
83				listener: callback_func,
84				capturing: capturing,
85				event_source_proxy: targ
86			};
87			
88			this.dispatchEvent( 'eventListenerRemoved', data, true, true );
89		}
90	},
91	
92	dispatchEvent: function( event_name, data, can_bubble, cancelable ) {
93		var targ = this.getEventTarget( event_name );
94		var event_data = {
95			event_name: event_name,
96			event_target: this,
97			data: data ? data : null
98		};
99		
100		if ( ! can_bubble ) can_bubble = false;
101		if ( ! cancelable ) cancelable = false;
102		
103		var event = Event.create( event_data, can_bubble, cancelable, true, targ );
104		
105		if ( this._fl_trace_events ) {
106			if ( event_name.match( /event(?:ListenerAdded|ListenerRemoved|Dispatched|Received)/ ) )
107				return;
108			
109			var data =  {
110				publisher: this.getEventSourceId(),
111				event_name: event_name,
112				event_data: event_data,
113				can_bubble: can_bubble,
114				cancelable: cancelable,
115				event_source_proxy: targ,
116				result: event
117			};
118			
119			this.dispatchEvent( 'eventDispatched', data, true, true );
120		}
121	},
122	
123	toggleEventsTrace: function() {
124		var trace = Event.Tracer.findTracer();
125		
126		if ( ! trace || ! this._fl_trace_events ) {
127			this._fl_trace_events = true;
128			
129			trace = Event.Tracer.startTrace();
130			
131			trace.registerPublisher( this );
132		}
133		else {
134			this._fl_trace_events = false;
135			
136			if ( trace )
137				trace.unregisterPublisher( this );
138		}
139		
140		return this._fl_trace_events;
141	},
142	
143	isEventsTraceActive: function() {
144		return this._fl_trace_events;
145	}
146} );
147
148/**
149  *  MIX IN: Event.Listener
150  *  
151  *  Description:
152  *    easily add support for receiving totally custom events
153  *    (to any object or class) by mixing this class into
154  *    your own
155  *  
156  *  Usage:
157  *	   To receive custom events:
158  *      1. mix this class with your own via
159  *         Object.extend( [your class or prototype], EventListener )
160  *      2. listen for events by calling (from your object)
161  *         this.listen()
162  *         (see params for this.listen, below)
163  **/
164Event.Listener = Class.create();
165Object.extend( Event.Listener,
166{
167	_listens: null,
168	
169	getEventHandlerName: function( event_name ) {
170		var onEvent_name = event_name.split( /[ _]/ ).join( '-' ).camelize();
171		
172		return "on" + onEvent_name.charAt( 0 ).toUpperCase() + onEvent_name.substr( 1 );
173	},
174	
175	/**
176	  *	 Params:
177      *    event_source [object]:
178      *      the object which will generate the events, and which implements (or
179      *      mixes in) the Event.Publisher interface (we need addEventListener)
180      *    event_name [string]:
181      *      the name of the event for which your object will listen
182      *    use_capture [boolean]:
183      *      standard DOM Event API param
184      *    onEvent_name [string]:
185      *      the name of the method in your object which will be called when the
186      *      event is received if you omit this param, listen will look for a
187      *      function named with the CapitalizedCamelCased name of the event with
188      *      "on" at the front. So, if the event is named "message_received",
189      *      we'll look for a function named "onMessageReceived" You can override
190      *      this behavior by overriding getEventHandlerName in your object.
191	  **/
192	listenForEvent: function( event_source, event_name, use_capture, onEvent_name ) {
193		if ( ! onEvent_name )
194			onEvent_name = this.getEventHandlerName( event_name );
195		
196		if ( ! this._listens ) this._listens = new Array();
197		
198		//added this in to allow for anonymous function handling of an event
199		var eventHandler = this[onEvent_name];
200		
201		if(typeof(onEvent_name) == 'function') {
202			eventHandler = onEvent_name;
203		}
204		
205		var cb = eventHandler.bindAsEventListener( this );
206		this._listens.push( [ event_source, event_name, use_capture, onEvent_name, cb ] )
207		
208		event_source.addEventListener( event_name, cb, use_capture );
209	},
210	
211	stopListeningForEvent: function( event_source, event_name, use_capture, onEvent_name ) {
212		if ( ! this._listens ) return false;
213		
214		if ( ! onEvent_name )
215			onEvent_name = this.getEventHandlerName( event_name );
216		
217		var ix_item = -1;
218		var ls = this._listens.detect( function( val, ix ) {
219			if ( ( val[ 0 ] == event_source )
220			  && ( val[ 1 ] == event_name )
221			  && ( val[ 2 ] == use_capture )
222			  && ( val[ 3 ] == onEvent_name ) ) {
223				ix_item = ix;
224				return true;
225			}
226		} );
227		
228		if ( ix_item >= 0 ) {
229			this._listens.splice( ix_item, 1 );
230			
231			event_source.removeEventListener( event_name, ls[ 4 ], use_capture );
232			
233			return true;
234		}
235		
236		return false;
237	}
238} );
239
240/**
241  *  Extensions to Prototype's Event object,
242  *  for cleanly creating and dispatching custom events
243  *  
244  *  Called from Event.Publisher
245  **/
246Object.extend( Event,
247{
248	create: function( event_data, can_bubble, cancelable, fl_dispatch, target ) {
249		var event;
250		
251		if ( document.createEvent ) {  // gecko, safari
252			if ( ! can_bubble ) can_bubble = false;
253			if ( ! cancelable ) cancelable = false;
254			
255			if ( /Konqueror|Safari|KHTML/.test( navigator.userAgent ) ) {
256				event = document.createEvent( 'HTMLEvents' )
257				
258				event.initEvent( 'click', can_bubble, cancelable );
259			}
260			else {  // gecko uses MouseEvents
261				event = document.createEvent( 'MouseEvents' )
262				
263				event.initMouseEvent( "click", can_bubble, cancelable,
264				                      window, 0, 0, 0, 0, 0,
265				                      false, false, false, false, 0, null );
266			}
267		}
268		else {  // msie
269			event = document.createEventObject();
270			event.event_type = 'onclick';
271		}
272		
273		event.event_data = event_data;
274		
275		if ( fl_dispatch )
276			Event.dispatch( target, event );
277		
278		return event;
279	},
280	
281	dispatch: function( target, event ) {
282		if ( document.createEvent )
283			return target.dispatchEvent( event );
284		else
285			return target.fireEvent( ( typeof( event.event_type ) != "undefined" ) ? event.event_type : 'onclick', event );
286	}
287} );
288
289

Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.