]> gerrit.simantics Code Review - simantics/sysdyn.git/blob
70dc93d34e7b84bf1999afe242acdc853c0eca7a
[simantics/sysdyn.git] /
1 /*******************************************************************************\r
2  * Copyright (c) 2007, 2011 Association for Decentralized Information Management in\r
3  * Industry THTH ry.\r
4  * All rights reserved. This program and the accompanying materials\r
5  * are made available under the terms of the Eclipse Public License v1.0\r
6  * which accompanies this distribution, and is available at\r
7  * http://www.eclipse.org/legal/epl-v10.html\r
8  *\r
9  * Contributors:\r
10  *     VTT Technical Research Centre of Finland - initial API and implementation\r
11  *******************************************************************************/\r
12 package org.simantics.sysdyn.ui.listeners;\r
13 \r
14 import java.util.HashMap;\r
15 \r
16 import org.eclipse.ui.IEditorPart;\r
17 import org.eclipse.ui.IEditorReference;\r
18 import org.eclipse.ui.IWorkbench;\r
19 import org.eclipse.ui.IWorkbenchPage;\r
20 import org.eclipse.ui.IWorkbenchWindow;\r
21 import org.eclipse.ui.PlatformUI;\r
22 import org.simantics.Simantics;\r
23 import org.simantics.db.Resource;\r
24 import org.simantics.db.WriteGraph;\r
25 import org.simantics.db.common.request.PossibleObjectWithType;\r
26 import org.simantics.db.common.request.WriteRequest;\r
27 import org.simantics.db.exception.DatabaseException;\r
28 import org.simantics.db.service.VirtualGraphSupport;\r
29 import org.simantics.diagram.profile.Profiles;\r
30 import org.simantics.diagram.stubs.DiagramResource;\r
31 import org.simantics.layer0.Layer0;\r
32 import org.simantics.modeling.ui.diagramEditor.DiagramEditor;\r
33 import org.simantics.project.IProject;\r
34 import org.simantics.simulation.experiment.ExperimentState;\r
35 import org.simantics.simulation.experiment.IExperiment;\r
36 import org.simantics.simulation.experiment.IExperimentListener;\r
37 import org.simantics.simulation.ontology.SimulationResource;\r
38 import org.simantics.simulation.project.IExperimentManager;\r
39 import org.simantics.sysdyn.SysdynResource;\r
40 import org.simantics.sysdyn.manager.SysdynPlaybackExperiment;\r
41 import org.simantics.sysdyn.ui.editor.DiagramViewer;\r
42 import org.simantics.ui.SimanticsUI;\r
43 \r
44 /**\r
45  * Listener for playback simulations. This listener activates and reverts the playback\r
46  * profile when a playback simlation is activated or disposed.\r
47  * @author Teemu Lempinen\r
48  *\r
49  */\r
50 public class SysdynPlaybackExperimentListener implements IExperimentListener {\r
51 \r
52     private Resource model;\r
53     private Resource previousProfile;\r
54 \r
55     public SysdynPlaybackExperimentListener(SysdynPlaybackExperiment experiment) {\r
56         this.model = experiment.getModel();\r
57         activatePlaybackProfile();\r
58     }\r
59 \r
60     @Override\r
61     public void stateChanged(final ExperimentState state) {\r
62         switch(state) {\r
63             case DISPOSED:\r
64                 revertPlaybackProfiles();\r
65             default:\r
66                 break;\r
67         }\r
68     }\r
69 \r
70     class DiagramInfo {\r
71         public Resource model = null;\r
72         public Resource previousProfile = null;\r
73     }\r
74 \r
75     HashMap<Resource, DiagramInfo> previousRuntimeDiagramsAndModelUris = new HashMap<Resource, DiagramInfo>(); \r
76 \r
77     private void activatePlaybackProfile() {\r
78         PlatformUI.getWorkbench().getDisplay().asyncExec(new Runnable() {\r
79 \r
80             @Override\r
81             public void run() {\r
82                 previousRuntimeDiagramsAndModelUris.clear();\r
83                 previousRuntimeDiagramsAndModelUris = getCurrentRuntimeDiagramInfos();\r
84                 activatePlaybackProfileRequest(previousRuntimeDiagramsAndModelUris);\r
85             }\r
86         });\r
87     }\r
88     \r
89     private void revertPlaybackProfiles() {\r
90         \r
91         IProject project =  SimanticsUI.getProject();\r
92         if(project == null)\r
93             return;\r
94         IExperimentManager manager = SimanticsUI.getProject().getHint(IExperimentManager.KEY_EXPERIMENT_MANAGER);\r
95         IExperiment experiment = manager.getActiveExperiment();\r
96         \r
97         if(experiment != null && experiment instanceof SysdynPlaybackExperiment && this.model.equals(experiment.getModel()))\r
98                 return;\r
99         \r
100         PlatformUI.getWorkbench().getDisplay().asyncExec(new Runnable() {\r
101 \r
102             @Override\r
103             public void run() {\r
104                 final HashMap<Resource, DiagramInfo> runtimeDiagramsAndModelUris = getCurrentRuntimeDiagramInfos();\r
105 \r
106                 VirtualGraphSupport support = Simantics.getSession().getService(VirtualGraphSupport.class);\r
107                 Simantics.getSession().asyncRequest(new WriteRequest(support.getWorkspacePersistent("profiles")) {\r
108                     \r
109                     @Override\r
110                     public void perform(WriteGraph graph) throws DatabaseException {\r
111                         \r
112                         Resource model = SysdynPlaybackExperimentListener.this.model;\r
113                         if(model == null)\r
114                             return;\r
115                         \r
116                         Layer0 l0 = Layer0.getInstance(graph);\r
117                         SysdynResource sr = SysdynResource.getInstance(graph);\r
118                         \r
119                         Resource defaultProfile = graph.syncRequest(new PossibleObjectWithType(model, l0.ConsistsOf, sr.DefaultProfile));\r
120                         if(defaultProfile == null)\r
121                             return;\r
122                         \r
123                         setProfileForModel(graph, model, previousProfile == null ? defaultProfile : previousProfile);\r
124                         \r
125                         HashMap<Resource, DiagramInfo> infos = getRuntimesForModel(graph, runtimeDiagramsAndModelUris, model);\r
126                         for(Resource runtimeDiagram : infos.keySet()) {\r
127                             Resource previous = null;\r
128                             if(previousRuntimeDiagramsAndModelUris.containsKey(runtimeDiagram)) {\r
129                                 previous = previousRuntimeDiagramsAndModelUris.get(runtimeDiagram).previousProfile;\r
130                             }\r
131                             setProfileForDiagram(graph, runtimeDiagram, previous == null ? defaultProfile : previous);\r
132                         }\r
133                     }\r
134                 });\r
135                 \r
136             }\r
137         });\r
138     }\r
139     \r
140     /**\r
141      * Run in display thread.\r
142      * \r
143      * @return\r
144      */\r
145     private HashMap<Resource, DiagramInfo> getCurrentRuntimeDiagramInfos() {\r
146         HashMap<Resource, DiagramInfo> runtimeDiagramsAndModelUris = new HashMap<Resource, DiagramInfo>(); \r
147         IWorkbench workBench =  PlatformUI.getWorkbench();\r
148         IWorkbenchWindow window = workBench.getActiveWorkbenchWindow();\r
149         IWorkbenchPage[] pages = window.getPages();\r
150         for(IWorkbenchPage page : pages) {\r
151             for(IEditorReference reference : page.getEditorReferences()) {\r
152                 IEditorPart iep = reference.getEditor(false);\r
153                 if(iep instanceof DiagramEditor) {\r
154                     DiagramEditor editor = (DiagramEditor) iep;\r
155                     if (editor.getViewer() instanceof DiagramViewer) {\r
156                         DiagramViewer viewer = (DiagramViewer) editor.getViewer();\r
157                         Resource runtime = viewer.getRuntime();\r
158                         Resource model = viewer.getResourceInput2().getModel(null);\r
159                         DiagramInfo info = new DiagramInfo();\r
160                         info.model = model;\r
161                         runtimeDiagramsAndModelUris.put(runtime, info);\r
162                     }\r
163                 }\r
164             }\r
165         }\r
166         return runtimeDiagramsAndModelUris;\r
167     }\r
168     \r
169     \r
170     private HashMap<Resource, DiagramInfo> getRuntimesForModel(WriteGraph graph, HashMap<Resource, DiagramInfo> allInfos, Resource model) throws DatabaseException {\r
171         HashMap<Resource, DiagramInfo> runtimeDiagramsAndModelUris = new HashMap<Resource, DiagramInfo>(); \r
172         for(Resource runtimeDiagram : allInfos.keySet()) {\r
173             DiagramInfo di = allInfos.get(runtimeDiagram);\r
174             if(di == null)\r
175                 continue;\r
176             Resource m = di.model;\r
177             if(m == null || !model.equals(m))                    \r
178                 continue;\r
179             \r
180             runtimeDiagramsAndModelUris.put(runtimeDiagram, di);\r
181         }\r
182         return runtimeDiagramsAndModelUris;\r
183     }\r
184     \r
185     private void activatePlaybackProfileRequest(final HashMap<Resource, DiagramInfo> allDiagramInfos) {\r
186         VirtualGraphSupport support = Simantics.getSession().getService(VirtualGraphSupport.class);\r
187         Simantics.getSession().asyncRequest(new WriteRequest(support.getWorkspacePersistent("profiles")) {\r
188             \r
189             @Override\r
190             public void perform(WriteGraph graph) throws DatabaseException {\r
191                 \r
192                 Resource model = SysdynPlaybackExperimentListener.this.model;\r
193                 if(model == null)\r
194                     return;\r
195                 \r
196                 Resource profile = getSimulationPlaybackProfile(graph, model);\r
197                 if(profile == null)\r
198                     return;\r
199                 \r
200                 DiagramResource DIA = DiagramResource.getInstance(graph);\r
201 \r
202                 Resource current = graph.getPossibleObject(model, DIA.HasActiveProfile);\r
203                 previousProfile = current;\r
204 \r
205                 if(!profile.equals(current)) {\r
206                     setProfileForModel(graph, model, profile);\r
207                 }\r
208                 \r
209                 HashMap<Resource, DiagramInfo> infos = getRuntimesForModel(graph, allDiagramInfos, model);\r
210                 for(Resource runtimeDiagram : infos.keySet()) {\r
211                     DiagramInfo di = infos.get(runtimeDiagram);\r
212                     current = graph.getPossibleObject(runtimeDiagram, DIA.RuntimeDiagram_HasRuntimeProfile);\r
213                     di.previousProfile = current;\r
214                     if(profile.equals(current)) \r
215                         continue;\r
216                     setProfileForDiagram(graph, runtimeDiagram, profile);\r
217                 }\r
218             }\r
219         });\r
220     }\r
221     \r
222     \r
223     private void setProfileForDiagram(WriteGraph graph, Resource runtimeDiagram, Resource profile) throws DatabaseException {\r
224         DiagramResource DIA = DiagramResource.getInstance(graph);\r
225 \r
226         Resource current = graph.getPossibleObject(runtimeDiagram, DIA.RuntimeDiagram_HasRuntimeProfile);\r
227         if(profile.equals(current)) return;\r
228         \r
229         if(current != null)\r
230             graph.deny(runtimeDiagram, DIA.RuntimeDiagram_HasRuntimeProfile, null, current);\r
231         graph.claim(runtimeDiagram, DIA.RuntimeDiagram_HasRuntimeProfile, null, profile);\r
232 \r
233         // Set this profile as the default profile for this diagram\r
234         Resource configuration = graph.getPossibleObject(runtimeDiagram, DIA.RuntimeDiagram_HasConfiguration);\r
235         graph.deny(configuration, DIA.HasActiveProfile);\r
236         graph.claim(configuration, DIA.HasActiveProfile, profile);\r
237     }\r
238     \r
239     private void setProfileForModel(WriteGraph graph, Resource model, Resource profile) throws DatabaseException {\r
240         DiagramResource DIA = DiagramResource.getInstance(graph);\r
241 \r
242         // Set this profile as the default profile for this model\r
243         graph.deny(model, DIA.HasActiveProfile);\r
244         graph.claim(model, DIA.HasActiveProfile, profile);\r
245     }\r
246     \r
247     private Resource getSimulationPlaybackProfile(WriteGraph graph, Resource model) throws DatabaseException {\r
248         Layer0 l0 = Layer0.getInstance(graph);\r
249         SysdynResource sr = SysdynResource.getInstance(graph);\r
250         SimulationResource SIMU = SimulationResource.getInstance(graph);\r
251         \r
252         Resource profile = graph.syncRequest(new PossibleObjectWithType(model, l0.ConsistsOf, sr.SimulationPlaybackProfile));\r
253         if(profile == null) {\r
254             profile = Profiles.createProfile(graph, "Simulation Playback", sr.Profiles_SimulationPlaybackColours);\r
255             graph.deny(profile, l0.InstanceOf);\r
256             graph.claim(profile, l0.InstanceOf, null, sr.SimulationPlaybackProfile);\r
257             graph.claim(model, l0.ConsistsOf, profile);\r
258         }\r
259 \r
260         if(!graph.hasStatement(profile, SIMU.IsActive)) {\r
261             graph.claim(profile, SIMU.IsActive, sr.Profiles_SimulationPlaybackColours);\r
262         }\r
263         \r
264         return profile;\r
265     }\r
266     \r
267 }\r