]> gerrit.simantics Code Review - simantics/platform.git/blob - bundles/org.simantics.modeling.ui/src/org/simantics/modeling/ui/diagramEditor/e4/DiagramEditor.java
Externalize strings
[simantics/platform.git] / bundles / org.simantics.modeling.ui / src / org / simantics / modeling / ui / diagramEditor / e4 / DiagramEditor.java
1 /*******************************************************************************
2  * Copyright (c) 2012 Association for Decentralized Information Management in
3  * Industry THTH ry.
4  * All rights reserved. This program and the accompanying materials
5  * are made available under the terms of the Eclipse Public License v1.0
6  * which accompanies this distribution, and is available at
7  * http://www.eclipse.org/legal/epl-v10.html
8  *
9  * Contributors:
10  *     VTT Technical Research Centre of Finland - initial API and implementation
11  *******************************************************************************/
12 package org.simantics.modeling.ui.diagramEditor.e4;
13
14 import java.lang.reflect.Constructor;
15
16 import org.eclipse.core.runtime.IConfigurationElement;
17 import org.eclipse.core.runtime.IExecutableExtension;
18 import org.eclipse.core.runtime.Platform;
19 import org.eclipse.e4.ui.model.application.ui.basic.MPart;
20 import org.eclipse.e4.ui.workbench.modeling.EPartService;
21 import org.eclipse.e4.ui.workbench.modeling.IPartListener;
22 import org.eclipse.osgi.util.NLS;
23 import org.eclipse.swt.SWT;
24 import org.eclipse.swt.widgets.Composite;
25 import org.eclipse.ui.PartInitException;
26 import org.osgi.framework.Bundle;
27 import org.simantics.db.Resource;
28 import org.simantics.modeling.ui.diagramEditor.DisposingPolicy;
29 import org.simantics.modeling.ui.diagramEditor.e4.DiagramViewer.DiagramViewerHost;
30 import org.simantics.ui.workbench.e4.E4ResourceEditorBase;
31 import org.simantics.utils.ui.ErrorLogger;
32
33 /**
34  * A class for diagram editor parts that contains logic for destruction and
35  * (re)initialization of the actual diagram viewer and its controls during the
36  * life cycle of this editor part.
37  * 
38  * <p>
39  * To use this class in an editor part extension, define the following in the
40  * <code>class</code> attribute of the extension:
41  * 
42  * <pre>
43  * class="org.simantics.modeling.ui.diagramEditor.DiagramEditor:viewer=%VIEWER%"
44  * </pre>
45  * 
46  * where <code>%VIEWER%</code> is the name of the class that either is or
47  * extends {@link org.simantics.modeling.ui.diagramEditor.DiagramViewer}. The
48  * <code>viewer</code> argument tells {@link DiagramEditor} where to find the
49  * initializer for the diagram editor controls. The initializer must have a
50  * default constructor.
51  * 
52  * <p>
53  * This class is not intended to be extended by clients. Customizations should
54  * be performed through the viewer class.
55  * 
56  * @author Tuukka Lehtonen
57  * @author Antti Villberg
58  */
59 public class DiagramEditor extends E4ResourceEditorBase implements DiagramViewerHost, IExecutableExtension, IPartListener {
60
61     /**
62      * The {@value #ARG_VIEWER} argument for this editor part class tells the
63      * name of the class to use for initializing the diagram viewer, i.e.
64      * {@link #viewer}. The class is instantiated through reflection using the
65      * class loader of the bundle named {@link #viewerContributor}.
66      * 
67      * @see #setInitializationData(IConfigurationElement, String, Object)
68      */
69     public static final String    ARG_VIEWER = "viewer"; //$NON-NLS-1$
70
71     private Composite             parent;
72
73     private String                viewerContributor;
74     private String                viewerClassName;
75
76 //    private ResourceEditorSupport support;
77     private DiagramViewer         viewer;
78
79     /**
80      * Reads the class arguments from the string in the data argument.
81      * 
82      * @see org.eclipse.ui.part.EditorPart#setInitializationData(org.eclipse.core.runtime.IConfigurationElement,
83      *      java.lang.String, java.lang.Object)
84      * @see #createViewer()
85      */
86     @Override
87     public void setInitializationData(IConfigurationElement cfig, String propertyName, Object data) {
88         // super.setInitializationData(cfig, propertyName, data);
89
90         if (data instanceof String) {
91             viewerContributor = cfig.getContributor().getName();
92
93             String[] parameters = ((String) data).split(";"); //$NON-NLS-1$
94
95             for (String parameter : parameters) {
96                 String[] keyValue = parameter.split("="); //$NON-NLS-1$
97                 if (keyValue.length > 2) {
98                     ErrorLogger.defaultLogWarning(NLS.bind(Messages.DiagramEditor_InvalidParameter, parameter, data),
99                             null);
100                     continue;
101                 }
102                 String key = keyValue[0];
103                 String value = keyValue.length > 1 ? keyValue[1] : ""; //$NON-NLS-1$
104
105                 if (ARG_VIEWER.equals(key)) {
106                     viewerClassName = value;
107                 }
108             }
109         }
110     }
111
112     protected DiagramViewer createViewer() throws PartInitException {
113         if (viewerClassName == null)
114             throw new PartInitException(
115                     "DiagramViewer contributor class was not specified in editor extension's class attribute viewer-argument. contributor is '" //$NON-NLS-1$
116                             + viewerContributor + "'"); //$NON-NLS-1$
117
118         try {
119             Bundle b = Platform.getBundle(viewerContributor);
120             if (b == null)
121                 throw new PartInitException("DiagramViewer '" + viewerClassName + "' contributor bundle '" //$NON-NLS-1$ //$NON-NLS-2$
122                         + viewerContributor + "' was not found in the platform."); //$NON-NLS-1$
123
124             Class<?> clazz = b.loadClass(viewerClassName);
125             if (!DiagramViewer.class.isAssignableFrom(clazz))
126                 throw new PartInitException("DiagramViewer class '" + viewerClassName + "' is not assignable to " //$NON-NLS-1$ //$NON-NLS-2$
127                         + DiagramViewer.class + "."); //$NON-NLS-1$
128
129             Constructor<?> ctor = clazz.getConstructor();
130             return (DiagramViewer) ctor.newInstance();
131         } catch (Exception e) {
132             throw new PartInitException("Failed to instantiate DiagramViewer implementation '" + viewerClassName //$NON-NLS-1$
133                     + "' from bundle '" + viewerContributor + "'. See exception for details.", e); //$NON-NLS-1$ //$NON-NLS-2$
134         }
135     }
136
137     public DiagramViewer getViewer() {
138         return viewer;
139     }
140
141     public Resource getRuntimeResource() {
142         DiagramViewer viewer = this.viewer;
143         return viewer != null ? viewer.getRuntime() : null;
144     }
145     
146 //    public Resource getInputResource() {
147 //        DiagramViewer viewer = this.viewer;
148 //        return viewer != null ? viewer.getInputResource() : null;
149 //    }
150
151     @Override
152     public void initImpl(MPart part) {
153         super.initImpl(part);
154  
155         try {
156             viewer = createViewer();
157         } catch (PartInitException e) {
158             // TODO Auto-generated catch block
159             e.printStackTrace();
160         }
161         // #TODO Finish this when we are going to use full E4 workbench
162 //        viewer.init(this, getResourceInput());
163         
164         EPartService partService = part.getContext().get(EPartService.class);
165         partService.addPartListener(this);
166     }
167
168     @Override
169     public void createPartControl(Composite parent) {
170         this.parent = parent;
171         initializeViewer();
172     }
173
174     private void initializeViewer() {
175         parent.setBackground(parent.getDisplay().getSystemColor(SWT.COLOR_WHITE));
176         viewer.createPartControl(parent);
177         // It is possible that something goes wrong and the parent gets disposed already
178         if(parent.isDisposed()) return;
179         parent.layout(true);
180     }
181
182     @Override
183     public void setFocus() {
184         if (viewer != null)
185             viewer.setFocus();
186     }
187
188     @SuppressWarnings("rawtypes")
189     public Object getAdapter(Class adapter) {
190         if (adapter == DiagramViewer.class)
191             return viewer;
192         if (viewer != null) {
193             Object result = viewer.getAdapter(adapter);
194             if (result != null)
195                 return result;
196         }
197         return null;
198     }
199
200
201     @Override
202     public void dispose() {
203         
204         EPartService partService = getPart().getContext().get(EPartService.class);
205         partService.removePartListener(this);
206
207         DISPOSING_POLICY.removeDisposer(disposer);
208         tryDisposeViewer();
209
210     }
211
212     
213     public void doSetPartName(String name) {
214         getPart().setLabel(name);
215     }
216
217     
218     public void doSetTitleToolTip(String tooltip) {
219         getPart().setTooltip(tooltip);
220     }
221     
222     private static final DisposingPolicy DISPOSING_POLICY = 
223             new DisposingPolicy();
224     
225     private Runnable disposer = new Runnable() {
226         @Override
227         public void run() {
228             tryDisposeViewer();
229         }
230     };
231
232     private void tryDisposeViewer() {
233         if (viewer != null) {
234             Composite viewerComposite = viewer.getComposite();
235             viewer.dispose();
236             viewer = null;
237             if (viewerComposite != null) {
238                 viewerComposite.dispose();
239             }
240         }
241     }
242     
243     @Override
244     public void partVisible(MPart part) {
245         if (getPart().equals(part)) {
246             DISPOSING_POLICY.removeDisposer(disposer);
247             if (viewer == null) {
248                 try {
249                     viewer = createViewer();
250                     // #TODO Finish this when we are going to use full E4 workbench
251 //                    viewer.init(DiagramEditor.this, getResourceInput());
252                     initializeViewer();
253                 } catch (PartInitException e) {
254                     // This should never happen!
255                     ErrorLogger.defaultLogError(e);
256                 }
257             }
258         }
259     }
260     
261     @Override
262     public void partHidden(MPart part) {
263         if (getPart().equals(part)) {
264             DISPOSING_POLICY.addDisposer(disposer);
265         }
266     }
267     
268     @Override
269     public void partDeactivated(MPart part) {
270     }
271     
272     @Override
273     public void partBroughtToTop(MPart part) {
274     }
275     
276     @Override
277     public void partActivated(MPart part) {
278     }
279
280 }