From d6818fbb03a931ffa345e6ee1f34ca8052d6f481 Mon Sep 17 00:00:00 2001 From: Jonah Graham Date: Sun, 10 May 2020 14:18:37 -0400 Subject: [PATCH] Bug 549697: Define standard terminal colors with Eclipse preferences New types TerminalColor and TerminalStyle replace StyleColor and Style to separate the meta information about styles and colors from the user currently selected colors. The StyleMap maps the TerminalColor/Style to the concrete fonts and colors used in the display. Colors are now configurable via the terminal preference page using the new TerminalColorsFieldEditor. All preferences are now passed in to the VT100 control so that different terminal consumers can have different preferences and styles. Remove dark theme contribution. The colors of the terminal are now inherited from the editor settings (using SystemDefaultColors) which come from the theme. If we were to invert colors too when in Dark theme then the colors actually end up light background. Change-Id: I2cf5427ac0be9a189a7f0d3565cfc97ceedb8749 --- .../guide/deprecated_API_removals.html | 31 ++- .../META-INF/MANIFEST.MF | 2 +- .../build.properties | 1 - ...rg.eclipse.tm.terminal.stylesheet.dark.css | 15 -- .../plugin.properties | 7 +- .../plugin.xml | 17 +- .../control/impl/TerminalMessages.java | 27 +++ .../control/impl/TerminalMessages.properties | 30 ++- .../emulator/IVT100EmulatorBackend.java | 10 +- .../emulator/VT100BackendTraceDecorator.java | 10 +- .../terminal/emulator/VT100Emulator.java | 43 ++-- .../emulator/VT100EmulatorBackend.java | 18 +- .../emulator/VT100TerminalControl.java | 124 +++++++--- .../model/SynchronizedTerminalTextData.java | 12 +- .../terminal/model/SystemDefaultColors.java | 113 +++++++++ .../terminal/model/TerminalTextData.java | 12 +- .../model/TerminalTextDataFastScroll.java | 12 +- .../model/TerminalTextDataSnapshot.java | 6 +- .../terminal/model/TerminalTextDataStore.java | 34 +-- .../model/TerminalTextDataWindow.java | 12 +- .../preferences/ITerminalConstants.java | 18 +- .../preferences/TerminalColorPresets.java | 134 +++++++++++ .../TerminalColorsFieldEditor.java | 227 ++++++++++++++++++ .../TerminalPreferenceInitializer.java | 11 + .../preferences/TerminalPreferencePage.java | 15 +- .../terminal/textcanvas/AnsiColorNames.java | 26 -- .../terminal/textcanvas/ILinelRenderer.java | 14 ++ .../terminal/textcanvas/StyleMap.java | 177 +++++--------- .../terminal/textcanvas/TextCanvas.java | 16 ++ .../terminal/textcanvas/TextLineRenderer.java | 40 ++- .../terminal/textcanvas/VirtualCanvas.java | 7 + .../tm/terminal/model/ITerminalTextData.java | 19 +- .../model/ITerminalTextDataReadOnly.java | 8 +- .../tm/terminal/model/LineSegment.java | 12 +- .../org/eclipse/tm/terminal/model/Style.java | 192 --------------- .../eclipse/tm/terminal/model/StyleColor.java | 56 ----- .../tm/terminal/model/TerminalColor.java | 168 +++++++++++++ .../tm/terminal/model/TerminalStyle.java | 193 +++++++++++++++ .../TerminalConnectorPluginTest.java | 4 +- .../emulator/VT100EmulatorBackendTest.java | 16 +- .../model/AbstractITerminalTextDataTest.java | 23 +- .../terminal/model/SnapshotChangesTest.java | 4 +- .../TerminalTextDataPerformanceTest.java | 21 +- .../model/TerminalTextDataSnapshotTest.java | 11 +- .../TerminalTextDataSnapshotWindowTest.java | 4 +- .../model/TerminalTextDataWindowTest.java | 18 +- .../model/TerminalTextTestHelper.java | 14 +- .../ui/AbstractLineOrientedDataSource.java | 6 +- .../terminal/test/ui/FastDataSource.java | 4 +- .../terminal/test/ui/FileDataSource.java | 11 +- .../test/ui/LineCountingDataSource.java | 20 +- .../terminal/test/ui/RandomDataSource.java | 20 +- .../eclipse/tm/terminal/model/AllTests.java | 3 +- .../tm/terminal/model/StyleColorTest.java | 35 --- .../eclipse/tm/terminal/model/StyleTest.java | 60 ++--- .../terminal/model/TerminalColorUITest.java | 82 +++++++ 56 files changed, 1496 insertions(+), 729 deletions(-) delete mode 100644 terminal/plugins/org.eclipse.tm.terminal.control/css/org.eclipse.tm.terminal.stylesheet.dark.css create mode 100644 terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/SystemDefaultColors.java create mode 100644 terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/preferences/TerminalColorPresets.java create mode 100644 terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/preferences/TerminalColorsFieldEditor.java delete mode 100644 terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/textcanvas/AnsiColorNames.java delete mode 100644 terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/Style.java delete mode 100644 terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/StyleColor.java create mode 100644 terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/TerminalColor.java create mode 100644 terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/TerminalStyle.java delete mode 100644 terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/terminal/model/StyleColorTest.java create mode 100644 terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/terminal/model/TerminalColorUITest.java diff --git a/doc/org.eclipse.cdt.doc.isv/guide/deprecated_API_removals.html b/doc/org.eclipse.cdt.doc.isv/guide/deprecated_API_removals.html index 5ca7c9f71f8..0cc11223002 100644 --- a/doc/org.eclipse.cdt.doc.isv/guide/deprecated_API_removals.html +++ b/doc/org.eclipse.cdt.doc.isv/guide/deprecated_API_removals.html @@ -43,6 +43,7 @@
  • DSF and DSF-GDB API Changes.
  • Partial removal of CDT 3.X project support.
  • Removal of CDT Core Options API.
  • +
  • TM Terminal has major changes to support new color and preference functionality.
  • Planned Removals after June 2022 @@ -228,6 +229,34 @@ See Bug 565154.

    +

    12. TM Terminal has major changes to support new color and preference functionality.

    +

    + The TM Terminal's control (org.eclipse.tm.terminal.control) bundle has a major new version to support numerous API + changes to support features such as new colors, preference sharing and some other code clean-up. +

    + + +

    Future Deletions

    @@ -289,4 +318,4 @@

    - \ No newline at end of file + diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/META-INF/MANIFEST.MF b/terminal/plugins/org.eclipse.tm.terminal.control/META-INF/MANIFEST.MF index 14b8ffa5393..f37c8e4105b 100644 --- a/terminal/plugins/org.eclipse.tm.terminal.control/META-INF/MANIFEST.MF +++ b/terminal/plugins/org.eclipse.tm.terminal.control/META-INF/MANIFEST.MF @@ -2,7 +2,7 @@ Manifest-Version: 1.0 Bundle-ManifestVersion: 2 Bundle-Name: %pluginName Bundle-SymbolicName: org.eclipse.tm.terminal.control; singleton:=true -Bundle-Version: 4.6.100.qualifier +Bundle-Version: 5.0.0.qualifier Bundle-Activator: org.eclipse.tm.internal.terminal.control.impl.TerminalPlugin Bundle-Vendor: %providerName Bundle-Localization: plugin diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/build.properties b/terminal/plugins/org.eclipse.tm.terminal.control/build.properties index 4e1b392a770..eb7d53d07b5 100644 --- a/terminal/plugins/org.eclipse.tm.terminal.control/build.properties +++ b/terminal/plugins/org.eclipse.tm.terminal.control/build.properties @@ -28,7 +28,6 @@ bin.includes = .,\ about.properties,\ icons/,\ HelpContexts.xml,\ - css/,\ about.mappings,\ cdt_logo_icon32.png diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/css/org.eclipse.tm.terminal.stylesheet.dark.css b/terminal/plugins/org.eclipse.tm.terminal.control/css/org.eclipse.tm.terminal.stylesheet.dark.css deleted file mode 100644 index 6b612015089..00000000000 --- a/terminal/plugins/org.eclipse.tm.terminal.control/css/org.eclipse.tm.terminal.stylesheet.dark.css +++ /dev/null @@ -1,15 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2014, 2015 vogella GmbH and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Eclipse Public License 2.0 - * which accompanies this distribution, and is available at - * https://www.eclipse.org/legal/epl-2.0/ - * - * Contributors: - * Lars Vogel - initial API and implementation - ******************************************************************************/ - -IEclipsePreferences#org-eclipse-tm-terminal-control { - preferences: - "TerminalPrefInvertColors=true" -} diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/plugin.properties b/terminal/plugins/org.eclipse.tm.terminal.control/plugin.properties index 6ac4936405a..e3c9236c3f2 100644 --- a/terminal/plugins/org.eclipse.tm.terminal.control/plugin.properties +++ b/terminal/plugins/org.eclipse.tm.terminal.control/plugin.properties @@ -1,5 +1,5 @@ ############################################################################### -# Copyright (c) 2003 - 2018 Wind River Systems, Inc. and others. +# Copyright (c) 2003, 2020 Wind River Systems, Inc. and others. # All rights reserved. This program and the accompanying materials # are made available under the terms of the Eclipse Public License 2.0 # which accompanies this distribution, and is available at @@ -40,7 +40,10 @@ terminal.command.maximize.name=Maximize Active View or Editor terminal.command.quickaccess.name=Quick Access terminal.preferences.name = Terminal -terminal.font.description = The font for the terminal console. +terminal.font.description = The font for the terminal console. Please also see the Terminal Preference pages for changing colors. terminal.font.label = Terminal Console Font +terminal.views.theme.category.label = Terminal +terminal.views.theme.category.description = Fonts used in the Terminal View. Please also see the Terminal Preference pages for changing colors. + terminal.connectors.name = Terminal Connector Extensions diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/plugin.xml b/terminal/plugins/org.eclipse.tm.terminal.control/plugin.xml index a5ca83d730d..ee9eaaf0a03 100644 --- a/terminal/plugins/org.eclipse.tm.terminal.control/plugin.xml +++ b/terminal/plugins/org.eclipse.tm.terminal.control/plugin.xml @@ -257,6 +257,7 @@ @@ -264,14 +265,14 @@ %terminal.font.description - + + + %terminal.views.theme.category.description + + - - - - - - + diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/control/impl/TerminalMessages.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/control/impl/TerminalMessages.java index cf95067c05c..2826d00fc31 100644 --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/control/impl/TerminalMessages.java +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/control/impl/TerminalMessages.java @@ -19,6 +19,33 @@ public class TerminalMessages extends NLS { NLS.initializeMessages(TerminalMessages.class.getName(), TerminalMessages.class); } + public static String TerminalColorPresets_EclipseDark; + public static String TerminalColorPresets_EclipseLight; + public static String TerminalColorPresets_TerminalDefaults; + public static String TerminalColorsFieldEditor_Background; + public static String TerminalColorsFieldEditor_Black; + public static String TerminalColorsFieldEditor_Blue; + public static String TerminalColorsFieldEditor_BrightBlack; + public static String TerminalColorsFieldEditor_BrightBlue; + public static String TerminalColorsFieldEditor_BrightCyan; + public static String TerminalColorsFieldEditor_BrightGreen; + public static String TerminalColorsFieldEditor_BrightMagenta; + public static String TerminalColorsFieldEditor_BrightRed; + public static String TerminalColorsFieldEditor_BrightWhite; + public static String TerminalColorsFieldEditor_BrightYellow; + public static String TerminalColorsFieldEditor_Cyan; + public static String TerminalColorsFieldEditor_GeneralColors; + public static String TerminalColorsFieldEditor_Green; + public static String TerminalColorsFieldEditor_LoadPresets; + public static String TerminalColorsFieldEditor_Magenta; + public static String TerminalColorsFieldEditor_PaletteColors; + public static String TerminalColorsFieldEditor_Presets; + public static String TerminalColorsFieldEditor_Red; + public static String TerminalColorsFieldEditor_SelectedText; + public static String TerminalColorsFieldEditor_Selection; + public static String TerminalColorsFieldEditor_TextColor; + public static String TerminalColorsFieldEditor_White; + public static String TerminalColorsFieldEditor_Yellow; public static String TerminalError; public static String SocketError; public static String IOError; diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/control/impl/TerminalMessages.properties b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/control/impl/TerminalMessages.properties index 34492a197cb..7d6366889ea 100644 --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/control/impl/TerminalMessages.properties +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/control/impl/TerminalMessages.properties @@ -1,5 +1,5 @@ ############################################################################### -# Copyright (c) 2003, 2018 Wind River Systems, Inc. and others. +# Copyright (c) 2003, 2020 Wind River Systems, Inc. and others. # All rights reserved. This program and the accompanying materials # are made available under the terms of the Eclipse Public License 2.0 # which accompanies this distribution, and is available at @@ -19,7 +19,33 @@ ############################################################################### # NLS_MESSAGEFORMAT_VAR - +TerminalColorPresets_EclipseLight=Eclipse Light +TerminalColorPresets_TerminalDefaults=Terminal Defaults +TerminalColorPresets_EclipseDark=Eclipse Dark +TerminalColorsFieldEditor_Background=Background +TerminalColorsFieldEditor_Black=Black +TerminalColorsFieldEditor_Blue=Blue +TerminalColorsFieldEditor_BrightBlack=Bright Black +TerminalColorsFieldEditor_BrightBlue=Bright Blue +TerminalColorsFieldEditor_BrightCyan=Bright Cyan +TerminalColorsFieldEditor_BrightGreen=Bright Green +TerminalColorsFieldEditor_BrightMagenta=Bright Magenta +TerminalColorsFieldEditor_BrightRed=Bright Red +TerminalColorsFieldEditor_BrightWhite=Bright White +TerminalColorsFieldEditor_BrightYellow=Bright Yellow +TerminalColorsFieldEditor_Cyan=Cyan +TerminalColorsFieldEditor_GeneralColors=General colors +TerminalColorsFieldEditor_Green=Green +TerminalColorsFieldEditor_LoadPresets=Load Presets... +TerminalColorsFieldEditor_Magenta=Magenta +TerminalColorsFieldEditor_PaletteColors=Palette colors +TerminalColorsFieldEditor_Presets=Presets +TerminalColorsFieldEditor_Red=Red +TerminalColorsFieldEditor_SelectedText=Selected text +TerminalColorsFieldEditor_Selection=Selection +TerminalColorsFieldEditor_TextColor=Text color +TerminalColorsFieldEditor_White=White +TerminalColorsFieldEditor_Yellow=Yellow TerminalError = Terminal Error SocketError = Socket Error IOError = IO Error diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/emulator/IVT100EmulatorBackend.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/emulator/IVT100EmulatorBackend.java index 6e67c970dcc..77f6f428aea 100644 --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/emulator/IVT100EmulatorBackend.java +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/emulator/IVT100EmulatorBackend.java @@ -13,7 +13,7 @@ *******************************************************************************/ package org.eclipse.tm.internal.terminal.emulator; -import org.eclipse.tm.terminal.model.Style; +import org.eclipse.tm.terminal.model.TerminalStyle; /** * @@ -100,17 +100,17 @@ public interface IVT100EmulatorBackend { */ void deleteLines(int n); - Style getDefaultStyle(); + TerminalStyle getDefaultStyle(); - void setDefaultStyle(Style defaultStyle); + void setDefaultStyle(TerminalStyle defaultStyle); - Style getStyle(); + TerminalStyle getStyle(); /** * Sets the style to be used from now on * @param style */ - void setStyle(Style style); + void setStyle(TerminalStyle style); /** * This method displays a subset of the newly-received text in the Terminal diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/emulator/VT100BackendTraceDecorator.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/emulator/VT100BackendTraceDecorator.java index 3626f18afc2..1c589c258c3 100644 --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/emulator/VT100BackendTraceDecorator.java +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/emulator/VT100BackendTraceDecorator.java @@ -15,7 +15,7 @@ package org.eclipse.tm.internal.terminal.emulator; import java.io.PrintStream; -import org.eclipse.tm.terminal.model.Style; +import org.eclipse.tm.terminal.model.TerminalStyle; public class VT100BackendTraceDecorator implements IVT100EmulatorBackend { final IVT100EmulatorBackend fBackend; @@ -102,7 +102,7 @@ public class VT100BackendTraceDecorator implements IVT100EmulatorBackend { } @Override - public Style getDefaultStyle() { + public TerminalStyle getDefaultStyle() { return fBackend.getDefaultStyle(); } @@ -112,7 +112,7 @@ public class VT100BackendTraceDecorator implements IVT100EmulatorBackend { } @Override - public Style getStyle() { + public TerminalStyle getStyle() { return fBackend.getStyle(); } @@ -153,7 +153,7 @@ public class VT100BackendTraceDecorator implements IVT100EmulatorBackend { } @Override - public void setDefaultStyle(Style defaultStyle) { + public void setDefaultStyle(TerminalStyle defaultStyle) { fWriter.println("setDefaultStyle(" + defaultStyle + ")"); //$NON-NLS-1$ //$NON-NLS-2$ fBackend.setDefaultStyle(defaultStyle); } @@ -165,7 +165,7 @@ public class VT100BackendTraceDecorator implements IVT100EmulatorBackend { } @Override - public void setStyle(Style style) { + public void setStyle(TerminalStyle style) { fWriter.println("setStyle(" + style + ")"); //$NON-NLS-1$ //$NON-NLS-2$ fBackend.setStyle(style); } diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/emulator/VT100Emulator.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/emulator/VT100Emulator.java index 080c26258e7..f6c20042b25 100644 --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/emulator/VT100Emulator.java +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/emulator/VT100Emulator.java @@ -29,15 +29,14 @@ *******************************************************************************/ package org.eclipse.tm.internal.terminal.emulator; -import static org.eclipse.tm.internal.terminal.textcanvas.AnsiColorNames.BLACK; -import static org.eclipse.tm.internal.terminal.textcanvas.AnsiColorNames.BLUE; -import static org.eclipse.tm.internal.terminal.textcanvas.AnsiColorNames.CYAN; -import static org.eclipse.tm.internal.terminal.textcanvas.AnsiColorNames.GREEN; -import static org.eclipse.tm.internal.terminal.textcanvas.AnsiColorNames.MAGENTA; -import static org.eclipse.tm.internal.terminal.textcanvas.AnsiColorNames.RED; -import static org.eclipse.tm.internal.terminal.textcanvas.AnsiColorNames.WHITE; -import static org.eclipse.tm.internal.terminal.textcanvas.AnsiColorNames.WHITE_FOREGROUND; -import static org.eclipse.tm.internal.terminal.textcanvas.AnsiColorNames.YELLOW; +import static org.eclipse.tm.terminal.model.TerminalColor.BLACK; +import static org.eclipse.tm.terminal.model.TerminalColor.BLUE; +import static org.eclipse.tm.terminal.model.TerminalColor.CYAN; +import static org.eclipse.tm.terminal.model.TerminalColor.GREEN; +import static org.eclipse.tm.terminal.model.TerminalColor.MAGENTA; +import static org.eclipse.tm.terminal.model.TerminalColor.RED; +import static org.eclipse.tm.terminal.model.TerminalColor.WHITE; +import static org.eclipse.tm.terminal.model.TerminalColor.YELLOW; import java.io.IOException; import java.io.Reader; @@ -49,7 +48,7 @@ import org.eclipse.tm.internal.terminal.control.impl.TerminalPlugin; import org.eclipse.tm.internal.terminal.provisional.api.ITerminalConnector; import org.eclipse.tm.internal.terminal.provisional.api.Logger; import org.eclipse.tm.terminal.model.ITerminalTextData; -import org.eclipse.tm.terminal.model.Style; +import org.eclipse.tm.terminal.model.TerminalStyle; /** * This class processes character data received from the remote host and @@ -170,7 +169,7 @@ public class VT100Emulator implements ControlListener { text = new VT100EmulatorBackend(data); // text.setDimensions(24, 80); - Style style = Style.getStyle("BLACK", "WHITE"); //$NON-NLS-1$ //$NON-NLS-2$ + TerminalStyle style = TerminalStyle.getDefaultStyle(); text.setDefaultStyle(style); text.setStyle(style); } @@ -851,7 +850,7 @@ public class VT100Emulator implements ControlListener { ansiParameters[0].append('0'); } - Style style = text.getStyle(); + TerminalStyle style = text.getStyle(); // There are a non-zero number of ANSI parameters. Process each one in // order. @@ -904,39 +903,39 @@ public class VT100Emulator implements ControlListener { break; case 30: - style = style.setForground(BLACK); + style = style.setForeground(BLACK); break; case 31: - style = style.setForground(RED); + style = style.setForeground(RED); break; case 32: - style = style.setForground(GREEN); + style = style.setForeground(GREEN); break; case 33: - style = style.setForground(YELLOW); + style = style.setForeground(YELLOW); break; case 34: - style = style.setForground(BLUE); + style = style.setForeground(BLUE); break; case 35: - style = style.setForground(MAGENTA); + style = style.setForeground(MAGENTA); break; case 36: - style = style.setForground(CYAN); + style = style.setForeground(CYAN); break; case 37: - style = style.setForground(WHITE_FOREGROUND); + style = style.setForeground(WHITE); break; case 39: //Foreground: Default - style = style.setForground(text.getDefaultStyle().getForground()); + style = style.setForeground(text.getDefaultStyle()); break; case 40: @@ -972,7 +971,7 @@ public class VT100Emulator implements ControlListener { break; case 49: //Background: Default - style = style.setBackground(text.getDefaultStyle().getBackground()); + style = style.setBackground(text.getDefaultStyle()); break; default: diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/emulator/VT100EmulatorBackend.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/emulator/VT100EmulatorBackend.java index d66b4bcd32c..959e8e85a2d 100644 --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/emulator/VT100EmulatorBackend.java +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/emulator/VT100EmulatorBackend.java @@ -15,7 +15,7 @@ package org.eclipse.tm.internal.terminal.emulator; import org.eclipse.tm.terminal.model.ITerminalTextData; -import org.eclipse.tm.terminal.model.Style; +import org.eclipse.tm.terminal.model.TerminalStyle; /** * @noextend This class is not intended to be subclassed by clients. @@ -87,8 +87,8 @@ public class VT100EmulatorBackend implements IVT100EmulatorBackend { * and next output requires line wrap */ private boolean fWrapPending; private boolean fInsertMode; - private Style fDefaultStyle; - private Style fStyle; + private TerminalStyle fDefaultStyle; + private TerminalStyle fStyle; int fLines; int fColumns; final private ITerminalTextData fTerminal; @@ -161,7 +161,7 @@ public class VT100EmulatorBackend implements IVT100EmulatorBackend { int n = charactersToInsert; for (int col = fColumns - 1; col >= fCursorColumn + n; col--) { char c = fTerminal.getChar(line, col - n); - Style style = fTerminal.getStyle(line, col - n); + TerminalStyle style = fTerminal.getStyle(line, col - n); fTerminal.setChar(line, col, c, style); } int last = Math.min(fCursorColumn + n, fColumns); @@ -246,7 +246,7 @@ public class VT100EmulatorBackend implements IVT100EmulatorBackend { int line = toAbsoluteLine(fCursorLine); for (int col = fCursorColumn + n; col < fColumns; col++) { char c = fTerminal.getChar(line, col); - Style style = fTerminal.getStyle(line, col); + TerminalStyle style = fTerminal.getStyle(line, col); fTerminal.setChar(line, col - n, c, style); } int first = Math.max(fCursorColumn, fColumns - n); @@ -273,21 +273,21 @@ public class VT100EmulatorBackend implements IVT100EmulatorBackend { } @Override - public Style getDefaultStyle() { + public TerminalStyle getDefaultStyle() { synchronized (fTerminal) { return fDefaultStyle; } } @Override - public void setDefaultStyle(Style defaultStyle) { + public void setDefaultStyle(TerminalStyle defaultStyle) { synchronized (fTerminal) { fDefaultStyle = defaultStyle; } } @Override - public Style getStyle() { + public TerminalStyle getStyle() { synchronized (fTerminal) { if (fStyle == null) return fDefaultStyle; @@ -296,7 +296,7 @@ public class VT100EmulatorBackend implements IVT100EmulatorBackend { } @Override - public void setStyle(Style style) { + public void setStyle(TerminalStyle style) { synchronized (fTerminal) { fStyle = style; } diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/emulator/VT100TerminalControl.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/emulator/VT100TerminalControl.java index ae58e006baf..6271c0d8733 100644 --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/emulator/VT100TerminalControl.java +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/emulator/VT100TerminalControl.java @@ -52,21 +52,26 @@ import java.io.UnsupportedEncodingException; import java.lang.reflect.Field; import java.net.SocketException; import java.nio.charset.Charset; +import java.util.EnumMap; +import java.util.Map; import org.eclipse.core.commands.ExecutionException; import org.eclipse.core.commands.ParameterizedCommand; import org.eclipse.core.runtime.Assert; import org.eclipse.core.runtime.IProgressMonitor; import org.eclipse.core.runtime.IStatus; -import org.eclipse.core.runtime.Platform; import org.eclipse.core.runtime.Status; import org.eclipse.core.runtime.jobs.Job; import org.eclipse.jface.bindings.Binding; import org.eclipse.jface.bindings.keys.KeySequence; import org.eclipse.jface.bindings.keys.KeyStroke; import org.eclipse.jface.bindings.keys.SWTKeySupport; +import org.eclipse.jface.preference.IPreferenceStore; +import org.eclipse.jface.resource.DataFormatException; import org.eclipse.jface.resource.JFaceResources; +import org.eclipse.jface.resource.StringConverter; import org.eclipse.jface.util.IPropertyChangeListener; +import org.eclipse.jface.util.PropertyChangeEvent; import org.eclipse.osgi.util.NLS; import org.eclipse.swt.SWT; import org.eclipse.swt.dnd.Clipboard; @@ -81,6 +86,7 @@ import org.eclipse.swt.events.KeyListener; import org.eclipse.swt.events.MouseAdapter; import org.eclipse.swt.events.MouseEvent; import org.eclipse.swt.graphics.Font; +import org.eclipse.swt.graphics.RGB; import org.eclipse.swt.layout.GridData; import org.eclipse.swt.layout.GridLayout; import org.eclipse.swt.widgets.Composite; @@ -98,6 +104,7 @@ import org.eclipse.tm.internal.terminal.control.impl.ITerminalControlForText; import org.eclipse.tm.internal.terminal.control.impl.TerminalMessages; import org.eclipse.tm.internal.terminal.control.impl.TerminalPlugin; import org.eclipse.tm.internal.terminal.preferences.ITerminalConstants; +import org.eclipse.tm.internal.terminal.preferences.TerminalColorPresets; import org.eclipse.tm.internal.terminal.provisional.api.ITerminalConnector; import org.eclipse.tm.internal.terminal.provisional.api.ITerminalControl; import org.eclipse.tm.internal.terminal.provisional.api.Logger; @@ -108,6 +115,7 @@ import org.eclipse.tm.internal.terminal.textcanvas.TextCanvas; import org.eclipse.tm.internal.terminal.textcanvas.TextLineRenderer; import org.eclipse.tm.terminal.model.ITerminalTextData; import org.eclipse.tm.terminal.model.ITerminalTextDataSnapshot; +import org.eclipse.tm.terminal.model.TerminalColor; import org.eclipse.tm.terminal.model.TerminalTextDataFactory; import org.eclipse.ui.PlatformUI; import org.eclipse.ui.contexts.IContextActivation; @@ -144,7 +152,7 @@ public class VT100TerminalControl implements ITerminalControlForText, ITerminalC private TerminalFocusListener fFocusListener; private ITerminalConnector fConnector; private final ITerminalConnector[] fConnectors; - private final boolean fUseCommonPrefs; + private final IPreferenceStore fPreferenceStore; private boolean connectOnEnterIfClosed = true; PipedInputStream fInputStream; @@ -165,17 +173,8 @@ public class VT100TerminalControl implements ITerminalControlForText, ITerminalC /** * Listens to changes in the preferences */ - private final IPropertyChangeListener fPreferenceListener = event -> { - if (event.getProperty().equals(ITerminalConstants.PREF_BUFFERLINES) - || event.getProperty().equals(ITerminalConstants.PREF_INVERT_COLORS)) { - updatePreferences(); - } - }; - private final IPropertyChangeListener fFontListener = event -> { - if (event.getProperty().equals(ITerminalConstants.FONT_DEFINITION)) { - onTerminalFontChanged(); - } - }; + private final IPropertyChangeListener fPreferenceListener = this::updatePreferences; + private final IPropertyChangeListener fFontListener = this::updateFont; /** * Is protected by synchronize on this @@ -184,12 +183,22 @@ public class VT100TerminalControl implements ITerminalControlForText, ITerminalC private PollingTextCanvasModel fPollingTextCanvasModel; + /** + * Instantiate a Terminal widget. + * @param target Callback for notifying the owner of Terminal state changes. + * @param wndParent The Window parent to embed the Terminal in. + * @param connectors Provided connectors. + * @param preferenceStore If non-null, the Terminal widget will pick up settings + * from the given store. + * @since 3.2 + */ public VT100TerminalControl(ITerminalListener target, Composite wndParent, ITerminalConnector[] connectors) { - this(target, wndParent, connectors, false); + this(target, wndParent, connectors, null); } /** - * Instantiate a Terminal widget. + * Instantiate a Terminal widget using the org.eclipse.tm.terminal.TerminalPreferencePage Preference page's + * default preference store. * @param target Callback for notifying the owner of Terminal state changes. * @param wndParent The Window parent to embed the Terminal in. * @param connectors Provided connectors. @@ -200,8 +209,22 @@ public class VT100TerminalControl implements ITerminalControlForText, ITerminalC */ public VT100TerminalControl(ITerminalListener target, Composite wndParent, ITerminalConnector[] connectors, boolean useCommonPrefs) { + this(target, wndParent, connectors, useCommonPrefs ? TerminalPlugin.getDefault().getPreferenceStore() : null); + } + + /** + * Instantiate a Terminal widget. + * @param target Callback for notifying the owner of Terminal state changes. + * @param wndParent The Window parent to embed the Terminal in. + * @param connectors Provided connectors. + * @param preferenceStore If non-null, the Terminal widget will pick up settings + * from the given store. + * @since 5.0 + */ + public VT100TerminalControl(ITerminalListener target, Composite wndParent, ITerminalConnector[] connectors, + IPreferenceStore preferenceStore) { fConnectors = connectors; - fUseCommonPrefs = useCommonPrefs; + fPreferenceStore = preferenceStore; fTerminalListener = target; fTerminalModel = TerminalTextDataFactory.makeTerminalTextData(); fTerminalModel.setMaxHeight(1000); @@ -373,10 +396,10 @@ public class VT100TerminalControl implements ITerminalControlForText, ITerminalC @Override public void disposeTerminal() { Logger.log("entered."); //$NON-NLS-1$ - if (fUseCommonPrefs) { - TerminalPlugin.getDefault().getPreferenceStore().removePropertyChangeListener(fPreferenceListener); - JFaceResources.getFontRegistry().removeListener(fFontListener); + if (fPreferenceStore != null) { + fPreferenceStore.removePropertyChangeListener(fPreferenceListener); } + JFaceResources.getFontRegistry().removeListener(fFontListener); disconnectTerminal(); fClipboard.dispose(); getTerminalText().dispose(); @@ -642,12 +665,11 @@ public class VT100TerminalControl implements ITerminalControlForText, ITerminalC setupControls(parent); setCommandInputField(fCommandInputField); setupListeners(); - if (fUseCommonPrefs && wasDisposed) { - updatePreferences(); - onTerminalFontChanged(); - TerminalPlugin.getDefault().getPreferenceStore().addPropertyChangeListener(fPreferenceListener); - JFaceResources.getFontRegistry().addListener(fFontListener); + if (fPreferenceStore != null && wasDisposed) { + updatePreferences(null); + fPreferenceStore.addPropertyChangeListener(fPreferenceListener); } + JFaceResources.getFontRegistry().addListener(fFontListener); setupHelp(fWndParent, TerminalPlugin.HELP_VIEW); if (!wasDisposed) { @@ -655,18 +677,58 @@ public class VT100TerminalControl implements ITerminalControlForText, ITerminalC } } - private void updatePreferences() { - int bufferLineLimit = Platform.getPreferencesService().getInt(TerminalPlugin.PLUGIN_ID, - ITerminalConstants.PREF_BUFFERLINES, 0, null); - boolean invert = Platform.getPreferencesService().getBoolean(TerminalPlugin.PLUGIN_ID, - ITerminalConstants.PREF_INVERT_COLORS, false, null); + private void updatePreferences(PropertyChangeEvent unused) { + int bufferLineLimit = fPreferenceStore.getInt(ITerminalConstants.PREF_BUFFERLINES); + boolean invert = fPreferenceStore.getBoolean(ITerminalConstants.PREF_INVERT_COLORS); setBufferLineLimit(bufferLineLimit); setInvertedColors(invert); + onTerminalColorsChanged(); + onTerminalFontChanged(); + } + + private void onTerminalColorsChanged() { + Map map = new EnumMap<>(TerminalColor.class); + TerminalColor[] values = TerminalColor.values(); + for (TerminalColor terminalColor : values) { + RGB rgb = null; + if (fPreferenceStore != null) { + try { + rgb = StringConverter.asRGB( + fPreferenceStore.getString(ITerminalConstants.getPrefForTerminalColor(terminalColor))); + } catch (DataFormatException dfe) { + // bad color, use default preset value instead + } + } + + if (rgb == null) { + rgb = TerminalColorPresets.INSTANCE.getDefaultPreset().getRGB(terminalColor); + } + map.put(terminalColor, rgb); + } + fCtlText.updateColors(map); + } + + private String getFontDefinition() { + String definition; + if (fPreferenceStore != null) { + definition = fPreferenceStore.getString(ITerminalConstants.PREF_FONT_DEFINITION); + } else { + definition = ITerminalConstants.DEFAULT_FONT_DEFINITION; + } + if (definition == null || definition.isEmpty()) { + definition = "org.eclipse.jface.textfont"; //$NON-NLS-1$ + } + return definition; } private void onTerminalFontChanged() { - // set the font for all - setFont(ITerminalConstants.FONT_DEFINITION); + setFont(getFontDefinition()); + } + + private void updateFont(PropertyChangeEvent event) { + if (event.getProperty().equals(getFontDefinition())) { + onTerminalFontChanged(); + } } @Override diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/SynchronizedTerminalTextData.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/SynchronizedTerminalTextData.java index c99d01a4a7a..54f637a78ab 100644 --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/SynchronizedTerminalTextData.java +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/SynchronizedTerminalTextData.java @@ -14,7 +14,7 @@ package org.eclipse.tm.internal.terminal.model; import org.eclipse.tm.terminal.model.ITerminalTextData; import org.eclipse.tm.terminal.model.ITerminalTextDataSnapshot; import org.eclipse.tm.terminal.model.LineSegment; -import org.eclipse.tm.terminal.model.Style; +import org.eclipse.tm.terminal.model.TerminalStyle; /** * This is a decorator to make all access to @@ -89,12 +89,12 @@ public class SynchronizedTerminalTextData implements ITerminalTextData { } @Override - synchronized public Style getStyle(int line, int column) { + synchronized public TerminalStyle getStyle(int line, int column) { return fData.getStyle(line, column); } @Override - synchronized public Style[] getStyles(int line) { + synchronized public TerminalStyle[] getStyles(int line) { return fData.getStyles(line); } @@ -114,17 +114,17 @@ public class SynchronizedTerminalTextData implements ITerminalTextData { } @Override - synchronized public void setChar(int line, int column, char c, Style style) { + synchronized public void setChar(int line, int column, char c, TerminalStyle style) { fData.setChar(line, column, c, style); } @Override - synchronized public void setChars(int line, int column, char[] chars, int start, int len, Style style) { + synchronized public void setChars(int line, int column, char[] chars, int start, int len, TerminalStyle style) { fData.setChars(line, column, chars, start, len, style); } @Override - synchronized public void setChars(int line, int column, char[] chars, Style style) { + synchronized public void setChars(int line, int column, char[] chars, TerminalStyle style) { fData.setChars(line, column, chars, style); } diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/SystemDefaultColors.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/SystemDefaultColors.java new file mode 100644 index 00000000000..930a97a1e73 --- /dev/null +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/SystemDefaultColors.java @@ -0,0 +1,113 @@ +/******************************************************************************* + * Copyright (c) 2020 Kichwa Coders Canada Inc. and others. + * All rights reserved. This program and the accompanying materials + * are made available under the terms of the Eclipse Public License 2.0 + * which accompanies this distribution, and is available at + * https://www.eclipse.org/legal/epl-2.0/ + * + * SPDX-License-Identifier: EPL-2.0 + *******************************************************************************/ +package org.eclipse.tm.internal.terminal.model; + +import java.util.function.Supplier; + +import org.eclipse.core.runtime.Platform; +import org.eclipse.core.runtime.preferences.InstanceScope; +import org.eclipse.jface.preference.IPreferenceStore; +import org.eclipse.jface.preference.PreferenceConverter; +import org.eclipse.swt.graphics.RGB; +import org.eclipse.ui.preferences.ScopedPreferenceStore; +import org.eclipse.ui.themes.ColorUtil; + +/** + * Wrapper class to get standard colors from Eclipse trying to match existing theme where possible + * by using standard editor colors. + * + * This class has an implied and optional dependency on org.eclipse.ui.editors bundle by reading + * that bundles preferences. + */ +public enum SystemDefaultColors implements Supplier { + + /** + * Standard text foreground. Typically black in Light theme. + */ + FOREGROUND("Foreground", "COLOR_LIST_FOREGROUND", new RGB(0, 0, 0)), //$NON-NLS-1$ //$NON-NLS-2$ + + /** + * Standard text background. Typically white in Light theme. + */ + BACKGROUND("Background", "COLOR_LIST_BACKGROUND", new RGB(255, 255, 255)), //$NON-NLS-1$ //$NON-NLS-2$ + + /** + * Selection foreground. Typically white in Light theme. + */ + SELECTION_FOREGROUND("SelectionForeground", "COLOR_LIST_SELECTION_TEXT", //$NON-NLS-1$ //$NON-NLS-2$ + new RGB(255, 255, 255)), + + /** + * Selection background. Typically blue in Light theme. + */ + SELECTION_BACKGROUND("SelectionBackground", "COLOR_LIST_SELECTION", new RGB(74, 144, 9)); //$NON-NLS-1$ //$NON-NLS-2$ + + private static final String EDITOR_SCOPE = "org.eclipse.ui.editors"; //$NON-NLS-1$ + private static final String PREF_PREFIX = "AbstractTextEditor.Color."; //$NON-NLS-1$ + private static final String PREF_SYSTEM_DEFAULT_SUFFIX = ".SystemDefault"; //$NON-NLS-1$ + + /** + * SWT Name of Color + * + * Values from SWT + */ + private String swtColor; + + /** + * Preference name for color. + * + * Values from org.eclipse.ui.texteditor.AbstractTextEditor.... + */ + private String editorColor; + + /** If all else fails, use this standard color */ + private RGB fallbackColor; + + SystemDefaultColors(String editorColor, String swtColor, RGB rgb) { + this.editorColor = editorColor; + this.swtColor = swtColor; + this.fallbackColor = rgb; + } + + /** + * Get the color for this enum value. + * + * @return the RGB color or a non-null color as a fallback. + */ + @Override + public RGB get() { + IPreferenceStore store = new ScopedPreferenceStore(InstanceScope.INSTANCE, EDITOR_SCOPE); + + RGB rgb = null; + String pref = PREF_PREFIX + editorColor; + String prefSystemDefault = pref + PREF_SYSTEM_DEFAULT_SUFFIX; + if (Platform.getPreferencesService() != null) { + if (!store.getBoolean(prefSystemDefault)) { + if (store.contains(pref)) { + if (store.isDefault(pref)) + rgb = PreferenceConverter.getDefaultColor(store, pref); + else { + rgb = PreferenceConverter.getColor(store, pref); + } + } + } + } + + if (rgb == null) { + rgb = ColorUtil.getColorValue(swtColor); + } + + if (rgb == null) { + rgb = fallbackColor; + } + + return rgb; + } +} \ No newline at end of file diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/TerminalTextData.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/TerminalTextData.java index 409e6bc63ee..9e6cf40f9d1 100644 --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/TerminalTextData.java +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/TerminalTextData.java @@ -22,7 +22,7 @@ import org.eclipse.tm.terminal.model.ITerminalTextData; import org.eclipse.tm.terminal.model.ITerminalTextDataReadOnly; import org.eclipse.tm.terminal.model.ITerminalTextDataSnapshot; import org.eclipse.tm.terminal.model.LineSegment; -import org.eclipse.tm.terminal.model.Style; +import org.eclipse.tm.terminal.model.TerminalStyle; /** * This class is thread safe. @@ -136,24 +136,24 @@ public class TerminalTextData implements ITerminalTextData { } @Override - public Style getStyle(int line, int column) { + public TerminalStyle getStyle(int line, int column) { return fData.getStyle(line, column); } @Override - public void setChar(int line, int column, char c, Style style) { + public void setChar(int line, int column, char c, TerminalStyle style) { fData.setChar(line, column, c, style); sendLineChangedToSnapshots(line); } @Override - public void setChars(int line, int column, char[] chars, Style style) { + public void setChars(int line, int column, char[] chars, TerminalStyle style) { fData.setChars(line, column, chars, style); sendLineChangedToSnapshots(line); } @Override - public void setChars(int line, int column, char[] chars, int start, int len, Style style) { + public void setChars(int line, int column, char[] chars, int start, int len, TerminalStyle style) { fData.setChars(line, column, chars, start, len, style); sendLineChangedToSnapshots(line); } @@ -279,7 +279,7 @@ public class TerminalTextData implements ITerminalTextData { } @Override - public Style[] getStyles(int line) { + public TerminalStyle[] getStyles(int line) { return fData.getStyles(line); } diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataFastScroll.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataFastScroll.java index 8cb0bd3cad5..519fad0a3e1 100644 --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataFastScroll.java +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataFastScroll.java @@ -14,7 +14,7 @@ package org.eclipse.tm.internal.terminal.model; import org.eclipse.tm.terminal.model.ITerminalTextData; import org.eclipse.tm.terminal.model.ITerminalTextDataSnapshot; import org.eclipse.tm.terminal.model.LineSegment; -import org.eclipse.tm.terminal.model.Style; +import org.eclipse.tm.terminal.model.TerminalStyle; /** * This class is optimized for scrolling the entire {@link #getHeight()}. @@ -151,13 +151,13 @@ public class TerminalTextDataFastScroll implements ITerminalTextData { } @Override - public Style getStyle(int line, int column) { + public TerminalStyle getStyle(int line, int column) { assert (line >= 0 && line < fHeight) || throwRuntimeException(); return fData.getStyle(getPositionOfLine(line), column); } @Override - public Style[] getStyles(int line) { + public TerminalStyle[] getStyles(int line) { assert (line >= 0 && line < fHeight) || throwRuntimeException(); return fData.getStyles(getPositionOfLine(line)); } @@ -214,19 +214,19 @@ public class TerminalTextDataFastScroll implements ITerminalTextData { } @Override - public void setChar(int line, int column, char c, Style style) { + public void setChar(int line, int column, char c, TerminalStyle style) { assert (line >= 0 && line < fHeight) || throwRuntimeException(); fData.setChar(getPositionOfLine(line), column, c, style); } @Override - public void setChars(int line, int column, char[] chars, int start, int len, Style style) { + public void setChars(int line, int column, char[] chars, int start, int len, TerminalStyle style) { assert (line >= 0 && line < fHeight) || throwRuntimeException(); fData.setChars(getPositionOfLine(line), column, chars, start, len, style); } @Override - public void setChars(int line, int column, char[] chars, Style style) { + public void setChars(int line, int column, char[] chars, TerminalStyle style) { assert (line >= 0 && line < fHeight) || throwRuntimeException(); fData.setChars(getPositionOfLine(line), column, chars, style); } diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataSnapshot.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataSnapshot.java index 7d3d5a7f88e..26a6982c871 100644 --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataSnapshot.java +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataSnapshot.java @@ -18,7 +18,7 @@ import java.util.List; import org.eclipse.tm.terminal.model.ITerminalTextData; import org.eclipse.tm.terminal.model.ITerminalTextDataSnapshot; import org.eclipse.tm.terminal.model.LineSegment; -import org.eclipse.tm.terminal.model.Style; +import org.eclipse.tm.terminal.model.TerminalStyle; /** * The public methods of this class have to be called from one thread! @@ -137,7 +137,7 @@ class TerminalTextDataSnapshot implements ITerminalTextDataSnapshot { } @Override - public Style getStyle(int line, int column) { + public TerminalStyle getStyle(int line, int column) { return fSnapshot.getStyle(line, column); } @@ -299,7 +299,7 @@ class TerminalTextDataSnapshot implements ITerminalTextDataSnapshot { } @Override - public Style[] getStyles(int line) { + public TerminalStyle[] getStyles(int line) { return fSnapshot.getStyles(line); } diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataStore.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataStore.java index 2ab5b22025a..f0472aba928 100644 --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataStore.java +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataStore.java @@ -19,7 +19,7 @@ import java.util.List; import org.eclipse.tm.terminal.model.ITerminalTextData; import org.eclipse.tm.terminal.model.ITerminalTextDataSnapshot; import org.eclipse.tm.terminal.model.LineSegment; -import org.eclipse.tm.terminal.model.Style; +import org.eclipse.tm.terminal.model.TerminalStyle; /** * This class is thread safe. @@ -27,7 +27,7 @@ import org.eclipse.tm.terminal.model.Style; */ public class TerminalTextDataStore implements ITerminalTextData { private char[][] fChars; - private Style[][] fStyle; + private TerminalStyle[][] fStyle; private int fWidth; private int fHeight; private int fMaxHeight; @@ -37,7 +37,7 @@ public class TerminalTextDataStore implements ITerminalTextData { public TerminalTextDataStore() { fChars = new char[0][]; - fStyle = new Style[0][]; + fStyle = new TerminalStyle[0][]; fWidth = 0; } @@ -69,7 +69,7 @@ public class TerminalTextDataStore implements ITerminalTextData { int h = 4 * height / 3; if (fMaxHeight > 0 && h > fMaxHeight) h = fMaxHeight; - fStyle = (Style[][]) resizeArray(fStyle, height); + fStyle = (TerminalStyle[][]) resizeArray(fStyle, height); fChars = (char[][]) resizeArray(fChars, height); } // clean the new lines @@ -106,16 +106,16 @@ public class TerminalTextDataStore implements ITerminalTextData { @Override public LineSegment[] getLineSegments(int line, int column, int len) { // get the styles and chars for this line - Style[] styles = fStyle[line]; + TerminalStyle[] styles = fStyle[line]; char[] chars = fChars[line]; int col = column; int n = column + len; // expand the line if needed.... if (styles == null) - styles = new Style[n]; + styles = new TerminalStyle[n]; else if (styles.length < n) - styles = (Style[]) resizeArray(styles, n); + styles = (TerminalStyle[]) resizeArray(styles, n); if (chars == null) chars = new char[n]; @@ -123,7 +123,7 @@ public class TerminalTextDataStore implements ITerminalTextData { chars = (char[]) resizeArray(chars, n); // and create the line segments - Style style = styles[column]; + TerminalStyle style = styles[column]; List segments = new ArrayList<>(); for (int i = column; i < n; i++) { if (styles[i] != style) { @@ -147,7 +147,7 @@ public class TerminalTextDataStore implements ITerminalTextData { } @Override - public Style getStyle(int line, int column) { + public TerminalStyle getStyle(int line, int column) { assert column < fWidth || throwRuntimeException(); if (fStyle[line] == null || column >= fStyle[line].length) return null; @@ -163,26 +163,26 @@ public class TerminalTextDataStore implements ITerminalTextData { fChars[iLine] = (char[]) resizeArray(fChars[iLine], length); } if (fStyle[iLine] == null) { - fStyle[iLine] = new Style[length]; + fStyle[iLine] = new TerminalStyle[length]; } else if (fStyle[iLine].length < length) { - fStyle[iLine] = (Style[]) resizeArray(fStyle[iLine], length); + fStyle[iLine] = (TerminalStyle[]) resizeArray(fStyle[iLine], length); } } @Override - public void setChar(int line, int column, char c, Style style) { + public void setChar(int line, int column, char c, TerminalStyle style) { ensureLineLength(line, column + 1); fChars[line][column] = c; fStyle[line][column] = style; } @Override - public void setChars(int line, int column, char[] chars, Style style) { + public void setChars(int line, int column, char[] chars, TerminalStyle style) { setChars(line, column, chars, 0, chars.length, style); } @Override - public void setChars(int line, int column, char[] chars, int start, int len, Style style) { + public void setChars(int line, int column, char[] chars, int start, int len, TerminalStyle style) { ensureLineLength(line, column + len); for (int i = 0; i < len; i++) { fChars[line][column + i] = chars[i + start]; @@ -262,7 +262,7 @@ public class TerminalTextDataStore implements ITerminalTextData { int n = source.getHeight(); if (getHeight() != n) { fChars = new char[n][]; - fStyle = new Style[n][]; + fStyle = new TerminalStyle[n][]; } for (int i = 0; i < n; i++) { copyLine(source, i, i); @@ -294,13 +294,13 @@ public class TerminalTextDataStore implements ITerminalTextData { } @Override - public Style[] getStyles(int line) { + public TerminalStyle[] getStyles(int line) { if (fStyle[line] == null) return null; return fStyle[line].clone(); } - public void setLine(int line, char[] chars, Style[] styles) { + public void setLine(int line, char[] chars, TerminalStyle[] styles) { fChars[line] = chars.clone(); fStyle[line] = styles.clone(); fWrappedLines.clear(line); diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataWindow.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataWindow.java index f9ec141d858..31e6d625901 100644 --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataWindow.java +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataWindow.java @@ -14,7 +14,7 @@ package org.eclipse.tm.internal.terminal.model; import org.eclipse.tm.terminal.model.ITerminalTextData; import org.eclipse.tm.terminal.model.ITerminalTextDataSnapshot; import org.eclipse.tm.terminal.model.LineSegment; -import org.eclipse.tm.terminal.model.Style; +import org.eclipse.tm.terminal.model.TerminalStyle; /** * This class stores the data only within a window {@link #setWindow(int, int)} and @@ -86,14 +86,14 @@ public class TerminalTextDataWindow implements ITerminalTextData { } @Override - public Style getStyle(int line, int column) { + public TerminalStyle getStyle(int line, int column) { if (!isInWindow(line)) return null; return fData.getStyle(line - fWindowStartLine, column); } @Override - public Style[] getStyles(int line) { + public TerminalStyle[] getStyles(int line) { if (!isInWindow(line)) return null; return fData.getStyles(line - fWindowStartLine); @@ -168,21 +168,21 @@ public class TerminalTextDataWindow implements ITerminalTextData { } @Override - public void setChar(int line, int column, char c, Style style) { + public void setChar(int line, int column, char c, TerminalStyle style) { if (!isInWindow(line)) return; fData.setChar(line - fWindowStartLine, column, c, style); } @Override - public void setChars(int line, int column, char[] chars, int start, int len, Style style) { + public void setChars(int line, int column, char[] chars, int start, int len, TerminalStyle style) { if (!isInWindow(line)) return; fData.setChars(line - fWindowStartLine, column, chars, start, len, style); } @Override - public void setChars(int line, int column, char[] chars, Style style) { + public void setChars(int line, int column, char[] chars, TerminalStyle style) { if (!isInWindow(line)) return; fData.setChars(line - fWindowStartLine, column, chars, style); diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/preferences/ITerminalConstants.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/preferences/ITerminalConstants.java index 0c44566fb77..9f87a310388 100644 --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/preferences/ITerminalConstants.java +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/preferences/ITerminalConstants.java @@ -14,6 +14,8 @@ *******************************************************************************/ package org.eclipse.tm.internal.terminal.preferences; +import org.eclipse.tm.terminal.model.TerminalColor; + /** * Constants for Terminal Preferences. * @@ -22,13 +24,27 @@ package org.eclipse.tm.internal.terminal.preferences; */ public interface ITerminalConstants { + public static final String FONT_DEFINITION = "terminal.views.view.font.definition"; //$NON-NLS-1$ public static final String PREF_HAS_MIGRATED = "TerminalPref.migrated"; //$NON-NLS-1$ public static final String PREF_BUFFERLINES = "TerminalPrefBufferLines"; //$NON-NLS-1$ public static final String PREF_INVERT_COLORS = "TerminalPrefInvertColors"; //$NON-NLS-1$ + /** + * @since 5.0 + */ + public static final String PREF_FONT_DEFINITION = "TerminalFontDefinition"; //$NON-NLS-1$ public static final int DEFAULT_BUFFERLINES = 1000; public static final boolean DEFAULT_INVERT_COLORS = false; + /** + * @since 5.0 + */ + public static final String DEFAULT_FONT_DEFINITION = FONT_DEFINITION; - public static final String FONT_DEFINITION = "terminal.views.view.font.definition"; //$NON-NLS-1$ + /** + * @since 5.0 + */ + public static String getPrefForTerminalColor(TerminalColor tc) { + return tc.toString(); + } } diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/preferences/TerminalColorPresets.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/preferences/TerminalColorPresets.java new file mode 100644 index 00000000000..108ac7de0c2 --- /dev/null +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/preferences/TerminalColorPresets.java @@ -0,0 +1,134 @@ +/******************************************************************************* + * Copyright (c) 2020 Kichwa Coders Canada Inc. and others. + * All rights reserved. This program and the accompanying materials + * are made available under the terms of the Eclipse Public License 2.0 + * which accompanies this distribution, and is available at + * https://www.eclipse.org/legal/epl-2.0/ + * + * SPDX-License-Identifier: EPL-2.0 + *******************************************************************************/ +package org.eclipse.tm.internal.terminal.preferences; + +import static org.eclipse.tm.terminal.model.TerminalColor.BACKGROUND; +import static org.eclipse.tm.terminal.model.TerminalColor.BLACK; +import static org.eclipse.tm.terminal.model.TerminalColor.BLUE; +import static org.eclipse.tm.terminal.model.TerminalColor.BRIGHT_BLACK; +import static org.eclipse.tm.terminal.model.TerminalColor.BRIGHT_BLUE; +import static org.eclipse.tm.terminal.model.TerminalColor.BRIGHT_CYAN; +import static org.eclipse.tm.terminal.model.TerminalColor.BRIGHT_GREEN; +import static org.eclipse.tm.terminal.model.TerminalColor.BRIGHT_MAGENTA; +import static org.eclipse.tm.terminal.model.TerminalColor.BRIGHT_RED; +import static org.eclipse.tm.terminal.model.TerminalColor.BRIGHT_WHITE; +import static org.eclipse.tm.terminal.model.TerminalColor.BRIGHT_YELLOW; +import static org.eclipse.tm.terminal.model.TerminalColor.CYAN; +import static org.eclipse.tm.terminal.model.TerminalColor.FOREGROUND; +import static org.eclipse.tm.terminal.model.TerminalColor.GREEN; +import static org.eclipse.tm.terminal.model.TerminalColor.MAGENTA; +import static org.eclipse.tm.terminal.model.TerminalColor.RED; +import static org.eclipse.tm.terminal.model.TerminalColor.SELECTION_BACKGROUND; +import static org.eclipse.tm.terminal.model.TerminalColor.SELECTION_FOREGROUND; +import static org.eclipse.tm.terminal.model.TerminalColor.WHITE; +import static org.eclipse.tm.terminal.model.TerminalColor.YELLOW; + +import java.util.ArrayList; +import java.util.EnumMap; +import java.util.List; +import java.util.Map; +import java.util.function.Supplier; +import java.util.stream.Collectors; + +import org.eclipse.swt.graphics.RGB; +import org.eclipse.tm.internal.terminal.control.impl.TerminalMessages; +import org.eclipse.tm.internal.terminal.model.SystemDefaultColors; +import org.eclipse.tm.terminal.model.TerminalColor; + +/** + * @since 5.0 + */ +public enum TerminalColorPresets { + + INSTANCE; + + private final List presets = new ArrayList<>(); + + public List getPresets() { + return presets.stream().map(Preset::getName).collect(Collectors.toList()); + } + + public Preset getPreset(int index) { + return presets.get(index); + } + + public static class Preset { + private String name; + private Map> map = new EnumMap<>(TerminalColor.class); + + Preset(String name) { + this.name = name; + set(BLACK, 0, 0, 0); + set(RED, 205, 0, 0); + set(GREEN, 0, 205, 0); + set(YELLOW, 205, 205, 0); + set(BLUE, 0, 0, 238); + set(MAGENTA, 205, 0, 205); + set(CYAN, 0, 205, 205); + set(WHITE, 229, 229, 229); + + set(BRIGHT_BLACK, 0, 0, 0); + set(BRIGHT_RED, 255, 0, 0); + set(BRIGHT_GREEN, 0, 255, 0); + set(BRIGHT_YELLOW, 255, 255, 0); + set(BRIGHT_BLUE, 92, 92, 255); + set(BRIGHT_MAGENTA, 255, 0, 255); + set(BRIGHT_CYAN, 0, 255, 255); + set(BRIGHT_WHITE, 255, 255, 255); + + set(FOREGROUND, SystemDefaultColors.FOREGROUND); + set(BACKGROUND, SystemDefaultColors.BACKGROUND); + set(SELECTION_FOREGROUND, SystemDefaultColors.SELECTION_FOREGROUND); + set(SELECTION_BACKGROUND, SystemDefaultColors.SELECTION_BACKGROUND); + } + + Preset set(TerminalColor color, RGB rgb) { + return set(color, () -> rgb); + } + + Preset set(TerminalColor color, int r, int g, int b) { + return set(color, new RGB(r, g, b)); + } + + Preset set(TerminalColor color, Supplier rgbSupplier) { + map.put(color, rgbSupplier); + return this; + } + + public String getName() { + return name; + } + + /** + * Returns the preset value for the given color. Will never return null + * because each color must be defined in the map. + * + * @param terminalColor to get RGB value for + * @return non-null color + */ + public RGB getRGB(TerminalColor terminalColor) { + return map.getOrDefault(terminalColor, () -> new RGB(0, 0, 0)).get(); + } + } + + TerminalColorPresets() { + presets.add(new Preset(TerminalMessages.TerminalColorPresets_TerminalDefaults)); + presets.add(new Preset(TerminalMessages.TerminalColorPresets_EclipseLight) // + .set(FOREGROUND, getDefaultPreset().getRGB(BLACK)) // + .set(BACKGROUND, getDefaultPreset().getRGB(WHITE))); + presets.add(new Preset(TerminalMessages.TerminalColorPresets_EclipseDark) // + .set(FOREGROUND, getDefaultPreset().getRGB(WHITE)) // + .set(BACKGROUND, getDefaultPreset().getRGB(BLACK))); + } + + public Preset getDefaultPreset() { + return presets.get(0); + } +} diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/preferences/TerminalColorsFieldEditor.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/preferences/TerminalColorsFieldEditor.java new file mode 100644 index 00000000000..1ea8983c5ac --- /dev/null +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/preferences/TerminalColorsFieldEditor.java @@ -0,0 +1,227 @@ +/******************************************************************************* + * Copyright (c) 2020 Kichwa Coders Canada Inc. and others. + * All rights reserved. This program and the accompanying materials + * are made available under the terms of the Eclipse Public License 2.0 + * which accompanies this distribution, and is available at + * https://www.eclipse.org/legal/epl-2.0/ + * + * SPDX-License-Identifier: EPL-2.0 + *******************************************************************************/ +package org.eclipse.tm.internal.terminal.preferences; + +import static org.eclipse.tm.terminal.model.TerminalColor.BACKGROUND; +import static org.eclipse.tm.terminal.model.TerminalColor.BLACK; +import static org.eclipse.tm.terminal.model.TerminalColor.BLUE; +import static org.eclipse.tm.terminal.model.TerminalColor.BRIGHT_BLACK; +import static org.eclipse.tm.terminal.model.TerminalColor.BRIGHT_BLUE; +import static org.eclipse.tm.terminal.model.TerminalColor.BRIGHT_CYAN; +import static org.eclipse.tm.terminal.model.TerminalColor.BRIGHT_GREEN; +import static org.eclipse.tm.terminal.model.TerminalColor.BRIGHT_MAGENTA; +import static org.eclipse.tm.terminal.model.TerminalColor.BRIGHT_RED; +import static org.eclipse.tm.terminal.model.TerminalColor.BRIGHT_WHITE; +import static org.eclipse.tm.terminal.model.TerminalColor.BRIGHT_YELLOW; +import static org.eclipse.tm.terminal.model.TerminalColor.CYAN; +import static org.eclipse.tm.terminal.model.TerminalColor.FOREGROUND; +import static org.eclipse.tm.terminal.model.TerminalColor.GREEN; +import static org.eclipse.tm.terminal.model.TerminalColor.MAGENTA; +import static org.eclipse.tm.terminal.model.TerminalColor.RED; +import static org.eclipse.tm.terminal.model.TerminalColor.SELECTION_BACKGROUND; +import static org.eclipse.tm.terminal.model.TerminalColor.SELECTION_FOREGROUND; +import static org.eclipse.tm.terminal.model.TerminalColor.WHITE; +import static org.eclipse.tm.terminal.model.TerminalColor.YELLOW; + +import java.util.EnumMap; + +import org.eclipse.jface.layout.GridDataFactory; +import org.eclipse.jface.layout.GridLayoutFactory; +import org.eclipse.jface.preference.ColorSelector; +import org.eclipse.jface.preference.FieldEditor; +import org.eclipse.jface.preference.IPreferenceStore; +import org.eclipse.jface.preference.PreferenceConverter; +import org.eclipse.jface.resource.FontDescriptor; +import org.eclipse.swt.SWT; +import org.eclipse.swt.graphics.Font; +import org.eclipse.swt.layout.GridData; +import org.eclipse.swt.widgets.Combo; +import org.eclipse.swt.widgets.Composite; +import org.eclipse.swt.widgets.Group; +import org.eclipse.swt.widgets.Label; +import org.eclipse.tm.internal.terminal.control.impl.TerminalMessages; +import org.eclipse.tm.terminal.model.TerminalColor; + +/** + * A field editor that can be used for editing terminal colors. + * + * @since 5.0 + */ +public class TerminalColorsFieldEditor extends FieldEditor { + + private EnumMap colorSelectors; + private Composite controls; + private Font boldFont; + + /** + * Creates a field editor for editing colors of {@link TerminalColor}. + * The preference names used are as they are returned from {@link TerminalColor#getPreferenceName()} + * @param labelText + * @param parent + */ + public TerminalColorsFieldEditor(Composite parent) { + super("", "", parent); //$NON-NLS-1$ //$NON-NLS-2$ + } + + @Override + protected void adjustForNumColumns(int numColumns) { + GridData gd = (GridData) controls.getLayoutData(); + gd.horizontalSpan = numColumns; + } + + @Override + public int getNumberOfControls() { + return 1; + } + + @Override + protected void doFillIntoGrid(Composite parent, int numColumns) { + colorSelectors = new EnumMap<>(TerminalColor.class); + controls = new Composite(parent, SWT.NONE); + GridDataFactory.fillDefaults().applyTo(controls); + GridLayoutFactory.fillDefaults().applyTo(controls); + + FontDescriptor boldDescriptor = FontDescriptor.createFrom(parent.getFont()).setStyle(SWT.BOLD); + boldFont = boldDescriptor.createFont(parent.getDisplay()); + + Group general = new Group(controls, SWT.SHADOW_NONE); + general.setText(TerminalMessages.TerminalColorsFieldEditor_GeneralColors); + general.setFont(boldFont); + GridDataFactory.fillDefaults().applyTo(general); + GridLayoutFactory.swtDefaults().numColumns(4).applyTo(general); + + createLabelledSelector(general, FOREGROUND, TerminalMessages.TerminalColorsFieldEditor_TextColor); + createLabelledSelector(general, BACKGROUND, TerminalMessages.TerminalColorsFieldEditor_Background); + createLabelledSelector(general, SELECTION_BACKGROUND, TerminalMessages.TerminalColorsFieldEditor_Selection); + createLabelledSelector(general, SELECTION_FOREGROUND, TerminalMessages.TerminalColorsFieldEditor_SelectedText); + + Group palette = new Group(controls, SWT.SHADOW_NONE); + palette.setText(TerminalMessages.TerminalColorsFieldEditor_PaletteColors); + palette.setFont(boldFont); + GridDataFactory.fillDefaults().applyTo(palette); + GridLayoutFactory.swtDefaults().numColumns(8).applyTo(palette); + + createSelector(palette, BLACK, TerminalMessages.TerminalColorsFieldEditor_Black); + createSelector(palette, RED, TerminalMessages.TerminalColorsFieldEditor_Red); + createSelector(palette, GREEN, TerminalMessages.TerminalColorsFieldEditor_Green); + createSelector(palette, YELLOW, TerminalMessages.TerminalColorsFieldEditor_Yellow); + createSelector(palette, BLUE, TerminalMessages.TerminalColorsFieldEditor_Blue); + createSelector(palette, MAGENTA, TerminalMessages.TerminalColorsFieldEditor_Magenta); + createSelector(palette, CYAN, TerminalMessages.TerminalColorsFieldEditor_Cyan); + createSelector(palette, WHITE, TerminalMessages.TerminalColorsFieldEditor_White); + + createSelector(palette, BRIGHT_BLACK, TerminalMessages.TerminalColorsFieldEditor_BrightBlack); + createSelector(palette, BRIGHT_RED, TerminalMessages.TerminalColorsFieldEditor_BrightRed); + createSelector(palette, BRIGHT_GREEN, TerminalMessages.TerminalColorsFieldEditor_BrightGreen); + createSelector(palette, BRIGHT_YELLOW, TerminalMessages.TerminalColorsFieldEditor_BrightYellow); + createSelector(palette, BRIGHT_BLUE, TerminalMessages.TerminalColorsFieldEditor_BrightBlue); + createSelector(palette, BRIGHT_MAGENTA, TerminalMessages.TerminalColorsFieldEditor_BrightMagenta); + createSelector(palette, BRIGHT_CYAN, TerminalMessages.TerminalColorsFieldEditor_BrightCyan); + createSelector(palette, BRIGHT_WHITE, TerminalMessages.TerminalColorsFieldEditor_BrightWhite); + + Group presets = new Group(controls, SWT.SHADOW_NONE); + presets.setText(TerminalMessages.TerminalColorsFieldEditor_Presets); + presets.setFont(boldFont); + GridDataFactory.fillDefaults().applyTo(presets); + GridLayoutFactory.swtDefaults().numColumns(2).applyTo(presets); + Combo presetsCombo = new Combo(presets, SWT.DROP_DOWN | SWT.READ_ONLY); + presetsCombo.add(TerminalMessages.TerminalColorsFieldEditor_LoadPresets); + TerminalColorPresets colorPresets = TerminalColorPresets.INSTANCE; + colorPresets.getPresets().forEach(presetsCombo::add); + presetsCombo.addListener(SWT.Selection, e -> { + int selectionIndex = presetsCombo.getSelectionIndex(); + if (selectionIndex > 0) { + int selectedPresetIndex = selectionIndex - 1; // account for "Load Presets..." entry + colorSelectors.forEach((terminalColor, colorSelector) -> colorSelector + .setColorValue(colorPresets.getPreset(selectedPresetIndex).getRGB(terminalColor))); + + } + }); + presetsCombo.select(0); + } + + @Override + public void dispose() { + if (boldFont != null) { + boldFont.dispose(); + } + } + + private void createLabelledSelector(Composite parent, TerminalColor color, String label) { + Label labelControl = new Label(parent, SWT.LEFT); + labelControl.setText(label); + GridDataFactory.fillDefaults().align(SWT.FILL, SWT.CENTER).applyTo(labelControl); + createSelector(parent, color, label); + } + + private void createSelector(Composite parent, TerminalColor color, String label) { + ColorSelector colorSelector = new ColorSelector(parent); + colorSelector.getButton().setToolTipText(label); + GridDataFactory.fillDefaults().applyTo(colorSelector.getButton()); + colorSelectors.put(color, colorSelector); + } + + @Override + protected void doLoad() { + IPreferenceStore store = getPreferenceStore(); + colorSelectors.forEach((terminalColor, colorSelector) -> colorSelector.setColorValue( + PreferenceConverter.getColor(store, ITerminalConstants.getPrefForTerminalColor(terminalColor)))); + } + + @Override + protected void doLoadDefault() { + IPreferenceStore store = getPreferenceStore(); + colorSelectors.forEach((terminalColor, colorSelector) -> colorSelector.setColorValue( + PreferenceConverter.getDefaultColor(store, ITerminalConstants.getPrefForTerminalColor(terminalColor)))); + } + + @Override + public void store() { + IPreferenceStore store = getPreferenceStore(); + if (store == null) { + return; + } + + if (presentsDefaultValue()) { + doStoreDefault(store); + } else { + doStore(); + } + } + + /** + * Stores the default preference value from this field editor into + * the preference store. + */ + protected void doStoreDefault(IPreferenceStore store) { + colorSelectors.forEach((terminalColor, colorSelector) -> store + .setToDefault(ITerminalConstants.getPrefForTerminalColor(terminalColor))); + } + + @Override + protected void doStore() { + IPreferenceStore store = getPreferenceStore(); + colorSelectors.forEach((terminalColor, colorSelector) -> PreferenceConverter.setValue(store, + ITerminalConstants.getPrefForTerminalColor(terminalColor), colorSelector.getColorValue())); + } + + @Override + public String getPreferenceName() { + throw new IllegalArgumentException( + "preference name should not be accessed as this class represent multiple preferences"); //$NON-NLS-1$ + } + + @Override + public String getLabelText() { + throw new IllegalArgumentException( + "label text should not be accessed as this class represent multiple preferences"); //$NON-NLS-1$ + } + +} diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/preferences/TerminalPreferenceInitializer.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/preferences/TerminalPreferenceInitializer.java index df901498ce6..d6d737459b4 100644 --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/preferences/TerminalPreferenceInitializer.java +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/preferences/TerminalPreferenceInitializer.java @@ -18,7 +18,10 @@ package org.eclipse.tm.internal.terminal.preferences; import org.eclipse.core.runtime.preferences.AbstractPreferenceInitializer; import org.eclipse.core.runtime.preferences.DefaultScope; import org.eclipse.core.runtime.preferences.IEclipsePreferences; +import org.eclipse.jface.resource.StringConverter; import org.eclipse.tm.internal.terminal.control.impl.TerminalPlugin; +import org.eclipse.tm.internal.terminal.preferences.TerminalColorPresets.Preset; +import org.eclipse.tm.terminal.model.TerminalColor; /** * Terminal Preference Initializer. @@ -38,5 +41,13 @@ public class TerminalPreferenceInitializer extends AbstractPreferenceInitializer IEclipsePreferences defaultPrefs = DefaultScope.INSTANCE.getNode(TerminalPlugin.PLUGIN_ID); defaultPrefs.putBoolean(ITerminalConstants.PREF_INVERT_COLORS, ITerminalConstants.DEFAULT_INVERT_COLORS); defaultPrefs.putInt(ITerminalConstants.PREF_BUFFERLINES, ITerminalConstants.DEFAULT_BUFFERLINES); + defaultPrefs.put(ITerminalConstants.PREF_FONT_DEFINITION, ITerminalConstants.DEFAULT_FONT_DEFINITION); + + Preset defaultPresets = TerminalColorPresets.INSTANCE.getDefaultPreset(); + TerminalColor[] colors = TerminalColor.values(); + for (TerminalColor color : colors) { + defaultPrefs.put(ITerminalConstants.getPrefForTerminalColor(color), + StringConverter.asString(defaultPresets.getRGB(color))); + } } } diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/preferences/TerminalPreferencePage.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/preferences/TerminalPreferencePage.java index e3b0691977a..6dcc77da03f 100644 --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/preferences/TerminalPreferencePage.java +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/preferences/TerminalPreferencePage.java @@ -36,9 +36,6 @@ import org.eclipse.ui.IWorkbenchPreferencePage; * @noreference This class is not intended to be referenced by clients. */ public class TerminalPreferencePage extends FieldEditorPreferencePage implements IWorkbenchPreferencePage { - protected BooleanFieldEditor fInvertColors; - - protected IntegerFieldEditor fEditorBufferSize; public TerminalPreferencePage() { super(GRID); @@ -69,14 +66,12 @@ public class TerminalPreferencePage extends FieldEditorPreferencePage implements } protected void setupEditors() { - fInvertColors = new BooleanFieldEditor(ITerminalConstants.PREF_INVERT_COLORS, TerminalMessages.INVERT_COLORS, - getFieldEditorParent()); - fEditorBufferSize = new IntegerFieldEditor(ITerminalConstants.PREF_BUFFERLINES, TerminalMessages.BUFFERLINES, - getFieldEditorParent()); + addField(new BooleanFieldEditor(ITerminalConstants.PREF_INVERT_COLORS, TerminalMessages.INVERT_COLORS, + getFieldEditorParent())); - fEditorBufferSize.setValidRange(0, Integer.MAX_VALUE); + addField(new IntegerFieldEditor(ITerminalConstants.PREF_BUFFERLINES, TerminalMessages.BUFFERLINES, + getFieldEditorParent())); - addField(fInvertColors); - addField(fEditorBufferSize); + addField(new TerminalColorsFieldEditor(getFieldEditorParent())); } } diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/textcanvas/AnsiColorNames.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/textcanvas/AnsiColorNames.java deleted file mode 100644 index b57da7239f3..00000000000 --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/textcanvas/AnsiColorNames.java +++ /dev/null @@ -1,26 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2007, 2020 Wind River Systems, Inc. and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Eclipse Public License 2.0 - * which accompanies this distribution, and is available at - * https://www.eclipse.org/legal/epl-2.0/ - * - * SPDX-License-Identifier: EPL-2.0 - * - * Contributors: - * Jonah Graham - extracted colour names from StyleMap to be reused and cross referenced in VT100Emulator - *******************************************************************************/ -package org.eclipse.tm.internal.terminal.textcanvas; - -public class AnsiColorNames { - public static final String BLACK = "black"; //$NON-NLS-1$ - public static final String WHITE = "white"; //$NON-NLS-1$ - public static final String WHITE_FOREGROUND = "white_foreground"; //$NON-NLS-1$ - public static final String GRAY = "gray"; //$NON-NLS-1$ - public static final String MAGENTA = "magenta"; //$NON-NLS-1$ - public static final String CYAN = "cyan"; //$NON-NLS-1$ - public static final String YELLOW = "yellow"; //$NON-NLS-1$ - public static final String BLUE = "blue"; //$NON-NLS-1$ - public static final String GREEN = "green"; //$NON-NLS-1$ - public static final String RED = "red"; //$NON-NLS-1$ -} diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/textcanvas/ILinelRenderer.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/textcanvas/ILinelRenderer.java index 2d38a96eac0..8ef7c58cb89 100644 --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/textcanvas/ILinelRenderer.java +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/textcanvas/ILinelRenderer.java @@ -14,8 +14,13 @@ *******************************************************************************/ package org.eclipse.tm.internal.terminal.textcanvas; +import java.util.Map; + import org.eclipse.swt.graphics.Color; +import org.eclipse.swt.graphics.Device; import org.eclipse.swt.graphics.GC; +import org.eclipse.swt.graphics.RGB; +import org.eclipse.tm.terminal.model.TerminalColor; /** * @@ -41,7 +46,16 @@ public interface ILinelRenderer { */ void updateFont(String fontName); + void updateColors(Map map); + void setInvertedColors(boolean invert); + /** + * @deprecated use {@link #getDefaultBackgroundColor(Device)} + */ + @Deprecated Color getDefaultBackgroundColor(); + + Color getDefaultBackgroundColor(Device device); + } diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/textcanvas/StyleMap.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/textcanvas/StyleMap.java index 6a0a7c0dd8b..badc43b6730 100644 --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/textcanvas/StyleMap.java +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/textcanvas/StyleMap.java @@ -19,170 +19,104 @@ *******************************************************************************/ package org.eclipse.tm.internal.terminal.textcanvas; -import static org.eclipse.tm.internal.terminal.textcanvas.AnsiColorNames.BLACK; -import static org.eclipse.tm.internal.terminal.textcanvas.AnsiColorNames.BLUE; -import static org.eclipse.tm.internal.terminal.textcanvas.AnsiColorNames.CYAN; -import static org.eclipse.tm.internal.terminal.textcanvas.AnsiColorNames.GRAY; -import static org.eclipse.tm.internal.terminal.textcanvas.AnsiColorNames.GREEN; -import static org.eclipse.tm.internal.terminal.textcanvas.AnsiColorNames.MAGENTA; -import static org.eclipse.tm.internal.terminal.textcanvas.AnsiColorNames.RED; -import static org.eclipse.tm.internal.terminal.textcanvas.AnsiColorNames.WHITE; -import static org.eclipse.tm.internal.terminal.textcanvas.AnsiColorNames.WHITE_FOREGROUND; -import static org.eclipse.tm.internal.terminal.textcanvas.AnsiColorNames.YELLOW; - -import java.util.HashMap; +import java.util.EnumMap; import java.util.Map; import org.eclipse.jface.resource.JFaceResources; -import org.eclipse.swt.SWT; -import org.eclipse.swt.graphics.Color; import org.eclipse.swt.graphics.Font; import org.eclipse.swt.graphics.GC; import org.eclipse.swt.graphics.Point; import org.eclipse.swt.graphics.RGB; import org.eclipse.swt.widgets.Display; import org.eclipse.tm.internal.terminal.preferences.ITerminalConstants; -import org.eclipse.tm.terminal.model.Style; -import org.eclipse.tm.terminal.model.StyleColor; +import org.eclipse.tm.internal.terminal.preferences.TerminalColorPresets; +import org.eclipse.tm.terminal.model.TerminalColor; +import org.eclipse.tm.terminal.model.TerminalStyle; +/** + * The split between responsibilities of StyleMap and TerminalStyle are not always clear. Generally + * the style parts that are global for a terminal are here, where as in TerminalStyle is about + * a specific range. + */ public class StyleMap { - private static final String PREFIX = "org.eclipse.tm.internal."; //$NON-NLS-1$ String fFontName = ITerminalConstants.FONT_DEFINITION; - Map fColorMapForeground = new HashMap<>(); - Map fColorMapBackground = new HashMap<>(); - Map fColorMapIntense = new HashMap<>(); private Point fCharSize; - private final Style fDefaultStyle; + private final TerminalStyle fDefaultStyle; private boolean fInvertColors; private boolean fProportional; private final int[] fOffsets = new int[256]; + private final Map fColorMap = new EnumMap<>(TerminalColor.class); - StyleMap() { + public StyleMap() { + fDefaultStyle = TerminalStyle.getDefaultStyle(); + initFont(); initColors(); - fDefaultStyle = Style.getStyle(StyleColor.getStyleColor(BLACK), StyleColor.getStyleColor(WHITE)); - updateFont(); } private void initColors() { - initForegroundColors(); - initBackgroundColors(); - initIntenseColors(); - } - - private void initForegroundColors() { - if (fInvertColors) { - setColor(fColorMapForeground, WHITE, 0, 0, 0); - setColor(fColorMapForeground, WHITE_FOREGROUND, 50, 50, 50); - setColor(fColorMapForeground, BLACK, 229, 229, 229); - } else { - setColor(fColorMapForeground, WHITE, 255, 255, 255); - setColor(fColorMapForeground, WHITE_FOREGROUND, 229, 229, 229); - setColor(fColorMapForeground, BLACK, 50, 50, 50); + Map map = new EnumMap<>(TerminalColor.class); + TerminalColor[] values = TerminalColor.values(); + for (TerminalColor terminalColor : values) { + RGB rgb = TerminalColorPresets.INSTANCE.getDefaultPreset().getRGB(terminalColor); + map.put(terminalColor, rgb); } - setColor(fColorMapForeground, RED, 205, 0, 0); - setColor(fColorMapForeground, GREEN, 0, 205, 0); - setColor(fColorMapForeground, BLUE, 0, 0, 238); - setColor(fColorMapForeground, YELLOW, 205, 205, 0); - setColor(fColorMapForeground, CYAN, 0, 205, 205); - setColor(fColorMapForeground, MAGENTA, 205, 0, 205); - setColor(fColorMapForeground, GRAY, 229, 229, 229); + updateColors(map); } - private void initBackgroundColors() { - if (fInvertColors) { - setColor(fColorMapBackground, WHITE, 0, 0, 0); - setColor(fColorMapBackground, WHITE_FOREGROUND, 50, 50, 50); // only used when colors are inverse - setColor(fColorMapBackground, BLACK, 255, 255, 255); + private void initFont() { + updateFont(ITerminalConstants.FONT_DEFINITION); + } + + private RGB getRGB(TerminalColor color) { + return fColorMap.get(color); + } + + public RGB getForegrondRGB(TerminalStyle style) { + style = defaultIfNull(style); + TerminalColor color; + if (style.isReverse()) { + color = style.getBackgroundTerminalColor(); } else { - setColor(fColorMapBackground, WHITE, 255, 255, 255); - setColor(fColorMapBackground, WHITE_FOREGROUND, 229, 229, 229); - setColor(fColorMapBackground, BLACK, 0, 0, 0); + color = style.getForegroundTerminalColor(); } - setColor(fColorMapBackground, RED, 205, 0, 0); - setColor(fColorMapBackground, GREEN, 0, 205, 0); - setColor(fColorMapBackground, BLUE, 0, 0, 238); - setColor(fColorMapBackground, YELLOW, 205, 205, 0); - setColor(fColorMapBackground, CYAN, 0, 205, 205); - setColor(fColorMapBackground, MAGENTA, 205, 0, 205); - setColor(fColorMapBackground, GRAY, 229, 229, 229); - } - private void initIntenseColors() { - if (fInvertColors) { - setColor(fColorMapIntense, WHITE, 127, 127, 127); - setColor(fColorMapIntense, WHITE_FOREGROUND, 0, 0, 0); // only used when colors are inverse - setColor(fColorMapIntense, BLACK, 255, 255, 255); - } else { - setColor(fColorMapIntense, WHITE, 255, 255, 255); - setColor(fColorMapIntense, WHITE_FOREGROUND, 255, 255, 255); - setColor(fColorMapIntense, BLACK, 0, 0, 0); - } - setColor(fColorMapIntense, RED, 255, 0, 0); - setColor(fColorMapIntense, GREEN, 0, 255, 0); - setColor(fColorMapIntense, BLUE, 92, 92, 255); - setColor(fColorMapIntense, YELLOW, 255, 255, 0); - setColor(fColorMapIntense, CYAN, 0, 255, 255); - setColor(fColorMapIntense, MAGENTA, 255, 0, 255); - setColor(fColorMapIntense, GRAY, 255, 255, 255); - } - - private void setColor(Map colorMap, String name, int r, int g, int b) { - String colorName = PREFIX + r + "-" + g + "-" + b; //$NON-NLS-1$//$NON-NLS-2$ - Color color = JFaceResources.getColorRegistry().get(colorName); if (color == null) { - JFaceResources.getColorRegistry().put(colorName, new RGB(r, g, b)); - color = JFaceResources.getColorRegistry().get(colorName); + color = TerminalColor.FOREGROUND; } - colorMap.put(StyleColor.getStyleColor(name), color); - colorMap.put(StyleColor.getStyleColor(name.toUpperCase()), color); + + color = color.convertColor(fInvertColors, style.isBold()); + return getRGB(color); } - public Color getForegrondColor(Style style) { + public RGB getBackgroundRGB(TerminalStyle style) { style = defaultIfNull(style); - Map map = style.isBold() ? fColorMapIntense : fColorMapForeground; - //Map map = fColorMapForeground; - if (style.isReverse()) - return getColor(map, style.getBackground()); - else - return getColor(map, style.getForground()); - } - - public Color getBackgroundColor(Style style) { - style = defaultIfNull(style); - if (style.isReverse()) - return getColor(fColorMapBackground, style.getForground()); - else - return getColor(fColorMapBackground, style.getBackground()); - } - - Color getColor(Map map, StyleColor color) { - Color c = map.get(color); - if (c == null) { - c = Display.getCurrent().getSystemColor(SWT.COLOR_GRAY); + TerminalColor color; + if (style.isReverse()) { + color = style.getForegroundTerminalColor(); + } else { + color = style.getBackgroundTerminalColor(); } - return c; + + if (color == null) { + color = TerminalColor.BACKGROUND; + } + + color = color.convertColor(fInvertColors, style.isBold()); + return getRGB(color); } - private Style defaultIfNull(Style style) { + private TerminalStyle defaultIfNull(TerminalStyle style) { if (style == null) style = fDefaultStyle; return style; } public void setInvertedColors(boolean invert) { - if (invert == fInvertColors) - return; fInvertColors = invert; - initColors(); } - // static Font getBoldFont(Font font) { - // FontData fontDatas[] = font.getFontData(); - // FontData data = fontDatas[0]; - // return new Font(Display.getCurrent(), data.getName(), data.getHeight(), data.getStyle()|SWT.BOLD); - // } - public Font getFont(Style style) { + public Font getFont(TerminalStyle style) { style = defaultIfNull(style); if (style.isBold()) { return JFaceResources.getFontRegistry().getBold(fFontName); @@ -195,7 +129,6 @@ public class StyleMap { public Font getFont() { return JFaceResources.getFontRegistry().get(fFontName); - } public int getFontWidth() { @@ -314,4 +247,8 @@ public class StyleMap { return 0; return fOffsets[c]; } + + public void updateColors(Map colorMap) { + fColorMap.putAll(colorMap); + } } diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/textcanvas/TextCanvas.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/textcanvas/TextCanvas.java index 5913fde1d9b..493b8b17c88 100644 --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/textcanvas/TextCanvas.java +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/textcanvas/TextCanvas.java @@ -25,6 +25,7 @@ package org.eclipse.tm.internal.terminal.textcanvas; import java.util.ArrayList; import java.util.List; +import java.util.Map; import org.eclipse.swt.SWT; import org.eclipse.swt.dnd.Clipboard; @@ -35,11 +36,14 @@ import org.eclipse.swt.events.FocusListener; import org.eclipse.swt.events.MouseEvent; import org.eclipse.swt.events.MouseListener; import org.eclipse.swt.graphics.Color; +import org.eclipse.swt.graphics.Device; import org.eclipse.swt.graphics.GC; import org.eclipse.swt.graphics.Point; +import org.eclipse.swt.graphics.RGB; import org.eclipse.swt.graphics.Rectangle; import org.eclipse.swt.widgets.Composite; import org.eclipse.tm.internal.terminal.control.ITerminalMouseListener; +import org.eclipse.tm.terminal.model.TerminalColor; /** * A cell oriented Canvas. Maintains a list of "cells". @@ -369,6 +373,12 @@ public class TextCanvas extends GridCanvas { } @Override + protected Color getTerminalBackgroundColor(Device device) { + return fCellRenderer.getDefaultBackgroundColor(device); + } + + @Override + @Deprecated protected Color getTerminalBackgroundColor() { return fCellRenderer.getDefaultBackgroundColor(); } @@ -490,6 +500,11 @@ public class TextCanvas extends GridCanvas { calculateGrid(); } + public void updateColors(Map map) { + fCellRenderer.updateColors(map); + redraw(); + } + public void setInvertedColors(boolean invert) { fCellRenderer.setInvertedColors(invert); redraw(); @@ -520,4 +535,5 @@ public class TextCanvas extends GridCanvas { public void removeTerminalMouseListener(ITerminalMouseListener listener) { fMouseListeners.remove(listener); } + } diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/textcanvas/TextLineRenderer.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/textcanvas/TextLineRenderer.java index 88babe72d6e..6f4cc343fbe 100644 --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/textcanvas/TextLineRenderer.java +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/textcanvas/TextLineRenderer.java @@ -16,26 +16,32 @@ *******************************************************************************/ package org.eclipse.tm.internal.terminal.textcanvas; +import java.util.Map; + import org.eclipse.swt.SWT; import org.eclipse.swt.graphics.Color; +import org.eclipse.swt.graphics.Device; import org.eclipse.swt.graphics.Font; import org.eclipse.swt.graphics.GC; import org.eclipse.swt.graphics.Image; import org.eclipse.swt.graphics.Point; +import org.eclipse.swt.graphics.RGB; import org.eclipse.swt.widgets.Display; import org.eclipse.tm.terminal.model.ITerminalTextDataReadOnly; import org.eclipse.tm.terminal.model.LineSegment; -import org.eclipse.tm.terminal.model.Style; +import org.eclipse.tm.terminal.model.TerminalColor; +import org.eclipse.tm.terminal.model.TerminalStyle; /** * */ public class TextLineRenderer implements ILinelRenderer { private final ITextCanvasModel fModel; - StyleMap fStyleMap = new StyleMap(); + private final StyleMap fStyleMap; public TextLineRenderer(TextCanvas c, ITextCanvasModel model) { fModel = model; + fStyleMap = new StyleMap(); } @Override @@ -65,7 +71,7 @@ public class TextLineRenderer implements ILinelRenderer { LineSegment[] segments = getTerminalText().getLineSegments(line, colFirst, colLast - colFirst); for (int i = 0; i < segments.length; i++) { LineSegment segment = segments[i]; - Style style = segment.getStyle(); + TerminalStyle style = segment.getStyle(); setupGC(doubleBufferGC, style); String text = segment.getText(); drawText(doubleBufferGC, 0, 0, colFirst, segment.getColumn(), text); @@ -102,7 +108,7 @@ public class TextLineRenderer implements ILinelRenderer { private void fillBackground(GC gc, int x, int y, int width, int height) { Color bg = gc.getBackground(); - gc.setBackground(getDefaultBackgroundColor()); + gc.setBackground(getDefaultBackgroundColor(gc.getDevice())); gc.fillRectangle(x, y, width, height); gc.setBackground(bg); @@ -110,8 +116,14 @@ public class TextLineRenderer implements ILinelRenderer { @Override public Color getDefaultBackgroundColor() { + return getDefaultBackgroundColor(Display.getDefault()); + } + + @Override + public Color getDefaultBackgroundColor(Device device) { // null == default style - return fStyleMap.getBackgroundColor(null); + RGB backgroundRGB = fStyleMap.getBackgroundRGB(null); + return new Color(device, backgroundRGB); } private void drawCursor(ITextCanvasModel model, GC gc, int row, int x, int y, int colFirst) { @@ -122,10 +134,10 @@ public class TextLineRenderer implements ILinelRenderer { if (row == cursorLine) { int cursorColumn = model.getCursorColumn(); if (cursorColumn < getTerminalText().getWidth()) { - Style style = getTerminalText().getStyle(row, cursorColumn); + TerminalStyle style = getTerminalText().getStyle(row, cursorColumn); if (style == null) { // TODO make the cursor color customizable - style = Style.getStyle("BLACK", "WHITE"); //$NON-NLS-1$//$NON-NLS-2$ + style = TerminalStyle.getStyle(TerminalColor.FOREGROUND, TerminalColor.BACKGROUND); } style = style.setReverse(!style.isReverse()); setupGC(gc, style); @@ -156,9 +168,12 @@ public class TextLineRenderer implements ILinelRenderer { } } - private void setupGC(GC gc, Style style) { - gc.setForeground(fStyleMap.getForegrondColor(style)); - gc.setBackground(fStyleMap.getBackgroundColor(style)); + private void setupGC(GC gc, TerminalStyle style) { + RGB foregrondColor = fStyleMap.getForegrondRGB(style); + gc.setForeground(new Color(gc.getDevice(), foregrondColor)); + RGB backgroundColor = fStyleMap.getBackgroundRGB(style); + gc.setBackground(new Color(gc.getDevice(), backgroundColor)); + Font f = fStyleMap.getFont(style); if (f != gc.getFont()) { gc.setFont(f); @@ -183,6 +198,11 @@ public class TextLineRenderer implements ILinelRenderer { fStyleMap.updateFont(fontName); } + @Override + public void updateColors(Map map) { + fStyleMap.updateColors(map); + } + @Override public void setInvertedColors(boolean invert) { fStyleMap.setInvertedColors(invert); diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/textcanvas/VirtualCanvas.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/textcanvas/VirtualCanvas.java index af4d794dc3e..2fc846e7dbc 100644 --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/textcanvas/VirtualCanvas.java +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/internal/terminal/textcanvas/VirtualCanvas.java @@ -15,6 +15,7 @@ import org.eclipse.core.runtime.IStatus; import org.eclipse.core.runtime.Status; import org.eclipse.swt.SWT; import org.eclipse.swt.graphics.Color; +import org.eclipse.swt.graphics.Device; import org.eclipse.swt.graphics.GC; import org.eclipse.swt.graphics.Rectangle; import org.eclipse.swt.widgets.Canvas; @@ -136,6 +137,12 @@ public abstract class VirtualCanvas extends Canvas { */ abstract protected void paint(GC gc); + abstract protected Color getTerminalBackgroundColor(Device device); + + /** + * @deprecated Use {@link #getTerminalBackgroundColor(Device)} + */ + @Deprecated protected Color getTerminalBackgroundColor() { // return getDisplay().getSystemColor(SWT.COLOR_LIST_BACKGROUND); return getDisplay().getSystemColor(SWT.COLOR_WIDGET_BACKGROUND); diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/ITerminalTextData.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/ITerminalTextData.java index 37a85731e45..37a563284b2 100644 --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/ITerminalTextData.java +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/ITerminalTextData.java @@ -15,7 +15,7 @@ package org.eclipse.tm.terminal.model; /** - * A writable matrix of characters and {@link Style}. This is intended to be the + * A writable matrix of characters and {@link TerminalStyle}. This is intended to be the * low level representation of the text of a Terminal. Higher layers are * responsible to fill the text and styles into this representation. *

    @@ -41,33 +41,36 @@ public interface ITerminalTextData extends ITerminalTextDataReadOnly { int getMaxHeight(); /** - * Set a single character and the associated {@link Style}. + * Set a single character and the associated {@link TerminalStyle}. * @param line line must be >=0 and < height * @param column column must be >=0 and < width * @param c the new character at this position * @param style the style or null + * @since 5.0 */ - void setChar(int line, int column, char c, Style style); + void setChar(int line, int column, char c, TerminalStyle style); /** - * Set an array of characters showing in the same {@link Style}. + * Set an array of characters showing in the same {@link TerminalStyle}. * @param line line must be >=0 and < height * @param column column must be >=0 and < width * @param chars the new characters at this position * @param style the style or null + * @since 5.0 */ - void setChars(int line, int column, char[] chars, Style style); + void setChars(int line, int column, char[] chars, TerminalStyle style); /** - * Set a subrange of an array of characters showing in the same {@link Style}. + * Set a subrange of an array of characters showing in the same {@link TerminalStyle}. * @param line line must be >=0 and < height * @param column column must be >=0 and < width * @param chars the new characters at this position * @param start the start index in the chars array * @param len the number of characters to insert. Characters beyond width are not inserted. * @param style the style or null + * @since 5.0 */ - void setChars(int line, int column, char[] chars, int start, int len, Style style); + void setChars(int line, int column, char[] chars, int start, int len, TerminalStyle style); /** * Cleans the entire line. @@ -77,7 +80,7 @@ public interface ITerminalTextData extends ITerminalTextDataReadOnly { /** * Shifts some lines up or down. The "empty" space is filled with '\000' chars - * and null {@link Style} + * and null {@link TerminalStyle} *

    To illustrate shift, here is some sample data: *

     	 * 0 aaaa
    diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/ITerminalTextDataReadOnly.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/ITerminalTextDataReadOnly.java
    index d935b409a71..af30864e56f 100644
    --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/ITerminalTextDataReadOnly.java
    +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/ITerminalTextDataReadOnly.java
    @@ -49,8 +49,9 @@ public interface ITerminalTextDataReadOnly {
     	 * @param line must be >=0 and < height
     	 * @param column must be >=0 and < width
     	 * @return style at column,line or null
    +	 * @since 5.0
     	 */
    -	Style getStyle(int line, int column);
    +	TerminalStyle getStyle(int line, int column);
     
     	/**
     	 * Creates a new instance of {@link ITerminalTextDataSnapshot} that
    @@ -67,7 +68,10 @@ public interface ITerminalTextDataReadOnly {
     
     	char[] getChars(int line);
     
    -	Style[] getStyles(int line);
    +	/**
    +	 * @since 5.0
    +	 */
    +	TerminalStyle[] getStyles(int line);
     
     	/**
     	 * @return the line in which the cursor is at the moment
    diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/LineSegment.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/LineSegment.java
    index d92100fd6ce..548dc705891 100644
    --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/LineSegment.java
    +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/LineSegment.java
    @@ -13,15 +13,21 @@ package org.eclipse.tm.terminal.model;
     public class LineSegment {
     	private final String fText;
     	private final int fCol;
    -	private final Style fStyle;
    +	private final TerminalStyle fStyle;
     
    -	public LineSegment(int col, String text, Style style) {
    +	/**
    +	 * @since 5.0
    +	 */
    +	public LineSegment(int col, String text, TerminalStyle style) {
     		fCol = col;
     		fText = text;
     		fStyle = style;
     	}
     
    -	public Style getStyle() {
    +	/**
    +	 * @since 5.0
    +	 */
    +	public TerminalStyle getStyle() {
     		return fStyle;
     	}
     
    diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/Style.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/Style.java
    deleted file mode 100644
    index e05d17e9eb7..00000000000
    --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/Style.java
    +++ /dev/null
    @@ -1,192 +0,0 @@
    -/*******************************************************************************
    - * Copyright (c) 2007, 2018 Wind River Systems, Inc. and others.
    - * All rights reserved. This program and the accompanying materials
    - * are made available under the terms of the Eclipse Public License 2.0
    - * which accompanies this distribution, and is available at
    - * https://www.eclipse.org/legal/epl-2.0/
    - *
    - * Contributors:
    - * Michael Scharf (Wind River) - initial API and implementation
    - *******************************************************************************/
    -package org.eclipse.tm.terminal.model;
    -
    -import java.util.Collections;
    -import java.util.LinkedHashMap;
    -import java.util.Map;
    -
    -import org.eclipse.tm.internal.terminal.control.impl.TerminalPlugin;
    -import org.eclipse.tm.internal.terminal.provisional.api.Logger;
    -
    -/**
    - * @author scharf
    - * Flyweight
    - * Threadsafe.
    - *
    - */
    -// TODO add an Object for user data, use weak map to keep track of styles with associated
    -// user data
    -public class Style {
    -	private final StyleColor fForground;
    -	private final StyleColor fBackground;
    -	private final boolean fBold;
    -	private final boolean fBlink;
    -	private final boolean fUnderline;
    -	private final boolean fReverse;
    -	private final static Map fgStyles = Collections.synchronizedMap(new LinkedHashMap() {
    -		@Override
    -		protected boolean removeEldestEntry(Map.Entry eldest) {
    -			int size = size();
    -			boolean removeEldest = size >= 1000;
    -			if (TerminalPlugin.isOptionEnabled(Logger.TRACE_DEBUG_LOG_VT100BACKEND)) {
    -				if (removeEldest) {
    -					Logger.log("Removing eldest Style from style cache, size = " + size); //$NON-NLS-1$
    -				} else {
    -					Logger.log("Leaving eldest Style in style cache, size = " + size); //$NON-NLS-1$
    -				}
    -			}
    -			return removeEldest;
    -		}
    -	});
    -
    -	private Style(StyleColor forground, StyleColor background, boolean bold, boolean blink, boolean underline,
    -			boolean reverse) {
    -		fForground = forground;
    -		fBackground = background;
    -		fBold = bold;
    -		fBlink = blink;
    -		fUnderline = underline;
    -		fReverse = reverse;
    -	}
    -
    -	public static Style getStyle(StyleColor forground, StyleColor background, boolean bold, boolean blink,
    -			boolean underline, boolean reverse) {
    -		Style style = new Style(forground, background, bold, blink, underline, reverse);
    -		// If set had a computeIfAbsent we would use a set, instead just store 1-2-1 mapping
    -		return fgStyles.computeIfAbsent(style, (s) -> style);
    -	}
    -
    -	public static Style getStyle(String forground, String background) {
    -		return getStyle(StyleColor.getStyleColor(forground), StyleColor.getStyleColor(background), false, false, false,
    -				false);
    -	}
    -
    -	public static Style getStyle(StyleColor forground, StyleColor background) {
    -		return getStyle(forground, background, false, false, false, false);
    -	}
    -
    -	public Style setForground(StyleColor forground) {
    -		return getStyle(forground, fBackground, fBold, fBlink, fUnderline, fReverse);
    -	}
    -
    -	public Style setBackground(StyleColor background) {
    -		return getStyle(fForground, background, fBold, fBlink, fUnderline, fReverse);
    -	}
    -
    -	public Style setForground(String colorName) {
    -		return getStyle(StyleColor.getStyleColor(colorName), fBackground, fBold, fBlink, fUnderline, fReverse);
    -	}
    -
    -	public Style setBackground(String colorName) {
    -		return getStyle(fForground, StyleColor.getStyleColor(colorName), fBold, fBlink, fUnderline, fReverse);
    -	}
    -
    -	public Style setBold(boolean bold) {
    -		return getStyle(fForground, fBackground, bold, fBlink, fUnderline, fReverse);
    -	}
    -
    -	public Style setBlink(boolean blink) {
    -		return getStyle(fForground, fBackground, fBold, blink, fUnderline, fReverse);
    -	}
    -
    -	public Style setUnderline(boolean underline) {
    -		return getStyle(fForground, fBackground, fBold, fBlink, underline, fReverse);
    -	}
    -
    -	public Style setReverse(boolean reverse) {
    -		return getStyle(fForground, fBackground, fBold, fBlink, fUnderline, reverse);
    -	}
    -
    -	public StyleColor getBackground() {
    -		return fBackground;
    -	}
    -
    -	public boolean isBlink() {
    -		return fBlink;
    -	}
    -
    -	public boolean isBold() {
    -		return fBold;
    -	}
    -
    -	public StyleColor getForground() {
    -		return fForground;
    -	}
    -
    -	public boolean isReverse() {
    -		return fReverse;
    -	}
    -
    -	public boolean isUnderline() {
    -		return fUnderline;
    -	}
    -
    -	@Override
    -	public int hashCode() {
    -		final int prime = 31;
    -		int result = 1;
    -		result = prime * result + ((fBackground == null) ? 0 : fBackground.hashCode());
    -		result = prime * result + (fBlink ? 1231 : 1237);
    -		result = prime * result + (fBold ? 1231 : 1237);
    -		result = prime * result + ((fForground == null) ? 0 : fForground.hashCode());
    -		result = prime * result + (fReverse ? 1231 : 1237);
    -		result = prime * result + (fUnderline ? 1231 : 1237);
    -		return result;
    -	}
    -
    -	@Override
    -	public boolean equals(Object obj) {
    -		if (this == obj)
    -			return true;
    -		if (obj == null)
    -			return false;
    -		if (getClass() != obj.getClass())
    -			return false;
    -		final Style other = (Style) obj;
    -		// background == is the same as equals
    -		if (fBackground != other.fBackground)
    -			return false;
    -		if (fBlink != other.fBlink)
    -			return false;
    -		if (fBold != other.fBold)
    -			return false;
    -		if (fForground != other.fForground)
    -			return false;
    -		if (fReverse != other.fReverse)
    -			return false;
    -		if (fUnderline != other.fUnderline)
    -			return false;
    -		return true;
    -	}
    -
    -	@Override
    -	public String toString() {
    -		StringBuffer result = new StringBuffer();
    -		result.append("Style(foreground="); //$NON-NLS-1$
    -		result.append(fForground);
    -		result.append(", background="); //$NON-NLS-1$
    -		result.append(fBackground);
    -		if (fBlink)
    -			result.append(", blink"); //$NON-NLS-1$
    -		if (fBold)
    -			result.append(", bold"); //$NON-NLS-1$
    -		if (fBlink)
    -			result.append(", blink"); //$NON-NLS-1$
    -		if (fReverse)
    -			result.append(", reverse"); //$NON-NLS-1$
    -		if (fUnderline)
    -			result.append(", underline"); //$NON-NLS-1$
    -		result.append(")"); //$NON-NLS-1$
    -		return result.toString();
    -	}
    -
    -}
    \ No newline at end of file
    diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/StyleColor.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/StyleColor.java
    deleted file mode 100644
    index be4611fb880..00000000000
    --- a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/StyleColor.java
    +++ /dev/null
    @@ -1,56 +0,0 @@
    -/*******************************************************************************
    - * Copyright (c) 2007, 2018 Wind River Systems, Inc. and others.
    - * All rights reserved. This program and the accompanying materials
    - * are made available under the terms of the Eclipse Public License 2.0
    - * which accompanies this distribution, and is available at
    - * https://www.eclipse.org/legal/epl-2.0/
    - *
    - * Contributors:
    - * Michael Scharf (Wind River) - initial API and implementation
    - *******************************************************************************/
    -package org.eclipse.tm.terminal.model;
    -
    -import java.util.HashMap;
    -import java.util.Map;
    -
    -/**
    - *
    - * Flyweight
    - * Threadsafe.
    - */
    -public class StyleColor {
    -	private final static Map fgStyleColors = new HashMap<>();
    -	final String fName;
    -
    -	/**
    -	 * @param name the name of the color. It is up to the UI to associate a
    -	 * named color with a visual representation
    -	 * @return a StyleColor
    -	 */
    -	public static StyleColor getStyleColor(String name) {
    -		StyleColor result;
    -		synchronized (fgStyleColors) {
    -			result = fgStyleColors.get(name);
    -			if (result == null) {
    -				result = new StyleColor(name);
    -				fgStyleColors.put(name, result);
    -			}
    -		}
    -		return result;
    -	}
    -
    -	// nobody except the factory method is allowed to instantiate this class!
    -	private StyleColor(String name) {
    -		fName = name;
    -	}
    -
    -	public String getName() {
    -		return fName;
    -	}
    -
    -	@Override
    -	public String toString() {
    -		return fName;
    -	}
    -	// no need to override equals and hashCode, because Object uses object identity
    -}
    \ No newline at end of file
    diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/TerminalColor.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/TerminalColor.java
    new file mode 100644
    index 00000000000..6ed0a1e89a3
    --- /dev/null
    +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/TerminalColor.java
    @@ -0,0 +1,168 @@
    +/*******************************************************************************
    + * Copyright (c) 2020 Kichwa Coders Canada Inc. and others.
    + * All rights reserved. This program and the accompanying materials
    + * are made available under the terms of the Eclipse Public License 2.0
    + * which accompanies this distribution, and is available at
    + * https://www.eclipse.org/legal/epl-2.0/
    + *
    + * SPDX-License-Identifier: EPL-2.0
    + *******************************************************************************/
    +package org.eclipse.tm.terminal.model;
    +
    +import org.eclipse.core.runtime.Assert;
    +import org.eclipse.jface.resource.ColorDescriptor;
    +import org.eclipse.swt.graphics.Color;
    +import org.eclipse.swt.graphics.RGB;
    +import org.eclipse.swt.widgets.Display;
    +
    +/**
    + * Colors that can be used in the Terminal are represented by this class. The enum contains
    + * the colors with well known names defined by the ANSI Escape Sequences, plus other colors needed
    + * to render a display (such as Background color).
    + *
    + * @since 5.0
    + */
    +public enum TerminalColor {
    +	BLACK, //
    +	RED, //
    +	GREEN, //
    +	YELLOW, //
    +	BLUE, //
    +	MAGENTA, //
    +	CYAN, //
    +	WHITE, //
    +
    +	BRIGHT_BLACK, //
    +	BRIGHT_RED, //
    +	BRIGHT_GREEN, //
    +	BRIGHT_YELLOW, //
    +	BRIGHT_BLUE, //
    +	BRIGHT_MAGENTA, //
    +	BRIGHT_CYAN, //
    +	BRIGHT_WHITE, //
    +
    +	FOREGROUND, //
    +	BACKGROUND, //
    +	SELECTION_FOREGROUND, //
    +	SELECTION_BACKGROUND;
    +
    +	/**
    +	 * The first 16-items in the 8-bit lookup table map to the user changeable colors
    +	 * above, so this array handles that mapping.
    +	 */
    +	private final static TerminalColor table8bitIndexedTerminalColors[] = new TerminalColor[16];
    +
    +	/**
    +	 * The rest of the colors in the lookup table (240 colors) are pre-defined by
    +	 * the standard. The colors that fill this table were derived from
    +	 * https://en.wikipedia.org/wiki/ANSI_escape_code#8-bit which was more
    +	 * digestible and accessible than the underlying ITU and ISO standards.
    +	 */
    +	private final static RGB table8bitIndexedRGB[] = new RGB[256 - 16];
    +
    +	/**
    +	 * Color to use instead when inverted color is selected
    +	 */
    +	private TerminalColor invertColor;
    +
    +	/**
    +	 * Color to use instead when bright color is selected
    +	 */
    +	private TerminalColor brightColor;
    +
    +	/**
    +	 * Pre-calculate the lookup tables for 8-bit colors, inverses and equivalent brights.
    +	 */
    +	static {
    +		TerminalColor[] values = TerminalColor.values();
    +
    +		// 8-bit color lookup tables
    +		{
    +			int index = 0;
    +			for (; index < 16; index++) {
    +				TerminalColor c = values[index];
    +				table8bitIndexedTerminalColors[index] = c;
    +			}
    +
    +			int vals[] = { 0x00, 0x5f, 0x87, 0xaf, 0xd7, 0xff };
    +			Assert.isTrue(index == 16);
    +			for (int r = 0; r < 6; r++) {
    +				for (int g = 0; g < 6; g++) {
    +					for (int b = 0; b < 6; b++) {
    +						table8bitIndexedRGB[index++ - 16] = new RGB(vals[r], vals[g], vals[b]);
    +					}
    +				}
    +			}
    +
    +			int greys[] = { 0x08, 0x12, 0x1c, 0x26, 0x30, 0x3a, 0x44, 0x4e, 0x58, 0x62, 0x6c, 0x76, 0x80, 0x8a, 0x94,
    +					0x9e, 0xa8, 0xb2, 0xbc, 0xc6, 0xd0, 0xda, 0xe4, 0xee };
    +
    +			Assert.isTrue(index == 232);
    +			for (int g : greys) {
    +				table8bitIndexedRGB[index++ - 16] = new RGB(g, g, g);
    +			}
    +			Assert.isTrue(index == 256);
    +		}
    +
    +		// bright equivalents
    +		{
    +			// The second set of 8 colors are the bright of the first 8.
    +			for (int i = 0; i < 8; i++) {
    +				values[i].brightColor = values[i + 8];
    +			}
    +			// The rest of the colors are not brightened
    +			for (int i = 8; i < values.length; i++) {
    +				values[i].brightColor = values[i];
    +			}
    +		}
    +
    +		// inverses
    +		{
    +			// by default make all colors invert of themself
    +			for (int i = 0; i < values.length; i++) {
    +				values[i].invertColor = values[i];
    +			}
    +			// and then mark the colors that are actual inverts
    +			inverts(BLACK, WHITE);
    +			inverts(BRIGHT_BLACK, BRIGHT_WHITE);
    +			inverts(BACKGROUND, FOREGROUND);
    +		}
    +
    +	}
    +
    +	private static void inverts(TerminalColor a, TerminalColor b) {
    +		a.invertColor = b;
    +		b.invertColor = a;
    +	}
    +
    +	/**
    +	 * Return a new color for the given color with inversions or brightness attributes applied.
    +	 *
    +	 * @param invert For invertible colors, return the inverse (typically white <-> black)
    +	 * @param bright returns the brighter version of the color if one is available
    +	 * @return {@link ColorDescriptor} that a {@link Color} can be made from
    +	 *     using {@link ColorDescriptor#createColor(org.eclipse.swt.graphics.Device)}
    +	 * @throws NullPointerException if there is no current {@link Display}
    +	 */
    +	public TerminalColor convertColor(boolean invert, boolean bright) {
    +		TerminalColor selected = this;
    +		// it doesn't matter which order you apply bright and invert, you get to
    +		// the same color when both are set
    +		if (invert) {
    +			selected = selected.invertColor;
    +		}
    +		if (bright) {
    +			selected = selected.brightColor;
    +		}
    +		return selected;
    +	}
    +
    +	/**
    +	 * FOR TEST ONLY.
    +	 *
    +	 * @noreference This enum method is not intended to be referenced by clients.
    +	 */
    +	public static TerminalColor getForTest(int c) {
    +		return TerminalColor.values()[c % TerminalColor.values().length];
    +	}
    +}
    diff --git a/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/TerminalStyle.java b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/TerminalStyle.java
    new file mode 100644
    index 00000000000..f63d0f0be2b
    --- /dev/null
    +++ b/terminal/plugins/org.eclipse.tm.terminal.control/src/org/eclipse/tm/terminal/model/TerminalStyle.java
    @@ -0,0 +1,193 @@
    +/*******************************************************************************
    + * Copyright (c) 2007, 2020 Wind River Systems, Inc. and others.
    + * All rights reserved. This program and the accompanying materials
    + * are made available under the terms of the Eclipse Public License 2.0
    + * which accompanies this distribution, and is available at
    + * https://www.eclipse.org/legal/epl-2.0/
    + *
    + * Contributors:
    + * Michael Scharf (Wind River) - initial API and implementation
    + *******************************************************************************/
    +package org.eclipse.tm.terminal.model;
    +
    +import java.util.Collections;
    +import java.util.LinkedHashMap;
    +import java.util.Map;
    +
    +import org.eclipse.tm.internal.terminal.control.impl.TerminalPlugin;
    +import org.eclipse.tm.internal.terminal.provisional.api.Logger;
    +
    +/**
    + * @author scharf
    + * Flyweight
    + * Threadsafe.
    + * @since 5.0
    + *
    + */
    +// TODO add an Object for user data, use weak map to keep track of styles with associated
    +// user data
    +public class TerminalStyle {
    +	private final TerminalColor fForegroundTerminalColor;
    +	private final TerminalColor fBackgroundTerminalColor;
    +	private final boolean fBold;
    +	private final boolean fBlink;
    +	private final boolean fUnderline;
    +	private final boolean fReverse;
    +	private final static Map fgStyles = Collections
    +			.synchronizedMap(new LinkedHashMap() {
    +				@Override
    +				protected boolean removeEldestEntry(Map.Entry eldest) {
    +					int size = size();
    +					boolean removeEldest = size >= 1000;
    +					if (TerminalPlugin.isOptionEnabled(Logger.TRACE_DEBUG_LOG_VT100BACKEND)) {
    +						if (removeEldest) {
    +							Logger.log("Removing eldest Style from style cache, size = " + size); //$NON-NLS-1$
    +						} else {
    +							Logger.log("Leaving eldest Style in style cache, size = " + size); //$NON-NLS-1$
    +						}
    +					}
    +					return removeEldest;
    +				}
    +			});
    +
    +	private TerminalStyle(TerminalColor foregroundTerminalColor, TerminalColor backgroundTerminalColor, boolean bold,
    +			boolean blink, boolean underline, boolean reverse) {
    +		fForegroundTerminalColor = foregroundTerminalColor;
    +		fBackgroundTerminalColor = backgroundTerminalColor;
    +		fBold = bold;
    +		fBlink = blink;
    +		fUnderline = underline;
    +		fReverse = reverse;
    +	}
    +
    +	public static TerminalStyle getStyle(TerminalColor foregroundTerminalColor, TerminalColor backgroundTerminalColor,
    +			boolean bold, boolean blink, boolean underline, boolean reverse) {
    +		TerminalStyle style = new TerminalStyle(foregroundTerminalColor, backgroundTerminalColor, bold, blink,
    +				underline, reverse);
    +		// If set had a computeIfAbsent we would use a set, instead just store 1-2-1 mapping
    +		return fgStyles.computeIfAbsent(style, (s) -> style);
    +	}
    +
    +	public static TerminalStyle getDefaultStyle() {
    +		return getStyle(TerminalColor.FOREGROUND, TerminalColor.BACKGROUND);
    +	}
    +
    +	public static TerminalStyle getStyle(TerminalColor foregroundTerminalColor, TerminalColor backgroundTerminalColor) {
    +		return getStyle(foregroundTerminalColor, backgroundTerminalColor, false, false, false, false);
    +	}
    +
    +	public TerminalStyle setForeground(TerminalColor foregroundTerminalColor) {
    +		return getStyle(foregroundTerminalColor, fBackgroundTerminalColor, fBold, fBlink, fUnderline, fReverse);
    +	}
    +
    +	public TerminalStyle setBackground(TerminalColor backgroundTerminalColor) {
    +		return getStyle(fForegroundTerminalColor, backgroundTerminalColor, fBold, fBlink, fUnderline, fReverse);
    +	}
    +
    +	public TerminalStyle setForeground(TerminalStyle other) {
    +		return getStyle(other.fForegroundTerminalColor, fBackgroundTerminalColor, fBold, fBlink, fUnderline, fReverse);
    +	}
    +
    +	public TerminalStyle setBackground(TerminalStyle other) {
    +		return getStyle(fForegroundTerminalColor, other.fBackgroundTerminalColor, fBold, fBlink, fUnderline, fReverse);
    +	}
    +
    +	public TerminalStyle setBold(boolean bold) {
    +		return getStyle(fForegroundTerminalColor, fBackgroundTerminalColor, bold, fBlink, fUnderline, fReverse);
    +	}
    +
    +	public TerminalStyle setBlink(boolean blink) {
    +		return getStyle(fForegroundTerminalColor, fBackgroundTerminalColor, fBold, blink, fUnderline, fReverse);
    +	}
    +
    +	public TerminalStyle setUnderline(boolean underline) {
    +		return getStyle(fForegroundTerminalColor, fBackgroundTerminalColor, fBold, fBlink, underline, fReverse);
    +	}
    +
    +	public TerminalStyle setReverse(boolean reverse) {
    +		return getStyle(fForegroundTerminalColor, fBackgroundTerminalColor, fBold, fBlink, fUnderline, reverse);
    +	}
    +
    +	public TerminalColor getForegroundTerminalColor() {
    +		return fForegroundTerminalColor;
    +	}
    +
    +	public TerminalColor getBackgroundTerminalColor() {
    +		return fBackgroundTerminalColor;
    +	}
    +
    +	public boolean isBlink() {
    +		return fBlink;
    +	}
    +
    +	public boolean isBold() {
    +		return fBold;
    +	}
    +
    +	public boolean isReverse() {
    +		return fReverse;
    +	}
    +
    +	public boolean isUnderline() {
    +		return fUnderline;
    +	}
    +
    +	@Override
    +	public int hashCode() {
    +		final int prime = 31;
    +		int result = 1;
    +		result = prime * result + ((fBackgroundTerminalColor == null) ? 0 : fBackgroundTerminalColor.hashCode());
    +		result = prime * result + (fBlink ? 1231 : 1237);
    +		result = prime * result + (fBold ? 1231 : 1237);
    +		result = prime * result + ((fForegroundTerminalColor == null) ? 0 : fForegroundTerminalColor.hashCode());
    +		result = prime * result + (fReverse ? 1231 : 1237);
    +		result = prime * result + (fUnderline ? 1231 : 1237);
    +		return result;
    +	}
    +
    +	@Override
    +	public boolean equals(Object obj) {
    +		if (this == obj)
    +			return true;
    +		if (obj == null)
    +			return false;
    +		if (getClass() != obj.getClass())
    +			return false;
    +		TerminalStyle other = (TerminalStyle) obj;
    +		if (fBackgroundTerminalColor != other.fBackgroundTerminalColor)
    +			return false;
    +		if (fBlink != other.fBlink)
    +			return false;
    +		if (fBold != other.fBold)
    +			return false;
    +		if (fForegroundTerminalColor != other.fForegroundTerminalColor)
    +			return false;
    +		if (fReverse != other.fReverse)
    +			return false;
    +		if (fUnderline != other.fUnderline)
    +			return false;
    +		return true;
    +	}
    +
    +	@Override
    +	public String toString() {
    +		StringBuffer result = new StringBuffer();
    +		result.append("Style(foreground="); //$NON-NLS-1$
    +		result.append(fForegroundTerminalColor);
    +		result.append(", background="); //$NON-NLS-1$
    +		result.append(fBackgroundTerminalColor);
    +		if (fBlink)
    +			result.append(", blink"); //$NON-NLS-1$
    +		if (fBold)
    +			result.append(", bold"); //$NON-NLS-1$
    +		if (fBlink)
    +			result.append(", blink"); //$NON-NLS-1$
    +		if (fReverse)
    +			result.append(", reverse"); //$NON-NLS-1$
    +		if (fUnderline)
    +			result.append(", underline"); //$NON-NLS-1$
    +		result.append(")"); //$NON-NLS-1$
    +		return result.toString();
    +	}
    +
    +}
    diff --git a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/connector/TerminalConnectorPluginTest.java b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/connector/TerminalConnectorPluginTest.java
    index 68e98bb2606..b5899dcd8e1 100644
    --- a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/connector/TerminalConnectorPluginTest.java
    +++ b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/connector/TerminalConnectorPluginTest.java
    @@ -14,13 +14,13 @@
     
     package org.eclipse.tm.internal.terminal.connector;
     
    -import junit.framework.TestCase;
    -
     import org.eclipse.core.runtime.Platform;
     import org.eclipse.tm.internal.terminal.connector.TerminalConnectorTest.ConnectorMock;
     import org.eclipse.tm.internal.terminal.connector.TerminalConnectorTest.SimpleFactory;
     import org.eclipse.tm.internal.terminal.connector.TerminalConnectorTest.TerminalControlMock;
     
    +import junit.framework.TestCase;
    +
     /**
      * Testcase for TerminalConnector that must run as a JUnit plug-in test.
      */
    diff --git a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/emulator/VT100EmulatorBackendTest.java b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/emulator/VT100EmulatorBackendTest.java
    index 81f93c9c063..3be4b5209ca 100644
    --- a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/emulator/VT100EmulatorBackendTest.java
    +++ b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/emulator/VT100EmulatorBackendTest.java
    @@ -16,13 +16,16 @@
      *******************************************************************************/
     package org.eclipse.tm.internal.terminal.emulator;
     
    -import junit.framework.TestCase;
    +import static org.eclipse.tm.terminal.model.TerminalColor.BLACK;
    +import static org.eclipse.tm.terminal.model.TerminalColor.WHITE;
     
     import org.eclipse.tm.internal.terminal.model.TerminalTextDataStore;
     import org.eclipse.tm.internal.terminal.model.TerminalTextTestHelper;
     import org.eclipse.tm.terminal.model.ITerminalTextData;
     import org.eclipse.tm.terminal.model.ITerminalTextDataReadOnly;
    -import org.eclipse.tm.terminal.model.Style;
    +import org.eclipse.tm.terminal.model.TerminalStyle;
    +
    +import junit.framework.TestCase;
     
     public class VT100EmulatorBackendTest extends TestCase {
     
    @@ -592,10 +595,10 @@ public class VT100EmulatorBackendTest extends TestCase {
     	public void testGetDefaultStyle() {
     		ITerminalTextData term = makeITerminalTextData();
     		IVT100EmulatorBackend vt100 = makeBakend(term);
    -		Style style = Style.getStyle("white", "black");
    +		TerminalStyle style = TerminalStyle.getStyle(WHITE, BLACK);
     		vt100.setDefaultStyle(style);
     		assertSame(style, vt100.getDefaultStyle());
    -		Style style2 = style.setBold(true);
    +		TerminalStyle style2 = style.setBold(true);
     		vt100.setDefaultStyle(style2);
     		assertSame(style2, vt100.getDefaultStyle());
     	}
    @@ -603,10 +606,10 @@ public class VT100EmulatorBackendTest extends TestCase {
     	public void testGetStyle() {
     		ITerminalTextData term = makeITerminalTextData();
     		IVT100EmulatorBackend vt100 = makeBakend(term);
    -		Style style = Style.getStyle("white", "black");
    +		TerminalStyle style = TerminalStyle.getStyle(WHITE, BLACK);
     		vt100.setStyle(style);
     		assertSame(style, vt100.getStyle());
    -		Style style2 = style.setBold(true);
    +		TerminalStyle style2 = style.setBold(true);
     		vt100.setStyle(style2);
     		assertSame(style2, vt100.getStyle());
     	}
    @@ -668,7 +671,6 @@ public class VT100EmulatorBackendTest extends TestCase {
     		assertEqualsTerm("klmn\n" + "opqr\n" + "sABC\n" + "DEFG\n" + "HIJK\n" + "L   ", toMultiLineText(term));
     		assertEquals(2, vt100.getCursorLine());
     		assertEquals(1, vt100.getCursorColumn());
    -
     	}
     
     	public void testProcessNewline() {
    diff --git a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/AbstractITerminalTextDataTest.java b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/AbstractITerminalTextDataTest.java
    index ebff202f013..9a85f508043 100644
    --- a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/AbstractITerminalTextDataTest.java
    +++ b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/AbstractITerminalTextDataTest.java
    @@ -14,8 +14,8 @@ package org.eclipse.tm.internal.terminal.model;
     import org.eclipse.tm.terminal.model.ITerminalTextData;
     import org.eclipse.tm.terminal.model.ITerminalTextDataReadOnly;
     import org.eclipse.tm.terminal.model.LineSegment;
    -import org.eclipse.tm.terminal.model.Style;
    -import org.eclipse.tm.terminal.model.StyleColor;
    +import org.eclipse.tm.terminal.model.TerminalColor;
    +import org.eclipse.tm.terminal.model.TerminalStyle;
     
     import junit.framework.TestCase;
     
    @@ -199,9 +199,9 @@ abstract public class AbstractITerminalTextDataTest extends TestCase {
     	}
     
     	public void testGetLineSegments() {
    -		Style s1 = getDefaultStyle();
    -		Style s2 = s1.setBold(true);
    -		Style s3 = s1.setUnderline(true);
    +		TerminalStyle s1 = getDefaultStyle();
    +		TerminalStyle s2 = s1.setBold(true);
    +		TerminalStyle s3 = s1.setUnderline(true);
     		ITerminalTextData term = makeITerminalTextData();
     		term.setDimensions(8, 8);
     		LineSegment[] segments;
    @@ -273,7 +273,7 @@ abstract public class AbstractITerminalTextDataTest extends TestCase {
     
     	}
     
    -	void assertSegment(int col, String text, Style style, LineSegment segment) {
    +	void assertSegment(int col, String text, TerminalStyle style, LineSegment segment) {
     		assertEquals(col, segment.getColumn());
     		assertEqualsTerm(text, segment.getText());
     		assertEquals(style, segment.getStyle());
    @@ -333,26 +333,25 @@ abstract public class AbstractITerminalTextDataTest extends TestCase {
     
     	public void testGetStyle() {
     		ITerminalTextData term = makeITerminalTextData();
    -		Style style = getDefaultStyle();
    +		TerminalStyle style = getDefaultStyle();
     		term.setDimensions(6, 3);
     		for (int line = 0; line < term.getHeight(); line++) {
     			for (int column = 0; column < term.getWidth(); column++) {
     				char c = (char) ('a' + column + line);
    -				term.setChar(line, column, c, style.setForground(StyleColor.getStyleColor("" + c)));
    +				term.setChar(line, column, c, style.setForeground(TerminalColor.getForTest(c)));
     			}
     		}
     		for (int line = 0; line < term.getHeight(); line++) {
     			for (int column = 0; column < term.getWidth(); column++) {
     				char c = (char) ('a' + column + line);
    -				assertSame(style.setForground(StyleColor.getStyleColor("" + c)), term.getStyle(line, column));
    +				assertSame(style.setForeground(TerminalColor.getForTest(c)), term.getStyle(line, column));
     			}
     		}
     
     	}
     
    -	protected Style getDefaultStyle() {
    -		return Style.getStyle(StyleColor.getStyleColor("fg"), StyleColor.getStyleColor("bg"), false, false, false,
    -				false);
    +	protected TerminalStyle getDefaultStyle() {
    +		return TerminalStyle.getDefaultStyle();
     	}
     
     	public void testSetChar() {
    diff --git a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/SnapshotChangesTest.java b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/SnapshotChangesTest.java
    index da40878a373..9a95ba2f8e8 100644
    --- a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/SnapshotChangesTest.java
    +++ b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/SnapshotChangesTest.java
    @@ -12,10 +12,10 @@
      *******************************************************************************/
     package org.eclipse.tm.internal.terminal.model;
     
    -import junit.framework.TestCase;
    -
     import org.eclipse.tm.terminal.model.ITerminalTextData;
     
    +import junit.framework.TestCase;
    +
     public class SnapshotChangesTest extends TestCase {
     	/**
     	 * @param change
    diff --git a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataPerformanceTest.java b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataPerformanceTest.java
    index 1440900c69c..6bfbb44237c 100644
    --- a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataPerformanceTest.java
    +++ b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataPerformanceTest.java
    @@ -12,8 +12,7 @@ package org.eclipse.tm.internal.terminal.model;
     
     import org.eclipse.tm.terminal.model.ITerminalTextData;
     import org.eclipse.tm.terminal.model.ITerminalTextDataSnapshot;
    -import org.eclipse.tm.terminal.model.Style;
    -import org.eclipse.tm.terminal.model.StyleColor;
    +import org.eclipse.tm.terminal.model.TerminalStyle;
     
     import junit.framework.TestCase;
     
    @@ -46,8 +45,7 @@ public class TerminalTextDataPerformanceTest extends TestCase {
     	}
     
     	private void method0(ITerminalTextData term, String label) {
    -		Style style = Style.getStyle(StyleColor.getStyleColor("fg"), StyleColor.getStyleColor("bg"), false, false,
    -				false, false);
    +		TerminalStyle style = TerminalStyle.getDefaultStyle();
     		initPerformance(term);
     		String s = "This is a test string";
     		long n = 0;
    @@ -90,8 +88,7 @@ public class TerminalTextDataPerformanceTest extends TestCase {
     	}
     
     	private void method1(ITerminalTextData term, String label) {
    -		Style style = Style.getStyle(StyleColor.getStyleColor("fg"), StyleColor.getStyleColor("bg"), false, false,
    -				false, false);
    +		TerminalStyle style = TerminalStyle.getDefaultStyle();
     		initPerformance(term);
     		String s = "This is a test string";
     		long n = 0;
    @@ -115,8 +112,7 @@ public class TerminalTextDataPerformanceTest extends TestCase {
     
     	public void testPerformance2() {
     		TerminalTextData term = new TerminalTextData();
    -		Style style = Style.getStyle(StyleColor.getStyleColor("fg"), StyleColor.getStyleColor("bg"), false, false,
    -				false, false);
    +		TerminalStyle style = TerminalStyle.getDefaultStyle();
     		initPerformance(term);
     		TerminalTextData copy = new TerminalTextData();
     		copy.copy(term);
    @@ -144,8 +140,7 @@ public class TerminalTextDataPerformanceTest extends TestCase {
     	public void testPerformance2a() {
     		TerminalTextData term = new TerminalTextData();
     		ITerminalTextDataSnapshot snapshot = term.makeSnapshot();
    -		Style style = Style.getStyle(StyleColor.getStyleColor("fg"), StyleColor.getStyleColor("bg"), false, false,
    -				false, false);
    +		TerminalStyle style = TerminalStyle.getDefaultStyle();
     		initPerformance(term);
     		TerminalTextData copy = new TerminalTextData();
     		copy.copy(term);
    @@ -178,8 +173,7 @@ public class TerminalTextDataPerformanceTest extends TestCase {
     		ITerminalTextDataSnapshot snapshot = term.makeSnapshot();
     		N = 0;
     		snapshot.addListener(snapshot1 -> N++);
    -		Style style = Style.getStyle(StyleColor.getStyleColor("fg"), StyleColor.getStyleColor("bg"), false, false,
    -				false, false);
    +		TerminalStyle style = TerminalStyle.getDefaultStyle();
     		initPerformance(term);
     		TerminalTextData copy = new TerminalTextData();
     		copy.copy(term);
    @@ -207,8 +201,7 @@ public class TerminalTextDataPerformanceTest extends TestCase {
     
     	public void testPerformance3() {
     		TerminalTextData term = new TerminalTextData();
    -		Style style = Style.getStyle(StyleColor.getStyleColor("fg"), StyleColor.getStyleColor("bg"), false, false,
    -				false, false);
    +		TerminalStyle style = TerminalStyle.getDefaultStyle();
     		initPerformance(term);
     		TerminalTextData copy = new TerminalTextData();
     		copy.copy(term);
    diff --git a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataSnapshotTest.java b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataSnapshotTest.java
    index c5e8fb2abcf..775f4d2e703 100644
    --- a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataSnapshotTest.java
    +++ b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataSnapshotTest.java
    @@ -13,8 +13,8 @@ package org.eclipse.tm.internal.terminal.model;
     import org.eclipse.tm.terminal.model.ITerminalTextData;
     import org.eclipse.tm.terminal.model.ITerminalTextDataReadOnly;
     import org.eclipse.tm.terminal.model.ITerminalTextDataSnapshot;
    -import org.eclipse.tm.terminal.model.Style;
    -import org.eclipse.tm.terminal.model.StyleColor;
    +import org.eclipse.tm.terminal.model.TerminalColor;
    +import org.eclipse.tm.terminal.model.TerminalStyle;
     
     import junit.framework.TestCase;
     
    @@ -317,13 +317,12 @@ public class TerminalTextDataSnapshotTest extends TestCase {
     	//
     	public void testGetStyle() {
     		ITerminalTextData term = makeITerminalTextData();
    -		Style style = Style.getStyle(StyleColor.getStyleColor("fg"), StyleColor.getStyleColor("bg"), false, false,
    -				false, false);
    +		TerminalStyle style = TerminalStyle.getDefaultStyle();
     		term.setDimensions(6, 3);
     		for (int line = 0; line < term.getHeight(); line++) {
     			for (int column = 0; column < term.getWidth(); column++) {
     				char c = (char) ('a' + column + line);
    -				term.setChar(line, column, c, style.setForground(StyleColor.getStyleColor("" + c)));
    +				term.setChar(line, column, c, style.setForeground(TerminalColor.getForTest(c)));
     			}
     		}
     		ITerminalTextDataSnapshot snapshot = term.makeSnapshot();
    @@ -332,7 +331,7 @@ public class TerminalTextDataSnapshotTest extends TestCase {
     		for (int line = 0; line < term.getHeight(); line++) {
     			for (int column = 0; column < term.getWidth(); column++) {
     				char c = (char) ('a' + column + line);
    -				assertSame(style.setForground(StyleColor.getStyleColor("" + c)), snapshot.getStyle(line, column));
    +				assertSame(style.setForeground(TerminalColor.getForTest(c)), snapshot.getStyle(line, column));
     			}
     		}
     
    diff --git a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataSnapshotWindowTest.java b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataSnapshotWindowTest.java
    index b8c980d4cba..c0988c78369 100644
    --- a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataSnapshotWindowTest.java
    +++ b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataSnapshotWindowTest.java
    @@ -10,12 +10,12 @@
      *******************************************************************************/
     package org.eclipse.tm.internal.terminal.model;
     
    -import junit.framework.TestCase;
    -
     import org.eclipse.tm.terminal.model.ITerminalTextData;
     import org.eclipse.tm.terminal.model.ITerminalTextDataReadOnly;
     import org.eclipse.tm.terminal.model.ITerminalTextDataSnapshot;
     
    +import junit.framework.TestCase;
    +
     public class TerminalTextDataSnapshotWindowTest extends TestCase {
     	String toMultiLineText(ITerminalTextDataReadOnly term) {
     		return TerminalTextTestHelper.toMultiLineText(term);
    diff --git a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataWindowTest.java b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataWindowTest.java
    index 4dedebdc9ff..a0a12dd8313 100644
    --- a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataWindowTest.java
    +++ b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/TerminalTextDataWindowTest.java
    @@ -17,8 +17,8 @@ import java.util.ArrayList;
     
     import org.eclipse.tm.terminal.model.ITerminalTextData;
     import org.eclipse.tm.terminal.model.LineSegment;
    -import org.eclipse.tm.terminal.model.Style;
    -import org.eclipse.tm.terminal.model.StyleColor;
    +import org.eclipse.tm.terminal.model.TerminalColor;
    +import org.eclipse.tm.terminal.model.TerminalStyle;
     
     public class TerminalTextDataWindowTest extends AbstractITerminalTextDataTest {
     	int fOffset;
    @@ -137,9 +137,9 @@ public class TerminalTextDataWindowTest extends AbstractITerminalTextDataTest {
     
     	@Override
     	public void testGetLineSegments() {
    -		Style s1 = getDefaultStyle();
    -		Style s2 = s1.setBold(true);
    -		Style s3 = s1.setUnderline(true);
    +		TerminalStyle s1 = getDefaultStyle();
    +		TerminalStyle s2 = s1.setBold(true);
    +		TerminalStyle s3 = s1.setUnderline(true);
     		ITerminalTextData term = makeITerminalTextData();
     		term.setDimensions(8, 8);
     		LineSegment[] segments;
    @@ -209,20 +209,20 @@ public class TerminalTextDataWindowTest extends AbstractITerminalTextDataTest {
     	@Override
     	public void testGetStyle() {
     		ITerminalTextData term = makeITerminalTextData();
    -		Style style = getDefaultStyle();
    +		TerminalStyle style = getDefaultStyle();
     		term.setDimensions(6, 3);
     		for (int line = 0; line < term.getHeight(); line++) {
     			for (int column = 0; column < term.getWidth(); column++) {
     				char c = (char) ('a' + column + line);
    -				term.setChar(line, column, c, style.setForground(StyleColor.getStyleColor("" + c)));
    +				term.setChar(line, column, c, style.setForeground(TerminalColor.getForTest(c)));
     			}
     		}
     		for (int line = 0; line < term.getHeight(); line++) {
     			for (int column = 0; column < term.getWidth(); column++) {
     				char c = (char) ('a' + column + line);
    -				Style s = null;
    +				TerminalStyle s = null;
     				if (line >= fOffset && line < fOffset + fSize)
    -					s = style.setForground(StyleColor.getStyleColor("" + c));
    +					s = style.setForeground(TerminalColor.getForTest(c));
     				assertSame(s, term.getStyle(line, column));
     			}
     		}
    diff --git a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/TerminalTextTestHelper.java b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/TerminalTextTestHelper.java
    index 945f3299317..7acfc8d7d13 100644
    --- a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/TerminalTextTestHelper.java
    +++ b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/model/TerminalTextTestHelper.java
    @@ -15,8 +15,8 @@ package org.eclipse.tm.internal.terminal.model;
     
     import org.eclipse.tm.terminal.model.ITerminalTextData;
     import org.eclipse.tm.terminal.model.ITerminalTextDataReadOnly;
    -import org.eclipse.tm.terminal.model.Style;
    -import org.eclipse.tm.terminal.model.StyleColor;
    +import org.eclipse.tm.terminal.model.TerminalColor;
    +import org.eclipse.tm.terminal.model.TerminalStyle;
     
     public class TerminalTextTestHelper {
     	static public String toSimple(ITerminalTextDataReadOnly term) {
    @@ -62,12 +62,11 @@ public class TerminalTextTestHelper {
     	 * @param s each character is one line
     	 */
     	static public void fillSimple(ITerminalTextData term, String s) {
    -		Style style = Style.getStyle(StyleColor.getStyleColor("fg"), StyleColor.getStyleColor("bg"), false, false,
    -				false, false);
    +		TerminalStyle style = TerminalStyle.getDefaultStyle();
     		term.setDimensions(s.length(), 1);
     		for (int i = 0; i < s.length(); i++) {
     			char c = s.charAt(i);
    -			term.setChar(i, 0, c, style.setForground(StyleColor.getStyleColor("" + c)));
    +			term.setChar(i, 0, c, style.setForeground(TerminalColor.getForTest(c)));
     		}
     	}
     
    @@ -99,15 +98,14 @@ public class TerminalTextTestHelper {
     	static public void fill(ITerminalTextData term, int column, int line, String s) {
     		int xx = column;
     		int yy = line;
    -		Style style = Style.getStyle(StyleColor.getStyleColor("fg"), StyleColor.getStyleColor("bg"), false, false,
    -				false, false);
    +		TerminalStyle style = TerminalStyle.getDefaultStyle();
     		for (int i = 0; i < s.length(); i++) {
     			char c = s.charAt(i);
     			if (c == '\n') {
     				yy++;
     				xx = column;
     			} else {
    -				term.setChar(yy, xx, c, style.setForground(StyleColor.getStyleColor("" + c)));
    +				term.setChar(yy, xx, c, style.setForeground(TerminalColor.getForTest(c)));
     				xx++;
     			}
     		}
    diff --git a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/test/ui/AbstractLineOrientedDataSource.java b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/test/ui/AbstractLineOrientedDataSource.java
    index a16cc187c94..923b7f8387c 100644
    --- a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/test/ui/AbstractLineOrientedDataSource.java
    +++ b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/test/ui/AbstractLineOrientedDataSource.java
    @@ -11,7 +11,7 @@
     package org.eclipse.tm.internal.terminal.test.ui;
     
     import org.eclipse.tm.terminal.model.ITerminalTextData;
    -import org.eclipse.tm.terminal.model.Style;
    +import org.eclipse.tm.terminal.model.TerminalStyle;
     
     /**
      * Adds line by line
    @@ -20,7 +20,7 @@ import org.eclipse.tm.terminal.model.Style;
     abstract class AbstractLineOrientedDataSource implements IDataSource {
     	abstract public char[] dataSource();
     
    -	abstract public Style getStyle();
    +	abstract public TerminalStyle getStyle();
     
     	abstract public void next();
     
    @@ -28,7 +28,7 @@ abstract class AbstractLineOrientedDataSource implements IDataSource {
     	public int step(ITerminalTextData terminal) {
     		next();
     		char[] chars = dataSource();
    -		Style style = getStyle();
    +		TerminalStyle style = getStyle();
     		int len;
     		// keep the synchronized block short!
     		synchronized (terminal) {
    diff --git a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/test/ui/FastDataSource.java b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/test/ui/FastDataSource.java
    index ad91ee664f6..a2b38d1e0ab 100644
    --- a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/test/ui/FastDataSource.java
    +++ b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/test/ui/FastDataSource.java
    @@ -10,7 +10,7 @@
      *******************************************************************************/
     package org.eclipse.tm.internal.terminal.test.ui;
     
    -import org.eclipse.tm.terminal.model.Style;
    +import org.eclipse.tm.terminal.model.TerminalStyle;
     
     final class FastDataSource extends AbstractLineOrientedDataSource {
     	char lines[][] = new char[][] {
    @@ -25,7 +25,7 @@ final class FastDataSource extends AbstractLineOrientedDataSource {
     	}
     
     	@Override
    -	public Style getStyle() {
    +	public TerminalStyle getStyle() {
     		return null;
     	}
     
    diff --git a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/test/ui/FileDataSource.java b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/test/ui/FileDataSource.java
    index adcd3739add..669fe792c4e 100644
    --- a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/test/ui/FileDataSource.java
    +++ b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/test/ui/FileDataSource.java
    @@ -14,8 +14,7 @@ import java.io.BufferedReader;
     import java.io.FileReader;
     import java.io.IOException;
     
    -import org.eclipse.tm.terminal.model.Style;
    -import org.eclipse.tm.terminal.model.StyleColor;
    +import org.eclipse.tm.terminal.model.TerminalStyle;
     
     /**
      * Reads the file in an infinite loop.
    @@ -29,11 +28,11 @@ final class FileDataSource extends AbstractLineOrientedDataSource {
     
     	String line;
     
    -	Style style;
    +	TerminalStyle style;
     
    -	Style styleNormal = Style.getStyle(StyleColor.getStyleColor("black"), StyleColor.getStyleColor("white"));
    +	TerminalStyle styleNormal = TerminalStyle.getDefaultStyle();
     
    -	Style styleBold = styleNormal.setBold(true);
    +	TerminalStyle styleBold = styleNormal.setBold(true);
     
     	FileDataSource(String file) {
     		fFile = file;
    @@ -45,7 +44,7 @@ final class FileDataSource extends AbstractLineOrientedDataSource {
     	}
     
     	@Override
    -	public Style getStyle() {
    +	public TerminalStyle getStyle() {
     		return style;
     	}
     
    diff --git a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/test/ui/LineCountingDataSource.java b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/test/ui/LineCountingDataSource.java
    index 1747e23192a..5baef90f258 100644
    --- a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/test/ui/LineCountingDataSource.java
    +++ b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/test/ui/LineCountingDataSource.java
    @@ -10,16 +10,20 @@
      *******************************************************************************/
     package org.eclipse.tm.internal.terminal.test.ui;
     
    -import org.eclipse.tm.terminal.model.Style;
    -import org.eclipse.tm.terminal.model.StyleColor;
    +import static org.eclipse.tm.terminal.model.TerminalColor.BLACK;
    +import static org.eclipse.tm.terminal.model.TerminalColor.BLUE;
    +import static org.eclipse.tm.terminal.model.TerminalColor.RED;
    +import static org.eclipse.tm.terminal.model.TerminalColor.YELLOW;
    +
    +import org.eclipse.tm.terminal.model.TerminalStyle;
     
     final class LineCountingDataSource extends AbstractLineOrientedDataSource {
    -	Style styleNormal = Style.getStyle(StyleColor.getStyleColor("black"), StyleColor.getStyleColor("red"));
    +	TerminalStyle styleNormal = TerminalStyle.getStyle(BLACK, RED);
     
    -	Style styles[] = new Style[] { styleNormal, styleNormal.setBold(true), styleNormal.setForground("blue"),
    -			styleNormal.setForground("yellow"), styleNormal.setBold(true).setUnderline(true),
    -			styleNormal.setReverse(true), styleNormal.setReverse(true).setBold(true),
    -			styleNormal.setReverse(true).setUnderline(true) };
    +	TerminalStyle styles[] = new TerminalStyle[] { styleNormal, styleNormal.setBold(true),
    +			styleNormal.setForeground(BLUE), styleNormal.setForeground(YELLOW),
    +			styleNormal.setBold(true).setUnderline(true), styleNormal.setReverse(true),
    +			styleNormal.setReverse(true).setBold(true), styleNormal.setReverse(true).setUnderline(true) };
     
     	int pos;
     
    @@ -30,7 +34,7 @@ final class LineCountingDataSource extends AbstractLineOrientedDataSource {
     	}
     
     	@Override
    -	public Style getStyle() {
    +	public TerminalStyle getStyle() {
     		return styles[pos % styles.length];
     	}
     
    diff --git a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/test/ui/RandomDataSource.java b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/test/ui/RandomDataSource.java
    index 4ddb10a638c..a13bf7c3101 100644
    --- a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/test/ui/RandomDataSource.java
    +++ b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/internal/terminal/test/ui/RandomDataSource.java
    @@ -10,19 +10,23 @@
      *******************************************************************************/
     package org.eclipse.tm.internal.terminal.test.ui;
     
    +import static org.eclipse.tm.terminal.model.TerminalColor.BLACK;
    +import static org.eclipse.tm.terminal.model.TerminalColor.GREEN;
    +import static org.eclipse.tm.terminal.model.TerminalColor.RED;
    +import static org.eclipse.tm.terminal.model.TerminalColor.YELLOW;
    +
     import java.util.Random;
     
     import org.eclipse.tm.terminal.model.ITerminalTextData;
    -import org.eclipse.tm.terminal.model.Style;
    -import org.eclipse.tm.terminal.model.StyleColor;
    +import org.eclipse.tm.terminal.model.TerminalStyle;
     
     public class RandomDataSource implements IDataSource {
     	Random fRandom = new Random();
    -	Style styleNormal = Style.getStyle(StyleColor.getStyleColor("black"), StyleColor.getStyleColor("green"));
    -	Style styles[] = new Style[] { styleNormal, styleNormal.setBold(true), styleNormal.setForground("red"),
    -			styleNormal.setForground("yellow"), styleNormal.setBold(true).setUnderline(true),
    -			styleNormal.setReverse(true), styleNormal.setReverse(true).setBold(true),
    -			styleNormal.setReverse(true).setUnderline(true) };
    +	TerminalStyle styleNormal = TerminalStyle.getStyle(BLACK, GREEN);
    +	TerminalStyle styles[] = new TerminalStyle[] { styleNormal, styleNormal.setBold(true),
    +			styleNormal.setForeground(RED), styleNormal.setForeground(YELLOW),
    +			styleNormal.setBold(true).setUnderline(true), styleNormal.setReverse(true),
    +			styleNormal.setReverse(true).setBold(true), styleNormal.setReverse(true).setUnderline(true) };
     
     	@Override
     	public int step(ITerminalTextData terminal) {
    @@ -34,7 +38,7 @@ public class RandomDataSource implements IDataSource {
     				int line = fRandom.nextInt(h);
     				int col = fRandom.nextInt(w);
     				char c = (char) ('A' + fRandom.nextInt('z' - 'A'));
    -				Style style = styles[fRandom.nextInt(styles.length)];
    +				TerminalStyle style = styles[fRandom.nextInt(styles.length)];
     				terminal.setChar(line, col, c, style);
     			}
     		}
    diff --git a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/terminal/model/AllTests.java b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/terminal/model/AllTests.java
    index 0b38892b92f..2bde0a9c693 100644
    --- a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/terminal/model/AllTests.java
    +++ b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/terminal/model/AllTests.java
    @@ -12,6 +12,7 @@
      *******************************************************************************/
     package org.eclipse.tm.terminal.model;
     
    +import junit.framework.JUnit4TestAdapter;
     import junit.framework.Test;
     import junit.framework.TestCase;
     import junit.framework.TestSuite;
    @@ -31,7 +32,7 @@ public class AllTests extends TestCase {
     
     	public static Test suite() {
     		TestSuite suite = new TestSuite(AllTests.class.getName());
    -		suite.addTestSuite(StyleColorTest.class);
    +		suite.addTest(new JUnit4TestAdapter(TerminalColorUITest.class));
     		suite.addTestSuite(StyleTest.class);
     		return suite;
     	}
    diff --git a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/terminal/model/StyleColorTest.java b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/terminal/model/StyleColorTest.java
    deleted file mode 100644
    index e2a48e04fdb..00000000000
    --- a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/terminal/model/StyleColorTest.java
    +++ /dev/null
    @@ -1,35 +0,0 @@
    -/*******************************************************************************
    - * Copyright (c) 2007, 2018 Wind River Systems, Inc. and others.
    - * All rights reserved. This program and the accompanying materials
    - * are made available under the terms of the Eclipse Public License 2.0
    - * which accompanies this distribution, and is available at
    - * https://www.eclipse.org/legal/epl-2.0/
    - *
    - * Contributors:
    - * Michael Scharf (Wind River) - initial API and implementation
    - *******************************************************************************/
    -package org.eclipse.tm.terminal.model;
    -
    -import junit.framework.TestCase;
    -
    -public class StyleColorTest extends TestCase {
    -
    -	public void testEqualsObject() {
    -		assertEquals(StyleColor.getStyleColor("foo"), StyleColor.getStyleColor("foo"));
    -		assertFalse(StyleColor.getStyleColor("foox").equals(StyleColor.getStyleColor("foo")));
    -	}
    -
    -	public void testSameObject() {
    -		assertSame(StyleColor.getStyleColor("foo"), StyleColor.getStyleColor("foo"));
    -		assertNotSame(StyleColor.getStyleColor("foox"), StyleColor.getStyleColor("foo"));
    -	}
    -
    -	public void testToString() {
    -		assertEquals("xxx", StyleColor.getStyleColor("xxx").toString());
    -	}
    -
    -	public void testGetName() {
    -		assertEquals("xxx", StyleColor.getStyleColor("xxx").getName());
    -	}
    -
    -}
    diff --git a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/terminal/model/StyleTest.java b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/terminal/model/StyleTest.java
    index 7e25628af66..9520e614ab4 100644
    --- a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/terminal/model/StyleTest.java
    +++ b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/terminal/model/StyleTest.java
    @@ -13,13 +13,13 @@ package org.eclipse.tm.terminal.model;
     import junit.framework.TestCase;
     
     public class StyleTest extends TestCase {
    -	final StyleColor c1 = StyleColor.getStyleColor("c1");
    -	final StyleColor c2 = StyleColor.getStyleColor("c2");
    -	final StyleColor c3 = StyleColor.getStyleColor("c3");
    +	final TerminalColor c1 = TerminalColor.getForTest(1);
    +	final TerminalColor c2 = TerminalColor.getForTest(2);
    +	final TerminalColor c3 = TerminalColor.getForTest(3);
     
     	public void testGetStyle() {
    -		Style s1 = Style.getStyle(c1, c2, true, false, true, false);
    -		Style s2 = Style.getStyle(c1, c2, true, false, true, false);
    +		TerminalStyle s1 = TerminalStyle.getStyle(c1, c2, true, false, true, false);
    +		TerminalStyle s2 = TerminalStyle.getStyle(c1, c2, true, false, true, false);
     		assertEquals(s1, s2);
     		assertSame(s1, s2);
     		s1 = s1.setBlink(!s1.isBlink());
    @@ -29,37 +29,37 @@ public class StyleTest extends TestCase {
     		assertSame(s1, s2);
     	}
     
    -	public void testSetForground() {
    -		Style s1 = Style.getStyle(c1, c2, true, false, true, false);
    -		Style s2 = s1;
    -		s2 = s1.setForground(c3);
    +	public void testSetForeground() {
    +		TerminalStyle s1 = TerminalStyle.getStyle(c1, c2, true, false, true, false);
    +		TerminalStyle s2 = s1;
    +		s2 = s1.setForeground(c3);
     		assertNotSame(s1, s2);
     		assertFalse(s1.equals(s2));
    -		assertSame(s2.getForground(), c3);
    -		assertSame(s1.getForground(), c1);
    -		assertSame(s1.getBackground(), c2);
    -		assertSame(s2.getBackground(), c2);
    -		s2 = s2.setForground(c1);
    +		assertSame(s2.getForegroundTerminalColor(), c3);
    +		assertSame(s1.getForegroundTerminalColor(), c1);
    +		assertSame(s1.getBackgroundTerminalColor(), c2);
    +		assertSame(s2.getBackgroundTerminalColor(), c2);
    +		s2 = s2.setForeground(c1);
     		assertSame(s1, s2);
     	}
     
     	public void testSetBackground() {
    -		Style s1 = Style.getStyle(c1, c2, true, false, true, false);
    -		Style s2 = s1;
    +		TerminalStyle s1 = TerminalStyle.getStyle(c1, c2, true, false, true, false);
    +		TerminalStyle s2 = s1;
     		s2 = s1.setBackground(c3);
     		assertNotSame(s1, s2);
     		assertFalse(s1.equals(s2));
    -		assertSame(s2.getForground(), c1);
    -		assertSame(s1.getForground(), c1);
    -		assertSame(s1.getBackground(), c2);
    -		assertSame(s2.getBackground(), c3);
    +		assertSame(s2.getForegroundTerminalColor(), c1);
    +		assertSame(s1.getForegroundTerminalColor(), c1);
    +		assertSame(s1.getBackgroundTerminalColor(), c2);
    +		assertSame(s2.getBackgroundTerminalColor(), c3);
     		s2 = s2.setBackground(c2);
     		assertSame(s1, s2);
     	}
     
     	public void testSetBold() {
    -		Style s1 = getDefaultStyle();
    -		Style s2 = s1;
    +		TerminalStyle s1 = getDefaultStyle();
    +		TerminalStyle s2 = s1;
     		assertSame(s1, s2);
     		assertFalse(s2.isBold());
     		s2 = s2.setBold(true);
    @@ -71,8 +71,8 @@ public class StyleTest extends TestCase {
     	}
     
     	public void testSetBlink() {
    -		Style s1 = getDefaultStyle();
    -		Style s2 = s1;
    +		TerminalStyle s1 = getDefaultStyle();
    +		TerminalStyle s2 = s1;
     		assertSame(s1, s2);
     		assertFalse(s2.isBlink());
     		s2 = s2.setBlink(true);
    @@ -84,8 +84,8 @@ public class StyleTest extends TestCase {
     	}
     
     	public void testSetUnderline() {
    -		Style s1 = getDefaultStyle();
    -		Style s2 = s1;
    +		TerminalStyle s1 = getDefaultStyle();
    +		TerminalStyle s2 = s1;
     		assertSame(s1, s2);
     		assertFalse(s2.isUnderline());
     		s2 = s2.setUnderline(true);
    @@ -97,8 +97,8 @@ public class StyleTest extends TestCase {
     	}
     
     	public void testSetReverse() {
    -		Style s1 = getDefaultStyle();
    -		Style s2 = s1;
    +		TerminalStyle s1 = getDefaultStyle();
    +		TerminalStyle s2 = s1;
     		assertSame(s1, s2);
     		assertFalse(s2.isReverse());
     		s2 = s2.setReverse(true);
    @@ -109,8 +109,8 @@ public class StyleTest extends TestCase {
     		assertFalse(s2.isReverse());
     	}
     
    -	private Style getDefaultStyle() {
    -		return Style.getStyle(c1, c2, false, false, false, false);
    +	private TerminalStyle getDefaultStyle() {
    +		return TerminalStyle.getStyle(c1, c2, false, false, false, false);
     	}
     
     }
    diff --git a/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/terminal/model/TerminalColorUITest.java b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/terminal/model/TerminalColorUITest.java
    new file mode 100644
    index 00000000000..588bcf63f4e
    --- /dev/null
    +++ b/terminal/plugins/org.eclipse.tm.terminal.test/src/org/eclipse/tm/terminal/model/TerminalColorUITest.java
    @@ -0,0 +1,82 @@
    +/*******************************************************************************
    + * Copyright (c) 2020 Kichwa Coders Canada Inc. and others.
    + * All rights reserved. This program and the accompanying materials
    + * are made available under the terms of the Eclipse Public License 2.0
    + * which accompanies this distribution, and is available at
    + * https://www.eclipse.org/legal/epl-2.0/
    + *******************************************************************************/
    +package org.eclipse.tm.terminal.model;
    +
    +import static org.eclipse.tm.terminal.model.TerminalColor.BLACK;
    +import static org.eclipse.tm.terminal.model.TerminalColor.BLUE;
    +import static org.eclipse.tm.terminal.model.TerminalColor.CYAN;
    +import static org.eclipse.tm.terminal.model.TerminalColor.GREEN;
    +import static org.eclipse.tm.terminal.model.TerminalColor.MAGENTA;
    +import static org.eclipse.tm.terminal.model.TerminalColor.RED;
    +import static org.eclipse.tm.terminal.model.TerminalColor.WHITE;
    +import static org.eclipse.tm.terminal.model.TerminalColor.YELLOW;
    +import static org.junit.Assert.assertEquals;
    +import static org.junit.Assert.assertNotEquals;
    +
    +import org.eclipse.swt.widgets.Display;
    +import org.junit.AfterClass;
    +import org.junit.BeforeClass;
    +import org.junit.Test;
    +
    +/**
    + * This is a UI test because {@link TerminalColor#convertColor(boolean, boolean)
    + * requires a Display to operate the ColorRegistry.
    + */
    +public class TerminalColorUITest {
    +
    +	private static Display display = null;
    +
    +	@BeforeClass
    +	public static void createDisplay() {
    +		Display current = Display.getCurrent();
    +		if (current == null) {
    +			display = new Display();
    +		}
    +	}
    +
    +	@AfterClass
    +	public static void disposeDisplay() {
    +		if (display != null) {
    +			display.dispose();
    +		}
    +	}
    +
    +	@Test
    +	public void testInversionsStandard() {
    +
    +		assertEquals(BLACK.convertColor(false, false), WHITE.convertColor(true, false));
    +		assertNotEquals(BLACK.convertColor(false, false), WHITE.convertColor(false, false));
    +
    +		assertEquals(RED.convertColor(false, false), RED.convertColor(true, false));
    +		assertEquals(GREEN.convertColor(false, false), GREEN.convertColor(true, false));
    +		assertEquals(YELLOW.convertColor(false, false), YELLOW.convertColor(true, false));
    +		assertEquals(BLUE.convertColor(false, false), BLUE.convertColor(true, false));
    +		assertEquals(MAGENTA.convertColor(false, false), MAGENTA.convertColor(true, false));
    +		assertEquals(CYAN.convertColor(false, false), CYAN.convertColor(true, false));
    +
    +		assertEquals(WHITE.convertColor(false, false), BLACK.convertColor(true, false));
    +		assertNotEquals(WHITE.convertColor(false, false), BLACK.convertColor(false, false));
    +
    +	}
    +
    +	@Test
    +	public void testInversionsBright() {
    +		assertEquals(BLACK.convertColor(false, true), WHITE.convertColor(true, true));
    +		assertNotEquals(BLACK.convertColor(false, true), WHITE.convertColor(false, true));
    +
    +		assertEquals(RED.convertColor(false, true), RED.convertColor(true, true));
    +		assertEquals(GREEN.convertColor(false, true), GREEN.convertColor(true, true));
    +		assertEquals(YELLOW.convertColor(false, true), YELLOW.convertColor(true, true));
    +		assertEquals(BLUE.convertColor(false, true), BLUE.convertColor(true, true));
    +		assertEquals(MAGENTA.convertColor(false, true), MAGENTA.convertColor(true, true));
    +		assertEquals(CYAN.convertColor(false, true), CYAN.convertColor(true, true));
    +
    +		assertEquals(WHITE.convertColor(false, true), BLACK.convertColor(true, true));
    +		assertNotEquals(WHITE.convertColor(false, true), BLACK.convertColor(false, true));
    +	}
    +}