提交 723b3348 编写于 作者: R Rob Lourens

Add literal match highlighting to NL settings search

上级 e8693114
......@@ -86,13 +86,13 @@ export interface IPreferencesEditorModel<T> {
}
export type IGroupFilter = (group: ISettingsGroup) => boolean;
export type ISettingFilter = (setting: ISetting) => IRange[];
export type ISettingMatcher = (setting: ISetting) => IRange[];
export interface ISettingsEditorModel extends IPreferencesEditorModel<ISetting> {
readonly onDidChangeGroups: Event<void>;
settingsGroups: ISettingsGroup[];
groupsTerms: string[];
filterSettings(filter: string, groupFilter: IGroupFilter, settingFilter: ISettingFilter, mostRelevantSettings?: string[]): IFilterResult;
filterSettings(filter: string, groupFilter: IGroupFilter, settingMatcher: ISettingMatcher, mostRelevantSettings?: string[]): IFilterResult;
findValueMatches(filter: string, setting: ISetting): IRange[];
}
......
......@@ -14,7 +14,7 @@ import { visit, JSONVisitor } from 'vs/base/common/json';
import { IModel } from 'vs/editor/common/editorCommon';
import { EditorModel } from 'vs/workbench/common/editor';
import { IConfigurationNode, IConfigurationRegistry, Extensions, OVERRIDE_PROPERTY_PATTERN, IConfigurationPropertySchema, ConfigurationScope } from 'vs/platform/configuration/common/configurationRegistry';
import { ISettingsEditorModel, IKeybindingsEditorModel, ISettingsGroup, ISetting, IFilterResult, ISettingsSection, IGroupFilter, ISettingFilter } from 'vs/workbench/parts/preferences/common/preferences';
import { ISettingsEditorModel, IKeybindingsEditorModel, ISettingsGroup, ISetting, IFilterResult, ISettingsSection, IGroupFilter, ISettingMatcher } from 'vs/workbench/parts/preferences/common/preferences';
import { IKeybindingService } from 'vs/platform/keybinding/common/keybinding';
import { ITextEditorModel } from 'vs/editor/common/services/resolverService';
import { IRange, Range } from 'vs/editor/common/core/range';
......@@ -26,7 +26,7 @@ export abstract class AbstractSettingsModel extends EditorModel {
return this.settingsGroups.map(group => '@' + group.id);
}
protected doFilterSettings(filter: string, groupFilter: IGroupFilter, settingFilter: ISettingFilter): IFilterResult {
protected doFilterSettings(filter: string, groupFilter: IGroupFilter, settingMatcher: ISettingMatcher): IFilterResult {
const allGroups = this.settingsGroups;
if (!filter) {
......@@ -56,7 +56,7 @@ export abstract class AbstractSettingsModel extends EditorModel {
for (const section of group.sections) {
const settings: ISetting[] = [];
for (const setting of section.settings) {
const settingMatches = settingFilter(setting);
const settingMatches = settingMatcher(setting);
if (groupMatched || settingMatches && settingMatches.length) {
settings.push(setting);
}
......@@ -108,6 +108,8 @@ export abstract class AbstractSettingsModel extends EditorModel {
}
public abstract settingsGroups: ISettingsGroup[];
public abstract findValueMatches(filter: string, setting: ISetting): IRange[];
}
export class SettingsEditorModel extends AbstractSettingsModel implements ISettingsEditorModel {
......@@ -147,8 +149,8 @@ export class SettingsEditorModel extends AbstractSettingsModel implements ISetti
return this.settingsModel.getValue();
}
public filterSettings(filter: string, groupFilter: IGroupFilter, settingFilter: ISettingFilter): IFilterResult {
return this.doFilterSettings(filter, groupFilter, settingFilter);
public filterSettings(filter: string, groupFilter: IGroupFilter, settingMatcher: ISettingMatcher): IFilterResult {
return this.doFilterSettings(filter, groupFilter, settingMatcher);
}
public findValueMatches(filter: string, setting: ISetting): IRange[] {
......@@ -388,24 +390,13 @@ export class DefaultSettings extends Disposable {
this.initAllSettingsMap(settingsGroups);
const mostCommonlyUsed = this.getMostCommonlyUsedSettings(settingsGroups);
this._allSettingsGroups = [mostCommonlyUsed, ...settingsGroups];
const builder = new SettingsContentBuilder();
builder.pushLine('[');
builder.pushGroups([mostCommonlyUsed]);
builder.pushLine(',');
builder.pushGroups(settingsGroups);
builder.pushLine(']');
this._content = builder.getContent();
this._content = this.toContent(this._allSettingsGroups, true);
return this._content;
}
get raw(): string {
if (!DefaultSettings._RAW) {
const settingsGroups = this.getRegisteredGroups();
const builder = new SettingsContentBuilder();
builder.pushGroups(settingsGroups);
DefaultSettings._RAW = builder.getContent();
DefaultSettings._RAW = this.toContent(this.getRegisteredGroups(), false);
}
return DefaultSettings._RAW;
}
......@@ -543,6 +534,18 @@ export class DefaultSettings extends Disposable {
return c1.order - c2.order;
}
private toContent(settingsGroups: ISettingsGroup[], asArray: boolean): string {
const builder = new SettingsContentBuilder();
if (asArray) {
builder.pushLine('[');
}
builder.pushGroups(settingsGroups);
if (asArray) {
builder.pushLine(']');
}
return builder.getContent();
}
}
export class DefaultSettingsEditorModel extends AbstractSettingsModel implements ISettingsEditorModel {
......@@ -576,20 +579,25 @@ export class DefaultSettingsEditorModel extends AbstractSettingsModel implements
return this.defaultSettings.settingsGroups;
}
public filterSettings(filter: string, groupFilter: IGroupFilter, settingFilter: ISettingFilter, mostRelevantSettings?: string[]): IFilterResult {
public filterSettings(filter: string, groupFilter: IGroupFilter, settingMatcher: ISettingMatcher, mostRelevantSettings?: string[]): IFilterResult {
if (mostRelevantSettings) {
const mostRelevantGroup = this.renderMostRelevantSettings(mostRelevantSettings);
// calculate match ranges
const matches = mostRelevantGroup.sections[0].settings.reduce((prev, s) => {
return prev.concat(settingMatcher(s));
}, []);
return {
allGroups: [...this.settingsGroups, mostRelevantGroup],
filteredGroups: mostRelevantGroup.sections[0].settings.length ? [mostRelevantGroup] : [],
matches: [],
matches,
query: filter
};
} else {
// Do local search and add empty 'most relevant' group
const mostRelevantGroup = this.renderMostRelevantSettings([]);
const result = this.doFilterSettings(filter, groupFilter, settingFilter);
const result = this.doFilterSettings(filter, groupFilter, settingMatcher);
result.allGroups = [...result.allGroups, mostRelevantGroup];
return result;
}
......
......@@ -128,11 +128,11 @@ class LocalSearchProvider {
return regex.test(group.title);
};
const settingFilter = (setting: ISetting) => {
return new SettingMatches(this._filter, setting, (filter, setting) => preferencesModel.findValueMatches(filter, setting)).matches;
const settingMatcher = (setting: ISetting) => {
return new SettingMatches(this._filter, setting, true, (filter, setting) => preferencesModel.findValueMatches(filter, setting)).matches;
};
return TPromise.wrap(preferencesModel.filterSettings(this._filter, groupFilter, settingFilter));
return TPromise.wrap(preferencesModel.filterSettings(this._filter, groupFilter, settingMatcher));
}
}
......@@ -150,19 +150,6 @@ class RemoteSearchProvider {
filterPreferences(preferencesModel: ISettingsEditorModel): TPromise<IFilterResult> {
return this._remoteSearchP.then(remoteResult => {
const settingFilter = (setting: ISetting) => {
if (!!remoteResult.scoredResults[setting.key]) {
const settingMatches = new SettingMatches(this._filter, setting, (filter, setting) => preferencesModel.findValueMatches(filter, setting)).matches;
if (settingMatches.length) {
return settingMatches;
} else {
return [new Range(setting.keyRange.startLineNumber, setting.keyRange.startColumn, setting.keyRange.endLineNumber, setting.keyRange.startColumn)];
}
} else {
return null;
}
};
if (remoteResult) {
let sortedNames = Object.keys(remoteResult.scoredResults).sort((a, b) => remoteResult.scoredResults[b] - remoteResult.scoredResults[a]);
if (sortedNames.length) {
......@@ -170,7 +157,8 @@ class RemoteSearchProvider {
sortedNames = sortedNames.filter(name => remoteResult.scoredResults[name] >= highScore / 2);
}
const result = preferencesModel.filterSettings(this._filter, group => null, settingFilter, sortedNames);
const settingMatcher = this.getRemoteSettingMatcher(sortedNames, preferencesModel);
const result = preferencesModel.filterSettings(this._filter, group => null, settingMatcher, sortedNames);
result.metadata = remoteResult;
return result;
} else {
......@@ -226,6 +214,22 @@ class RemoteSearchProvider {
return TPromise.as(p as any);
}
private getRemoteSettingMatcher(names: string[], preferencesModel: ISettingsEditorModel): any {
const resultSet = new Set();
names.forEach(name => resultSet.add(name));
return (setting: ISetting) => {
if (resultSet.has(setting.key)) {
const settingMatches = new SettingMatches(this._filter, setting, false, (filter, setting) => preferencesModel.findValueMatches(filter, setting)).matches;
if (settingMatches.length) {
return settingMatches;
}
}
return [];
};
}
}
const API_VERSION = 'api-version=2016-09-01-Preview';
......@@ -275,7 +279,7 @@ class SettingMatches {
public readonly matches: IRange[];
constructor(searchString: string, setting: ISetting, private valuesMatcher: (filter: string, setting: ISetting) => IRange[]) {
constructor(searchString: string, setting: ISetting, private requireFullQueryMatch: boolean, private valuesMatcher: (filter: string, setting: ISetting) => IRange[]) {
this.matches = distinct(this._findMatchesInSetting(searchString, setting), (match) => `${match.startLineNumber}_${match.startColumn}_${match.endLineNumber}_${match.endColumn}_`);
}
......@@ -283,7 +287,7 @@ class SettingMatches {
const result = this._doFindMatchesInSetting(searchString, setting);
if (setting.overrides && setting.overrides.length) {
for (const subSetting of setting.overrides) {
const subSettingMatches = new SettingMatches(searchString, subSetting, this.valuesMatcher);
const subSettingMatches = new SettingMatches(searchString, subSetting, this.requireFullQueryMatch, this.valuesMatcher);
let words = searchString.split(' ');
const descriptionRanges: IRange[] = this.getRangesForWords(words, this.descriptionMatchingWords, [subSettingMatches.descriptionMatchingWords, subSettingMatches.keyMatchingWords, subSettingMatches.valueMatchingWords]);
const keyRanges: IRange[] = this.getRangesForWords(words, this.keyMatchingWords, [subSettingMatches.descriptionMatchingWords, subSettingMatches.keyMatchingWords, subSettingMatches.valueMatchingWords]);
......@@ -353,7 +357,7 @@ class SettingMatches {
const ranges = from.get(word);
if (ranges) {
result.push(...ranges);
} else if (others.every(o => !o.has(word))) {
} else if (this.requireFullQueryMatch && others.every(o => !o.has(word))) {
return [];
}
}
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册