Change:
In user research Command Center () we found that the Command Palette on first opening is overwhelming, which might keep users from finding its value. One core problem is that it is sorted A-Z, the top-most commands mostly not making sense in an environment that might not even have a file open: <img width="300" alt="image" src="https://user-"One idea would be to curate ~5 commonly used commands that have high usage (format) and make make sense in a workspace-less state (split editor, toggle sidebars). It would be only shown when the user doesn't have past command history (which will then show the recently used). cc
fyi
I think that makes sense, similar to the settings editor: <img width="629" alt="image" src="https://user-"I am just not sure how to present this, should it be another group below the recently used commands? And how do we pick the commands to add there, based on usage numbers? //cc as component owner
How about renaming "recently used" to "commonly used" and always mix in certain default commands until enough true recently used commands push them out?
and I were thinking: last command at the top list of pinned commands (that default to some list we come up with) rest of recently used other commands It might be a bit busy, but it does: still keep the command you spam at the top but makes the pinned commands reachable from the keyboard Ultimately it's one of those "I'd like to see it before I make a decisions"
Here's what a relatively basic version of this could look like: "commonly used" section initially shows at the top for new installs After commands have been run, "recently used" pushes "commonly used" down Users can remove commonly used command individually, eventually removing the section https://user- I'm interested in the idea of mixing in default items to "recently used" as a way to cut down the number of sections. However neither title really captures what the section is in that case. It would be strange to open the command palette for the first time and see "recently used" commands. It would also feel weird to have run a bunch of commands and see them under "commonly used".
+1 for the idea of renaming "recently used" to "commonly used" and simply seeding that list with some defaults based on telemetry so that first time users get this. We could also think about filling the set up with the commonly used ones even for those users that only have a few commands that they had invoked. In other words, I would not introduce a third group for this.
We can't use the term quick access but it reminds me of this feature in Windows File Explorer. You get a default set of pinned folders and you can unpin and add more. <img width="185" alt="image" src="https://user-"
Love where the discussion went. Curating one list that is slowly being replaces by what users actually use helps new users but also keeps guiding users for a bit longer. Also less mental load for the user from one list vs another. I will take a shot at the curated list based on most used, most likely to add value for new users, and most likely to work on all workspaces.
For our initial attempt at implementing this, we will rename to (or something else) and follow this pattern: For a new user They will see 5 pre-seeded items underneath , these items will have a certain to them and will be 5 commands we recommend for new users. When they run a command, that command will show at the very top, under the section, but above the 5 pre-seeded commands... it now has a , or , of . If it's run again, that number bumps to , etc. Eventually The first 5 items in the section will be the last 5 run commands. This is to not mess with muscle memory, and allow folks an easy way to re-run the last command or last few commands they just ran. The next 5 items will be the top 5 unique commands by /. These may include pre-seeded ones or ones that that user just runs a lot. The next X items will be the rest of the commands as it works today. This is to allow searching for a command to still be sorted by recently used. Then the section remains as is. will be getting me a nice list of pre-seeded commands based on our telemetry and other things. Interesting details Since commands showing up in the command palette is context driven (you can't if you don't have a repo open) we should handle the case for when there isn't a resolvable top 5. This would happen if the pre-seeded commands are run recently and are showing in the first 5 recently run section... the next 5, which should be the next unique top 5 commands by / might not have anything to pull from... or the next highest frequency is like... 0 or 1. In this case, we can just only as many as we have.
I have playing around with this proposal, and frankly, I don't like it. It might be helpful for new users to see the 5 recommended commands, but for experienced users, it makes no difference and it doesn't feel any different than the current solution... so it's more complication and more work for no value. So I have a different proposal. For new users, they will see a new section called : ! This is a list that we come up with based on telemetry. As they start to run commands, recently used slowly pushes that list down below the fold and if a command inside of it is run, it will jump up to the recently used section: ! Eventually, an experienced user will either: no longer see the list have run all the commands in the list causing them to go up to ! This behavior is to help new users become experienced users. But experienced users should have some benefit of this work, which is why I propose that New Windows swap the list and the list: ! As the screenshot says, after the first command is run in a window, the and swap going back to the normal experience above. This proposal, I feel, enables new users to learn the ropes of the command palette while also making the Command Palette a useful launching pad for new windows. Thoughts?
I think I partially get it and like the things I get: first time users: get to see commonly used commands existing users: will not see commonly used commands unless there is a commonly used command they have not run yet recently used commands are always on top of commonly used commands (for muscle memory) The part I do not get is the swapping thing? I am worried that changing the order of "commonly used" and "recently used" will break muscle memory. Think about users that blindly accept the first command from the picker.
yeah the swapping thing is a little tricky. My motivation for doing it is to ensure that that last command you ran is on top. Once the user runs any command, we expect that command to be on top. However, without the swapping idea, if in new windows we show commonly used at the top always, then the recently run command will be below it.
The list of recently run commands is global state though, so why would the new window show anything different?
The thought was that a new window (ex. one without a workspace), the command palette could be used as a launcher in the same idea that the welcome view of the explorer is: ! or the Remote Indicator is: !
The launcher idea came out of standup. I thought it was interesting... esp since a new window doesn't have anything open, and the first text you see is "Show All Commands": !
This sounds to me like it could confuse users quickly as to why sometimes "recently used" is there and sometimes "commonly used". I do not think that users (even experienced ones) could make the connection to the fact that its only for new (empty?) windows.
Perhaps the Command Center could be the difference instead of the "New Window" idea. Command Center always shows "commonly used" on top since it's mostly mouse driven. Command Palette always shows "recently used" on top for consistency
To make the "commonly used" a little bit smarter, we were wanting the list to be updated over time based on the commands that the user actually used. So in the Command Center, that "commonly used" section that showed at the top would show the top 5 commands that the user uses, rather than 5 hard coded suggestions.
So I played around with the Command Freqency idea and ultimately, I don't think it provides a ton of value. My top 5 commands were like: Reload Window GitHub Copy Permalink Show Running Extensions Configure Display Language I might be a bit bias because I work on VS Code but idk to me these aren't so useful and frankly I'm not about to open the Command Center, click "Show and Run Commands", then click on one of my top 5. That's too many clicks. To simplify this change, and put focus on the users we are focusing on in this issue, new users, I have simplified the proposal above to everything but the "New Window/Command Center" proposal. In other words: We show a suggested list initially and over time that list either: gets buried underneath all of the "recently opened" items that the user actually uses gets replaced by the item going into "recently opened" This is implemented in
Perhaps one day, we allow users to pin commands () and have that experience be tied to the Command Center.
to clarify, even for existing users, we now always show "commonly used" commands section in commands quick access? And if so, is that section below or above "recently used"?
yes correct. And it is always below recently used

