Bug 1636696 - Highlight suggestions only if the typed token prefixes a word in the suggestion. r=mak

Differential Revision: https://phabricator.services.mozilla.com/D74966
This commit is contained in:
Harry Twyford 2020-05-14 16:32:58 +00:00
Родитель b2578e4b34
Коммит 52c65880a4
3 изменённых файлов: 42 добавлений и 11 удалений

Просмотреть файл

@ -275,8 +275,11 @@ var UrlbarUtils = {
*
* @param {array} tokens The tokens to search for.
* @param {string} str The string to match against.
* @param {boolean} highlightType If HIGHLIGHT.SUGGESTED, return a list of all
* the token string non-matches. Otherwise, return matches.
* @param {boolean} highlightType
* One of the HIGHLIGHT values:
* TYPED: match ranges matching the tokens; or
* SUGGESTED: match ranges for words not matching the tokens and the
* endings of words that start with a token.
* @returns {array} An array: [
* [matchIndex_0, matchLength_0],
* [matchIndex_1, matchLength_1],
@ -289,7 +292,7 @@ var UrlbarUtils = {
str = str.toLocaleLowerCase();
// To generate non-overlapping ranges, we start from a 0-filled array with
// the same length of the string, and use it as a collision marker, setting
// 1 where a token matches.
// 1 where the text should be highlighted.
let hits = new Array(str.length).fill(
highlightType == this.HIGHLIGHT.SUGGESTED ? 1 : 0
);
@ -308,6 +311,20 @@ var UrlbarUtils = {
if (index < 0) {
break;
}
if (highlightType == UrlbarUtils.HIGHLIGHT.SUGGESTED) {
// We de-emphasize the match only if it's preceded by a space, thus
// it's a perfect match or the beginning of a longer word.
let previousSpaceIndex = str.lastIndexOf(" ", index) + 1;
if (index != previousSpaceIndex) {
index += needle.length;
// We found the token but we won't de-emphasize it, because it's not
// after a word boundary.
found = true;
continue;
}
}
hits.fill(
highlightType == this.HIGHLIGHT.SUGGESTED ? 0 : 1,
index,
@ -335,6 +352,13 @@ var UrlbarUtils = {
while (index < str.length) {
let hay = str.substr(index, needle.length);
if (compareIgnoringDiacritics(needle, hay) === 0) {
if (highlightType == UrlbarUtils.HIGHLIGHT.SUGGESTED) {
let previousSpaceIndex = str.lastIndexOf(" ", index) + 1;
if (index != previousSpaceIndex) {
index += needle.length;
continue;
}
}
hits.fill(
highlightType == this.HIGHLIGHT.SUGGESTED ? 0 : 1,
index,

Просмотреть файл

@ -105,9 +105,9 @@ add_task(async function searchSuggestions() {
);
// The first expected search is the search term itself since the heuristic
// result will come before the search suggestions.
// The extra space is here due to bug 1550644.
// The extra spaces are here due to bug 1550644.
let searchTerm = "foo ";
let expectedSearches = [searchTerm, "foofoo ", "foo bar"];
let expectedSearches = [searchTerm, "foo foo", "foo bar"];
for (let i = 0; i < length; i++) {
let result = await UrlbarTestUtils.getDetailsOfResultAt(window, i);
if (result.type === UrlbarUtils.RESULT_TYPE.SEARCH) {

Просмотреть файл

@ -211,7 +211,11 @@ add_task(function test() {
}
});
add_task(function testReverse() {
/**
* Tests suggestion highlighting. Note that suggestions are only highlighted if
* the matching token is at the beginning of a word in the matched string.
*/
add_task(function testSuggestions() {
const tests = [
{
tokens: ["mozilla", "is", "i"],
@ -232,12 +236,12 @@ add_task(function testReverse() {
{
tokens: ["mo", "zilla"],
phrase: "mOzIlLa",
expected: [],
expected: [[2, 5]],
},
{
tokens: ["MO", "ZILLA"],
phrase: "mozilla",
expected: [],
expected: [[2, 5]],
},
{
tokens: [""], // Should never happen in practice.
@ -245,27 +249,30 @@ add_task(function testReverse() {
expected: [[0, 7]],
},
{
tokens: ["mo", "om"],
tokens: ["mo", "om", "la"],
phrase: "mozilla mozzarella momo",
expected: [
[2, 6],
[10, 9],
[21, 2],
],
},
{
tokens: ["mo", "om"],
tokens: ["mo", "om", "la"],
phrase: "MOZILLA MOZZARELLA MOMO",
expected: [
[2, 6],
[10, 9],
[21, 2],
],
},
{
tokens: ["MO", "OM"],
tokens: ["MO", "OM", "LA"],
phrase: "mozilla mozzarella momo",
expected: [
[2, 6],
[10, 9],
[21, 2],
],
},
];