# This patch file was generated by NetBeans IDE # Following Index: paths are relative to: /doma/jarda/netbeans-src/openide/util # This patch can be applied using context Tools: Patch action on respective folder. # It uses platform neutral UTF-8 encoding and \n newlines. # Above lines and this line are ignored by the patching process. Index: test/unit/src/org/openide/util/ChangeSupportTest.java *** /doma/jarda/netbeans-src/openide/util/test/unit/src/org/openide/util/ChangeSupportTest.java No Base Revision --- /doma/jarda/netbeans-src/openide/util/test/unit/src/org/openide/util/ChangeSupportTest.java Locally New *************** *** 1,0 **** --- 1,131 ---- + /* + * The contents of this file are subject to the terms of the Common Development + * and Distribution License (the License). You may not use this file except in + * compliance with the License. + * + * You can obtain a copy of the License at http://www.netbeans.org/cddl.html + * or http://www.netbeans.org/cddl.txt. + * + * When distributing Covered Code, include this CDDL Header Notice in each file + * and include the License file at http://www.netbeans.org/cddl.txt. + * If applicable, add the following below the CDDL Header, with the fields + * enclosed by brackets [] replaced by your own identifying information: + * "Portions Copyrighted [year] [name of copyright owner]" + * + * The Original Software is NetBeans. The Initial Developer of the Original + * Software is Sun Microsystems, Inc. Portions Copyright 1997-2007 Sun + * Microsystems, Inc. All Rights Reserved. + */ + + package org.openide.util; + + import java.util.Arrays; + import java.util.HashSet; + import java.util.List; + import java.util.Set; + import java.util.concurrent.CopyOnWriteArrayList; + import junit.framework.TestCase; + import javax.swing.event.ChangeEvent; + import javax.swing.event.ChangeListener; + + /** + * + * @author Andrei Badea + */ + public class ChangeSupportTest extends TestCase { + + public ChangeSupportTest(String testName) { + super(testName); + } + + public void testChangeSupport() { + final int[] changeCount = { 0 }; + class Listener implements ChangeListener { + private int notified; + private ChangeEvent lastEvent; + public void stateChanged(ChangeEvent event) { + lastEvent = event; + notified++; + } + public int getNotifiedAndReset() { + try { + return notified; + } finally { + notified = 0; + } + } + public ChangeEvent getLastEvent() { + return lastEvent; + } + } + ChangeSupport support = new ChangeSupport(); + Listener listener1 = new Listener(), listener2 = new Listener(); + + support.addChangeListener(null); + assertEquals(0, support.getChangeListeners().length); + + support.removeChangeListener(null); + assertEquals(0, support.getChangeListeners().length); + + support.addChangeListener(listener1); + support.addChangeListener(listener2); + Set listeners = new HashSet(Arrays.asList(support.getChangeListeners())); + assertEquals(2, listeners.size()); + assertTrue(listeners.contains(listener1)); + assertTrue(listeners.contains(listener2)); + + support.fireChange(); + assertEquals(1, listener1.getNotifiedAndReset()); + assertEquals(1, listener2.getNotifiedAndReset()); + assertSame(this, listener1.getLastEvent().getSource()); + + Object source = new Object(); + support.fireChange(new ChangeEvent(source)); + assertEquals(1, listener1.getNotifiedAndReset()); + assertEquals(1, listener2.getNotifiedAndReset()); + assertSame(source, listener1.getLastEvent().getSource()); + + support.fireChange(null); + assertEquals(0, listener1.getNotifiedAndReset()); + assertEquals(0, listener2.getNotifiedAndReset()); + + support.removeChangeListener(new ChangeListener() { + public void stateChanged(ChangeEvent e) { + } + }); + support.fireChange(new ChangeEvent(this)); + assertEquals(1, listener1.getNotifiedAndReset()); + assertEquals(1, listener2.getNotifiedAndReset()); + + support.removeChangeListener(listener1); + support.fireChange(); + assertEquals(0, listener1.getNotifiedAndReset()); + assertEquals(1, listener2.getNotifiedAndReset()); + + support.addChangeListener(listener2); + support.fireChange(); + assertEquals(2, listener2.getNotifiedAndReset()); + + support.removeChangeListener(listener2); + support.fireChange(); + assertEquals(1, listener2.getNotifiedAndReset()); + + support.removeChangeListener(listener2); + support.fireChange(); + assertEquals(0, listener2.getNotifiedAndReset()); + } + + private final class ChangeSupport { + List list = new CopyOnWriteArrayList(); + ChangeListener support = WeakListeners.createSupport(ChangeListener.class, list); + + void addChangeListener(ChangeListener l) { if (l != null) list.add(l); } + void removeChangeListener(ChangeListener l) { list.remove(l); } + void fireChange(ChangeEvent ev) { if (ev != null) support.stateChanged(ev); } + void fireChange() { fireChange(new ChangeEvent(ChangeSupportTest.this)); } + + ChangeListener[] getChangeListeners() { + return list.toArray(new ChangeListener[0]); + } + } + } Index: apichanges.xml *** /doma/jarda/netbeans-src/openide/util/apichanges.xml Base (1.22) --- /doma/jarda/netbeans-src/openide/util/apichanges.xml Locally Modified (Based On 1.22) *************** *** 27,32 **** --- 27,50 ---- + + + + Added support for arbitrary listeners + + + + + +

