From: Tuukka Lehtonen Date: Mon, 6 Mar 2017 21:44:51 +0000 (+0200) Subject: Added org.simantics.views.text[.ontology] for modelled source viewers X-Git-Tag: v1.28.0~72 X-Git-Url: https://gerrit.simantics.org/r/gitweb?p=simantics%2Fplatform.git;a=commitdiff_plain;h=5b3a1f2d3bffe5a79e344b55087fb161541a4301;ds=sidebyside Added org.simantics.views.text[.ontology] for modelled source viewers For now, SWTMarkupSourceViewer is hardcoded for mediawiki markup. The new plug-ins are included in org.simantics.views.swt.feature. Also: * removed useless old code SG loader code from org.simantics.views.swt * started using SLF4J in org.simantics.document.ui refs #7066 Change-Id: Id3d058d676072ccff5898c013cf3353a5a54dce9 --- diff --git a/bundles/org.simantics.document.ui.ontology/META-INF/MANIFEST.MF b/bundles/org.simantics.document.ui.ontology/META-INF/MANIFEST.MF index e1ef05947..dc11fa0e3 100644 --- a/bundles/org.simantics.document.ui.ontology/META-INF/MANIFEST.MF +++ b/bundles/org.simantics.document.ui.ontology/META-INF/MANIFEST.MF @@ -6,6 +6,7 @@ Bundle-Version: 1.1.0.qualifier Bundle-Vendor: Semantum Oy Require-Bundle: org.simantics.layer0, org.simantics.views.ontology;bundle-version="1.1.0", + org.simantics.views.text.ontology;bundle-version="1.0.0", org.simantics.modeling.ontology;bundle-version="1.1.0", org.simantics.scenegraph.ontology;bundle-version="1.0.0", org.simantics.document.ontology;bundle-version="1.1.0", diff --git a/bundles/org.simantics.document.ui.ontology/graph.tg b/bundles/org.simantics.document.ui.ontology/graph.tg index 66fea4038..8ef6e047f 100644 Binary files a/bundles/org.simantics.document.ui.ontology/graph.tg and b/bundles/org.simantics.document.ui.ontology/graph.tg differ diff --git a/bundles/org.simantics.document.ui.ontology/graph/DocumentUI.pgraph b/bundles/org.simantics.document.ui.ontology/graph/DocumentUI.pgraph index 3ac065d5e..b06a314a3 100644 --- a/bundles/org.simantics.document.ui.ontology/graph/DocumentUI.pgraph +++ b/bundles/org.simantics.document.ui.ontology/graph/DocumentUI.pgraph @@ -1,5 +1,6 @@ L0 = VIEWS = +TEXTVIEWS = SG = DOC = ACT = @@ -40,11 +41,6 @@ UI.WikitextContribution.View : VIEWS.Composite @L0.list _ : VIEWS.Composite VIEWS.Composite.layout _ : VIEWS.RowLayout - //VIEWS.RowLayout.type VIEWS.Control.Style.Constant.Horizontal - //VIEWS.RowLayout.spacing 0 - //VIEWS.RowLayout.justify true - //VIEWS.RowLayout.pack true - //VIEWS.RowLayout.wrap true VIEWS.Control.layoutData _ : VIEWS.GridLayout.GridData VIEWS.GridLayout.GridData.horizontalGrab true SG.Node.children _ : L0.List @@ -159,7 +155,7 @@ UI.WikitextContribution.View : VIEWS.Composite VIEWS.Composite.layout _ : VIEWS.GridLayout SG.Node.children _ : L0.List @L0.list - UI.WikitextContribution.View.Text : VIEWS.StyledText + UI.WikitextContribution.View.Text : TEXTVIEWS.MarkupSourceViewer @VIEWS.Control.style4 VIEWS.Control.Style.Constant.Multi VIEWS.Control.Style.Constant.Border VIEWS.Control.Style.Constant.VScroll VIEWS.Control.Style.Constant.HScroll VIEWS.TextContainer.text UI.Functions.selectedDocumentPart : L0.Function L0.HasValueType "String" @@ -200,13 +196,6 @@ UI.Sash : VIEWS.SashForm VIEWS.SashForm.orientation VIEWS.SashForm.Vertical SG.Node.children _ : L0.List @L0.list -// UI.Scroll : VIEWS.ScrolledComposite - // VIEWS.Control.layoutData - // _ : VIEWS.GridLayout.GridData - // VIEWS.GridLayout.GridData.horizontalGrab true - // VIEWS.GridLayout.GridData.verticalGrab true - // SG.Node.children _ : L0.List - // @L0.list UI.Browser : VIEWS.Browser VIEWS.Control.layoutData _ : VIEWS.GridLayout.GridData diff --git a/bundles/org.simantics.document.ui/META-INF/MANIFEST.MF b/bundles/org.simantics.document.ui/META-INF/MANIFEST.MF index 5d0115b16..fa2877b11 100644 --- a/bundles/org.simantics.document.ui/META-INF/MANIFEST.MF +++ b/bundles/org.simantics.document.ui/META-INF/MANIFEST.MF @@ -7,6 +7,7 @@ Bundle-Activator: org.simantics.document.ui.Activator Bundle-Vendor: Semantum Oy Require-Bundle: org.eclipse.ui, org.eclipse.core.runtime, + org.simantics.views;bundle-version="1.1.0", org.simantics.views.swt;bundle-version="1.0.0", org.simantics.document.ontology;bundle-version="1.0.0", org.simantics.document.ui.ontology;bundle-version="1.0.0", @@ -14,12 +15,9 @@ Require-Bundle: org.eclipse.ui, org.simantics.modeling.ontology;bundle-version="1.1.0", org.simantics.scenegraph.ontology;bundle-version="1.0.0", org.simantics.document;bundle-version="1.0.0", - org.eclipse.mylyn.wikitext.mediawiki.core;bundle-version="1.5.2", - org.eclipse.mylyn.wikitext.core;bundle-version="1.5.1", org.simantics.wiki.ui;bundle-version="1.1.0", org.simantics.browsing.ui;bundle-version="1.1.0", org.simantics.selectionview;bundle-version="1.0.0", - org.simantics.views;bundle-version="1.1.0", org.simantics.utils.thread.swt;bundle-version="1.1.0", org.simantics.browsing.ui.model;bundle-version="1.0.0";visibility:=reexport, org.simantics.graphfile;bundle-version="0.1.0", @@ -29,7 +27,8 @@ Require-Bundle: org.eclipse.ui, org.simantics.annotation.ontology;bundle-version="1.0.0", org.simantics.annotation.ui;bundle-version="1.0.0", org.eclipse.ui.editors;bundle-version="3.9.0", - org.eclipse.jface.text + org.eclipse.jface.text, + org.slf4j.api;bundle-version="1.7.2" Bundle-RequiredExecutionEnvironment: JavaSE-1.8 Bundle-ActivationPolicy: lazy Export-Package: org.simantics.document.ui, diff --git a/bundles/org.simantics.document.ui/src/org/simantics/document/ui/function/All.java b/bundles/org.simantics.document.ui/src/org/simantics/document/ui/function/All.java index 76b5abe95..effe30cd9 100644 --- a/bundles/org.simantics.document.ui/src/org/simantics/document/ui/function/All.java +++ b/bundles/org.simantics.document.ui/src/org/simantics/document/ui/function/All.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2012 Association for Decentralized Information Management in + * Copyright (c) 2012, 2017 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 @@ -8,6 +8,7 @@ * * Contributors: * VTT Technical Research Centre of Finland - initial API and implementation + * Semantum Oy - (#7066) introducing logger & refactoring *******************************************************************************/ package org.simantics.document.ui.function; @@ -38,7 +39,6 @@ import org.simantics.db.WriteGraph; import org.simantics.db.common.request.ReadRequest; import org.simantics.db.common.request.UnaryRead; import org.simantics.db.common.request.WriteRequest; -import org.simantics.db.common.utils.Logger; import org.simantics.db.common.utils.NameUtils; import org.simantics.db.common.utils.RequestUtil; import org.simantics.db.exception.DatabaseException; @@ -68,10 +68,14 @@ import org.simantics.ui.workbench.ResourceEditorInput2; import org.simantics.ui.workbench.action.DefaultActions; import org.simantics.utils.threads.SWTThread; import org.simantics.utils.ui.workbench.WorkbenchUtils; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; public class All { + private static final Logger LOGGER = LoggerFactory.getLogger(All.class); + private static boolean createDocument(WriteGraph graph, Resource resource, Resource model) throws DatabaseException { Layer0 L0 = Layer0.getInstance(graph); @@ -187,6 +191,7 @@ public class All { if(document == null) return; RemoverUtil.remove(graph, document); + graph.markUndoPoint(); } @@ -318,12 +323,12 @@ public class All { @Override public void perform(WriteGraph graph) throws DatabaseException { - Variable selection = resolveEditSelection(graph, context, "..../Scroll/Browser#edited"); - if (selection != null) + if (selection != null) { selection.setValue(graph, (String)value, Bindings.STRING); - else { - System.err.println("no selection for resource : " + resource + ", Variable context : " + context + ", value : " + value); + graph.markUndoPoint(); + } else { + LOGGER.error("No selection for resource : " + resource + ", Variable context : " + context + ", value : " + value); } } @@ -743,19 +748,12 @@ public class All { String editorId = CSSEditor.EDITOR_ID; RVI rvi = null; - PlatformUI.getWorkbench().getDisplay().asyncExec(new Runnable() { - - @Override - public void run() { - - try { - WorkbenchUtils.openEditor(editorId, new ResourceEditorInput2(editorId, root, root, rvi)); - } catch (PartInitException e) { - Logger.defaultLogError(e); - } - + PlatformUI.getWorkbench().getDisplay().asyncExec(() -> { + try { + WorkbenchUtils.openEditor(editorId, new ResourceEditorInput2(editorId, root, root, rvi)); + } catch (PartInitException e) { + LOGGER.error("Failed to open CSS editor for root " + root, e); } - }); } diff --git a/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/ButtonLoader.java.keep b/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/ButtonLoader.java.keep deleted file mode 100644 index 388fa8678..000000000 --- a/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/ButtonLoader.java.keep +++ /dev/null @@ -1,36 +0,0 @@ -package org.simantics.views.swt.loader; - -import org.simantics.db.Resource; -import org.simantics.db.exception.DatabaseException; -import org.simantics.db.layer0.variable.Variable; -import org.simantics.scenegraph.ParentNode; -import org.simantics.scenegraph.loader.ScenegraphLoader; -import org.simantics.views.ontology.ViewsResources; -import org.simantics.views.swt.client.base.ISWTViewNode; -import org.simantics.views.swt.client.impl.SWTButton; - -public class ButtonLoader implements ScenegraphLoader { - - final private Resource configuration; - - public ButtonLoader(Resource configuration) { - this.configuration = configuration; - } - - @Override - public ISWTViewNode create(ParentNode parent, Variable context) throws DatabaseException { - - SWTButton node = parent.addNode(SWTButton.class); - - node.setLayoutData(LoaderUtils.getGridData(configuration)); - node.setStyle(LoaderUtils.getStyle(configuration)); - - LoaderUtils.listen(configuration, context, ViewsResources.URIs.TextContainer_HasText, node.getTextFunction()); - LoaderUtils.listen(configuration, context, ViewsResources.URIs.Button_Modifier, node.getModifierFunction()); - LoaderUtils.listen(configuration, context, ViewsResources.URIs.Button_HasImage, node.getImageFunction()); - - return node; - - } - -} diff --git a/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/CComboLoader.java.keep b/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/CComboLoader.java.keep deleted file mode 100644 index f9a53451f..000000000 --- a/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/CComboLoader.java.keep +++ /dev/null @@ -1,36 +0,0 @@ -package org.simantics.views.swt.loader; - -import org.simantics.db.Resource; -import org.simantics.db.exception.DatabaseException; -import org.simantics.db.layer0.variable.Variable; -import org.simantics.scenegraph.ParentNode; -import org.simantics.scenegraph.loader.ScenegraphLoader; -import org.simantics.views.ontology.ViewsResources; -import org.simantics.views.swt.client.base.ISWTViewNode; -import org.simantics.views.swt.client.impl.SWTCCombo; - -public class CComboLoader implements ScenegraphLoader { - - final private Resource configuration; - - public CComboLoader(Resource configuration) { - this.configuration = configuration; - } - - @Override - public ISWTViewNode create(ParentNode parent, Variable context) throws DatabaseException { - - SWTCCombo node = parent.addNode(SWTCCombo.class); - - node.setLayoutData(LoaderUtils.getGridData(configuration)); - node.setStyle(LoaderUtils.getStyle(configuration)); - - LoaderUtils.listen(configuration, context, ViewsResources.URIs.Combo_AvailableItems, node.getAvailableFunction()); - LoaderUtils.listen(configuration, context, ViewsResources.URIs.Combo_SelectedItem, node.getSelectionFunction()); - LoaderUtils.listen(configuration, context, ViewsResources.URIs.Combo_Modifier, node.getModifierFunction()); - - return node; - - } - -} diff --git a/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/ComboLoader.java.keep b/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/ComboLoader.java.keep deleted file mode 100644 index 036ce94f8..000000000 --- a/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/ComboLoader.java.keep +++ /dev/null @@ -1,36 +0,0 @@ -package org.simantics.views.swt.loader; - -import org.simantics.db.Resource; -import org.simantics.db.exception.DatabaseException; -import org.simantics.db.layer0.variable.Variable; -import org.simantics.scenegraph.ParentNode; -import org.simantics.scenegraph.loader.ScenegraphLoader; -import org.simantics.views.ontology.ViewsResources; -import org.simantics.views.swt.client.base.ISWTViewNode; -import org.simantics.views.swt.client.impl.SWTCombo; - -public class ComboLoader implements ScenegraphLoader { - - final private Resource configuration; - - public ComboLoader(Resource configuration) { - this.configuration = configuration; - } - - @Override - public ISWTViewNode create(ParentNode parent, Variable context) throws DatabaseException { - - SWTCombo node = parent.addNode(SWTCombo.class); - - node.setLayoutData(LoaderUtils.getGridData(configuration)); - node.setStyle(LoaderUtils.getStyle(configuration)); - - LoaderUtils.listen(configuration, context, ViewsResources.URIs.Combo_AvailableItems, node.getAvailableFunction()); - LoaderUtils.listen(configuration, context, ViewsResources.URIs.Combo_SelectedItem, node.getSelectionFunction()); - LoaderUtils.listen(configuration, context, ViewsResources.URIs.Combo_Modifier, node.getModifierFunction()); - - return node; - - } - -} diff --git a/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/CompositeLoader.java.keep b/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/CompositeLoader.java.keep deleted file mode 100644 index 846df84ef..000000000 --- a/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/CompositeLoader.java.keep +++ /dev/null @@ -1,36 +0,0 @@ -package org.simantics.views.swt.loader; - -import org.simantics.datatypes.literal.RGB; -import org.simantics.db.Resource; -import org.simantics.db.exception.DatabaseException; -import org.simantics.db.layer0.variable.Variable; -import org.simantics.scenegraph.ParentNode; -import org.simantics.scenegraph.loader.ScenegraphLoader; -import org.simantics.views.ontology.ViewsResources; -import org.simantics.views.swt.client.base.ISWTViewNode; -import org.simantics.views.swt.client.impl.SWTComposite; - -public class CompositeLoader implements ScenegraphLoader { - - final private Resource configuration; - - public CompositeLoader(Resource configuration) { - this.configuration = configuration; - } - - @Override - public ISWTViewNode create(ParentNode parent, Variable context) throws DatabaseException { - - SWTComposite node = parent.addNode(SWTComposite.class); - - LoaderUtils.listen(configuration, context, ViewsResources.URIs.Control_HasBackground, RGB.Integer.BINDING, node.getBackgroundFunction()); - - node.setLayoutData(LoaderUtils.getGridData(configuration)); - node.setLayout(LoaderUtils.getLayout(configuration)); - node.setStyle(LoaderUtils.getStyle(configuration)); - - return node; - - } - -} diff --git a/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/ExplorerLoader.java.keep b/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/ExplorerLoader.java.keep deleted file mode 100644 index a767ed970..000000000 --- a/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/ExplorerLoader.java.keep +++ /dev/null @@ -1,109 +0,0 @@ -package org.simantics.views.swt.loader; - -import org.eclipse.swt.SWT; -import org.eclipse.swt.widgets.Event; -import org.eclipse.swt.widgets.Listener; -import org.eclipse.swt.widgets.TreeItem; -import org.simantics.browsing.ui.BuiltinKeys; -import org.simantics.browsing.ui.NodeContext; -import org.simantics.databoard.Bindings; -import org.simantics.db.ReadGraph; -import org.simantics.db.Resource; -import org.simantics.db.VirtualGraph; -import org.simantics.db.WriteGraph; -import org.simantics.db.common.request.ResourceRead; -import org.simantics.db.common.request.WriteRequest; -import org.simantics.db.exception.DatabaseException; -import org.simantics.db.layer0.util.Simantics; -import org.simantics.db.layer0.variable.Variable; -import org.simantics.scenegraph.ParentNode; -import org.simantics.scenegraph.loader.ScenegraphLoader; -import org.simantics.views.ViewUtils; -import org.simantics.views.ontology.ViewsResources; -import org.simantics.views.swt.client.base.ISWTViewNode; -import org.simantics.views.swt.client.impl.SWTExplorer; - -public class ExplorerLoader implements ScenegraphLoader { - - final private Resource configuration; - - public ExplorerLoader(Resource configuration) { - this.configuration = configuration; - } - - @Override - public ISWTViewNode create(ParentNode parent, final Variable context) throws DatabaseException { - - SWTExplorer node = parent.addNode(SWTExplorer.class); - - node.setStyle(LoaderUtils.getStyle(configuration)); - - String browseContextURI = Simantics.getSession().sync(new ResourceRead(configuration) { - - @Override - public String perform(ReadGraph graph) throws DatabaseException { - ViewsResources VIEW = ViewsResources.getInstance(graph); - Resource browseContext = graph.getSingleObject(resource, VIEW.Explorer_BrowseContext); - return graph.getURI(browseContext); - } - - }); - - node.setBrowseContextURI(browseContextURI); - - node.setLayoutData(LoaderUtils.getGridData(configuration)); - - node.setColumns(LoaderUtils.getColumns(configuration)); - - LoaderUtils.listen(configuration, context, ViewsResources.URIs.Explorer_InputTransformation, node.getInputFunction()); - - LoaderUtils.listen(configuration, context, ViewsResources.URIs.Explorer_HasColumnsVisible, node.getColumnsVisibleFunction()); - - Listener selectionListener = Simantics.getSession().sync(new ResourceRead(configuration) { - - @Override - public Listener perform(ReadGraph graph) throws DatabaseException { - ViewsResources VIEW = ViewsResources.getInstance(graph); - Resource listener = graph.getPossibleObject(resource, VIEW.Explorer_SelectionListener); - if(listener == null) return null; - return graph.adapt(listener, Listener.class); - } - - }); - - if(selectionListener != null) node.addListenerToControl(SWT.Selection, selectionListener); - - node.addListenerToControl(SWT.Selection, new Listener() { - - @Override - public void handleEvent(Event event) { - - TreeItem item = (TreeItem)event.item; -// Tree tree = item.getParent(); -// GraphExplorer explorer = (GraphExplorer)tree.getData("GraphExplorer"); -// final Resource runtimeDiagram = (Resource)explorer.getRoot().getConstant(BuiltinKeys.INPUT); -// final boolean checked = item.getChecked(); - NodeContext nc = (NodeContext)item.getData(); - Object obj = nc.getConstant(BuiltinKeys.INPUT); - - if (obj instanceof Variable) { - final Variable var = (Variable) obj; - Simantics.getSession().async(new WriteRequest(Simantics.getSession().getService(VirtualGraph.class)) { - @Override - public void perform(WriteGraph graph) throws DatabaseException { - ViewsResources VIEW = ViewsResources.getInstance(graph); - System.err.println("setParameter " + context.getURI(graph) + " -> " + var.getURI(graph)); - ViewUtils.setParameter(graph, context, VIEW.Explorer_Selection, var.getURI(graph), Bindings.STRING); - } - }); - } - } - - }); - - return node; - - } - -} - diff --git a/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/LabelLoader.java.keep b/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/LabelLoader.java.keep deleted file mode 100644 index 53aa17f2c..000000000 --- a/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/LabelLoader.java.keep +++ /dev/null @@ -1,34 +0,0 @@ -package org.simantics.views.swt.loader; - -import org.simantics.db.Resource; -import org.simantics.db.exception.DatabaseException; -import org.simantics.db.layer0.variable.Variable; -import org.simantics.scenegraph.ParentNode; -import org.simantics.scenegraph.loader.ScenegraphLoader; -import org.simantics.views.ontology.ViewsResources; -import org.simantics.views.swt.client.base.ISWTViewNode; -import org.simantics.views.swt.client.impl.SWTLabel; - -public class LabelLoader implements ScenegraphLoader { - - final private Resource configuration; - - public LabelLoader(Resource configuration) { - this.configuration = configuration; - } - - @Override - public ISWTViewNode create(ParentNode parent, Variable context) throws DatabaseException { - - SWTLabel node = parent.addNode(SWTLabel.class); - - node.setLayoutData(LoaderUtils.getGridData(configuration)); - node.setStyle(LoaderUtils.getStyle(configuration)); - - LoaderUtils.listen(configuration, context, ViewsResources.URIs.TextContainer_HasText, node.getTextFunction()); - - return node; - - } - -} diff --git a/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/ScrolledCompositeLoader.java.keep b/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/ScrolledCompositeLoader.java.keep deleted file mode 100644 index 66dcb2844..000000000 --- a/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/ScrolledCompositeLoader.java.keep +++ /dev/null @@ -1,32 +0,0 @@ -package org.simantics.views.swt.loader; - -import org.simantics.db.Resource; -import org.simantics.db.exception.DatabaseException; -import org.simantics.db.layer0.variable.Variable; -import org.simantics.scenegraph.ParentNode; -import org.simantics.scenegraph.loader.ScenegraphLoader; -import org.simantics.views.swt.client.base.ISWTViewNode; -import org.simantics.views.swt.client.impl.SWTScrolledComposite; - -public class ScrolledCompositeLoader implements ScenegraphLoader { - - final private Resource configuration; - - public ScrolledCompositeLoader(Resource configuration) { - this.configuration = configuration; - } - - @Override - public ISWTViewNode create(ParentNode parent, Variable context) throws DatabaseException { - - SWTScrolledComposite node = parent.addNode(SWTScrolledComposite.class); - - node.setLayoutData(LoaderUtils.getGridData(configuration)); - node.setLayout(LoaderUtils.getLayout(configuration)); - node.setStyle(LoaderUtils.getStyle(configuration)); - - return node; - - } - -} diff --git a/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/TabFolderLoader.java.keep b/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/TabFolderLoader.java.keep deleted file mode 100644 index 4c6cdf059..000000000 --- a/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/TabFolderLoader.java.keep +++ /dev/null @@ -1,75 +0,0 @@ -package org.simantics.views.swt.loader; - -import java.util.Collection; -import java.util.HashSet; -import java.util.Set; - -import org.eclipse.swt.custom.CTabItem; -import org.eclipse.swt.widgets.Composite; -import org.eclipse.swt.widgets.Control; -import org.simantics.db.ReadGraph; -import org.simantics.db.Resource; -import org.simantics.db.common.request.UniqueRead; -import org.simantics.db.exception.DatabaseException; -import org.simantics.db.layer0.util.Simantics; -import org.simantics.db.layer0.variable.Variable; -import org.simantics.db.layer0.variable.Variables; -import org.simantics.scenegraph.ParentNode; -import org.simantics.scenegraph.loader.ScenegraphLoader; -import org.simantics.views.swt.client.base.ISWTViewNode; -import org.simantics.views.swt.client.impl.SWTTabFolder; - -public class TabFolderLoader implements ScenegraphLoader { - - final private Resource configuration; - - public TabFolderLoader(Resource configuration) { - this.configuration = configuration; - } - - @Override - public ISWTViewNode create(ParentNode parent, Variable context) throws DatabaseException { - - SWTTabFolder node = parent.addNode(SWTTabFolder.class); - - final Collection children = LoaderUtils.getChildren(configuration); - - String[] names = Simantics.getSession().sync(new UniqueRead() { - - @Override - public String[] perform(ReadGraph graph) throws DatabaseException { - - String[] result = new String[children.size()]; - - int index = 0; - for(Variable child : children) { - result[index++] = child.getPropertyValue(graph, Variables.LABEL); - } - - return result; - - } - - }); - - node.setTabNames(names); - - return node; - - } - - Set getControls(CTabItem item) { - HashSet result = new HashSet(); - forControl(item.getControl(), result); - return result; - } - - void forControl(Control control, HashSet controls) { - controls.add(control); - if(control instanceof Composite) { - Composite composite = (Composite)control; - for(Control child : composite.getChildren()) forControl(child, controls); - } - } - -} diff --git a/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/TextLoader.java.keep b/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/TextLoader.java.keep deleted file mode 100644 index 01417152b..000000000 --- a/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/TextLoader.java.keep +++ /dev/null @@ -1,39 +0,0 @@ -package org.simantics.views.swt.loader; - -import org.simantics.datatypes.literal.Font; -import org.simantics.datatypes.literal.RGB; -import org.simantics.db.Resource; -import org.simantics.db.exception.DatabaseException; -import org.simantics.db.layer0.variable.Variable; -import org.simantics.scenegraph.ParentNode; -import org.simantics.scenegraph.loader.ScenegraphLoader; -import org.simantics.views.ontology.ViewsResources; -import org.simantics.views.swt.client.base.ISWTViewNode; -import org.simantics.views.swt.client.impl.SWTText; - -public class TextLoader implements ScenegraphLoader { - - final private Resource configuration; - - public TextLoader(Resource configuration) { - this.configuration = configuration; - } - - @Override - public ISWTViewNode create(ParentNode parent, Variable context) throws DatabaseException { - - SWTText node = parent.addNode(SWTText.class); - - node.setLayoutData(LoaderUtils.getGridData(configuration)); - node.setStyle(LoaderUtils.getStyle(configuration)); - - LoaderUtils.listen(configuration, context, ViewsResources.URIs.TextContainer_HasText, node.getTextFunction()); - LoaderUtils.listen(configuration, context, ViewsResources.URIs.Control_HasBackground, RGB.Integer.BINDING, node.getBackgroundFunction()); - LoaderUtils.listen(configuration, context, ViewsResources.URIs.Control_HasForeground, RGB.Integer.BINDING, node.getForegroundFunction()); - LoaderUtils.listen(configuration, context, ViewsResources.URIs.Control_HasFont, Font.BINDING, node.getFontFunction()); - - return node; - - } - -} diff --git a/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/TrackedTextLoader.java.keep b/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/TrackedTextLoader.java.keep deleted file mode 100644 index 699f8ee68..000000000 --- a/bundles/org.simantics.views.swt/src/org/simantics/views/swt/loader/TrackedTextLoader.java.keep +++ /dev/null @@ -1,75 +0,0 @@ -package org.simantics.views.swt.loader; - -import org.simantics.databoard.Bindings; -import org.simantics.datatypes.literal.Font; -import org.simantics.datatypes.literal.RGB; -import org.simantics.db.Resource; -import org.simantics.db.VirtualGraph; -import org.simantics.db.WriteGraph; -import org.simantics.db.common.request.WriteRequest; -import org.simantics.db.exception.DatabaseException; -import org.simantics.db.layer0.util.Simantics; -import org.simantics.db.layer0.variable.Variable; -import org.simantics.scenegraph.ParentNode; -import org.simantics.scenegraph.loader.ScenegraphLoader; -import org.simantics.utils.ui.widgets.TrackedModifyEvent; -import org.simantics.utils.ui.widgets.TrackedModifyListener; -import org.simantics.views.ViewUtils; -import org.simantics.views.ontology.ViewsResources; -import org.simantics.views.swt.client.base.ISWTViewNode; -import org.simantics.views.swt.client.impl.SWTTrackedText; - -public class TrackedTextLoader implements ScenegraphLoader { - - final private Resource configuration; - - public TrackedTextLoader(Resource configuration) { - this.configuration = configuration; - } - - @Override - public ISWTViewNode create(ParentNode parent, final Variable context) throws DatabaseException { - - SWTTrackedText node = parent.addNode(SWTTrackedText.class); - - node.setLayoutData(LoaderUtils.getGridData(configuration)); - node.setStyle(LoaderUtils.getStyle(configuration)); - - LoaderUtils.listen(configuration, context, ViewsResources.URIs.TextContainer_HasText, node.getTextFunction()); - LoaderUtils.listen(configuration, context, ViewsResources.URIs.Control_HasForeground, RGB.Integer.BINDING, node.getForegroundFunction()); - LoaderUtils.listen(configuration, context, ViewsResources.URIs.TrackedText_HasInvalidBackground, RGB.Integer.BINDING, node.getInvalidBackgroundFunction()); - LoaderUtils.listen(configuration, context, ViewsResources.URIs.TrackedText_HasInactiveBackground, RGB.Integer.BINDING, node.getInactiveBackgroundFunction()); - LoaderUtils.listen(configuration, context, ViewsResources.URIs.TrackedText_HasHoverBackground, RGB.Integer.BINDING, node.getHoverBackgroundFunction()); - LoaderUtils.listen(configuration, context, ViewsResources.URIs.TrackedText_HasEditingBackground, RGB.Integer.BINDING, node.getEditingBackgroundFunction()); - LoaderUtils.listen(configuration, context, ViewsResources.URIs.Control_HasFont, Font.BINDING, node.getFontFunction()); - - LoaderUtils.listen(configuration, context, ViewsResources.URIs.TextReceiver_Modifier, node.getModifierFunction()); - LoaderUtils.listen(configuration, context, ViewsResources.URIs.TextReceiver_Validator, node.getValidatorFunction()); - - node.addModifyListener(new TrackedModifyListener() { - - @Override - public void modifyText(TrackedModifyEvent e) { - - final String text = e.getText(); - - Simantics.getSession().async(new WriteRequest(Simantics.getSession().getService(VirtualGraph.class)) { - - @Override - public void perform(WriteGraph graph) throws DatabaseException { - ViewsResources VIEW = ViewsResources.getInstance(graph); - System.err.println("setParameter " + context.getURI(graph) + " -> " + text); - ViewUtils.setParameter(graph, context, VIEW.TrackedText_Content, text, Bindings.STRING); - } - - }); - - } - - }); - - return node; - - } - -} diff --git a/bundles/org.simantics.views.text.ontology/.classpath b/bundles/org.simantics.views.text.ontology/.classpath new file mode 100644 index 000000000..b862a296d --- /dev/null +++ b/bundles/org.simantics.views.text.ontology/.classpath @@ -0,0 +1,7 @@ + + + + + + + diff --git a/bundles/org.simantics.views.text.ontology/.project b/bundles/org.simantics.views.text.ontology/.project new file mode 100644 index 000000000..7750c6c9d --- /dev/null +++ b/bundles/org.simantics.views.text.ontology/.project @@ -0,0 +1,34 @@ + + + org.simantics.views.text.ontology + + + + + + org.simantics.graph.builder + + + + + org.eclipse.jdt.core.javabuilder + + + + + org.eclipse.pde.ManifestBuilder + + + + + org.eclipse.pde.SchemaBuilder + + + + + + org.eclipse.pde.PluginNature + org.eclipse.jdt.core.javanature + org.simantics.graph.nature + + diff --git a/bundles/org.simantics.views.text.ontology/.settings/org.eclipse.jdt.core.prefs b/bundles/org.simantics.views.text.ontology/.settings/org.eclipse.jdt.core.prefs new file mode 100644 index 000000000..295926d96 --- /dev/null +++ b/bundles/org.simantics.views.text.ontology/.settings/org.eclipse.jdt.core.prefs @@ -0,0 +1,7 @@ +eclipse.preferences.version=1 +org.eclipse.jdt.core.compiler.codegen.inlineJsrBytecode=enabled +org.eclipse.jdt.core.compiler.codegen.targetPlatform=1.8 +org.eclipse.jdt.core.compiler.compliance=1.8 +org.eclipse.jdt.core.compiler.problem.assertIdentifier=error +org.eclipse.jdt.core.compiler.problem.enumIdentifier=error +org.eclipse.jdt.core.compiler.source=1.8 diff --git a/bundles/org.simantics.views.text.ontology/META-INF/MANIFEST.MF b/bundles/org.simantics.views.text.ontology/META-INF/MANIFEST.MF new file mode 100644 index 000000000..6d858cb04 --- /dev/null +++ b/bundles/org.simantics.views.text.ontology/META-INF/MANIFEST.MF @@ -0,0 +1,9 @@ +Manifest-Version: 1.0 +Bundle-ManifestVersion: 2 +Bundle-Name: http://www.simantics.org/TextViews +Bundle-SymbolicName: org.simantics.views.text.ontology +Bundle-Version: 1.0.0.qualifier +Bundle-Vendor: Semantum Oy +Require-Bundle: org.simantics.layer0, + org.simantics.views.ontology;bundle-version="1.2.0" +Bundle-RequiredExecutionEnvironment: JavaSE-1.8 diff --git a/bundles/org.simantics.views.text.ontology/build.properties b/bundles/org.simantics.views.text.ontology/build.properties new file mode 100644 index 000000000..fb164279d --- /dev/null +++ b/bundles/org.simantics.views.text.ontology/build.properties @@ -0,0 +1,6 @@ +source.. = src/ +output.. = bin/ +bin.includes = META-INF/,\ + .,\ + graph.tg +src.includes = graph/ diff --git a/bundles/org.simantics.views.text.ontology/graph.tg b/bundles/org.simantics.views.text.ontology/graph.tg new file mode 100644 index 000000000..5c3d7dba6 Binary files /dev/null and b/bundles/org.simantics.views.text.ontology/graph.tg differ diff --git a/bundles/org.simantics.views.text.ontology/graph/TextViews.pgraph b/bundles/org.simantics.views.text.ontology/graph/TextViews.pgraph new file mode 100644 index 000000000..6a9c846ff --- /dev/null +++ b/bundles/org.simantics.views.text.ontology/graph/TextViews.pgraph @@ -0,0 +1,7 @@ +L0 = +VIEWS = + +TEXTVIEWS = : L0.Ontology + @L0.new + +TEXTVIEWS.MarkupSourceViewer + + + + + + diff --git a/bundles/org.simantics.views.text/.project b/bundles/org.simantics.views.text/.project new file mode 100644 index 000000000..f3bb00f2b --- /dev/null +++ b/bundles/org.simantics.views.text/.project @@ -0,0 +1,28 @@ + + + org.simantics.views.text + + + + + + org.eclipse.jdt.core.javabuilder + + + + + org.eclipse.pde.ManifestBuilder + + + + + org.eclipse.pde.SchemaBuilder + + + + + + org.eclipse.pde.PluginNature + org.eclipse.jdt.core.javanature + + diff --git a/bundles/org.simantics.views.text/.settings/org.eclipse.jdt.core.prefs b/bundles/org.simantics.views.text/.settings/org.eclipse.jdt.core.prefs new file mode 100644 index 000000000..295926d96 --- /dev/null +++ b/bundles/org.simantics.views.text/.settings/org.eclipse.jdt.core.prefs @@ -0,0 +1,7 @@ +eclipse.preferences.version=1 +org.eclipse.jdt.core.compiler.codegen.inlineJsrBytecode=enabled +org.eclipse.jdt.core.compiler.codegen.targetPlatform=1.8 +org.eclipse.jdt.core.compiler.compliance=1.8 +org.eclipse.jdt.core.compiler.problem.assertIdentifier=error +org.eclipse.jdt.core.compiler.problem.enumIdentifier=error +org.eclipse.jdt.core.compiler.source=1.8 diff --git a/bundles/org.simantics.views.text/META-INF/MANIFEST.MF b/bundles/org.simantics.views.text/META-INF/MANIFEST.MF new file mode 100644 index 000000000..6e60a5a19 --- /dev/null +++ b/bundles/org.simantics.views.text/META-INF/MANIFEST.MF @@ -0,0 +1,20 @@ +Manifest-Version: 1.0 +Bundle-ManifestVersion: 2 +Bundle-Name: Modelled Text Viewer UI Controls +Bundle-SymbolicName: org.simantics.views.text;singleton:=true +Bundle-Version: 1.0.0.qualifier +Bundle-Activator: org.simantics.views.text.internal.Activator +Bundle-Vendor: Semantum Oy +Require-Bundle: org.eclipse.ui, + org.eclipse.ui.editors;bundle-version="3.9.0", + org.eclipse.core.runtime, + org.eclipse.jface.text;bundle-version="3.10.0", + org.eclipse.mylyn.wikitext.core;bundle-version="2.7.0", + org.eclipse.mylyn.wikitext.mediawiki.core;bundle-version="2.7.0", + org.eclipse.mylyn.wikitext.ui;bundle-version="2.7.0", + org.eclipse.mylyn.wikitext.mediawiki.ui;bundle-version="2.7.0", + org.simantics.views;bundle-version="1.1.0", + org.simantics.views.swt;bundle-version="1.0.0", + org.simantics.views.swt.client;bundle-version="1.0.0" +Bundle-RequiredExecutionEnvironment: JavaSE-1.8 +Bundle-ActivationPolicy: lazy diff --git a/bundles/org.simantics.views.text/adapters.xml b/bundles/org.simantics.views.text/adapters.xml new file mode 100644 index 000000000..c6dbeee60 --- /dev/null +++ b/bundles/org.simantics.views.text/adapters.xml @@ -0,0 +1,23 @@ + + + + + + + + + org.simantics.views.text.internal.SWTMarkupSourceViewer + + + + diff --git a/bundles/org.simantics.views.text/build.properties b/bundles/org.simantics.views.text/build.properties new file mode 100644 index 000000000..1ec5e34ca --- /dev/null +++ b/bundles/org.simantics.views.text/build.properties @@ -0,0 +1,6 @@ +source.. = src/ +output.. = bin/ +bin.includes = META-INF/,\ + .,\ + adapters.xml,\ + plugin.xml diff --git a/bundles/org.simantics.views.text/plugin.xml b/bundles/org.simantics.views.text/plugin.xml new file mode 100644 index 000000000..d2c90910a --- /dev/null +++ b/bundles/org.simantics.views.text/plugin.xml @@ -0,0 +1,45 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/bundles/org.simantics.views.text/src/org/simantics/views/text/internal/Activator.java b/bundles/org.simantics.views.text/src/org/simantics/views/text/internal/Activator.java new file mode 100644 index 000000000..e0ee562ff --- /dev/null +++ b/bundles/org.simantics.views.text/src/org/simantics/views/text/internal/Activator.java @@ -0,0 +1,63 @@ +/******************************************************************************* + * Copyright (c) 2017 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: + * Semantum Oy - initial API and implementation + *******************************************************************************/ +package org.simantics.views.text.internal; + +import org.eclipse.ui.plugin.AbstractUIPlugin; +import org.osgi.framework.BundleContext; + +/** + * The activator class controls the plug-in life cycle + * @author Tuukka Lehtonen + * @since 1.28.0 + */ +public class Activator extends AbstractUIPlugin { + + // The plug-in ID + public static final String PLUGIN_ID = "org.simantics.views.text"; //$NON-NLS-1$ + + // The shared instance + private static Activator plugin; + + /** + * The constructor + */ + public Activator() { + } + + /* + * (non-Javadoc) + * @see org.eclipse.ui.plugin.AbstractUIPlugin#start(org.osgi.framework.BundleContext) + */ + public void start(BundleContext context) throws Exception { + super.start(context); + plugin = this; + } + + /* + * (non-Javadoc) + * @see org.eclipse.ui.plugin.AbstractUIPlugin#stop(org.osgi.framework.BundleContext) + */ + public void stop(BundleContext context) throws Exception { + plugin = null; + super.stop(context); + } + + /** + * Returns the shared instance + * + * @return the shared instance + */ + public static Activator getDefault() { + return plugin; + } + +} diff --git a/bundles/org.simantics.views.text/src/org/simantics/views/text/internal/SWTMarkupSourceViewer.java b/bundles/org.simantics.views.text/src/org/simantics/views/text/internal/SWTMarkupSourceViewer.java new file mode 100644 index 000000000..756dfe21a --- /dev/null +++ b/bundles/org.simantics.views.text/src/org/simantics/views/text/internal/SWTMarkupSourceViewer.java @@ -0,0 +1,119 @@ +/******************************************************************************* + * Copyright (c) 2017 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: + * Semantum Oy - (#7066) initial API and implementation + *******************************************************************************/ +package org.simantics.views.text.internal; + +import org.eclipse.jface.text.Document; +import org.eclipse.mylyn.wikitext.core.parser.markup.MarkupLanguage; +import org.eclipse.mylyn.wikitext.mediawiki.core.MediaWikiLanguage; +import org.eclipse.mylyn.wikitext.ui.editor.MarkupSourceViewer; +import org.eclipse.mylyn.wikitext.ui.editor.MarkupSourceViewerConfiguration; +import org.eclipse.mylyn.wikitext.ui.editor.ShowInTargetBridge; +import org.eclipse.swt.SWT; +import org.eclipse.swt.custom.StyledText; +import org.eclipse.swt.events.SelectionEvent; +import org.eclipse.swt.events.SelectionListener; +import org.eclipse.swt.graphics.Point; +import org.eclipse.swt.widgets.Composite; +import org.eclipse.ui.services.IServiceLocator; +import org.eclipse.ui.swt.IFocusService; +import org.simantics.views.ViewUtils; +import org.simantics.views.swt.client.base.SingleSWTViewNode; + +/** + * @author Tuukka Lehtonen + * @since 1.28.0 + */ +public class SWTMarkupSourceViewer extends SingleSWTViewNode { + + private static final long serialVersionUID = 3034624586096417826L; + + private MarkupSourceViewer viewer; + private boolean textInitialized = false; + + @Override + public void createControls(Composite parent) { + MarkupLanguage language = new MediaWikiLanguage(); + viewer = new MarkupSourceViewer(parent, null, style | SWT.WRAP, language); + viewer.setEditable(false); + MarkupSourceViewerConfiguration configuration = new MarkupSourceViewerConfiguration(Activator.getDefault().getPreferenceStore()); + configuration.setMarkupLanguage(language); + configuration.setShowInTarget(new ShowInTargetBridge(viewer)); + viewer.configure(configuration); + viewer.setDocument(new Document(text != null ? text : "")); + control = viewer.getTextWidget(); + control.setData(TextViewerConstants.KEY_UNDO_MANAGER, viewer.getUndoManager()); + control.setEnabled(false); + + setProperties(); + + // Allow undo/redo handler to be bound to this text editor's focus + IServiceLocator locator = getSite(); + if (locator != null) { + IFocusService focusService = locator.getService(IFocusService.class); + if (focusService != null) { + focusService.addFocusTracker(control, TextViewerConstants.CONTEXT_IN_TEXT_VIEWER); + } + } + + control.addSelectionListener(new SelectionListener() { + @Override + public void widgetSelected(SelectionEvent e) { + ViewUtils.setWorkbenchSelection(viewer.getSelection()); + } + @Override + public void widgetDefaultSelected(SelectionEvent e) { + widgetSelected(e); + } + }); + } + + @Override + public void synchronizeText(String text) { + this.text = text; + if (text != null) { + // Try to keep the vertical scroll position of the text widget + int caretOffset = control.getCaretOffset(); + int charCount = control.getCharCount(); + int topIndex = viewer.getTopIndex(); + int diff = text.length() - charCount; + int newCaretOffset = Math.max(0, Math.min(caretOffset + diff, text.length())); + + viewer.getDocument().set(text); + viewer.setTopIndex(topIndex); + control.setCaretOffset(newCaretOffset); + viewer.setEditable(true); + control.setEnabled(true); + + // Prevent text viewer undo from allowing the + // user to undo the text viewer back to empty. + if (!textInitialized) { + viewer.getUndoManager().reset(); + textInitialized = true; + } + } else { + textInitialized = false; + viewer.setEditable(false); + control.setEnabled(false); + viewer.getDocument().set(""); + viewer.getUndoManager().reset(); + } + } + + public String readText() { + return viewer.getDocument().get(); + } + + public Point readSelection() { + return control.getSelection(); + } + +} \ No newline at end of file diff --git a/bundles/org.simantics.views.text/src/org/simantics/views/text/internal/TextViewerConstants.java b/bundles/org.simantics.views.text/src/org/simantics/views/text/internal/TextViewerConstants.java new file mode 100644 index 000000000..2924dc3ec --- /dev/null +++ b/bundles/org.simantics.views.text/src/org/simantics/views/text/internal/TextViewerConstants.java @@ -0,0 +1,36 @@ +/******************************************************************************* + * Copyright (c) 2017 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: + * Semantum Oy - (#7066) initial API and implementation + *******************************************************************************/ +package org.simantics.views.text.internal; + +import org.eclipse.jface.text.IUndoManager; +import org.eclipse.jface.text.TextViewer; +import org.eclipse.swt.widgets.Control; + +/** + * @author Tuukka Lehtonen + * @since 1.28.0 + */ +public class TextViewerConstants { + + /** + * The UI focus control context used for enabling normal text undo/redo for + * {@link TextViewer} controls. + */ + public static final String CONTEXT_IN_TEXT_VIEWER = "inTextViewer"; + + /** + * A key used for storing an {@link IUndoManager} as data of a + * {@link Control} using {@link Control#setData(String, Object)}. + */ + public static final String KEY_UNDO_MANAGER = "undoManager"; + +} diff --git a/bundles/org.simantics.views.text/src/org/simantics/views/text/internal/TextViewerUndoHandler.java b/bundles/org.simantics.views.text/src/org/simantics/views/text/internal/TextViewerUndoHandler.java new file mode 100644 index 000000000..f1c8adeab --- /dev/null +++ b/bundles/org.simantics.views.text/src/org/simantics/views/text/internal/TextViewerUndoHandler.java @@ -0,0 +1,169 @@ +/******************************************************************************* + * Copyright (c) 2017 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: + * Semantum Oy - (#7066) initial API and implementation + *******************************************************************************/ +package org.simantics.views.text.internal; + +import java.lang.reflect.InvocationTargetException; +import java.lang.reflect.Method; +import java.util.concurrent.Callable; + +import org.eclipse.core.commands.AbstractHandler; +import org.eclipse.core.commands.ExecutionEvent; +import org.eclipse.core.commands.ExecutionException; +import org.eclipse.core.runtime.IConfigurationElement; +import org.eclipse.core.runtime.IExecutableExtension; +import org.eclipse.jface.text.IUndoManager; +import org.eclipse.jface.text.TextViewer; +import org.eclipse.swt.SWT; +import org.eclipse.swt.widgets.Control; +import org.eclipse.swt.widgets.Display; +import org.eclipse.swt.widgets.Event; +import org.eclipse.swt.widgets.Listener; + +/** + * Handles the undo/redo command for {@link TextViewer}s through + * {@link IUndoManager}. + * + *

