]> gerrit.simantics Code Review - simantics/platform.git/blobdiff - bundles/org.simantics.simulation/src/org/simantics/simulation/project/ExperimentManager.java
Fixed all line endings of the repository
[simantics/platform.git] / bundles / org.simantics.simulation / src / org / simantics / simulation / project / ExperimentManager.java
index 19d8832342f368e61df9241f1ab14b77cfc11b2b..ec56854751f55bc5d5666cb29422b6a7ff10e184 100644 (file)
-/*******************************************************************************\r
- * Copyright (c) 2007, 2010 Association for Decentralized Information Management\r
- * in Industry THTH ry.\r
- * All rights reserved. This program and the accompanying materials\r
- * are made available under the terms of the Eclipse Public License v1.0\r
- * which accompanies this distribution, and is available at\r
- * http://www.eclipse.org/legal/epl-v10.html\r
- *\r
- * Contributors:\r
- *     VTT Technical Research Centre of Finland - initial API and implementation\r
- *******************************************************************************/\r
-package org.simantics.simulation.project;\r
-\r
-import java.lang.reflect.InvocationTargetException;\r
-import java.util.concurrent.CopyOnWriteArrayList;\r
-import java.util.concurrent.atomic.AtomicBoolean;\r
-\r
-import org.eclipse.core.runtime.IProgressMonitor;\r
-import org.eclipse.jface.operation.IRunnableWithProgress;\r
-import org.eclipse.ui.PlatformUI;\r
-import org.eclipse.ui.progress.IProgressService;\r
-import org.osgi.framework.BundleContext;\r
-import org.osgi.framework.ServiceReference;\r
-import org.simantics.Simantics;\r
-import org.simantics.db.ReadGraph;\r
-import org.simantics.db.Resource;\r
-import org.simantics.db.common.procedure.adapter.ProcedureAdapter;\r
-import org.simantics.db.common.request.ReadRequest;\r
-import org.simantics.db.exception.DatabaseException;\r
-import org.simantics.db.service.LifecycleSupport;\r
-import org.simantics.layer0.Layer0;\r
-import org.simantics.project.IProject;\r
-import org.simantics.simulation.Activator;\r
-import org.simantics.simulation.experiment.ExperimentState;\r
-import org.simantics.simulation.experiment.IExperiment;\r
-import org.simantics.simulation.experiment.IExperimentListener;\r
-import org.simantics.simulation.model.IModel;\r
-import org.simantics.ui.workbench.WorkbenchShutdownService;\r
-import org.simantics.utils.datastructures.ListenerList;\r
-\r
-/**\r
- * Simple local ExperimentManager implementation\r
- */\r
-public class ExperimentManager implements IExperimentManager {\r
-\r
-    CopyOnWriteArrayList<IExperimentManagerListener> listeners = new CopyOnWriteArrayList<IExperimentManagerListener>();\r
-    ListenerList<IExperiment> experiments = new ListenerList<IExperiment>(IExperiment.class);\r
-    IExperiment activeExperiment;\r
-    AtomicBoolean isDisposed = new AtomicBoolean(false);\r
-\r
-    public ExperimentManager() {\r
-        BundleContext context = Activator.getDefault().getBundle().getBundleContext();\r
-        ServiceReference<?> ref = context.getServiceReference(WorkbenchShutdownService.class.getName());\r
-        if (ref != null) {\r
-            WorkbenchShutdownService shutdown = (WorkbenchShutdownService) context.getService(ref);\r
-            shutdown.registerShutdownHook(new Runnable() {\r
-                @Override\r
-                public void run() {\r
-                    IRunnableWithProgress runnable = new IRunnableWithProgress() {\r
-                        @Override\r
-                        public void run(IProgressMonitor monitor) throws InvocationTargetException, InterruptedException {\r
-                            try {\r
-                                ExperimentManager.this.dispose(monitor);\r
-                            } finally {\r
-                                monitor.done();\r
-                            }\r
-                        }\r
-                    };\r
-                    try {\r
-                        if (PlatformUI.isWorkbenchRunning()) {\r
-                            IProgressService progress = (IProgressService) PlatformUI.getWorkbench().getService(IProgressService.class);\r
-                            progress.run(true, false, runnable);\r
-                        } else {\r
-                            runnable.run(null);\r
-                        }\r
-                    } catch (InvocationTargetException e) {\r
-                        Activator.logError("Experiment manager shutdown failed, see exception for details.", e.getCause());\r
-                    } catch (InterruptedException e) {\r
-                        Activator.logError("Experiment manager shutdown was interrupted, see exception for details.", e);\r
-                    }\r
-                }\r
-            });\r
-            context.ungetService(ref);\r
-        }\r
-    }\r
-\r
-    class ManagingExperimentListener implements IExperimentListener {\r
-\r
-        IExperiment experiment;\r
-        boolean setActive;\r
-\r
-        public ManagingExperimentListener(IExperiment experiment, boolean setActive) {\r
-            this.experiment = experiment;\r
-            this.setActive = setActive;\r
-        }\r
-\r
-        @Override\r
-        public void stateChanged(ExperimentState state) {\r
-            if(state==ExperimentState.RUNNING || state==ExperimentState.STOPPED) {\r
-                if(setActive && activeExperiment != experiment)\r
-                    setActiveExperiment(experiment);\r
-            }\r
-            else if(state==ExperimentState.DISPOSED) {\r
-                removeActiveExperiment(experiment);\r
-                experiments.remove(experiment);\r
-                experiment.removeListener(this);\r
-                experiment = null;\r
-            }\r
-        }\r
-    }\r
-\r
-    protected void manageExperiment(IExperiment experiment, boolean setActive) {\r
-        experiments.add(experiment);\r
-        experiment.addListener(new ManagingExperimentListener(experiment, setActive));\r
-    }\r
-\r
-    @Override\r
-    public void startExperiment(final Resource experimentResource,\r
-            final IExperimentActivationListener listener, final boolean setActive) {\r
-        // ENFORCE SINGLE_EXPERIMENT MODE POLICY:\r
-        // Shutdown active experiment before loading new experiment.\r
-        // IMPORTANT: Perform shutdown outside of a graph transaction to allow\r
-        // shutdown to perform graph requests at will.\r
-        synchronized (ExperimentManager.this) {\r
-            ExperimentManagerMode mode = getMode();\r
-            // Close previous active experiment before loading new\r
-            if (mode == ExperimentManagerMode.SINGLE_EXPERIMENT) {\r
-                if (activeExperiment != null && setActive) {\r
-                    // TODO: provide a proper progress monitor for shutdown! \r
-                    activeExperiment.shutdown(null);\r
-                }\r
-            }\r
-        }\r
-\r
-        Simantics.getSession().asyncRequest(new ReadRequest() {\r
-            @Override\r
-            public void run(ReadGraph g) throws DatabaseException {\r
-                \r
-                LifecycleSupport ls = g.getService(LifecycleSupport.class);\r
-                if(ls.isClosing() || ls.isClosed()) {\r
-                    return;\r
-                }\r
-                \r
-                Layer0 L0 = Layer0.getInstance(g);\r
-                final IModel model =\r
-                    g.adaptUnique(\r
-                            g.getSingleObject(experimentResource, L0.PartOf),\r
-                            IModel.class);\r
-\r
-                final IExperimentActivationListener proxy = new ProxyExperimentActivationListener(listener) {\r
-                    @Override\r
-                    public void onExperimentActivated(IExperiment experiment) {\r
-                        if (experiment != null)\r
-                            manageExperiment(experiment, setActive);\r
-                        super.onExperimentActivated(experiment);\r
-                    }\r
-                    @Override\r
-                    public void onFailure(Throwable e) {\r
-                        super.onFailure(e);\r
-                    }\r
-                };\r
-\r
-                // Ignore return value, the experiment is\r
-                // provided to proxy.onExperimentActivated.\r
-                model.loadExperiment(g, experimentResource, proxy);\r
-            }\r
-        }, new ProcedureAdapter<Object>() {\r
-            @Override\r
-            public void exception(Throwable t) {\r
-                listener.onFailure(t);\r
-            }\r
-        });\r
-    }\r
-\r
-    synchronized void setActiveExperiment(IExperiment experiment) {\r
-        // Multiple experiments may need to run concurrently - so don't shutdown\r
-        // if not explicitly requested to do so.\r
-        if (getMode() == ExperimentManagerMode.SINGLE_EXPERIMENT) {\r
-            if (activeExperiment != null) {\r
-                activeExperiment.shutdown(null);\r
-                for (IExperimentManagerListener listener : listeners)\r
-                    listener.activeExperimentUnloaded();\r
-            }\r
-        }\r
-        activeExperiment = experiment;\r
-        for(IExperimentManagerListener listener : listeners)\r
-            listener.activeExperimentLoaded(experiment);\r
-    }\r
-\r
-    synchronized private void removeActiveExperiment(IExperiment experiment) {\r
-        if(activeExperiment == experiment) {\r
-            activeExperiment = null;\r
-            for(IExperimentManagerListener listener : listeners)\r
-                listener.activeExperimentUnloaded();\r
-        }\r
-    }\r
-\r
-    @Override\r
-    synchronized public void addListener(IExperimentManagerListener listener) {\r
-        listeners.add(listener);\r
-        if(activeExperiment != null)\r
-            listener.activeExperimentLoaded(activeExperiment);\r
-    }\r
-\r
-    @Override\r
-    synchronized public void removeListener(IExperimentManagerListener listener) {\r
-        listeners.remove(listener);\r
-    }\r
-\r
-    public void dispose(IProgressMonitor monitor) {\r
-        if(isDisposed.compareAndSet(false, true)) {\r
-            if(activeExperiment != null)\r
-                activeExperiment.shutdown(monitor);\r
-            activeExperiment = null;\r
-\r
-            for(IExperimentManagerListener listener : listeners)\r
-                listener.managerDisposed();\r
-\r
-            if (!listeners.isEmpty()) {\r
-                // Some clients are leaking listeners. Shame on them.\r
-                System.err.println("ExperimentManager still contains the following listeners after disposal:");\r
-                for (IExperimentManagerListener listener : listeners)\r
-                    System.err.println("\t" + listener);\r
-            }\r
-        }\r
-    }\r
-\r
-    @Override\r
-    public IExperiment getActiveExperiment() {\r
-        return activeExperiment;\r
-    }\r
-\r
-    @Override\r
-    public IExperiment getExperiment(final String identifier) {\r
-        if(identifier == null) return null;\r
-        for(IExperiment experiment : experiments.getListeners()) {\r
-            if(experiment != null && identifier.equals(experiment.getIdentifier())) {\r
-                return experiment;\r
-            }\r
-        }\r
-        return null;\r
-    }\r
-\r
-    @Override\r
-    public IExperiment[] getExperiments() {\r
-       return experiments.getListeners();\r
-    }\r
-\r
-    private ExperimentManagerMode getMode() {\r
-        ExperimentManagerMode mode = ExperimentManagerMode.MULTI_EXPERIMENT;\r
-        IProject project = org.simantics.Simantics.peekProject();\r
-        if (project == null)\r
-            return mode;\r
-        mode = project.getHint(ExperimentManagerKeys.EXPERIMENT_MANAGER_MODE);\r
-        return mode != null ? mode : ExperimentManagerMode.MULTI_EXPERIMENT;\r
-    }\r
-\r
-}\r
+/*******************************************************************************
+ * Copyright (c) 2007, 2010 Association for Decentralized Information Management
+ * in Industry THTH ry.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ *     VTT Technical Research Centre of Finland - initial API and implementation
+ *******************************************************************************/
+package org.simantics.simulation.project;
+
+import java.lang.reflect.InvocationTargetException;
+import java.util.concurrent.CopyOnWriteArrayList;
+import java.util.concurrent.atomic.AtomicBoolean;
+
+import org.eclipse.core.runtime.IProgressMonitor;
+import org.eclipse.jface.operation.IRunnableWithProgress;
+import org.eclipse.ui.PlatformUI;
+import org.eclipse.ui.progress.IProgressService;
+import org.osgi.framework.BundleContext;
+import org.osgi.framework.ServiceReference;
+import org.simantics.Simantics;
+import org.simantics.db.ReadGraph;
+import org.simantics.db.Resource;
+import org.simantics.db.common.procedure.adapter.ProcedureAdapter;
+import org.simantics.db.common.request.ReadRequest;
+import org.simantics.db.exception.DatabaseException;
+import org.simantics.db.service.LifecycleSupport;
+import org.simantics.layer0.Layer0;
+import org.simantics.project.IProject;
+import org.simantics.simulation.Activator;
+import org.simantics.simulation.experiment.ExperimentState;
+import org.simantics.simulation.experiment.IExperiment;
+import org.simantics.simulation.experiment.IExperimentListener;
+import org.simantics.simulation.model.IModel;
+import org.simantics.ui.workbench.WorkbenchShutdownService;
+import org.simantics.utils.datastructures.ListenerList;
+
+/**
+ * Simple local ExperimentManager implementation
+ */
+public class ExperimentManager implements IExperimentManager {
+
+    CopyOnWriteArrayList<IExperimentManagerListener> listeners = new CopyOnWriteArrayList<IExperimentManagerListener>();
+    ListenerList<IExperiment> experiments = new ListenerList<IExperiment>(IExperiment.class);
+    IExperiment activeExperiment;
+    AtomicBoolean isDisposed = new AtomicBoolean(false);
+
+    public ExperimentManager() {
+        BundleContext context = Activator.getDefault().getBundle().getBundleContext();
+        ServiceReference<?> ref = context.getServiceReference(WorkbenchShutdownService.class.getName());
+        if (ref != null) {
+            WorkbenchShutdownService shutdown = (WorkbenchShutdownService) context.getService(ref);
+            shutdown.registerShutdownHook(new Runnable() {
+                @Override
+                public void run() {
+                    IRunnableWithProgress runnable = new IRunnableWithProgress() {
+                        @Override
+                        public void run(IProgressMonitor monitor) throws InvocationTargetException, InterruptedException {
+                            try {
+                                ExperimentManager.this.dispose(monitor);
+                            } finally {
+                                monitor.done();
+                            }
+                        }
+                    };
+                    try {
+                        if (PlatformUI.isWorkbenchRunning()) {
+                            IProgressService progress = (IProgressService) PlatformUI.getWorkbench().getService(IProgressService.class);
+                            progress.run(true, false, runnable);
+                        } else {
+                            runnable.run(null);
+                        }
+                    } catch (InvocationTargetException e) {
+                        Activator.logError("Experiment manager shutdown failed, see exception for details.", e.getCause());
+                    } catch (InterruptedException e) {
+                        Activator.logError("Experiment manager shutdown was interrupted, see exception for details.", e);
+                    }
+                }
+            });
+            context.ungetService(ref);
+        }
+    }
+
+    class ManagingExperimentListener implements IExperimentListener {
+
+        IExperiment experiment;
+        boolean setActive;
+
+        public ManagingExperimentListener(IExperiment experiment, boolean setActive) {
+            this.experiment = experiment;
+            this.setActive = setActive;
+        }
+
+        @Override
+        public void stateChanged(ExperimentState state) {
+            if(state==ExperimentState.RUNNING || state==ExperimentState.STOPPED) {
+                if(setActive && activeExperiment != experiment)
+                    setActiveExperiment(experiment);
+            }
+            else if(state==ExperimentState.DISPOSED) {
+                removeActiveExperiment(experiment);
+                experiments.remove(experiment);
+                experiment.removeListener(this);
+                experiment = null;
+            }
+        }
+    }
+
+    protected void manageExperiment(IExperiment experiment, boolean setActive) {
+        experiments.add(experiment);
+        experiment.addListener(new ManagingExperimentListener(experiment, setActive));
+    }
+
+    @Override
+    public void startExperiment(final Resource experimentResource,
+            final IExperimentActivationListener listener, final boolean setActive) {
+        // ENFORCE SINGLE_EXPERIMENT MODE POLICY:
+        // Shutdown active experiment before loading new experiment.
+        // IMPORTANT: Perform shutdown outside of a graph transaction to allow
+        // shutdown to perform graph requests at will.
+        synchronized (ExperimentManager.this) {
+            ExperimentManagerMode mode = getMode();
+            // Close previous active experiment before loading new
+            if (mode == ExperimentManagerMode.SINGLE_EXPERIMENT) {
+                if (activeExperiment != null && setActive) {
+                    // TODO: provide a proper progress monitor for shutdown! 
+                    activeExperiment.shutdown(null);
+                }
+            }
+        }
+
+        Simantics.getSession().asyncRequest(new ReadRequest() {
+            @Override
+            public void run(ReadGraph g) throws DatabaseException {
+                
+                LifecycleSupport ls = g.getService(LifecycleSupport.class);
+                if(ls.isClosing() || ls.isClosed()) {
+                    return;
+                }
+                
+                Layer0 L0 = Layer0.getInstance(g);
+                final IModel model =
+                    g.adaptUnique(
+                            g.getSingleObject(experimentResource, L0.PartOf),
+                            IModel.class);
+
+                final IExperimentActivationListener proxy = new ProxyExperimentActivationListener(listener) {
+                    @Override
+                    public void onExperimentActivated(IExperiment experiment) {
+                        if (experiment != null)
+                            manageExperiment(experiment, setActive);
+                        super.onExperimentActivated(experiment);
+                    }
+                    @Override
+                    public void onFailure(Throwable e) {
+                        super.onFailure(e);
+                    }
+                };
+
+                // Ignore return value, the experiment is
+                // provided to proxy.onExperimentActivated.
+                model.loadExperiment(g, experimentResource, proxy);
+            }
+        }, new ProcedureAdapter<Object>() {
+            @Override
+            public void exception(Throwable t) {
+                listener.onFailure(t);
+            }
+        });
+    }
+
+    synchronized void setActiveExperiment(IExperiment experiment) {
+        // Multiple experiments may need to run concurrently - so don't shutdown
+        // if not explicitly requested to do so.
+        if (getMode() == ExperimentManagerMode.SINGLE_EXPERIMENT) {
+            if (activeExperiment != null) {
+                activeExperiment.shutdown(null);
+                for (IExperimentManagerListener listener : listeners)
+                    listener.activeExperimentUnloaded();
+            }
+        }
+        activeExperiment = experiment;
+        for(IExperimentManagerListener listener : listeners)
+            listener.activeExperimentLoaded(experiment);
+    }
+
+    synchronized private void removeActiveExperiment(IExperiment experiment) {
+        if(activeExperiment == experiment) {
+            activeExperiment = null;
+            for(IExperimentManagerListener listener : listeners)
+                listener.activeExperimentUnloaded();
+        }
+    }
+
+    @Override
+    synchronized public void addListener(IExperimentManagerListener listener) {
+        listeners.add(listener);
+        if(activeExperiment != null)
+            listener.activeExperimentLoaded(activeExperiment);
+    }
+
+    @Override
+    synchronized public void removeListener(IExperimentManagerListener listener) {
+        listeners.remove(listener);
+    }
+
+    public void dispose(IProgressMonitor monitor) {
+        if(isDisposed.compareAndSet(false, true)) {
+            if(activeExperiment != null)
+                activeExperiment.shutdown(monitor);
+            activeExperiment = null;
+
+            for(IExperimentManagerListener listener : listeners)
+                listener.managerDisposed();
+
+            if (!listeners.isEmpty()) {
+                // Some clients are leaking listeners. Shame on them.
+                System.err.println("ExperimentManager still contains the following listeners after disposal:");
+                for (IExperimentManagerListener listener : listeners)
+                    System.err.println("\t" + listener);
+            }
+        }
+    }
+
+    @Override
+    public IExperiment getActiveExperiment() {
+        return activeExperiment;
+    }
+
+    @Override
+    public IExperiment getExperiment(final String identifier) {
+        if(identifier == null) return null;
+        for(IExperiment experiment : experiments.getListeners()) {
+            if(experiment != null && identifier.equals(experiment.getIdentifier())) {
+                return experiment;
+            }
+        }
+        return null;
+    }
+
+    @Override
+    public IExperiment[] getExperiments() {
+       return experiments.getListeners();
+    }
+
+    private ExperimentManagerMode getMode() {
+        ExperimentManagerMode mode = ExperimentManagerMode.MULTI_EXPERIMENT;
+        IProject project = org.simantics.Simantics.peekProject();
+        if (project == null)
+            return mode;
+        mode = project.getHint(ExperimentManagerKeys.EXPERIMENT_MANAGER_MODE);
+        return mode != null ? mode : ExperimentManagerMode.MULTI_EXPERIMENT;
+    }
+
+}