1 package org.simantics.document.ui.contribution;
3 import java.util.Collection;
5 import org.eclipse.jface.layout.GridDataFactory;
6 import org.eclipse.jface.layout.GridLayoutFactory;
7 import org.eclipse.jface.viewers.ISelection;
8 import org.eclipse.swt.SWT;
9 import org.eclipse.swt.dnd.DND;
10 import org.eclipse.swt.dnd.DropTarget;
11 import org.eclipse.swt.dnd.DropTargetAdapter;
12 import org.eclipse.swt.dnd.DropTargetEvent;
13 import org.eclipse.swt.dnd.TextTransfer;
14 import org.eclipse.swt.dnd.Transfer;
15 import org.eclipse.swt.events.SelectionAdapter;
16 import org.eclipse.swt.events.SelectionEvent;
17 import org.eclipse.swt.widgets.Button;
18 import org.eclipse.swt.widgets.Composite;
19 import org.eclipse.swt.widgets.Display;
20 import org.eclipse.swt.widgets.Label;
21 import org.eclipse.swt.widgets.Text;
22 import org.eclipse.ui.IWorkbenchSite;
23 import org.simantics.Simantics;
24 import org.simantics.browsing.ui.swt.widgets.StringPropertyFactory;
25 import org.simantics.browsing.ui.swt.widgets.StringPropertyModifier;
26 import org.simantics.browsing.ui.swt.widgets.TrackedText;
27 import org.simantics.browsing.ui.swt.widgets.impl.Widget;
28 import org.simantics.browsing.ui.swt.widgets.impl.WidgetSupport;
29 import org.simantics.db.AsyncReadGraph;
30 import org.simantics.db.ReadGraph;
31 import org.simantics.db.Resource;
32 import org.simantics.db.WriteGraph;
33 import org.simantics.db.common.NamedResource;
34 import org.simantics.db.common.ResourceArray;
35 import org.simantics.db.common.procedure.adapter.AsyncListenerAdapter;
36 import org.simantics.db.common.request.ReadRequest;
37 import org.simantics.db.common.request.WriteRequest;
38 import org.simantics.db.exception.DatabaseException;
39 import org.simantics.db.management.ISessionContext;
40 import org.simantics.db.request.Read;
41 import org.simantics.db.service.SerialisationSupport;
42 import org.simantics.document.DocumentResource;
43 import org.simantics.document.ui.graphfile.DocumentVersionUtils;
44 import org.simantics.layer0.Layer0;
45 import org.simantics.selectionview.AbstractResourceTabContribution;
46 import org.simantics.selectionview.ComparableTabContributor;
47 import org.simantics.selectionview.PropertyTabContributorImpl;
48 import org.simantics.ui.dnd.LocalObjectTransfer;
49 import org.simantics.ui.dnd.ResourceReferenceTransfer;
50 import org.simantics.ui.dnd.ResourceTransferUtils;
51 import org.simantics.ui.utils.ResourceAdaptionUtils;
52 import org.simantics.ui.workbench.editor.EditorAdapter;
53 import org.simantics.ui.workbench.editor.EditorRegistry;
54 import org.simantics.utils.ui.AdaptionUtils;
55 import org.simantics.utils.ui.ErrorLogger;
56 import org.simantics.utils.ui.ExceptionUtils;
59 * PropertyTab for documents.
62 * @author Marko Luukkainen <marko.luukkainen@vtt.fi>
65 public class DocumentTabContribution extends AbstractResourceTabContribution{
68 public DocumentTabContribution(ReadGraph graph, Resource r) throws DatabaseException{
73 public void getContributors(ReadGraph graph, Resource resource,
74 Integer priority, String label,
75 Collection<ComparableTabContributor> result)
76 throws DatabaseException {
77 DocumentResource doc = DocumentResource.getInstance(graph);
78 if (!graph.isInstanceOf(resource, doc.Document))
80 result.add(new ComparableTabContributor(new DocumentPropertyTabContributor(), 1, resource, "Document"));
83 private class DocumentPropertyTabContributor extends PropertyTabContributorImpl {
86 public void createControls(Composite body, IWorkbenchSite site, ISessionContext context, final WidgetSupport support) {
88 Composite composite = new Composite(body, SWT.NONE);
89 GridDataFactory.fillDefaults().grab(true, true).applyTo(composite);
90 GridLayoutFactory.fillDefaults().margins(3,3).spacing(1, 1).numColumns(4).applyTo(composite);
92 Label label = new Label(composite, SWT.NONE);
93 label.setText("Name");
95 TrackedText name = new TrackedText(composite, support, SWT.BORDER);
96 name.setTextFactory(new StringPropertyFactory(Layer0.URIs.HasName));
97 name.addModifyListener(new StringPropertyModifier(context, Layer0.URIs.HasName));
98 NameInputValidator validator = new NameInputValidator();
99 name.setInputValidator(validator);
100 support.register(validator);
102 Button showButton = new Button(composite, SWT.PUSH);
103 showButton.setText("Show");
104 showButton.addSelectionListener(new SelectionAdapter() {
106 public void widgetSelected(SelectionEvent e) {
107 openResource(AdaptionUtils.adaptToSingle(support.getInput(),Resource.class));
110 DocumentResource doc;
112 doc = DocumentResource.getInstance(context.getSession());
113 new DocumentRevisionWidget(composite, support, doc.HasOlderVersion, "Old");
114 new DocumentRevisionWidget(composite, support, doc.HasNewerVersion, "New");
115 } catch (DatabaseException e1) {
116 ExceptionUtils.logAndShowError("Cannot create documen version UI", e1);
120 GridDataFactory.fillDefaults().grab(true, false).align(SWT.FILL, SWT.CENTER).applyTo(name.getWidget());
121 GridDataFactory.fillDefaults().span(2, 1).applyTo(showButton);
125 public Read<String> getPartNameReadRequest(final ISelection forSelection) {
127 return new Read<String>() {
129 public String perform(ReadGraph graph) throws DatabaseException {
130 Resource res = AdaptionUtils.adaptToSingle(forSelection, Resource.class);
133 Layer0 l0 = Layer0.getInstance(graph);
134 return graph.getPossibleRelatedValue(res, l0.HasName);
140 private static void openResource(final Resource resource) {
141 Simantics.getSession().asyncRequest(new ReadRequest() {
144 public void run(ReadGraph graph) throws DatabaseException {
145 openResource(graph, resource);
150 private static void openResource(ReadGraph graph, final Resource resource) throws DatabaseException{
151 EditorAdapter[] adapters = EditorRegistry.getInstance().getAdaptersFor(graph, resource);
152 if (adapters.length == 0)
154 EditorAdapter highPri = null;
155 int pri = Integer.MIN_VALUE;
156 for (EditorAdapter a : adapters) {
157 int p = a.getPriority();
158 if (highPri == null || p > pri) {
163 final EditorAdapter adapter = highPri;
165 Display.getDefault().asyncExec(new Runnable() {
170 adapter.openEditor(resource);
171 } catch (Exception e) {
172 ExceptionUtils.logAndShowError("Cannot open editor", e);
178 private static class DocumentRevisionWidget implements Widget {
179 ISessionContext context;
182 Resource revisionRel;
183 NamedResource revisionDoc;
189 public DocumentRevisionWidget(Composite parent, WidgetSupport support, Resource rel, String name) {
190 support.register(this);
191 this.revisionRel = rel;
193 Label label = new Label(parent, SWT.NONE);
195 text = new Text(parent, SWT.SINGLE|SWT.BORDER|SWT.READ_ONLY);
196 showButton = new Button(parent, SWT.PUSH);
197 showButton.setText("Show");
198 showButton.addSelectionListener(new SelectionAdapter() {
200 public void widgetSelected(SelectionEvent e) {
201 if (revisionDoc != null)
202 openResource(revisionDoc.getResource());
205 removeButton = new Button(parent, SWT.PUSH);
206 removeButton.setText("Unset");
207 removeButton.addSelectionListener(new SelectionAdapter() {
209 public void widgetSelected(SelectionEvent e) {
210 if (revisionDoc == null)
213 context.getSession().syncRequest(new WriteRequest() {
216 public void perform(WriteGraph graph) throws DatabaseException {
217 DocumentVersionUtils.unsetVersion(graph, document, revisionDoc.getResource(), revisionRel);
221 } catch (DatabaseException e1) {
222 ExceptionUtils.logAndShowError("Cannot remove document revision", e1);
228 DropTarget dropTarget = new DropTarget(text, DND.DROP_COPY|DND.DROP_LINK);
229 dropTarget.setTransfer(new Transfer[] { TextTransfer.getInstance(),ResourceReferenceTransfer.getInstance(), LocalObjectTransfer.getTransfer() });
230 dropTarget.addDropListener(new DropTargetAdapter() {
233 public void dragEnter(DropTargetEvent event) {
234 // drop data is null, so we cannot to validate drop.
235 event.detail = DND.DROP_LINK;
239 public void drop(DropTargetEvent event) {
240 ResourceArray[] data = parseEventData(event);
241 if (data.length != 1)
243 if (data[0].resources ==null || data[0].resources.length != 1)
245 setRevisionDoc(data[0].resources[0]);
248 private ResourceArray[] parseEventData(DropTargetEvent event) {
249 if (event.data instanceof String) {
251 SerialisationSupport support = context.getSession().getService(SerialisationSupport.class);
252 return ResourceTransferUtils.readStringTransferable(support, (String) event.data).toResourceArrayArray();
253 } catch (IllegalArgumentException e) {
254 ErrorLogger.defaultLogError(e);
255 } catch (DatabaseException e) {
256 ErrorLogger.defaultLogError(e);
259 ResourceArray[] ret = ResourceAdaptionUtils.toResourceArrays(event.data);
266 GridDataFactory.fillDefaults().grab(true, false).align(SWT.FILL, SWT.CENTER).applyTo(text);
271 public void setInput(ISessionContext context, Object input) {
272 this.context = context;
273 document = AdaptionUtils.adaptToSingle(input, Resource.class);
275 context.getSession().asyncRequest(new Read<NamedResource>() {
277 public NamedResource perform(ReadGraph graph)
278 throws DatabaseException {
279 Layer0 l0 = Layer0.getInstance(graph);
280 Resource revisionDoc = graph.getPossibleObject(document, revisionRel);
281 if (revisionDoc == null)
283 return new NamedResource((String)graph.getRelatedValue(revisionDoc, l0.HasName), revisionDoc);
285 },new AsyncListenerAdapter<NamedResource>(){
287 public void execute(AsyncReadGraph graph,final NamedResource result) {
288 Display.getDefault().asyncExec(new Runnable() {
292 revisionDoc = result;
299 public void exception(AsyncReadGraph graph, Throwable t) {
300 ExceptionUtils.logAndShowError("Cannot show document revision", t);
304 public boolean isDisposed() {
305 return showButton.isDisposed();
313 private void updateUI() {
314 if (showButton.isDisposed())
316 showButton.setEnabled(revisionDoc != null);
317 removeButton.setEnabled(revisionDoc != null);
318 if (revisionDoc != null)
319 text.setText(revisionDoc.getName());
324 private void setRevisionDoc(final Resource toSet) {
325 context.getSession().asyncRequest(new WriteRequest() {
328 public void perform(WriteGraph graph) throws DatabaseException {
329 DocumentVersionUtils.setVersion(graph, document, toSet, revisionRel);