+ * The implementation looks for an IUndoManager from the current focus control + * using the {@link TextViewerConstants#KEY_UNDO_MANAGER} data key. Its + * existence determines whether this handler {@link #isHandled()} returns + * true or false. + * + *

+ * The handler expects to receive a single string as an argument through the + * extension definitions ({@link IExecutableExtension}) that determines which + * method is invoked from IUndoManager (undo or redo). + * + *

+ * Implementation is partially copied from + * org.eclipse.ui.internal.handlers.WidgetMethodHandler. + * + * @since 1.28.0 + */ +public class TextViewerUndoHandler extends AbstractHandler implements IExecutableExtension { + + /** + * The parameters to pass to the method this handler invokes. This handler + * always passes no parameters. + */ + protected static final Class[] NO_PARAMETERS = new Class[0]; + + public TextViewerUndoHandler() { + display = Display.getCurrent(); + if (display != null) { + focusListener = new Listener() { + @Override + public void handleEvent(Event event) { + updateEnablement(); + } + }; + display.addFilter(SWT.FocusIn, focusListener); + } + } + + void updateEnablement() { + boolean rc = isHandled(); + if (rc != isEnabled()) { + setBaseEnabled(rc); + } + } + + /** + * The name of the method to be invoked by this handler. This value should + * never be null. + */ + protected String methodName; + private Listener focusListener; + private Display display; + + @Override + public Object execute(final ExecutionEvent event) throws ExecutionException { + Callable runnable = getMethodToExecute(); + if (runnable != null) { + try { + runnable.call(); + } catch (ExecutionException e) { + throw e; + } catch (Exception e) { + throw new ExecutionException("Unexpected failure executing method " + methodName + " through " + runnable); + } + } + return null; + } + + @Override + public final boolean isHandled() { + return getMethodToExecute() != null; + } + + /** + * Looks up the method on the focus control. + * + * @return The method on the focus control; null if none. + */ + protected Callable getMethodToExecute() { + Display display = Display.getCurrent(); + if (display == null) + return null; + + Control focusControl = display.getFocusControl(); + if (focusControl == null) + return null; + + IUndoManager undoManager = (IUndoManager) focusControl.getData(TextViewerConstants.KEY_UNDO_MANAGER); + if (undoManager == null) + return null; + + try { + Method method = undoManager.getClass().getMethod(methodName, NO_PARAMETERS); + if (method != null) + return runner(undoManager, method); + } catch (NoSuchMethodException e) { + // Fall through... + } + + return null; + } + + protected Callable runner(IUndoManager undoManager, Method method) { + return () -> { + try { + method.invoke(undoManager); + return true; + } catch (IllegalAccessException e) { + // The method is protected, so do nothing. + return false; + } catch (InvocationTargetException e) { + throw new ExecutionException( + "An exception occurred while executing " //$NON-NLS-1$ + + method.getName(), e + .getTargetException()); + + } + }; + } + + @Override + public void setInitializationData(IConfigurationElement config, String propertyName, Object data) { + methodName = data.toString(); + } + + @Override + public void dispose() { + if (display != null && !display.isDisposed()) { + display.removeFilter(SWT.FocusIn, focusListener); + } + display = null; + focusListener = null; + } + +} \ No newline at end of file diff --git a/bundles/pom.xml b/bundles/pom.xml index bbc378243..319859a65 100644 --- a/bundles/pom.xml +++ b/bundles/pom.xml @@ -221,6 +221,8 @@ org.simantics.views.ontology org.simantics.views.swt org.simantics.views.swt.client + org.simantics.views.text + org.simantics.views.text.ontology org.simantics.wiki.ui org.simantics.workbench org.simantics.workbench.ontology diff --git a/features/org.simantics.views.swt.feature/feature.xml b/features/org.simantics.views.swt.feature/feature.xml index 17247686e..41508ef1c 100644 --- a/features/org.simantics.views.swt.feature/feature.xml +++ b/features/org.simantics.views.swt.feature/feature.xml @@ -1,7 +1,7 @@ @@ -35,4 +35,18 @@ version="0.0.0" unpack="false"/> + + + +