Change:
Including all who have commented : New SelectBox implementation: Standard native select allows navigation to an item using the first character. This can be done both on a unexpanded or expanded select. Should this behavior be implemented in the new custom SelectBox ?
yeah good catch I think it should. If the control has focus at least. Please do not assign the "candidate" label to issues. It is reserved for issues we plan to fix in a stable recovery release.
though assigning milestones is usualy a good idea, if you plan to fix this until the end of january just assign to December / January milestone.
Noted on the labeling issues (verified, candidate, milestones), sorry don't know all the workflows :-( Sorry to pepper you with a few more questions: I saw you wrote a draft test plan, would you like me to add some more specificity on keyboard support so people know exactly what to look for? If I have small tweaks/cleanup should I create an issue(s) or is using notes in a pull request sufficient? Essentially when is it appropriate Not to do an issue for work in progress? I will fix all issues posted for the December/January milestone assuming they are known in time.
yeah feel free to make tweaks to the test plan item: I also published some release notes on it here: The advantage of having an issue is that it will get verified in the endgame if it is a bug. If the thing you are changing cannot be verified or is not a bug, doing just a PR is fine.
You chose selectBoxCustom for the filename, do you prefer that I re- factor the delegate class and symbols to use custom instead of list?
no I think its fine
Fixed with:

Discussion:
import * as nls from 'vs/nls'; import { IDisposable, dispose } from 'vs/base/common/lifecycle'; import Event, { Emitter, chain } from 'vs/base/common/event'; <del> import { KeyCode } from 'vs/base/common/keyCodes'; </del> <ins> import { KeyCode, KeyCodeUtils } from 'vs/base/common/keyCodes'; </ins> import { StandardKeyboardEvent } from 'vs/base/browser/keyboardEvent'; import * as dom from 'vs/base/browser/dom'; import * as arrays from 'vs/base/common/arrays';

} })); <del> this.toDispose.push(dom.addDisposableListener(this.selectElement, dom.EventType.MOUSE_UP, (e) => { dom.EventHelper.stop(e); })); </del> this.toDispose.push(dom.addDisposableListener(this.selectElement, dom.EventType.MOUSE_DOWN, (e) => { dom.EventHelper.stop(e); })); // Intercept keyboard handling <del> this.toDispose.push(dom.addDisposableListener(this.selectElement, dom.EventType.KEY_UP, (e: KeyboardEvent) => { dom.EventHelper.stop(e); })); </del> this.toDispose.push(dom.addDisposableListener(this.selectElement, dom.EventType.KEY_DOWN, (e: KeyboardEvent) => { const event = new StandardKeyboardEvent(e); let showDropDown = false;

dom.EventHelper.stop(e); } })); <del> this.toDispose.push(dom.addDisposableListener(this.selectElement, dom.EventType.KEY_PRESS, (e: KeyboardEvent) => { dom.EventHelper.stop(e); })); </del> } public get onDidSelect(): Event<ISelectData> {

onSelectDropDownKeyDown.filter(e => e.keyCode === KeyCode.Escape).on(e => this.onEscape(e), this, this.toDispose); onSelectDropDownKeyDown.filter(e => e.keyCode === KeyCode.UpArrow).on(this.onUpArrow, this, this.toDispose); onSelectDropDownKeyDown.filter(e => e.keyCode === KeyCode.DownArrow).on(this.onDownArrow, this, this.toDispose); <ins> onSelectDropDownKeyDown.filter(e => (e.keyCode >= KeyCode.KEY_0 && e.keyCode <= KeyCode.KEY_Z) || (e.keyCode >= KeyCode.US_SEMICOLON && e.keyCode <= KeyCode.NUMPAD_DIVIDE)).on(this.onCharacter, this, this.toDispose); </ins> // SetUp list mouse controller - control navigation, disabled items, focus

} } <ins> // Mimic option first character navigation of native select private onCharacter(e: StandardKeyboardEvent): void { const ch = KeyCodeUtils.toString(e.keyCode); let optionIndex = -1; for (let i = 0; i < this.options.length - 1; i++) { optionIndex = (i + this.selected + 1) % this.options.length; if (this.options[optionIndex].charAt(0).toUpperCase() === ch) { this.select(optionIndex); this.selectList.setFocus([optionIndex]); this.selectList.reveal(this.selectList.getFocus()[0]); dom.EventHelper.stop(e); break; } } } </ins> public dispose(): void { this.toDispose = dispose(this.toDispose); }