mirror of
https://github.com/coder/code-server.git
synced 2026-05-08 13:27:25 +02:00
Merge commit 'be3e8236086165e5e45a5a10783823874b3f3ebd' as 'lib/vscode'
This commit is contained in:
26
lib/vscode/src/vs/platform/theme/browser/checkbox.ts
Normal file
26
lib/vscode/src/vs/platform/theme/browser/checkbox.ts
Normal file
@@ -0,0 +1,26 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { CheckboxActionViewItem } from 'vs/base/browser/ui/checkbox/checkbox';
|
||||
import { IAction } from 'vs/base/common/actions';
|
||||
import { IThemeService } from 'vs/platform/theme/common/themeService';
|
||||
import { attachCheckboxStyler } from 'vs/platform/theme/common/styler';
|
||||
import { IBaseActionViewItemOptions } from 'vs/base/browser/ui/actionbar/actionViewItems';
|
||||
|
||||
export class ThemableCheckboxActionViewItem extends CheckboxActionViewItem {
|
||||
|
||||
constructor(context: any, action: IAction, options: IBaseActionViewItemOptions | undefined, private readonly themeService: IThemeService) {
|
||||
super(context, action, options);
|
||||
}
|
||||
|
||||
render(container: HTMLElement): void {
|
||||
super.render(container);
|
||||
if (this.checkbox) {
|
||||
this.disposables.add(attachCheckboxStyler(this.checkbox, this.themeService));
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
552
lib/vscode/src/vs/platform/theme/common/colorRegistry.ts
Normal file
552
lib/vscode/src/vs/platform/theme/common/colorRegistry.ts
Normal file
@@ -0,0 +1,552 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import * as platform from 'vs/platform/registry/common/platform';
|
||||
import { IJSONSchema, IJSONSchemaMap } from 'vs/base/common/jsonSchema';
|
||||
import { Color, RGBA } from 'vs/base/common/color';
|
||||
import { IColorTheme } from 'vs/platform/theme/common/themeService';
|
||||
import { Event, Emitter } from 'vs/base/common/event';
|
||||
import * as nls from 'vs/nls';
|
||||
import { Extensions as JSONExtensions, IJSONContributionRegistry } from 'vs/platform/jsonschemas/common/jsonContributionRegistry';
|
||||
import { RunOnceScheduler } from 'vs/base/common/async';
|
||||
|
||||
// ------ API types
|
||||
|
||||
export type ColorIdentifier = string;
|
||||
|
||||
export interface ColorContribution {
|
||||
readonly id: ColorIdentifier;
|
||||
readonly description: string;
|
||||
readonly defaults: ColorDefaults | null;
|
||||
readonly needsTransparency: boolean;
|
||||
readonly deprecationMessage: string | undefined;
|
||||
}
|
||||
|
||||
|
||||
export interface ColorFunction {
|
||||
(theme: IColorTheme): Color | undefined;
|
||||
}
|
||||
|
||||
export interface ColorDefaults {
|
||||
light: ColorValue | null;
|
||||
dark: ColorValue | null;
|
||||
hc: ColorValue | null;
|
||||
}
|
||||
|
||||
/**
|
||||
* A Color Value is either a color literal, a refence to other color or a derived color
|
||||
*/
|
||||
export type ColorValue = Color | string | ColorIdentifier | ColorFunction;
|
||||
|
||||
// color registry
|
||||
export const Extensions = {
|
||||
ColorContribution: 'base.contributions.colors'
|
||||
};
|
||||
|
||||
export interface IColorRegistry {
|
||||
|
||||
readonly onDidChangeSchema: Event<void>;
|
||||
|
||||
/**
|
||||
* Register a color to the registry.
|
||||
* @param id The color id as used in theme description files
|
||||
* @param defaults The default values
|
||||
* @description the description
|
||||
*/
|
||||
registerColor(id: string, defaults: ColorDefaults, description: string): ColorIdentifier;
|
||||
|
||||
/**
|
||||
* Register a color to the registry.
|
||||
*/
|
||||
deregisterColor(id: string): void;
|
||||
|
||||
/**
|
||||
* Get all color contributions
|
||||
*/
|
||||
getColors(): ColorContribution[];
|
||||
|
||||
/**
|
||||
* Gets the default color of the given id
|
||||
*/
|
||||
resolveDefaultColor(id: ColorIdentifier, theme: IColorTheme): Color | undefined;
|
||||
|
||||
/**
|
||||
* JSON schema for an object to assign color values to one of the color contributions.
|
||||
*/
|
||||
getColorSchema(): IJSONSchema;
|
||||
|
||||
/**
|
||||
* JSON schema to for a reference to a color contribution.
|
||||
*/
|
||||
getColorReferenceSchema(): IJSONSchema;
|
||||
|
||||
}
|
||||
|
||||
class ColorRegistry implements IColorRegistry {
|
||||
|
||||
private readonly _onDidChangeSchema = new Emitter<void>();
|
||||
readonly onDidChangeSchema: Event<void> = this._onDidChangeSchema.event;
|
||||
|
||||
private colorsById: { [key: string]: ColorContribution };
|
||||
private colorSchema: IJSONSchema & { properties: IJSONSchemaMap } = { type: 'object', properties: {} };
|
||||
private colorReferenceSchema: IJSONSchema & { enum: string[], enumDescriptions: string[] } = { type: 'string', enum: [], enumDescriptions: [] };
|
||||
|
||||
constructor() {
|
||||
this.colorsById = {};
|
||||
}
|
||||
|
||||
public registerColor(id: string, defaults: ColorDefaults | null, description: string, needsTransparency = false, deprecationMessage?: string): ColorIdentifier {
|
||||
let colorContribution: ColorContribution = { id, description, defaults, needsTransparency, deprecationMessage };
|
||||
this.colorsById[id] = colorContribution;
|
||||
let propertySchema: IJSONSchema = { type: 'string', description, format: 'color-hex', defaultSnippets: [{ body: '${1:#ff0000}' }] };
|
||||
if (deprecationMessage) {
|
||||
propertySchema.deprecationMessage = deprecationMessage;
|
||||
}
|
||||
this.colorSchema.properties[id] = propertySchema;
|
||||
this.colorReferenceSchema.enum.push(id);
|
||||
this.colorReferenceSchema.enumDescriptions.push(description);
|
||||
|
||||
this._onDidChangeSchema.fire();
|
||||
return id;
|
||||
}
|
||||
|
||||
|
||||
public deregisterColor(id: string): void {
|
||||
delete this.colorsById[id];
|
||||
delete this.colorSchema.properties[id];
|
||||
const index = this.colorReferenceSchema.enum.indexOf(id);
|
||||
if (index !== -1) {
|
||||
this.colorReferenceSchema.enum.splice(index, 1);
|
||||
this.colorReferenceSchema.enumDescriptions.splice(index, 1);
|
||||
}
|
||||
this._onDidChangeSchema.fire();
|
||||
}
|
||||
|
||||
public getColors(): ColorContribution[] {
|
||||
return Object.keys(this.colorsById).map(id => this.colorsById[id]);
|
||||
}
|
||||
|
||||
public resolveDefaultColor(id: ColorIdentifier, theme: IColorTheme): Color | undefined {
|
||||
const colorDesc = this.colorsById[id];
|
||||
if (colorDesc && colorDesc.defaults) {
|
||||
const colorValue = colorDesc.defaults[theme.type];
|
||||
return resolveColorValue(colorValue, theme);
|
||||
}
|
||||
return undefined;
|
||||
}
|
||||
|
||||
public getColorSchema(): IJSONSchema {
|
||||
return this.colorSchema;
|
||||
}
|
||||
|
||||
public getColorReferenceSchema(): IJSONSchema {
|
||||
return this.colorReferenceSchema;
|
||||
}
|
||||
|
||||
public toString() {
|
||||
let sorter = (a: string, b: string) => {
|
||||
let cat1 = a.indexOf('.') === -1 ? 0 : 1;
|
||||
let cat2 = b.indexOf('.') === -1 ? 0 : 1;
|
||||
if (cat1 !== cat2) {
|
||||
return cat1 - cat2;
|
||||
}
|
||||
return a.localeCompare(b);
|
||||
};
|
||||
|
||||
return Object.keys(this.colorsById).sort(sorter).map(k => `- \`${k}\`: ${this.colorsById[k].description}`).join('\n');
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
const colorRegistry = new ColorRegistry();
|
||||
platform.Registry.add(Extensions.ColorContribution, colorRegistry);
|
||||
|
||||
export function registerColor(id: string, defaults: ColorDefaults | null, description: string, needsTransparency?: boolean, deprecationMessage?: string): ColorIdentifier {
|
||||
return colorRegistry.registerColor(id, defaults, description, needsTransparency, deprecationMessage);
|
||||
}
|
||||
|
||||
export function getColorRegistry(): IColorRegistry {
|
||||
return colorRegistry;
|
||||
}
|
||||
|
||||
// ----- base colors
|
||||
|
||||
export const foreground = registerColor('foreground', { dark: '#CCCCCC', light: '#616161', hc: '#FFFFFF' }, nls.localize('foreground', "Overall foreground color. This color is only used if not overridden by a component."));
|
||||
export const errorForeground = registerColor('errorForeground', { dark: '#F48771', light: '#A1260D', hc: '#F48771' }, nls.localize('errorForeground', "Overall foreground color for error messages. This color is only used if not overridden by a component."));
|
||||
export const descriptionForeground = registerColor('descriptionForeground', { light: '#717171', dark: transparent(foreground, 0.7), hc: transparent(foreground, 0.7) }, nls.localize('descriptionForeground', "Foreground color for description text providing additional information, for example for a label."));
|
||||
export const iconForeground = registerColor('icon.foreground', { dark: '#C5C5C5', light: '#424242', hc: '#FFFFFF' }, nls.localize('iconForeground', "The default color for icons in the workbench."));
|
||||
|
||||
export const focusBorder = registerColor('focusBorder', { dark: '#007FD4', light: '#0090F1', hc: '#F38518' }, nls.localize('focusBorder', "Overall border color for focused elements. This color is only used if not overridden by a component."));
|
||||
|
||||
export const contrastBorder = registerColor('contrastBorder', { light: null, dark: null, hc: '#6FC3DF' }, nls.localize('contrastBorder', "An extra border around elements to separate them from others for greater contrast."));
|
||||
export const activeContrastBorder = registerColor('contrastActiveBorder', { light: null, dark: null, hc: focusBorder }, nls.localize('activeContrastBorder', "An extra border around active elements to separate them from others for greater contrast."));
|
||||
|
||||
export const selectionBackground = registerColor('selection.background', { light: null, dark: null, hc: null }, nls.localize('selectionBackground', "The background color of text selections in the workbench (e.g. for input fields or text areas). Note that this does not apply to selections within the editor."));
|
||||
|
||||
// ------ text colors
|
||||
|
||||
export const textSeparatorForeground = registerColor('textSeparator.foreground', { light: '#0000002e', dark: '#ffffff2e', hc: Color.black }, nls.localize('textSeparatorForeground', "Color for text separators."));
|
||||
export const textLinkForeground = registerColor('textLink.foreground', { light: '#006AB1', dark: '#3794FF', hc: '#3794FF' }, nls.localize('textLinkForeground', "Foreground color for links in text."));
|
||||
export const textLinkActiveForeground = registerColor('textLink.activeForeground', { light: '#006AB1', dark: '#3794FF', hc: '#3794FF' }, nls.localize('textLinkActiveForeground', "Foreground color for links in text when clicked on and on mouse hover."));
|
||||
export const textPreformatForeground = registerColor('textPreformat.foreground', { light: '#A31515', dark: '#D7BA7D', hc: '#D7BA7D' }, nls.localize('textPreformatForeground', "Foreground color for preformatted text segments."));
|
||||
export const textBlockQuoteBackground = registerColor('textBlockQuote.background', { light: '#7f7f7f1a', dark: '#7f7f7f1a', hc: null }, nls.localize('textBlockQuoteBackground', "Background color for block quotes in text."));
|
||||
export const textBlockQuoteBorder = registerColor('textBlockQuote.border', { light: '#007acc80', dark: '#007acc80', hc: Color.white }, nls.localize('textBlockQuoteBorder', "Border color for block quotes in text."));
|
||||
export const textCodeBlockBackground = registerColor('textCodeBlock.background', { light: '#dcdcdc66', dark: '#0a0a0a66', hc: Color.black }, nls.localize('textCodeBlockBackground', "Background color for code blocks in text."));
|
||||
|
||||
// ----- widgets
|
||||
export const widgetShadow = registerColor('widget.shadow', { dark: '#000000', light: '#A8A8A8', hc: null }, nls.localize('widgetShadow', 'Shadow color of widgets such as find/replace inside the editor.'));
|
||||
|
||||
export const inputBackground = registerColor('input.background', { dark: '#3C3C3C', light: Color.white, hc: Color.black }, nls.localize('inputBoxBackground', "Input box background."));
|
||||
export const inputForeground = registerColor('input.foreground', { dark: foreground, light: foreground, hc: foreground }, nls.localize('inputBoxForeground', "Input box foreground."));
|
||||
export const inputBorder = registerColor('input.border', { dark: null, light: null, hc: contrastBorder }, nls.localize('inputBoxBorder', "Input box border."));
|
||||
export const inputActiveOptionBorder = registerColor('inputOption.activeBorder', { dark: '#007ACC00', light: '#007ACC00', hc: contrastBorder }, nls.localize('inputBoxActiveOptionBorder', "Border color of activated options in input fields."));
|
||||
export const inputActiveOptionBackground = registerColor('inputOption.activeBackground', { dark: transparent(focusBorder, 0.4), light: transparent(focusBorder, 0.2), hc: Color.transparent }, nls.localize('inputOption.activeBackground', "Background color of activated options in input fields."));
|
||||
export const inputActiveOptionForeground = registerColor('inputOption.activeForeground', { dark: Color.white, light: Color.black, hc: null }, nls.localize('inputOption.activeForeground', "Foreground color of activated options in input fields."));
|
||||
export const inputPlaceholderForeground = registerColor('input.placeholderForeground', { light: transparent(foreground, 0.5), dark: transparent(foreground, 0.5), hc: transparent(foreground, 0.7) }, nls.localize('inputPlaceholderForeground', "Input box foreground color for placeholder text."));
|
||||
|
||||
export const inputValidationInfoBackground = registerColor('inputValidation.infoBackground', { dark: '#063B49', light: '#D6ECF2', hc: Color.black }, nls.localize('inputValidationInfoBackground', "Input validation background color for information severity."));
|
||||
export const inputValidationInfoForeground = registerColor('inputValidation.infoForeground', { dark: null, light: null, hc: null }, nls.localize('inputValidationInfoForeground', "Input validation foreground color for information severity."));
|
||||
export const inputValidationInfoBorder = registerColor('inputValidation.infoBorder', { dark: '#007acc', light: '#007acc', hc: contrastBorder }, nls.localize('inputValidationInfoBorder', "Input validation border color for information severity."));
|
||||
export const inputValidationWarningBackground = registerColor('inputValidation.warningBackground', { dark: '#352A05', light: '#F6F5D2', hc: Color.black }, nls.localize('inputValidationWarningBackground', "Input validation background color for warning severity."));
|
||||
export const inputValidationWarningForeground = registerColor('inputValidation.warningForeground', { dark: null, light: null, hc: null }, nls.localize('inputValidationWarningForeground', "Input validation foreground color for warning severity."));
|
||||
export const inputValidationWarningBorder = registerColor('inputValidation.warningBorder', { dark: '#B89500', light: '#B89500', hc: contrastBorder }, nls.localize('inputValidationWarningBorder', "Input validation border color for warning severity."));
|
||||
export const inputValidationErrorBackground = registerColor('inputValidation.errorBackground', { dark: '#5A1D1D', light: '#F2DEDE', hc: Color.black }, nls.localize('inputValidationErrorBackground', "Input validation background color for error severity."));
|
||||
export const inputValidationErrorForeground = registerColor('inputValidation.errorForeground', { dark: null, light: null, hc: null }, nls.localize('inputValidationErrorForeground', "Input validation foreground color for error severity."));
|
||||
export const inputValidationErrorBorder = registerColor('inputValidation.errorBorder', { dark: '#BE1100', light: '#BE1100', hc: contrastBorder }, nls.localize('inputValidationErrorBorder', "Input validation border color for error severity."));
|
||||
|
||||
export const selectBackground = registerColor('dropdown.background', { dark: '#3C3C3C', light: Color.white, hc: Color.black }, nls.localize('dropdownBackground', "Dropdown background."));
|
||||
export const selectListBackground = registerColor('dropdown.listBackground', { dark: null, light: null, hc: Color.black }, nls.localize('dropdownListBackground', "Dropdown list background."));
|
||||
export const selectForeground = registerColor('dropdown.foreground', { dark: '#F0F0F0', light: null, hc: Color.white }, nls.localize('dropdownForeground', "Dropdown foreground."));
|
||||
export const selectBorder = registerColor('dropdown.border', { dark: selectBackground, light: '#CECECE', hc: contrastBorder }, nls.localize('dropdownBorder', "Dropdown border."));
|
||||
|
||||
export const simpleCheckboxBackground = registerColor('checkbox.background', { dark: selectBackground, light: selectBackground, hc: selectBackground }, nls.localize('checkbox.background', "Background color of checkbox widget."));
|
||||
export const simpleCheckboxForeground = registerColor('checkbox.foreground', { dark: selectForeground, light: selectForeground, hc: selectForeground }, nls.localize('checkbox.foreground', "Foreground color of checkbox widget."));
|
||||
export const simpleCheckboxBorder = registerColor('checkbox.border', { dark: selectBorder, light: selectBorder, hc: selectBorder }, nls.localize('checkbox.border', "Border color of checkbox widget."));
|
||||
|
||||
export const buttonForeground = registerColor('button.foreground', { dark: Color.white, light: Color.white, hc: Color.white }, nls.localize('buttonForeground', "Button foreground color."));
|
||||
export const buttonBackground = registerColor('button.background', { dark: '#0E639C', light: '#007ACC', hc: null }, nls.localize('buttonBackground', "Button background color."));
|
||||
export const buttonHoverBackground = registerColor('button.hoverBackground', { dark: lighten(buttonBackground, 0.2), light: darken(buttonBackground, 0.2), hc: null }, nls.localize('buttonHoverBackground', "Button background color when hovering."));
|
||||
|
||||
export const buttonSecondaryForeground = registerColor('button.secondaryForeground', { dark: Color.white, light: Color.white, hc: Color.white }, nls.localize('buttonSecondaryForeground', "Secondary button foreground color."));
|
||||
export const buttonSecondaryBackground = registerColor('button.secondaryBackground', { dark: '#3A3D41', light: '#5F6A79', hc: null }, nls.localize('buttonSecondaryBackground', "Secondary button background color."));
|
||||
export const buttonSecondaryHoverBackground = registerColor('button.secondaryHoverBackground', { dark: lighten(buttonSecondaryBackground, 0.2), light: darken(buttonSecondaryBackground, 0.2), hc: null }, nls.localize('buttonSecondaryHoverBackground', "Secondary button background color when hovering."));
|
||||
|
||||
export const badgeBackground = registerColor('badge.background', { dark: '#4D4D4D', light: '#C4C4C4', hc: Color.black }, nls.localize('badgeBackground', "Badge background color. Badges are small information labels, e.g. for search results count."));
|
||||
export const badgeForeground = registerColor('badge.foreground', { dark: Color.white, light: '#333', hc: Color.white }, nls.localize('badgeForeground', "Badge foreground color. Badges are small information labels, e.g. for search results count."));
|
||||
|
||||
export const scrollbarShadow = registerColor('scrollbar.shadow', { dark: '#000000', light: '#DDDDDD', hc: null }, nls.localize('scrollbarShadow', "Scrollbar shadow to indicate that the view is scrolled."));
|
||||
export const scrollbarSliderBackground = registerColor('scrollbarSlider.background', { dark: Color.fromHex('#797979').transparent(0.4), light: Color.fromHex('#646464').transparent(0.4), hc: transparent(contrastBorder, 0.6) }, nls.localize('scrollbarSliderBackground', "Scrollbar slider background color."));
|
||||
export const scrollbarSliderHoverBackground = registerColor('scrollbarSlider.hoverBackground', { dark: Color.fromHex('#646464').transparent(0.7), light: Color.fromHex('#646464').transparent(0.7), hc: transparent(contrastBorder, 0.8) }, nls.localize('scrollbarSliderHoverBackground', "Scrollbar slider background color when hovering."));
|
||||
export const scrollbarSliderActiveBackground = registerColor('scrollbarSlider.activeBackground', { dark: Color.fromHex('#BFBFBF').transparent(0.4), light: Color.fromHex('#000000').transparent(0.6), hc: contrastBorder }, nls.localize('scrollbarSliderActiveBackground', "Scrollbar slider background color when clicked on."));
|
||||
|
||||
export const progressBarBackground = registerColor('progressBar.background', { dark: Color.fromHex('#0E70C0'), light: Color.fromHex('#0E70C0'), hc: contrastBorder }, nls.localize('progressBarBackground', "Background color of the progress bar that can show for long running operations."));
|
||||
|
||||
export const editorErrorForeground = registerColor('editorError.foreground', { dark: '#F48771', light: '#E51400', hc: null }, nls.localize('editorError.foreground', 'Foreground color of error squigglies in the editor.'));
|
||||
export const editorErrorBorder = registerColor('editorError.border', { dark: null, light: null, hc: Color.fromHex('#E47777').transparent(0.8) }, nls.localize('errorBorder', 'Border color of error boxes in the editor.'));
|
||||
|
||||
export const editorWarningForeground = registerColor('editorWarning.foreground', { dark: '#CCA700', light: '#E9A700', hc: null }, nls.localize('editorWarning.foreground', 'Foreground color of warning squigglies in the editor.'));
|
||||
export const editorWarningBorder = registerColor('editorWarning.border', { dark: null, light: null, hc: Color.fromHex('#FFCC00').transparent(0.8) }, nls.localize('warningBorder', 'Border color of warning boxes in the editor.'));
|
||||
|
||||
export const editorInfoForeground = registerColor('editorInfo.foreground', { dark: '#75BEFF', light: '#75BEFF', hc: null }, nls.localize('editorInfo.foreground', 'Foreground color of info squigglies in the editor.'));
|
||||
export const editorInfoBorder = registerColor('editorInfo.border', { dark: null, light: null, hc: Color.fromHex('#75BEFF').transparent(0.8) }, nls.localize('infoBorder', 'Border color of info boxes in the editor.'));
|
||||
|
||||
export const editorHintForeground = registerColor('editorHint.foreground', { dark: Color.fromHex('#eeeeee').transparent(0.7), light: '#6c6c6c', hc: null }, nls.localize('editorHint.foreground', 'Foreground color of hint squigglies in the editor.'));
|
||||
export const editorHintBorder = registerColor('editorHint.border', { dark: null, light: null, hc: Color.fromHex('#eeeeee').transparent(0.8) }, nls.localize('hintBorder', 'Border color of hint boxes in the editor.'));
|
||||
|
||||
/**
|
||||
* Editor background color.
|
||||
* Because of bug https://monacotools.visualstudio.com/DefaultCollection/Monaco/_workitems/edit/13254
|
||||
* we are *not* using the color white (or #ffffff, rgba(255,255,255)) but something very close to white.
|
||||
*/
|
||||
export const editorBackground = registerColor('editor.background', { light: '#fffffe', dark: '#1E1E1E', hc: Color.black }, nls.localize('editorBackground', "Editor background color."));
|
||||
|
||||
/**
|
||||
* Editor foreground color.
|
||||
*/
|
||||
export const editorForeground = registerColor('editor.foreground', { light: '#333333', dark: '#BBBBBB', hc: Color.white }, nls.localize('editorForeground', "Editor default foreground color."));
|
||||
|
||||
/**
|
||||
* Editor widgets
|
||||
*/
|
||||
export const editorWidgetBackground = registerColor('editorWidget.background', { dark: '#252526', light: '#F3F3F3', hc: '#0C141F' }, nls.localize('editorWidgetBackground', 'Background color of editor widgets, such as find/replace.'));
|
||||
export const editorWidgetForeground = registerColor('editorWidget.foreground', { dark: foreground, light: foreground, hc: foreground }, nls.localize('editorWidgetForeground', 'Foreground color of editor widgets, such as find/replace.'));
|
||||
|
||||
export const editorWidgetBorder = registerColor('editorWidget.border', { dark: '#454545', light: '#C8C8C8', hc: contrastBorder }, nls.localize('editorWidgetBorder', 'Border color of editor widgets. The color is only used if the widget chooses to have a border and if the color is not overridden by a widget.'));
|
||||
|
||||
export const editorWidgetResizeBorder = registerColor('editorWidget.resizeBorder', { light: null, dark: null, hc: null }, nls.localize('editorWidgetResizeBorder', "Border color of the resize bar of editor widgets. The color is only used if the widget chooses to have a resize border and if the color is not overridden by a widget."));
|
||||
|
||||
/**
|
||||
* Quick pick widget
|
||||
*/
|
||||
export const quickInputBackground = registerColor('quickInput.background', { dark: editorWidgetBackground, light: editorWidgetBackground, hc: editorWidgetBackground }, nls.localize('pickerBackground', "Quick picker background color. The quick picker widget is the container for pickers like the command palette."));
|
||||
export const quickInputForeground = registerColor('quickInput.foreground', { dark: editorWidgetForeground, light: editorWidgetForeground, hc: editorWidgetForeground }, nls.localize('pickerForeground', "Quick picker foreground color. The quick picker widget is the container for pickers like the command palette."));
|
||||
export const quickInputTitleBackground = registerColor('quickInputTitle.background', { dark: new Color(new RGBA(255, 255, 255, 0.105)), light: new Color(new RGBA(0, 0, 0, 0.06)), hc: '#000000' }, nls.localize('pickerTitleBackground', "Quick picker title background color. The quick picker widget is the container for pickers like the command palette."));
|
||||
export const pickerGroupForeground = registerColor('pickerGroup.foreground', { dark: '#3794FF', light: '#0066BF', hc: Color.white }, nls.localize('pickerGroupForeground', "Quick picker color for grouping labels."));
|
||||
export const pickerGroupBorder = registerColor('pickerGroup.border', { dark: '#3F3F46', light: '#CCCEDB', hc: Color.white }, nls.localize('pickerGroupBorder', "Quick picker color for grouping borders."));
|
||||
|
||||
/**
|
||||
* Editor selection colors.
|
||||
*/
|
||||
export const editorSelectionBackground = registerColor('editor.selectionBackground', { light: '#ADD6FF', dark: '#264F78', hc: '#f3f518' }, nls.localize('editorSelectionBackground', "Color of the editor selection."));
|
||||
export const editorSelectionForeground = registerColor('editor.selectionForeground', { light: null, dark: null, hc: '#000000' }, nls.localize('editorSelectionForeground', "Color of the selected text for high contrast."));
|
||||
export const editorInactiveSelection = registerColor('editor.inactiveSelectionBackground', { light: transparent(editorSelectionBackground, 0.5), dark: transparent(editorSelectionBackground, 0.5), hc: transparent(editorSelectionBackground, 0.5) }, nls.localize('editorInactiveSelection', "Color of the selection in an inactive editor. The color must not be opaque so as not to hide underlying decorations."), true);
|
||||
export const editorSelectionHighlight = registerColor('editor.selectionHighlightBackground', { light: lessProminent(editorSelectionBackground, editorBackground, 0.3, 0.6), dark: lessProminent(editorSelectionBackground, editorBackground, 0.3, 0.6), hc: null }, nls.localize('editorSelectionHighlight', 'Color for regions with the same content as the selection. The color must not be opaque so as not to hide underlying decorations.'), true);
|
||||
export const editorSelectionHighlightBorder = registerColor('editor.selectionHighlightBorder', { light: null, dark: null, hc: activeContrastBorder }, nls.localize('editorSelectionHighlightBorder', "Border color for regions with the same content as the selection."));
|
||||
|
||||
|
||||
/**
|
||||
* Editor find match colors.
|
||||
*/
|
||||
export const editorFindMatch = registerColor('editor.findMatchBackground', { light: '#A8AC94', dark: '#515C6A', hc: null }, nls.localize('editorFindMatch', "Color of the current search match."));
|
||||
export const editorFindMatchHighlight = registerColor('editor.findMatchHighlightBackground', { light: '#EA5C0055', dark: '#EA5C0055', hc: null }, nls.localize('findMatchHighlight', "Color of the other search matches. The color must not be opaque so as not to hide underlying decorations."), true);
|
||||
export const editorFindRangeHighlight = registerColor('editor.findRangeHighlightBackground', { dark: '#3a3d4166', light: '#b4b4b44d', hc: null }, nls.localize('findRangeHighlight', "Color of the range limiting the search. The color must not be opaque so as not to hide underlying decorations."), true);
|
||||
export const editorFindMatchBorder = registerColor('editor.findMatchBorder', { light: null, dark: null, hc: activeContrastBorder }, nls.localize('editorFindMatchBorder', "Border color of the current search match."));
|
||||
export const editorFindMatchHighlightBorder = registerColor('editor.findMatchHighlightBorder', { light: null, dark: null, hc: activeContrastBorder }, nls.localize('findMatchHighlightBorder', "Border color of the other search matches."));
|
||||
export const editorFindRangeHighlightBorder = registerColor('editor.findRangeHighlightBorder', { dark: null, light: null, hc: transparent(activeContrastBorder, 0.4) }, nls.localize('findRangeHighlightBorder', "Border color of the range limiting the search. The color must not be opaque so as not to hide underlying decorations."), true);
|
||||
|
||||
/**
|
||||
* Search Editor query match colors.
|
||||
*
|
||||
* Distinct from normal editor find match to allow for better differentiation
|
||||
*/
|
||||
export const searchEditorFindMatch = registerColor('searchEditor.findMatchBackground', { light: transparent(editorFindMatchHighlight, 0.66), dark: transparent(editorFindMatchHighlight, 0.66), hc: editorFindMatchHighlight }, nls.localize('searchEditor.queryMatch', "Color of the Search Editor query matches."));
|
||||
export const searchEditorFindMatchBorder = registerColor('searchEditor.findMatchBorder', { light: transparent(editorFindMatchHighlightBorder, 0.66), dark: transparent(editorFindMatchHighlightBorder, 0.66), hc: editorFindMatchHighlightBorder }, nls.localize('searchEditor.editorFindMatchBorder', "Border color of the Search Editor query matches."));
|
||||
|
||||
/**
|
||||
* Editor hover
|
||||
*/
|
||||
export const editorHoverHighlight = registerColor('editor.hoverHighlightBackground', { light: '#ADD6FF26', dark: '#264f7840', hc: '#ADD6FF26' }, nls.localize('hoverHighlight', 'Highlight below the word for which a hover is shown. The color must not be opaque so as not to hide underlying decorations.'), true);
|
||||
export const editorHoverBackground = registerColor('editorHoverWidget.background', { light: editorWidgetBackground, dark: editorWidgetBackground, hc: editorWidgetBackground }, nls.localize('hoverBackground', 'Background color of the editor hover.'));
|
||||
export const editorHoverForeground = registerColor('editorHoverWidget.foreground', { light: editorWidgetForeground, dark: editorWidgetForeground, hc: editorWidgetForeground }, nls.localize('hoverForeground', 'Foreground color of the editor hover.'));
|
||||
export const editorHoverBorder = registerColor('editorHoverWidget.border', { light: editorWidgetBorder, dark: editorWidgetBorder, hc: editorWidgetBorder }, nls.localize('hoverBorder', 'Border color of the editor hover.'));
|
||||
export const editorHoverStatusBarBackground = registerColor('editorHoverWidget.statusBarBackground', { dark: lighten(editorHoverBackground, 0.2), light: darken(editorHoverBackground, 0.05), hc: editorWidgetBackground }, nls.localize('statusBarBackground', "Background color of the editor hover status bar."));
|
||||
/**
|
||||
* Editor link colors
|
||||
*/
|
||||
export const editorActiveLinkForeground = registerColor('editorLink.activeForeground', { dark: '#4E94CE', light: Color.blue, hc: Color.cyan }, nls.localize('activeLinkForeground', 'Color of active links.'));
|
||||
|
||||
/**
|
||||
* Editor lighbulb icon colors
|
||||
*/
|
||||
export const editorLightBulbForeground = registerColor('editorLightBulb.foreground', { dark: '#FFCC00', light: '#DDB100', hc: '#FFCC00' }, nls.localize('editorLightBulbForeground', "The color used for the lightbulb actions icon."));
|
||||
export const editorLightBulbAutoFixForeground = registerColor('editorLightBulbAutoFix.foreground', { dark: '#75BEFF', light: '#007ACC', hc: '#75BEFF' }, nls.localize('editorLightBulbAutoFixForeground', "The color used for the lightbulb auto fix actions icon."));
|
||||
|
||||
/**
|
||||
* Diff Editor Colors
|
||||
*/
|
||||
export const defaultInsertColor = new Color(new RGBA(155, 185, 85, 0.2));
|
||||
export const defaultRemoveColor = new Color(new RGBA(255, 0, 0, 0.2));
|
||||
|
||||
export const diffInserted = registerColor('diffEditor.insertedTextBackground', { dark: defaultInsertColor, light: defaultInsertColor, hc: null }, nls.localize('diffEditorInserted', 'Background color for text that got inserted. The color must not be opaque so as not to hide underlying decorations.'), true);
|
||||
export const diffRemoved = registerColor('diffEditor.removedTextBackground', { dark: defaultRemoveColor, light: defaultRemoveColor, hc: null }, nls.localize('diffEditorRemoved', 'Background color for text that got removed. The color must not be opaque so as not to hide underlying decorations.'), true);
|
||||
|
||||
export const diffInsertedOutline = registerColor('diffEditor.insertedTextBorder', { dark: null, light: null, hc: '#33ff2eff' }, nls.localize('diffEditorInsertedOutline', 'Outline color for the text that got inserted.'));
|
||||
export const diffRemovedOutline = registerColor('diffEditor.removedTextBorder', { dark: null, light: null, hc: '#FF008F' }, nls.localize('diffEditorRemovedOutline', 'Outline color for text that got removed.'));
|
||||
|
||||
export const diffBorder = registerColor('diffEditor.border', { dark: null, light: null, hc: contrastBorder }, nls.localize('diffEditorBorder', 'Border color between the two text editors.'));
|
||||
export const diffDiagonalFill = registerColor('diffEditor.diagonalFill', { dark: '#cccccc33', light: '#22222233', hc: null }, nls.localize('diffDiagonalFill', "Color of the diff editor's diagonal fill. The diagonal fill is used in side-by-side diff views."));
|
||||
|
||||
/**
|
||||
* List and tree colors
|
||||
*/
|
||||
export const listFocusBackground = registerColor('list.focusBackground', { dark: '#062F4A', light: '#D6EBFF', hc: null }, nls.localize('listFocusBackground', "List/Tree background color for the focused item when the list/tree is active. An active list/tree has keyboard focus, an inactive does not."));
|
||||
export const listFocusForeground = registerColor('list.focusForeground', { dark: null, light: null, hc: null }, nls.localize('listFocusForeground', "List/Tree foreground color for the focused item when the list/tree is active. An active list/tree has keyboard focus, an inactive does not."));
|
||||
export const listActiveSelectionBackground = registerColor('list.activeSelectionBackground', { dark: '#094771', light: '#0074E8', hc: null }, nls.localize('listActiveSelectionBackground', "List/Tree background color for the selected item when the list/tree is active. An active list/tree has keyboard focus, an inactive does not."));
|
||||
export const listActiveSelectionForeground = registerColor('list.activeSelectionForeground', { dark: Color.white, light: Color.white, hc: null }, nls.localize('listActiveSelectionForeground', "List/Tree foreground color for the selected item when the list/tree is active. An active list/tree has keyboard focus, an inactive does not."));
|
||||
export const listInactiveSelectionBackground = registerColor('list.inactiveSelectionBackground', { dark: '#37373D', light: '#E4E6F1', hc: null }, nls.localize('listInactiveSelectionBackground', "List/Tree background color for the selected item when the list/tree is inactive. An active list/tree has keyboard focus, an inactive does not."));
|
||||
export const listInactiveSelectionForeground = registerColor('list.inactiveSelectionForeground', { dark: null, light: null, hc: null }, nls.localize('listInactiveSelectionForeground', "List/Tree foreground color for the selected item when the list/tree is inactive. An active list/tree has keyboard focus, an inactive does not."));
|
||||
export const listInactiveFocusBackground = registerColor('list.inactiveFocusBackground', { dark: null, light: null, hc: null }, nls.localize('listInactiveFocusBackground', "List/Tree background color for the focused item when the list/tree is inactive. An active list/tree has keyboard focus, an inactive does not."));
|
||||
export const listHoverBackground = registerColor('list.hoverBackground', { dark: '#2A2D2E', light: '#F0F0F0', hc: null }, nls.localize('listHoverBackground', "List/Tree background when hovering over items using the mouse."));
|
||||
export const listHoverForeground = registerColor('list.hoverForeground', { dark: null, light: null, hc: null }, nls.localize('listHoverForeground', "List/Tree foreground when hovering over items using the mouse."));
|
||||
export const listDropBackground = registerColor('list.dropBackground', { dark: listFocusBackground, light: listFocusBackground, hc: null }, nls.localize('listDropBackground', "List/Tree drag and drop background when moving items around using the mouse."));
|
||||
export const listHighlightForeground = registerColor('list.highlightForeground', { dark: '#0097fb', light: '#0066BF', hc: focusBorder }, nls.localize('highlight', 'List/Tree foreground color of the match highlights when searching inside the list/tree.'));
|
||||
export const listInvalidItemForeground = registerColor('list.invalidItemForeground', { dark: '#B89500', light: '#B89500', hc: '#B89500' }, nls.localize('invalidItemForeground', 'List/Tree foreground color for invalid items, for example an unresolved root in explorer.'));
|
||||
export const listErrorForeground = registerColor('list.errorForeground', { dark: '#F88070', light: '#B01011', hc: null }, nls.localize('listErrorForeground', 'Foreground color of list items containing errors.'));
|
||||
export const listWarningForeground = registerColor('list.warningForeground', { dark: '#CCA700', light: '#855F00', hc: null }, nls.localize('listWarningForeground', 'Foreground color of list items containing warnings.'));
|
||||
export const listFilterWidgetBackground = registerColor('listFilterWidget.background', { light: '#efc1ad', dark: '#653723', hc: Color.black }, nls.localize('listFilterWidgetBackground', 'Background color of the type filter widget in lists and trees.'));
|
||||
export const listFilterWidgetOutline = registerColor('listFilterWidget.outline', { dark: Color.transparent, light: Color.transparent, hc: '#f38518' }, nls.localize('listFilterWidgetOutline', 'Outline color of the type filter widget in lists and trees.'));
|
||||
export const listFilterWidgetNoMatchesOutline = registerColor('listFilterWidget.noMatchesOutline', { dark: '#BE1100', light: '#BE1100', hc: contrastBorder }, nls.localize('listFilterWidgetNoMatchesOutline', 'Outline color of the type filter widget in lists and trees, when there are no matches.'));
|
||||
export const listFilterMatchHighlight = registerColor('list.filterMatchBackground', { dark: editorFindMatchHighlight, light: editorFindMatchHighlight, hc: null }, nls.localize('listFilterMatchHighlight', 'Background color of the filtered match.'));
|
||||
export const listFilterMatchHighlightBorder = registerColor('list.filterMatchBorder', { dark: editorFindMatchHighlightBorder, light: editorFindMatchHighlightBorder, hc: contrastBorder }, nls.localize('listFilterMatchHighlightBorder', 'Border color of the filtered match.'));
|
||||
export const treeIndentGuidesStroke = registerColor('tree.indentGuidesStroke', { dark: '#585858', light: '#a9a9a9', hc: '#a9a9a9' }, nls.localize('treeIndentGuidesStroke', "Tree stroke color for the indentation guides."));
|
||||
export const listDeemphasizedForeground = registerColor('list.deemphasizedForeground', { dark: '#8C8C8C', light: '#8E8E90', hc: '#A7A8A9' }, nls.localize('listDeemphasizedForeground', "List/Tree foreground color for items that are deemphasized. "));
|
||||
|
||||
/**
|
||||
* Menu colors
|
||||
*/
|
||||
export const menuBorder = registerColor('menu.border', { dark: null, light: null, hc: contrastBorder }, nls.localize('menuBorder', "Border color of menus."));
|
||||
export const menuForeground = registerColor('menu.foreground', { dark: selectForeground, light: foreground, hc: selectForeground }, nls.localize('menuForeground', "Foreground color of menu items."));
|
||||
export const menuBackground = registerColor('menu.background', { dark: selectBackground, light: selectBackground, hc: selectBackground }, nls.localize('menuBackground', "Background color of menu items."));
|
||||
export const menuSelectionForeground = registerColor('menu.selectionForeground', { dark: listActiveSelectionForeground, light: listActiveSelectionForeground, hc: listActiveSelectionForeground }, nls.localize('menuSelectionForeground', "Foreground color of the selected menu item in menus."));
|
||||
export const menuSelectionBackground = registerColor('menu.selectionBackground', { dark: listActiveSelectionBackground, light: listActiveSelectionBackground, hc: listActiveSelectionBackground }, nls.localize('menuSelectionBackground', "Background color of the selected menu item in menus."));
|
||||
export const menuSelectionBorder = registerColor('menu.selectionBorder', { dark: null, light: null, hc: activeContrastBorder }, nls.localize('menuSelectionBorder', "Border color of the selected menu item in menus."));
|
||||
export const menuSeparatorBackground = registerColor('menu.separatorBackground', { dark: '#BBBBBB', light: '#888888', hc: contrastBorder }, nls.localize('menuSeparatorBackground', "Color of a separator menu item in menus."));
|
||||
|
||||
/**
|
||||
* Snippet placeholder colors
|
||||
*/
|
||||
export const snippetTabstopHighlightBackground = registerColor('editor.snippetTabstopHighlightBackground', { dark: new Color(new RGBA(124, 124, 124, 0.3)), light: new Color(new RGBA(10, 50, 100, 0.2)), hc: new Color(new RGBA(124, 124, 124, 0.3)) }, nls.localize('snippetTabstopHighlightBackground', "Highlight background color of a snippet tabstop."));
|
||||
export const snippetTabstopHighlightBorder = registerColor('editor.snippetTabstopHighlightBorder', { dark: null, light: null, hc: null }, nls.localize('snippetTabstopHighlightBorder', "Highlight border color of a snippet tabstop."));
|
||||
export const snippetFinalTabstopHighlightBackground = registerColor('editor.snippetFinalTabstopHighlightBackground', { dark: null, light: null, hc: null }, nls.localize('snippetFinalTabstopHighlightBackground', "Highlight background color of the final tabstop of a snippet."));
|
||||
export const snippetFinalTabstopHighlightBorder = registerColor('editor.snippetFinalTabstopHighlightBorder', { dark: '#525252', light: new Color(new RGBA(10, 50, 100, 0.5)), hc: '#525252' }, nls.localize('snippetFinalTabstopHighlightBorder', "Highlight border color of the final tabstop of a snippet."));
|
||||
|
||||
/**
|
||||
* Breadcrumb colors
|
||||
*/
|
||||
export const breadcrumbsForeground = registerColor('breadcrumb.foreground', { light: transparent(foreground, 0.8), dark: transparent(foreground, 0.8), hc: transparent(foreground, 0.8) }, nls.localize('breadcrumbsFocusForeground', "Color of focused breadcrumb items."));
|
||||
export const breadcrumbsBackground = registerColor('breadcrumb.background', { light: editorBackground, dark: editorBackground, hc: editorBackground }, nls.localize('breadcrumbsBackground', "Background color of breadcrumb items."));
|
||||
export const breadcrumbsFocusForeground = registerColor('breadcrumb.focusForeground', { light: darken(foreground, 0.2), dark: lighten(foreground, 0.1), hc: lighten(foreground, 0.1) }, nls.localize('breadcrumbsFocusForeground', "Color of focused breadcrumb items."));
|
||||
export const breadcrumbsActiveSelectionForeground = registerColor('breadcrumb.activeSelectionForeground', { light: darken(foreground, 0.2), dark: lighten(foreground, 0.1), hc: lighten(foreground, 0.1) }, nls.localize('breadcrumbsSelectedForegound', "Color of selected breadcrumb items."));
|
||||
export const breadcrumbsPickerBackground = registerColor('breadcrumbPicker.background', { light: editorWidgetBackground, dark: editorWidgetBackground, hc: editorWidgetBackground }, nls.localize('breadcrumbsSelectedBackground', "Background color of breadcrumb item picker."));
|
||||
|
||||
/**
|
||||
* Merge-conflict colors
|
||||
*/
|
||||
|
||||
const headerTransparency = 0.5;
|
||||
const currentBaseColor = Color.fromHex('#40C8AE').transparent(headerTransparency);
|
||||
const incomingBaseColor = Color.fromHex('#40A6FF').transparent(headerTransparency);
|
||||
const commonBaseColor = Color.fromHex('#606060').transparent(0.4);
|
||||
const contentTransparency = 0.4;
|
||||
const rulerTransparency = 1;
|
||||
|
||||
export const mergeCurrentHeaderBackground = registerColor('merge.currentHeaderBackground', { dark: currentBaseColor, light: currentBaseColor, hc: null }, nls.localize('mergeCurrentHeaderBackground', 'Current header background in inline merge-conflicts. The color must not be opaque so as not to hide underlying decorations.'), true);
|
||||
export const mergeCurrentContentBackground = registerColor('merge.currentContentBackground', { dark: transparent(mergeCurrentHeaderBackground, contentTransparency), light: transparent(mergeCurrentHeaderBackground, contentTransparency), hc: transparent(mergeCurrentHeaderBackground, contentTransparency) }, nls.localize('mergeCurrentContentBackground', 'Current content background in inline merge-conflicts. The color must not be opaque so as not to hide underlying decorations.'), true);
|
||||
export const mergeIncomingHeaderBackground = registerColor('merge.incomingHeaderBackground', { dark: incomingBaseColor, light: incomingBaseColor, hc: null }, nls.localize('mergeIncomingHeaderBackground', 'Incoming header background in inline merge-conflicts. The color must not be opaque so as not to hide underlying decorations.'), true);
|
||||
export const mergeIncomingContentBackground = registerColor('merge.incomingContentBackground', { dark: transparent(mergeIncomingHeaderBackground, contentTransparency), light: transparent(mergeIncomingHeaderBackground, contentTransparency), hc: transparent(mergeIncomingHeaderBackground, contentTransparency) }, nls.localize('mergeIncomingContentBackground', 'Incoming content background in inline merge-conflicts. The color must not be opaque so as not to hide underlying decorations.'), true);
|
||||
export const mergeCommonHeaderBackground = registerColor('merge.commonHeaderBackground', { dark: commonBaseColor, light: commonBaseColor, hc: null }, nls.localize('mergeCommonHeaderBackground', 'Common ancestor header background in inline merge-conflicts. The color must not be opaque so as not to hide underlying decorations.'), true);
|
||||
export const mergeCommonContentBackground = registerColor('merge.commonContentBackground', { dark: transparent(mergeCommonHeaderBackground, contentTransparency), light: transparent(mergeCommonHeaderBackground, contentTransparency), hc: transparent(mergeCommonHeaderBackground, contentTransparency) }, nls.localize('mergeCommonContentBackground', 'Common ancestor content background in inline merge-conflicts. The color must not be opaque so as not to hide underlying decorations.'), true);
|
||||
|
||||
export const mergeBorder = registerColor('merge.border', { dark: null, light: null, hc: '#C3DF6F' }, nls.localize('mergeBorder', 'Border color on headers and the splitter in inline merge-conflicts.'));
|
||||
|
||||
export const overviewRulerCurrentContentForeground = registerColor('editorOverviewRuler.currentContentForeground', { dark: transparent(mergeCurrentHeaderBackground, rulerTransparency), light: transparent(mergeCurrentHeaderBackground, rulerTransparency), hc: mergeBorder }, nls.localize('overviewRulerCurrentContentForeground', 'Current overview ruler foreground for inline merge-conflicts.'));
|
||||
export const overviewRulerIncomingContentForeground = registerColor('editorOverviewRuler.incomingContentForeground', { dark: transparent(mergeIncomingHeaderBackground, rulerTransparency), light: transparent(mergeIncomingHeaderBackground, rulerTransparency), hc: mergeBorder }, nls.localize('overviewRulerIncomingContentForeground', 'Incoming overview ruler foreground for inline merge-conflicts.'));
|
||||
export const overviewRulerCommonContentForeground = registerColor('editorOverviewRuler.commonContentForeground', { dark: transparent(mergeCommonHeaderBackground, rulerTransparency), light: transparent(mergeCommonHeaderBackground, rulerTransparency), hc: mergeBorder }, nls.localize('overviewRulerCommonContentForeground', 'Common ancestor overview ruler foreground for inline merge-conflicts.'));
|
||||
|
||||
export const overviewRulerFindMatchForeground = registerColor('editorOverviewRuler.findMatchForeground', { dark: '#d186167e', light: '#d186167e', hc: '#AB5A00' }, nls.localize('overviewRulerFindMatchForeground', 'Overview ruler marker color for find matches. The color must not be opaque so as not to hide underlying decorations.'), true);
|
||||
|
||||
export const overviewRulerSelectionHighlightForeground = registerColor('editorOverviewRuler.selectionHighlightForeground', { dark: '#A0A0A0CC', light: '#A0A0A0CC', hc: '#A0A0A0CC' }, nls.localize('overviewRulerSelectionHighlightForeground', 'Overview ruler marker color for selection highlights. The color must not be opaque so as not to hide underlying decorations.'), true);
|
||||
|
||||
export const minimapFindMatch = registerColor('minimap.findMatchHighlight', { light: '#d18616', dark: '#d18616', hc: '#AB5A00' }, nls.localize('minimapFindMatchHighlight', 'Minimap marker color for find matches.'), true);
|
||||
export const minimapSelection = registerColor('minimap.selectionHighlight', { light: '#ADD6FF', dark: '#264F78', hc: '#ffffff' }, nls.localize('minimapSelectionHighlight', 'Minimap marker color for the editor selection.'), true);
|
||||
export const minimapError = registerColor('minimap.errorHighlight', { dark: new Color(new RGBA(255, 18, 18, 0.7)), light: new Color(new RGBA(255, 18, 18, 0.7)), hc: new Color(new RGBA(255, 50, 50, 1)) }, nls.localize('minimapError', 'Minimap marker color for errors.'));
|
||||
export const minimapWarning = registerColor('minimap.warningHighlight', { dark: editorWarningForeground, light: editorWarningForeground, hc: editorWarningBorder }, nls.localize('overviewRuleWarning', 'Minimap marker color for warnings.'));
|
||||
export const minimapBackground = registerColor('minimap.background', { dark: null, light: null, hc: null }, nls.localize('minimapBackground', "Minimap background color."));
|
||||
|
||||
export const minimapSliderBackground = registerColor('minimapSlider.background', { light: transparent(scrollbarSliderBackground, 0.5), dark: transparent(scrollbarSliderBackground, 0.5), hc: transparent(scrollbarSliderBackground, 0.5) }, nls.localize('minimapSliderBackground', "Minimap slider background color."));
|
||||
export const minimapSliderHoverBackground = registerColor('minimapSlider.hoverBackground', { light: transparent(scrollbarSliderHoverBackground, 0.5), dark: transparent(scrollbarSliderHoverBackground, 0.5), hc: transparent(scrollbarSliderHoverBackground, 0.5) }, nls.localize('minimapSliderHoverBackground', "Minimap slider background color when hovering."));
|
||||
export const minimapSliderActiveBackground = registerColor('minimapSlider.activeBackground', { light: transparent(scrollbarSliderActiveBackground, 0.5), dark: transparent(scrollbarSliderActiveBackground, 0.5), hc: transparent(scrollbarSliderActiveBackground, 0.5) }, nls.localize('minimapSliderActiveBackground', "Minimap slider background color when clicked on."));
|
||||
|
||||
export const problemsErrorIconForeground = registerColor('problemsErrorIcon.foreground', { dark: editorErrorForeground, light: editorErrorForeground, hc: editorErrorForeground }, nls.localize('problemsErrorIconForeground', "The color used for the problems error icon."));
|
||||
export const problemsWarningIconForeground = registerColor('problemsWarningIcon.foreground', { dark: editorWarningForeground, light: editorWarningForeground, hc: editorWarningForeground }, nls.localize('problemsWarningIconForeground', "The color used for the problems warning icon."));
|
||||
export const problemsInfoIconForeground = registerColor('problemsInfoIcon.foreground', { dark: editorInfoForeground, light: editorInfoForeground, hc: editorInfoForeground }, nls.localize('problemsInfoIconForeground', "The color used for the problems info icon."));
|
||||
|
||||
/**
|
||||
* Chart colors
|
||||
*/
|
||||
export const chartsForeground = registerColor('charts.foreground', { dark: foreground, light: foreground, hc: foreground }, nls.localize('chartsForeground', "The foreground color used in charts."));
|
||||
export const chartsLines = registerColor('charts.lines', { dark: transparent(foreground, .5), light: transparent(foreground, .5), hc: transparent(foreground, .5) }, nls.localize('chartsLines', "The color used for horizontal lines in charts."));
|
||||
export const chartsRed = registerColor('charts.red', { dark: editorErrorForeground, light: editorErrorForeground, hc: editorErrorForeground }, nls.localize('chartsRed', "The red color used in chart visualizations."));
|
||||
export const chartsBlue = registerColor('charts.blue', { dark: editorInfoForeground, light: editorInfoForeground, hc: editorInfoForeground }, nls.localize('chartsBlue', "The blue color used in chart visualizations."));
|
||||
export const chartsYellow = registerColor('charts.yellow', { dark: editorWarningForeground, light: editorWarningForeground, hc: editorWarningForeground }, nls.localize('chartsYellow', "The yellow color used in chart visualizations."));
|
||||
export const chartsOrange = registerColor('charts.orange', { dark: minimapFindMatch, light: minimapFindMatch, hc: minimapFindMatch }, nls.localize('chartsOrange', "The orange color used in chart visualizations."));
|
||||
export const chartsGreen = registerColor('charts.green', { dark: '#89D185', light: '#388A34', hc: '#89D185' }, nls.localize('chartsGreen', "The green color used in chart visualizations."));
|
||||
export const chartsPurple = registerColor('charts.purple', { dark: '#B180D7', light: '#652D90', hc: '#B180D7' }, nls.localize('chartsPurple', "The purple color used in chart visualizations."));
|
||||
|
||||
// ----- color functions
|
||||
|
||||
export function darken(colorValue: ColorValue, factor: number): ColorFunction {
|
||||
return (theme) => {
|
||||
let color = resolveColorValue(colorValue, theme);
|
||||
if (color) {
|
||||
return color.darken(factor);
|
||||
}
|
||||
return undefined;
|
||||
};
|
||||
}
|
||||
|
||||
export function lighten(colorValue: ColorValue, factor: number): ColorFunction {
|
||||
return (theme) => {
|
||||
let color = resolveColorValue(colorValue, theme);
|
||||
if (color) {
|
||||
return color.lighten(factor);
|
||||
}
|
||||
return undefined;
|
||||
};
|
||||
}
|
||||
|
||||
export function transparent(colorValue: ColorValue, factor: number): ColorFunction {
|
||||
return (theme) => {
|
||||
let color = resolveColorValue(colorValue, theme);
|
||||
if (color) {
|
||||
return color.transparent(factor);
|
||||
}
|
||||
return undefined;
|
||||
};
|
||||
}
|
||||
|
||||
export function oneOf(...colorValues: ColorValue[]): ColorFunction {
|
||||
return (theme) => {
|
||||
for (let colorValue of colorValues) {
|
||||
let color = resolveColorValue(colorValue, theme);
|
||||
if (color) {
|
||||
return color;
|
||||
}
|
||||
}
|
||||
return undefined;
|
||||
};
|
||||
}
|
||||
|
||||
function lessProminent(colorValue: ColorValue, backgroundColorValue: ColorValue, factor: number, transparency: number): ColorFunction {
|
||||
return (theme) => {
|
||||
let from = resolveColorValue(colorValue, theme);
|
||||
if (from) {
|
||||
let backgroundColor = resolveColorValue(backgroundColorValue, theme);
|
||||
if (backgroundColor) {
|
||||
if (from.isDarkerThan(backgroundColor)) {
|
||||
return Color.getLighterColor(from, backgroundColor, factor).transparent(transparency);
|
||||
}
|
||||
return Color.getDarkerColor(from, backgroundColor, factor).transparent(transparency);
|
||||
}
|
||||
return from.transparent(factor * transparency);
|
||||
}
|
||||
return undefined;
|
||||
};
|
||||
}
|
||||
|
||||
// ----- implementation
|
||||
|
||||
/**
|
||||
* @param colorValue Resolve a color value in the context of a theme
|
||||
*/
|
||||
export function resolveColorValue(colorValue: ColorValue | null, theme: IColorTheme): Color | undefined {
|
||||
if (colorValue === null) {
|
||||
return undefined;
|
||||
} else if (typeof colorValue === 'string') {
|
||||
if (colorValue[0] === '#') {
|
||||
return Color.fromHex(colorValue);
|
||||
}
|
||||
return theme.getColor(colorValue);
|
||||
} else if (colorValue instanceof Color) {
|
||||
return colorValue;
|
||||
} else if (typeof colorValue === 'function') {
|
||||
return colorValue(theme);
|
||||
}
|
||||
return undefined;
|
||||
}
|
||||
|
||||
export const workbenchColorsSchemaId = 'vscode://schemas/workbench-colors';
|
||||
|
||||
let schemaRegistry = platform.Registry.as<IJSONContributionRegistry>(JSONExtensions.JSONContribution);
|
||||
schemaRegistry.registerSchema(workbenchColorsSchemaId, colorRegistry.getColorSchema());
|
||||
|
||||
const delayer = new RunOnceScheduler(() => schemaRegistry.notifySchemaChanged(workbenchColorsSchemaId), 200);
|
||||
colorRegistry.onDidChangeSchema(() => {
|
||||
if (!delayer.isScheduled()) {
|
||||
delayer.schedule();
|
||||
}
|
||||
});
|
||||
|
||||
// setTimeout(_ => console.log(colorRegistry.toString()), 5000);
|
||||
216
lib/vscode/src/vs/platform/theme/common/iconRegistry.ts
Normal file
216
lib/vscode/src/vs/platform/theme/common/iconRegistry.ts
Normal file
@@ -0,0 +1,216 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import * as platform from 'vs/platform/registry/common/platform';
|
||||
import { IJSONSchema, IJSONSchemaMap } from 'vs/base/common/jsonSchema';
|
||||
import { ThemeIcon } from 'vs/platform/theme/common/themeService';
|
||||
import { Event, Emitter } from 'vs/base/common/event';
|
||||
import { localize } from 'vs/nls';
|
||||
import { Extensions as JSONExtensions, IJSONContributionRegistry } from 'vs/platform/jsonschemas/common/jsonContributionRegistry';
|
||||
import { RunOnceScheduler } from 'vs/base/common/async';
|
||||
import * as Codicons from 'vs/base/common/codicons';
|
||||
|
||||
// ------ API types
|
||||
|
||||
|
||||
// color registry
|
||||
export const Extensions = {
|
||||
IconContribution: 'base.contributions.icons'
|
||||
};
|
||||
|
||||
export type IconDefaults = ThemeIcon | IconDefinition;
|
||||
|
||||
export interface IconDefinition {
|
||||
fontId?: string;
|
||||
character: string;
|
||||
}
|
||||
|
||||
export interface IconContribution {
|
||||
id: string;
|
||||
description: string;
|
||||
deprecationMessage?: string;
|
||||
defaults: IconDefaults;
|
||||
}
|
||||
|
||||
export interface IIconRegistry {
|
||||
|
||||
readonly onDidChangeSchema: Event<void>;
|
||||
|
||||
/**
|
||||
* Register a icon to the registry.
|
||||
* @param id The icon id
|
||||
* @param defaults The default values
|
||||
* @description the description
|
||||
*/
|
||||
registerIcon(id: string, defaults: IconDefaults, description: string): ThemeIcon;
|
||||
|
||||
/**
|
||||
* Register a icon to the registry.
|
||||
*/
|
||||
deregisterIcon(id: string): void;
|
||||
|
||||
/**
|
||||
* Get all icon contributions
|
||||
*/
|
||||
getIcons(): IconContribution[];
|
||||
|
||||
/**
|
||||
* Get the icon for the given id
|
||||
*/
|
||||
getIcon(id: string): IconContribution | undefined;
|
||||
|
||||
/**
|
||||
* JSON schema for an object to assign icon values to one of the color contributions.
|
||||
*/
|
||||
getIconSchema(): IJSONSchema;
|
||||
|
||||
/**
|
||||
* JSON schema to for a reference to a icon contribution.
|
||||
*/
|
||||
getIconReferenceSchema(): IJSONSchema;
|
||||
|
||||
}
|
||||
|
||||
class IconRegistry implements IIconRegistry {
|
||||
|
||||
private readonly _onDidChangeSchema = new Emitter<void>();
|
||||
readonly onDidChangeSchema: Event<void> = this._onDidChangeSchema.event;
|
||||
|
||||
private iconsById: { [key: string]: IconContribution };
|
||||
private iconSchema: IJSONSchema & { properties: IJSONSchemaMap } = {
|
||||
definitions: {
|
||||
icons: {
|
||||
type: 'object',
|
||||
properties: {
|
||||
fontId: { type: 'string', description: localize('iconDefintion.fontId', 'The id of the font to use. If not set, the font that is defined first is used.') },
|
||||
fontCharacter: { type: 'string', description: localize('iconDefintion.fontCharacter', 'The font character associated with the icon definition.') }
|
||||
},
|
||||
additionalProperties: false,
|
||||
defaultSnippets: [{ body: { fontCharacter: '\\\\e030' } }]
|
||||
}
|
||||
},
|
||||
type: 'object',
|
||||
properties: {}
|
||||
};
|
||||
private iconReferenceSchema: IJSONSchema & { enum: string[], enumDescriptions: string[] } = { type: 'string', enum: [], enumDescriptions: [] };
|
||||
|
||||
constructor() {
|
||||
this.iconsById = {};
|
||||
}
|
||||
|
||||
public registerIcon(id: string, defaults: IconDefaults, description?: string, deprecationMessage?: string): ThemeIcon {
|
||||
if (!description) {
|
||||
description = localize('icon.defaultDescription', 'Icon with identifier \'{0}\'', id);
|
||||
}
|
||||
let iconContribution: IconContribution = { id, description, defaults, deprecationMessage };
|
||||
this.iconsById[id] = iconContribution;
|
||||
let propertySchema: IJSONSchema = { $ref: '#/definitions/icons' };
|
||||
if (deprecationMessage) {
|
||||
propertySchema.deprecationMessage = deprecationMessage;
|
||||
}
|
||||
propertySchema.markdownDescription = `${description}: $(${id})`;
|
||||
this.iconSchema.properties[id] = propertySchema;
|
||||
this.iconReferenceSchema.enum.push(id);
|
||||
this.iconReferenceSchema.enumDescriptions.push(description);
|
||||
|
||||
this._onDidChangeSchema.fire();
|
||||
return { id };
|
||||
}
|
||||
|
||||
|
||||
public deregisterIcon(id: string): void {
|
||||
delete this.iconsById[id];
|
||||
delete this.iconSchema.properties[id];
|
||||
const index = this.iconReferenceSchema.enum.indexOf(id);
|
||||
if (index !== -1) {
|
||||
this.iconReferenceSchema.enum.splice(index, 1);
|
||||
this.iconReferenceSchema.enumDescriptions.splice(index, 1);
|
||||
}
|
||||
this._onDidChangeSchema.fire();
|
||||
}
|
||||
|
||||
public getIcons(): IconContribution[] {
|
||||
return Object.keys(this.iconsById).map(id => this.iconsById[id]);
|
||||
}
|
||||
|
||||
public getIcon(id: string): IconContribution | undefined {
|
||||
return this.iconsById[id];
|
||||
}
|
||||
|
||||
public getIconSchema(): IJSONSchema {
|
||||
return this.iconSchema;
|
||||
}
|
||||
|
||||
public getIconReferenceSchema(): IJSONSchema {
|
||||
return this.iconReferenceSchema;
|
||||
}
|
||||
|
||||
public toString() {
|
||||
const sorter = (i1: IconContribution, i2: IconContribution) => {
|
||||
const isThemeIcon1 = ThemeIcon.isThemeIcon(i1.defaults);
|
||||
const isThemeIcon2 = ThemeIcon.isThemeIcon(i2.defaults);
|
||||
if (isThemeIcon1 !== isThemeIcon2) {
|
||||
return isThemeIcon1 ? -1 : 1;
|
||||
}
|
||||
return i1.id.localeCompare(i2.id);
|
||||
};
|
||||
const classNames = (i: IconContribution) => {
|
||||
while (ThemeIcon.isThemeIcon(i.defaults)) {
|
||||
i = this.iconsById[i.defaults.id];
|
||||
}
|
||||
return `codicon codicon-${i ? i.id : ''}`;
|
||||
};
|
||||
|
||||
let reference = [];
|
||||
let docCss = [];
|
||||
|
||||
const contributions = Object.keys(this.iconsById).map(key => this.iconsById[key]);
|
||||
|
||||
for (const i of contributions.sort(sorter)) {
|
||||
reference.push(`|<i class="${classNames(i)}"></i>|${i.id}|${ThemeIcon.isThemeIcon(i.defaults) ? i.defaults.id : ''}|`);
|
||||
|
||||
if (!ThemeIcon.isThemeIcon((i.defaults))) {
|
||||
docCss.push(`.codicon-${i.id}:before { content: "${i.defaults.character}" }`);
|
||||
}
|
||||
}
|
||||
return reference.join('\n') + '\n\n' + docCss.join('\n');
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
const iconRegistry = new IconRegistry();
|
||||
platform.Registry.add(Extensions.IconContribution, iconRegistry);
|
||||
|
||||
export function registerIcon(id: string, defaults: IconDefaults, description?: string, deprecationMessage?: string): ThemeIcon {
|
||||
return iconRegistry.registerIcon(id, defaults, description, deprecationMessage);
|
||||
}
|
||||
|
||||
export function getIconRegistry(): IIconRegistry {
|
||||
return iconRegistry;
|
||||
}
|
||||
|
||||
function initialize() {
|
||||
for (const icon of Codicons.iconRegistry.all) {
|
||||
registerIcon(icon.id, icon.definition);
|
||||
}
|
||||
Codicons.iconRegistry.onDidRegister(icon => registerIcon(icon.id, icon.definition));
|
||||
}
|
||||
initialize();
|
||||
|
||||
|
||||
export const iconsSchemaId = 'vscode://schemas/icons';
|
||||
|
||||
let schemaRegistry = platform.Registry.as<IJSONContributionRegistry>(JSONExtensions.JSONContribution);
|
||||
schemaRegistry.registerSchema(iconsSchemaId, iconRegistry.getIconSchema());
|
||||
|
||||
const delayer = new RunOnceScheduler(() => schemaRegistry.notifySchemaChanged(iconsSchemaId), 200);
|
||||
iconRegistry.onDidChangeSchema(() => {
|
||||
if (!delayer.isScheduled()) {
|
||||
delayer.schedule();
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
//setTimeout(_ => console.log(iconRegistry.toString()), 5000);
|
||||
391
lib/vscode/src/vs/platform/theme/common/styler.ts
Normal file
391
lib/vscode/src/vs/platform/theme/common/styler.ts
Normal file
@@ -0,0 +1,391 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { IColorTheme, IThemeService } from 'vs/platform/theme/common/themeService';
|
||||
import { focusBorder, inputBackground, inputForeground, ColorIdentifier, selectForeground, selectBackground, selectListBackground, selectBorder, inputBorder, foreground, editorBackground, contrastBorder, inputActiveOptionBorder, inputActiveOptionBackground, inputActiveOptionForeground, listFocusBackground, listFocusForeground, listActiveSelectionBackground, listActiveSelectionForeground, listInactiveSelectionForeground, listInactiveSelectionBackground, listInactiveFocusBackground, listHoverBackground, listHoverForeground, listDropBackground, pickerGroupBorder, pickerGroupForeground, widgetShadow, inputValidationInfoBorder, inputValidationInfoBackground, inputValidationWarningBorder, inputValidationWarningBackground, inputValidationErrorBorder, inputValidationErrorBackground, activeContrastBorder, buttonForeground, buttonBackground, buttonHoverBackground, ColorFunction, badgeBackground, badgeForeground, progressBarBackground, breadcrumbsForeground, breadcrumbsFocusForeground, breadcrumbsActiveSelectionForeground, breadcrumbsBackground, editorWidgetBorder, inputValidationInfoForeground, inputValidationWarningForeground, inputValidationErrorForeground, menuForeground, menuBackground, menuSelectionForeground, menuSelectionBackground, menuSelectionBorder, menuBorder, menuSeparatorBackground, darken, listFilterWidgetOutline, listFilterWidgetNoMatchesOutline, listFilterWidgetBackground, editorWidgetBackground, treeIndentGuidesStroke, editorWidgetForeground, simpleCheckboxBackground, simpleCheckboxBorder, simpleCheckboxForeground, ColorValue, resolveColorValue, textLinkForeground, problemsWarningIconForeground, problemsErrorIconForeground, problemsInfoIconForeground, buttonSecondaryBackground, buttonSecondaryForeground, buttonSecondaryHoverBackground } from 'vs/platform/theme/common/colorRegistry';
|
||||
import { IDisposable } from 'vs/base/common/lifecycle';
|
||||
import { Color } from 'vs/base/common/color';
|
||||
import { IThemable, styleFn } from 'vs/base/common/styler';
|
||||
|
||||
export interface IStyleOverrides {
|
||||
[color: string]: ColorIdentifier | undefined;
|
||||
}
|
||||
|
||||
export interface IColorMapping {
|
||||
[optionsKey: string]: ColorValue | undefined;
|
||||
}
|
||||
|
||||
export interface IComputedStyles {
|
||||
[color: string]: Color | undefined;
|
||||
}
|
||||
|
||||
export function computeStyles(theme: IColorTheme, styleMap: IColorMapping): IComputedStyles {
|
||||
const styles = Object.create(null) as IComputedStyles;
|
||||
for (let key in styleMap) {
|
||||
const value = styleMap[key];
|
||||
if (value) {
|
||||
styles[key] = resolveColorValue(value, theme);
|
||||
}
|
||||
}
|
||||
|
||||
return styles;
|
||||
}
|
||||
|
||||
export function attachStyler<T extends IColorMapping>(themeService: IThemeService, styleMap: T, widgetOrCallback: IThemable | styleFn): IDisposable {
|
||||
function applyStyles(theme: IColorTheme): void {
|
||||
const styles = computeStyles(themeService.getColorTheme(), styleMap);
|
||||
|
||||
if (typeof widgetOrCallback === 'function') {
|
||||
widgetOrCallback(styles);
|
||||
} else {
|
||||
widgetOrCallback.style(styles);
|
||||
}
|
||||
}
|
||||
|
||||
applyStyles(themeService.getColorTheme());
|
||||
|
||||
return themeService.onDidColorThemeChange(applyStyles);
|
||||
}
|
||||
|
||||
export interface ICheckboxStyleOverrides extends IStyleOverrides {
|
||||
inputActiveOptionBorderColor?: ColorIdentifier;
|
||||
inputActiveOptionForegroundColor?: ColorIdentifier;
|
||||
inputActiveOptionBackgroundColor?: ColorIdentifier;
|
||||
}
|
||||
|
||||
export function attachCheckboxStyler(widget: IThemable, themeService: IThemeService, style?: ICheckboxStyleOverrides): IDisposable {
|
||||
return attachStyler(themeService, {
|
||||
inputActiveOptionBorder: (style && style.inputActiveOptionBorderColor) || inputActiveOptionBorder,
|
||||
inputActiveOptionForeground: (style && style.inputActiveOptionForegroundColor) || inputActiveOptionForeground,
|
||||
inputActiveOptionBackground: (style && style.inputActiveOptionBackgroundColor) || inputActiveOptionBackground
|
||||
} as ICheckboxStyleOverrides, widget);
|
||||
}
|
||||
|
||||
export interface IBadgeStyleOverrides extends IStyleOverrides {
|
||||
badgeBackground?: ColorIdentifier;
|
||||
badgeForeground?: ColorIdentifier;
|
||||
}
|
||||
|
||||
export function attachBadgeStyler(widget: IThemable, themeService: IThemeService, style?: IBadgeStyleOverrides): IDisposable {
|
||||
return attachStyler(themeService, {
|
||||
badgeBackground: (style && style.badgeBackground) || badgeBackground,
|
||||
badgeForeground: (style && style.badgeForeground) || badgeForeground,
|
||||
badgeBorder: contrastBorder
|
||||
} as IBadgeStyleOverrides, widget);
|
||||
}
|
||||
|
||||
export interface IInputBoxStyleOverrides extends IStyleOverrides {
|
||||
inputBackground?: ColorIdentifier;
|
||||
inputForeground?: ColorIdentifier;
|
||||
inputBorder?: ColorIdentifier;
|
||||
inputActiveOptionBorder?: ColorIdentifier;
|
||||
inputActiveOptionForeground?: ColorIdentifier;
|
||||
inputActiveOptionBackground?: ColorIdentifier;
|
||||
inputValidationInfoBorder?: ColorIdentifier;
|
||||
inputValidationInfoBackground?: ColorIdentifier;
|
||||
inputValidationInfoForeground?: ColorIdentifier;
|
||||
inputValidationWarningBorder?: ColorIdentifier;
|
||||
inputValidationWarningBackground?: ColorIdentifier;
|
||||
inputValidationWarningForeground?: ColorIdentifier;
|
||||
inputValidationErrorBorder?: ColorIdentifier;
|
||||
inputValidationErrorBackground?: ColorIdentifier;
|
||||
inputValidationErrorForeground?: ColorIdentifier;
|
||||
}
|
||||
|
||||
export function attachInputBoxStyler(widget: IThemable, themeService: IThemeService, style?: IInputBoxStyleOverrides): IDisposable {
|
||||
return attachStyler(themeService, {
|
||||
inputBackground: (style && style.inputBackground) || inputBackground,
|
||||
inputForeground: (style && style.inputForeground) || inputForeground,
|
||||
inputBorder: (style && style.inputBorder) || inputBorder,
|
||||
inputValidationInfoBorder: (style && style.inputValidationInfoBorder) || inputValidationInfoBorder,
|
||||
inputValidationInfoBackground: (style && style.inputValidationInfoBackground) || inputValidationInfoBackground,
|
||||
inputValidationInfoForeground: (style && style.inputValidationInfoForeground) || inputValidationInfoForeground,
|
||||
inputValidationWarningBorder: (style && style.inputValidationWarningBorder) || inputValidationWarningBorder,
|
||||
inputValidationWarningBackground: (style && style.inputValidationWarningBackground) || inputValidationWarningBackground,
|
||||
inputValidationWarningForeground: (style && style.inputValidationWarningForeground) || inputValidationWarningForeground,
|
||||
inputValidationErrorBorder: (style && style.inputValidationErrorBorder) || inputValidationErrorBorder,
|
||||
inputValidationErrorBackground: (style && style.inputValidationErrorBackground) || inputValidationErrorBackground,
|
||||
inputValidationErrorForeground: (style && style.inputValidationErrorForeground) || inputValidationErrorForeground
|
||||
} as IInputBoxStyleOverrides, widget);
|
||||
}
|
||||
|
||||
export interface ISelectBoxStyleOverrides extends IStyleOverrides, IListStyleOverrides {
|
||||
selectBackground?: ColorIdentifier;
|
||||
selectListBackground?: ColorIdentifier;
|
||||
selectForeground?: ColorIdentifier;
|
||||
decoratorRightForeground?: ColorIdentifier;
|
||||
selectBorder?: ColorIdentifier;
|
||||
focusBorder?: ColorIdentifier;
|
||||
}
|
||||
|
||||
export function attachSelectBoxStyler(widget: IThemable, themeService: IThemeService, style?: ISelectBoxStyleOverrides): IDisposable {
|
||||
return attachStyler(themeService, {
|
||||
selectBackground: (style && style.selectBackground) || selectBackground,
|
||||
selectListBackground: (style && style.selectListBackground) || selectListBackground,
|
||||
selectForeground: (style && style.selectForeground) || selectForeground,
|
||||
decoratorRightForeground: (style && style.pickerGroupForeground) || pickerGroupForeground,
|
||||
selectBorder: (style && style.selectBorder) || selectBorder,
|
||||
focusBorder: (style && style.focusBorder) || focusBorder,
|
||||
listFocusBackground: (style && style.listFocusBackground) || listFocusBackground,
|
||||
listFocusForeground: (style && style.listFocusForeground) || listFocusForeground,
|
||||
listFocusOutline: (style && style.listFocusOutline) || activeContrastBorder,
|
||||
listHoverBackground: (style && style.listHoverBackground) || listHoverBackground,
|
||||
listHoverForeground: (style && style.listHoverForeground) || listHoverForeground,
|
||||
listHoverOutline: (style && style.listFocusOutline) || activeContrastBorder,
|
||||
selectListBorder: (style && style.selectListBorder) || editorWidgetBorder
|
||||
} as ISelectBoxStyleOverrides, widget);
|
||||
}
|
||||
|
||||
export function attachFindReplaceInputBoxStyler(widget: IThemable, themeService: IThemeService, style?: IInputBoxStyleOverrides): IDisposable {
|
||||
return attachStyler(themeService, {
|
||||
inputBackground: (style && style.inputBackground) || inputBackground,
|
||||
inputForeground: (style && style.inputForeground) || inputForeground,
|
||||
inputBorder: (style && style.inputBorder) || inputBorder,
|
||||
inputActiveOptionBorder: (style && style.inputActiveOptionBorder) || inputActiveOptionBorder,
|
||||
inputActiveOptionForeground: (style && style.inputActiveOptionForeground) || inputActiveOptionForeground,
|
||||
inputActiveOptionBackground: (style && style.inputActiveOptionBackground) || inputActiveOptionBackground,
|
||||
inputValidationInfoBorder: (style && style.inputValidationInfoBorder) || inputValidationInfoBorder,
|
||||
inputValidationInfoBackground: (style && style.inputValidationInfoBackground) || inputValidationInfoBackground,
|
||||
inputValidationInfoForeground: (style && style.inputValidationInfoForeground) || inputValidationInfoForeground,
|
||||
inputValidationWarningBorder: (style && style.inputValidationWarningBorder) || inputValidationWarningBorder,
|
||||
inputValidationWarningBackground: (style && style.inputValidationWarningBackground) || inputValidationWarningBackground,
|
||||
inputValidationWarningForeground: (style && style.inputValidationWarningForeground) || inputValidationWarningForeground,
|
||||
inputValidationErrorBorder: (style && style.inputValidationErrorBorder) || inputValidationErrorBorder,
|
||||
inputValidationErrorBackground: (style && style.inputValidationErrorBackground) || inputValidationErrorBackground,
|
||||
inputValidationErrorForeground: (style && style.inputValidationErrorForeground) || inputValidationErrorForeground
|
||||
} as IInputBoxStyleOverrides, widget);
|
||||
}
|
||||
|
||||
export interface IQuickInputStyleOverrides extends IListStyleOverrides, IInputBoxStyleOverrides, IProgressBarStyleOverrides {
|
||||
foreground?: ColorIdentifier;
|
||||
background?: ColorIdentifier;
|
||||
borderColor?: ColorIdentifier;
|
||||
widgetShadow?: ColorIdentifier;
|
||||
pickerGroupForeground?: ColorIdentifier;
|
||||
pickerGroupBorder?: ColorIdentifier;
|
||||
}
|
||||
|
||||
export function attachQuickInputStyler(widget: IThemable, themeService: IThemeService, style?: IQuickInputStyleOverrides): IDisposable {
|
||||
return attachStyler(themeService, {
|
||||
foreground: (style && style.foreground) || foreground,
|
||||
background: (style && style.background) || editorBackground,
|
||||
borderColor: style && style.borderColor || contrastBorder,
|
||||
widgetShadow: style && style.widgetShadow || widgetShadow,
|
||||
progressBarBackground: style && style.progressBarBackground || progressBarBackground,
|
||||
pickerGroupForeground: style && style.pickerGroupForeground || pickerGroupForeground,
|
||||
pickerGroupBorder: style && style.pickerGroupBorder || pickerGroupBorder,
|
||||
inputBackground: (style && style.inputBackground) || inputBackground,
|
||||
inputForeground: (style && style.inputForeground) || inputForeground,
|
||||
inputBorder: (style && style.inputBorder) || inputBorder,
|
||||
inputValidationInfoBorder: (style && style.inputValidationInfoBorder) || inputValidationInfoBorder,
|
||||
inputValidationInfoBackground: (style && style.inputValidationInfoBackground) || inputValidationInfoBackground,
|
||||
inputValidationInfoForeground: (style && style.inputValidationInfoForeground) || inputValidationInfoForeground,
|
||||
inputValidationWarningBorder: (style && style.inputValidationWarningBorder) || inputValidationWarningBorder,
|
||||
inputValidationWarningBackground: (style && style.inputValidationWarningBackground) || inputValidationWarningBackground,
|
||||
inputValidationWarningForeground: (style && style.inputValidationWarningForeground) || inputValidationWarningForeground,
|
||||
inputValidationErrorBorder: (style && style.inputValidationErrorBorder) || inputValidationErrorBorder,
|
||||
inputValidationErrorBackground: (style && style.inputValidationErrorBackground) || inputValidationErrorBackground,
|
||||
inputValidationErrorForeground: (style && style.inputValidationErrorForeground) || inputValidationErrorForeground,
|
||||
listFocusBackground: (style && style.listFocusBackground) || listFocusBackground,
|
||||
listFocusForeground: (style && style.listFocusForeground) || listFocusForeground,
|
||||
listActiveSelectionBackground: (style && style.listActiveSelectionBackground) || darken(listActiveSelectionBackground, 0.1),
|
||||
listActiveSelectionForeground: (style && style.listActiveSelectionForeground) || listActiveSelectionForeground,
|
||||
listFocusAndSelectionBackground: style && style.listFocusAndSelectionBackground || listActiveSelectionBackground,
|
||||
listFocusAndSelectionForeground: (style && style.listFocusAndSelectionForeground) || listActiveSelectionForeground,
|
||||
listInactiveSelectionBackground: (style && style.listInactiveSelectionBackground) || listInactiveSelectionBackground,
|
||||
listInactiveSelectionForeground: (style && style.listInactiveSelectionForeground) || listInactiveSelectionForeground,
|
||||
listInactiveFocusBackground: (style && style.listInactiveFocusBackground) || listInactiveFocusBackground,
|
||||
listHoverBackground: (style && style.listHoverBackground) || listHoverBackground,
|
||||
listHoverForeground: (style && style.listHoverForeground) || listHoverForeground,
|
||||
listDropBackground: (style && style.listDropBackground) || listDropBackground,
|
||||
listFocusOutline: (style && style.listFocusOutline) || activeContrastBorder,
|
||||
listSelectionOutline: (style && style.listSelectionOutline) || activeContrastBorder,
|
||||
listHoverOutline: (style && style.listHoverOutline) || activeContrastBorder
|
||||
} as IQuickInputStyleOverrides, widget);
|
||||
}
|
||||
|
||||
export interface IListStyleOverrides extends IStyleOverrides {
|
||||
listBackground?: ColorIdentifier;
|
||||
listFocusBackground?: ColorIdentifier;
|
||||
listFocusForeground?: ColorIdentifier;
|
||||
listActiveSelectionBackground?: ColorIdentifier;
|
||||
listActiveSelectionForeground?: ColorIdentifier;
|
||||
listFocusAndSelectionBackground?: ColorIdentifier;
|
||||
listFocusAndSelectionForeground?: ColorIdentifier;
|
||||
listInactiveSelectionBackground?: ColorIdentifier;
|
||||
listInactiveSelectionForeground?: ColorIdentifier;
|
||||
listInactiveFocusBackground?: ColorIdentifier;
|
||||
listHoverBackground?: ColorIdentifier;
|
||||
listHoverForeground?: ColorIdentifier;
|
||||
listDropBackground?: ColorIdentifier;
|
||||
listFocusOutline?: ColorIdentifier;
|
||||
listInactiveFocusOutline?: ColorIdentifier;
|
||||
listSelectionOutline?: ColorIdentifier;
|
||||
listHoverOutline?: ColorIdentifier;
|
||||
listFilterWidgetBackground?: ColorIdentifier;
|
||||
listFilterWidgetOutline?: ColorIdentifier;
|
||||
listFilterWidgetNoMatchesOutline?: ColorIdentifier;
|
||||
listMatchesShadow?: ColorIdentifier;
|
||||
treeIndentGuidesStroke?: ColorIdentifier;
|
||||
}
|
||||
|
||||
export function attachListStyler(widget: IThemable, themeService: IThemeService, overrides?: IColorMapping): IDisposable {
|
||||
return attachStyler(themeService, { ...defaultListStyles, ...(overrides || {}) }, widget);
|
||||
}
|
||||
|
||||
export const defaultListStyles: IColorMapping = {
|
||||
listFocusBackground: listFocusBackground,
|
||||
listFocusForeground: listFocusForeground,
|
||||
listActiveSelectionBackground: darken(listActiveSelectionBackground, 0.1),
|
||||
listActiveSelectionForeground: listActiveSelectionForeground,
|
||||
listFocusAndSelectionBackground: listActiveSelectionBackground,
|
||||
listFocusAndSelectionForeground: listActiveSelectionForeground,
|
||||
listInactiveSelectionBackground: listInactiveSelectionBackground,
|
||||
listInactiveSelectionForeground: listInactiveSelectionForeground,
|
||||
listInactiveFocusBackground: listInactiveFocusBackground,
|
||||
listHoverBackground: listHoverBackground,
|
||||
listHoverForeground: listHoverForeground,
|
||||
listDropBackground: listDropBackground,
|
||||
listFocusOutline: activeContrastBorder,
|
||||
listSelectionOutline: activeContrastBorder,
|
||||
listHoverOutline: activeContrastBorder,
|
||||
listFilterWidgetBackground: listFilterWidgetBackground,
|
||||
listFilterWidgetOutline: listFilterWidgetOutline,
|
||||
listFilterWidgetNoMatchesOutline: listFilterWidgetNoMatchesOutline,
|
||||
listMatchesShadow: widgetShadow,
|
||||
treeIndentGuidesStroke: treeIndentGuidesStroke
|
||||
};
|
||||
|
||||
export interface IButtonStyleOverrides extends IStyleOverrides {
|
||||
buttonForeground?: ColorIdentifier;
|
||||
buttonBackground?: ColorIdentifier;
|
||||
buttonHoverBackground?: ColorIdentifier;
|
||||
buttonSecondaryForeground?: ColorIdentifier;
|
||||
buttonSecondaryBackground?: ColorIdentifier;
|
||||
buttonSecondaryHoverBackground?: ColorIdentifier;
|
||||
}
|
||||
|
||||
export function attachButtonStyler(widget: IThemable, themeService: IThemeService, style?: IButtonStyleOverrides): IDisposable {
|
||||
return attachStyler(themeService, {
|
||||
buttonForeground: (style && style.buttonForeground) || buttonForeground,
|
||||
buttonBackground: (style && style.buttonBackground) || buttonBackground,
|
||||
buttonHoverBackground: (style && style.buttonHoverBackground) || buttonHoverBackground,
|
||||
buttonSecondaryForeground: (style && style.buttonSecondaryForeground) || buttonSecondaryForeground,
|
||||
buttonSecondaryBackground: (style && style.buttonSecondaryBackground) || buttonSecondaryBackground,
|
||||
buttonSecondaryHoverBackground: (style && style.buttonSecondaryHoverBackground) || buttonSecondaryHoverBackground,
|
||||
buttonBorder: contrastBorder
|
||||
} as IButtonStyleOverrides, widget);
|
||||
}
|
||||
|
||||
export interface ILinkStyleOverrides extends IStyleOverrides {
|
||||
textLinkForeground?: ColorIdentifier;
|
||||
}
|
||||
|
||||
export function attachLinkStyler(widget: IThemable, themeService: IThemeService, style?: ILinkStyleOverrides): IDisposable {
|
||||
return attachStyler(themeService, {
|
||||
textLinkForeground: (style && style.textLinkForeground) || textLinkForeground,
|
||||
} as ILinkStyleOverrides, widget);
|
||||
}
|
||||
|
||||
export interface IProgressBarStyleOverrides extends IStyleOverrides {
|
||||
progressBarBackground?: ColorIdentifier;
|
||||
}
|
||||
|
||||
export function attachProgressBarStyler(widget: IThemable, themeService: IThemeService, style?: IProgressBarStyleOverrides): IDisposable {
|
||||
return attachStyler(themeService, {
|
||||
progressBarBackground: (style && style.progressBarBackground) || progressBarBackground
|
||||
} as IProgressBarStyleOverrides, widget);
|
||||
}
|
||||
|
||||
export function attachStylerCallback(themeService: IThemeService, colors: { [name: string]: ColorIdentifier }, callback: styleFn): IDisposable {
|
||||
return attachStyler(themeService, colors, callback);
|
||||
}
|
||||
|
||||
export interface IBreadcrumbsWidgetStyleOverrides extends IColorMapping {
|
||||
breadcrumbsBackground?: ColorIdentifier | ColorFunction;
|
||||
breadcrumbsForeground?: ColorIdentifier;
|
||||
breadcrumbsHoverForeground?: ColorIdentifier;
|
||||
breadcrumbsFocusForeground?: ColorIdentifier;
|
||||
breadcrumbsFocusAndSelectionForeground?: ColorIdentifier;
|
||||
}
|
||||
|
||||
export const defaultBreadcrumbsStyles = <IBreadcrumbsWidgetStyleOverrides>{
|
||||
breadcrumbsBackground: breadcrumbsBackground,
|
||||
breadcrumbsForeground: breadcrumbsForeground,
|
||||
breadcrumbsHoverForeground: breadcrumbsFocusForeground,
|
||||
breadcrumbsFocusForeground: breadcrumbsFocusForeground,
|
||||
breadcrumbsFocusAndSelectionForeground: breadcrumbsActiveSelectionForeground,
|
||||
};
|
||||
|
||||
export function attachBreadcrumbsStyler(widget: IThemable, themeService: IThemeService, style?: IBreadcrumbsWidgetStyleOverrides): IDisposable {
|
||||
return attachStyler(themeService, { ...defaultBreadcrumbsStyles, ...style }, widget);
|
||||
}
|
||||
|
||||
export interface IMenuStyleOverrides extends IColorMapping {
|
||||
shadowColor?: ColorIdentifier;
|
||||
borderColor?: ColorIdentifier;
|
||||
foregroundColor?: ColorIdentifier;
|
||||
backgroundColor?: ColorIdentifier;
|
||||
selectionForegroundColor?: ColorIdentifier;
|
||||
selectionBackgroundColor?: ColorIdentifier;
|
||||
selectionBorderColor?: ColorIdentifier;
|
||||
separatorColor?: ColorIdentifier;
|
||||
}
|
||||
|
||||
export const defaultMenuStyles = <IMenuStyleOverrides>{
|
||||
shadowColor: widgetShadow,
|
||||
borderColor: menuBorder,
|
||||
foregroundColor: menuForeground,
|
||||
backgroundColor: menuBackground,
|
||||
selectionForegroundColor: menuSelectionForeground,
|
||||
selectionBackgroundColor: menuSelectionBackground,
|
||||
selectionBorderColor: menuSelectionBorder,
|
||||
separatorColor: menuSeparatorBackground
|
||||
};
|
||||
|
||||
export function attachMenuStyler(widget: IThemable, themeService: IThemeService, style?: IMenuStyleOverrides): IDisposable {
|
||||
return attachStyler(themeService, { ...defaultMenuStyles, ...style }, widget);
|
||||
}
|
||||
|
||||
export interface IDialogStyleOverrides extends IButtonStyleOverrides {
|
||||
dialogForeground?: ColorIdentifier;
|
||||
dialogBackground?: ColorIdentifier;
|
||||
dialogShadow?: ColorIdentifier;
|
||||
dialogBorder?: ColorIdentifier;
|
||||
checkboxBorder?: ColorIdentifier;
|
||||
checkboxBackground?: ColorIdentifier;
|
||||
checkboxForeground?: ColorIdentifier;
|
||||
errorIconForeground?: ColorIdentifier;
|
||||
warningIconForeground?: ColorIdentifier;
|
||||
infoIconForeground?: ColorIdentifier;
|
||||
inputBackground?: ColorIdentifier;
|
||||
inputForeground?: ColorIdentifier;
|
||||
inputBorder?: ColorIdentifier;
|
||||
}
|
||||
|
||||
export const defaultDialogStyles = <IDialogStyleOverrides>{
|
||||
dialogBackground: editorWidgetBackground,
|
||||
dialogForeground: editorWidgetForeground,
|
||||
dialogShadow: widgetShadow,
|
||||
dialogBorder: contrastBorder,
|
||||
buttonForeground: buttonForeground,
|
||||
buttonBackground: buttonBackground,
|
||||
buttonHoverBackground: buttonHoverBackground,
|
||||
buttonBorder: contrastBorder,
|
||||
checkboxBorder: simpleCheckboxBorder,
|
||||
checkboxBackground: simpleCheckboxBackground,
|
||||
checkboxForeground: simpleCheckboxForeground,
|
||||
errorIconForeground: problemsErrorIconForeground,
|
||||
warningIconForeground: problemsWarningIconForeground,
|
||||
infoIconForeground: problemsInfoIconForeground,
|
||||
inputBackground: inputBackground,
|
||||
inputForeground: inputForeground,
|
||||
inputBorder: inputBorder
|
||||
};
|
||||
|
||||
|
||||
export function attachDialogStyler(widget: IThemable, themeService: IThemeService, style?: IDialogStyleOverrides): IDisposable {
|
||||
return attachStyler(themeService, { ...defaultDialogStyles, ...style }, widget);
|
||||
}
|
||||
13
lib/vscode/src/vs/platform/theme/common/theme.ts
Normal file
13
lib/vscode/src/vs/platform/theme/common/theme.ts
Normal file
@@ -0,0 +1,13 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
/**
|
||||
* Color scheme used by the OS and by color themes.
|
||||
*/
|
||||
export enum ColorScheme {
|
||||
DARK = 'dark',
|
||||
LIGHT = 'light',
|
||||
HIGH_CONTRAST = 'hc'
|
||||
}
|
||||
235
lib/vscode/src/vs/platform/theme/common/themeService.ts
Normal file
235
lib/vscode/src/vs/platform/theme/common/themeService.ts
Normal file
@@ -0,0 +1,235 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { createDecorator } from 'vs/platform/instantiation/common/instantiation';
|
||||
import { Color } from 'vs/base/common/color';
|
||||
import { IDisposable, toDisposable, Disposable } from 'vs/base/common/lifecycle';
|
||||
import * as platform from 'vs/platform/registry/common/platform';
|
||||
import { ColorIdentifier } from 'vs/platform/theme/common/colorRegistry';
|
||||
import { Event, Emitter } from 'vs/base/common/event';
|
||||
import { IEnvironmentService } from 'vs/platform/environment/common/environment';
|
||||
import { ColorScheme } from 'vs/platform/theme/common/theme';
|
||||
|
||||
export const IThemeService = createDecorator<IThemeService>('themeService');
|
||||
|
||||
export interface ThemeColor {
|
||||
id: string;
|
||||
}
|
||||
|
||||
export function themeColorFromId(id: ColorIdentifier) {
|
||||
return { id };
|
||||
}
|
||||
|
||||
// theme icon
|
||||
export interface ThemeIcon {
|
||||
readonly id: string;
|
||||
readonly color?: ThemeColor;
|
||||
}
|
||||
|
||||
export namespace ThemeIcon {
|
||||
export function isThemeIcon(obj: any): obj is ThemeIcon | { id: string } {
|
||||
return obj && typeof obj === 'object' && typeof (<ThemeIcon>obj).id === 'string';
|
||||
}
|
||||
|
||||
const _regexFromString = /^\$\(([a-z.]+\/)?([a-z-~]+)\)$/i;
|
||||
|
||||
export function fromString(str: string): ThemeIcon | undefined {
|
||||
const match = _regexFromString.exec(str);
|
||||
if (!match) {
|
||||
return undefined;
|
||||
}
|
||||
let [, owner, name] = match;
|
||||
if (!owner) {
|
||||
owner = `codicon/`;
|
||||
}
|
||||
return { id: owner + name };
|
||||
}
|
||||
|
||||
const _regexAsClassName = /^(codicon\/)?([a-z-]+)(~[a-z]+)?$/i;
|
||||
|
||||
export function asClassName(icon: ThemeIcon): string | undefined {
|
||||
// todo@martin,joh -> this should go into the ThemeService
|
||||
const match = _regexAsClassName.exec(icon.id);
|
||||
if (!match) {
|
||||
return undefined;
|
||||
}
|
||||
let [, , name, modifier] = match;
|
||||
let className = `codicon codicon-${name}`;
|
||||
if (modifier) {
|
||||
className += ` ${modifier.substr(1)}`;
|
||||
}
|
||||
return className;
|
||||
}
|
||||
}
|
||||
|
||||
export const FileThemeIcon = { id: 'file' };
|
||||
export const FolderThemeIcon = { id: 'folder' };
|
||||
|
||||
export function getThemeTypeSelector(type: ColorScheme): string {
|
||||
switch (type) {
|
||||
case ColorScheme.DARK: return 'vs-dark';
|
||||
case ColorScheme.HIGH_CONTRAST: return 'hc-black';
|
||||
default: return 'vs';
|
||||
}
|
||||
}
|
||||
|
||||
export interface ITokenStyle {
|
||||
readonly foreground?: number;
|
||||
readonly bold?: boolean;
|
||||
readonly underline?: boolean;
|
||||
readonly italic?: boolean;
|
||||
}
|
||||
|
||||
export interface IColorTheme {
|
||||
|
||||
readonly type: ColorScheme;
|
||||
|
||||
readonly label: string;
|
||||
|
||||
/**
|
||||
* Resolves the color of the given color identifier. If the theme does not
|
||||
* specify the color, the default color is returned unless <code>useDefault</code> is set to false.
|
||||
* @param color the id of the color
|
||||
* @param useDefault specifies if the default color should be used. If not set, the default is used.
|
||||
*/
|
||||
getColor(color: ColorIdentifier, useDefault?: boolean): Color | undefined;
|
||||
|
||||
/**
|
||||
* Returns whether the theme defines a value for the color. If not, that means the
|
||||
* default color will be used.
|
||||
*/
|
||||
defines(color: ColorIdentifier): boolean;
|
||||
|
||||
/**
|
||||
* Returns the token style for a given classification. The result uses the <code>MetadataConsts</code> format
|
||||
*/
|
||||
getTokenStyleMetadata(type: string, modifiers: string[], modelLanguage: string): ITokenStyle | undefined;
|
||||
|
||||
/**
|
||||
* List of all colors used with tokens. <code>getTokenStyleMetadata</code> references the colors by index into this list.
|
||||
*/
|
||||
readonly tokenColorMap: string[];
|
||||
|
||||
/**
|
||||
* Defines whether semantic highlighting should be enabled for the theme.
|
||||
*/
|
||||
readonly semanticHighlighting: boolean;
|
||||
}
|
||||
|
||||
export interface IFileIconTheme {
|
||||
readonly hasFileIcons: boolean;
|
||||
readonly hasFolderIcons: boolean;
|
||||
readonly hidesExplorerArrows: boolean;
|
||||
}
|
||||
|
||||
export interface ICssStyleCollector {
|
||||
addRule(rule: string): void;
|
||||
}
|
||||
|
||||
export interface IThemingParticipant {
|
||||
(theme: IColorTheme, collector: ICssStyleCollector, environment: IEnvironmentService): void;
|
||||
}
|
||||
|
||||
export interface IThemeService {
|
||||
readonly _serviceBrand: undefined;
|
||||
|
||||
getColorTheme(): IColorTheme;
|
||||
|
||||
readonly onDidColorThemeChange: Event<IColorTheme>;
|
||||
|
||||
getFileIconTheme(): IFileIconTheme;
|
||||
|
||||
readonly onDidFileIconThemeChange: Event<IFileIconTheme>;
|
||||
|
||||
}
|
||||
|
||||
// static theming participant
|
||||
export const Extensions = {
|
||||
ThemingContribution: 'base.contributions.theming'
|
||||
};
|
||||
|
||||
export interface IThemingRegistry {
|
||||
|
||||
/**
|
||||
* Register a theming participant that is invoked on every theme change.
|
||||
*/
|
||||
onColorThemeChange(participant: IThemingParticipant): IDisposable;
|
||||
|
||||
getThemingParticipants(): IThemingParticipant[];
|
||||
|
||||
readonly onThemingParticipantAdded: Event<IThemingParticipant>;
|
||||
}
|
||||
|
||||
class ThemingRegistry implements IThemingRegistry {
|
||||
private themingParticipants: IThemingParticipant[] = [];
|
||||
private readonly onThemingParticipantAddedEmitter: Emitter<IThemingParticipant>;
|
||||
|
||||
constructor() {
|
||||
this.themingParticipants = [];
|
||||
this.onThemingParticipantAddedEmitter = new Emitter<IThemingParticipant>();
|
||||
}
|
||||
|
||||
public onColorThemeChange(participant: IThemingParticipant): IDisposable {
|
||||
this.themingParticipants.push(participant);
|
||||
this.onThemingParticipantAddedEmitter.fire(participant);
|
||||
return toDisposable(() => {
|
||||
const idx = this.themingParticipants.indexOf(participant);
|
||||
this.themingParticipants.splice(idx, 1);
|
||||
});
|
||||
}
|
||||
|
||||
public get onThemingParticipantAdded(): Event<IThemingParticipant> {
|
||||
return this.onThemingParticipantAddedEmitter.event;
|
||||
}
|
||||
|
||||
public getThemingParticipants(): IThemingParticipant[] {
|
||||
return this.themingParticipants;
|
||||
}
|
||||
}
|
||||
|
||||
let themingRegistry = new ThemingRegistry();
|
||||
platform.Registry.add(Extensions.ThemingContribution, themingRegistry);
|
||||
|
||||
export function registerThemingParticipant(participant: IThemingParticipant): IDisposable {
|
||||
return themingRegistry.onColorThemeChange(participant);
|
||||
}
|
||||
|
||||
/**
|
||||
* Utility base class for all themable components.
|
||||
*/
|
||||
export class Themable extends Disposable {
|
||||
protected theme: IColorTheme;
|
||||
|
||||
constructor(
|
||||
protected themeService: IThemeService
|
||||
) {
|
||||
super();
|
||||
|
||||
this.theme = themeService.getColorTheme();
|
||||
|
||||
// Hook up to theme changes
|
||||
this._register(this.themeService.onDidColorThemeChange(theme => this.onThemeChange(theme)));
|
||||
}
|
||||
|
||||
protected onThemeChange(theme: IColorTheme): void {
|
||||
this.theme = theme;
|
||||
|
||||
this.updateStyles();
|
||||
}
|
||||
|
||||
protected updateStyles(): void {
|
||||
// Subclasses to override
|
||||
}
|
||||
|
||||
protected getColor(id: string, modify?: (color: Color, theme: IColorTheme) => Color): string | null {
|
||||
let color = this.theme.getColor(id);
|
||||
|
||||
if (color && modify) {
|
||||
color = modify(color, this.theme);
|
||||
}
|
||||
|
||||
return color ? color.toString() : null;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,593 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import * as platform from 'vs/platform/registry/common/platform';
|
||||
import { Color } from 'vs/base/common/color';
|
||||
import { IColorTheme } from 'vs/platform/theme/common/themeService';
|
||||
import * as nls from 'vs/nls';
|
||||
import { Extensions as JSONExtensions, IJSONContributionRegistry } from 'vs/platform/jsonschemas/common/jsonContributionRegistry';
|
||||
import { RunOnceScheduler } from 'vs/base/common/async';
|
||||
import { Event, Emitter } from 'vs/base/common/event';
|
||||
import { IJSONSchema, IJSONSchemaMap } from 'vs/base/common/jsonSchema';
|
||||
|
||||
export const TOKEN_TYPE_WILDCARD = '*';
|
||||
export const TOKEN_CLASSIFIER_LANGUAGE_SEPARATOR = ':';
|
||||
export const CLASSIFIER_MODIFIER_SEPARATOR = '.';
|
||||
|
||||
// qualified string [type|*](.modifier)*(/language)!
|
||||
export type TokenClassificationString = string;
|
||||
|
||||
export const idPattern = '\\w+[-_\\w+]*';
|
||||
export const typeAndModifierIdPattern = `^${idPattern}$`;
|
||||
|
||||
export const selectorPattern = `^(${idPattern}|\\*)(\\${CLASSIFIER_MODIFIER_SEPARATOR}${idPattern})*(\\${TOKEN_CLASSIFIER_LANGUAGE_SEPARATOR}${idPattern})?$`;
|
||||
|
||||
export const fontStylePattern = '^(\\s*(italic|bold|underline))*\\s*$';
|
||||
|
||||
export interface TokenSelector {
|
||||
match(type: string, modifiers: string[], language: string): number;
|
||||
readonly id: string;
|
||||
}
|
||||
|
||||
export interface TokenTypeOrModifierContribution {
|
||||
readonly num: number;
|
||||
readonly id: string;
|
||||
readonly superType?: string;
|
||||
readonly description: string;
|
||||
readonly deprecationMessage?: string;
|
||||
}
|
||||
|
||||
|
||||
export interface TokenStyleData {
|
||||
foreground?: Color;
|
||||
bold?: boolean;
|
||||
underline?: boolean;
|
||||
italic?: boolean;
|
||||
}
|
||||
|
||||
export class TokenStyle implements Readonly<TokenStyleData> {
|
||||
constructor(
|
||||
public readonly foreground?: Color,
|
||||
public readonly bold?: boolean,
|
||||
public readonly underline?: boolean,
|
||||
public readonly italic?: boolean,
|
||||
) {
|
||||
}
|
||||
}
|
||||
|
||||
export namespace TokenStyle {
|
||||
export function toJSONObject(style: TokenStyle): any {
|
||||
return {
|
||||
_foreground: style.foreground === undefined ? null : Color.Format.CSS.formatHexA(style.foreground, true),
|
||||
_bold: style.bold === undefined ? null : style.bold,
|
||||
_underline: style.underline === undefined ? null : style.underline,
|
||||
_italic: style.italic === undefined ? null : style.italic,
|
||||
};
|
||||
}
|
||||
export function fromJSONObject(obj: any): TokenStyle | undefined {
|
||||
if (obj) {
|
||||
const boolOrUndef = (b: any) => (typeof b === 'boolean') ? b : undefined;
|
||||
const colorOrUndef = (s: any) => (typeof s === 'string') ? Color.fromHex(s) : undefined;
|
||||
return new TokenStyle(colorOrUndef(obj._foreground), boolOrUndef(obj._bold), boolOrUndef(obj._underline), boolOrUndef(obj._italic));
|
||||
}
|
||||
return undefined;
|
||||
}
|
||||
export function equals(s1: any, s2: any): boolean {
|
||||
if (s1 === s2) {
|
||||
return true;
|
||||
}
|
||||
return s1 !== undefined && s2 !== undefined
|
||||
&& (s1.foreground instanceof Color ? s1.foreground.equals(s2.foreground) : s2.foreground === undefined)
|
||||
&& s1.bold === s2.bold
|
||||
&& s1.underline === s2.underline
|
||||
&& s1.italic === s2.italic;
|
||||
}
|
||||
export function is(s: any): s is TokenStyle {
|
||||
return s instanceof TokenStyle;
|
||||
}
|
||||
export function fromData(data: { foreground?: Color, bold?: boolean, underline?: boolean, italic?: boolean }): TokenStyle {
|
||||
return new TokenStyle(data.foreground, data.bold, data.underline, data.italic);
|
||||
}
|
||||
export function fromSettings(foreground: string | undefined, fontStyle: string | undefined, bold?: boolean, underline?: boolean, italic?: boolean): TokenStyle {
|
||||
let foregroundColor = undefined;
|
||||
if (foreground !== undefined) {
|
||||
foregroundColor = Color.fromHex(foreground);
|
||||
}
|
||||
if (fontStyle !== undefined) {
|
||||
bold = italic = underline = false;
|
||||
const expression = /italic|bold|underline/g;
|
||||
let match;
|
||||
while ((match = expression.exec(fontStyle))) {
|
||||
switch (match[0]) {
|
||||
case 'bold': bold = true; break;
|
||||
case 'italic': italic = true; break;
|
||||
case 'underline': underline = true; break;
|
||||
}
|
||||
}
|
||||
}
|
||||
return new TokenStyle(foregroundColor, bold, underline, italic);
|
||||
}
|
||||
}
|
||||
|
||||
export type ProbeScope = string[];
|
||||
|
||||
export interface TokenStyleFunction {
|
||||
(theme: IColorTheme): TokenStyle | undefined;
|
||||
}
|
||||
|
||||
export interface TokenStyleDefaults {
|
||||
scopesToProbe?: ProbeScope[];
|
||||
light?: TokenStyleValue;
|
||||
dark?: TokenStyleValue;
|
||||
hc?: TokenStyleValue;
|
||||
}
|
||||
|
||||
export interface SemanticTokenDefaultRule {
|
||||
selector: TokenSelector;
|
||||
defaults: TokenStyleDefaults;
|
||||
}
|
||||
|
||||
export interface SemanticTokenRule {
|
||||
style: TokenStyle;
|
||||
selector: TokenSelector;
|
||||
}
|
||||
|
||||
export namespace SemanticTokenRule {
|
||||
export function fromJSONObject(registry: ITokenClassificationRegistry, o: any): SemanticTokenRule | undefined {
|
||||
if (o && typeof o._selector === 'string' && o._style) {
|
||||
const style = TokenStyle.fromJSONObject(o._style);
|
||||
if (style) {
|
||||
try {
|
||||
return { selector: registry.parseTokenSelector(o._selector), style };
|
||||
} catch (_ignore) {
|
||||
}
|
||||
}
|
||||
}
|
||||
return undefined;
|
||||
}
|
||||
export function toJSONObject(rule: SemanticTokenRule): any {
|
||||
return {
|
||||
_selector: rule.selector.id,
|
||||
_style: TokenStyle.toJSONObject(rule.style)
|
||||
};
|
||||
}
|
||||
export function equals(r1: SemanticTokenRule | undefined, r2: SemanticTokenRule | undefined) {
|
||||
if (r1 === r2) {
|
||||
return true;
|
||||
}
|
||||
return r1 !== undefined && r2 !== undefined
|
||||
&& r1.selector && r2.selector && r1.selector.id === r2.selector.id
|
||||
&& TokenStyle.equals(r1.style, r2.style);
|
||||
}
|
||||
export function is(r: any): r is SemanticTokenRule {
|
||||
return r && r.selector && typeof r.selector.id === 'string' && TokenStyle.is(r.style);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* A TokenStyle Value is either a token style literal, or a TokenClassificationString
|
||||
*/
|
||||
export type TokenStyleValue = TokenStyle | TokenClassificationString;
|
||||
|
||||
// TokenStyle registry
|
||||
export const Extensions = {
|
||||
TokenClassificationContribution: 'base.contributions.tokenClassification'
|
||||
};
|
||||
|
||||
export interface ITokenClassificationRegistry {
|
||||
|
||||
readonly onDidChangeSchema: Event<void>;
|
||||
|
||||
/**
|
||||
* Register a token type to the registry.
|
||||
* @param id The TokenType id as used in theme description files
|
||||
* @param description the description
|
||||
*/
|
||||
registerTokenType(id: string, description: string, superType?: string, deprecationMessage?: string): void;
|
||||
|
||||
/**
|
||||
* Register a token modifier to the registry.
|
||||
* @param id The TokenModifier id as used in theme description files
|
||||
* @param description the description
|
||||
*/
|
||||
registerTokenModifier(id: string, description: string): void;
|
||||
|
||||
/**
|
||||
* Parses a token selector from a selector string.
|
||||
* @param selectorString selector string in the form (*|type)(.modifier)*
|
||||
* @param language language to which the selector applies or undefined if the selector is for all languafe
|
||||
* @returns the parsesd selector
|
||||
* @throws an error if the string is not a valid selector
|
||||
*/
|
||||
parseTokenSelector(selectorString: string, language?: string): TokenSelector;
|
||||
|
||||
/**
|
||||
* Register a TokenStyle default to the registry.
|
||||
* @param selector The rule selector
|
||||
* @param defaults The default values
|
||||
*/
|
||||
registerTokenStyleDefault(selector: TokenSelector, defaults: TokenStyleDefaults): void;
|
||||
|
||||
/**
|
||||
* Deregister a TokenStyle default to the registry.
|
||||
* @param selector The rule selector
|
||||
*/
|
||||
deregisterTokenStyleDefault(selector: TokenSelector): void;
|
||||
|
||||
/**
|
||||
* Deregister a TokenType from the registry.
|
||||
*/
|
||||
deregisterTokenType(id: string): void;
|
||||
|
||||
/**
|
||||
* Deregister a TokenModifier from the registry.
|
||||
*/
|
||||
deregisterTokenModifier(id: string): void;
|
||||
|
||||
/**
|
||||
* Get all TokenType contributions
|
||||
*/
|
||||
getTokenTypes(): TokenTypeOrModifierContribution[];
|
||||
|
||||
/**
|
||||
* Get all TokenModifier contributions
|
||||
*/
|
||||
getTokenModifiers(): TokenTypeOrModifierContribution[];
|
||||
|
||||
/**
|
||||
* The styling rules to used when a schema does not define any styling rules.
|
||||
*/
|
||||
getTokenStylingDefaultRules(): SemanticTokenDefaultRule[];
|
||||
|
||||
/**
|
||||
* JSON schema for an object to assign styling to token classifications
|
||||
*/
|
||||
getTokenStylingSchema(): IJSONSchema;
|
||||
}
|
||||
|
||||
class TokenClassificationRegistry implements ITokenClassificationRegistry {
|
||||
|
||||
private readonly _onDidChangeSchema = new Emitter<void>();
|
||||
readonly onDidChangeSchema: Event<void> = this._onDidChangeSchema.event;
|
||||
|
||||
private currentTypeNumber = 0;
|
||||
private currentModifierBit = 1;
|
||||
|
||||
private tokenTypeById: { [key: string]: TokenTypeOrModifierContribution };
|
||||
private tokenModifierById: { [key: string]: TokenTypeOrModifierContribution };
|
||||
|
||||
private tokenStylingDefaultRules: SemanticTokenDefaultRule[] = [];
|
||||
|
||||
private typeHierarchy: { [id: string]: string[] };
|
||||
|
||||
private tokenStylingSchema: IJSONSchema & { properties: IJSONSchemaMap, patternProperties: IJSONSchemaMap } = {
|
||||
type: 'object',
|
||||
properties: {},
|
||||
patternProperties: {
|
||||
[selectorPattern]: getStylingSchemeEntry()
|
||||
},
|
||||
//errorMessage: nls.localize('schema.token.errors', 'Valid token selectors have the form (*|tokenType)(.tokenModifier)*(:tokenLanguage)?.'),
|
||||
additionalProperties: false,
|
||||
definitions: {
|
||||
style: {
|
||||
type: 'object',
|
||||
description: nls.localize('schema.token.settings', 'Colors and styles for the token.'),
|
||||
properties: {
|
||||
foreground: {
|
||||
type: 'string',
|
||||
description: nls.localize('schema.token.foreground', 'Foreground color for the token.'),
|
||||
format: 'color-hex',
|
||||
default: '#ff0000'
|
||||
},
|
||||
background: {
|
||||
type: 'string',
|
||||
deprecationMessage: nls.localize('schema.token.background.warning', 'Token background colors are currently not supported.')
|
||||
},
|
||||
fontStyle: {
|
||||
type: 'string',
|
||||
description: nls.localize('schema.token.fontStyle', 'Sets the all font styles of the rule: \'italic\', \'bold\' or \'underline\' or a combination. All styles that are not listed are unset. The empty string unsets all styles.'),
|
||||
pattern: fontStylePattern,
|
||||
patternErrorMessage: nls.localize('schema.fontStyle.error', 'Font style must be \'italic\', \'bold\' or \'underline\' or a combination. The empty string unsets all styles.'),
|
||||
defaultSnippets: [{ label: nls.localize('schema.token.fontStyle.none', 'None (clear inherited style)'), bodyText: '""' }, { body: 'italic' }, { body: 'bold' }, { body: 'underline' }, { body: 'italic underline' }, { body: 'bold underline' }, { body: 'italic bold underline' }]
|
||||
},
|
||||
bold: {
|
||||
type: 'boolean',
|
||||
description: nls.localize('schema.token.bold', 'Sets or unsets the font style to bold. Note, the presence of \'fontStyle\' overrides this setting.'),
|
||||
},
|
||||
italic: {
|
||||
type: 'boolean',
|
||||
description: nls.localize('schema.token.italic', 'Sets or unsets the font style to italic. Note, the presence of \'fontStyle\' overrides this setting.'),
|
||||
},
|
||||
underline: {
|
||||
type: 'boolean',
|
||||
description: nls.localize('schema.token.underline', 'Sets or unsets the font style to underline. Note, the presence of \'fontStyle\' overrides this setting.'),
|
||||
}
|
||||
|
||||
},
|
||||
defaultSnippets: [{ body: { foreground: '${1:#FF0000}', fontStyle: '${2:bold}' } }]
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
constructor() {
|
||||
this.tokenTypeById = Object.create(null);
|
||||
this.tokenModifierById = Object.create(null);
|
||||
this.typeHierarchy = Object.create(null);
|
||||
}
|
||||
|
||||
public registerTokenType(id: string, description: string, superType?: string, deprecationMessage?: string): void {
|
||||
if (!id.match(typeAndModifierIdPattern)) {
|
||||
throw new Error('Invalid token type id.');
|
||||
}
|
||||
if (superType && !superType.match(typeAndModifierIdPattern)) {
|
||||
throw new Error('Invalid token super type id.');
|
||||
}
|
||||
|
||||
const num = this.currentTypeNumber++;
|
||||
let tokenStyleContribution: TokenTypeOrModifierContribution = { num, id, superType, description, deprecationMessage };
|
||||
this.tokenTypeById[id] = tokenStyleContribution;
|
||||
|
||||
const stylingSchemeEntry = getStylingSchemeEntry(description, deprecationMessage);
|
||||
this.tokenStylingSchema.properties[id] = stylingSchemeEntry;
|
||||
this.typeHierarchy = Object.create(null);
|
||||
}
|
||||
|
||||
public registerTokenModifier(id: string, description: string, deprecationMessage?: string): void {
|
||||
if (!id.match(typeAndModifierIdPattern)) {
|
||||
throw new Error('Invalid token modifier id.');
|
||||
}
|
||||
|
||||
const num = this.currentModifierBit;
|
||||
this.currentModifierBit = this.currentModifierBit * 2;
|
||||
let tokenStyleContribution: TokenTypeOrModifierContribution = { num, id, description, deprecationMessage };
|
||||
this.tokenModifierById[id] = tokenStyleContribution;
|
||||
|
||||
this.tokenStylingSchema.properties[`*.${id}`] = getStylingSchemeEntry(description, deprecationMessage);
|
||||
}
|
||||
|
||||
public parseTokenSelector(selectorString: string, language?: string): TokenSelector {
|
||||
const selector = parseClassifierString(selectorString, language);
|
||||
|
||||
if (!selector.type) {
|
||||
return {
|
||||
match: () => -1,
|
||||
id: '$invalid'
|
||||
};
|
||||
}
|
||||
|
||||
return {
|
||||
match: (type: string, modifiers: string[], language: string) => {
|
||||
let score = 0;
|
||||
if (selector.language !== undefined) {
|
||||
if (selector.language !== language) {
|
||||
return -1;
|
||||
}
|
||||
score += 10;
|
||||
}
|
||||
if (selector.type !== TOKEN_TYPE_WILDCARD) {
|
||||
const hierarchy = this.getTypeHierarchy(type);
|
||||
const level = hierarchy.indexOf(selector.type);
|
||||
if (level === -1) {
|
||||
return -1;
|
||||
}
|
||||
score += (100 - level);
|
||||
}
|
||||
// all selector modifiers must be present
|
||||
for (const selectorModifier of selector.modifiers) {
|
||||
if (modifiers.indexOf(selectorModifier) === -1) {
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
return score + selector.modifiers.length * 100;
|
||||
},
|
||||
id: `${[selector.type, ...selector.modifiers.sort()].join('.')}${selector.language !== undefined ? ':' + selector.language : ''}`
|
||||
};
|
||||
}
|
||||
|
||||
public registerTokenStyleDefault(selector: TokenSelector, defaults: TokenStyleDefaults): void {
|
||||
this.tokenStylingDefaultRules.push({ selector, defaults });
|
||||
}
|
||||
|
||||
public deregisterTokenStyleDefault(selector: TokenSelector): void {
|
||||
const selectorString = selector.id;
|
||||
this.tokenStylingDefaultRules = this.tokenStylingDefaultRules.filter(r => r.selector.id !== selectorString);
|
||||
}
|
||||
|
||||
public deregisterTokenType(id: string): void {
|
||||
delete this.tokenTypeById[id];
|
||||
delete this.tokenStylingSchema.properties[id];
|
||||
this.typeHierarchy = Object.create(null);
|
||||
}
|
||||
|
||||
public deregisterTokenModifier(id: string): void {
|
||||
delete this.tokenModifierById[id];
|
||||
delete this.tokenStylingSchema.properties[`*.${id}`];
|
||||
}
|
||||
|
||||
public getTokenTypes(): TokenTypeOrModifierContribution[] {
|
||||
return Object.keys(this.tokenTypeById).map(id => this.tokenTypeById[id]);
|
||||
}
|
||||
|
||||
public getTokenModifiers(): TokenTypeOrModifierContribution[] {
|
||||
return Object.keys(this.tokenModifierById).map(id => this.tokenModifierById[id]);
|
||||
}
|
||||
|
||||
public getTokenStylingSchema(): IJSONSchema {
|
||||
return this.tokenStylingSchema;
|
||||
}
|
||||
|
||||
public getTokenStylingDefaultRules(): SemanticTokenDefaultRule[] {
|
||||
return this.tokenStylingDefaultRules;
|
||||
}
|
||||
|
||||
private getTypeHierarchy(typeId: string): string[] {
|
||||
let hierarchy = this.typeHierarchy[typeId];
|
||||
if (!hierarchy) {
|
||||
this.typeHierarchy[typeId] = hierarchy = [typeId];
|
||||
let type = this.tokenTypeById[typeId];
|
||||
while (type && type.superType) {
|
||||
hierarchy.push(type.superType);
|
||||
type = this.tokenTypeById[type.superType];
|
||||
}
|
||||
}
|
||||
return hierarchy;
|
||||
}
|
||||
|
||||
|
||||
public toString() {
|
||||
let sorter = (a: string, b: string) => {
|
||||
let cat1 = a.indexOf('.') === -1 ? 0 : 1;
|
||||
let cat2 = b.indexOf('.') === -1 ? 0 : 1;
|
||||
if (cat1 !== cat2) {
|
||||
return cat1 - cat2;
|
||||
}
|
||||
return a.localeCompare(b);
|
||||
};
|
||||
|
||||
return Object.keys(this.tokenTypeById).sort(sorter).map(k => `- \`${k}\`: ${this.tokenTypeById[k].description}`).join('\n');
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
const CHAR_LANGUAGE = TOKEN_CLASSIFIER_LANGUAGE_SEPARATOR.charCodeAt(0);
|
||||
const CHAR_MODIFIER = CLASSIFIER_MODIFIER_SEPARATOR.charCodeAt(0);
|
||||
|
||||
export function parseClassifierString(s: string, defaultLanguage: string): { type: string, modifiers: string[], language: string; };
|
||||
export function parseClassifierString(s: string, defaultLanguage?: string): { type: string, modifiers: string[], language: string | undefined; };
|
||||
export function parseClassifierString(s: string, defaultLanguage: string | undefined): { type: string, modifiers: string[], language: string | undefined; } {
|
||||
let k = s.length;
|
||||
let language: string | undefined = defaultLanguage;
|
||||
const modifiers = [];
|
||||
|
||||
for (let i = k - 1; i >= 0; i--) {
|
||||
const ch = s.charCodeAt(i);
|
||||
if (ch === CHAR_LANGUAGE || ch === CHAR_MODIFIER) {
|
||||
const segment = s.substring(i + 1, k);
|
||||
k = i;
|
||||
if (ch === CHAR_LANGUAGE) {
|
||||
language = segment;
|
||||
} else {
|
||||
modifiers.push(segment);
|
||||
}
|
||||
}
|
||||
}
|
||||
const type = s.substring(0, k);
|
||||
return { type, modifiers, language };
|
||||
}
|
||||
|
||||
|
||||
let tokenClassificationRegistry = createDefaultTokenClassificationRegistry();
|
||||
platform.Registry.add(Extensions.TokenClassificationContribution, tokenClassificationRegistry);
|
||||
|
||||
|
||||
function createDefaultTokenClassificationRegistry(): TokenClassificationRegistry {
|
||||
|
||||
const registry = new TokenClassificationRegistry();
|
||||
|
||||
function registerTokenType(id: string, description: string, scopesToProbe: ProbeScope[] = [], superType?: string, deprecationMessage?: string): string {
|
||||
registry.registerTokenType(id, description, superType, deprecationMessage);
|
||||
if (scopesToProbe) {
|
||||
registerTokenStyleDefault(id, scopesToProbe);
|
||||
}
|
||||
return id;
|
||||
}
|
||||
|
||||
function registerTokenStyleDefault(selectorString: string, scopesToProbe: ProbeScope[]) {
|
||||
try {
|
||||
const selector = registry.parseTokenSelector(selectorString);
|
||||
registry.registerTokenStyleDefault(selector, { scopesToProbe });
|
||||
} catch (e) {
|
||||
console.log(e);
|
||||
}
|
||||
}
|
||||
|
||||
// default token types
|
||||
|
||||
registerTokenType('comment', nls.localize('comment', "Style for comments."), [['comment']]);
|
||||
registerTokenType('string', nls.localize('string', "Style for strings."), [['string']]);
|
||||
registerTokenType('keyword', nls.localize('keyword', "Style for keywords."), [['keyword.control']]);
|
||||
registerTokenType('number', nls.localize('number', "Style for numbers."), [['constant.numeric']]);
|
||||
registerTokenType('regexp', nls.localize('regexp', "Style for expressions."), [['constant.regexp']]);
|
||||
registerTokenType('operator', nls.localize('operator', "Style for operators."), [['keyword.operator']]);
|
||||
|
||||
registerTokenType('namespace', nls.localize('namespace', "Style for namespaces."), [['entity.name.namespace']]);
|
||||
|
||||
registerTokenType('type', nls.localize('type', "Style for types."), [['entity.name.type'], ['support.type']]);
|
||||
registerTokenType('struct', nls.localize('struct', "Style for structs."), [['entity.name.type.struct']]);
|
||||
registerTokenType('class', nls.localize('class', "Style for classes."), [['entity.name.type.class'], ['support.class']]);
|
||||
registerTokenType('interface', nls.localize('interface', "Style for interfaces."), [['entity.name.type.interface']]);
|
||||
registerTokenType('enum', nls.localize('enum', "Style for enums."), [['entity.name.type.enum']]);
|
||||
registerTokenType('typeParameter', nls.localize('typeParameter', "Style for type parameters."), [['entity.name.type.parameter']]);
|
||||
|
||||
registerTokenType('function', nls.localize('function', "Style for functions"), [['entity.name.function'], ['support.function']]);
|
||||
registerTokenType('member', nls.localize('member', "Style for member"), [['entity.name.function.member'], ['support.function']]);
|
||||
registerTokenType('macro', nls.localize('macro', "Style for macros."), [['entity.name.other.preprocessor.macro']]);
|
||||
|
||||
registerTokenType('variable', nls.localize('variable', "Style for variables."), [['variable.other.readwrite'], ['entity.name.variable']]);
|
||||
registerTokenType('parameter', nls.localize('parameter', "Style for parameters."), [['variable.parameter']]);
|
||||
registerTokenType('property', nls.localize('property', "Style for properties."), [['variable.other.property']]);
|
||||
registerTokenType('enumMember', nls.localize('enumMember', "Style for enum members."), [['variable.other.enummember']]);
|
||||
registerTokenType('event', nls.localize('event', "Style for events."), [['variable.other.event']]);
|
||||
|
||||
registerTokenType('label', nls.localize('labels', "Style for labels. "), undefined);
|
||||
|
||||
// default token modifiers
|
||||
|
||||
registry.registerTokenModifier('declaration', nls.localize('declaration', "Style for all symbol declarations."), undefined);
|
||||
registry.registerTokenModifier('documentation', nls.localize('documentation', "Style to use for references in documentation."), undefined);
|
||||
registry.registerTokenModifier('static', nls.localize('static', "Style to use for symbols that are static."), undefined);
|
||||
registry.registerTokenModifier('abstract', nls.localize('abstract', "Style to use for symbols that are abstract."), undefined);
|
||||
registry.registerTokenModifier('deprecated', nls.localize('deprecated', "Style to use for symbols that are deprecated."), undefined);
|
||||
registry.registerTokenModifier('modification', nls.localize('modification', "Style to use for write accesses."), undefined);
|
||||
registry.registerTokenModifier('async', nls.localize('async', "Style to use for symbols that are async."), undefined);
|
||||
registry.registerTokenModifier('readonly', nls.localize('readonly', "Style to use for symbols that are readonly."), undefined);
|
||||
|
||||
|
||||
registerTokenStyleDefault('variable.readonly', [['variable.other.constant']]);
|
||||
registerTokenStyleDefault('property.readonly', [['variable.other.constant.property']]);
|
||||
registerTokenStyleDefault('type.defaultLibrary', [['support.type']]);
|
||||
registerTokenStyleDefault('class.defaultLibrary', [['support.class']]);
|
||||
registerTokenStyleDefault('interface.defaultLibrary', [['support.class']]);
|
||||
registerTokenStyleDefault('variable.defaultLibrary', [['support.variable'], ['support.other.variable']]);
|
||||
registerTokenStyleDefault('variable.defaultLibrary.readonly', [['support.constant']]);
|
||||
registerTokenStyleDefault('property.defaultLibrary', [['support.variable.property']]);
|
||||
registerTokenStyleDefault('property.defaultLibrary.readonly', [['support.constant.property']]);
|
||||
registerTokenStyleDefault('function.defaultLibrary', [['support.function']]);
|
||||
registerTokenStyleDefault('member.defaultLibrary', [['support.function']]);
|
||||
return registry;
|
||||
}
|
||||
|
||||
export function getTokenClassificationRegistry(): ITokenClassificationRegistry {
|
||||
return tokenClassificationRegistry;
|
||||
}
|
||||
|
||||
function getStylingSchemeEntry(description?: string, deprecationMessage?: string): IJSONSchema {
|
||||
return {
|
||||
description,
|
||||
deprecationMessage,
|
||||
defaultSnippets: [{ body: '${1:#ff0000}' }],
|
||||
anyOf: [
|
||||
{
|
||||
type: 'string',
|
||||
format: 'color-hex'
|
||||
},
|
||||
{
|
||||
$ref: '#definitions/style'
|
||||
}
|
||||
]
|
||||
};
|
||||
}
|
||||
|
||||
export const tokenStylingSchemaId = 'vscode://schemas/token-styling';
|
||||
|
||||
let schemaRegistry = platform.Registry.as<IJSONContributionRegistry>(JSONExtensions.JSONContribution);
|
||||
schemaRegistry.registerSchema(tokenStylingSchemaId, tokenClassificationRegistry.getTokenStylingSchema());
|
||||
|
||||
const delayer = new RunOnceScheduler(() => schemaRegistry.notifySchemaChanged(tokenStylingSchemaId), 200);
|
||||
tokenClassificationRegistry.onDidChangeSchema(() => {
|
||||
if (!delayer.isScheduled()) {
|
||||
delayer.schedule();
|
||||
}
|
||||
});
|
||||
@@ -0,0 +1,67 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { isWindows, isMacintosh } from 'vs/base/common/platform';
|
||||
import { ipcMain as ipc, nativeTheme } from 'electron';
|
||||
import { IStateService } from 'vs/platform/state/node/state';
|
||||
import { createDecorator } from 'vs/platform/instantiation/common/instantiation';
|
||||
|
||||
const DEFAULT_BG_LIGHT = '#FFFFFF';
|
||||
const DEFAULT_BG_DARK = '#1E1E1E';
|
||||
const DEFAULT_BG_HC_BLACK = '#000000';
|
||||
|
||||
const THEME_STORAGE_KEY = 'theme';
|
||||
const THEME_BG_STORAGE_KEY = 'themeBackground';
|
||||
|
||||
export const IThemeMainService = createDecorator<IThemeMainService>('themeMainService');
|
||||
|
||||
export interface IThemeMainService {
|
||||
readonly _serviceBrand: undefined;
|
||||
|
||||
getBackgroundColor(): string;
|
||||
}
|
||||
|
||||
export class ThemeMainService implements IThemeMainService {
|
||||
|
||||
declare readonly _serviceBrand: undefined;
|
||||
|
||||
constructor(@IStateService private stateService: IStateService) {
|
||||
ipc.on('vscode:changeColorTheme', (e: Event, windowId: number, broadcast: string) => {
|
||||
// Theme changes
|
||||
if (typeof broadcast === 'string') {
|
||||
this.storeBackgroundColor(JSON.parse(broadcast));
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private storeBackgroundColor(data: { baseTheme: string, background: string }): void {
|
||||
this.stateService.setItem(THEME_STORAGE_KEY, data.baseTheme);
|
||||
this.stateService.setItem(THEME_BG_STORAGE_KEY, data.background);
|
||||
}
|
||||
|
||||
getBackgroundColor(): string {
|
||||
if ((isWindows || isMacintosh) && nativeTheme.shouldUseInvertedColorScheme) {
|
||||
return DEFAULT_BG_HC_BLACK;
|
||||
}
|
||||
|
||||
let background = this.stateService.getItem<string | null>(THEME_BG_STORAGE_KEY, null);
|
||||
if (!background) {
|
||||
let baseTheme: string;
|
||||
if ((isWindows || isMacintosh) && nativeTheme.shouldUseInvertedColorScheme) {
|
||||
baseTheme = 'hc-black';
|
||||
} else {
|
||||
baseTheme = this.stateService.getItem<string>(THEME_STORAGE_KEY, 'vs-dark').split(' ')[0];
|
||||
}
|
||||
|
||||
background = (baseTheme === 'hc-black') ? DEFAULT_BG_HC_BLACK : (baseTheme === 'vs' ? DEFAULT_BG_LIGHT : DEFAULT_BG_DARK);
|
||||
}
|
||||
|
||||
if (isMacintosh && background.toUpperCase() === DEFAULT_BG_DARK) {
|
||||
background = '#171717'; // https://github.com/electron/electron/issues/5150
|
||||
}
|
||||
|
||||
return background;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,84 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { Event, Emitter } from 'vs/base/common/event';
|
||||
import { IThemeService, IColorTheme, IFileIconTheme, ITokenStyle } from 'vs/platform/theme/common/themeService';
|
||||
import { Color } from 'vs/base/common/color';
|
||||
import { ColorScheme } from 'vs/platform/theme/common/theme';
|
||||
|
||||
export class TestColorTheme implements IColorTheme {
|
||||
|
||||
public readonly label = 'test';
|
||||
|
||||
constructor(private colors: { [id: string]: string; } = {}, public type = ColorScheme.DARK) {
|
||||
}
|
||||
|
||||
getColor(color: string, useDefault?: boolean): Color | undefined {
|
||||
let value = this.colors[color];
|
||||
if (value) {
|
||||
return Color.fromHex(value);
|
||||
}
|
||||
return undefined;
|
||||
}
|
||||
|
||||
defines(color: string): boolean {
|
||||
throw new Error('Method not implemented.');
|
||||
}
|
||||
|
||||
getTokenStyleMetadata(type: string, modifiers: string[], modelLanguage: string): ITokenStyle | undefined {
|
||||
return undefined;
|
||||
}
|
||||
|
||||
readonly semanticHighlighting = false;
|
||||
|
||||
get tokenColorMap(): string[] {
|
||||
return [];
|
||||
}
|
||||
}
|
||||
|
||||
export class TestFileIconTheme implements IFileIconTheme {
|
||||
hasFileIcons = false;
|
||||
hasFolderIcons = false;
|
||||
hidesExplorerArrows = false;
|
||||
}
|
||||
|
||||
export class TestThemeService implements IThemeService {
|
||||
|
||||
declare readonly _serviceBrand: undefined;
|
||||
_colorTheme: IColorTheme;
|
||||
_fileIconTheme: IFileIconTheme;
|
||||
_onThemeChange = new Emitter<IColorTheme>();
|
||||
_onFileIconThemeChange = new Emitter<IFileIconTheme>();
|
||||
|
||||
constructor(theme = new TestColorTheme(), iconTheme = new TestFileIconTheme()) {
|
||||
this._colorTheme = theme;
|
||||
this._fileIconTheme = iconTheme;
|
||||
}
|
||||
|
||||
getColorTheme(): IColorTheme {
|
||||
return this._colorTheme;
|
||||
}
|
||||
|
||||
setTheme(theme: IColorTheme) {
|
||||
this._colorTheme = theme;
|
||||
this.fireThemeChange();
|
||||
}
|
||||
|
||||
fireThemeChange() {
|
||||
this._onThemeChange.fire(this._colorTheme);
|
||||
}
|
||||
|
||||
public get onDidColorThemeChange(): Event<IColorTheme> {
|
||||
return this._onThemeChange.event;
|
||||
}
|
||||
|
||||
getFileIconTheme(): IFileIconTheme {
|
||||
return this._fileIconTheme;
|
||||
}
|
||||
|
||||
public get onDidFileIconThemeChange(): Event<IFileIconTheme> {
|
||||
return this._onFileIconThemeChange.event;
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user