diff --git a/packages/frontend/src/components/MkAutocomplete.vue b/packages/frontend/src/components/MkAutocomplete.vue index 2af1cc299e3c..064d69250b13 100644 --- a/packages/frontend/src/components/MkAutocomplete.vue +++ b/packages/frontend/src/components/MkAutocomplete.vue @@ -57,7 +57,7 @@ import { i18n } from '@/i18n.js'; import { miLocalStorage } from '@/local-storage.js'; import { customEmojis } from '@/custom-emojis.js'; import { MFM_TAGS, MFM_PARAMS } from '@/const.js'; -import { searchEmoji, EmojiDef } from '@/scripts/search-emoji.js'; +import { searchEmoji, searchEmojiExact, EmojiDef } from '@/scripts/search-emoji.js'; export type CompleteInfo = { user: { @@ -282,13 +282,7 @@ function exec() { emojis.value = searchEmoji(props.q, emojiDb.value); } else if (props.type === 'emojiComplete') { - if (!props.q || props.q === '') { - // 最近使った絵文字をサジェスト - emojis.value = defaultStore.state.recentlyUsedEmojis.map(emoji => unicodeEmojiDB.value.find(dbEmoji => dbEmoji.emoji === emoji)).filter(x => x) as EmojiDef[]; - return; - } - - emojis.value = searchEmoji(props.q, unicodeEmojiDB.value); + emojis.value = searchEmojiExact(props.q, unicodeEmojiDB.value); } else if (props.type === 'mfmTag') { if (!props.q || props.q === '') { mfmTags.value = MFM_TAGS; diff --git a/packages/frontend/src/scripts/search-emoji.ts b/packages/frontend/src/scripts/search-emoji.ts index 371f69b9a77d..4cda880bff23 100644 --- a/packages/frontend/src/scripts/search-emoji.ts +++ b/packages/frontend/src/scripts/search-emoji.ts @@ -104,3 +104,33 @@ export function searchEmoji(query: string | null, emojiDb: EmojiDef[], max = 30) .slice(0, max) .map(it => it.emoji); } + +export function searchEmojiExact(query: string | null, emojiDb: EmojiDef[], max = 30): EmojiDef[] { + if (!query) { + return []; + } + + const matched = new Map(); + // 完全一致(エイリアスなし) + emojiDb.some(x => { + if (x.name === query && !x.aliasOf) { + matched.set(x.name, { emoji: x, score: query.length + 3 }); + } + return matched.size === max; + }); + + // 完全一致(エイリアス込み) + if (matched.size < max) { + emojiDb.some(x => { + if (x.name === query && !matched.has(x.aliasOf ?? x.name)) { + matched.set(x.aliasOf ?? x.name, { emoji: x, score: query.length + 2 }); + } + return matched.size === max; + }); + } + + return [...matched.values()] + .sort((x, y) => y.score - x.score) + .slice(0, max) + .map(it => it.emoji); +}