1
>
/*---------------------------------------------------------------------------------------------
themeConfiguration.ts
2
>
* Copyright (c) Microsoft Corporation. All rights reserved.
3
>
* Licensed under the MIT License. See License.txt in the project root for license information.
4
>
*--------------------------------------------------------------------------------------------*/
5
>
6
>
import * as nls from '../../../../nls.js';
7
>
import * as types from '../../../../base/common/types.js';
8
>
import { Registry } from '../../../../platform/registry/common/platform.js';
9
>
import { IConfigurationRegistry, Extensions as ConfigurationExtensions, IConfigurationPropertySchema, IConfigurationNode, ConfigurationScope } from '../../../../platform/configuration/common/configurationRegistry.js';
10
>
11
>
import { IJSONSchema } from '../../../../base/common/jsonSchema.js';
12
>
import { textmateColorsSchemaId, textmateColorGroupSchemaId } from './colorThemeSchema.js';
13
>
import { workbenchColorsSchemaId } from '../../../../platform/theme/common/colorRegistry.js';
14
>
import { tokenStylingSchemaId } from '../../../../platform/theme/common/tokenClassificationRegistry.js';
15
>
import { ThemeSettings, IWorkbenchColorTheme, IWorkbenchFileIconTheme, IColorCustomizations, ITokenColorCustomizations, IWorkbenchProductIconTheme, ISemanticTokenColorCustomizations, ThemeSettingTarget, ThemeSettingDefaults } from './workbenchThemeService.js';
16
>
import { IConfigurationService, ConfigurationTarget } from '../../../../platform/configuration/common/configuration.js';
17
>
import { isWeb } from '../../../../base/common/platform.js';
18
>
import { ColorScheme } from '../../../../platform/theme/common/theme.js';
19
>
import { IHostColorSchemeService } from './hostColorSchemeService.js';
20
>
import { IColorScheme } from '../../../../platform/window/common/window.js';
21
>
22
>
// Configuration: Themes
23
>
const configurationRegistry = Registry.as<IConfigurationRegistry>(ConfigurationExtensions.Configuration);
24
>
25
>
const colorThemeSettingEnum: string[] = [];
26
>
const colorThemeSettingEnumItemLabels: string[] = [];
27
>
const colorThemeSettingEnumDescriptions: string[] = [];
28
>
29
>
export function formatSettingAsLink(str: string) {
30
>
return `\`#${str}#\``;
31
>
}
32
>
33
>
export const COLOR_THEME_CONFIGURATION_SETTINGS_TAG = 'colorThemeConfiguration';
34
>
35
>
const colorThemeSettingSchema: IConfigurationPropertySchema = {
36
>
type: 'string',
37
>
markdownDescription: nls.localize({ key: 'colorTheme', comment: ['{0} will become a link to another setting.'] }, "Specifies the color theme used in the workbench when {0} is not enabled.", formatSettingAsLink(ThemeSettings.DETECT_COLOR_SCHEME)),
38
>
default: isWeb ? ThemeSettingDefaults.COLOR_THEME_LIGHT : ThemeSettingDefaults.COLOR_THEME_DARK,
39
>
tags: [COLOR_THEME_CONFIGURATION_SETTINGS_TAG],
40
>
enum: colorThemeSettingEnum,
41
>
enumDescriptions: colorThemeSettingEnumDescriptions,
42
>
enumItemLabels: colorThemeSettingEnumItemLabels,
43
>
errorMessage: nls.localize('colorThemeError', "Theme is unknown or not installed."),
44
>
};
45
>
const preferredDarkThemeSettingSchema: IConfigurationPropertySchema = {
46
>
type: 'string', //
47
>
markdownDescription: nls.localize({ key: 'preferredDarkColorTheme', comment: ['{0} will become a link to another setting.'] }, 'Specifies the color theme when system color mode is dark and {0} is enabled.', formatSettingAsLink(ThemeSettings.DETECT_COLOR_SCHEME)),
48
>
default: ThemeSettingDefaults.COLOR_THEME_DARK,
49
>
tags: [COLOR_THEME_CONFIGURATION_SETTINGS_TAG],
50
>
enum: colorThemeSettingEnum,
51
>
enumDescriptions: colorThemeSettingEnumDescriptions,
52
>
enumItemLabels: colorThemeSettingEnumItemLabels,
53
>
errorMessage: nls.localize('colorThemeError', "Theme is unknown or not installed."),
54
>
};
55
>
const preferredLightThemeSettingSchema: IConfigurationPropertySchema = {
56
>
type: 'string',
57
>
markdownDescription: nls.localize({ key: 'preferredLightColorTheme', comment: ['{0} will become a link to another setting.'] }, 'Specifies the color theme when system color mode is light and {0} is enabled.', formatSettingAsLink(ThemeSettings.DETECT_COLOR_SCHEME)),
58
>
default: ThemeSettingDefaults.COLOR_THEME_LIGHT,
59
>
tags: [COLOR_THEME_CONFIGURATION_SETTINGS_TAG],
60
>
enum: colorThemeSettingEnum,
61
>
enumDescriptions: colorThemeSettingEnumDescriptions,
62
>
enumItemLabels: colorThemeSettingEnumItemLabels,
63
>
errorMessage: nls.localize('colorThemeError', "Theme is unknown or not installed."),
64
>
};
65
>
const preferredHCDarkThemeSettingSchema: IConfigurationPropertySchema = {
66
>
type: 'string',
67
>
markdownDescription: nls.localize({ key: 'preferredHCDarkColorTheme', comment: ['{0} will become a link to another setting.'] }, 'Specifies the color theme when in high contrast dark mode and {0} is enabled.', formatSettingAsLink(ThemeSettings.DETECT_HC)),
68
>
default: ThemeSettingDefaults.COLOR_THEME_HC_DARK,
69
>
tags: [COLOR_THEME_CONFIGURATION_SETTINGS_TAG],
70
>
enum: colorThemeSettingEnum,
71
>
enumDescriptions: colorThemeSettingEnumDescriptions,
72
>
enumItemLabels: colorThemeSettingEnumItemLabels,
73
>
errorMessage: nls.localize('colorThemeError', "Theme is unknown or not installed."),
74
>
};
75
>
const preferredHCLightThemeSettingSchema: IConfigurationPropertySchema = {
76
>
type: 'string',
77
>
markdownDescription: nls.localize({ key: 'preferredHCLightColorTheme', comment: ['{0} will become a link to another setting.'] }, 'Specifies the color theme when in high contrast light mode and {0} is enabled.', formatSettingAsLink(ThemeSettings.DETECT_HC)),
78
>
default: ThemeSettingDefaults.COLOR_THEME_HC_LIGHT,
79
>
tags: [COLOR_THEME_CONFIGURATION_SETTINGS_TAG],
80
>
enum: colorThemeSettingEnum,
81
>
enumDescriptions: colorThemeSettingEnumDescriptions,
82
>
enumItemLabels: colorThemeSettingEnumItemLabels,
83
>
errorMessage: nls.localize('colorThemeError', "Theme is unknown or not installed."),
84
>
};
85
>
const detectColorSchemeSettingSchema: IConfigurationPropertySchema = {
86
>
type: 'boolean',
87
>
markdownDescription: nls.localize({ key: 'detectColorScheme', comment: ['{0} and {1} will become links to other settings.'] }, 'If enabled, will automatically select a color theme based on the system color mode. If the system color mode is dark, {0} is used, else {1}.', formatSettingAsLink(ThemeSettings.PREFERRED_DARK_THEME), formatSettingAsLink(ThemeSettings.PREFERRED_LIGHT_THEME)),
88
>
default: false,
89
>
...(isWeb ? { agentsWindow: { default: true } } : {}),
90
>
tags: [COLOR_THEME_CONFIGURATION_SETTINGS_TAG],
91
>
};
92
>
93
>
const colorCustomizationsSchema: IConfigurationPropertySchema = {
94
>
type: 'object',
95
>
description: nls.localize('workbenchColors', "Overrides colors from the currently selected color theme."),
96
>
allOf: [{ $ref: workbenchColorsSchemaId }],
97
>
default: {},
98
>
defaultSnippets: [{
99
>
body: {
100
>
}
101
>
}]
102
>
};
103
>
const fileIconThemeSettingSchema: IConfigurationPropertySchema = {
104
>
type: ['string', 'null'],
105
>
default: ThemeSettingDefaults.FILE_ICON_THEME,
106
>
description: nls.localize('iconTheme', "Specifies the file icon theme used in the workbench or 'null' to not show any file icons."),
107
>
enum: [null],
108
>
enumItemLabels: [nls.localize('noIconThemeLabel', 'None')],
109
>
enumDescriptions: [nls.localize('noIconThemeDesc', 'No file icons')],
110
>
errorMessage: nls.localize('iconThemeError', "File icon theme is unknown or not installed.")
111
>
};
112
>
const productIconThemeSettingSchema: IConfigurationPropertySchema = {
113
>
type: ['string', 'null'],
114
>
default: ThemeSettingDefaults.PRODUCT_ICON_THEME,
115
>
description: nls.localize('productIconTheme', "Specifies the product icon theme used."),
116
>
enum: [ThemeSettingDefaults.PRODUCT_ICON_THEME],
117
>
enumItemLabels: [nls.localize('defaultProductIconThemeLabel', 'Default')],
118
>
enumDescriptions: [nls.localize('defaultProductIconThemeDesc', 'Default')],
119
>
errorMessage: nls.localize('productIconThemeError', "Product icon theme is unknown or not installed.")
120
>
};
121
>
122
>
const detectHCSchemeSettingSchema: IConfigurationPropertySchema = {
123
>
type: 'boolean',
124
>
default: true,
125
>
markdownDescription: nls.localize({ key: 'autoDetectHighContrast', comment: ['{0} and {1} will become links to other settings.'] }, "If enabled, will automatically change to high contrast theme if the OS is using a high contrast theme. The high contrast theme to use is specified by {0} and {1}.", formatSettingAsLink(ThemeSettings.PREFERRED_HC_DARK_THEME), formatSettingAsLink(ThemeSettings.PREFERRED_HC_LIGHT_THEME)),
126
>
scope: ConfigurationScope.APPLICATION,
127
>
tags: [COLOR_THEME_CONFIGURATION_SETTINGS_TAG],
128
>
};
129
>
130
>
const themeSettingsConfiguration: IConfigurationNode = {
131
>
id: 'workbench',
132
>
order: 7.1,
133
>
type: 'object',
134
>
properties: {
135
>
[ThemeSettings.COLOR_THEME]: colorThemeSettingSchema,
136
>
[ThemeSettings.PREFERRED_DARK_THEME]: preferredDarkThemeSettingSchema,
137
>
[ThemeSettings.PREFERRED_LIGHT_THEME]: preferredLightThemeSettingSchema,
138
>
[ThemeSettings.PREFERRED_HC_DARK_THEME]: preferredHCDarkThemeSettingSchema,
139
>
[ThemeSettings.PREFERRED_HC_LIGHT_THEME]: preferredHCLightThemeSettingSchema,
140
>
[ThemeSettings.FILE_ICON_THEME]: fileIconThemeSettingSchema,
141
>
[ThemeSettings.COLOR_CUSTOMIZATIONS]: colorCustomizationsSchema,
142
>
[ThemeSettings.PRODUCT_ICON_THEME]: productIconThemeSettingSchema
143
>
}
144
>
};
145
>
configurationRegistry.registerConfiguration(themeSettingsConfiguration);
146
>
147
>
const themeSettingsWindowConfiguration: IConfigurationNode = {
148
>
id: 'window',
149
>
order: 8.1,
150
>
type: 'object',
151
>
properties: {
152
>
[ThemeSettings.DETECT_HC]: detectHCSchemeSettingSchema,
153
>
[ThemeSettings.DETECT_COLOR_SCHEME]: detectColorSchemeSettingSchema,
154
>
}
155
>
};
156
>
configurationRegistry.registerConfiguration(themeSettingsWindowConfiguration);
157
>
158
>
function tokenGroupSettings(description: string): IJSONSchema {
159
>
return {
160
>
description,
161
>
$ref: textmateColorGroupSchemaId
162
>
};
163
>
}
164
>
165
>
const themeSpecificSettingKey = '^\\[[^\\]]*(\\]\\s*\\[[^\\]]*)*\\]$';
166
>
167
>
const tokenColorSchema: IJSONSchema = {
168
>
type: 'object',
169
>
properties: {
170
>
comments: tokenGroupSettings(nls.localize('editorColors.comments', "Sets the colors and styles for comments")),
171
>
strings: tokenGroupSettings(nls.localize('editorColors.strings', "Sets the colors and styles for strings literals.")),
172
>
keywords: tokenGroupSettings(nls.localize('editorColors.keywords', "Sets the colors and styles for keywords.")),
173
>
numbers: tokenGroupSettings(nls.localize('editorColors.numbers', "Sets the colors and styles for number literals.")),
174
>
types: tokenGroupSettings(nls.localize('editorColors.types', "Sets the colors and styles for type declarations and references.")),
175
>
functions: tokenGroupSettings(nls.localize('editorColors.functions', "Sets the colors and styles for functions declarations and references.")),
176
>
variables: tokenGroupSettings(nls.localize('editorColors.variables', "Sets the colors and styles for variables declarations and references.")),
177
>
textMateRules: {
178
>
description: nls.localize('editorColors.textMateRules', 'Sets colors and styles using textmate theming rules (advanced).'),
179
>
$ref: textmateColorsSchemaId
180
>
},
181
>
semanticHighlighting: {
182
>
description: nls.localize('editorColors.semanticHighlighting', 'Whether semantic highlighting should be enabled for this theme.'),
183
>
deprecationMessage: nls.localize('editorColors.semanticHighlighting.deprecationMessage', 'Use `enabled` in `editor.semanticTokenColorCustomizations` setting instead.'),
184
>
markdownDeprecationMessage: nls.localize({ key: 'editorColors.semanticHighlighting.deprecationMessageMarkdown', comment: ['{0} will become a link to another setting.'] }, 'Use `enabled` in {0} setting instead.', formatSettingAsLink('editor.semanticTokenColorCustomizations')),
185
>
type: 'boolean'
186
>
}
187
>
},
188
>
additionalProperties: false
189
>
};
190
>
191
>
const tokenColorCustomizationSchema: IConfigurationPropertySchema = {
192
>
description: nls.localize('editorColors', "Overrides editor syntax colors and font style from the currently selected color theme."),
193
>
default: {},
194
>
allOf: [{ ...tokenColorSchema, patternProperties: { '^\\[': {} } }]
195
>
};
196
>
197
>
const semanticTokenColorSchema: IJSONSchema = {
198
>
type: 'object',
199
>
properties: {
200
>
enabled: {
201
>
type: 'boolean',
202
>
description: nls.localize('editorColors.semanticHighlighting.enabled', 'Whether semantic highlighting is enabled or disabled for this theme'),
203
>
suggestSortText: '0_enabled'
204
>
},
205
>
rules: {
206
>
$ref: tokenStylingSchemaId,
207
>
description: nls.localize('editorColors.semanticHighlighting.rules', 'Semantic token styling rules for this theme.'),
208
>
suggestSortText: '0_rules'
209
>
}
210
>
},
211
>
additionalProperties: false
212
>
};
213
>
214
>
const semanticTokenColorCustomizationSchema: IConfigurationPropertySchema = {
215
>
description: nls.localize('semanticTokenColors', "Overrides editor semantic token color and styles from the currently selected color theme."),
216
>
default: {},
217
>
allOf: [{ ...semanticTokenColorSchema, patternProperties: { '^\\[': {} } }]
218
>
};
219
>
220
>
const tokenColorCustomizationConfiguration: IConfigurationNode = {
221
>
id: 'editor',
222
>
order: 7.2,
223
>
type: 'object',
224
>
properties: {
225
>
[ThemeSettings.TOKEN_COLOR_CUSTOMIZATIONS]: tokenColorCustomizationSchema,
226
>
[ThemeSettings.SEMANTIC_TOKEN_COLOR_CUSTOMIZATIONS]: semanticTokenColorCustomizationSchema
227
>
}
228
>
};
229
>
230
>
configurationRegistry.registerConfiguration(tokenColorCustomizationConfiguration);
231
>
232
>
export function updateColorThemeConfigurationSchemas(themes: IWorkbenchColorTheme[]) {
233
// updates enum for the 'workbench.colorTheme` setting
234
themes.sort((a, b) => a.label.localeCompare(b.label));