Whitespace and formatting fixes.
[jFCPlib.git] / src / net / pterodactylus / fcp / highlevel / HighLevelCallback.java
index aed413d..7dc55df 100644 (file)
@@ -30,26 +30,29 @@ import java.util.List;
  * @param <R>
  *            The type of the high-level operation result
  * @author David ‘Bombe’ Roden &lt;bombe@freenetproject.org&gt;
- * @version $Id$
  */
 public class HighLevelCallback<R extends HighLevelResult> {
 
        /** Object used for synchronization. */
-       private final Object syncObject = new Object();
+       protected final Object syncObject = new Object();
 
        /** The list of callback listeners. */
        private final List<HighLevelCallbackListener<R>> highLevelCallbackListeners = Collections.synchronizedList(new ArrayList<HighLevelCallbackListener<R>>());
 
        /** Whether the result is complete. */
-       private boolean resultComplete = false;
+       protected boolean resultComplete = false;
 
        /** The result of the operation. */
        private R result = null;
 
        /**
         * Package-private construtor.
+        * 
+        * @param result
+        *            The result of the operation
         */
-       HighLevelCallback() {
+       HighLevelCallback(R result) {
+               this.result = result;
        }
 
        /**
@@ -80,15 +83,17 @@ public class HighLevelCallback<R extends HighLevelResult> {
        }
 
        /**
-        * Notifies all listeners that the result of the operation is now known.
+        * Notifies all listeners that the result of the operation is now known. As
+        * soon as a listener was notified it will be removed from the list of
+        * listeners!
         * 
         * @see HighLevelCallbackListener#gotResult(HighLevelCallback)
         */
        private synchronized void fireGotResult() {
                for (HighLevelCallbackListener<R> highLevelCallbackListener: highLevelCallbackListeners) {
-                       highLevelCallbackListeners.remove(highLevelCallbackListener);
                        highLevelCallbackListener.gotResult(this);
                }
+               highLevelCallbackListeners.clear();
        }
 
        /**
@@ -129,7 +134,7 @@ public class HighLevelCallback<R extends HighLevelResult> {
         */
        public R getResult(long waitTime) throws InterruptedException {
                synchronized (syncObject) {
-                       if (!resultComplete) {
+                       while (!resultComplete) {
                                syncObject.wait(waitTime);
                        }
                        return result;
@@ -137,52 +142,29 @@ public class HighLevelCallback<R extends HighLevelResult> {
        }
 
        /**
-        * Sets the complete result of the operation. Calling this method will
-        * result in all listeners being notified.
-        * 
-        * @see #fireGotResult()
-        * @param result
-        *            The result of the operation
-        */
-       void setResult(R result) {
-               setResult(result, true);
-       }
-
-       /**
-        * Sets the result of the operation. Depending on the <code>notify</code>
-        * parameter the listeners are notified. You have to call this method with
-        * <code>notify = true</code> after your result is completed, otherwise
-        * clients will block endlessly!
+        * Returns the result even if it is not yet complete.
         * 
-        * @param result
-        *            The result of the operation
-        * @param notify
-        *            <code>true</code> to finalize the result and notify all
-        *            listeners, <code>false</code> if something in the result
-        *            might still change
+        * @return The result of the operation
         */
-       void setResult(R result, boolean notify) {
+       R getIntermediaryResult() {
                synchronized (syncObject) {
-                       this.result = result;
-                       if (notify) {
-                               resultComplete = true;
-                               syncObject.notifyAll();
-                       }
-               }
-               if (notify) {
-                       fireGotResult();
+                       return result;
                }
        }
 
        /**
-        * Returns the result even if it is not yet complete.
-        * 
-        * @return The result of the operation
+        * Marks the result as complete and notify the listeners. If the result was
+        * already complete, nothing will be done.
         */
-       R getIntermediaryResult() {
+       void setDone() {
                synchronized (syncObject) {
-                       return result;
+                       if (resultComplete) {
+                               return;
+                       }
+                       resultComplete = true;
+                       syncObject.notifyAll();
                }
+               fireGotResult();
        }
 
 }