blob: ca6d7837e7847f8a31a8333ffa4ff281387ffed2 [file] [log] [blame]
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.apache.jena.atlas.event;
import java.util.ArrayList ;
import java.util.HashMap ;
import java.util.List ;
import java.util.Map ;
/** The event system - the single, global event manager control the registration and delivery of events.
* An event is a label and an argument. */
public class EventManager
{
private static EventManager eventManager = new EventManager() ;
// Public operations
static public void register(Object object, EventType type, EventListener listener)
{ eventManager.register$(object, type, listener) ; }
/** Unregister a listener for events */
static public void unregister(Object object, EventType type, EventListener listener)
{ eventManager.unregister$(object, type, listener) ; }
/** Send an event to all listeners on an object for the event's type */
static public void send(Object dest, Event event)
{ eventManager.send$(dest, event) ; }
// All registered objects
// All registered type
// ---- The object EventManager itself
// There are 2 event sets: one for specific objects and one for general event types (no object)
// MultipMap.MultiMapToList
private Map<Object, Map<EventType, List<EventListener>>> listenersByObject = new HashMap<>() ;
private Map<EventType, List<EventListener>> listenersAllObjects = new HashMap<>() ;
// Singleton above.
private EventManager () {}
private void register$(Object object, EventType type, EventListener listener)
{
Map<EventType, List<EventListener>> x = get(object) ;
if ( x == null )
{
// Because listeners2 is never null.
x = new HashMap<>() ;
listenersByObject.put(object, x) ;
}
List<EventListener> z = x.get(type) ;
if ( z == null )
{
//?? new CopyOnWriteArrayList<EventListener>() ;
z = new ArrayList<>() ;
x.put(type, z) ;
}
z.add(listener) ;
}
private void unregister$(Object object, EventType type, EventListener listener)
{
List<EventListener> x = find(object, type) ;
if ( x == null )
return ;
x.remove(listener);
// if the list has gone to zero, remove it.
if ( x.size() != 0 )
return ;
if ( object == null )
{
listenersAllObjects.remove(type) ;
return ;
}
listenersByObject.get(object).remove(type) ;
// if the map for this object has gone to zero, remove it.
if ( listenersByObject.get(object).size() == 0 )
listenersByObject.remove(object) ;
}
private void send$(Object dest, Event event)
{
// Send on the specific object channel.
if ( dest != null )
{
Map<EventType, List<EventListener>> map = listenersByObject.get(dest) ;
if ( map != null )
send(dest, event, map) ;
}
// // Check.
// List<EventListener> x = find(dest, event.getType()) ;
// if ( x == null )
// {
// deliveryFailure(dest, event) ;
// return ;
// }
// Now send on the "all objects channel"
send(dest, event, listenersAllObjects) ;
}
private void send(Object dest, Event event, Map<EventType, List<EventListener>> listeners)
{
List<EventListener> x = listeners.get(event.getType()) ;
if ( x != null )
{
for ( EventListener listener : x )
listener.event(dest, event) ;
}
}
private void deliveryFailure(Object object, Event event)
{}
private Map<EventType, List<EventListener>> get(Object object)
{
if ( object == null )
return listenersAllObjects ;
else
return listenersByObject.get(object) ;
}
private List<EventListener> find(Object object, EventType type)
{
Map<EventType, List<EventListener>> x = get(object) ;
if ( x == null )
return null ;
List<EventListener> z = x.get(type) ;
return z ;
}
}