From 4c3c201cb5ca57be2a6dfd66875c79df59a0c62c Mon Sep 17 00:00:00 2001 From: Alain Magloire Date: Fri, 29 Aug 2003 15:04:57 +0000 Subject: [PATCH] First draft of a Make Editor. --- build/org.eclipse.cdt.make.ui/.project | 2 + .../icons/ctool16/makefile.gif | Bin 0 -> 571 bytes build/org.eclipse.cdt.make.ui/plugin.xml | 12 + .../internal/ui/editor/IMakeColorManager.java | 35 +++ .../internal/ui/editor/MakeCodeScanner.java | 177 +++++++++++++ .../internal/ui/editor/MakeColorManager.java | 47 ++++ .../ui/editor/MakeDocumentProvider.java | 55 ++++ .../editor/MakeEditorActionContributor.java | 61 +++++ .../ui/editor/MakeEditorConfiguration.java | 109 ++++++++ .../MakeEditorTogglePresentationAction.java | 70 ++++++ .../internal/ui/editor/MakeMacroScanner.java | 114 +++++++++ .../ui/editor/MakePartitionScanner.java | 234 ++++++++++++++++++ .../ui/editor/MakeSimpleMacroRule.java | 54 ++++ .../internal/ui/editor/MakeTextEditor.java | 89 +++++++ .../internal/ui/editor/MakeWordDetector.java | 34 +++ 15 files changed, 1093 insertions(+) create mode 100644 build/org.eclipse.cdt.make.ui/icons/ctool16/makefile.gif create mode 100644 build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/IMakeColorManager.java create mode 100644 build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeCodeScanner.java create mode 100644 build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeColorManager.java create mode 100644 build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeDocumentProvider.java create mode 100644 build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeEditorActionContributor.java create mode 100644 build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeEditorConfiguration.java create mode 100644 build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeEditorTogglePresentationAction.java create mode 100644 build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeMacroScanner.java create mode 100644 build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakePartitionScanner.java create mode 100644 build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeSimpleMacroRule.java create mode 100644 build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeTextEditor.java create mode 100644 build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeWordDetector.java diff --git a/build/org.eclipse.cdt.make.ui/.project b/build/org.eclipse.cdt.make.ui/.project index 13502de135f..36dd5636da8 100644 --- a/build/org.eclipse.cdt.make.ui/.project +++ b/build/org.eclipse.cdt.make.ui/.project @@ -10,7 +10,9 @@ org.eclipse.cdt.core.win32 org.eclipse.cdt.make.core org.eclipse.cdt.ui + org.eclipse.core.boot org.eclipse.core.resources + org.eclipse.core.runtime org.eclipse.ui diff --git a/build/org.eclipse.cdt.make.ui/icons/ctool16/makefile.gif b/build/org.eclipse.cdt.make.ui/icons/ctool16/makefile.gif new file mode 100644 index 0000000000000000000000000000000000000000..9d5a508bc4931b0d1b59c7a7ef53bd9350451e8a GIT binary patch literal 571 zcmZ?wbhEHb6krfwc*ejWt{f$!l`W@VA*)*~qn$6MnIWrNB(GmSVeX*|kA6vIol~!T zpqzVBt>CO?$wmFThdLFPJvweg&Ul_Y_gT`chqI3SoU!-K)a?&1Jo#hScH`!&zy98K z{|`!?nI*cUMzAK1cS)1_{|CKEVP-GScRJbV{Qq!l(~7R%0_{z6k`AuS?(3}aG-8Nx zmH+?$|BoL(zI^%e>C>kVA3i*K^l0nWt?SpXU$SJ$!i5W`PMzA@+gnppQ(Rn}mX?;9 znwpZ5lAN4uYirBEzyQ<>B!?(a{K>+|z~IQB19CqoP8ir{G&nXjH(6QPwKS=Bt2fyh z7#Z8QsB0=}C@a|*Sg^BOPf=7;mDblaFlQ8DogyPIqoQSLV8$r6x>;RTK~9#1&A`;w zmP2?=llDm+ad9R?Jrib8{^Ly!lHy`wObiTSqM||$&DW(K+`2Ey$@lo0fS|;KPn?20 qZ?AEE_$(4AuZWX`Va) literal 0 HcmV?d00001 diff --git a/build/org.eclipse.cdt.make.ui/plugin.xml b/build/org.eclipse.cdt.make.ui/plugin.xml index 1c0ac1a4fe1..d3980d58d98 100644 --- a/build/org.eclipse.cdt.make.ui/plugin.xml +++ b/build/org.eclipse.cdt.make.ui/plugin.xml @@ -249,5 +249,17 @@ + + + + diff --git a/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/IMakeColorManager.java b/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/IMakeColorManager.java new file mode 100644 index 00000000000..17a296fa998 --- /dev/null +++ b/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/IMakeColorManager.java @@ -0,0 +1,35 @@ +/********************************************************************** + * Copyright (c) 2002,2003 QNX Software Systems and others. + * All rights reserved. This program and the accompanying materials + * are made available under the terms of the Common Public License v1.0 + * which accompanies this distribution, and is available at + * http://www.eclipse.org/legal/cpl-v10.html + * + * Contributors: + * QNX Software Systems - Initial API and implementation +***********************************************************************/ +package org.eclipse.cdt.make.internal.ui.editor; + +import org.eclipse.swt.SWT; +import org.eclipse.swt.graphics.Color; +import org.eclipse.swt.graphics.RGB; +import org.eclipse.swt.widgets.Display; + +public interface IMakeColorManager { + public static final RGB MAKE_COMMENT = new RGB(128, 0, 0); + public static final RGB MAKE_KEYWORD = new RGB(128, 128, 0); + public static final RGB MAKE_FUNCTION = new RGB(128, 0, 128); + public static final RGB MAKE_MACRO_VAR = new RGB(0, 0, 128); + public static final RGB MAKE_META_DATA = new RGB(0, 128, 0); + public static final RGB MAKE_DEFAULT = new RGB(0, 0, 0); + + public static final RGB MAKE_FORM_FOREGROUND = Display.getCurrent().getSystemColor(SWT.COLOR_LIST_FOREGROUND).getRGB(); + public static final RGB MAKE_FORM_BACKGROUND = new RGB(0xff, 0xff, 0xff); //RGB(0xff, 0xfe, 0xf9); + public static final RGB MAKE_DEFAULT_PAGE_HEADER = new RGB(0x48, 0x70, 0x98); + public static final RGB MAKE_HYPERLINK_TEXT = new RGB(0, 0, 128); + public static final RGB MAKE_CONTROL_BORDER = new RGB(195, 191, 179); + + void dispose(); + Color getColor(RGB rgb); + +} diff --git a/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeCodeScanner.java b/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeCodeScanner.java new file mode 100644 index 00000000000..4315b3a4322 --- /dev/null +++ b/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeCodeScanner.java @@ -0,0 +1,177 @@ +/********************************************************************** + * Copyright (c) 2002,2003 QNX Software Systems and others. + * All rights reserved. This program and the accompanying materials + * are made available under the terms of the Common Public License v1.0 + * which accompanies this distribution, and is available at + * http://www.eclipse.org/legal/cpl-v10.html + * + * Contributors: + * QNX Software Systems - Initial API and implementation +***********************************************************************/ +package org.eclipse.cdt.make.internal.ui.editor; + +import java.util.ArrayList; +import java.util.List; + +import org.eclipse.jface.text.TextAttribute; +import org.eclipse.jface.text.rules.EndOfLineRule; +import org.eclipse.jface.text.rules.ICharacterScanner; +import org.eclipse.jface.text.rules.IRule; +import org.eclipse.jface.text.rules.IToken; +import org.eclipse.jface.text.rules.IWhitespaceDetector; +import org.eclipse.jface.text.rules.PatternRule; +import org.eclipse.jface.text.rules.RuleBasedScanner; +import org.eclipse.jface.text.rules.Token; +import org.eclipse.jface.text.rules.WhitespaceRule; +import org.eclipse.jface.text.rules.WordRule; + +public class MakeCodeScanner extends RuleBasedScanner { + + private final static String[] keywords = { "define", "endef", "ifdef", "ifndef", //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$ + "ifeq", "ifneq", "else", "endif", "include", //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$ //$NON-NLS-5$ + "-include", "sinclude", "override", "endef", //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$ + "export", "unexport", "vpath" }; //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ + private final static String[] functions = { "subst", "patsubst", "strip", //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ + "findstring", "filter", "sort", "dir", "notdir", //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$ //$NON-NLS-5$ + "suffix", "basename", "addsuffix", "addprefix", //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$ + "join", "word", "words", "wordlist", //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$ + "firstword", "wildcard", "error", "warning", //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$ + "shell", "origin", "foreach", "call" }; //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$ + /** + * Constructor for MakeCodeScanner + */ + public MakeCodeScanner(IMakeColorManager provider) { + super(); + + IToken keyword = new Token(new TextAttribute(provider.getColor(IMakeColorManager.MAKE_KEYWORD))); + IToken function = new Token(new TextAttribute(provider.getColor(IMakeColorManager.MAKE_FUNCTION))); + IToken comment = new Token(new TextAttribute(provider.getColor(IMakeColorManager.MAKE_COMMENT))); + IToken macro = new Token(new TextAttribute(provider.getColor(IMakeColorManager.MAKE_MACRO_VAR))); + IToken other = new Token(new TextAttribute(provider.getColor(IMakeColorManager.MAKE_DEFAULT))); + + List rules = new ArrayList(); + + // Add rule for single line comments. + rules.add(new EndOfLineRule("#", comment)); //$NON-NLS-1$ + + // Add generic whitespace rule. + rules.add(new WhitespaceRule(new IWhitespaceDetector() { + public boolean isWhitespace(char character) { + return Character.isWhitespace(character); + } + })); + + // Add word rule for keywords, types, and constants. + WordRule wordRule = new WordRule(new MakeWordDetector(), Token.UNDEFINED); + for (int i = 0; i < keywords.length; i++) + wordRule.addWord(keywords[i], keyword); + for (int i = 0; i < functions.length; i++) + wordRule.addWord(functions[i], function); + + rules.add(wordRule); + + rules.add(new PatternRule("$(", ")", macro, '\\', true)); //$NON-NLS-1$ //$NON-NLS-2$ + + rules.add(new MacroRule(macro, other)); + + IRule[] result = new IRule[rules.size()]; + + rules.toArray(result); + + setRules(result); + + } + + private class MacroRule implements IRule { + private static final int INIT_STATE = 0; + private static final int VAR_STATE = 1; + private static final int END_VAR_STATE = 2; + private static final int EQUAL_STATE = 3; + private static final int FINISH_STATE = 4; + private static final int ERROR_STATE = 5; + + private IToken token; + private StringBuffer buffer = new StringBuffer(); + protected IToken defaultToken; + public MacroRule(IToken token, IToken defaultToken) { + this.token = token; + this.defaultToken = defaultToken; + } + public IToken evaluate(ICharacterScanner scanner) { + int state = INIT_STATE; + buffer.setLength(0); + boolean bTwoCharsAssign = false; + + for (int c = scanner.read(); c != ICharacterScanner.EOF; c = scanner.read()) { + switch (state) { + case INIT_STATE : + if (c != '\n' && Character.isWhitespace((char) c)) + break; + if (isValidCharacter(c)) + state = VAR_STATE; + else + state = ERROR_STATE; + break; + case VAR_STATE : + if (isValidCharacter(c)) + break; + case END_VAR_STATE : + if (c != '\n' && Character.isWhitespace((char) c)) + state = END_VAR_STATE; + else if (c == ':' || c == '+') { + bTwoCharsAssign = true; + state = EQUAL_STATE; + } else if (c == '=') + state = FINISH_STATE; + else { + if (state == END_VAR_STATE) + scanner.unread(); // Return back to the space + state = ERROR_STATE; + } + break; + case EQUAL_STATE : + if (c == '=') + state = FINISH_STATE; + else + state = ERROR_STATE; + break; + case FINISH_STATE : + break; + default : + break; + } + if (state >= FINISH_STATE) + break; + buffer.append((char) c); + } + + scanner.unread(); + + if (state == FINISH_STATE) { + if (bTwoCharsAssign) + scanner.unread(); + return token; + } + + if (defaultToken.isUndefined()) + unreadBuffer(scanner); + + return Token.UNDEFINED; + } + /** + * Returns the characters in the buffer to the scanner. + * + * @param scanner the scanner to be used + */ + protected void unreadBuffer(ICharacterScanner scanner) { + for (int i = buffer.length() - 1; i >= 0; i--) + scanner.unread(); + } + + protected boolean isValidCharacter(int c) { + char c0 = (char) c; + return Character.isLetterOrDigit(c0) || (c0 == '_'); + } + } + +} diff --git a/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeColorManager.java b/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeColorManager.java new file mode 100644 index 00000000000..601d1aff490 --- /dev/null +++ b/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeColorManager.java @@ -0,0 +1,47 @@ +/********************************************************************** + * Copyright (c) 2002,2003 QNX Software Systems and others. + * All rights reserved. This program and the accompanying materials + * are made available under the terms of the Common Public License v1.0 + * which accompanies this distribution, and is available at + * http://www.eclipse.org/legal/cpl-v10.html + * + * Contributors: + * QNX Software Systems - Initial API and implementation +***********************************************************************/ +package org.eclipse.cdt.make.internal.ui.editor; + +import java.util.HashMap; +import java.util.Iterator; +import java.util.Map; + +import org.eclipse.swt.graphics.Color; +import org.eclipse.swt.graphics.RGB; +import org.eclipse.swt.widgets.Display; + +public class MakeColorManager implements IMakeColorManager { + + protected Map fColorTable = new HashMap(10); + + /** + * @see IMakeColorManager#dispose() + */ + public void dispose() { + Iterator e = fColorTable.values().iterator(); + while (e.hasNext()) + ((Color) e.next()).dispose(); + } + + /** + * @see IMakeColorManager#getColor(RGB) + */ + public Color getColor(RGB rgb) { + Color color = (Color) fColorTable.get(rgb); + if (color == null) { + color = new Color(Display.getCurrent(), rgb); + fColorTable.put(rgb, color); + } + return color; + + } + +} diff --git a/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeDocumentProvider.java b/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeDocumentProvider.java new file mode 100644 index 00000000000..d4fa03e256d --- /dev/null +++ b/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeDocumentProvider.java @@ -0,0 +1,55 @@ +/********************************************************************** + * Copyright (c) 2002,2003 QNX Software Systems and others. + * All rights reserved. This program and the accompanying materials + * are made available under the terms of the Common Public License v1.0 + * which accompanies this distribution, and is available at + * http://www.eclipse.org/legal/cpl-v10.html + * + * Contributors: + * QNX Software Systems - Initial API and implementation +***********************************************************************/ +package org.eclipse.cdt.make.internal.ui.editor; + +import org.eclipse.core.runtime.CoreException; +import org.eclipse.jface.text.IDocument; +import org.eclipse.jface.text.IDocumentPartitioner; +import org.eclipse.jface.text.rules.DefaultPartitioner; +import org.eclipse.ui.editors.text.FileDocumentProvider; + +/** + */ +public class MakeDocumentProvider extends FileDocumentProvider { + + private static MakePartitionScanner scanner = null; + + /** + * Constructor for MakeDocumentProvider. + */ + public MakeDocumentProvider() { + super(); + } + + /** + * @see org.eclipse.ui.texteditor.AbstractDocumentProvider#createDocument(Object) + */ + protected IDocument createDocument(Object element) throws CoreException { + IDocument document = super.createDocument(element); + if (document != null) { + IDocumentPartitioner partitioner = createPartitioner(); + document.setDocumentPartitioner(partitioner); + partitioner.connect(document); + } + return document; + } + + private IDocumentPartitioner createPartitioner() { + return new DefaultPartitioner(getPartitionScanner(), MakePartitionScanner.TYPES); + } + + private MakePartitionScanner getPartitionScanner() { + if (scanner == null) + scanner = new MakePartitionScanner(); + return scanner; + } + +} diff --git a/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeEditorActionContributor.java b/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeEditorActionContributor.java new file mode 100644 index 00000000000..1a3dd707a2c --- /dev/null +++ b/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeEditorActionContributor.java @@ -0,0 +1,61 @@ +/********************************************************************** + * Copyright (c) 2002,2003 QNX Software Systems and others. + * All rights reserved. This program and the accompanying materials + * are made available under the terms of the Common Public License v1.0 + * which accompanies this distribution, and is available at + * http://www.eclipse.org/legal/cpl-v10.html + * + * Contributors: + * QNX Software Systems - Initial API and implementation +***********************************************************************/ +package org.eclipse.cdt.make.internal.ui.editor; + +import org.eclipse.jface.action.IToolBarManager; +import org.eclipse.ui.IActionBars; +import org.eclipse.ui.IEditorPart; +import org.eclipse.ui.texteditor.BasicTextEditorActionContributor; +import org.eclipse.ui.texteditor.ITextEditor; + +/** + */ +public class MakeEditorActionContributor extends BasicTextEditorActionContributor { + private MakeEditorTogglePresentationAction togglePresentationAction; + private static final String TOGGLE_PRESENTATION = "make_toggle_presentation"; //$NON-NLS-1$ + + /** + * Constructor for MakeEditorActionContributor. + */ + public MakeEditorActionContributor() { + super(); + togglePresentationAction = new MakeEditorTogglePresentationAction(); + } + + /** + * @see org.eclipse.ui.IEditorActionBarContributor#setActiveEditor(IEditorPart) + */ + public void setActiveEditor(IEditorPart targetEditor) { + super.setActiveEditor(targetEditor); + ITextEditor textEditor = null; + if (targetEditor instanceof ITextEditor) + textEditor = (ITextEditor) targetEditor; + + togglePresentationAction.setEditor(textEditor); + } + + /** + * @see org.eclipse.ui.part.EditorActionBarContributor#init(IActionBars) + */ + public void init(IActionBars bars) { + super.init(bars); + bars.setGlobalActionHandler(TOGGLE_PRESENTATION, togglePresentationAction); + } + + /** + * @see org.eclipse.ui.part.EditorActionBarContributor#contributeToToolBar(IToolBarManager) + */ + public void contributeToToolBar(IToolBarManager toolBarManager) { + super.contributeToToolBar(toolBarManager); + toolBarManager.add(togglePresentationAction); + } + +} diff --git a/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeEditorConfiguration.java b/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeEditorConfiguration.java new file mode 100644 index 00000000000..44cf9a3b4b9 --- /dev/null +++ b/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeEditorConfiguration.java @@ -0,0 +1,109 @@ +/********************************************************************** + * Copyright (c) 2002,2003 QNX Software Systems and others. + * All rights reserved. This program and the accompanying materials + * are made available under the terms of the Common Public License v1.0 + * which accompanies this distribution, and is available at + * http://www.eclipse.org/legal/cpl-v10.html + * + * Contributors: + * QNX Software Systems - Initial API and implementation +***********************************************************************/ +package org.eclipse.cdt.make.internal.ui.editor; + +import org.eclipse.jface.text.IDocument; +import org.eclipse.jface.text.TextAttribute; +import org.eclipse.jface.text.presentation.IPresentationReconciler; +import org.eclipse.jface.text.presentation.PresentationReconciler; +import org.eclipse.jface.text.rules.BufferedRuleBasedScanner; +import org.eclipse.jface.text.rules.DefaultDamagerRepairer; +import org.eclipse.jface.text.rules.Token; +import org.eclipse.jface.text.source.ISourceViewer; +import org.eclipse.jface.text.source.SourceViewerConfiguration; + +public class MakeEditorConfiguration extends SourceViewerConfiguration { + + private IMakeColorManager colorManager = null; + private MakeCodeScanner codeScanner = null; + + /** + * Single token scanner. + */ + static class SingleTokenScanner extends BufferedRuleBasedScanner { + public SingleTokenScanner(TextAttribute attribute) { + setDefaultReturnToken(new Token(attribute)); + } + }; + + /** + * Constructor for MakeConfiguration + */ + public MakeEditorConfiguration(IMakeColorManager colorManager) { + super(); + this.colorManager = colorManager; + } + + /** + * @see SourceViewerConfiguration#getConfiguredContentTypes(ISourceViewer) + */ + public String[] getConfiguredContentTypes(ISourceViewer v) { + return new String[] { + IDocument.DEFAULT_CONTENT_TYPE, + MakeTextEditor.MAKE_COMMENT, + MakeTextEditor.MAKE_KEYWORD, + MakeTextEditor.MAKE_MACRO_VAR, + MakeTextEditor.MAKE_META_DATA }; + + } + + protected IMakeColorManager getColorManager() { + if (null == colorManager) + colorManager = new MakeColorManager(); + return colorManager; + } + + protected MakeCodeScanner getCodeScanner() { + if (null == codeScanner) + codeScanner = new MakeCodeScanner(getColorManager()); + return codeScanner; + + } + + public IPresentationReconciler getPresentationReconciler(ISourceViewer v) { + + PresentationReconciler reconciler = new PresentationReconciler(); + + DefaultDamagerRepairer dr = new DefaultDamagerRepairer(getCodeScanner()); + reconciler.setDamager(dr, IDocument.DEFAULT_CONTENT_TYPE); + reconciler.setRepairer(dr, IDocument.DEFAULT_CONTENT_TYPE); + + dr = new DefaultDamagerRepairer(getCodeScanner()); + reconciler.setDamager(dr, MakePartitionScanner.MAKE_INTERNAL); + reconciler.setRepairer(dr, MakePartitionScanner.MAKE_INTERNAL); + + dr = new DefaultDamagerRepairer(getCodeScanner()); + reconciler.setDamager(dr, MakePartitionScanner.MAKE_COMMENT); + reconciler.setRepairer(dr, MakePartitionScanner.MAKE_COMMENT); + + dr = new DefaultDamagerRepairer(getCodeScanner()); + reconciler.setDamager(dr, MakePartitionScanner.MAKE_MACRO_ASSIGNEMENT); + reconciler.setRepairer(dr, MakePartitionScanner.MAKE_MACRO_ASSIGNEMENT); + + dr = new DefaultDamagerRepairer(getCodeScanner()); + reconciler.setDamager(dr, MakePartitionScanner.MAKE_INCLUDE_BLOCK); + reconciler.setRepairer(dr, MakePartitionScanner.MAKE_INCLUDE_BLOCK); + + dr = new DefaultDamagerRepairer(getCodeScanner()); + reconciler.setDamager(dr, MakePartitionScanner.MAKE_IF_BLOCK); + reconciler.setRepairer(dr, MakePartitionScanner.MAKE_IF_BLOCK); + + dr = new DefaultDamagerRepairer(getCodeScanner()); + reconciler.setDamager(dr, MakePartitionScanner.MAKE_DEF_BLOCK); + reconciler.setRepairer(dr, MakePartitionScanner.MAKE_DEF_BLOCK); + + dr = new DefaultDamagerRepairer(getCodeScanner()); + reconciler.setDamager(dr, MakePartitionScanner.MAKE_OTHER); + reconciler.setRepairer(dr, MakePartitionScanner.MAKE_OTHER); + return reconciler; + } + +} diff --git a/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeEditorTogglePresentationAction.java b/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeEditorTogglePresentationAction.java new file mode 100644 index 00000000000..6e8a87e3785 --- /dev/null +++ b/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeEditorTogglePresentationAction.java @@ -0,0 +1,70 @@ +/********************************************************************** + * Copyright (c) 2002,2003 QNX Software Systems and others. + * All rights reserved. This program and the accompanying materials + * are made available under the terms of the Common Public License v1.0 + * which accompanies this distribution, and is available at + * http://www.eclipse.org/legal/cpl-v10.html + * + * Contributors: + * QNX Software Systems - Initial API and implementation +***********************************************************************/ +package org.eclipse.cdt.make.internal.ui.editor; + +import org.eclipse.cdt.make.internal.ui.MakeUIPlugin; +import org.eclipse.ui.texteditor.ITextEditor; +import org.eclipse.ui.texteditor.TextEditorAction; + +/** + */ +public class MakeEditorTogglePresentationAction extends TextEditorAction { + + private final static String ACTION_ID = "org.eclipse.cdt.make.ui.MakeEditorTogglePresentationAction"; //$NON-NLS-1$ + /** + * Constructor for MakeEditorTogglePresentationAction. + * @param bundle + * @param prefix + * @param editor + */ + public MakeEditorTogglePresentationAction() { + super(MakeUIPlugin.getDefault().getResourceBundle(), "MakeEditorTogglePresentationAction.", null); //$NON-NLS-1$ + + setToolTipText("MakeEditorTogglePresentationAction.tooltip"); //$NON-NLS-1$ + setActionDefinitionId(ACTION_ID); + update(); + + } + + /** + * @see org.eclipse.jface.action.IAction#run() + */ + public void run() { + super.run(); + ITextEditor editor = getTextEditor(); + if (editor == null) + return; + if (!(editor instanceof MakeTextEditor)) + return; + ((MakeTextEditor) editor).setPresentationState(!((MakeTextEditor) editor).getPresentationState()); + // update(); + } + + /** + * @see org.eclipse.ui.texteditor.IUpdate#update() + */ + public void update() { + setChecked(isChecked()); + setEnabled(isEnabled()); + } + + /** + * @see org.eclipse.ui.texteditor.TextEditorAction#setEditor(ITextEditor) + */ + public void setEditor(ITextEditor editor) { + super.setEditor(editor); + if (editor instanceof MakeTextEditor) { + ((MakeTextEditor) editor).setPresentationState(isChecked()); + } + update(); + } + +} diff --git a/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeMacroScanner.java b/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeMacroScanner.java new file mode 100644 index 00000000000..7255c2310ab --- /dev/null +++ b/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeMacroScanner.java @@ -0,0 +1,114 @@ +/********************************************************************** + * Copyright (c) 2002,2003 QNX Software Systems and others. + * All rights reserved. This program and the accompanying materials + * are made available under the terms of the Common Public License v1.0 + * which accompanies this distribution, and is available at + * http://www.eclipse.org/legal/cpl-v10.html + * + * Contributors: + * QNX Software Systems - Initial API and implementation +***********************************************************************/ +package org.eclipse.cdt.make.internal.ui.editor; + +import java.util.ArrayList; +import java.util.List; + +import org.eclipse.jface.text.IDocument; +import org.eclipse.jface.text.rules.IRule; +import org.eclipse.jface.text.rules.IToken; +import org.eclipse.jface.text.rules.IWhitespaceDetector; +import org.eclipse.jface.text.rules.IWordDetector; +import org.eclipse.jface.text.rules.PatternRule; +import org.eclipse.jface.text.rules.RuleBasedScanner; +import org.eclipse.jface.text.rules.Token; +import org.eclipse.jface.text.rules.WhitespaceRule; +import org.eclipse.jface.text.rules.WordRule; + +public class MakeMacroScanner extends RuleBasedScanner { + private String buffer; + private final static String[] DELIMITERS = { "\r", "\n", "\r\n" }; //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ + + public final static String tokenText = "text"; //$NON-NLS-1$ + public final static String tokenMacro = "macro"; //$NON-NLS-1$ + public final static String tokenOther = "other"; //$NON-NLS-1$ + + /** + * Constructor for MakeMacroScanner + */ + public MakeMacroScanner(String buffer) { + super(); + this.buffer = buffer; + fOffset = 0; + + IToken tText = new Token(tokenText); + IToken tMacro = new Token(tokenMacro); + IToken tOther = new Token(tokenOther); + + List rules = new ArrayList(); + + rules.add(new PatternRule("\"", "\"", tText, '\\', true)); //$NON-NLS-1$ //$NON-NLS-2$ + rules.add(new PatternRule("\'", "\'", tText, '\\', true)); //$NON-NLS-1$ //$NON-NLS-2$ + + rules.add(new MakeSimpleMacroRule(tMacro)); + + // Add generic whitespace rule. + rules.add(new WhitespaceRule(new IWhitespaceDetector() { + public boolean isWhitespace(char character) { + return Character.isWhitespace(character); + } + })); + + WordRule wRule = new WordRule(new IWordDetector() { + public boolean isWordPart(char c) { + return isWordStart(c); + } + public boolean isWordStart(char c) { + return !(((short) c == EOF) || Character.isSpaceChar(c)); + } + }, tOther); + + rules.add(wRule); + + IRule[] result = new IRule[rules.size()]; + + rules.toArray(result); + + setRules(result); + + setRange(null, 0, buffer.length()); + } + + /** + * @see RuleBasedScanner#getColumn() + */ + public int getColumn() { + return fOffset; + } + + /** + * @see RuleBasedScanner#read() + */ + public int read() { + int c; + if (fOffset == buffer.length()) + c = EOF; + else + c = buffer.charAt(fOffset); + ++fOffset; + return c; + } + + /** + * @see RuleBasedScanner#setRange(IDocument, int, int) + */ + public void setRange(IDocument document, int offset, int length) { + fDocument = document; + fOffset = offset; + fRangeEnd = offset + length; + + fDelimiters = new char[DELIMITERS.length][]; + for (int i = 0; i < DELIMITERS.length; i++) + fDelimiters[i] = DELIMITERS[i].toCharArray(); + } + +} diff --git a/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakePartitionScanner.java b/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakePartitionScanner.java new file mode 100644 index 00000000000..306007a64cf --- /dev/null +++ b/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakePartitionScanner.java @@ -0,0 +1,234 @@ +/********************************************************************** + * Copyright (c) 2002,2003 QNX Software Systems and others. + * All rights reserved. This program and the accompanying materials + * are made available under the terms of the Common Public License v1.0 + * which accompanies this distribution, and is available at + * http://www.eclipse.org/legal/cpl-v10.html + * + * Contributors: + * QNX Software Systems - Initial API and implementation +***********************************************************************/ +package org.eclipse.cdt.make.internal.ui.editor; + +import java.util.ArrayList; +import java.util.List; + +import org.eclipse.jface.text.rules.EndOfLineRule; +import org.eclipse.jface.text.rules.ICharacterScanner; +import org.eclipse.jface.text.rules.IPredicateRule; +import org.eclipse.jface.text.rules.IToken; +import org.eclipse.jface.text.rules.MultiLineRule; +import org.eclipse.jface.text.rules.RuleBasedPartitionScanner; +import org.eclipse.jface.text.rules.Token; + +public class MakePartitionScanner extends RuleBasedPartitionScanner { + // Partition types + public final static String MAKE_INTERNAL = "make_internal"; //$NON-NLS-1$ + public final static String MAKE_COMMENT = "make_comment"; //$NON-NLS-1$ + public final static String MAKE_MACRO_ASSIGNEMENT = "make_macro_assig"; //$NON-NLS-1$ + public final static String MAKE_INCLUDE_BLOCK = "make_include_block"; //$NON-NLS-1$ + public final static String MAKE_IF_BLOCK = "make_if_block"; //$NON-NLS-1$ + public final static String MAKE_DEF_BLOCK = "make_def_block"; //$NON-NLS-1$ + public final static String MAKE_OTHER = "make_other"; //$NON-NLS-1$ + + public final static String[] TYPES = + new String[] { + MAKE_INTERNAL, + MAKE_COMMENT, + MAKE_MACRO_ASSIGNEMENT, + MAKE_INCLUDE_BLOCK, + MAKE_IF_BLOCK, + MAKE_DEF_BLOCK, + MAKE_OTHER, + // All other + }; + + /** The predefined delimiters of this tracker */ + private char[][] fModDelimiters = { { '\r', '\n' }, { + '\r' }, { + '\n' } + }; + + /** + * Constructor for MakePartitionScanner + */ + public MakePartitionScanner() { + super(); + + IToken tInternal = new Token(MAKE_INTERNAL); + IToken tComment = new Token(MAKE_COMMENT); + IToken tMacro = new Token(MAKE_MACRO_ASSIGNEMENT); + IToken tInclude = new Token(MAKE_INCLUDE_BLOCK); + IToken tIf = new Token(MAKE_IF_BLOCK); + IToken tDef = new Token(MAKE_DEF_BLOCK); + IToken tOther = new Token(MAKE_OTHER); + + List rules = new ArrayList(); + + // Add rule for single line comments. + //rules.add(new MultiLineRule("#QNX internal start", "#QNX internal end", tInternal)); //$NON-NLS-1$ //$NON-NLS-2$ + + rules.add(new EndOfLineRule("#", tComment)); //$NON-NLS-1$ + + rules.add(new EndOfLineRule("include", tInclude)); //$NON-NLS-1$ + + // Add rules for multi-line comments and javadoc. + rules.add(new MultiLineRule("ifdef", "endif", tIf)); //$NON-NLS-1$ //$NON-NLS-2$ + rules.add(new MultiLineRule("ifndef", "endif", tIf)); //$NON-NLS-1$ //$NON-NLS-2$ + rules.add(new MultiLineRule("ifeq", "endif", tIf)); //$NON-NLS-1$ //$NON-NLS-2$ + rules.add(new MultiLineRule("ifnneq", "endif", tIf)); //$NON-NLS-1$ //$NON-NLS-2$ + + rules.add(new MultiLineRule("define", "endef", tDef)); //$NON-NLS-1$ //$NON-NLS-2$ + + // Last rule must be supplied with default token! + rules.add(new MacroRule(tMacro, tOther)); //$NON-NLS-1$ + + IPredicateRule[] result = new IPredicateRule[rules.size()]; + rules.toArray(result); + setPredicateRules(result); + + } + + /* + * @see ICharacterScanner#getLegalLineDelimiters + */ + public char[][] getLegalLineDelimiters() { + return fModDelimiters; + } + + private class MacroRule implements IPredicateRule { + private static final int INIT_STATE = 0; + private static final int VAR_STATE = 1; + private static final int END_VAR_STATE = 2; + private static final int EQUAL_STATE = 3; + private static final int FINISH_STATE = 4; + private static final int ERROR_STATE = 5; + + private IToken token; + private StringBuffer buffer = new StringBuffer(); + protected IToken defaultToken; + public MacroRule(IToken token, IToken defaultToken) { + this.token = token; + this.defaultToken = defaultToken; + } + + public IToken getSuccessToken() { + return token; + } + + public IToken evaluate(ICharacterScanner scanner, boolean resume) { + buffer.setLength(0); + int state = INIT_STATE; + + if (resume) + scanToBeginOfLine(scanner); + + for (int c = scanner.read(); c != ICharacterScanner.EOF; c = scanner.read()) { + switch (state) { + case INIT_STATE : + if (c != '\n' && Character.isWhitespace((char) c)) + break; + if (isValidCharacter(c)) + state = VAR_STATE; + else + state = ERROR_STATE; + break; + case VAR_STATE : + if (isValidCharacter(c)) + break; + case END_VAR_STATE : + if (c != '\n' && Character.isWhitespace((char) c)) + state = END_VAR_STATE; + else if (c == ':' || c == '+') + state = EQUAL_STATE; + else if (c == '=') + state = FINISH_STATE; + else { + if (state == END_VAR_STATE) + scanner.unread(); // Return back to the space + state = ERROR_STATE; + } + break; + case EQUAL_STATE : + if (c == '=') + state = FINISH_STATE; + else + state = ERROR_STATE; + break; + case FINISH_STATE : + break; + default : + break; + } + if (state >= FINISH_STATE) + break; + buffer.append((char) c); + } + + scanner.unread(); + + if (state == FINISH_STATE) { + scanToEndOfLine(scanner); + return token; + } + + if (defaultToken.isUndefined()) + unreadBuffer(scanner); + + return Token.UNDEFINED; + + } + + public IToken evaluate(ICharacterScanner scanner) { + return evaluate(scanner, false); + } + + /** + * Returns the characters in the buffer to the scanner. + * + * @param scanner the scanner to be used + */ + protected void unreadBuffer(ICharacterScanner scanner) { + for (int i = buffer.length() - 1; i >= 0; i--) + scanner.unread(); + } + + private void scanToEndOfLine(ICharacterScanner scanner) { + int c; + char[][] delimiters = scanner.getLegalLineDelimiters(); + while ((c = scanner.read()) != ICharacterScanner.EOF) { + // Check for end of line since it can be used to terminate the pattern. + for (int i = 0; i < delimiters.length; i++) { + if (c == delimiters[i][0] && sequenceDetected(scanner, delimiters[i])) + return; + } + } + } + + private void scanToBeginOfLine(ICharacterScanner scanner) { + for (; scanner.getColumn() != 0; scanner.unread()); + } + + private boolean sequenceDetected(ICharacterScanner scanner, char[] sequence) { + for (int i = 1; i < sequence.length; i++) { + int c = scanner.read(); + if (c == ICharacterScanner.EOF) { + return true; + } else if (c != sequence[i]) { + // Non-matching character detected, rewind the scanner back to the start. + for (; i > 0; i--) + scanner.unread(); + return false; + } + } + + return true; + } + protected boolean isValidCharacter(int c) { + char c0 = (char) c; + return Character.isLetterOrDigit(c0) || (c0 == '_'); + } + + } + +} diff --git a/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeSimpleMacroRule.java b/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeSimpleMacroRule.java new file mode 100644 index 00000000000..dc87b2a64bf --- /dev/null +++ b/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeSimpleMacroRule.java @@ -0,0 +1,54 @@ +/********************************************************************** + * Copyright (c) 2002,2003 QNX Software Systems and others. + * All rights reserved. This program and the accompanying materials + * are made available under the terms of the Common Public License v1.0 + * which accompanies this distribution, and is available at + * http://www.eclipse.org/legal/cpl-v10.html + * + * Contributors: + * QNX Software Systems - Initial API and implementation +***********************************************************************/ +package org.eclipse.cdt.make.internal.ui.editor; + +import org.eclipse.jface.text.rules.ICharacterScanner; +import org.eclipse.jface.text.rules.IToken; +import org.eclipse.jface.text.rules.PatternRule; + +public class MakeSimpleMacroRule extends PatternRule { + + private int nOfBrackets; + + public MakeSimpleMacroRule(IToken token) { + super("$(", ")", token, (char) 0, true); //$NON-NLS-1$ //$NON-NLS-2$ + } + + protected IToken doEvaluate(ICharacterScanner scanner) { + nOfBrackets = 1; + return super.doEvaluate(scanner); + } + + protected boolean endSequenceDetected(ICharacterScanner scanner) { + int c; + char[][] delimiters = scanner.getLegalLineDelimiters(); + while ((c = scanner.read()) != ICharacterScanner.EOF) { + if ('(' == (char) c) + ++nOfBrackets; + if (fEndSequence.length > 0 && c == fEndSequence[0]) { + // Check if the specified end sequence has been found. + if (sequenceDetected(scanner, fEndSequence, true)) { + if (0 == --nOfBrackets) + return true; + } + } else if (fBreaksOnEOL) { + // Check for end of line since it can be used to terminate the pattern. + for (int i = 0; i < delimiters.length; i++) { + if (c == delimiters[i][0] && sequenceDetected(scanner, delimiters[i], false)) + return true; + } + } + } + scanner.unread(); + return true; + } + +} diff --git a/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeTextEditor.java b/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeTextEditor.java new file mode 100644 index 00000000000..9d5b04ea453 --- /dev/null +++ b/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeTextEditor.java @@ -0,0 +1,89 @@ +/********************************************************************** + * Copyright (c) 2002,2003 QNX Software Systems and others. + * All rights reserved. This program and the accompanying materials + * are made available under the terms of the Common Public License v1.0 + * which accompanies this distribution, and is available at + * http://www.eclipse.org/legal/cpl-v10.html + * + * Contributors: + * QNX Software Systems - Initial API and implementation +***********************************************************************/ +package org.eclipse.cdt.make.internal.ui.editor; + +import org.eclipse.jface.text.BadLocationException; +import org.eclipse.jface.text.IDocument; +import org.eclipse.jface.text.ITypedRegion; +import org.eclipse.jface.text.source.ISourceViewer; +import org.eclipse.ui.texteditor.DefaultRangeIndicator; +import org.eclipse.ui.texteditor.StatusTextEditor; + +public class MakeTextEditor extends StatusTextEditor { + public final static String MAKE_COMMENT = "make_comment"; //$NON-NLS-1$ + public final static String MAKE_KEYWORD = "make_keyword"; //$NON-NLS-1$ + public final static String MAKE_MACRO_VAR = "macro_var"; //$NON-NLS-1$ + public final static String MAKE_META_DATA = "meta_data"; //$NON-NLS-1$ + + private boolean presentationState; + + public MakeTextEditor() { + super(); + initializeEditor(); + } + + /** + * @see AbstractTextEditor#init(IEditorSite, IEditorInput) + */ + protected void initializeEditor() { + + setSourceViewerConfiguration(new MakeEditorConfiguration(new MakeColorManager())); + setRangeIndicator(new DefaultRangeIndicator()); + setEditorContextMenuId("#MakeEditorContext"); //$NON-NLS-1$ + setRulerContextMenuId("#MakeRulerContext"); //$NON-NLS-1$ + + } + + public boolean getPresentationState() { + return presentationState; + } + + public void setPresentationState(boolean newState) { + ISourceViewer srcViewer = getSourceViewer(); + if (null == srcViewer) + return; + presentationState = newState; + if (newState) + srcViewer.resetVisibleRegion(); + else { + IDocument document = getDocumentProvider().getDocument(getEditorInput()); + int nVisibleRegionLength; + // Collect old information + for (int offset = 0; offset < document.getLength();) { + try { + ITypedRegion region = document.getPartition(offset); + if (region.getType().equals(MakePartitionScanner.MAKE_INTERNAL)) { + nVisibleRegionLength = region.getOffset(); + srcViewer = getSourceViewer(); + if (null != srcViewer) + srcViewer.setVisibleRegion(0, nVisibleRegionLength); + break; + } + offset += Math.max(region.getLength(), 1); + } catch (BadLocationException e) { + break; + } + } + } + } + + /** + * @see org.eclipse.ui.texteditor.ITextEditor#selectAndReveal(int, int) + */ + public void selectAndReveal(int offset, int length) { + super.selectAndReveal(offset, length); + // Update visible region because text could be updated + // This is not the best place for that, at least not very + // straightforward. However keep it there for a meantime. + setPresentationState(getPresentationState()); + } + +} diff --git a/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeWordDetector.java b/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeWordDetector.java new file mode 100644 index 00000000000..837a0e19cd7 --- /dev/null +++ b/build/org.eclipse.cdt.make.ui/src/org/eclipse/cdt/make/internal/ui/editor/MakeWordDetector.java @@ -0,0 +1,34 @@ +/********************************************************************** + * Copyright (c) 2002,2003 QNX Software Systems and others. + * All rights reserved. This program and the accompanying materials + * are made available under the terms of the Common Public License v1.0 + * which accompanies this distribution, and is available at + * http://www.eclipse.org/legal/cpl-v10.html + * + * Contributors: + * QNX Software Systems - Initial API and implementation +***********************************************************************/ +package org.eclipse.cdt.make.internal.ui.editor; + +import org.eclipse.jface.text.rules.IWordDetector; + +public class MakeWordDetector implements IWordDetector { + + private static final String correctStartSpecChars = "%*().><"; //$NON-NLS-1$ + private static final String correctSpecChars = "@$/\\"; //$NON-NLS-1$ + + /** + * @see IWordDetector#isWordPart(character) + */ + public boolean isWordPart(char character) { + return Character.isLetterOrDigit(character) || (correctSpecChars.indexOf(character) >= 0); + } + + /** + * @see IWordDetector#isWordStart(char) + */ + public boolean isWordStart(char character) { + return Character.isLetterOrDigit(character) || (correctStartSpecChars.indexOf(character) >= 0); + } + +}