diff --git a/src/plugins/music-together/index.ts b/src/plugins/music-together/index.ts index 79c974fa..d208cec6 100644 --- a/src/plugins/music-together/index.ts +++ b/src/plugins/music-together/index.ts @@ -21,6 +21,8 @@ import { createSettingPopup } from './ui/setting'; import settingHTML from './templates/setting.html?raw'; import style from './style.css?inline'; +import { waitForElement } from '@/utils/wait-for-element'; + import type { YoutubePlayer } from '@/types/youtube-player'; import type { RendererContext } from '@/types/contexts'; import type { VideoDataChanged } from '@/types/video-data-changed'; @@ -595,19 +597,22 @@ export default createPlugin< this.elements.spinner.setAttribute('hidden', ''); }, - initMyProfile() { - const accountButton = document.querySelector< - HTMLElement & { - onButtonTap: () => void; - } - >('ytmusic-settings-button'); + async initMyProfile() { + const accountButton = await waitForElement( + '#right-content > ytmusic-settings-button *:where(tp-yt-paper-icon-button,yt-icon-button,.ytmusic-settings-button)', + { + maxRetry: 10000, + }, + ); - accountButton?.onButtonTap(); - setTimeout(() => { - accountButton?.onButtonTap(); - const renderer = document.querySelector< - HTMLElement & { data: unknown } - >('ytd-active-account-header-renderer'); + accountButton?.click(); + setTimeout(async () => { + const renderer = await waitForElement( + 'ytd-active-account-header-renderer', + { + maxRetry: 10000, + }, + ); if (!accountButton || !renderer) { console.warn('Music Together: Cannot find account'); this.me = getDefaultProfile(this.connection?.id ?? ''); @@ -628,6 +633,7 @@ export default createPlugin< this.popups.guest.setProfile(this.me.thumbnail); this.popups.setting.setProfile(this.me.thumbnail); } + accountButton?.click(); // close menu }, 0); }, /* hooks */ diff --git a/src/utils/wait-for-element.ts b/src/utils/wait-for-element.ts index f80955e9..3f84d4c7 100644 --- a/src/utils/wait-for-element.ts +++ b/src/utils/wait-for-element.ts @@ -1,13 +1,30 @@ export const waitForElement = ( selector: string, + options: { + maxRetry?: number; + retryInterval?: number; + } = { + maxRetry: -1, + retryInterval: 100, + }, ): Promise => { return new Promise((resolve) => { + let retryCount = 0; + const maxRetry = options.maxRetry ?? -1; + const retryInterval = options.retryInterval ?? 100; const interval = setInterval(() => { + if (maxRetry > 0 && retryCount >= maxRetry) { + clearInterval(interval); + return; + } const elem = document.querySelector(selector); - if (!elem) return; + if (!elem) { + retryCount++; + return; + } clearInterval(interval); resolve(elem); - }, 100 /* ms */); + }, retryInterval /* ms */); }); };