Discussion:
readonly trustedExtensionUrlPublicKeys?: { [id: string]: string[] }; readonly trustedExtensionAuthAccess?: readonly string[]; <ins> readonly commandPaletteSuggestedCommandIds?: string[]; </ins> readonly crashReporter?: { readonly companyName: string; readonly productName: string;

export interface ICommandsQuickAccessOptions extends IPickerQuickAccessProviderOptions<ICommandQuickPick> { showAlias: boolean; <ins> suggestedCommandIds?: Set<string>; </ins> } export abstract class AbstractCommandsQuickAccessProvider extends PickerQuickAccessProvider<ICommandQuickPick> implements IDisposable {

return 1; // other command was used so it wins over the command } <ins> if (this.options.suggestedCommandIds) { const commandASuggestion = this.options.suggestedCommandIds.has(commandPickA.commandId); const commandBSuggestion = this.options.suggestedCommandIds.has(commandPickB.commandId); if (commandASuggestion && commandBSuggestion) { return 0; // honor the order of the array } if (commandASuggestion) { return -1; // first command was suggested, so it wins over the non suggested one } if (commandBSuggestion) { return 1; // other command was suggested so it wins over the command } } </ins> // both commands were never used, so we sort by name return commandPickA.label.localeCompare(commandPickB.label); }); const commandPicks: Array<ICommandQuickPick | IQuickPickSeparator> = []; <del> let addSeparator = false; </del> <ins> let addOtherSeparator = false; let addCommonlyUsedSeparator = !!this.options.suggestedCommandIds; </ins> for (let i = 0; i < filteredCommandPicks.length; i++) { const commandPick = filteredCommandPicks[i]; const keybinding = this.keybindingService.lookupKeybinding(commandPick.commandId);

// Separator: recently used if (i === 0 && this.commandsHistory.peek(commandPick.commandId)) { commandPicks.push({ type: 'separator', label: localize('recentlyUsed', "recently used") }); <del> addSeparator = true; </del> <ins> addOtherSeparator = true; } // Separator: commonly used if (addCommonlyUsedSeparator && !this.commandsHistory.peek(commandPick.commandId) && this.options.suggestedCommandIds?.has(commandPick.commandId)) { commandPicks.push({ type: 'separator', label: localize('commonlyUsed', "commonly used") }); addOtherSeparator = true; addCommonlyUsedSeparator = false; </ins> } // Separator: other commands <del> if (i !== 0 && addSeparator && !this.commandsHistory.peek(commandPick.commandId)) { </del> <ins> if (addOtherSeparator && !this.commandsHistory.peek(commandPick.commandId) && !this.options.suggestedCommandIds?.has(commandPick.commandId)) { </ins> commandPicks.push({ type: 'separator', label: localize('morecCommands', "other commands") }); <del> addSeparator = false; // only once </del> <ins> addOtherSeparator = false; </ins> } // Command

commandPalette: { history: number; preserveInput: boolean; <ins> experimental: { suggestCommands: boolean; }; </ins> }; quickOpen: { enableExperimentalNewVersion: boolean;

'description': localize('preserveInput', "Controls whether the last typed input to the command palette should be restored when opening it the next time."), 'default': false }, <ins> 'workbench.commandPalette.experimental.suggestCommands': { 'type': 'boolean', 'description': localize('suggestCommands', "Controls whether the command palette should have a list of commonly used commands."), 'default': false }, </ins> 'workbench.quickOpen.closeOnFocusLost': { 'type': 'boolean', 'description': localize('closeOnFocusLost', "Controls whether Quick Open should close automatically once it loses focus."),

import { IPreferencesService } from 'vs/workbench/services/preferences/common/preferences'; import { stripIcons } from 'vs/base/common/iconLabels'; import { isFirefox } from 'vs/base/browser/browser'; <ins> import { IProductService } from 'vs/platform/product/common/productService'; const SUGGEST_COMMANDS_ID = 'workbench.commandPalette.experimental.suggestCommands'; </ins> export class CommandsQuickAccessProvider extends AbstractEditorCommandsQuickAccessProvider {

@IConfigurationService private readonly configurationService: IConfigurationService, @IEditorGroupsService private readonly editorGroupService: IEditorGroupsService, @IPreferencesService private readonly preferencesService: IPreferencesService, <ins> @IProductService productService: IProductService </ins> ) { <ins> const suggestCommands = configurationService.getValue<boolean>('workbench.commandPalette.experimental.suggestCommands'); const suggestedCommandIds = suggestCommands && productService.commandPaletteSuggestedCommandIds?.length ? new Set(productService.commandPaletteSuggestedCommandIds) : undefined; </ins> super({ <ins> suggestedCommandIds, </ins> showAlias: !Language.isDefaultVariant(), noResultsPick: { label: localize('noCommandResults', "No matching commands"), commandId: '' } }, instantiationService, keybindingService, commandService, telemetryService, dialogService); <ins> this._register(configurationService.onDidChangeConfiguration((e) => { if (e.affectsConfiguration(SUGGEST_COMMANDS_ID)) { const suggestCommands = configurationService.getValue<boolean>('workbench.commandPalette.experimental.suggestCommands'); const suggestedCommandIds = suggestCommands && productService.commandPaletteSuggestedCommandIds?.length ? new Set(productService.commandPaletteSuggestedCommandIds) : undefined; this.options.suggestedCommandIds = suggestedCommandIds; } })); </ins> } private get configuration() {