diff --git a/Cargo.lock b/Cargo.lock index 36c1a62d7c..805a9f4bf6 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -4457,6 +4457,12 @@ dependencies = [ "wasm-bindgen", ] +[[package]] +name = "json_comments" +version = "0.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9dbbfed4e59ba9750e15ba154fdfd9329cee16ff3df539c2666b70f58cc32105" + [[package]] name = "jwt" version = "0.16.0" @@ -9180,10 +9186,13 @@ dependencies = [ "anyhow", "convert_case 0.6.0", "gpui2", + "indexmap 1.9.3", + "json_comments", "log", "rust-embed", "serde", "simplelog", + "strum", "theme2", "uuid 1.4.1", ] diff --git a/assets/settings/default.json b/assets/settings/default.json index 19c73ca021..9a6c7587d6 100644 --- a/assets/settings/default.json +++ b/assets/settings/default.json @@ -102,6 +102,16 @@ "selections": true }, "relative_line_numbers": false, + // When to populate a new search's query based on the text under the cursor. + // This setting can take the following three values: + // + // 1. Always populate the search query with the word under the cursor (default). + // "always" + // 2. Only populate the search query when there is text selected + // "selection" + // 3. Never populate the search query + // "never" + "seed_search_query_from_cursor": "always", // Inlay hint related settings "inlay_hints": { // Global switch to toggle hints on and off, switched off by default. diff --git a/assets/themes/src/vscode/gruvbox/gruvbox-dark-hard.json b/assets/themes/src/vscode/gruvbox/gruvbox-dark-hard.json index 4c1a7c9e8a..1b7eb8eef6 100644 --- a/assets/themes/src/vscode/gruvbox/gruvbox-dark-hard.json +++ b/assets/themes/src/vscode/gruvbox/gruvbox-dark-hard.json @@ -423,7 +423,10 @@ } }, { - "scope": ["string.interpolated.dollar.shell", "string.interpolated.backtick.shell"], + "scope": [ + "string.interpolated.dollar.shell", + "string.interpolated.backtick.shell" + ], "settings": { "foreground": "#8ec07c" } @@ -489,13 +492,19 @@ { "name": "coloring of the Java import and package identifiers", - "scope": ["storage.modifier.import.java", "storage.modifier.package.java"], + "scope": [ + "storage.modifier.import.java", + "storage.modifier.package.java" + ], "settings": { "foreground": "#bdae93" } }, { - "scope": ["keyword.other.import.java", "keyword.other.package.java"], + "scope": [ + "keyword.other.import.java", + "keyword.other.package.java" + ], "settings": { "foreground": "#8ec07c" } @@ -628,7 +637,9 @@ }, { "name": "JSON Level 0", - "scope": ["source.json meta.structure.dictionary.json support.type.property-name.json"], + "scope": [ + "source.json meta.structure.dictionary.json support.type.property-name.json" + ], "settings": { "foreground": "#b8bb26" } @@ -761,7 +772,10 @@ } }, { - "scope": ["source.go keyword.interface", "source.go keyword.struct"], + "scope": [ + "source.go keyword.interface", + "source.go keyword.struct" + ], "settings": { "foreground": "#83a598" } @@ -788,7 +802,10 @@ { "name": "ReasonML String", - "scope": ["source.reason string.double", "source.reason string.regexp"], + "scope": [ + "source.reason string.double", + "source.reason string.regexp" + ], "settings": { "foreground": "#b8bb26" } @@ -809,7 +826,10 @@ }, { "name": "ReasonML property", - "scope": ["source.reason support.property-value", "source.reason entity.name.filename"], + "scope": [ + "source.reason support.property-value", + "source.reason entity.name.filename" + ], "settings": { "foreground": "#fe8019" } @@ -831,7 +851,9 @@ }, { "name": "Powershell function attribute", - "scope": ["source.powershell support.function.attribute.powershell"], + "scope": [ + "source.powershell support.function.attribute.powershell" + ], "settings": { "foreground": "#bdae93" } diff --git a/assets/themes/src/vscode/gruvbox/gruvbox-dark-medium.json b/assets/themes/src/vscode/gruvbox/gruvbox-dark-medium.json index e9ef916193..0f22d6fc21 100644 --- a/assets/themes/src/vscode/gruvbox/gruvbox-dark-medium.json +++ b/assets/themes/src/vscode/gruvbox/gruvbox-dark-medium.json @@ -423,7 +423,10 @@ } }, { - "scope": ["string.interpolated.dollar.shell", "string.interpolated.backtick.shell"], + "scope": [ + "string.interpolated.dollar.shell", + "string.interpolated.backtick.shell" + ], "settings": { "foreground": "#8ec07c" } @@ -489,13 +492,19 @@ { "name": "coloring of the Java import and package identifiers", - "scope": ["storage.modifier.import.java", "storage.modifier.package.java"], + "scope": [ + "storage.modifier.import.java", + "storage.modifier.package.java" + ], "settings": { "foreground": "#bdae93" } }, { - "scope": ["keyword.other.import.java", "keyword.other.package.java"], + "scope": [ + "keyword.other.import.java", + "keyword.other.package.java" + ], "settings": { "foreground": "#8ec07c" } @@ -628,7 +637,9 @@ }, { "name": "JSON Level 0", - "scope": ["source.json meta.structure.dictionary.json support.type.property-name.json"], + "scope": [ + "source.json meta.structure.dictionary.json support.type.property-name.json" + ], "settings": { "foreground": "#b8bb26" } @@ -761,7 +772,10 @@ } }, { - "scope": ["source.go keyword.interface", "source.go keyword.struct"], + "scope": [ + "source.go keyword.interface", + "source.go keyword.struct" + ], "settings": { "foreground": "#83a598" } @@ -788,7 +802,10 @@ { "name": "ReasonML String", - "scope": ["source.reason string.double", "source.reason string.regexp"], + "scope": [ + "source.reason string.double", + "source.reason string.regexp" + ], "settings": { "foreground": "#b8bb26" } @@ -809,7 +826,10 @@ }, { "name": "ReasonML property", - "scope": ["source.reason support.property-value", "source.reason entity.name.filename"], + "scope": [ + "source.reason support.property-value", + "source.reason entity.name.filename" + ], "settings": { "foreground": "#fe8019" } @@ -831,7 +851,9 @@ }, { "name": "Powershell function attribute", - "scope": ["source.powershell support.function.attribute.powershell"], + "scope": [ + "source.powershell support.function.attribute.powershell" + ], "settings": { "foreground": "#bdae93" } diff --git a/assets/themes/src/vscode/gruvbox/gruvbox-dark-soft.json b/assets/themes/src/vscode/gruvbox/gruvbox-dark-soft.json index 8581447f49..e03a9f0f5c 100644 --- a/assets/themes/src/vscode/gruvbox/gruvbox-dark-soft.json +++ b/assets/themes/src/vscode/gruvbox/gruvbox-dark-soft.json @@ -423,7 +423,10 @@ } }, { - "scope": ["string.interpolated.dollar.shell", "string.interpolated.backtick.shell"], + "scope": [ + "string.interpolated.dollar.shell", + "string.interpolated.backtick.shell" + ], "settings": { "foreground": "#8ec07c" } @@ -489,13 +492,19 @@ { "name": "coloring of the Java import and package identifiers", - "scope": ["storage.modifier.import.java", "storage.modifier.package.java"], + "scope": [ + "storage.modifier.import.java", + "storage.modifier.package.java" + ], "settings": { "foreground": "#bdae93" } }, { - "scope": ["keyword.other.import.java", "keyword.other.package.java"], + "scope": [ + "keyword.other.import.java", + "keyword.other.package.java" + ], "settings": { "foreground": "#8ec07c" } @@ -628,7 +637,9 @@ }, { "name": "JSON Level 0", - "scope": ["source.json meta.structure.dictionary.json support.type.property-name.json"], + "scope": [ + "source.json meta.structure.dictionary.json support.type.property-name.json" + ], "settings": { "foreground": "#b8bb26" } @@ -761,7 +772,10 @@ } }, { - "scope": ["source.go keyword.interface", "source.go keyword.struct"], + "scope": [ + "source.go keyword.interface", + "source.go keyword.struct" + ], "settings": { "foreground": "#83a598" } @@ -788,7 +802,10 @@ { "name": "ReasonML String", - "scope": ["source.reason string.double", "source.reason string.regexp"], + "scope": [ + "source.reason string.double", + "source.reason string.regexp" + ], "settings": { "foreground": "#b8bb26" } @@ -809,7 +826,10 @@ }, { "name": "ReasonML property", - "scope": ["source.reason support.property-value", "source.reason entity.name.filename"], + "scope": [ + "source.reason support.property-value", + "source.reason entity.name.filename" + ], "settings": { "foreground": "#fe8019" } @@ -831,7 +851,9 @@ }, { "name": "Powershell function attribute", - "scope": ["source.powershell support.function.attribute.powershell"], + "scope": [ + "source.powershell support.function.attribute.powershell" + ], "settings": { "foreground": "#bdae93" } diff --git a/assets/themes/src/vscode/gruvbox/gruvbox-light-hard.json b/assets/themes/src/vscode/gruvbox/gruvbox-light-hard.json index bd0f60eac9..71af6c807e 100644 --- a/assets/themes/src/vscode/gruvbox/gruvbox-light-hard.json +++ b/assets/themes/src/vscode/gruvbox/gruvbox-light-hard.json @@ -422,7 +422,10 @@ } }, { - "scope": ["string.interpolated.dollar.shell", "string.interpolated.backtick.shell"], + "scope": [ + "string.interpolated.dollar.shell", + "string.interpolated.backtick.shell" + ], "settings": { "foreground": "#427b58" } @@ -488,13 +491,19 @@ { "name": "coloring of the Java import and package identifiers", - "scope": ["storage.modifier.import.java", "storage.modifier.package.java"], + "scope": [ + "storage.modifier.import.java", + "storage.modifier.package.java" + ], "settings": { "foreground": "#665c54" } }, { - "scope": ["keyword.other.import.java", "keyword.other.package.java"], + "scope": [ + "keyword.other.import.java", + "keyword.other.package.java" + ], "settings": { "foreground": "#427b58" } @@ -627,7 +636,9 @@ }, { "name": "JSON Level 0", - "scope": ["source.json meta.structure.dictionary.json support.type.property-name.json"], + "scope": [ + "source.json meta.structure.dictionary.json support.type.property-name.json" + ], "settings": { "foreground": "#79740e" } @@ -760,7 +771,10 @@ } }, { - "scope": ["source.go keyword.interface", "source.go keyword.struct"], + "scope": [ + "source.go keyword.interface", + "source.go keyword.struct" + ], "settings": { "foreground": "#076678" } @@ -787,7 +801,10 @@ { "name": "ReasonML String", - "scope": ["source.reason string.double", "source.reason string.regexp"], + "scope": [ + "source.reason string.double", + "source.reason string.regexp" + ], "settings": { "foreground": "#79740e" } @@ -808,7 +825,10 @@ }, { "name": "ReasonML property", - "scope": ["source.reason support.property-value", "source.reason entity.name.filename"], + "scope": [ + "source.reason support.property-value", + "source.reason entity.name.filename" + ], "settings": { "foreground": "#af3a03" } @@ -830,7 +850,9 @@ }, { "name": "Powershell function attribute", - "scope": ["source.powershell support.function.attribute.powershell"], + "scope": [ + "source.powershell support.function.attribute.powershell" + ], "settings": { "foreground": "#665c54" } diff --git a/assets/themes/src/vscode/gruvbox/gruvbox-light-medium.json b/assets/themes/src/vscode/gruvbox/gruvbox-light-medium.json index 6cd742090e..39de91c9ec 100644 --- a/assets/themes/src/vscode/gruvbox/gruvbox-light-medium.json +++ b/assets/themes/src/vscode/gruvbox/gruvbox-light-medium.json @@ -422,7 +422,10 @@ } }, { - "scope": ["string.interpolated.dollar.shell", "string.interpolated.backtick.shell"], + "scope": [ + "string.interpolated.dollar.shell", + "string.interpolated.backtick.shell" + ], "settings": { "foreground": "#427b58" } @@ -488,13 +491,19 @@ { "name": "coloring of the Java import and package identifiers", - "scope": ["storage.modifier.import.java", "storage.modifier.package.java"], + "scope": [ + "storage.modifier.import.java", + "storage.modifier.package.java" + ], "settings": { "foreground": "#665c54" } }, { - "scope": ["keyword.other.import.java", "keyword.other.package.java"], + "scope": [ + "keyword.other.import.java", + "keyword.other.package.java" + ], "settings": { "foreground": "#427b58" } @@ -627,7 +636,9 @@ }, { "name": "JSON Level 0", - "scope": ["source.json meta.structure.dictionary.json support.type.property-name.json"], + "scope": [ + "source.json meta.structure.dictionary.json support.type.property-name.json" + ], "settings": { "foreground": "#79740e" } @@ -760,7 +771,10 @@ } }, { - "scope": ["source.go keyword.interface", "source.go keyword.struct"], + "scope": [ + "source.go keyword.interface", + "source.go keyword.struct" + ], "settings": { "foreground": "#076678" } @@ -787,7 +801,10 @@ { "name": "ReasonML String", - "scope": ["source.reason string.double", "source.reason string.regexp"], + "scope": [ + "source.reason string.double", + "source.reason string.regexp" + ], "settings": { "foreground": "#79740e" } @@ -808,7 +825,10 @@ }, { "name": "ReasonML property", - "scope": ["source.reason support.property-value", "source.reason entity.name.filename"], + "scope": [ + "source.reason support.property-value", + "source.reason entity.name.filename" + ], "settings": { "foreground": "#af3a03" } @@ -830,7 +850,9 @@ }, { "name": "Powershell function attribute", - "scope": ["source.powershell support.function.attribute.powershell"], + "scope": [ + "source.powershell support.function.attribute.powershell" + ], "settings": { "foreground": "#665c54" } diff --git a/assets/themes/src/vscode/gruvbox/gruvbox-light-soft.json b/assets/themes/src/vscode/gruvbox/gruvbox-light-soft.json index a101704eed..997dcfe154 100644 --- a/assets/themes/src/vscode/gruvbox/gruvbox-light-soft.json +++ b/assets/themes/src/vscode/gruvbox/gruvbox-light-soft.json @@ -422,7 +422,10 @@ } }, { - "scope": ["string.interpolated.dollar.shell", "string.interpolated.backtick.shell"], + "scope": [ + "string.interpolated.dollar.shell", + "string.interpolated.backtick.shell" + ], "settings": { "foreground": "#427b58" } @@ -488,13 +491,19 @@ { "name": "coloring of the Java import and package identifiers", - "scope": ["storage.modifier.import.java", "storage.modifier.package.java"], + "scope": [ + "storage.modifier.import.java", + "storage.modifier.package.java" + ], "settings": { "foreground": "#665c54" } }, { - "scope": ["keyword.other.import.java", "keyword.other.package.java"], + "scope": [ + "keyword.other.import.java", + "keyword.other.package.java" + ], "settings": { "foreground": "#427b58" } @@ -627,7 +636,9 @@ }, { "name": "JSON Level 0", - "scope": ["source.json meta.structure.dictionary.json support.type.property-name.json"], + "scope": [ + "source.json meta.structure.dictionary.json support.type.property-name.json" + ], "settings": { "foreground": "#79740e" } @@ -760,7 +771,10 @@ } }, { - "scope": ["source.go keyword.interface", "source.go keyword.struct"], + "scope": [ + "source.go keyword.interface", + "source.go keyword.struct" + ], "settings": { "foreground": "#076678" } @@ -787,7 +801,10 @@ { "name": "ReasonML String", - "scope": ["source.reason string.double", "source.reason string.regexp"], + "scope": [ + "source.reason string.double", + "source.reason string.regexp" + ], "settings": { "foreground": "#79740e" } @@ -808,7 +825,10 @@ }, { "name": "ReasonML property", - "scope": ["source.reason support.property-value", "source.reason entity.name.filename"], + "scope": [ + "source.reason support.property-value", + "source.reason entity.name.filename" + ], "settings": { "foreground": "#af3a03" } @@ -830,7 +850,9 @@ }, { "name": "Powershell function attribute", - "scope": ["source.powershell support.function.attribute.powershell"], + "scope": [ + "source.powershell support.function.attribute.powershell" + ], "settings": { "foreground": "#665c54" } diff --git a/assets/themes/src/vscode/noctis/family.json b/assets/themes/src/vscode/noctis/family.json index 26aba7e213..525cb160f5 100644 --- a/assets/themes/src/vscode/noctis/family.json +++ b/assets/themes/src/vscode/noctis/family.json @@ -1,61 +1,61 @@ { - "name": "Notctis", - "author": "Liviu Schera (liviuschera)", - "themes": [ - { - "name": "Noctis Azureus", - "file_name": "azureus.json", - "appearance": "dark" - }, - { - "name": "Noctis Bordo", - "file_name": "bordo.json", - "appearance": "dark" - }, - { - "name": "Noctus Hibernus", - "file_name": "hibernus.json", - "appearance": "light" - }, - { - "name": "Noctis Lilac", - "file_name": "lilac.json", - "appearance": "dark" - }, - { - "name": "Noctis Lux", - "file_name": "lux.json", - "appearance": "light" - }, - { - "name": "Noctis Minimus", - "file_name": "minimus.json", - "appearance": "dark" - }, - { - "name": "Noctis", - "file_name": "noctis.json", - "appearance": "dark" - }, - { - "name": "Noctis Obscuro", - "file_name": "obscuro.json", - "appearance": "dark" - }, - { - "name": "Noctis Sereno", - "file_name": "obscuro.json", - "appearance": "dark" - }, - { - "name": "Noctis Uva", - "file_name": "uva.json", - "appearance": "dark" - }, - { - "name": "Noctis Viola", - "file_name": "viola.json", - "appearance": "dark" - } - ] + "name": "Noctis", + "author": "Liviu Schera (liviuschera)", + "themes": [ + { + "name": "Noctis Azureus", + "file_name": "azureus.json", + "appearance": "dark" + }, + { + "name": "Noctis Bordo", + "file_name": "bordo.json", + "appearance": "dark" + }, + { + "name": "Noctus Hibernus", + "file_name": "hibernus.json", + "appearance": "light" + }, + { + "name": "Noctis Lilac", + "file_name": "lilac.json", + "appearance": "dark" + }, + { + "name": "Noctis Lux", + "file_name": "lux.json", + "appearance": "light" + }, + { + "name": "Noctis Minimus", + "file_name": "minimus.json", + "appearance": "dark" + }, + { + "name": "Noctis", + "file_name": "noctis.json", + "appearance": "dark" + }, + { + "name": "Noctis Obscuro", + "file_name": "obscuro.json", + "appearance": "dark" + }, + { + "name": "Noctis Sereno", + "file_name": "obscuro.json", + "appearance": "dark" + }, + { + "name": "Noctis Uva", + "file_name": "uva.json", + "appearance": "dark" + }, + { + "name": "Noctis Viola", + "file_name": "viola.json", + "appearance": "dark" + } + ] } diff --git a/assets/themes/src/vscode/rose-pine/family.json b/assets/themes/src/vscode/rose-pine/family.json index 5b72edd300..1cdcab7842 100644 --- a/assets/themes/src/vscode/rose-pine/family.json +++ b/assets/themes/src/vscode/rose-pine/family.json @@ -1,21 +1,21 @@ { - "name": "Rose Pine", - "author": "Rosé Pine", - "themes": [ - { - "name": "Rose Pine", - "file_name": "rose-pine.json", - "appearance": "dark" - }, - { - "name": "Rose Moon", - "file_name": "rose-pine-moon.json", - "appearance": "dark" - }, - { - "name": "Rose Pine Dawn", - "file_name": "rose-pine-dawn.json", - "appearance": "light" - } - ] + "name": "Rose Pine", + "author": "Rosé Pine", + "themes": [ + { + "name": "Rose Pine", + "file_name": "rose-pine.json", + "appearance": "dark" + }, + { + "name": "Rose Pine Moon", + "file_name": "rose-pine-moon.json", + "appearance": "dark" + }, + { + "name": "Rose Pine Dawn", + "file_name": "rose-pine-dawn.json", + "appearance": "light" + } + ] } diff --git a/assets/themes/src/vscode/synthwave-84/synthwave.json b/assets/themes/src/vscode/synthwave-84/synthwave.json index 5b38ef46fa..9b23270d8c 100644 --- a/assets/themes/src/vscode/synthwave-84/synthwave.json +++ b/assets/themes/src/vscode/synthwave-84/synthwave.json @@ -1,822 +1,841 @@ { - "name": "SynthWave 84", - "type": "dark", - "semanticHighlighting": true, - "colors": { - "focusBorder": "#1f212b", - "foreground": "#ffffff", - "widget.shadow": "#2a2139", - "selection.background": "#ffffff20", - "errorForeground": "#fe4450", - "textLink.activeForeground": "#ff7edb", - "textLink.foreground": "#f97e72", - "button.background": "#614D85", - "dropdown.background": "#232530", - "dropdown.listBackground": "#2a2139", - "input.background": "#2a2139", - "inputOption.activeBorder": "#ff7edb99", - "inputValidation.errorBackground": "#fe445080", - "inputValidation.errorBorder": "#fe445000", - "scrollbar.shadow": "#2a2139", - "scrollbarSlider.activeBackground": "#9d8bca20", - "scrollbarSlider.background": "#9d8bca30", - "scrollbarSlider.hoverBackground": "#9d8bca50", - "badge.foreground": "#ffffff", - "badge.background": "#2a2139", - "progressBar.background": "#f97e72", - "list.activeSelectionBackground": "#ffffff20", - "list.activeSelectionForeground": "#ffffff", - "list.dropBackground": "#34294f66", - "list.focusBackground": "#ffffff20", - "list.focusForeground": "#ffffff", - "list.highlightForeground": "#f97e72", - "list.hoverBackground": "#37294d99", - "list.hoverForeground": "#ffffff", - "list.inactiveSelectionBackground": "#ffffff20", - "list.inactiveSelectionForeground": "#ffffff", - "list.inactiveFocusBackground": "#2a213999", - "list.errorForeground": "#fe4450E6", - "list.warningForeground": "#72f1b8bb", - "activityBar.background": "#171520", - "activityBar.dropBackground": "#34294f66", - "activityBar.foreground": "#ffffffCC", - "activityBarBadge.background": "#f97e72", - "activityBarBadge.foreground": "#2a2139", - "sideBar.background": "#241b2f", - "sideBar.foreground": "#ffffff99", - "sideBar.dropBackground": "#34294f4c", - "sideBarSectionHeader.background": "#241b2f", - "sideBarSectionHeader.foreground": "#ffffffca", - "menu.background": "#463465", - "editorGroup.border": "#495495", - "editorGroup.dropBackground": "#4954954a", - "editorGroupHeader.tabsBackground": "#241b2f", - "tab.border": "#241b2f00", - "tab.activeBorder": "#880088", - "tab.inactiveBackground": "#262335", - "editor.background": "#262335", - "editorLineNumber.foreground": "#ffffff73", - "editorLineNumber.activeForeground": "#ffffffcc", - "editorCursor.background": "#241b2f", - "editorCursor.foreground": "#f97e72", - "editor.selectionBackground": "#ffffff20", - "editor.selectionHighlightBackground": "#ffffff20", - "editor.wordHighlightBackground": "#34294f88", - "editor.wordHighlightStrongBackground": "#34294f88", - "editor.findMatchBackground": "#D18616bb", - "editor.findMatchHighlightBackground": "#D1861655", - "editor.findRangeHighlightBackground": "#34294f1a", - "editor.hoverHighlightBackground": "#463564", - "editor.lineHighlightBorder": "#7059AB66", - "editor.rangeHighlightBackground": "#49549539", - "editorIndentGuide.background": "#444251", - "editorIndentGuide.activeBackground": "#A148AB80", - "editorRuler.foreground": "#A148AB80", - "editorCodeLens.foreground": "#ffffff7c", - "editorBracketMatch.background": "#34294f66", - "editorBracketMatch.border": "#495495", - "editorOverviewRuler.border": "#34294fb3", - "editorOverviewRuler.findMatchForeground": "#D1861699", - "editorOverviewRuler.modifiedForeground": "#b893ce99", - "editorOverviewRuler.addedForeground": "#09f7a099", - "editorOverviewRuler.deletedForeground": "#fe445099", - "editorOverviewRuler.errorForeground": "#fe4450dd", - "editorOverviewRuler.warningForeground": "#72f1b8cc", - "editorError.foreground": "#fe4450", - "editorWarning.foreground": "#72f1b8cc", - "editorGutter.modifiedBackground": "#b893ce8f", - "editorGutter.addedBackground": "#206d4bd6", - "editorGutter.deletedBackground": "#fa2e46a4", - "diffEditor.insertedTextBackground": "#0beb9935", - "diffEditor.removedTextBackground": "#fe445035", - "editorWidget.background": "#171520DC", - "editorWidget.border": "#ffffff22", - "editorWidget.resizeBorder": "#ffffff44", - "editorSuggestWidget.highlightForeground": "#f97e72", - "editorSuggestWidget.selectedBackground": "#ffffff36", - "peekView.border": "#495495", - "peekViewEditor.background": "#232530", - "peekViewEditor.matchHighlightBackground": "#D18616bb", - "peekViewResult.background": "#232530", - "peekViewResult.matchHighlightBackground": "#D1861655", - "peekViewResult.selectionBackground": "#2a213980", - "peekViewTitle.background": "#232530", - "panelTitle.activeBorder": "#f97e72", - "statusBar.background": "#241b2f", - "statusBar.foreground": "#ffffff80", - "statusBar.debuggingBackground": "#f97e72", - "statusBar.debuggingForeground": "#08080f", - "statusBar.noFolderBackground": "#241b2f", - "statusBarItem.prominentBackground": "#2a2139", - "statusBarItem.prominentHoverBackground": "#34294f", - "titleBar.activeBackground": "#241b2f", - "titleBar.inactiveBackground": "#241b2f", - "extensionButton.prominentBackground": "#f97e72", - "extensionButton.prominentHoverBackground": "#ff7edb", - "pickerGroup.foreground": "#f97e72ea", - "terminal.foreground": "#ffffff", - "terminal.ansiBlue": "#03edf9", - "terminal.ansiBrightBlue": "#03edf9", - "terminal.ansiBrightCyan": "#03edf9", - "terminal.ansiBrightGreen": "#72f1b8", - "terminal.ansiBrightMagenta": "#ff7edb", - "terminal.ansiBrightRed": "#fe4450", - "terminal.ansiBrightYellow": "#fede5d", - "terminal.ansiCyan": "#03edf9", - "terminal.ansiGreen": "#72f1b8", - "terminal.ansiMagenta": "#ff7edb", - "terminal.ansiRed": "#fe4450", - "terminal.ansiYellow": "#f3e70f", - "terminal.selectionBackground": "#ffffff20", - "terminalCursor.background": "#ffffff", - "terminalCursor.foreground": "#03edf9", - "debugToolBar.background": "#463465", - "walkThrough.embeddedEditorBackground": "#232530", - "gitDecoration.modifiedResourceForeground": "#b893ceee", - "gitDecoration.deletedResourceForeground": "#fe4450", - "gitDecoration.addedResourceForeground": "#72f1b8cc", - "gitDecoration.untrackedResourceForeground": "#72f1b8", - "gitDecoration.ignoredResourceForeground": "#ffffff59", - "minimapGutter.addedBackground": "#09f7a099", - "minimapGutter.modifiedBackground": "#b893ce", - "minimapGutter.deletedBackground": "#fe4450", - "breadcrumbPicker.background": "#232530" + "name": "SynthWave 84", + "type": "dark", + "semanticHighlighting": true, + "colors": { + "focusBorder": "#1f212b", + "foreground": "#ffffff", + "widget.shadow": "#2a2139", + "selection.background": "#ffffff20", + "errorForeground": "#fe4450", + "textLink.activeForeground": "#ff7edb", + "textLink.foreground": "#f97e72", + "button.background": "#614D85", + "dropdown.background": "#232530", + "dropdown.listBackground": "#2a2139", + "input.background": "#2a2139", + "inputOption.activeBorder": "#ff7edb99", + "inputValidation.errorBackground": "#fe445080", + "inputValidation.errorBorder": "#fe445000", + "scrollbar.shadow": "#2a2139", + "scrollbarSlider.activeBackground": "#9d8bca20", + "scrollbarSlider.background": "#9d8bca30", + "scrollbarSlider.hoverBackground": "#9d8bca50", + "badge.foreground": "#ffffff", + "badge.background": "#2a2139", + "progressBar.background": "#f97e72", + "list.activeSelectionBackground": "#ffffff20", + "list.activeSelectionForeground": "#ffffff", + "list.dropBackground": "#34294f66", + "list.focusBackground": "#ffffff20", + "list.focusForeground": "#ffffff", + "list.highlightForeground": "#f97e72", + "list.hoverBackground": "#37294d99", + "list.hoverForeground": "#ffffff", + "list.inactiveSelectionBackground": "#ffffff20", + "list.inactiveSelectionForeground": "#ffffff", + "list.inactiveFocusBackground": "#2a213999", + "list.errorForeground": "#fe4450E6", + "list.warningForeground": "#72f1b8bb", + "activityBar.background": "#171520", + "activityBar.dropBackground": "#34294f66", + "activityBar.foreground": "#ffffffCC", + "activityBarBadge.background": "#f97e72", + "activityBarBadge.foreground": "#2a2139", + "sideBar.background": "#241b2f", + "sideBar.foreground": "#ffffff99", + "sideBar.dropBackground": "#34294f4c", + "sideBarSectionHeader.background": "#241b2f", + "sideBarSectionHeader.foreground": "#ffffffca", + "menu.background": "#463465", + "editorGroup.border": "#495495", + "editorGroup.dropBackground": "#4954954a", + "editorGroupHeader.tabsBackground": "#241b2f", + "tab.border": "#241b2f00", + "tab.activeBorder": "#880088", + "tab.inactiveBackground": "#262335", + "editor.background": "#262335", + "editorLineNumber.foreground": "#ffffff73", + "editorLineNumber.activeForeground": "#ffffffcc", + "editorCursor.background": "#241b2f", + "editorCursor.foreground": "#f97e72", + "editor.selectionBackground": "#ffffff20", + "editor.selectionHighlightBackground": "#ffffff20", + "editor.wordHighlightBackground": "#34294f88", + "editor.wordHighlightStrongBackground": "#34294f88", + "editor.findMatchBackground": "#D18616bb", + "editor.findMatchHighlightBackground": "#D1861655", + "editor.findRangeHighlightBackground": "#34294f1a", + "editor.hoverHighlightBackground": "#463564", + "editor.lineHighlightBorder": "#7059AB66", + "editor.rangeHighlightBackground": "#49549539", + "editorIndentGuide.background": "#444251", + "editorIndentGuide.activeBackground": "#A148AB80", + "editorRuler.foreground": "#A148AB80", + "editorCodeLens.foreground": "#ffffff7c", + "editorBracketMatch.background": "#34294f66", + "editorBracketMatch.border": "#495495", + "editorOverviewRuler.border": "#34294fb3", + "editorOverviewRuler.findMatchForeground": "#D1861699", + "editorOverviewRuler.modifiedForeground": "#b893ce99", + "editorOverviewRuler.addedForeground": "#09f7a099", + "editorOverviewRuler.deletedForeground": "#fe445099", + "editorOverviewRuler.errorForeground": "#fe4450dd", + "editorOverviewRuler.warningForeground": "#72f1b8cc", + "editorError.foreground": "#fe4450", + "editorWarning.foreground": "#72f1b8cc", + "editorGutter.modifiedBackground": "#b893ce8f", + "editorGutter.addedBackground": "#206d4bd6", + "editorGutter.deletedBackground": "#fa2e46a4", + "diffEditor.insertedTextBackground": "#0beb9935", + "diffEditor.removedTextBackground": "#fe445035", + "editorWidget.background": "#171520DC", + "editorWidget.border": "#ffffff22", + "editorWidget.resizeBorder": "#ffffff44", + "editorSuggestWidget.highlightForeground": "#f97e72", + "editorSuggestWidget.selectedBackground": "#ffffff36", + "peekView.border": "#495495", + "peekViewEditor.background": "#232530", + "peekViewEditor.matchHighlightBackground": "#D18616bb", + "peekViewResult.background": "#232530", + "peekViewResult.matchHighlightBackground": "#D1861655", + "peekViewResult.selectionBackground": "#2a213980", + "peekViewTitle.background": "#232530", + "panelTitle.activeBorder": "#f97e72", + "statusBar.background": "#241b2f", + "statusBar.foreground": "#ffffff80", + "statusBar.debuggingBackground": "#f97e72", + "statusBar.debuggingForeground": "#08080f", + "statusBar.noFolderBackground": "#241b2f", + "statusBarItem.prominentBackground": "#2a2139", + "statusBarItem.prominentHoverBackground": "#34294f", + "titleBar.activeBackground": "#241b2f", + "titleBar.inactiveBackground": "#241b2f", + "extensionButton.prominentBackground": "#f97e72", + "extensionButton.prominentHoverBackground": "#ff7edb", + "pickerGroup.foreground": "#f97e72ea", + "terminal.foreground": "#ffffff", + "terminal.ansiBlue": "#03edf9", + "terminal.ansiBrightBlue": "#03edf9", + "terminal.ansiBrightCyan": "#03edf9", + "terminal.ansiBrightGreen": "#72f1b8", + "terminal.ansiBrightMagenta": "#ff7edb", + "terminal.ansiBrightRed": "#fe4450", + "terminal.ansiBrightYellow": "#fede5d", + "terminal.ansiCyan": "#03edf9", + "terminal.ansiGreen": "#72f1b8", + "terminal.ansiMagenta": "#ff7edb", + "terminal.ansiRed": "#fe4450", + "terminal.ansiYellow": "#f3e70f", + "terminal.selectionBackground": "#ffffff20", + "terminalCursor.background": "#ffffff", + "terminalCursor.foreground": "#03edf9", + "debugToolBar.background": "#463465", + "walkThrough.embeddedEditorBackground": "#232530", + "gitDecoration.modifiedResourceForeground": "#b893ceee", + "gitDecoration.deletedResourceForeground": "#fe4450", + "gitDecoration.addedResourceForeground": "#72f1b8cc", + "gitDecoration.untrackedResourceForeground": "#72f1b8", + "gitDecoration.ignoredResourceForeground": "#ffffff59", + "minimapGutter.addedBackground": "#09f7a099", + "minimapGutter.modifiedBackground": "#b893ce", + "minimapGutter.deletedBackground": "#fe4450", + "breadcrumbPicker.background": "#232530" + }, + "tokenColors": [ + { + "name": "Comment", + "scope": [ + "comment", + "string.quoted.docstring.multi.python", + "string.quoted.docstring.multi.python punctuation.definition.string.begin.python", + "string.quoted.docstring.multi.python punctuation.definition.string.end.python" + ], + "settings": { + "foreground": "#848bbd", + "fontStyle": "italic" + } }, - "tokenColors": [ - { - "name": "Comment", - "scope": [ - "comment", - "string.quoted.docstring.multi.python", - "string.quoted.docstring.multi.python punctuation.definition.string.begin.python", - "string.quoted.docstring.multi.python punctuation.definition.string.end.python" - ], - "settings": { - "foreground": "#848bbd", - "fontStyle": "italic" - } - }, - { - "name": "String", - "scope": ["string.quoted", "string.template", "punctuation.definition.string"], - "settings": { - "foreground": "#ff8b39" - } - }, - { - "name": "Punctuation within templates", - "scope": "string.template meta.embedded.line", - "settings": { - "foreground": "#b6b1b1" - } - }, - { - "name": "Variable", - "scope": ["variable", "entity.name.variable"], - "settings": { - "foreground": "#ff7edb" - } - }, - { - "name": "Language variable", - "scope": "variable.language", - "settings": { - "foreground": "#fe4450", - "fontStyle": "bold" - } - }, - { - "name": "Parameter", - "scope": "variable.parameter", - "settings": { - "fontStyle": "italic" - } - }, - { - "name": "Storage (declaration or modifier keyword)", - "scope": ["storage.type", "storage.modifier"], - "settings": { - "foreground": "#fede5d" - } - }, - { - "name": "Constant", - "scope": "constant", - "settings": { - "foreground": "#f97e72" - } - }, - { - "name": "Regex", - "scope": "string.regexp", - "settings": { - "foreground": "#f97e72" - } - }, - { - "name": "Number", - "scope": "constant.numeric", - "settings": { - "foreground": "#f97e72" - } - }, - { - "name": "Language constant (boolean, null)", - "scope": "constant.language", - "settings": { - "foreground": "#f97e72" - } - }, - { - "name": "Character escape", - "scope": "constant.character.escape", - "settings": { - "foreground": "#36f9f6" - } - }, - { - "name": "Entity", - "scope": "entity.name", - "settings": { - "foreground": "#fe4450" - } - }, - { - "name": "HTML or XML tag", - "scope": "entity.name.tag", - "settings": { - "foreground": "#72f1b8" - } - }, - { - "name": "HTML or XML tag brackets", - "scope": ["punctuation.definition.tag"], - "settings": { - "foreground": "#36f9f6" - } - }, - { - "name": "Tag attribute", - "scope": "entity.other.attribute-name", - "settings": { - "foreground": "#fede5d" - } - }, - { - "name": "Tag attribute HTML", - "scope": "entity.other.attribute-name.html", - "settings": { - "foreground": "#fede5d", - "fontStyle": "italic" - } - }, - { - "name": "Class", - "scope": ["entity.name.type", "meta.attribute.class.html"], - "settings": { - "foreground": "#fe4450" - } - }, - { - "name": "Inherited class", - "scope": "entity.other.inherited-class", - "settings": { - "foreground": "#D50" - } - }, - { - "name": "Function", - "scope": ["entity.name.function", "variable.function"], - "settings": { - "foreground": "#36f9f6" - } - }, - { - "name": "JS Export", - "scope": ["keyword.control.export.js", "keyword.control.import.js"], - "settings": { - "foreground": "#72f1b8" - } - }, - { - "name": "JS Numerics", - "scope": ["constant.numeric.decimal.js"], - "settings": { - "foreground": "#2EE2FA" - } - }, - { - "name": "Keyword", - "scope": "keyword", - "settings": { - "foreground": "#fede5d" - } - }, - { - "name": "Control keyword", - "scope": "keyword.control", - "settings": { - "foreground": "#fede5d" - } - }, - { - "name": "Operator", - "scope": "keyword.operator", - "settings": { - "foreground": "#fede5d" - } - }, - { - "name": "Special operator", - "scope": [ - "keyword.operator.new", - "keyword.operator.expression", - "keyword.operator.logical" - ], - "settings": { - "foreground": "#fede5d" - } - }, - { - "name": "Unit", - "scope": "keyword.other.unit", - "settings": { - "foreground": "#f97e72" - } - }, - { - "name": "Support", - "scope": "support", - "settings": { - "foreground": "#fe4450" - } - }, - { - "name": "Support function", - "scope": "support.function", - "settings": { - "foreground": "#36f9f6" - } - }, - { - "name": "Support variable", - "scope": "support.variable", - "settings": { - "foreground": "#ff7edb" - } - }, - { - "name": "Object literal key / property", - "scope": ["meta.object-literal.key", "support.type.property-name"], - "settings": { - "foreground": "#ff7edb" - } - }, - { - "name": "Key-value separator", - "scope": "punctuation.separator.key-value", - "settings": { - "foreground": "#b6b1b1" - } - }, - { - "name": "Embedded punctuation", - "scope": "punctuation.section.embedded", - "settings": { - "foreground": "#fede5d" - } - }, - { - "name": "Template expression", - "scope": [ - "punctuation.definition.template-expression.begin", - "punctuation.definition.template-expression.end" - ], - "settings": { - "foreground": "#72f1b8" - } - }, - { - "name": "CSS property", - "scope": ["support.type.property-name.css", "support.type.property-name.json"], - "settings": { - "foreground": "#72f1b8" - } - }, - { - "name": "JS Switch control", - "scope": "switch-block.expr.js", - "settings": { - "foreground": "#72f1b8" - } - }, - { - "name": "JS object path", - "scope": "variable.other.constant.property.js, variable.other.property.js", - "settings": { - "foreground": "#2ee2fa" - } - }, - { - "name": "Color", - "scope": "constant.other.color", - "settings": { - "foreground": "#f97e72" - } - }, - { - "name": "Font names", - "scope": "support.constant.font-name", - "settings": { - "foreground": "#f97e72" - } - }, - { - "name": "CSS #id", - "scope": "entity.other.attribute-name.id", - "settings": { - "foreground": "#36f9f6" - } - }, - { - "name": "Pseudo CSS", - "scope": [ - "entity.other.attribute-name.pseudo-element", - "entity.other.attribute-name.pseudo-class" - ], - "settings": { - "foreground": "#D50" - } - }, - { - "name": "CSS support functions (rgb)", - "scope": "support.function.misc.css", - "settings": { - "foreground": "#fe4450" - } - }, - { - "name": "Markup heading", - "scope": ["markup.heading", "entity.name.section"], - "settings": { - "foreground": "#ff7edb" - } - }, - { - "name": "Markup text", - "scope": ["text.html", "keyword.operator.assignment"], - "settings": { - "foreground": "#ffffffee" - } - }, - { - "name": "Markup quote", - "scope": "markup.quote", - "settings": { - "foreground": "#b6b1b1cc", - "fontStyle": "italic" - } - }, - { - "name": "Markup list", - "scope": "beginning.punctuation.definition.list", - "settings": { - "foreground": "#ff7edb" - } - }, - { - "name": "Markup link", - "scope": "markup.underline.link", - "settings": { - "foreground": "#D50" - } - }, - { - "name": "Markup link description", - "scope": "string.other.link.description", - "settings": { - "foreground": "#f97e72" - } - }, - { - "name": "Python function call", - "scope": "meta.function-call.generic.python", - "settings": { - "foreground": "#36f9f6" - } - }, - { - "name": "Python variable params", - "scope": "variable.parameter.function-call.python", - "settings": { - "foreground": "#72f1b8" - } - }, - { - "name": "C# storage type", - "scope": "storage.type.cs", - "settings": { - "foreground": "#fe4450" - } - }, - { - "name": "C# local variable", - "scope": "entity.name.variable.local.cs", - "settings": { - "foreground": "#ff7edb" - } - }, - { - "name": "C# properties and fields", - "scope": ["entity.name.variable.field.cs", "entity.name.variable.property.cs"], - "settings": { - "foreground": "#ff7edb" - } - }, - { - "name": "C placeholder", - "scope": "constant.other.placeholder.c", - "settings": { - "foreground": "#72f1b8", - "fontStyle": "italic" - } - }, - { - "name": "C preprocessors", - "scope": ["keyword.control.directive.include.c", "keyword.control.directive.define.c"], - "settings": { - "foreground": "#72f1b8" - } - }, - { - "name": "C storage modifier", - "scope": "storage.modifier.c", - "settings": { - "foreground": "#fe4450" - } - }, - { - "name": "C++ operators", - "scope": "source.cpp keyword.operator", - "settings": { - "foreground": "#fede5d" - } - }, - { - "name": "C++ placeholder", - "scope": "constant.other.placeholder.cpp", - "settings": { - "foreground": "#72f1b8", - "fontStyle": "italic" - } - }, - { - "name": "C++ include", - "scope": [ - "keyword.control.directive.include.cpp", - "keyword.control.directive.define.cpp" - ], - "settings": { - "foreground": "#72f1b8" - } - }, - { - "name": "C++ constant modifier", - "scope": "storage.modifier.specifier.const.cpp", - "settings": { - "foreground": "#fe4450" - } - }, - { - "name": "Elixir Classes", - "scope": [ - "source.elixir support.type.elixir", - "source.elixir meta.module.elixir entity.name.class.elixir" - ], - "settings": { - "foreground": "#36f9f6" - } - }, - { - "name": "Elixir Functions", - "scope": "source.elixir entity.name.function", - "settings": { - "foreground": "#72f1b8" - } - }, - { - "name": "Elixir Constants", - "scope": [ - "source.elixir constant.other.symbol.elixir", - "source.elixir constant.other.keywords.elixir" - ], - "settings": { - "foreground": "#36f9f6" - } - }, - { - "name": "Elixir String Punctuation", - "scope": "source.elixir punctuation.definition.string", - "settings": { - "foreground": "#72f1b8" - } - }, - { - "name": "Elixir", - "scope": [ - "source.elixir variable.other.readwrite.module.elixir", - "source.elixir variable.other.readwrite.module.elixir punctuation.definition.variable.elixir" - ], - "settings": { - "foreground": "#72f1b8" - } - }, - { - "name": "Elixir Binary Punctuation", - "scope": "source.elixir .punctuation.binary.elixir", - "settings": { - "foreground": "#ff7edb", - "fontStyle": "italic" - } - }, - { - "name": "Clojure Globals", - "scope": ["entity.global.clojure"], - "settings": { - "foreground": "#36f9f6", - "fontStyle": "bold" - } - }, - { - "name": "Clojure Storage", - "scope": ["storage.control.clojure"], - "settings": { - "foreground": "#36f9f6", - "fontStyle": "italic" - } - }, - { - "name": "Clojure Metadata", - "scope": ["meta.metadata.simple.clojure", "meta.metadata.map.clojure"], - "settings": { - "foreground": "#fe4450", - "fontStyle": "italic" - } - }, - { - "name": "Clojure Macros, Quoted", - "scope": ["meta.quoted-expression.clojure"], - "settings": { - "fontStyle": "italic" - } - }, - { - "name": "Clojure Symbols", - "scope": ["meta.symbol.clojure"], - "settings": { - "foreground": "#ff7edbff" - } - }, - { - "name": "Go basic", - "scope": "source.go", - "settings": { - "foreground": "#ff7edbff" - } - }, - { - "name": "Go Function Calls", - "scope": "source.go meta.function-call.go", - "settings": { - "foreground": "#36f9f6" - } - }, - { - "name": "Go Keywords", - "scope": [ - "source.go keyword.package.go", - "source.go keyword.import.go", - "source.go keyword.function.go", - "source.go keyword.type.go", - "source.go keyword.const.go", - "source.go keyword.var.go", - "source.go keyword.map.go", - "source.go keyword.channel.go", - "source.go keyword.control.go" - ], - "settings": { - "foreground": "#fede5d" - } - }, - { - "name": "Go interfaces", - "scope": [ - "source.go storage.type", - "source.go keyword.struct.go", - "source.go keyword.interface.go" - ], - "settings": { - "foreground": "#72f1b8" - } - }, - { - "name": "Go Constants e.g. nil, string format (%s, %d, etc.)", - "scope": [ - "source.go constant.language.go", - "source.go constant.other.placeholder.go", - "source.go variable" - ], - "settings": { - "foreground": "#2EE2FA" - } - }, - { - "name": "Markdown links and image paths", - "scope": ["markup.underline.link.markdown", "markup.inline.raw.string.markdown"], - "settings": { - "foreground": "#72f1b8", - "fontStyle": "italic" - } - }, - { - "name": "Markdown links and image paths", - "scope": ["string.other.link.title.markdown"], - "settings": { - "foreground": "#fede5d" - } - }, - { - "name": "Markdown headings", - "scope": ["markup.heading.markdown", "entity.name.section.markdown"], - "settings": { - "foreground": "#ff7edb", - "fontStyle": "bold" - } - }, - { - "name": "Markdown italic", - "scope": ["markup.italic.markdown"], - "settings": { - "foreground": "#2EE2FA", - "fontStyle": "italic" - } - }, - { - "name": "Markdown bold", - "scope": ["markup.bold.markdown"], - "settings": { - "foreground": "#2EE2FA", - "fontStyle": "bold" - } - }, - { - "name": "Markdown quotes", - "scope": ["punctuation.definition.quote.begin.markdown", "markup.quote.markdown"], - "settings": { - "foreground": "#72f1b8" - } - }, - { - "name": "Basic source colours", - "scope": ["source.dart", "source.python", "source.scala"], - "settings": { - "foreground": "#ff7edbff" - } - }, - { - "name": "Dart strings", - "scope": ["string.interpolated.single.dart"], - "settings": { - "foreground": "#f97e72" - } - }, - { - "name": "Dart variable params", - "scope": ["variable.parameter.dart"], - "settings": { - "foreground": "#72f1b8" - } - }, - { - "name": "Dart numerics", - "scope": ["constant.numeric.dart"], - "settings": { - "foreground": "#2EE2FA" - } - }, - { - "name": "Scala variable params", - "scope": ["variable.parameter.scala"], - "settings": { - "foreground": "#2EE2FA" - } - }, - { - "name": "Scala", - "scope": ["meta.template.expression.scala"], - "settings": { - "foreground": "#72f1b8" - } - } - ] + { + "name": "String", + "scope": [ + "string.quoted", + "string.template", + "punctuation.definition.string" + ], + "settings": { + "foreground": "#ff8b39" + } + }, + { + "name": "Punctuation within templates", + "scope": "string.template meta.embedded.line", + "settings": { + "foreground": "#b6b1b1" + } + }, + { + "name": "Variable", + "scope": ["variable", "entity.name.variable"], + "settings": { + "foreground": "#ff7edb" + } + }, + { + "name": "Language variable", + "scope": "variable.language", + "settings": { + "foreground": "#fe4450", + "fontStyle": "bold" + } + }, + { + "name": "Parameter", + "scope": "variable.parameter", + "settings": { + "fontStyle": "italic" + } + }, + { + "name": "Storage (declaration or modifier keyword)", + "scope": ["storage.type", "storage.modifier"], + "settings": { + "foreground": "#fede5d" + } + }, + { + "name": "Constant", + "scope": "constant", + "settings": { + "foreground": "#f97e72" + } + }, + { + "name": "Regex", + "scope": "string.regexp", + "settings": { + "foreground": "#f97e72" + } + }, + { + "name": "Number", + "scope": "constant.numeric", + "settings": { + "foreground": "#f97e72" + } + }, + { + "name": "Language constant (boolean, null)", + "scope": "constant.language", + "settings": { + "foreground": "#f97e72" + } + }, + { + "name": "Character escape", + "scope": "constant.character.escape", + "settings": { + "foreground": "#36f9f6" + } + }, + { + "name": "Entity", + "scope": "entity.name", + "settings": { + "foreground": "#fe4450" + } + }, + { + "name": "HTML or XML tag", + "scope": "entity.name.tag", + "settings": { + "foreground": "#72f1b8" + } + }, + { + "name": "HTML or XML tag brackets", + "scope": ["punctuation.definition.tag"], + "settings": { + "foreground": "#36f9f6" + } + }, + { + "name": "Tag attribute", + "scope": "entity.other.attribute-name", + "settings": { + "foreground": "#fede5d" + } + }, + { + "name": "Tag attribute HTML", + "scope": "entity.other.attribute-name.html", + "settings": { + "foreground": "#fede5d", + "fontStyle": "italic" + } + }, + { + "name": "Class", + "scope": ["entity.name.type", "meta.attribute.class.html"], + "settings": { + "foreground": "#fe4450" + } + }, + { + "name": "Inherited class", + "scope": "entity.other.inherited-class", + "settings": { + "foreground": "#D50" + } + }, + { + "name": "Function", + "scope": ["entity.name.function", "variable.function"], + "settings": { + "foreground": "#36f9f6" + } + }, + { + "name": "JS Export", + "scope": ["keyword.control.export.js", "keyword.control.import.js"], + "settings": { + "foreground": "#72f1b8" + } + }, + { + "name": "JS Numerics", + "scope": ["constant.numeric.decimal.js"], + "settings": { + "foreground": "#2EE2FA" + } + }, + { + "name": "Keyword", + "scope": "keyword", + "settings": { + "foreground": "#fede5d" + } + }, + { + "name": "Control keyword", + "scope": "keyword.control", + "settings": { + "foreground": "#fede5d" + } + }, + { + "name": "Operator", + "scope": "keyword.operator", + "settings": { + "foreground": "#fede5d" + } + }, + { + "name": "Special operator", + "scope": [ + "keyword.operator.new", + "keyword.operator.expression", + "keyword.operator.logical" + ], + "settings": { + "foreground": "#fede5d" + } + }, + { + "name": "Unit", + "scope": "keyword.other.unit", + "settings": { + "foreground": "#f97e72" + } + }, + { + "name": "Support", + "scope": "support", + "settings": { + "foreground": "#fe4450" + } + }, + { + "name": "Support function", + "scope": "support.function", + "settings": { + "foreground": "#36f9f6" + } + }, + { + "name": "Support variable", + "scope": "support.variable", + "settings": { + "foreground": "#ff7edb" + } + }, + { + "name": "Object literal key / property", + "scope": ["meta.object-literal.key", "support.type.property-name"], + "settings": { + "foreground": "#ff7edb" + } + }, + { + "name": "Key-value separator", + "scope": "punctuation.separator.key-value", + "settings": { + "foreground": "#b6b1b1" + } + }, + { + "name": "Embedded punctuation", + "scope": "punctuation.section.embedded", + "settings": { + "foreground": "#fede5d" + } + }, + { + "name": "Template expression", + "scope": [ + "punctuation.definition.template-expression.begin", + "punctuation.definition.template-expression.end" + ], + "settings": { + "foreground": "#72f1b8" + } + }, + { + "name": "CSS property", + "scope": [ + "support.type.property-name.css", + "support.type.property-name.json" + ], + "settings": { + "foreground": "#72f1b8" + } + }, + { + "name": "JS Switch control", + "scope": "switch-block.expr.js", + "settings": { + "foreground": "#72f1b8" + } + }, + { + "name": "JS object path", + "scope": "variable.other.constant.property.js, variable.other.property.js", + "settings": { + "foreground": "#2ee2fa" + } + }, + { + "name": "Color", + "scope": "constant.other.color", + "settings": { + "foreground": "#f97e72" + } + }, + { + "name": "Font names", + "scope": "support.constant.font-name", + "settings": { + "foreground": "#f97e72" + } + }, + { + "name": "CSS #id", + "scope": "entity.other.attribute-name.id", + "settings": { + "foreground": "#36f9f6" + } + }, + { + "name": "Pseudo CSS", + "scope": [ + "entity.other.attribute-name.pseudo-element", + "entity.other.attribute-name.pseudo-class" + ], + "settings": { + "foreground": "#D50" + } + }, + { + "name": "CSS support functions (rgb)", + "scope": "support.function.misc.css", + "settings": { + "foreground": "#fe4450" + } + }, + { + "name": "Markup heading", + "scope": ["markup.heading", "entity.name.section"], + "settings": { + "foreground": "#ff7edb" + } + }, + { + "name": "Markup text", + "scope": ["text.html", "keyword.operator.assignment"], + "settings": { + "foreground": "#ffffffee" + } + }, + { + "name": "Markup quote", + "scope": "markup.quote", + "settings": { + "foreground": "#b6b1b1cc", + "fontStyle": "italic" + } + }, + { + "name": "Markup list", + "scope": "beginning.punctuation.definition.list", + "settings": { + "foreground": "#ff7edb" + } + }, + { + "name": "Markup link", + "scope": "markup.underline.link", + "settings": { + "foreground": "#D50" + } + }, + { + "name": "Markup link description", + "scope": "string.other.link.description", + "settings": { + "foreground": "#f97e72" + } + }, + { + "name": "Python function call", + "scope": "meta.function-call.generic.python", + "settings": { + "foreground": "#36f9f6" + } + }, + { + "name": "Python variable params", + "scope": "variable.parameter.function-call.python", + "settings": { + "foreground": "#72f1b8" + } + }, + { + "name": "C# storage type", + "scope": "storage.type.cs", + "settings": { + "foreground": "#fe4450" + } + }, + { + "name": "C# local variable", + "scope": "entity.name.variable.local.cs", + "settings": { + "foreground": "#ff7edb" + } + }, + { + "name": "C# properties and fields", + "scope": [ + "entity.name.variable.field.cs", + "entity.name.variable.property.cs" + ], + "settings": { + "foreground": "#ff7edb" + } + }, + { + "name": "C placeholder", + "scope": "constant.other.placeholder.c", + "settings": { + "foreground": "#72f1b8", + "fontStyle": "italic" + } + }, + { + "name": "C preprocessors", + "scope": [ + "keyword.control.directive.include.c", + "keyword.control.directive.define.c" + ], + "settings": { + "foreground": "#72f1b8" + } + }, + { + "name": "C storage modifier", + "scope": "storage.modifier.c", + "settings": { + "foreground": "#fe4450" + } + }, + { + "name": "C++ operators", + "scope": "source.cpp keyword.operator", + "settings": { + "foreground": "#fede5d" + } + }, + { + "name": "C++ placeholder", + "scope": "constant.other.placeholder.cpp", + "settings": { + "foreground": "#72f1b8", + "fontStyle": "italic" + } + }, + { + "name": "C++ include", + "scope": [ + "keyword.control.directive.include.cpp", + "keyword.control.directive.define.cpp" + ], + "settings": { + "foreground": "#72f1b8" + } + }, + { + "name": "C++ constant modifier", + "scope": "storage.modifier.specifier.const.cpp", + "settings": { + "foreground": "#fe4450" + } + }, + { + "name": "Elixir Classes", + "scope": [ + "source.elixir support.type.elixir", + "source.elixir meta.module.elixir entity.name.class.elixir" + ], + "settings": { + "foreground": "#36f9f6" + } + }, + { + "name": "Elixir Functions", + "scope": "source.elixir entity.name.function", + "settings": { + "foreground": "#72f1b8" + } + }, + { + "name": "Elixir Constants", + "scope": [ + "source.elixir constant.other.symbol.elixir", + "source.elixir constant.other.keywords.elixir" + ], + "settings": { + "foreground": "#36f9f6" + } + }, + { + "name": "Elixir String Punctuation", + "scope": "source.elixir punctuation.definition.string", + "settings": { + "foreground": "#72f1b8" + } + }, + { + "name": "Elixir", + "scope": [ + "source.elixir variable.other.readwrite.module.elixir", + "source.elixir variable.other.readwrite.module.elixir punctuation.definition.variable.elixir" + ], + "settings": { + "foreground": "#72f1b8" + } + }, + { + "name": "Elixir Binary Punctuation", + "scope": "source.elixir .punctuation.binary.elixir", + "settings": { + "foreground": "#ff7edb", + "fontStyle": "italic" + } + }, + { + "name": "Clojure Globals", + "scope": ["entity.global.clojure"], + "settings": { + "foreground": "#36f9f6", + "fontStyle": "bold" + } + }, + { + "name": "Clojure Storage", + "scope": ["storage.control.clojure"], + "settings": { + "foreground": "#36f9f6", + "fontStyle": "italic" + } + }, + { + "name": "Clojure Metadata", + "scope": ["meta.metadata.simple.clojure", "meta.metadata.map.clojure"], + "settings": { + "foreground": "#fe4450", + "fontStyle": "italic" + } + }, + { + "name": "Clojure Macros, Quoted", + "scope": ["meta.quoted-expression.clojure"], + "settings": { + "fontStyle": "italic" + } + }, + { + "name": "Clojure Symbols", + "scope": ["meta.symbol.clojure"], + "settings": { + "foreground": "#ff7edbff" + } + }, + { + "name": "Go basic", + "scope": "source.go", + "settings": { + "foreground": "#ff7edbff" + } + }, + { + "name": "Go Function Calls", + "scope": "source.go meta.function-call.go", + "settings": { + "foreground": "#36f9f6" + } + }, + { + "name": "Go Keywords", + "scope": [ + "source.go keyword.package.go", + "source.go keyword.import.go", + "source.go keyword.function.go", + "source.go keyword.type.go", + "source.go keyword.const.go", + "source.go keyword.var.go", + "source.go keyword.map.go", + "source.go keyword.channel.go", + "source.go keyword.control.go" + ], + "settings": { + "foreground": "#fede5d" + } + }, + { + "name": "Go interfaces", + "scope": [ + "source.go storage.type", + "source.go keyword.struct.go", + "source.go keyword.interface.go" + ], + "settings": { + "foreground": "#72f1b8" + } + }, + { + "name": "Go Constants e.g. nil, string format (%s, %d, etc.)", + "scope": [ + "source.go constant.language.go", + "source.go constant.other.placeholder.go", + "source.go variable" + ], + "settings": { + "foreground": "#2EE2FA" + } + }, + { + "name": "Markdown links and image paths", + "scope": [ + "markup.underline.link.markdown", + "markup.inline.raw.string.markdown" + ], + "settings": { + "foreground": "#72f1b8", + "fontStyle": "italic" + } + }, + { + "name": "Markdown links and image paths", + "scope": ["string.other.link.title.markdown"], + "settings": { + "foreground": "#fede5d" + } + }, + { + "name": "Markdown headings", + "scope": ["markup.heading.markdown", "entity.name.section.markdown"], + "settings": { + "foreground": "#ff7edb", + "fontStyle": "bold" + } + }, + { + "name": "Markdown italic", + "scope": ["markup.italic.markdown"], + "settings": { + "foreground": "#2EE2FA", + "fontStyle": "italic" + } + }, + { + "name": "Markdown bold", + "scope": ["markup.bold.markdown"], + "settings": { + "foreground": "#2EE2FA", + "fontStyle": "bold" + } + }, + { + "name": "Markdown quotes", + "scope": [ + "punctuation.definition.quote.begin.markdown", + "markup.quote.markdown" + ], + "settings": { + "foreground": "#72f1b8" + } + }, + { + "name": "Basic source colours", + "scope": ["source.dart", "source.python", "source.scala"], + "settings": { + "foreground": "#ff7edbff" + } + }, + { + "name": "Dart strings", + "scope": ["string.interpolated.single.dart"], + "settings": { + "foreground": "#f97e72" + } + }, + { + "name": "Dart variable params", + "scope": ["variable.parameter.dart"], + "settings": { + "foreground": "#72f1b8" + } + }, + { + "name": "Dart numerics", + "scope": ["constant.numeric.dart"], + "settings": { + "foreground": "#2EE2FA" + } + }, + { + "name": "Scala variable params", + "scope": ["variable.parameter.scala"], + "settings": { + "foreground": "#2EE2FA" + } + }, + { + "name": "Scala", + "scope": ["meta.template.expression.scala"], + "settings": { + "foreground": "#72f1b8" + } + } + ] } diff --git a/crates/editor/src/editor_settings.rs b/crates/editor/src/editor_settings.rs index 75f8b800f9..b885e065a1 100644 --- a/crates/editor/src/editor_settings.rs +++ b/crates/editor/src/editor_settings.rs @@ -2,7 +2,7 @@ use schemars::JsonSchema; use serde::{Deserialize, Serialize}; use settings::Setting; -#[derive(Deserialize)] +#[derive(Clone, Deserialize)] pub struct EditorSettings { pub cursor_blink: bool, pub hover_popover_enabled: bool, @@ -11,6 +11,15 @@ pub struct EditorSettings { pub use_on_type_format: bool, pub scrollbar: Scrollbar, pub relative_line_numbers: bool, + pub seed_search_query_from_cursor: SeedQuerySetting, +} + +#[derive(Copy, Clone, Debug, Serialize, Deserialize, PartialEq, Eq, JsonSchema)] +#[serde(rename_all = "snake_case")] +pub enum SeedQuerySetting { + Always, + Selection, + Never, } #[derive(Copy, Clone, Debug, Serialize, Deserialize, JsonSchema, PartialEq, Eq)] @@ -38,6 +47,7 @@ pub struct EditorSettingsContent { pub use_on_type_format: Option, pub scrollbar: Option, pub relative_line_numbers: Option, + pub seed_search_query_from_cursor: Option, } #[derive(Copy, Clone, Debug, Serialize, Deserialize, JsonSchema, PartialEq, Eq)] diff --git a/crates/editor/src/items.rs b/crates/editor/src/items.rs index 1b922848e0..4c45904c50 100644 --- a/crates/editor/src/items.rs +++ b/crates/editor/src/items.rs @@ -1,7 +1,7 @@ use crate::{ - display_map::ToDisplayPoint, link_go_to_definition::hide_link_definition, - movement::surrounding_word, persistence::DB, scroll::ScrollAnchor, Anchor, Autoscroll, Editor, - Event, ExcerptId, ExcerptRange, MultiBuffer, MultiBufferSnapshot, NavigationData, ToPoint as _, + editor_settings::SeedQuerySetting, link_go_to_definition::hide_link_definition, + persistence::DB, scroll::ScrollAnchor, Anchor, Autoscroll, Editor, EditorSettings, Event, + ExcerptId, ExcerptRange, MultiBuffer, MultiBufferSnapshot, NavigationData, ToPoint as _, }; use anyhow::{Context, Result}; use collections::HashSet; @@ -13,8 +13,8 @@ use gpui::{ ViewHandle, WeakViewHandle, }; use language::{ - proto::serialize_anchor as serialize_text_anchor, Bias, Buffer, OffsetRangeExt, Point, - SelectionGoal, + proto::serialize_anchor as serialize_text_anchor, Bias, Buffer, CharKind, OffsetRangeExt, + Point, SelectionGoal, }; use project::{search::SearchQuery, FormatTrigger, Item as _, Project, ProjectPath}; use rpc::proto::{self, update_view, PeerId}; @@ -937,24 +937,28 @@ impl SearchableItem for Editor { } fn query_suggestion(&mut self, cx: &mut ViewContext) -> String { - let display_map = self.snapshot(cx).display_snapshot; + let setting = settings::get::(cx).seed_search_query_from_cursor; + let snapshot = &self.snapshot(cx).buffer_snapshot; let selection = self.selections.newest::(cx); - if selection.start == selection.end { - let point = selection.start.to_display_point(&display_map); - let range = surrounding_word(&display_map, point); - let range = range.start.to_offset(&display_map, Bias::Left) - ..range.end.to_offset(&display_map, Bias::Right); - let text: String = display_map.buffer_snapshot.text_for_range(range).collect(); - if text.trim().is_empty() { - String::new() - } else { - text + + match setting { + SeedQuerySetting::Never => String::new(), + SeedQuerySetting::Selection | SeedQuerySetting::Always if !selection.is_empty() => { + snapshot + .text_for_range(selection.start..selection.end) + .collect() + } + SeedQuerySetting::Selection => String::new(), + SeedQuerySetting::Always => { + let (range, kind) = snapshot.surrounding_word(selection.start); + if kind == Some(CharKind::Word) { + let text: String = snapshot.text_for_range(range).collect(); + if !text.trim().is_empty() { + return text; + } + } + String::new() } - } else { - display_map - .buffer_snapshot - .text_for_range(selection.start..selection.end) - .collect() } } diff --git a/crates/editor2/src/editor_settings.rs b/crates/editor2/src/editor_settings.rs index 45c797598f..fd7e2feea3 100644 --- a/crates/editor2/src/editor_settings.rs +++ b/crates/editor2/src/editor_settings.rs @@ -11,6 +11,15 @@ pub struct EditorSettings { pub use_on_type_format: bool, pub scrollbar: Scrollbar, pub relative_line_numbers: bool, + pub seed_search_query_from_cursor: SeedQuerySetting, +} + +#[derive(Copy, Clone, Debug, Serialize, Deserialize, PartialEq, Eq, JsonSchema)] +#[serde(rename_all = "snake_case")] +pub enum SeedQuerySetting { + Always, + Selection, + Never, } #[derive(Copy, Clone, Debug, Serialize, Deserialize, JsonSchema, PartialEq, Eq)] @@ -38,6 +47,7 @@ pub struct EditorSettingsContent { pub use_on_type_format: Option, pub scrollbar: Option, pub relative_line_numbers: Option, + pub seed_search_query_from_cursor: Option, } #[derive(Copy, Clone, Debug, Serialize, Deserialize, JsonSchema, PartialEq, Eq)] diff --git a/crates/editor2/src/items.rs b/crates/editor2/src/items.rs index 1081a329c6..25e9f91608 100644 --- a/crates/editor2/src/items.rs +++ b/crates/editor2/src/items.rs @@ -1,7 +1,8 @@ use crate::{ - display_map::ToDisplayPoint, link_go_to_definition::hide_link_definition, + editor_settings::SeedQuerySetting, link_go_to_definition::hide_link_definition, movement::surrounding_word, persistence::DB, scroll::ScrollAnchor, Anchor, Autoscroll, Editor, - Event, ExcerptId, ExcerptRange, MultiBuffer, MultiBufferSnapshot, NavigationData, ToPoint as _, + EditorSettings, Event, ExcerptId, ExcerptRange, MultiBuffer, MultiBufferSnapshot, + NavigationData, ToPoint as _, }; use anyhow::{anyhow, Context, Result}; use collections::HashSet; @@ -12,11 +13,12 @@ use gpui::{ ViewContext, VisualContext, WeakView, }; use language::{ - proto::serialize_anchor as serialize_text_anchor, Bias, Buffer, OffsetRangeExt, Point, - SelectionGoal, + proto::serialize_anchor as serialize_text_anchor, Bias, Buffer, CharKind, OffsetRangeExt, + Point, SelectionGoal, }; use project::{search::SearchQuery, FormatTrigger, Item as _, Project, ProjectPath}; use rpc::proto::{self, update_view, PeerId}; +use settings::Settings; use smallvec::SmallVec; use std::{ borrow::Cow, @@ -918,24 +920,28 @@ impl SearchableItem for Editor { } fn query_suggestion(&mut self, cx: &mut ViewContext) -> String { - let display_map = self.snapshot(cx).display_snapshot; + let setting = EditorSettings::get_global(cx).seed_search_query_from_cursor; + let snapshot = &self.snapshot(cx).buffer_snapshot; let selection = self.selections.newest::(cx); - if selection.start == selection.end { - let point = selection.start.to_display_point(&display_map); - let range = surrounding_word(&display_map, point); - let range = range.start.to_offset(&display_map, Bias::Left) - ..range.end.to_offset(&display_map, Bias::Right); - let text: String = display_map.buffer_snapshot.text_for_range(range).collect(); - if text.trim().is_empty() { - String::new() - } else { - text + + match setting { + SeedQuerySetting::Never => String::new(), + SeedQuerySetting::Selection | SeedQuerySetting::Always if !selection.is_empty() => { + snapshot + .text_for_range(selection.start..selection.end) + .collect() + } + SeedQuerySetting::Selection => String::new(), + SeedQuerySetting::Always => { + let (range, kind) = snapshot.surrounding_word(selection.start); + if kind == Some(CharKind::Word) { + let text: String = snapshot.text_for_range(range).collect(); + if !text.trim().is_empty() { + return text; + } + } + String::new() } - } else { - display_map - .buffer_snapshot - .text_for_range(selection.start..selection.end) - .collect() } } diff --git a/crates/go_to_line2/src/go_to_line.rs b/crates/go_to_line2/src/go_to_line.rs index ca68a9ae79..cc41f63718 100644 --- a/crates/go_to_line2/src/go_to_line.rs +++ b/crates/go_to_line2/src/go_to_line.rs @@ -39,12 +39,6 @@ pub struct GoToLine { _subscriptions: Vec, } -pub enum Event { - Dismissed, -} - -impl EventEmitter for GoToLine {} - impl EventEmitter for GoToLine {} impl Modal for GoToLine { fn focus(&self, cx: &mut WindowContext) { @@ -81,7 +75,6 @@ impl GoToLine { fn release(&mut self, cx: &mut WindowContext) { let scroll_position = self.prev_scroll_position.take(); self.active_editor.update(cx, |editor, cx| { - editor.focus(cx); editor.highlight_rows(None); if let Some(scroll_position) = scroll_position { editor.set_scroll_position(scroll_position, cx); @@ -98,7 +91,7 @@ impl GoToLine { ) { match event { // todo!() this isn't working... - editor::Event::Blurred => cx.emit(Event::Dismissed), + editor::Event::Blurred => cx.emit(ModalEvent::Dismissed), editor::Event::BufferEdited { .. } => self.highlight_current_line(cx), _ => {} } @@ -133,22 +126,28 @@ impl GoToLine { } fn cancel(&mut self, _: &menu::Cancel, cx: &mut ViewContext) { - cx.emit(Event::Dismissed); + self.active_editor.update(cx, |editor, cx| { + editor.focus(cx); + cx.notify(); + }); + cx.emit(ModalEvent::Dismissed); } fn confirm(&mut self, _: &menu::Confirm, cx: &mut ViewContext) { if let Some(point) = self.point_from_query(cx) { - self.active_editor.update(cx, |active_editor, cx| { - let snapshot = active_editor.snapshot(cx).display_snapshot; + self.active_editor.update(cx, |editor, cx| { + let snapshot = editor.snapshot(cx).display_snapshot; let point = snapshot.buffer_snapshot.clip_point(point, Bias::Left); - active_editor.change_selections(Some(Autoscroll::center()), cx, |s| { + editor.change_selections(Some(Autoscroll::center()), cx, |s| { s.select_ranges([point..point]) }); + editor.focus(cx); + cx.notify(); }); self.prev_scroll_position.take(); } - cx.emit(Event::Dismissed); + cx.emit(ModalEvent::Dismissed); } } diff --git a/crates/gpui/src/geometry.rs b/crates/gpui/src/geometry.rs index 40b0682787..fe197af5d2 100644 --- a/crates/gpui/src/geometry.rs +++ b/crates/gpui/src/geometry.rs @@ -136,7 +136,7 @@ impl ToJson for RectF { } #[derive(Refineable, Debug)] -#[refineable(debug)] +#[refineable(Debug)] pub struct Point { pub x: T, pub y: T, @@ -161,7 +161,7 @@ impl Into> for Point { } #[derive(Refineable, Clone, Debug)] -#[refineable(debug)] +#[refineable(Debug)] pub struct Size { pub width: T, pub height: T, @@ -227,7 +227,7 @@ impl Size { } #[derive(Clone, Default, Refineable, Debug)] -#[refineable(debug)] +#[refineable(Debug)] pub struct Edges { pub top: T, pub right: T, diff --git a/crates/gpui2/src/color.rs b/crates/gpui2/src/color.rs index 3ae247962b..6fcb12e178 100644 --- a/crates/gpui2/src/color.rs +++ b/crates/gpui2/src/color.rs @@ -1,8 +1,8 @@ #![allow(dead_code)] +use anyhow::bail; use serde::de::{self, Deserialize, Deserializer, Visitor}; use std::fmt; -use std::num::ParseIntError; pub fn rgb>(hex: u32) -> C { let r = ((hex >> 16) & 0xFF) as f32 / 255.0; @@ -19,7 +19,7 @@ pub fn rgba(hex: u32) -> Rgba { Rgba { r, g, b, a } } -#[derive(Clone, Copy, Default)] +#[derive(PartialEq, Clone, Copy, Default)] pub struct Rgba { pub r: f32, pub g: f32, @@ -70,21 +70,7 @@ impl<'de> Visitor<'de> for RgbaVisitor { } fn visit_str(self, value: &str) -> Result { - if value.len() == 7 || value.len() == 9 { - let r = u8::from_str_radix(&value[1..3], 16).unwrap() as f32 / 255.0; - let g = u8::from_str_radix(&value[3..5], 16).unwrap() as f32 / 255.0; - let b = u8::from_str_radix(&value[5..7], 16).unwrap() as f32 / 255.0; - let a = if value.len() == 9 { - u8::from_str_radix(&value[7..9], 16).unwrap() as f32 / 255.0 - } else { - 1.0 - }; - Ok(Rgba { r, g, b, a }) - } else { - Err(E::custom( - "Bad format for RGBA. Expected #rrggbb or #rrggbbaa.", - )) - } + Rgba::try_from(value).map_err(E::custom) } } @@ -125,19 +111,59 @@ impl From for Rgba { } impl TryFrom<&'_ str> for Rgba { - type Error = ParseIntError; + type Error = anyhow::Error; fn try_from(value: &'_ str) -> Result { - let r = u8::from_str_radix(&value[1..3], 16)? as f32 / 255.0; - let g = u8::from_str_radix(&value[3..5], 16)? as f32 / 255.0; - let b = u8::from_str_radix(&value[5..7], 16)? as f32 / 255.0; - let a = if value.len() > 7 { - u8::from_str_radix(&value[7..9], 16)? as f32 / 255.0 - } else { - 1.0 + const RGB: usize = "rgb".len(); + const RGBA: usize = "rgba".len(); + const RRGGBB: usize = "rrggbb".len(); + const RRGGBBAA: usize = "rrggbbaa".len(); + + const EXPECTED_FORMATS: &'static str = "Expected #rgb, #rgba, #rrggbb, or #rrggbbaa"; + + let Some(("", hex)) = value.trim().split_once('#') else { + bail!("invalid RGBA hex color: '{value}'. {EXPECTED_FORMATS}"); }; - Ok(Rgba { r, g, b, a }) + let (r, g, b, a) = match hex.len() { + RGB | RGBA => { + let r = u8::from_str_radix(&hex[0..1], 16)?; + let g = u8::from_str_radix(&hex[1..2], 16)?; + let b = u8::from_str_radix(&hex[2..3], 16)?; + let a = if hex.len() == RGBA { + u8::from_str_radix(&hex[3..4], 16)? + } else { + 0xf + }; + + /// Duplicates a given hex digit. + /// E.g., `0xf` -> `0xff`. + const fn duplicate(value: u8) -> u8 { + value << 4 | value + } + + (duplicate(r), duplicate(g), duplicate(b), duplicate(a)) + } + RRGGBB | RRGGBBAA => { + let r = u8::from_str_radix(&hex[0..2], 16)?; + let g = u8::from_str_radix(&hex[2..4], 16)?; + let b = u8::from_str_radix(&hex[4..6], 16)?; + let a = if hex.len() == RRGGBBAA { + u8::from_str_radix(&hex[6..8], 16)? + } else { + 0xff + }; + (r, g, b, a) + } + _ => bail!("invalid RGBA hex color: '{value}'. {EXPECTED_FORMATS}"), + }; + + Ok(Rgba { + r: r as f32 / 255., + g: g as f32 / 255., + b: b as f32 / 255., + a: a as f32 / 255., + }) } } @@ -311,3 +337,52 @@ impl<'de> Deserialize<'de> for Hsla { Ok(Hsla::from(rgba)) } } + +#[cfg(test)] +mod tests { + use serde_json::json; + + use super::*; + + #[test] + fn test_deserialize_three_value_hex_to_rgba() { + let actual: Rgba = serde_json::from_value(json!("#f09")).unwrap(); + + assert_eq!(actual, rgba(0xff0099ff)) + } + + #[test] + fn test_deserialize_four_value_hex_to_rgba() { + let actual: Rgba = serde_json::from_value(json!("#f09f")).unwrap(); + + assert_eq!(actual, rgba(0xff0099ff)) + } + + #[test] + fn test_deserialize_six_value_hex_to_rgba() { + let actual: Rgba = serde_json::from_value(json!("#ff0099")).unwrap(); + + assert_eq!(actual, rgba(0xff0099ff)) + } + + #[test] + fn test_deserialize_eight_value_hex_to_rgba() { + let actual: Rgba = serde_json::from_value(json!("#ff0099ff")).unwrap(); + + assert_eq!(actual, rgba(0xff0099ff)) + } + + #[test] + fn test_deserialize_eight_value_hex_with_padding_to_rgba() { + let actual: Rgba = serde_json::from_value(json!(" #f5f5f5ff ")).unwrap(); + + assert_eq!(actual, rgba(0xf5f5f5ff)) + } + + #[test] + fn test_deserialize_eight_value_hex_with_mixed_case_to_rgba() { + let actual: Rgba = serde_json::from_value(json!("#DeAdbEeF")).unwrap(); + + assert_eq!(actual, rgba(0xdeadbeef)) + } +} diff --git a/crates/gpui2/src/geometry.rs b/crates/gpui2/src/geometry.rs index c5209239ae..f290c6a81c 100644 --- a/crates/gpui2/src/geometry.rs +++ b/crates/gpui2/src/geometry.rs @@ -9,7 +9,7 @@ use std::{ }; #[derive(Refineable, Default, Add, AddAssign, Sub, SubAssign, Copy, Debug, PartialEq, Eq, Hash)] -#[refineable(debug)] +#[refineable(Debug)] #[repr(C)] pub struct Point { pub x: T, @@ -140,7 +140,7 @@ impl Clone for Point { } #[derive(Refineable, Default, Clone, Copy, PartialEq, Div, Hash, Serialize, Deserialize)] -#[refineable(debug)] +#[refineable(Debug)] #[repr(C)] pub struct Size { pub width: T, @@ -313,7 +313,7 @@ impl Size { } #[derive(Refineable, Clone, Default, Debug, Eq, PartialEq)] -#[refineable(debug)] +#[refineable(Debug)] #[repr(C)] pub struct Bounds { pub origin: Point, @@ -477,7 +477,7 @@ impl Bounds { impl Copy for Bounds {} #[derive(Refineable, Clone, Default, Debug, Eq, PartialEq)] -#[refineable(debug)] +#[refineable(Debug)] #[repr(C)] pub struct Edges { pub top: T, @@ -619,7 +619,7 @@ impl Edges { } #[derive(Refineable, Clone, Default, Debug, Eq, PartialEq)] -#[refineable(debug)] +#[refineable(Debug)] #[repr(C)] pub struct Corners { pub top_left: T, diff --git a/crates/gpui2/src/style.rs b/crates/gpui2/src/style.rs index 6d3b31c1f7..664cc61f8a 100644 --- a/crates/gpui2/src/style.rs +++ b/crates/gpui2/src/style.rs @@ -14,7 +14,7 @@ pub use taffy::style::{ pub type StyleCascade = Cascade