diff options
| author | Hunternif <hunternif@gmail.com> | 2022-10-02 04:37:48 +0100 |
|---|---|---|
| committer | Hunternif <hunternif@gmail.com> | 2022-10-02 04:44:46 +0100 |
| commit | 757d0ee8a6fc54e10d6f7c28d79b927d8eb0382d (patch) | |
| tree | ab61109254f07d39edc1b0d8c1714d0f0eff5f0c /client/js/controls | |
| parent | a82fa8940158784285872434659b5cb7fb9b817a (diff) | |
client: suggest tags based on lookalike posts
Diffstat (limited to 'client/js/controls')
| -rw-r--r-- | client/js/controls/post_edit_sidebar_control.js | 4 | ||||
| -rw-r--r-- | client/js/controls/tag_input_control.js | 45 |
2 files changed, 47 insertions, 2 deletions
diff --git a/client/js/controls/post_edit_sidebar_control.js b/client/js/controls/post_edit_sidebar_control.js index c840da8..053a317 100644 --- a/client/js/controls/post_edit_sidebar_control.js +++ b/client/js/controls/post_edit_sidebar_control.js @@ -104,7 +104,9 @@ class PostEditSidebarControl extends events.EventTarget { if (this._tagInputNode) { this._tagControl = new TagInputControl( this._tagInputNode, - this._post.tags + this._post.tags, + null, + this._post, ); } diff --git a/client/js/controls/tag_input_control.js b/client/js/controls/tag_input_control.js index a0c9eee..35bbe9f 100644 --- a/client/js/controls/tag_input_control.js +++ b/client/js/controls/tag_input_control.js @@ -10,6 +10,7 @@ const settings = require("../models/settings.js"); const events = require("../events.js"); const views = require("../util/views.js"); const TagAutoCompleteControl = require("./tag_auto_complete_control.js"); +const PostList = require("../models/post_list.js"); const KEY_SPACE = 32; const KEY_RETURN = 13; @@ -83,9 +84,10 @@ class SuggestionList { } class TagInputControl extends events.EventTarget { - constructor(hostNode, tagList, placeholder) { + constructor(hostNode, tagList, placeholder, post) { super(); this.tags = tagList; + this._post = post; this._hostNode = hostNode; this._suggestions = new SuggestionList(); this._tagToListItemNode = new Map(); @@ -153,6 +155,8 @@ class TagInputControl extends events.EventTarget { const listItemNode = this._createListItemNode(tag); this._tagListNode.appendChild(listItemNode); } + + this._createSuggestionsFromLookalikes(); } addTagByText(text, source) { @@ -349,6 +353,20 @@ class TagInputControl extends events.EventTarget { return listItemNode; } + _createSuggestionsFromLookalikes() { + const node = this._editAreaNode.querySelector("a.tag-from-lookalikes"); + if (this._post === undefined) { + node.style.display = "none"; + } else { + node.addEventListener("click", (e) => { + e.preventDefault(); + this._suggestions.clear(); + this._loadSuggestionsFromLookalikes(); + this._removeSuggestionsPopupOpacity(); + }); + } + } + _deleteListItemNode(tag) { const listItemNode = this._getListItemNode(tag); if (listItemNode) { @@ -399,6 +417,31 @@ class TagInputControl extends events.EventTarget { }); } + _loadSuggestionsFromLookalikes() { + const limit = 20; + const fields = ["id", "thumbnailUrl", "tags"]; + const threshold = 1; + PostList.reverseSearch(this._post.id, limit, threshold, fields) + .then((response) => { + const tagOccurrences = {}; + for (let post of response.results) { + for (let tag of post.tags) { + const name = tag.names[0]; + let count = tagOccurrences[name] || 0; + tagOccurrences[name] = count + 1; + } + } + for (const [tagName, count] of Object.entries(tagOccurrences)) { + this._suggestions.set(tagName, count); + } + if (this._suggestions.length) { + this._openSuggestionsPopup(); + } else { + this._closeSuggestionsPopup(); + } + }); + } + _refreshSuggestionsPopup() { if (!this._suggestionsNode.classList.contains("shown")) { return; |