+ Added a WeakListeners.createSupport class to simplify + the management of any listeners and firing of events to them. +

+
+ + +
+ Added Utilities.isMac() method Index: nbproject/project.properties *** /doma/jarda/netbeans-src/openide/util/nbproject/project.properties Base (1.25) --- /doma/jarda/netbeans-src/openide/util/nbproject/project.properties Locally Modified (Based On 1.25) *************** *** 19,25 **** javac.source=1.5 module.jar.dir=lib ! spec.version.base=7.7.0 # For XMLSerializer, needed for XMLUtil.write to work w/ namespaces under JDK 1.4: --- 19,25 ---- javac.source=1.5 module.jar.dir=lib ! spec.version.base=7.8.0 # For XMLSerializer, needed for XMLUtil.write to work w/ namespaces under JDK 1.4: Index: src/org/openide/util/WeakListeners.java *** /doma/jarda/netbeans-src/openide/util/src/org/openide/util/WeakListeners.java Base (1.3) --- /doma/jarda/netbeans-src/openide/util/src/org/openide/util/WeakListeners.java Locally Modified (Based On 1.3) *************** *** 19,30 **** package org.openide.util; import java.awt.event.FocusListener; - import java.beans.PropertyChangeListener; import java.beans.VetoableChangeListener; ! import java.util.EventListener; - import javax.swing.event.ChangeListener; import javax.swing.event.DocumentListener; --- 19,34 ---- package org.openide.util; import java.awt.event.FocusListener; import java.beans.PropertyChangeListener; import java.beans.VetoableChangeListener; ! import java.lang.reflect.InvocationHandler; ! import java.lang.reflect.Method; ! import java.lang.reflect.Proxy; ! import java.util.Collection; import java.util.EventListener; import javax.swing.event.ChangeListener; import javax.swing.event.DocumentListener; *************** *** 305,311 **** --- 306,341 ---- return wl; } + + /** + * Collection listeners = new CopyOnWriteArrayList(); + * ChangeListener support = WeakListeners.createSupport(ChangeListener.class, listeners); + * + * void addChangeListener(ChangeListener l) { list.add(l); } + * void removeChangeListener(ChangeListener l) { list.remove(l); } + * void stateChanged(ChangeEvent ev) { support.stateChanged(ev); } + * + * @param listenerType the class representing a listener + * @param listeners collection that holds listeners which is safe to be iterated - CopyOnWriteArrayList seems like the best + * @return a dispatch listener to delegate to all listeners in the collection + * @see CopyOnWriteArrayList + * @see CopyOnWriteArraySet + * @since 7.8 + */ + public static L createSupport(Class listenerType, final Collection listeners) { + class H implements InvocationHandler { + public Object invoke(Object target, Method m, Object[] args) throws Throwable { + for (L l : listeners) { + m.invoke(l, args); } + return null; + } + } + H handler = new H(); + return listenerType.cast(Proxy.newProxyInstance(listenerType.getClassLoader(), new Class[] { listenerType }, handler)); + } + }