diff --git a/org.eclipse.gef.dot.tests/src/org/eclipse/gef/dot/tests/DotEditorDoubleClickingTests.xtend b/org.eclipse.gef.dot.tests/src/org/eclipse/gef/dot/tests/DotEditorDoubleClickingTests.xtend
index e15d0f1ca3..50b1ff11c7 100644
--- a/org.eclipse.gef.dot.tests/src/org/eclipse/gef/dot/tests/DotEditorDoubleClickingTests.xtend
+++ b/org.eclipse.gef.dot.tests/src/org/eclipse/gef/dot/tests/DotEditorDoubleClickingTests.xtend
@@ -472,6 +472,199 @@ class DotEditorDoubleClickingTests extends AbstractEditorDoubleClickTextSelectio
'''.assertSelectedTextAfterDoubleClicking('''"x11"''')
}
+ @Test def edge_html_label_001() {
+ '''
+ digraph {
+ 1->2[label=<bold Te«c»xt>]
+ }
+ '''.assertSelectedTextAfterDoubleClicking('''Text''')
+ }
+
+ @Test def edge_html_label_002() {
+ '''
+ digraph {
+ 1->2[label=<<«c»b>bold Text>]
+ }
+ '''.assertSelectedTextAfterDoubleClicking('''b''')
+ }
+
+ @Test def edge_html_label_003() {
+ '''
+ digraph {
+ 1->2[label=<«c»bold Text>]
+ }
+ '''.assertSelectedTextAfterDoubleClicking('''<''')
+ }
+
+ @Test def edge_html_label_004() {
+ '''
+ digraph {
+ 1->2[label=<serif Text>]
+ }
+ '''.assertSelectedTextAfterDoubleClicking('''="''')
+ }
+
+ @Test def edge_html_label_005() {
+ '''
+ digraph {
+ 1->2[label=<serif Text>]
+ }
+ '''.assertSelectedTextAfterDoubleClicking('''Times''')
+ }
+
+ @Test def edge_html_label_006() {
+ '''
+ digraph {
+ 1->2[label=<serif Text>]
+ }
+ '''.assertSelectedTextAfterDoubleClicking('''face''')
+ }
+
+ @Test def edge_html_label_007() {
+ '''
+ digraph {
+ 1->2[label=<serif Text>]
+ }
+ '''.assertSelectedTextAfterDoubleClicking('''face''')
+ }
+
+ @Test def edge_html_label_008() {
+ '''
+ digraph {
+ 1->2[label=<serif Text>]
+ }
+ '''.assertSelectedTextAfterDoubleClicking('''font''')
+ }
+
+
+ @Test def edge_html_label_009() {
+ '''
+ digraph {
+ 1->2[label=«c»<serif Text>]
+ }
+ '''.assertSelectedTextAfterDoubleClicking('''<serif Text>''')
+ }
+
+ @Test def edge_html_label_010() {
+ '''
+ digraph{1->2[label=<«c»text>]}
+ '''.assertSelectedTextAfterDoubleClicking('''text''')
+ }
+
+ @Test def edge_html_label_011() {
+ '''
+ digraph{1->2[label=]}
+ '''.assertSelectedTextAfterDoubleClicking('''text''')
+ }
+
+ @Test def edge_html_label_012() {
+ '''
+ digraph{1->2[label=]}
+ '''.assertSelectedTextAfterDoubleClicking('''text''')
+ }
+
+ @Test def edge_html_label_013() {
+ '''
+ digraph{1->2[label=]}
+ '''.assertSelectedTextAfterDoubleClicking('''text''')
+ }
+
+ @Test def edge_html_label_014() {
+ '''
+ digraph{1->2[label=]}
+ '''.assertSelectedTextAfterDoubleClicking('''text''')
+ }
+
+ @Test def edge_html_label_015() {
+ '''
+ digraph{1->2[label=< «c»text >]}
+ '''.assertSelectedTextAfterDoubleClicking('''text''')
+ }
+
+ @Test def edge_html_label_016() {
+ '''
+ digraph{1->2[label=< t«c»ext >]}
+ '''.assertSelectedTextAfterDoubleClicking('''text''')
+ }
+
+ @Test def edge_html_label_017() {
+ '''
+ digraph{1->2[label=< te«c»xt >]}
+ '''.assertSelectedTextAfterDoubleClicking('''text''')
+ }
+
+ @Test def edge_html_label_018() {
+ '''
+ digraph{1->2[label=< tex«c»t >]}
+ '''.assertSelectedTextAfterDoubleClicking('''text''')
+ }
+
+ @Test def edge_html_label_019() {
+ '''
+ digraph{1->2[label=< text«c» >]}
+ '''.assertSelectedTextAfterDoubleClicking('''text''')
+ }
+
+ @Test def edge_html_label_020() {
+ '''
+ digraph{1->2[label=<«c»text>]}
+ '''.assertSelectedTextAfterDoubleClicking('''text''')
+ }
+
+ @Test def edge_html_label_021() {
+ '''
+ digraph{1->2[label=<t«c»ext>]}
+ '''.assertSelectedTextAfterDoubleClicking('''text''')
+ }
+
+ @Test def edge_html_label_022() {
+ '''
+ digraph{1->2[label=<te«c»xt>]}
+ '''.assertSelectedTextAfterDoubleClicking('''text''')
+ }
+
+ @Test def edge_html_label_023() {
+ '''
+ digraph{1->2[label=<tex«c»t>]}
+ '''.assertSelectedTextAfterDoubleClicking('''text''')
+ }
+
+ @Test def edge_html_label_024() {
+ '''
+ digraph{1->2[label=<text«c»>]}
+ '''.assertSelectedTextAfterDoubleClicking('''text''')
+ }
+
+ @Test def edge_html_label_025() {
+ '''
+ digraph{1->2[label=< «c»text >]}
+ '''.assertSelectedTextAfterDoubleClicking('''text''')
+ }
+
+ @Test def edge_html_label_026() {
+ '''
+ digraph{1->2[label=< t«c»ext >]}
+ '''.assertSelectedTextAfterDoubleClicking('''text''')
+ }
+
+ @Test def edge_html_label_027() {
+ '''
+ digraph{1->2[label=< te«c»xt >]}
+ '''.assertSelectedTextAfterDoubleClicking('''text''')
+ }
+
+ @Test def edge_html_label_028() {
+ '''
+ digraph{1->2[label=< tex«c»t >]}
+ '''.assertSelectedTextAfterDoubleClicking('''text''')
+ }
+
+ @Test def edge_html_label_029() {
+ '''
+ digraph{1->2[label=< text«c» >]}
+ '''.assertSelectedTextAfterDoubleClicking('''text''')
+ }
+
@Test def edge_style_001() {
'''
graph{
@@ -986,6 +1179,132 @@ class DotEditorDoubleClickingTests extends AbstractEditorDoubleClickTextSelectio
'''.assertSelectedTextAfterDoubleClicking('''"2.3"''')
}
+ @Test def node_html_label_001() {
+ '''
+ graph {
+ 1[label=<
+
+ >]
+ }
+ '''.assertSelectedTextAfterDoubleClicking('''Category''')
+ }
+
+ @Test def node_html_label_002() {
+ '''
+ graph {
+ 1[label=<
+
+ >]
+ }
+ '''.assertSelectedTextAfterDoubleClicking('''Category''')
+ }
+
+ @Test def node_html_label_003() {
+ '''
+ graph {
+ 1[label=<
+
+ >]
+ }
+ '''.assertSelectedTextAfterDoubleClicking('''Category''')
+ }
+
+ @Test def node_html_label_004() {
+ '''
+ graph {
+ 1[label=<
+
+ >]
+ }
+ '''.assertSelectedTextAfterDoubleClicking('''One''')
+ }
+
+ @Test def node_html_label_005() {
+ '''
+ graph {
+ 1[label=<
+
+ >]
+ }
+ '''.assertSelectedTextAfterDoubleClicking('''align''')
+ }
+
+ @Test def node_html_label_006() {
+ '''
+ graph {
+ 1[label=<
+
+ >]
+ }
+ '''.assertSelectedTextAfterDoubleClicking('''center''')
+ }
+
+ @Test def node_html_label_007() {
+ '''
+ graph {
+ 1[label=<
+
+
+ <«c»td align="center">Category
+
+
+ >]
+ }
+ '''.assertSelectedTextAfterDoubleClicking('''td''')
+ }
+
+ @Test def node_html_label_008() {
+ '''
+ graph {
+ 1[label=<
+
+ >]
+ }
+ '''.assertSelectedTextAfterDoubleClicking('''tr''')
+ }
+
+ @Test def node_html_label_009() {
+ '''
+ graph {
+ 1[label=<
+
+ >]
+ }
+ '''.assertSelectedTextAfterDoubleClicking('''Category''')
+ }
+
@Test def node_record_label_001() {
'''
graph{
diff --git a/org.eclipse.gef.dot.tests/src/org/eclipse/gef/dot/tests/DotHtmlLabelTokenTypeToPartitionMapperTests.xtend b/org.eclipse.gef.dot.tests/src/org/eclipse/gef/dot/tests/DotHtmlLabelTokenTypeToPartitionMapperTests.xtend
index 5f234d9cf5..d39c0cb4d3 100644
--- a/org.eclipse.gef.dot.tests/src/org/eclipse/gef/dot/tests/DotHtmlLabelTokenTypeToPartitionMapperTests.xtend
+++ b/org.eclipse.gef.dot.tests/src/org/eclipse/gef/dot/tests/DotHtmlLabelTokenTypeToPartitionMapperTests.xtend
@@ -7,12 +7,14 @@
* http://www.eclipse.org/legal/epl-v10.html
*
* Contributors:
- * Tamas Miklossy (itemis AG) - initial API and implementation
+ * Tamas Miklossy (itemis AG) - initial API and implementation
+ * Zoey Gerrit Prigge (itemis AG) - introduced textPartition (bug #532244)
*******************************************************************************/
package org.eclipse.gef.dot.tests
import com.google.inject.Inject
import org.eclipse.gef.dot.internal.language.DotHtmlLabelUiInjectorProvider
+import org.eclipse.gef.dot.internal.ui.language.editor.DotHtmlLabelTerminalsTokenTypeToPartitionMapper
import org.eclipse.jface.text.IDocument
import org.eclipse.xtext.junit4.InjectWith
import org.eclipse.xtext.junit4.XtextRunner
@@ -49,7 +51,7 @@ class DotHtmlLabelTokenTypeToPartitionMapperTests {
@Test def RULE_WS() { "RULE_WS".hasDefaultPartition }
- @Test def RULE_TEXT() { "RULE_TEXT".hasDefaultPartition }
+ @Test def RULE_TEXT() { "RULE_TEXT".hasTextPartition }
private def hasDefaultPartition(String tokenName) {
tokenName.hasPartition(IDocument.DEFAULT_CONTENT_TYPE)
@@ -62,6 +64,10 @@ class DotHtmlLabelTokenTypeToPartitionMapperTests {
private def hasCommentPartition(String tokenName) {
tokenName.hasPartition(TerminalsTokenTypeToPartitionMapper.COMMENT_PARTITION)
}
+
+ private def hasTextPartition(String tokenName) {
+ tokenName.hasPartition(DotHtmlLabelTerminalsTokenTypeToPartitionMapper.TEXT_PARTITION)
+ }
private def hasPartition(String tokenName, String expectedPartition) {
val actualPartition = tokenName.tokenType.partitionType
diff --git a/org.eclipse.gef.dot.tests/src/org/eclipse/gef/dot/tests/DotTokenTypeToPartitionMapperTests.xtend b/org.eclipse.gef.dot.tests/src/org/eclipse/gef/dot/tests/DotTokenTypeToPartitionMapperTests.xtend
index fa7aeea6c5..64314a86c8 100644
--- a/org.eclipse.gef.dot.tests/src/org/eclipse/gef/dot/tests/DotTokenTypeToPartitionMapperTests.xtend
+++ b/org.eclipse.gef.dot.tests/src/org/eclipse/gef/dot/tests/DotTokenTypeToPartitionMapperTests.xtend
@@ -7,12 +7,14 @@
* http://www.eclipse.org/legal/epl-v10.html
*
* Contributors:
- * Tamas Miklossy (itemis AG) - initial API and implementation
+ * Tamas Miklossy (itemis AG) - initial API and implementation
+ * Zoey Gerrit Prigge (itemis AG) - introduced htmlStringPartition (bug #532244)
*******************************************************************************/
package org.eclipse.gef.dot.tests
import com.google.inject.Inject
import org.eclipse.gef.dot.internal.language.DotUiInjectorProvider
+import org.eclipse.gef.dot.internal.ui.language.editor.DotTerminalsTokenTypeToPartitionMapper
import org.eclipse.jface.text.IDocument
import org.eclipse.xtext.junit4.InjectWith
import org.eclipse.xtext.junit4.XtextRunner
@@ -77,7 +79,7 @@ class DotTokenTypeToPartitionMapperTests {
@Test def RULE_HTML_CHARS() { "RULE_HTML_CHARS".hasDefaultPartition }
- @Test def RULE_HTML_STRING() { "RULE_HTML_STRING".hasDefaultPartition }
+ @Test def RULE_HTML_STRING() { "RULE_HTML_STRING".hasHtmlStringPartition }
@Test def RULE_ML_COMMENT() { "RULE_ML_COMMENT".hasCommentPartition }
@@ -102,6 +104,10 @@ class DotTokenTypeToPartitionMapperTests {
private def hasCommentPartition(String tokenName) {
tokenName.hasPartition(TerminalsTokenTypeToPartitionMapper.COMMENT_PARTITION)
}
+
+ private def hasHtmlStringPartition(String tokenName) {
+ tokenName.hasPartition(DotTerminalsTokenTypeToPartitionMapper.HTML_STRING_PARTITION)
+ }
private def hasPartition(String tokenName, String expectedPartition) {
val actualPartition = tokenName.tokenType.partitionType
diff --git a/org.eclipse.gef.dot.ui/src/org/eclipse/gef/dot/internal/ui/language/DotHtmlLabelUiModule.java b/org.eclipse.gef.dot.ui/src/org/eclipse/gef/dot/internal/ui/language/DotHtmlLabelUiModule.java
index 3469829a4d..d647a4b61e 100644
--- a/org.eclipse.gef.dot.ui/src/org/eclipse/gef/dot/internal/ui/language/DotHtmlLabelUiModule.java
+++ b/org.eclipse.gef.dot.ui/src/org/eclipse/gef/dot/internal/ui/language/DotHtmlLabelUiModule.java
@@ -7,16 +7,19 @@
* http://www.eclipse.org/legal/epl-v10.html
*
* Contributors:
- * Matthias Wienand (itemis AG) - initial API and implementation
- * Tamas Miklossy (itemis AG) - improve html-label highlighting/folding
+ * Matthias Wienand (itemis AG) - initial API and implementation
+ * Tamas Miklossy (itemis AG) - improve html-label highlighting/folding
+ * Zoey Gerrit Prigge (itemis AG) - bind double click strategy provider (bug #532244)
*
*******************************************************************************/
package org.eclipse.gef.dot.internal.ui.language;
+import org.eclipse.gef.dot.internal.ui.language.doubleclicking.DotHtmlLabelDoubleClickStrategyProvider;
import org.eclipse.gef.dot.internal.ui.language.editor.DotHtmlLabelTerminalsTokenTypeToPartitionMapper;
import org.eclipse.gef.dot.internal.ui.language.folding.DotHtmlLabelFoldingRegionProvider;
import org.eclipse.gef.dot.internal.ui.language.highlighting.DotHtmlLabelSemanticHighlightingCalculator;
import org.eclipse.ui.plugin.AbstractUIPlugin;
+import org.eclipse.xtext.ui.editor.doubleClicking.DoubleClickStrategyProvider;
import org.eclipse.xtext.ui.editor.folding.IFoldingRegionProvider;
import org.eclipse.xtext.ui.editor.model.ITokenTypeToPartitionTypeMapper;
import org.eclipse.xtext.ui.editor.syntaxcoloring.ISemanticHighlightingCalculator;
@@ -41,4 +44,9 @@ public Class extends IFoldingRegionProvider> bindIFoldingRegionProvider() {
public Class extends ITokenTypeToPartitionTypeMapper> bindITokenTypeToPartitionTypeMapper() {
return DotHtmlLabelTerminalsTokenTypeToPartitionMapper.class;
}
+
+ public Class extends DoubleClickStrategyProvider> bindDoubleClickStrategyProvider() {
+ return DotHtmlLabelDoubleClickStrategyProvider.class;
+ }
+
}
diff --git a/org.eclipse.gef.dot.ui/src/org/eclipse/gef/dot/internal/ui/language/DotUiModule.java b/org.eclipse.gef.dot.ui/src/org/eclipse/gef/dot/internal/ui/language/DotUiModule.java
index 5b6f8a345a..b2addd8981 100644
--- a/org.eclipse.gef.dot.ui/src/org/eclipse/gef/dot/internal/ui/language/DotUiModule.java
+++ b/org.eclipse.gef.dot.ui/src/org/eclipse/gef/dot/internal/ui/language/DotUiModule.java
@@ -7,20 +7,22 @@
* http://www.eclipse.org/legal/epl-v10.html
*
* Contributors:
- * Alexander Nyßen (itemis AG) - initial API and implementation
- * Tamas Miklossy (itemis AG) - add binding for template proposal provider (bug #321775)
- * - add binding for folding region provider (bug #321775)
- * - add binding for EObject hover/hover provider (bug #461506)
- * - add binding for hyperlink helper (bug #461506)
- * - add binding for rename strategy (bug #530423)
- * - add binding for occurrence computer (bug #530699)
- * - add binding for reference finder/reference query executor (bug #531049)
- * - add binding for the Xtext Editor
- * - add binding for token type to partition mapper (bug #532244)
+ * Alexander Nyßen (itemis AG) - initial API and implementation
+ * Tamas Miklossy (itemis AG) - add binding for template proposal provider (bug #321775)
+ * - add binding for folding region provider (bug #321775)
+ * - add binding for EObject hover/hover provider (bug #461506)
+ * - add binding for hyperlink helper (bug #461506)
+ * - add binding for rename strategy (bug #530423)
+ * - add binding for occurrence computer (bug #530699)
+ * - add binding for reference finder/reference query executor (bug #531049)
+ * - add binding for the Xtext Editor
+ * - add binding for token type to partition mapper (bug #532244)
+ * Zoey Gerrit Prigge (itemis AG) - add binding for doubleClickStrategyProvider (bug #532244)
*******************************************************************************/
package org.eclipse.gef.dot.internal.ui.language;
import org.eclipse.gef.dot.internal.ui.language.contentassist.DynamicTemplateProposalProvider;
+import org.eclipse.gef.dot.internal.ui.language.doubleclicking.DotDoubleClickStrategyProvider;
import org.eclipse.gef.dot.internal.ui.language.editor.DotEditor;
import org.eclipse.gef.dot.internal.ui.language.editor.DotTerminalsTokenTypeToPartitionMapper;
import org.eclipse.gef.dot.internal.ui.language.findreferences.DotFindReferencesQueryExecutor;
@@ -37,6 +39,7 @@
import org.eclipse.ui.plugin.AbstractUIPlugin;
import org.eclipse.xtext.ui.editor.XtextEditor;
import org.eclipse.xtext.ui.editor.contentassist.ITemplateProposalProvider;
+import org.eclipse.xtext.ui.editor.doubleClicking.DoubleClickStrategyProvider;
import org.eclipse.xtext.ui.editor.findrefs.IReferenceFinder;
import org.eclipse.xtext.ui.editor.findrefs.ReferenceQueryExecutor;
import org.eclipse.xtext.ui.editor.folding.IFoldingRegionProvider;
@@ -117,4 +120,8 @@ public Class extends XtextEditor> bindXtextEditor() {
public Class extends ITokenTypeToPartitionTypeMapper> bindITokenTypeToPartitionTypeMapper() {
return DotTerminalsTokenTypeToPartitionMapper.class;
}
+
+ public Class extends DoubleClickStrategyProvider> bindDoubleClickStrategyProvider() {
+ return DotDoubleClickStrategyProvider.class;
+ }
}
diff --git a/org.eclipse.gef.dot.ui/src/org/eclipse/gef/dot/internal/ui/language/doubleclicking/DotDoubleClickStrategyProvider.java b/org.eclipse.gef.dot.ui/src/org/eclipse/gef/dot/internal/ui/language/doubleclicking/DotDoubleClickStrategyProvider.java
new file mode 100644
index 0000000000..7a9ac4c5e0
--- /dev/null
+++ b/org.eclipse.gef.dot.ui/src/org/eclipse/gef/dot/internal/ui/language/doubleclicking/DotDoubleClickStrategyProvider.java
@@ -0,0 +1,33 @@
+/*******************************************************************************
+ * Copyright (c) 2018 itemis AG and others.
+ *
+ * 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:
+ * Zoey Gerrit Prigge (itemis AG) - initial API and implementation (bug #532244)
+ *******************************************************************************/
+package org.eclipse.gef.dot.internal.ui.language.doubleclicking;
+
+import org.eclipse.gef.dot.internal.ui.language.editor.DotTerminalsTokenTypeToPartitionMapper;
+import org.eclipse.jface.text.ITextDoubleClickStrategy;
+import org.eclipse.jface.text.source.ISourceViewer;
+import org.eclipse.xtext.ui.editor.doubleClicking.DoubleClickStrategyProvider;
+
+public class DotDoubleClickStrategyProvider
+ extends DoubleClickStrategyProvider {
+
+ @Override
+ public ITextDoubleClickStrategy getStrategy(ISourceViewer sourceViewer,
+ String contentType, String documentPartitioning) {
+ if (DotTerminalsTokenTypeToPartitionMapper.HTML_STRING_PARTITION
+ .equals(contentType)) {
+ return new DotHtmlLabelDoubleClickStrategy();
+ }
+ return super.getStrategy(sourceViewer, contentType,
+ documentPartitioning);
+ }
+
+}
diff --git a/org.eclipse.gef.dot.ui/src/org/eclipse/gef/dot/internal/ui/language/doubleclicking/DotHtmlLabelDoubleClickStrategy.java b/org.eclipse.gef.dot.ui/src/org/eclipse/gef/dot/internal/ui/language/doubleclicking/DotHtmlLabelDoubleClickStrategy.java
new file mode 100644
index 0000000000..483858e2d1
--- /dev/null
+++ b/org.eclipse.gef.dot.ui/src/org/eclipse/gef/dot/internal/ui/language/doubleclicking/DotHtmlLabelDoubleClickStrategy.java
@@ -0,0 +1,186 @@
+/*******************************************************************************
+ * Copyright (c) 2018 itemis AG and others.
+ *
+ * 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:
+ * Zoey Gerrit Prigge (itemis AG) - initial API and implementation (bug #532244)
+ *******************************************************************************/
+package org.eclipse.gef.dot.internal.ui.language.doubleclicking;
+
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+
+import org.eclipse.gef.dot.internal.ui.language.editor.DotEditorUtils;
+import org.eclipse.gef.dot.internal.ui.language.internal.DotActivator;
+import org.eclipse.jface.text.BadLocationException;
+import org.eclipse.jface.text.DefaultTextDoubleClickStrategy;
+import org.eclipse.jface.text.IDocument;
+import org.eclipse.jface.text.IRegion;
+import org.eclipse.jface.text.ITextDoubleClickStrategy;
+import org.eclipse.jface.text.ITypedRegion;
+import org.eclipse.jface.text.Region;
+import org.eclipse.xtext.ui.editor.doubleClicking.DoubleClickStrategyProvider;
+import org.eclipse.xtext.ui.editor.model.IXtextDocument;
+import org.eclipse.xtext.ui.editor.model.XtextDocument;
+
+import com.google.inject.Injector;
+
+public class DotHtmlLabelDoubleClickStrategy
+ extends DefaultTextDoubleClickStrategy {
+
+ @Override
+ protected IRegion findWord(IDocument document, int offset) {
+ ITypedRegion region = null;
+ try {
+ region = document.getPartition(offset);
+ } catch (BadLocationException e) {
+ e.printStackTrace();
+ return null;
+ }
+
+ // Translate the partition offset for the HtmlLabel by one to point to
+ // the position after the angle bracket indicating an HtmlLabelStart in
+ // the host grammar.
+ int htmlLabelStartOffset = region.getOffset() + 1;
+ // Translate the partition length by two points to discount for both
+ // HtmlLabel indicating angle brackets (start and end) only present in
+ // the dot host grammar.
+ int htmlLabelLength = region.getLength() - 2;
+
+ String htmlLabel = null;
+ try {
+ htmlLabel = document.get(htmlLabelStartOffset, htmlLabelLength);
+ } catch (BadLocationException e) {
+ e.printStackTrace();
+ return null;
+ }
+
+ Injector injector = DotActivator.getInstance().getInjector(
+ DotActivator.ORG_ECLIPSE_GEF_DOT_INTERNAL_LANGUAGE_DOTHTMLLABEL);
+
+ IXtextDocument htmlDocument = null;
+ try {
+ htmlDocument = DotEditorUtils.getDocument(injector, htmlLabel);
+ } catch (Exception e) {
+ e.printStackTrace();
+ return null;
+ }
+
+ // translate the offset of the double-click position relative to
+ // the htmlDocument
+ int htmlLabelClickOffset = offset - htmlLabelStartOffset;
+
+ ITextDoubleClickStrategy doubleClickStrategy = null;
+ try {
+ doubleClickStrategy = injector
+ .getInstance(DoubleClickStrategyProvider.class)
+ .getStrategy(null,
+ htmlDocument.getContentType(htmlLabelClickOffset),
+ XtextDocument.DEFAULT_PARTITIONING);
+ } catch (BadLocationException e) {
+ e.printStackTrace();
+ return null;
+ }
+
+ IRegion htmlRegion = findRegionHtml(htmlDocument, htmlLabelClickOffset,
+ doubleClickStrategy);
+
+ return new Region(htmlLabelStartOffset + htmlRegion.getOffset(),
+ htmlRegion.getLength());
+ }
+
+ private IRegion findRegionHtml(IXtextDocument htmlDocument,
+ int htmlLabelClickOffset,
+ ITextDoubleClickStrategy doubleClickStrategy) {
+ IRegion htmlRegion = findExtendedSelectionHtml(doubleClickStrategy,
+ htmlDocument, htmlLabelClickOffset);
+
+ if (htmlRegion != null)
+ return htmlRegion;
+
+ return findWordHtml(doubleClickStrategy, htmlDocument,
+ htmlLabelClickOffset);
+ }
+
+ private IRegion findExtendedSelectionHtml(
+ ITextDoubleClickStrategy doubleClickStrategy,
+ IXtextDocument htmlDocument, int htmlLabelClickOffset) {
+ Method findExtendedSelection = findExtendedDoubleClickSelectionMethod(
+ doubleClickStrategy.getClass());
+ return invokeMethodOn(findExtendedSelection, doubleClickStrategy,
+ htmlDocument, htmlLabelClickOffset);
+ }
+
+ private IRegion findWordHtml(ITextDoubleClickStrategy doubleClickStrategy,
+ IXtextDocument htmlDocument, int htmlLabelClickOffset) {
+ Method findWord = findWordMethod(doubleClickStrategy.getClass());
+ return invokeMethodOn(findWord, doubleClickStrategy, htmlDocument,
+ htmlLabelClickOffset);
+ }
+
+ /**
+ * Returns a Method Object encapsulating the protected findWord Method
+ * inherited from DefaultTextDoubleClickStrategy.
+ *
+ * The method object is set to be accessible.
+ *
+ * @param strategyClass
+ * may not be null
+ * @return
+ */
+ private Method findWordMethod(Class> strategyClass) {
+ return methodByName("findWord", strategyClass); //$NON-NLS-1$
+ }
+
+ /**
+ * Returns a Method Object encapsulating the protected
+ * findExtendedDoubleClickSelection Method inherited from
+ * DefaultTextDoubleClickStrategy.
+ *
+ * The method object is set to be accessible.
+ *
+ * @param strategyClass
+ * may not be null
+ * @return
+ */
+ private Method findExtendedDoubleClickSelectionMethod(
+ Class> strategyClass) {
+ return methodByName("findExtendedDoubleClickSelection", //$NON-NLS-1$
+ strategyClass);
+ }
+
+ private Method methodByName(String name, Class> strategyClass) {
+ Method method;
+ try {
+ method = strategyClass.getDeclaredMethod(name, IDocument.class,
+ int.class);
+ } catch (NoSuchMethodException | SecurityException e) {
+ Class> superClass = strategyClass.getSuperclass();
+ if (superClass != null)
+ return methodByName(name, strategyClass.getSuperclass());
+ return null;
+ }
+ method.setAccessible(true);
+ return method;
+ }
+
+ private IRegion invokeMethodOn(Method method,
+ ITextDoubleClickStrategy doubleClickStrategy,
+ IXtextDocument htmlDocument, int htmlLabelClickOffset) {
+ IRegion htmlRegion = null;
+ try {
+ htmlRegion = (IRegion) method.invoke(doubleClickStrategy,
+ htmlDocument, htmlLabelClickOffset);
+ } catch (IllegalAccessException | IllegalArgumentException
+ | InvocationTargetException | ClassCastException e) {
+ e.printStackTrace();
+ return null;
+ }
+ return htmlRegion;
+ }
+
+}
diff --git a/org.eclipse.gef.dot.ui/src/org/eclipse/gef/dot/internal/ui/language/doubleclicking/DotHtmlLabelDoubleClickStrategyProvider.java b/org.eclipse.gef.dot.ui/src/org/eclipse/gef/dot/internal/ui/language/doubleclicking/DotHtmlLabelDoubleClickStrategyProvider.java
new file mode 100644
index 0000000000..40066c6ed0
--- /dev/null
+++ b/org.eclipse.gef.dot.ui/src/org/eclipse/gef/dot/internal/ui/language/doubleclicking/DotHtmlLabelDoubleClickStrategyProvider.java
@@ -0,0 +1,34 @@
+/*******************************************************************************
+ * Copyright (c) 2018 itemis AG and others.
+ *
+ * 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:
+ * Zoey Gerrit Prigge (itemis AG) - initial API and implementation (bug #532244)
+ *******************************************************************************/
+package org.eclipse.gef.dot.internal.ui.language.doubleclicking;
+
+import org.eclipse.gef.dot.internal.ui.language.editor.DotHtmlLabelTerminalsTokenTypeToPartitionMapper;
+import org.eclipse.jface.text.ITextDoubleClickStrategy;
+import org.eclipse.jface.text.source.ISourceViewer;
+import org.eclipse.xtext.ui.editor.doubleClicking.AbstractWordAwareDoubleClickStrategy;
+import org.eclipse.xtext.ui.editor.doubleClicking.DoubleClickStrategyProvider;
+
+public class DotHtmlLabelDoubleClickStrategyProvider
+ extends DoubleClickStrategyProvider {
+
+ @Override
+ public ITextDoubleClickStrategy getStrategy(ISourceViewer sourceViewer,
+ String contentType, String documentPartitioning) {
+ if (DotHtmlLabelTerminalsTokenTypeToPartitionMapper.TEXT_PARTITION
+ .equals(contentType)) {
+ return new AbstractWordAwareDoubleClickStrategy();
+ }
+ return super.getStrategy(sourceViewer, contentType,
+ documentPartitioning);
+ }
+
+}
diff --git a/org.eclipse.gef.dot.ui/src/org/eclipse/gef/dot/internal/ui/language/editor/DotHtmlLabelTerminalsTokenTypeToPartitionMapper.java b/org.eclipse.gef.dot.ui/src/org/eclipse/gef/dot/internal/ui/language/editor/DotHtmlLabelTerminalsTokenTypeToPartitionMapper.java
index e4ba09b79d..194d39ac6d 100644
--- a/org.eclipse.gef.dot.ui/src/org/eclipse/gef/dot/internal/ui/language/editor/DotHtmlLabelTerminalsTokenTypeToPartitionMapper.java
+++ b/org.eclipse.gef.dot.ui/src/org/eclipse/gef/dot/internal/ui/language/editor/DotHtmlLabelTerminalsTokenTypeToPartitionMapper.java
@@ -7,15 +7,22 @@
* http://www.eclipse.org/legal/epl-v10.html
*
* Contributors:
- * Tamas Miklossy (itemis AG) - initial API and implementation
+ * Tamas Miklossy (itemis AG) - initial API and implementation
+ * Zoey Gerrit Prigge (itemis AG) - add TEXT_PARTITION type (bug #532244)
*******************************************************************************/
package org.eclipse.gef.dot.internal.ui.language.editor;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+
import org.eclipse.xtext.ui.editor.model.TerminalsTokenTypeToPartitionMapper;
public class DotHtmlLabelTerminalsTokenTypeToPartitionMapper
extends TerminalsTokenTypeToPartitionMapper {
+ public static final String TEXT_PARTITION = "__html_text"; //$NON-NLS-1$
+
@Override
protected String calculateId(String tokenName, int tokenType) {
switch (tokenName) {
@@ -31,8 +38,23 @@ protected String calculateId(String tokenName, int tokenType) {
* otherwise, the double click text selection does not work properly
*/
return STRING_LITERAL_PARTITION;
+ case "RULE_TEXT": //$NON-NLS-1$
+ /**
+ * assign the TEXT_PARTITION to the TEXT rule, to assign double
+ * click strategy manually as double click text selection does not
+ * work properly otherwise.
+ */
+ return TEXT_PARTITION;
default:
return super.calculateId(tokenName, tokenType);
}
}
+
+ @Override
+ public String[] getSupportedPartitionTypes() {
+ List supportedTypes = new ArrayList<>(
+ Arrays.asList(super.getSupportedPartitionTypes()));
+ supportedTypes.add(TEXT_PARTITION);
+ return supportedTypes.toArray(new String[supportedTypes.size()]);
+ }
}
diff --git a/org.eclipse.gef.dot.ui/src/org/eclipse/gef/dot/internal/ui/language/editor/DotTerminalsTokenTypeToPartitionMapper.java b/org.eclipse.gef.dot.ui/src/org/eclipse/gef/dot/internal/ui/language/editor/DotTerminalsTokenTypeToPartitionMapper.java
index 31e7004f32..978a8a8b58 100644
--- a/org.eclipse.gef.dot.ui/src/org/eclipse/gef/dot/internal/ui/language/editor/DotTerminalsTokenTypeToPartitionMapper.java
+++ b/org.eclipse.gef.dot.ui/src/org/eclipse/gef/dot/internal/ui/language/editor/DotTerminalsTokenTypeToPartitionMapper.java
@@ -7,16 +7,23 @@
* http://www.eclipse.org/legal/epl-v10.html
*
* Contributors:
- * Tamas Miklossy (itemis AG) - initial API and implementation (bug #532244)
+ * Tamas Miklossy (itemis AG) - initial API and implementation (bug #532244)
+ * Zoey Gerrit Prigge (itemis AG) - added HTML_STRING_PARTITION type (bug #532244)
*******************************************************************************/
package org.eclipse.gef.dot.internal.ui.language.editor;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+
import org.eclipse.jface.text.IDocument;
import org.eclipse.xtext.ui.editor.model.TerminalsTokenTypeToPartitionMapper;
public class DotTerminalsTokenTypeToPartitionMapper
extends TerminalsTokenTypeToPartitionMapper {
+ public static final String HTML_STRING_PARTITION = "__html_string"; //$NON-NLS-1$
+
@Override
protected String calculateId(String tokenName, int tokenType) {
/**
@@ -41,8 +48,23 @@ protected String calculateId(String tokenName, int tokenType) {
return IDocument.DEFAULT_CONTENT_TYPE;
case "RULE_QUOTED_STRING": //$NON-NLS-1$
return STRING_LITERAL_PARTITION;
+ /**
+ * Html strings ('RULE_HTML_STRING') in dot use a specific syntax, hence
+ * for double clicking support, we need to implement a custom double
+ * click strategy using the HTML_STRING_PARTITION.
+ */
+ case "RULE_HTML_STRING": //$NON-NLS-1$
+ return HTML_STRING_PARTITION;
default:
return super.calculateId(tokenName, tokenType);
}
}
+
+ @Override
+ public String[] getSupportedPartitionTypes() {
+ List supportedTypes = new ArrayList<>(
+ Arrays.asList(super.getSupportedPartitionTypes()));
+ supportedTypes.add(HTML_STRING_PARTITION);
+ return supportedTypes.toArray(new String[supportedTypes.size()]);
+ }
}