r/ListenToThis에서 좋아하는 음악을 강조하는 브라우저 확장

104391 단어
나는 새로운 것과 무시당하는 음악을 발견하고 싶을 때 https://www.reddit.com/r/listentothis/에 갈 것이다.매일 신곡이 많이 들어가기 때문에, 내가 가장 좋아하는 유형을 빨리 찾을 수 있는 방법이 필요하다.다행히도 모든 문장의 제목에는 유파 정보가 포함되어 있기 때문에...키워드(유형)가 포함된 게시물을 다양한 색상으로 강조 표시하는 브라우저 확장을 구축했습니다.

너는 이곳에서 온전한 원본 코드를 찾을 수 있다: https://github.com/alexadam/ListenToThis-Highlight

브라우저 확장을 만드는 방법


음악 하이라이트라는 폴더를 만듭니다.확장된 루트 폴더가 됩니다.
mkdir music-highlight
cd music-highlight
각 브라우저 확장자에는 작성자 이름, 설명, 권한, 라이센스, 스크립트 등의 메타데이터가 들어 있는 목록 파일이 있어야 합니다. 자세한 내용은 https://developer.mozilla.org/en-US/docs/Mozilla/Add-ons/WebExtensions/manifest.json
파일 생성 manifest.json 및 붙여넣기:
{
  "manifest_version": 2,
  "name": "music-highlight",
  "version": "1",
  "author": "Your Name",
  "homepage_url": "https://www.reddit.com/r/listentothis/",
  "description": "Highlight your favorite music genres on r/ListenToThis",
  "content_scripts": [{
    "matches": ["*://*.reddit.com/r/listentothis*"],
    "js": ["colors.js"]
  }],
  "permissions": [
    "activeTab",
    "https://www.reddit.com/r/listentothis/",
    "https://old.reddit.com/r/listentothis/",
    "storage"
  ]
}
컨텐트 스크립트 섹션에서는 Chrome이나 Firefox에 색상을 실행하라고 알려 줍니다.URL이 정규 표현식 모드와 일치하는 웹 페이지에서 js를 사용합니다. 우리의 예에는 신구reddit가 있습니다.
색을 주입하다.reddit 페이지에서 표준 DOM API(색상 변경, 새 HTML 요소 추가 등)를 사용하여 컨텐트에 액세스하고 수정할 수 있습니다.컨텐츠 스크립트에 대한 자세한 내용: https://developer.mozilla.org/en-US/docs/Mozilla/Add-ons/WebExtensions/Content_scripts
얼마나 예쁜 색깔인데.js 작품:
  • 페이지의 각 기사
  • 게시물 제목 및 URL 획득
  • 목록에 제목이 포함된 경우
  • 배경색 변경
  • 우리는 어떻게 직위를 찾습니까?요소를 확인하려면 마우스 오른쪽 버튼으로 클릭합니다.이전 Reddit에서 Scroll Releement 클래스 또는 thing 클래스를 포함하는 모든 HTML 요소를 가져옵니다.

    파일 colors.js을 만들고 모든 게시물을 반환하는 함수를 추가합니다.
    const getAllPosts = () => {
      // old reddit
      const allPosts = document.getElementsByClassName('thing');
      if (allPosts.length === 0) {
        // new reddit
        return document.getElementsByClassName('scrollerItem');
      }
      return allPosts
    }
    
    그런 다음 추출 머리글의 함수를 만듭니다.
    const getTitle = (post) => {
      // old reddit
      const titleElem = post.querySelector('a.title');
      // new reddit
      if (!titleElem) {
        return post.querySelector('h3');
      }
      return titleElem
    }
    
    제목 형식은 Band - Song [genre1/genre2, genre3] (2020)과 비슷하며 대괄호 안의 내용만 필요합니다.
    const getGenresAsString = (titleElem) => {
      const text = titleElem.innerText.toLowerCase()
    
      // Extract the genres from the title 
      const genresRegex = /\[([^\]]+)\]/g
      const match = genresRegex.exec(text)
    
      // Skip over posts that are not properly formatted
      if (!match) {
        return null
      }
      return match[0]
    }
    
    가장 좋아하는 유형과 색상을 나열하는 목록을 추가합니다.
    const favoriteGenres = {
      'ambient': '#fa8335',
      'blues': '#0df9f9',
      'country': '#fad337',
      'chill': '#a8f830',
      'funk': '#F2EF0C',
      'jazz': '#fba19d',
      'soul': '#aca2bb',
    }
    
    모든 fav를 옮겨다니는 함수를 만듭니다.위 목록에 정의된 유형입니다.getGenresAsString이 반환하는 문자열에서 어떤 종류가 언급되면 함수는 그 색을 반환합니다. (일치하는 항목이 여러 개 있으면 마지막 종류의 색을 반환합니다.)
    const getBGColor = (allGenresStr, favGenres) => {
      let bgColor = null
    
      // Test if the post contains any of our fav. genres
      for (const genre of Object.keys(favGenres)) {
        const genreRegex = new RegExp('.*' + genre + '.*', "i")
        if (!genreRegex.test(allGenresStr)) {
          continue
        }
        bgColor = 'background-color: ' + favGenres[genre] + ' !important'
      }
    
      return bgColor
    }
    
    시도하기 전에 우리는 또 다른 문제를 해결해야 한다...새 레딧은 동적으로 컨텐트를 로드하고 로드할 때 색상을 추가합니다.js가 페이지에서 실행되고 유용한 데이터가 없습니다.또한 아래로 스크롤할 때 새로운 내용을 추가합니다. 논리를 다시 적용하고 색을 업데이트해야 합니다.따라서 코드를 트리거하는 새로운 컨텐츠 모니터가 필요합니다.
    const observeDOM = (() => {
      const MutationObserver = window.MutationObserver || window.WebKitMutationObserver;
      const eventListenerSupported = window.addEventListener;
    
      return (obj, callback) => {
        if (MutationObserver) {
          const obs = new MutationObserver((mutations, observer) => {
            if (mutations[0].addedNodes.length)
              callback(mutations[0].addedNodes);
          });
          obs.observe(obj, {
            childList: true,
            subtree: true
          });
        } else if (eventListenerSupported) {
          obj.addEventListener('DOMNodeInserted', callback, false);
          obj.addEventListener('DOMNodeRemoved', callback, false);
        }
      };
    
    })();
    
    // detect if on the new Reddit before the content is loaded
    const targetElem = document.getElementById('2x-container')
    if (targetElem) {
      observeDOM(targetElem, (addedNodes) => {
        // whenever new content is added
        addColorsOnSongs(favoriteGenres);
      });
    }
    
    우리가 모든 물건을 한데 놓은 후에 색깔.js는 다음과 같습니다.
    const favoriteGenres = {
      'ambient': '#fa8335',
      'blues': '#0df9f9',
      'country': '#fad337',
      'chill': '#a8f830',
      'funk': '#F2EF0C',
      'jazz': '#fba19d',
      'soul': '#aca2bb',
    }
    
    const getAllPosts = () => {
      // old reddit
      const allPosts = document.getElementsByClassName('thing');
      if (allPosts.length === 0) {
        // new reddit
        return document.getElementsByClassName('scrollerItem');
      }
      return allPosts
    }
    
    const getTitle = (post) => {
      // old reddit
      const titleElem = post.querySelector('a.title');
      // new reddit
      if (!titleElem) {
        return post.querySelector('h3');
      }
      return titleElem
    }
    
    const getGenresAsString = (titleElem) => {
      const text = titleElem.innerText.toLowerCase()
    
      // Extract the genres from the title 
      const genresRegex = /\[([^\]]+)\]/g
      const match = genresRegex.exec(text)
    
      // Skip over posts that are not properly formatted
      if (!match) {
        return null
      }
      return match[0]
    }
    
    
    const getBGColor = (allGenresStr, favGenres) => {
      let bgColor = null
    
      // Test if the post contains any of our fav. genres
      for (const genre of Object.keys(favGenres)) {
        const genreRegex = new RegExp('.*' + genre + '.*', "i")
        if (!genreRegex.test(allGenresStr)) {
          continue
        }
        bgColor = 'background-color: ' + favGenres[genre] + ' !important'
      }
    
      return bgColor
    }
    
    const changePostColor = (post, bgColor) => {
      post.setAttribute('style', bgColor);
        for (let child of post.children) {
          child.setAttribute('style', bgColor);
          for (let child2 of child.children) {
            child2.setAttribute('style', bgColor);
          }
        }
    }
    
    const addColorsOnSongs = (colorData) => {
      const allPosts = getAllPosts();
    
      for (const post of allPosts) {
    
        const titleElem = getTitle(post)
    
        if (!titleElem) continue
    
        const genresStr = getGenresAsString(titleElem)
        const bgColor = getBGColor(genresStr, favoriteGenres)
    
        if (!bgColor) continue
    
        // Change the post's & its children bg color
        changePostColor(post, bgColor)
    
      }
    
    }
    
    addColorsOnSongs(favoriteGenres)
    
    const observeDOM = (() => {
      const MutationObserver = window.MutationObserver || window.WebKitMutationObserver;
      const eventListenerSupported = window.addEventListener;
    
      return (obj, callback) => {
        if (MutationObserver) {
          const obs = new MutationObserver((mutations, observer) => {
            if (mutations[0].addedNodes.length)
              callback(mutations[0].addedNodes);
          });
          obs.observe(obj, {
            childList: true,
            subtree: true
          });
        } else if (eventListenerSupported) {
          obj.addEventListener('DOMNodeInserted', callback, false);
          obj.addEventListener('DOMNodeRemoved', callback, false);
        }
      };
    
    })();
    
    // detect if on the new Reddit before the content is loaded
    const targetElem = document.getElementById('2x-container')
    if (targetElem) {
      observeDOM(targetElem, (addedNodes) => {
        addColorsOnSongs(favoriteGenres);
      });
    }
    
    우리 한번 테스트해 보자...
    Chrome:
  • 탐색chrome://extensions
  • 개발자 모드 전환(오른쪽)
  • 클릭 로드 미포장
  • 내선 폴더 "음악 강조 표시"선택
  • 클릭하여
  • 열기
    Firefox:
  • 탐색 정보: 디버깅
  • 이 불여우(왼쪽 위)
  • 클릭
  • 클릭하여 임시 로드 항목 로드
  • 내선 폴더로 이동
  • 선택 목록.json
  • 클릭하여
  • 열기
    그리고 https://old.reddit.com/r/listentothis/을 방문하면 다음을 볼 수 있습니다.

    https://www.reddit.com/r/listentothis/

    사용자 경험 문제 해결


    다른 색깔의 하이라이트 디스플레이를 사용하면 목록에서 재미있는 음악을 쉽게 찾을 수 있지만, 우리는 여전히 그것을 개선할 수 있다.더 큰 글꼴로 유파를 표시하는 요소를 추가하고 싶습니다. 유파를 클릭하면 레드디트 평론 페이지를 열지 않고 링크된 노래로 바로 들어갑니다.
    그래서 한 편의 댓글에 적어도 나의 최애를 포함한다면.장르:
  • 하이퍼링크 HTML 요소 만들기
  • , href 소스
  • 과 일치하는 모든 장르를 내부 텍스트로
  • 그리고 레드디트의 게시물
  • 유용한 함수를 추가하는 것부터 시작하겠습니다. 게시물에서 원본 URL을 추출합니다.
    const getSongURL = (titleElem, post) => {
      // old reddit
      let href = titleElem.href
      // new reddit
      if (!href) {
        const extLink = post.querySelector('a.styled-outbound-link')
        if (extLink) {
          return extLink.href
        }
      }
      return href
    }
    
    createSongLink에서 HTML 요소를 만들려면 다음과 같이 하십시오.
    const createSongLink = (titleElem, post, genresText) => {
      post.style.position = 'relative'
      let linkElem = document.createElement('a')
      linkElem.className = "favGenresLink"
      linkElem.style.position = 'absolute'
      linkElem.style.right = '20px'
      linkElem.style.bottom = '0'
      linkElem.style.height = '50px'
      linkElem.style.color = 'black'
      linkElem.style.fontSize = '50px'
      linkElem.style.zIndex = '999999'
      linkElem.innerText = genresText
      linkElem.href = getSongURL(titleElem, post)
      return linkElem
    }
    
    getBGcolor를 수정하여 색상과 일치하는 모든 유형을 텍스트로 반환합니다.
    const getBGColor = (allGenresStr, favGenres) => {
      let bgColor = null
      let favGenresStr = ''
    
      // Test if the post contains any of our fav. genres
      for (const genre of Object.keys(favGenres)) {
        const genreRegex = new RegExp('.*' + genre + '.*', "i")
        if (!genreRegex.test(allGenresStr)) {
          continue
        }
        bgColor = 'background-color: ' + favGenres[genre] + ' !important'
        favGenresStr += genre + ' '
      }
    
      return {bgColor, favGenresStr}
    }
    
    addColorsOnSongs 업데이트:
    const addColorsOnSongs = (colorData) => {
      const allPosts = getAllPosts();
    
      for (const post of allPosts) {
    
        // Ingnore this post if it already
        // contains a favGenresLink
        let colorObj = post.querySelector('a.favGenresLink');
        if (colorObj) continue
    
        const titleElem = getTitle(post)
    
        if (!titleElem) continue
    
        const genresStr = getGenresAsString(titleElem)
        const {bgColor, favGenresStr} = getBGColor(genresStr, favoriteGenres)
    
        if (!bgColor) continue
    
        // Change the post's & its children bg color
        changePostColor(post, bgColor)
    
        // Create the genres link and add it to the post
        const linkElem = createSongLink(titleElem, post, favGenresStr)
        post.insertAdjacentElement('afterbegin', linkElem)
      }
    
    }
    
    새로 추가한 모든 HTML 요소는 이전에 만든 새 컨텐트 탐지기를 트리거하여 동적 컨텐트의 색상을 업데이트합니다.무한 순환 방지 - 새 콘텐츠 탐지기 -> 색상 추가 () -> 유파 링크 만들기 및 추가 -> 새 콘텐츠 탐지기 트리거 - 조건을 추가해야 합니다:
    if (targetElem) {
      observeDOM(targetElem, (addedNodes) => {
        // ignore favGenresLink to avoid an infinite loop
        for (let addedNode of addedNodes) {
          if (addedNode.classList.contains('favGenresLink')) {
            return
          }
        }
    
        // whenever new content is added
        addColorsOnSongs(favoriteGenres);
      });
    }
    

    이게 컬러예요.업데이트된 js 파일을 모두 포함합니다.
    const favoriteGenres = {
      'ambient': '#fa8335',
      'blues': '#0df9f9',
      'country': '#fad337',
      'chill': '#a8f830',
      'funk': '#F2EF0C',
      'jazz': '#fba19d',
      'soul': '#aca2bb',
    }
    
    const getAllPosts = () => {
      // old reddit
      const allPosts = document.getElementsByClassName('thing');
      if (allPosts.length === 0) {
        // new reddit
        return document.getElementsByClassName('scrollerItem');
      }
      return allPosts
    }
    
    const getTitle = (post) => {
      // old reddit
      const titleElem = post.querySelector('a.title');
      // new reddit
      if (!titleElem) {
        return post.querySelector('h3');
      }
      return titleElem
    }
    
    const getGenresAsString = (titleElem) => {
      const text = titleElem.innerText.toLowerCase()
    
      // Extract the genres from the title 
      const genresRegex = /\[([^\]]+)\]/g
      const match = genresRegex.exec(text)
    
      // Skip over posts that are not properly formatted
      if (!match) {
        return null
      }
      return match[0]
    }
    
    
    const getBGColor = (allGenresStr, favGenres) => {
      let bgColor = null
      let favGenresStr = ''
    
      // Test if the post contains any of our fav. genres
      for (const genre of Object.keys(favGenres)) {
        const genreRegex = new RegExp('.*' + genre + '.*', "i")
        if (!genreRegex.test(allGenresStr)) {
          continue
        }
        bgColor = 'background-color: ' + favGenres[genre] + ' !important'
        favGenresStr += genre + ' '
      }
    
      return {bgColor, favGenresStr}
    }
    
    const changePostColor = (post, bgColor) => {
      post.setAttribute('style', bgColor);
      for (let child of post.children) {
        child.setAttribute('style', bgColor);
        for (let child2 of child.children) {
          child2.setAttribute('style', bgColor);
        }
      }
    }
    
    const getSongURL = (titleElem, post) => {
      // old reddit
      let href = titleElem.href
      // new reddit
      if (!href) {
        const extLink = post.querySelector('a.styled-outbound-link')
        if (extLink) {
          return extLink.href
        }
      }
      return href
    }
    
    const createSongLink = (titleElem, post, genresText) => {
      post.style.position = 'relative'
      let linkElem = document.createElement('a')
      linkElem.className = "favGenresLink"
      linkElem.style.position = 'absolute'
      linkElem.style.right = '20px'
      linkElem.style.bottom = '0'
      linkElem.style.height = '50px'
      linkElem.style.color = 'black'
      linkElem.style.fontSize = '50px'
      linkElem.style.zIndex = '999999'
      linkElem.innerText = genresText
      linkElem.href = getSongURL(titleElem, post)
      return linkElem
    }
    
    const addColorsOnSongs = (colorData) => {
      const allPosts = getAllPosts();
    
      for (const post of allPosts) {
    
        // ignore
        let colorObj = post.querySelector('a.favGenresLink');
        if (colorObj) continue //TODO
    
        const titleElem = getTitle(post)
    
        if (!titleElem) continue
    
        const genresStr = getGenresAsString(titleElem)
        const {bgColor, favGenresStr} = getBGColor(genresStr, favoriteGenres)
    
        if (!bgColor) continue
    
        // Change the post's & its children bg color
        changePostColor(post, bgColor)
    
        // Create the genres link and add it to the post
        const linkElem = createSongLink(titleElem, post, favGenresStr)
        post.insertAdjacentElement('afterbegin', linkElem)
      }
    
    }
    
    addColorsOnSongs(favoriteGenres)
    
    
    const observeDOM = (() => {
      const MutationObserver = window.MutationObserver || window.WebKitMutationObserver;
      const eventListenerSupported = window.addEventListener;
    
      return (obj, callback) => {
        if (MutationObserver) {
          const obs = new MutationObserver((mutations, observer) => {
            if (mutations[0].addedNodes.length)
              callback(mutations[0].addedNodes);
          });
          obs.observe(obj, {
            childList: true,
            subtree: true
          });
        } else if (eventListenerSupported) {
          obj.addEventListener('DOMNodeInserted', callback, false);
          obj.addEventListener('DOMNodeRemoved', callback, false);
        }
      };
    
    })();
    
    // detect if on the new Reddit before the content is loaded
    const targetElem = document.getElementById('2x-container')
    if (targetElem) {
      observeDOM(targetElem, (addedNodes) => {
        // ignore favGenresLink to avoid an infinite loop
        for (let addedNode of addedNodes) {
          if (addedNode.classList.contains('favGenresLink')) {
            return
          }
        }
    
        // whenever new content is added
        addColorsOnSongs(favoriteGenres);
      });
    }
    

    사용자 정의 스타일 및 색상


    현재 가장 좋아하는 유형은 코드 형식으로 목록에 저장되어 있다.이 설정을 변경하고 원하는 유형을 정의할 수 있는 설정 페이지를 만듭니다.
    먼저 manifest.json을 업데이트하고 옵션 페이지를 지정해야 합니다.
    ...
      "options_page": "options.html",
      "options_ui": {
        "page": "options.html"
      }
    ...
    
    파일 생성 옵션.html:
    <html>
      <head></head>
      <body>
        <h1>Music Highlight Options</h1>
    
        <div id="root">
          <div id="container">
          </div>
          <button id="add" class="button" type="button" name="button">Add genre</button>
          <hr />
          <div id="buttons">
              <button id="save" class="button" type="button" name="button">Save</button>
              <div id="status"></div>
          </div>
        </div>
    
        <script src="options.js"></script>
      </body>
    </html>
    
    및 를 선택합니다.js...
    const defaultGenres = {
      'ambient': '#fa8335',
      'blues': '#0df9f9',
      'country': '#fad337',
      'chill': '#a8f830',
      'funk': '#F2EF0C',
      'jazz': '#fba19d',
      'soul': '#aca2bb',
    }
    
    const restoreOptions = () => {
      chrome.storage.local.get('colors', (data) => {
        if (!data 
            || Object.keys(data).length === 0 
          || Object.keys(data.colors).length === 0) {
          createColorsUI(defaultGenres);
        } else {
          createColorsUI(data.colors);
        }
      });
    }
    
    document.addEventListener('DOMContentLoaded', restoreOptions);
    
    다음 장르 색상 입력을 만드는 함수를 추가합니다.
    const createColorInput = (genre, color, id) => {
      let genreInputLabel = document.createElement('span')
      genreInputLabel.innerText = 'Genre:'
      genreInputLabel.className = 'genreNameLabel'
      let genreInput = document.createElement('input')
      genreInput.className = 'genreName'
      genreInput.type = 'text'
      genreInput.value = genre
      let colorInputLabel = document.createElement('span')
      colorInputLabel.innerText = 'Color:'
      colorInputLabel.className = 'colorNameLabel'
      let colorInput = document.createElement('input')
      colorInput.className = 'colorName'
      colorInput.type = 'color'
      colorInput.value = color
      let removeButton = document.createElement('button')
      removeButton.innerText = 'Remove'
      removeButton.className = 'removeButton button'
      removeButton.addEventListener('click', ((e) => {
        let tmpElem = document.getElementById(e.target.parentElement.id)
        if (tmpElem && tmpElem.parentElement) {
          tmpElem.parentElement.removeChild(tmpElem)
        }
      }))
    
      let group = document.createElement('div')
      group.id = 'data' + id
      group.className = 'genreColorGroup'
      group.appendChild(genreInputLabel)
      group.appendChild(genreInput)
      group.appendChild(colorInputLabel)
      group.appendChild(colorInput)
      group.appendChild(removeButton)
    
      let container = document.getElementById('container')
      container.appendChild(group)
    }
    
    다음 함수createColorsUI
    const createColorsUI = (data) => {
      let index = 0
      for (let variable in data) {
        if (data.hasOwnProperty(variable)) {
          createColorInput(variable, data[variable], index)
          index++
        }
      }
    }
    
    및 addOption 기능:
    const addOption = () => {
      let index = Math.floor(Math.random() * 1000000)
      createColorInput('misc', '#000000', index)
    }
    
    document.getElementById('add').addEventListener('click', addOption);
    
    변경 사항을 크롬에 저장합니다.저장실.지역:
    const saveOptions = () => {
      let allGenreNames = document.getElementsByClassName('genreName')
      let allColorNames = document.getElementsByClassName('colorName')
    
      let data = {}
    
      for (let i = 0; i < allGenreNames.length; i++) {
        let name = allGenreNames[i].value
        let color = allColorNames[i].value
        data[name] = color
      }
    
      chrome.storage.local.set({
        colors: data
      }, () => {
        let status = document.getElementById('status');
        status.textContent = 'Options saved.';
        setTimeout(() => {
          status.textContent = '';
        }, 2750);
      });
    }
    
    document.getElementById('save').addEventListener('click', saveOptions);
    
    Chrome에서 옵션 페이지를 여는 방법:
  • 도구 모음
  • 에서 확장 버튼 클릭
  • 음악 하이라이트의 더 많은 조작 메뉴 클릭
  • 클릭 옵션

  • Firefox:
  • 도구 모음에서 확장 아이콘
  • 클릭
  • 클릭 관리 확장
  • 기본 설정 메뉴 시작

  • 마지막 부분


    그런 다음 작업을 수행하려면 저장된 옵션을 강조 표시된 코드에 링크해야 합니다.
    열린 색상.js 및 바꾸기:
    addColorsOnSongs(favoriteGenres)
    
    및:
    chrome.storage.local.get('colors', (data) => {
      if (!data || Object.keys(data).length === 0 || Object.keys(data.colors).length === 0) {
          addColorsOnSongs(favoriteGenres);
      } else {
        console.log(data)
          addColorsOnSongs(data.colors);
      }
    });
    
    및 업데이트:
    // detect if on the new Reddit before the content is loaded
    const targetElem = document.getElementById('2x-container')
    if (targetElem) {
      observeDOM(targetElem, (addedNodes) => {
        // ignore favGenresLink to avoid an infinite loop
        for (let addedNode of addedNodes) {
          if (addedNode.classList.contains('favGenresLink')) {
            return
          }
        }
    
        // whenever new content is added
        //addColorsOnSongs(favoriteGenres);
    
        chrome.storage.local.get('colors', (data) => {
          if (!data || Object.keys(data).length === 0 || Object.keys(data.colors).length === 0) {
              addColorsOnSongs(favoriteGenres);
          } else {
            console.log(data)
              addColorsOnSongs(data.colors);
          }
        });
      });
    }
    

    브라우저 작업 및 아이콘 만들기


    도구막대 메뉴의 확장 단추에 아이콘을 추가합니다. (r/ListenToThis 아이콘을 다시 사용합니다.)
      "icons": {
        "48": "icons/logo.png"
      },
      "browser_action": {
        "default_icon": {
          "48": "icons/logo.png"
        },
        "default_title": "Music-Highlight",
        "browser_style": true,
        "default_popup": "action.html"
      }
    
    옵션 페이지에 들어가려면 여러 단계가 필요하므로 옵션 버튼이 있는 메뉴를 만들고, 클릭만 하면 페이지를 열 수 있습니다.
    행동을 창조하다.html:
    <html>
    <body>
      <button id="openOptions">Options...</button>
      <script src="action.js" charset="utf-8"></script>
    </body>
    </html>
    
    그리고 행동.js
    document.getElementById('openOptions').addEventListener('click', (e) => {
      let optionsUrl = chrome.extension.getURL("./options.html");
      chrome.tabs.create({
        url: optionsUrl
      });
    })
    
    현재 확장된 도구막대 아이콘을 누르면 메뉴가 팝업됩니다. 그 중 하나의 단추가 옵션 페이지를 엽니다.


    너는 이곳에서 온전한 원본 코드를 찾을 수 있다: https://github.com/alexadam/ListenToThis-Highlight

    좋은 웹페이지 즐겨찾기