From 87e1093c4d07b406f06825619c648b207c7da5dd Mon Sep 17 00:00:00 2001 From: PikachuEXE Date: Fri, 1 Oct 2021 15:38:33 +0800 Subject: [PATCH] Update top nav input box action button icon depends on input (#1738) * Rename `showArrow` to `showActionButton` * * Display different icon for action button when input text look like a Youtube URL * ! Fix transition for button appearing absent * * Update to use new icon for all FT supported URLs * Update src/renderer/components/ft-input/ft-input.js Co-authored-by: Jason <84899178+jasonhenriquez@users.noreply.github.com> * * Update action button to look disabled when input text is empty * * Disable button hover/active visual effect when "disabled" * * Make action button only respond to cursor when enabled Co-authored-by: Jason <84899178+jasonhenriquez@users.noreply.github.com> --- .../external-player-settings.vue | 4 +- src/renderer/components/ft-input/ft-input.css | 21 +++-- src/renderer/components/ft-input/ft-input.js | 80 +++++++++++++++++-- src/renderer/components/ft-input/ft-input.vue | 13 +-- .../ft-profile-edit/ft-profile-edit.vue | 4 +- .../general-settings/general-settings.vue | 2 +- .../proxy-settings/proxy-settings.vue | 4 +- .../sponsor-block-settings.vue | 2 +- 8 files changed, 104 insertions(+), 26 deletions(-) diff --git a/src/renderer/components/external-player-settings/external-player-settings.vue b/src/renderer/components/external-player-settings/external-player-settings.vue index 59ab38804..c2298dc22 100644 --- a/src/renderer/components/external-player-settings/external-player-settings.vue +++ b/src/renderer/components/external-player-settings/external-player-settings.vue @@ -33,7 +33,7 @@ > { + this.clearTextButtonVisible = true + }, 0) } else { - // Hide the button after the transition + // Hide the button with transition + this.clearTextButtonVisible = false + // Remove the button after the transition // 0.2s in CSS = 200ms in JS setTimeout(() => { - this.clearTextButtonVisible = false + this.clearTextButtonExisting = false }, 200) } } @@ -109,6 +119,9 @@ export default Vue.extend({ }, methods: { handleClick: function () { + // No action if no input text + if (!this.inputDataPresent) { return } + this.searchState.showOptions = false this.$emit('input', this.inputData) this.$emit('click', this.inputData) @@ -118,11 +131,13 @@ export default Vue.extend({ if (this.isSearch && this.searchState.selectedOption !== -1 && this.inputData === this.dataList[this.searchState.selectedOption]) { return } + this.handleActionIconChange() this.$emit('input', this.inputData) }, handleClearTextClick: function () { this.inputData = '' + this.handleActionIconChange() this.$emit('input', this.inputData) // Focus on input element after text is clear for better UX @@ -130,6 +145,55 @@ export default Vue.extend({ inputElement.focus() }, + handleActionIconChange: function() { + // Only need to update icon if visible + if (!this.showActionButton) { return } + + if (!this.inputDataPresent) { + // Change back to default icon if text is blank + this.actionButtonIconName = 'search' + return + } + + // Update action button icon according to input + try { + this.getYoutubeUrlInfo(this.inputData).then((result) => { + let isYoutubeLink = false + + switch (result.urlType) { + case 'video': + case 'playlist': + case 'search': + case 'channel': + isYoutubeLink = true + break + case 'hashtag': + // TODO: Implement a hashtag related view + // isYoutubeLink is already `false` + break + + case 'invalid_url': + default: { + // isYoutubeLink is already `false` + } + } + + if (isYoutubeLink) { + // Go to URL (i.e. Video/Playlist/Channel + this.actionButtonIconName = 'arrow-right' + } else { + // Search with text + this.actionButtonIconName = 'search' + } + }) + } catch (ex) { + // On exception, consider text as invalid URL + this.actionButtonIconName = 'search' + // Rethrow exception + throw ex + } + }, + addListener: function () { const inputElement = document.getElementById(this.id) @@ -178,6 +242,10 @@ export default Vue.extend({ if (this.selectOnFocus) { e.target.select() } - } + }, + + ...mapActions([ + 'getYoutubeUrlInfo' + ]) } }) diff --git a/src/renderer/components/ft-input/ft-input.vue b/src/renderer/components/ft-input/ft-input.vue index 3e3cf733f..bd78dceb2 100644 --- a/src/renderer/components/ft-input/ft-input.vue +++ b/src/renderer/components/ft-input/ft-input.vue @@ -4,7 +4,7 @@ :class="{ search: isSearch, forceTextColor: forceTextColor, - showArrow: showArrow, + showActionButton: showActionButton, showClearTextButton: showClearTextButton }" > @@ -21,11 +21,11 @@ /> diff --git a/src/renderer/components/ft-profile-edit/ft-profile-edit.vue b/src/renderer/components/ft-profile-edit/ft-profile-edit.vue index bd2c0d5b5..e6c072708 100644 --- a/src/renderer/components/ft-profile-edit/ft-profile-edit.vue +++ b/src/renderer/components/ft-profile-edit/ft-profile-edit.vue @@ -7,7 +7,7 @@ class="profileName" placeholder="Profile Name" :value="profileName" - :show-arrow="false" + :show-action-button="false" @input="e => profileName = e" /> @@ -40,7 +40,7 @@ class="profileName" placeholder="" :value="profileBgColor" - :show-arrow="false" + :show-action-button="false" :disabled="true" /> diff --git a/src/renderer/components/general-settings/general-settings.vue b/src/renderer/components/general-settings/general-settings.vue index 39af5b5b0..35ab256e6 100644 --- a/src/renderer/components/general-settings/general-settings.vue +++ b/src/renderer/components/general-settings/general-settings.vue @@ -96,7 +96,7 @@