├── .eslintignore ├── .eslintrc.js ├── .github └── workflows │ └── codeql-analysis.yml ├── .gitignore ├── .prettierrc ├── LICENSE ├── README.md ├── docs ├── assets │ ├── css │ │ └── main.css │ ├── images │ │ ├── icons.png │ │ ├── icons@2x.png │ │ ├── widgets.png │ │ └── widgets@2x.png │ └── js │ │ ├── main.js │ │ └── search.js ├── classes │ └── spotify.default.html ├── index.html ├── modules.html └── modules │ ├── index.html │ └── spotify.html ├── package-lock.json ├── package.json ├── src ├── Spotify.ts ├── index.ts ├── lib │ ├── API.ts │ ├── Error.ts │ ├── details │ │ ├── Atrist.ts │ │ ├── Playlist.ts │ │ └── Track.ts │ ├── download.ts │ ├── getYtlink.ts │ └── metadata.ts └── typings │ └── index.d.ts ├── tests └── index.js ├── tsconfig.json └── typedoc.json /.eslintignore: -------------------------------------------------------------------------------- 1 | **/*.js -------------------------------------------------------------------------------- /.eslintrc.js: -------------------------------------------------------------------------------- 1 | module.exports = { 2 | parser: '@typescript-eslint/parser', 3 | extends: [ 4 | 'plugin:@typescript-eslint/recommended', 5 | ], 6 | parserOptions: { 7 | ecmaVersion: 2020, 8 | sourceType: 'module', 9 | }, 10 | rules: { 11 | 12 | }, 13 | } -------------------------------------------------------------------------------- /.github/workflows/codeql-analysis.yml: -------------------------------------------------------------------------------- 1 | # For most projects, this workflow file will not need changing; you simply need 2 | # to commit it to your repository. 3 | # 4 | # You may wish to alter this file to override the set of languages analyzed, 5 | # or to provide custom queries or build logic. 6 | # 7 | # ******** NOTE ******** 8 | # We have attempted to detect the languages in your repository. Please check 9 | # the `language` matrix defined below to confirm you have the correct set of 10 | # supported CodeQL languages. 11 | # 12 | name: "CodeQL" 13 | 14 | on: 15 | push: 16 | branches: [ master ] 17 | pull_request: 18 | # The branches below must be a subset of the branches above 19 | branches: [ master ] 20 | schedule: 21 | - cron: '31 5 * * 5' 22 | 23 | jobs: 24 | analyze: 25 | name: Analyze 26 | runs-on: ubuntu-latest 27 | permissions: 28 | actions: read 29 | contents: read 30 | security-events: write 31 | 32 | strategy: 33 | fail-fast: false 34 | matrix: 35 | language: [ 'javascript' ] 36 | # CodeQL supports [ 'cpp', 'csharp', 'go', 'java', 'javascript', 'python' ] 37 | # Learn more: 38 | # https://docs.github.com/en/free-pro-team@latest/github/finding-security-vulnerabilities-and-errors-in-your-code/configuring-code-scanning#changing-the-languages-that-are-analyzed 39 | 40 | steps: 41 | - name: Checkout repository 42 | uses: actions/checkout@v2 43 | 44 | # Initializes the CodeQL tools for scanning. 45 | - name: Initialize CodeQL 46 | uses: github/codeql-action/init@v1 47 | with: 48 | languages: ${{ matrix.language }} 49 | # If you wish to specify custom queries, you can do so here or in a config file. 50 | # By default, queries listed here will override any specified in a config file. 51 | # Prefix the list here with "+" to use these queries and those in the config file. 52 | # queries: ./path/to/local/query, your-org/your-repo/queries@main 53 | 54 | # Autobuild attempts to build any compiled languages (C/C++, C#, or Java). 55 | # If this step fails, then you should remove it and run the build manually (see below) 56 | - name: Autobuild 57 | uses: github/codeql-action/autobuild@v1 58 | 59 | # ℹ️ Command-line programs to run using the OS shell. 60 | # 📚 https://git.io/JvXDl 61 | 62 | # ✏️ If the Autobuild fails above, remove it and uncomment the following three lines 63 | # and modify them (or add more) to build your code if your project 64 | # uses a compiled language 65 | 66 | #- run: | 67 | # make bootstrap 68 | # make release 69 | 70 | - name: Perform CodeQL Analysis 71 | uses: github/codeql-action/analyze@v1 72 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | node_modules 2 | dist -------------------------------------------------------------------------------- /.prettierrc: -------------------------------------------------------------------------------- 1 | { 2 | "semi": false, 3 | "trailingComma": "none", 4 | "singleQuote": true, 5 | "printWidth": 120, 6 | "tabWidth": 4 7 | } -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2021 Alen Yohannan 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 |
2 | 3 | # Spotifydl-Core 4 | 5 | Never gonna give up, never gonna let you down 6 | 7 | ### A simple package to download music tracks from spotify 🎵 8 |
9 | 10 | ## Installation 11 | 12 | ```sh 13 | > npm i spotifydl-core 14 | ``` 15 | 16 | ## Intialization 17 | 18 | You need to intialize the `Spotify` Class before acessing the methods inside it. 19 | 20 | ```js 21 | const Spotify = require('spotifydl-core').default 22 | //import Spotify from 'spotifydl-core' 23 | 24 | const credentials = { 25 | clientId: 'your-client-id', 26 | clientSecret: 'your-client-secret' 27 | } 28 | const spotify = new Spotify(credentials) 29 | ``` 30 | 31 | ## Methods 32 | > **NOTE: Only some methods are shown here. Checkout the [docs](https://alensaito1.github.io/spotifydl-core/) for a more in-depth documentation** 33 | 34 | **Get Track ⏭️** 35 | ```JS 36 | await spotify.getTrack(track_url) 37 | 38 | // For Example: track_url = 'https://open.spotify.com/track/1Ub6VfiTXgyV8HnsfzrZzC?si=4412ef4ebd8141ab' 39 | 40 | // Input: url of the track, Type: string 41 | ``` 42 | **Download Track/Song ⬇️** 43 | ```JS 44 | await spotify.downloadTrack(track_url, file_name) 45 | 46 | // For Example: track_url = 'https://open.spotify.com/track/1Ub6VfiTXgyV8HnsfzrZzC?si=4412ef4ebd8141ab' & file_name = 'song.mp3' 47 | 48 | // Input: url of the track and name of the filename, Both Type: string 49 | 50 | // It'll return buffer (promise) if you don't provide any filename 51 | 52 | ``` 53 | 54 | **Get Artist 👩‍🎤🧑‍🎤** 55 | ```JS 56 | await spotify.getArtist(artist_url) 57 | 58 | // For Example: artist_url = 'https://open.spotify.com/artist/3B9O5mYYw89fFXkwKh7jCS' 59 | 60 | // Input: url of the artist, Type: string 61 | ``` 62 | 63 | **Get Album 💽** 64 | ```JS 65 | await spotify.getAlbum(album_url) 66 | 67 | // For Example: album_url = 'https://open.spotify.com/album/3u3WsbVPLT0fXiClx9GYD9?si=pfGAdL3VRiid0M3Ln_0DNg' 68 | 69 | // Input: url of the album, Type: string 70 | ``` 71 | 72 | **Get Playlist 🎧** 73 | 74 | ```JS 75 | await spotify.getPlylist(playlist_url) 76 | 77 | // Input: url of the playlist, Type: string 78 | ``` 79 | 80 | **Download an Entire playlist** 81 | 82 | ```JS 83 | await spotify.downloadPlaylist(playlist_url) 84 | 85 | //It'll return an array containing the Buffer of the songs in the playlist 86 | ``` 87 | 88 | ## Usage Example 89 | ```JS 90 | const fs = require('fs-extra') 91 | // Initialization and Authentication 92 | const Spotify = require('spotifydl-core').default // Import the library 93 | const spotify = new Spotify({ // Authentication 94 | clientId: 'acc6302297e040aeb6e4ac1fbdfd62c3', // <-- add your own clientId 95 | clientSecret: '0e8439a1280a43aba9a5bc0a16f3f009', // <-- add your own clientSecret 96 | }) 97 | /* To learn more about clientId and Secret , 98 | visit https://developer.spotify.com/documentation/general/guides/app-settings/ 99 | */ 100 | 101 | // Declaring the respective url in 'links' object 102 | const links = { 103 | artist: 'https://open.spotify.com/artist/7ky9g1jEjCsjNjZbYuflUJ?si=2To3fmc-T9KuyyrQ-Qp5KQ', // Url of the artist you want to gather info about 104 | album: 'https://open.spotify.com/album/3u3WsbVPLT0fXiClx9GYD9?si=pfGAdL3VRiid0M3Ln_0DNg', // Url of the album you want to gather info about 105 | song: 'https://open.spotify.com/track/1Ub6VfiTXgyV8HnsfzrZzC?si=4412ef4ebd8141ab' // Url of the song you want to gather info about or download 106 | }; 107 | 108 | // Engine 109 | (async () => { 110 | const data = await spotify.getTrack(links.song) // Waiting for the data 🥱 111 | console.log('Downloading: ', data.name, 'by:', data.artists.join(' ')) // Keep an eye on the progress 112 | const song = await spotify.downloadTrack(links.song) // Downloading goes brr brr 113 | fs.writeFileSync('song.mp3', song) // Let's write the buffer to the woofer (i mean file, hehehe) 114 | })() 115 | 116 | //spotify.verifyCredentials().then(() => Promise.all([spotify.getTrack(links.song), spotify.getAlbum(links.album), spotify.getArtistAlbums(links.artist)]).then(console.log)) 117 | ``` 118 | 119 | # 🙇‍ Special Thanks 120 | 121 | - Swapnil Soni: [Spotify-dl](https://github.com/SwapnilSoni1999/spotify-dl) 122 | - Fent: [Ytdl-core](https://github.com/fent/node-ytdl-core) 123 | -------------------------------------------------------------------------------- /docs/assets/css/main.css: -------------------------------------------------------------------------------- 1 | :root { 2 | --color-background: #fdfdfd; 3 | --color-text: #222; 4 | --color-text-aside: #707070; 5 | --color-link: #4da6ff; 6 | --color-menu-divider: #eee; 7 | --color-menu-divider-focus: #000; 8 | --color-menu-label: #707070; 9 | --color-panel: #fff; 10 | --color-panel-divider: #eee; 11 | --color-comment-tag: #707070; 12 | --color-comment-tag-text: #fff; 13 | --color-code-background: rgba(0, 0, 0, 0.04); 14 | --color-ts: #9600ff; 15 | --color-ts-interface: #647f1b; 16 | --color-ts-enum: #937210; 17 | --color-ts-class: #0672de; 18 | --color-ts-private: #707070; 19 | --color-toolbar: #fff; 20 | --color-toolbar-text: #333; 21 | } 22 | 23 | /*! normalize.css v1.1.3 | MIT License | git.io/normalize */ 24 | /* ========================================================================== 25 | * * HTML5 display definitions 26 | * * ========================================================================== */ 27 | /** 28 | * * Correct `block` display not defined in IE 6/7/8/9 and Firefox 3. */ 29 | article, aside, details, figcaption, figure, footer, header, hgroup, main, nav, section, summary { 30 | display: block; 31 | } 32 | 33 | /** 34 | * * Correct `inline-block` display not defined in IE 6/7/8/9 and Firefox 3. */ 35 | audio, canvas, video { 36 | display: inline-block; 37 | *display: inline; 38 | *zoom: 1; 39 | } 40 | 41 | /** 42 | * * Prevent modern browsers from displaying `audio` without controls. 43 | * * Remove excess height in iOS 5 devices. */ 44 | audio:not([controls]) { 45 | display: none; 46 | height: 0; 47 | } 48 | 49 | /** 50 | * * Address styling not present in IE 7/8/9, Firefox 3, and Safari 4. 51 | * * Known issue: no IE 6 support. */ 52 | [hidden] { 53 | display: none; 54 | } 55 | 56 | /* ========================================================================== 57 | * * Base 58 | * * ========================================================================== */ 59 | /** 60 | * * 1. Correct text resizing oddly in IE 6/7 when body `font-size` is set using 61 | * * `em` units. 62 | * * 2. Prevent iOS text size adjust after orientation change, without disabling 63 | * * user zoom. */ 64 | html { 65 | font-size: 100%; 66 | /* 1 */ 67 | -ms-text-size-adjust: 100%; 68 | /* 2 */ 69 | -webkit-text-size-adjust: 100%; 70 | /* 2 */ 71 | font-family: sans-serif; 72 | } 73 | 74 | /** 75 | * * Address `font-family` inconsistency between `textarea` and other form 76 | * * elements. */ 77 | button, input, select, textarea { 78 | font-family: sans-serif; 79 | } 80 | 81 | /** 82 | * * Address margins handled incorrectly in IE 6/7. */ 83 | body { 84 | margin: 0; 85 | } 86 | 87 | /* ========================================================================== 88 | * * Links 89 | * * ========================================================================== */ 90 | /** 91 | * * Address `outline` inconsistency between Chrome and other browsers. */ 92 | a:focus { 93 | outline: thin dotted; 94 | } 95 | a:active, a:hover { 96 | outline: 0; 97 | } 98 | 99 | /** 100 | * * Improve readability when focused and also mouse hovered in all browsers. */ 101 | /* ========================================================================== 102 | * * Typography 103 | * * ========================================================================== */ 104 | /** 105 | * * Address font sizes and margins set differently in IE 6/7. 106 | * * Address font sizes within `section` and `article` in Firefox 4+, Safari 5, 107 | * * and Chrome. */ 108 | h1 { 109 | font-size: 2em; 110 | margin: 0.67em 0; 111 | } 112 | 113 | h2 { 114 | font-size: 1.5em; 115 | margin: 0.83em 0; 116 | } 117 | 118 | h3 { 119 | font-size: 1.17em; 120 | margin: 1em 0; 121 | } 122 | 123 | h4, .tsd-index-panel h3 { 124 | font-size: 1em; 125 | margin: 1.33em 0; 126 | } 127 | 128 | h5 { 129 | font-size: 0.83em; 130 | margin: 1.67em 0; 131 | } 132 | 133 | h6 { 134 | font-size: 0.67em; 135 | margin: 2.33em 0; 136 | } 137 | 138 | /** 139 | * * Address styling not present in IE 7/8/9, Safari 5, and Chrome. */ 140 | abbr[title] { 141 | border-bottom: 1px dotted; 142 | } 143 | 144 | /** 145 | * * Address style set to `bolder` in Firefox 3+, Safari 4/5, and Chrome. */ 146 | b, strong { 147 | font-weight: bold; 148 | } 149 | 150 | blockquote { 151 | margin: 1em 40px; 152 | } 153 | 154 | /** 155 | * * Address styling not present in Safari 5 and Chrome. */ 156 | dfn { 157 | font-style: italic; 158 | } 159 | 160 | /** 161 | * * Address differences between Firefox and other browsers. 162 | * * Known issue: no IE 6/7 normalization. */ 163 | hr { 164 | -moz-box-sizing: content-box; 165 | box-sizing: content-box; 166 | height: 0; 167 | } 168 | 169 | /** 170 | * * Address styling not present in IE 6/7/8/9. */ 171 | mark { 172 | background: #ff0; 173 | color: #000; 174 | } 175 | 176 | /** 177 | * * Address margins set differently in IE 6/7. */ 178 | p, pre { 179 | margin: 1em 0; 180 | } 181 | 182 | /** 183 | * * Correct font family set oddly in IE 6, Safari 4/5, and Chrome. */ 184 | code, kbd, pre, samp { 185 | font-family: monospace, serif; 186 | _font-family: "courier new", monospace; 187 | font-size: 1em; 188 | } 189 | 190 | /** 191 | * * Improve readability of pre-formatted text in all browsers. */ 192 | pre { 193 | white-space: pre; 194 | white-space: pre-wrap; 195 | word-wrap: break-word; 196 | } 197 | 198 | /** 199 | * * Address CSS quotes not supported in IE 6/7. */ 200 | q { 201 | quotes: none; 202 | } 203 | q:before, q:after { 204 | content: ""; 205 | content: none; 206 | } 207 | 208 | /** 209 | * * Address `quotes` property not supported in Safari 4. */ 210 | /** 211 | * * Address inconsistent and variable font size in all browsers. */ 212 | small { 213 | font-size: 80%; 214 | } 215 | 216 | /** 217 | * * Prevent `sub` and `sup` affecting `line-height` in all browsers. */ 218 | sub { 219 | font-size: 75%; 220 | line-height: 0; 221 | position: relative; 222 | vertical-align: baseline; 223 | } 224 | 225 | sup { 226 | font-size: 75%; 227 | line-height: 0; 228 | position: relative; 229 | vertical-align: baseline; 230 | top: -0.5em; 231 | } 232 | 233 | sub { 234 | bottom: -0.25em; 235 | } 236 | 237 | /* ========================================================================== 238 | * * Lists 239 | * * ========================================================================== */ 240 | /** 241 | * * Address margins set differently in IE 6/7. */ 242 | dl, menu, ol, ul { 243 | margin: 1em 0; 244 | } 245 | 246 | dd { 247 | margin: 0 0 0 40px; 248 | } 249 | 250 | /** 251 | * * Address paddings set differently in IE 6/7. */ 252 | menu, ol, ul { 253 | padding: 0 0 0 40px; 254 | } 255 | 256 | /** 257 | * * Correct list images handled incorrectly in IE 7. */ 258 | nav ul, nav ol { 259 | list-style: none; 260 | list-style-image: none; 261 | } 262 | 263 | /* ========================================================================== 264 | * * Embedded content 265 | * * ========================================================================== */ 266 | /** 267 | * * 1. Remove border when inside `a` element in IE 6/7/8/9 and Firefox 3. 268 | * * 2. Improve image quality when scaled in IE 7. */ 269 | img { 270 | border: 0; 271 | /* 1 */ 272 | -ms-interpolation-mode: bicubic; 273 | } 274 | 275 | /* 2 */ 276 | /** 277 | * * Correct overflow displayed oddly in IE 9. */ 278 | svg:not(:root) { 279 | overflow: hidden; 280 | } 281 | 282 | /* ========================================================================== 283 | * * Figures 284 | * * ========================================================================== */ 285 | /** 286 | * * Address margin not present in IE 6/7/8/9, Safari 5, and Opera 11. */ 287 | figure, form { 288 | margin: 0; 289 | } 290 | 291 | /* ========================================================================== 292 | * * Forms 293 | * * ========================================================================== */ 294 | /** 295 | * * Correct margin displayed oddly in IE 6/7. */ 296 | /** 297 | * * Define consistent border, margin, and padding. */ 298 | fieldset { 299 | border: 1px solid #c0c0c0; 300 | margin: 0 2px; 301 | padding: 0.35em 0.625em 0.75em; 302 | } 303 | 304 | /** 305 | * * 1. Correct color not being inherited in IE 6/7/8/9. 306 | * * 2. Correct text not wrapping in Firefox 3. 307 | * * 3. Correct alignment displayed oddly in IE 6/7. */ 308 | legend { 309 | border: 0; 310 | /* 1 */ 311 | padding: 0; 312 | white-space: normal; 313 | /* 2 */ 314 | *margin-left: -7px; 315 | } 316 | 317 | /* 3 */ 318 | /** 319 | * * 1. Correct font size not being inherited in all browsers. 320 | * * 2. Address margins set differently in IE 6/7, Firefox 3+, Safari 5, 321 | * * and Chrome. 322 | * * 3. Improve appearance and consistency in all browsers. */ 323 | button, input, select, textarea { 324 | font-size: 100%; 325 | /* 1 */ 326 | margin: 0; 327 | /* 2 */ 328 | vertical-align: baseline; 329 | /* 3 */ 330 | *vertical-align: middle; 331 | } 332 | 333 | /* 3 */ 334 | /** 335 | * * Address Firefox 3+ setting `line-height` on `input` using `!important` in 336 | * * the UA stylesheet. */ 337 | button, input { 338 | line-height: normal; 339 | } 340 | 341 | /** 342 | * * Address inconsistent `text-transform` inheritance for `button` and `select`. 343 | * * All other form control elements do not inherit `text-transform` values. 344 | * * Correct `button` style inheritance in Chrome, Safari 5+, and IE 6+. 345 | * * Correct `select` style inheritance in Firefox 4+ and Opera. */ 346 | button, select { 347 | text-transform: none; 348 | } 349 | 350 | /** 351 | * * 1. Avoid the WebKit bug in Android 4.0.* where (2) destroys native `audio` 352 | * * and `video` controls. 353 | * * 2. Correct inability to style clickable `input` types in iOS. 354 | * * 3. Improve usability and consistency of cursor style between image-type 355 | * * `input` and others. 356 | * * 4. Remove inner spacing in IE 7 without affecting normal text inputs. 357 | * * Known issue: inner spacing remains in IE 6. */ 358 | button, html input[type=button] { 359 | -webkit-appearance: button; 360 | /* 2 */ 361 | cursor: pointer; 362 | /* 3 */ 363 | *overflow: visible; 364 | } 365 | 366 | /* 4 */ 367 | input[type=reset], input[type=submit] { 368 | -webkit-appearance: button; 369 | /* 2 */ 370 | cursor: pointer; 371 | /* 3 */ 372 | *overflow: visible; 373 | } 374 | 375 | /* 4 */ 376 | /** 377 | * * Re-set default cursor for disabled elements. */ 378 | button[disabled], html input[disabled] { 379 | cursor: default; 380 | } 381 | 382 | /** 383 | * * 1. Address box sizing set to content-box in IE 8/9. 384 | * * 2. Remove excess padding in IE 8/9. 385 | * * 3. Remove excess padding in IE 7. 386 | * * Known issue: excess padding remains in IE 6. */ 387 | input { 388 | /* 3 */ 389 | } 390 | input[type=checkbox], input[type=radio] { 391 | box-sizing: border-box; 392 | /* 1 */ 393 | padding: 0; 394 | /* 2 */ 395 | *height: 13px; 396 | /* 3 */ 397 | *width: 13px; 398 | } 399 | input[type=search] { 400 | -webkit-appearance: textfield; 401 | /* 1 */ 402 | -moz-box-sizing: content-box; 403 | -webkit-box-sizing: content-box; 404 | /* 2 */ 405 | box-sizing: content-box; 406 | } 407 | input[type=search]::-webkit-search-cancel-button, input[type=search]::-webkit-search-decoration { 408 | -webkit-appearance: none; 409 | } 410 | 411 | /** 412 | * * 1. Address `appearance` set to `searchfield` in Safari 5 and Chrome. 413 | * * 2. Address `box-sizing` set to `border-box` in Safari 5 and Chrome 414 | * * (include `-moz` to future-proof). */ 415 | /** 416 | * * Remove inner padding and search cancel button in Safari 5 and Chrome 417 | * * on OS X. */ 418 | /** 419 | * * Remove inner padding and border in Firefox 3+. */ 420 | button::-moz-focus-inner, input::-moz-focus-inner { 421 | border: 0; 422 | padding: 0; 423 | } 424 | 425 | /** 426 | * * 1. Remove default vertical scrollbar in IE 6/7/8/9. 427 | * * 2. Improve readability and alignment in all browsers. */ 428 | textarea { 429 | overflow: auto; 430 | /* 1 */ 431 | vertical-align: top; 432 | } 433 | 434 | /* 2 */ 435 | /* ========================================================================== 436 | * * Tables 437 | * * ========================================================================== */ 438 | /** 439 | * * Remove most spacing between table cells. */ 440 | table { 441 | border-collapse: collapse; 442 | border-spacing: 0; 443 | } 444 | 445 | ul.tsd-descriptions > li > :first-child, .tsd-panel > :first-child, .col > :first-child, .col-11 > :first-child, .col-10 > :first-child, .col-9 > :first-child, .col-8 > :first-child, .col-7 > :first-child, .col-6 > :first-child, .col-5 > :first-child, .col-4 > :first-child, .col-3 > :first-child, .col-2 > :first-child, .col-1 > :first-child, 446 | ul.tsd-descriptions > li > :first-child > :first-child, 447 | .tsd-panel > :first-child > :first-child, 448 | .col > :first-child > :first-child, 449 | .col-11 > :first-child > :first-child, 450 | .col-10 > :first-child > :first-child, 451 | .col-9 > :first-child > :first-child, 452 | .col-8 > :first-child > :first-child, 453 | .col-7 > :first-child > :first-child, 454 | .col-6 > :first-child > :first-child, 455 | .col-5 > :first-child > :first-child, 456 | .col-4 > :first-child > :first-child, 457 | .col-3 > :first-child > :first-child, 458 | .col-2 > :first-child > :first-child, 459 | .col-1 > :first-child > :first-child, 460 | ul.tsd-descriptions > li > :first-child > :first-child > :first-child, 461 | .tsd-panel > :first-child > :first-child > :first-child, 462 | .col > :first-child > :first-child > :first-child, 463 | .col-11 > :first-child > :first-child > :first-child, 464 | .col-10 > :first-child > :first-child > :first-child, 465 | .col-9 > :first-child > :first-child > :first-child, 466 | .col-8 > :first-child > :first-child > :first-child, 467 | .col-7 > :first-child > :first-child > :first-child, 468 | .col-6 > :first-child > :first-child > :first-child, 469 | .col-5 > :first-child > :first-child > :first-child, 470 | .col-4 > :first-child > :first-child > :first-child, 471 | .col-3 > :first-child > :first-child > :first-child, 472 | .col-2 > :first-child > :first-child > :first-child, 473 | .col-1 > :first-child > :first-child > :first-child { 474 | margin-top: 0; 475 | } 476 | ul.tsd-descriptions > li > :last-child, .tsd-panel > :last-child, .col > :last-child, .col-11 > :last-child, .col-10 > :last-child, .col-9 > :last-child, .col-8 > :last-child, .col-7 > :last-child, .col-6 > :last-child, .col-5 > :last-child, .col-4 > :last-child, .col-3 > :last-child, .col-2 > :last-child, .col-1 > :last-child, 477 | ul.tsd-descriptions > li > :last-child > :last-child, 478 | .tsd-panel > :last-child > :last-child, 479 | .col > :last-child > :last-child, 480 | .col-11 > :last-child > :last-child, 481 | .col-10 > :last-child > :last-child, 482 | .col-9 > :last-child > :last-child, 483 | .col-8 > :last-child > :last-child, 484 | .col-7 > :last-child > :last-child, 485 | .col-6 > :last-child > :last-child, 486 | .col-5 > :last-child > :last-child, 487 | .col-4 > :last-child > :last-child, 488 | .col-3 > :last-child > :last-child, 489 | .col-2 > :last-child > :last-child, 490 | .col-1 > :last-child > :last-child, 491 | ul.tsd-descriptions > li > :last-child > :last-child > :last-child, 492 | .tsd-panel > :last-child > :last-child > :last-child, 493 | .col > :last-child > :last-child > :last-child, 494 | .col-11 > :last-child > :last-child > :last-child, 495 | .col-10 > :last-child > :last-child > :last-child, 496 | .col-9 > :last-child > :last-child > :last-child, 497 | .col-8 > :last-child > :last-child > :last-child, 498 | .col-7 > :last-child > :last-child > :last-child, 499 | .col-6 > :last-child > :last-child > :last-child, 500 | .col-5 > :last-child > :last-child > :last-child, 501 | .col-4 > :last-child > :last-child > :last-child, 502 | .col-3 > :last-child > :last-child > :last-child, 503 | .col-2 > :last-child > :last-child > :last-child, 504 | .col-1 > :last-child > :last-child > :last-child { 505 | margin-bottom: 0; 506 | } 507 | 508 | .container { 509 | max-width: 1200px; 510 | margin: 0 auto; 511 | padding: 0 40px; 512 | } 513 | @media (max-width: 640px) { 514 | .container { 515 | padding: 0 20px; 516 | } 517 | } 518 | 519 | .container-main { 520 | padding-bottom: 200px; 521 | } 522 | 523 | .row { 524 | display: flex; 525 | position: relative; 526 | margin: 0 -10px; 527 | } 528 | .row:after { 529 | visibility: hidden; 530 | display: block; 531 | content: ""; 532 | clear: both; 533 | height: 0; 534 | } 535 | 536 | .col, .col-11, .col-10, .col-9, .col-8, .col-7, .col-6, .col-5, .col-4, .col-3, .col-2, .col-1 { 537 | box-sizing: border-box; 538 | float: left; 539 | padding: 0 10px; 540 | } 541 | 542 | .col-1 { 543 | width: 8.3333333333%; 544 | } 545 | 546 | .offset-1 { 547 | margin-left: 8.3333333333%; 548 | } 549 | 550 | .col-2 { 551 | width: 16.6666666667%; 552 | } 553 | 554 | .offset-2 { 555 | margin-left: 16.6666666667%; 556 | } 557 | 558 | .col-3 { 559 | width: 25%; 560 | } 561 | 562 | .offset-3 { 563 | margin-left: 25%; 564 | } 565 | 566 | .col-4 { 567 | width: 33.3333333333%; 568 | } 569 | 570 | .offset-4 { 571 | margin-left: 33.3333333333%; 572 | } 573 | 574 | .col-5 { 575 | width: 41.6666666667%; 576 | } 577 | 578 | .offset-5 { 579 | margin-left: 41.6666666667%; 580 | } 581 | 582 | .col-6 { 583 | width: 50%; 584 | } 585 | 586 | .offset-6 { 587 | margin-left: 50%; 588 | } 589 | 590 | .col-7 { 591 | width: 58.3333333333%; 592 | } 593 | 594 | .offset-7 { 595 | margin-left: 58.3333333333%; 596 | } 597 | 598 | .col-8 { 599 | width: 66.6666666667%; 600 | } 601 | 602 | .offset-8 { 603 | margin-left: 66.6666666667%; 604 | } 605 | 606 | .col-9 { 607 | width: 75%; 608 | } 609 | 610 | .offset-9 { 611 | margin-left: 75%; 612 | } 613 | 614 | .col-10 { 615 | width: 83.3333333333%; 616 | } 617 | 618 | .offset-10 { 619 | margin-left: 83.3333333333%; 620 | } 621 | 622 | .col-11 { 623 | width: 91.6666666667%; 624 | } 625 | 626 | .offset-11 { 627 | margin-left: 91.6666666667%; 628 | } 629 | 630 | .tsd-kind-icon { 631 | display: block; 632 | position: relative; 633 | padding-left: 20px; 634 | text-indent: -20px; 635 | } 636 | .tsd-kind-icon:before { 637 | content: ""; 638 | display: inline-block; 639 | vertical-align: middle; 640 | width: 17px; 641 | height: 17px; 642 | margin: 0 3px 2px 0; 643 | background-image: url(../images/icons.png); 644 | } 645 | @media (-webkit-min-device-pixel-ratio: 1.5), (min-resolution: 144dpi) { 646 | .tsd-kind-icon:before { 647 | background-image: url(../images/icons@2x.png); 648 | background-size: 238px 204px; 649 | } 650 | } 651 | 652 | .tsd-signature.tsd-kind-icon:before { 653 | background-position: 0 -153px; 654 | } 655 | 656 | .tsd-kind-object-literal > .tsd-kind-icon:before { 657 | background-position: 0px -17px; 658 | } 659 | .tsd-kind-object-literal.tsd-is-protected > .tsd-kind-icon:before { 660 | background-position: -17px -17px; 661 | } 662 | .tsd-kind-object-literal.tsd-is-private > .tsd-kind-icon:before { 663 | background-position: -34px -17px; 664 | } 665 | 666 | .tsd-kind-class > .tsd-kind-icon:before { 667 | background-position: 0px -34px; 668 | } 669 | .tsd-kind-class.tsd-is-protected > .tsd-kind-icon:before { 670 | background-position: -17px -34px; 671 | } 672 | .tsd-kind-class.tsd-is-private > .tsd-kind-icon:before { 673 | background-position: -34px -34px; 674 | } 675 | 676 | .tsd-kind-class.tsd-has-type-parameter > .tsd-kind-icon:before { 677 | background-position: 0px -51px; 678 | } 679 | .tsd-kind-class.tsd-has-type-parameter.tsd-is-protected > .tsd-kind-icon:before { 680 | background-position: -17px -51px; 681 | } 682 | .tsd-kind-class.tsd-has-type-parameter.tsd-is-private > .tsd-kind-icon:before { 683 | background-position: -34px -51px; 684 | } 685 | 686 | .tsd-kind-interface > .tsd-kind-icon:before { 687 | background-position: 0px -68px; 688 | } 689 | .tsd-kind-interface.tsd-is-protected > .tsd-kind-icon:before { 690 | background-position: -17px -68px; 691 | } 692 | .tsd-kind-interface.tsd-is-private > .tsd-kind-icon:before { 693 | background-position: -34px -68px; 694 | } 695 | 696 | .tsd-kind-interface.tsd-has-type-parameter > .tsd-kind-icon:before { 697 | background-position: 0px -85px; 698 | } 699 | .tsd-kind-interface.tsd-has-type-parameter.tsd-is-protected > .tsd-kind-icon:before { 700 | background-position: -17px -85px; 701 | } 702 | .tsd-kind-interface.tsd-has-type-parameter.tsd-is-private > .tsd-kind-icon:before { 703 | background-position: -34px -85px; 704 | } 705 | 706 | .tsd-kind-namespace > .tsd-kind-icon:before { 707 | background-position: 0px -102px; 708 | } 709 | .tsd-kind-namespace.tsd-is-protected > .tsd-kind-icon:before { 710 | background-position: -17px -102px; 711 | } 712 | .tsd-kind-namespace.tsd-is-private > .tsd-kind-icon:before { 713 | background-position: -34px -102px; 714 | } 715 | 716 | .tsd-kind-module > .tsd-kind-icon:before { 717 | background-position: 0px -102px; 718 | } 719 | .tsd-kind-module.tsd-is-protected > .tsd-kind-icon:before { 720 | background-position: -17px -102px; 721 | } 722 | .tsd-kind-module.tsd-is-private > .tsd-kind-icon:before { 723 | background-position: -34px -102px; 724 | } 725 | 726 | .tsd-kind-enum > .tsd-kind-icon:before { 727 | background-position: 0px -119px; 728 | } 729 | .tsd-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 730 | background-position: -17px -119px; 731 | } 732 | .tsd-kind-enum.tsd-is-private > .tsd-kind-icon:before { 733 | background-position: -34px -119px; 734 | } 735 | 736 | .tsd-kind-enum-member > .tsd-kind-icon:before { 737 | background-position: 0px -136px; 738 | } 739 | .tsd-kind-enum-member.tsd-is-protected > .tsd-kind-icon:before { 740 | background-position: -17px -136px; 741 | } 742 | .tsd-kind-enum-member.tsd-is-private > .tsd-kind-icon:before { 743 | background-position: -34px -136px; 744 | } 745 | 746 | .tsd-kind-signature > .tsd-kind-icon:before { 747 | background-position: 0px -153px; 748 | } 749 | .tsd-kind-signature.tsd-is-protected > .tsd-kind-icon:before { 750 | background-position: -17px -153px; 751 | } 752 | .tsd-kind-signature.tsd-is-private > .tsd-kind-icon:before { 753 | background-position: -34px -153px; 754 | } 755 | 756 | .tsd-kind-type-alias > .tsd-kind-icon:before { 757 | background-position: 0px -170px; 758 | } 759 | .tsd-kind-type-alias.tsd-is-protected > .tsd-kind-icon:before { 760 | background-position: -17px -170px; 761 | } 762 | .tsd-kind-type-alias.tsd-is-private > .tsd-kind-icon:before { 763 | background-position: -34px -170px; 764 | } 765 | 766 | .tsd-kind-type-alias.tsd-has-type-parameter > .tsd-kind-icon:before { 767 | background-position: 0px -187px; 768 | } 769 | .tsd-kind-type-alias.tsd-has-type-parameter.tsd-is-protected > .tsd-kind-icon:before { 770 | background-position: -17px -187px; 771 | } 772 | .tsd-kind-type-alias.tsd-has-type-parameter.tsd-is-private > .tsd-kind-icon:before { 773 | background-position: -34px -187px; 774 | } 775 | 776 | .tsd-kind-variable > .tsd-kind-icon:before { 777 | background-position: -136px -0px; 778 | } 779 | .tsd-kind-variable.tsd-is-protected > .tsd-kind-icon:before { 780 | background-position: -153px -0px; 781 | } 782 | .tsd-kind-variable.tsd-is-private > .tsd-kind-icon:before { 783 | background-position: -119px -0px; 784 | } 785 | .tsd-kind-variable.tsd-parent-kind-class > .tsd-kind-icon:before { 786 | background-position: -51px -0px; 787 | } 788 | .tsd-kind-variable.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 789 | background-position: -68px -0px; 790 | } 791 | .tsd-kind-variable.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 792 | background-position: -85px -0px; 793 | } 794 | .tsd-kind-variable.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 795 | background-position: -102px -0px; 796 | } 797 | .tsd-kind-variable.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 798 | background-position: -119px -0px; 799 | } 800 | .tsd-kind-variable.tsd-parent-kind-enum > .tsd-kind-icon:before { 801 | background-position: -170px -0px; 802 | } 803 | .tsd-kind-variable.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 804 | background-position: -187px -0px; 805 | } 806 | .tsd-kind-variable.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 807 | background-position: -119px -0px; 808 | } 809 | .tsd-kind-variable.tsd-parent-kind-interface > .tsd-kind-icon:before { 810 | background-position: -204px -0px; 811 | } 812 | .tsd-kind-variable.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 813 | background-position: -221px -0px; 814 | } 815 | 816 | .tsd-kind-property > .tsd-kind-icon:before { 817 | background-position: -136px -0px; 818 | } 819 | .tsd-kind-property.tsd-is-protected > .tsd-kind-icon:before { 820 | background-position: -153px -0px; 821 | } 822 | .tsd-kind-property.tsd-is-private > .tsd-kind-icon:before { 823 | background-position: -119px -0px; 824 | } 825 | .tsd-kind-property.tsd-parent-kind-class > .tsd-kind-icon:before { 826 | background-position: -51px -0px; 827 | } 828 | .tsd-kind-property.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 829 | background-position: -68px -0px; 830 | } 831 | .tsd-kind-property.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 832 | background-position: -85px -0px; 833 | } 834 | .tsd-kind-property.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 835 | background-position: -102px -0px; 836 | } 837 | .tsd-kind-property.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 838 | background-position: -119px -0px; 839 | } 840 | .tsd-kind-property.tsd-parent-kind-enum > .tsd-kind-icon:before { 841 | background-position: -170px -0px; 842 | } 843 | .tsd-kind-property.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 844 | background-position: -187px -0px; 845 | } 846 | .tsd-kind-property.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 847 | background-position: -119px -0px; 848 | } 849 | .tsd-kind-property.tsd-parent-kind-interface > .tsd-kind-icon:before { 850 | background-position: -204px -0px; 851 | } 852 | .tsd-kind-property.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 853 | background-position: -221px -0px; 854 | } 855 | 856 | .tsd-kind-get-signature > .tsd-kind-icon:before { 857 | background-position: -136px -17px; 858 | } 859 | .tsd-kind-get-signature.tsd-is-protected > .tsd-kind-icon:before { 860 | background-position: -153px -17px; 861 | } 862 | .tsd-kind-get-signature.tsd-is-private > .tsd-kind-icon:before { 863 | background-position: -119px -17px; 864 | } 865 | .tsd-kind-get-signature.tsd-parent-kind-class > .tsd-kind-icon:before { 866 | background-position: -51px -17px; 867 | } 868 | .tsd-kind-get-signature.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 869 | background-position: -68px -17px; 870 | } 871 | .tsd-kind-get-signature.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 872 | background-position: -85px -17px; 873 | } 874 | .tsd-kind-get-signature.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 875 | background-position: -102px -17px; 876 | } 877 | .tsd-kind-get-signature.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 878 | background-position: -119px -17px; 879 | } 880 | .tsd-kind-get-signature.tsd-parent-kind-enum > .tsd-kind-icon:before { 881 | background-position: -170px -17px; 882 | } 883 | .tsd-kind-get-signature.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 884 | background-position: -187px -17px; 885 | } 886 | .tsd-kind-get-signature.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 887 | background-position: -119px -17px; 888 | } 889 | .tsd-kind-get-signature.tsd-parent-kind-interface > .tsd-kind-icon:before { 890 | background-position: -204px -17px; 891 | } 892 | .tsd-kind-get-signature.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 893 | background-position: -221px -17px; 894 | } 895 | 896 | .tsd-kind-set-signature > .tsd-kind-icon:before { 897 | background-position: -136px -34px; 898 | } 899 | .tsd-kind-set-signature.tsd-is-protected > .tsd-kind-icon:before { 900 | background-position: -153px -34px; 901 | } 902 | .tsd-kind-set-signature.tsd-is-private > .tsd-kind-icon:before { 903 | background-position: -119px -34px; 904 | } 905 | .tsd-kind-set-signature.tsd-parent-kind-class > .tsd-kind-icon:before { 906 | background-position: -51px -34px; 907 | } 908 | .tsd-kind-set-signature.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 909 | background-position: -68px -34px; 910 | } 911 | .tsd-kind-set-signature.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 912 | background-position: -85px -34px; 913 | } 914 | .tsd-kind-set-signature.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 915 | background-position: -102px -34px; 916 | } 917 | .tsd-kind-set-signature.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 918 | background-position: -119px -34px; 919 | } 920 | .tsd-kind-set-signature.tsd-parent-kind-enum > .tsd-kind-icon:before { 921 | background-position: -170px -34px; 922 | } 923 | .tsd-kind-set-signature.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 924 | background-position: -187px -34px; 925 | } 926 | .tsd-kind-set-signature.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 927 | background-position: -119px -34px; 928 | } 929 | .tsd-kind-set-signature.tsd-parent-kind-interface > .tsd-kind-icon:before { 930 | background-position: -204px -34px; 931 | } 932 | .tsd-kind-set-signature.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 933 | background-position: -221px -34px; 934 | } 935 | 936 | .tsd-kind-accessor > .tsd-kind-icon:before { 937 | background-position: -136px -51px; 938 | } 939 | .tsd-kind-accessor.tsd-is-protected > .tsd-kind-icon:before { 940 | background-position: -153px -51px; 941 | } 942 | .tsd-kind-accessor.tsd-is-private > .tsd-kind-icon:before { 943 | background-position: -119px -51px; 944 | } 945 | .tsd-kind-accessor.tsd-parent-kind-class > .tsd-kind-icon:before { 946 | background-position: -51px -51px; 947 | } 948 | .tsd-kind-accessor.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 949 | background-position: -68px -51px; 950 | } 951 | .tsd-kind-accessor.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 952 | background-position: -85px -51px; 953 | } 954 | .tsd-kind-accessor.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 955 | background-position: -102px -51px; 956 | } 957 | .tsd-kind-accessor.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 958 | background-position: -119px -51px; 959 | } 960 | .tsd-kind-accessor.tsd-parent-kind-enum > .tsd-kind-icon:before { 961 | background-position: -170px -51px; 962 | } 963 | .tsd-kind-accessor.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 964 | background-position: -187px -51px; 965 | } 966 | .tsd-kind-accessor.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 967 | background-position: -119px -51px; 968 | } 969 | .tsd-kind-accessor.tsd-parent-kind-interface > .tsd-kind-icon:before { 970 | background-position: -204px -51px; 971 | } 972 | .tsd-kind-accessor.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 973 | background-position: -221px -51px; 974 | } 975 | 976 | .tsd-kind-function > .tsd-kind-icon:before { 977 | background-position: -136px -68px; 978 | } 979 | .tsd-kind-function.tsd-is-protected > .tsd-kind-icon:before { 980 | background-position: -153px -68px; 981 | } 982 | .tsd-kind-function.tsd-is-private > .tsd-kind-icon:before { 983 | background-position: -119px -68px; 984 | } 985 | .tsd-kind-function.tsd-parent-kind-class > .tsd-kind-icon:before { 986 | background-position: -51px -68px; 987 | } 988 | .tsd-kind-function.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 989 | background-position: -68px -68px; 990 | } 991 | .tsd-kind-function.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 992 | background-position: -85px -68px; 993 | } 994 | .tsd-kind-function.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 995 | background-position: -102px -68px; 996 | } 997 | .tsd-kind-function.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 998 | background-position: -119px -68px; 999 | } 1000 | .tsd-kind-function.tsd-parent-kind-enum > .tsd-kind-icon:before { 1001 | background-position: -170px -68px; 1002 | } 1003 | .tsd-kind-function.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1004 | background-position: -187px -68px; 1005 | } 1006 | .tsd-kind-function.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1007 | background-position: -119px -68px; 1008 | } 1009 | .tsd-kind-function.tsd-parent-kind-interface > .tsd-kind-icon:before { 1010 | background-position: -204px -68px; 1011 | } 1012 | .tsd-kind-function.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1013 | background-position: -221px -68px; 1014 | } 1015 | 1016 | .tsd-kind-method > .tsd-kind-icon:before { 1017 | background-position: -136px -68px; 1018 | } 1019 | .tsd-kind-method.tsd-is-protected > .tsd-kind-icon:before { 1020 | background-position: -153px -68px; 1021 | } 1022 | .tsd-kind-method.tsd-is-private > .tsd-kind-icon:before { 1023 | background-position: -119px -68px; 1024 | } 1025 | .tsd-kind-method.tsd-parent-kind-class > .tsd-kind-icon:before { 1026 | background-position: -51px -68px; 1027 | } 1028 | .tsd-kind-method.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 1029 | background-position: -68px -68px; 1030 | } 1031 | .tsd-kind-method.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 1032 | background-position: -85px -68px; 1033 | } 1034 | .tsd-kind-method.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 1035 | background-position: -102px -68px; 1036 | } 1037 | .tsd-kind-method.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 1038 | background-position: -119px -68px; 1039 | } 1040 | .tsd-kind-method.tsd-parent-kind-enum > .tsd-kind-icon:before { 1041 | background-position: -170px -68px; 1042 | } 1043 | .tsd-kind-method.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1044 | background-position: -187px -68px; 1045 | } 1046 | .tsd-kind-method.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1047 | background-position: -119px -68px; 1048 | } 1049 | .tsd-kind-method.tsd-parent-kind-interface > .tsd-kind-icon:before { 1050 | background-position: -204px -68px; 1051 | } 1052 | .tsd-kind-method.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1053 | background-position: -221px -68px; 1054 | } 1055 | 1056 | .tsd-kind-call-signature > .tsd-kind-icon:before { 1057 | background-position: -136px -68px; 1058 | } 1059 | .tsd-kind-call-signature.tsd-is-protected > .tsd-kind-icon:before { 1060 | background-position: -153px -68px; 1061 | } 1062 | .tsd-kind-call-signature.tsd-is-private > .tsd-kind-icon:before { 1063 | background-position: -119px -68px; 1064 | } 1065 | .tsd-kind-call-signature.tsd-parent-kind-class > .tsd-kind-icon:before { 1066 | background-position: -51px -68px; 1067 | } 1068 | .tsd-kind-call-signature.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 1069 | background-position: -68px -68px; 1070 | } 1071 | .tsd-kind-call-signature.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 1072 | background-position: -85px -68px; 1073 | } 1074 | .tsd-kind-call-signature.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 1075 | background-position: -102px -68px; 1076 | } 1077 | .tsd-kind-call-signature.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 1078 | background-position: -119px -68px; 1079 | } 1080 | .tsd-kind-call-signature.tsd-parent-kind-enum > .tsd-kind-icon:before { 1081 | background-position: -170px -68px; 1082 | } 1083 | .tsd-kind-call-signature.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1084 | background-position: -187px -68px; 1085 | } 1086 | .tsd-kind-call-signature.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1087 | background-position: -119px -68px; 1088 | } 1089 | .tsd-kind-call-signature.tsd-parent-kind-interface > .tsd-kind-icon:before { 1090 | background-position: -204px -68px; 1091 | } 1092 | .tsd-kind-call-signature.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1093 | background-position: -221px -68px; 1094 | } 1095 | 1096 | .tsd-kind-function.tsd-has-type-parameter > .tsd-kind-icon:before { 1097 | background-position: -136px -85px; 1098 | } 1099 | .tsd-kind-function.tsd-has-type-parameter.tsd-is-protected > .tsd-kind-icon:before { 1100 | background-position: -153px -85px; 1101 | } 1102 | .tsd-kind-function.tsd-has-type-parameter.tsd-is-private > .tsd-kind-icon:before { 1103 | background-position: -119px -85px; 1104 | } 1105 | .tsd-kind-function.tsd-has-type-parameter.tsd-parent-kind-class > .tsd-kind-icon:before { 1106 | background-position: -51px -85px; 1107 | } 1108 | .tsd-kind-function.tsd-has-type-parameter.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 1109 | background-position: -68px -85px; 1110 | } 1111 | .tsd-kind-function.tsd-has-type-parameter.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 1112 | background-position: -85px -85px; 1113 | } 1114 | .tsd-kind-function.tsd-has-type-parameter.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 1115 | background-position: -102px -85px; 1116 | } 1117 | .tsd-kind-function.tsd-has-type-parameter.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 1118 | background-position: -119px -85px; 1119 | } 1120 | .tsd-kind-function.tsd-has-type-parameter.tsd-parent-kind-enum > .tsd-kind-icon:before { 1121 | background-position: -170px -85px; 1122 | } 1123 | .tsd-kind-function.tsd-has-type-parameter.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1124 | background-position: -187px -85px; 1125 | } 1126 | .tsd-kind-function.tsd-has-type-parameter.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1127 | background-position: -119px -85px; 1128 | } 1129 | .tsd-kind-function.tsd-has-type-parameter.tsd-parent-kind-interface > .tsd-kind-icon:before { 1130 | background-position: -204px -85px; 1131 | } 1132 | .tsd-kind-function.tsd-has-type-parameter.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1133 | background-position: -221px -85px; 1134 | } 1135 | 1136 | .tsd-kind-method.tsd-has-type-parameter > .tsd-kind-icon:before { 1137 | background-position: -136px -85px; 1138 | } 1139 | .tsd-kind-method.tsd-has-type-parameter.tsd-is-protected > .tsd-kind-icon:before { 1140 | background-position: -153px -85px; 1141 | } 1142 | .tsd-kind-method.tsd-has-type-parameter.tsd-is-private > .tsd-kind-icon:before { 1143 | background-position: -119px -85px; 1144 | } 1145 | .tsd-kind-method.tsd-has-type-parameter.tsd-parent-kind-class > .tsd-kind-icon:before { 1146 | background-position: -51px -85px; 1147 | } 1148 | .tsd-kind-method.tsd-has-type-parameter.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 1149 | background-position: -68px -85px; 1150 | } 1151 | .tsd-kind-method.tsd-has-type-parameter.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 1152 | background-position: -85px -85px; 1153 | } 1154 | .tsd-kind-method.tsd-has-type-parameter.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 1155 | background-position: -102px -85px; 1156 | } 1157 | .tsd-kind-method.tsd-has-type-parameter.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 1158 | background-position: -119px -85px; 1159 | } 1160 | .tsd-kind-method.tsd-has-type-parameter.tsd-parent-kind-enum > .tsd-kind-icon:before { 1161 | background-position: -170px -85px; 1162 | } 1163 | .tsd-kind-method.tsd-has-type-parameter.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1164 | background-position: -187px -85px; 1165 | } 1166 | .tsd-kind-method.tsd-has-type-parameter.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1167 | background-position: -119px -85px; 1168 | } 1169 | .tsd-kind-method.tsd-has-type-parameter.tsd-parent-kind-interface > .tsd-kind-icon:before { 1170 | background-position: -204px -85px; 1171 | } 1172 | .tsd-kind-method.tsd-has-type-parameter.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1173 | background-position: -221px -85px; 1174 | } 1175 | 1176 | .tsd-kind-constructor > .tsd-kind-icon:before { 1177 | background-position: -136px -102px; 1178 | } 1179 | .tsd-kind-constructor.tsd-is-protected > .tsd-kind-icon:before { 1180 | background-position: -153px -102px; 1181 | } 1182 | .tsd-kind-constructor.tsd-is-private > .tsd-kind-icon:before { 1183 | background-position: -119px -102px; 1184 | } 1185 | .tsd-kind-constructor.tsd-parent-kind-class > .tsd-kind-icon:before { 1186 | background-position: -51px -102px; 1187 | } 1188 | .tsd-kind-constructor.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 1189 | background-position: -68px -102px; 1190 | } 1191 | .tsd-kind-constructor.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 1192 | background-position: -85px -102px; 1193 | } 1194 | .tsd-kind-constructor.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 1195 | background-position: -102px -102px; 1196 | } 1197 | .tsd-kind-constructor.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 1198 | background-position: -119px -102px; 1199 | } 1200 | .tsd-kind-constructor.tsd-parent-kind-enum > .tsd-kind-icon:before { 1201 | background-position: -170px -102px; 1202 | } 1203 | .tsd-kind-constructor.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1204 | background-position: -187px -102px; 1205 | } 1206 | .tsd-kind-constructor.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1207 | background-position: -119px -102px; 1208 | } 1209 | .tsd-kind-constructor.tsd-parent-kind-interface > .tsd-kind-icon:before { 1210 | background-position: -204px -102px; 1211 | } 1212 | .tsd-kind-constructor.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1213 | background-position: -221px -102px; 1214 | } 1215 | 1216 | .tsd-kind-constructor-signature > .tsd-kind-icon:before { 1217 | background-position: -136px -102px; 1218 | } 1219 | .tsd-kind-constructor-signature.tsd-is-protected > .tsd-kind-icon:before { 1220 | background-position: -153px -102px; 1221 | } 1222 | .tsd-kind-constructor-signature.tsd-is-private > .tsd-kind-icon:before { 1223 | background-position: -119px -102px; 1224 | } 1225 | .tsd-kind-constructor-signature.tsd-parent-kind-class > .tsd-kind-icon:before { 1226 | background-position: -51px -102px; 1227 | } 1228 | .tsd-kind-constructor-signature.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 1229 | background-position: -68px -102px; 1230 | } 1231 | .tsd-kind-constructor-signature.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 1232 | background-position: -85px -102px; 1233 | } 1234 | .tsd-kind-constructor-signature.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 1235 | background-position: -102px -102px; 1236 | } 1237 | .tsd-kind-constructor-signature.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 1238 | background-position: -119px -102px; 1239 | } 1240 | .tsd-kind-constructor-signature.tsd-parent-kind-enum > .tsd-kind-icon:before { 1241 | background-position: -170px -102px; 1242 | } 1243 | .tsd-kind-constructor-signature.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1244 | background-position: -187px -102px; 1245 | } 1246 | .tsd-kind-constructor-signature.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1247 | background-position: -119px -102px; 1248 | } 1249 | .tsd-kind-constructor-signature.tsd-parent-kind-interface > .tsd-kind-icon:before { 1250 | background-position: -204px -102px; 1251 | } 1252 | .tsd-kind-constructor-signature.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1253 | background-position: -221px -102px; 1254 | } 1255 | 1256 | .tsd-kind-index-signature > .tsd-kind-icon:before { 1257 | background-position: -136px -119px; 1258 | } 1259 | .tsd-kind-index-signature.tsd-is-protected > .tsd-kind-icon:before { 1260 | background-position: -153px -119px; 1261 | } 1262 | .tsd-kind-index-signature.tsd-is-private > .tsd-kind-icon:before { 1263 | background-position: -119px -119px; 1264 | } 1265 | .tsd-kind-index-signature.tsd-parent-kind-class > .tsd-kind-icon:before { 1266 | background-position: -51px -119px; 1267 | } 1268 | .tsd-kind-index-signature.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 1269 | background-position: -68px -119px; 1270 | } 1271 | .tsd-kind-index-signature.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 1272 | background-position: -85px -119px; 1273 | } 1274 | .tsd-kind-index-signature.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 1275 | background-position: -102px -119px; 1276 | } 1277 | .tsd-kind-index-signature.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 1278 | background-position: -119px -119px; 1279 | } 1280 | .tsd-kind-index-signature.tsd-parent-kind-enum > .tsd-kind-icon:before { 1281 | background-position: -170px -119px; 1282 | } 1283 | .tsd-kind-index-signature.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1284 | background-position: -187px -119px; 1285 | } 1286 | .tsd-kind-index-signature.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1287 | background-position: -119px -119px; 1288 | } 1289 | .tsd-kind-index-signature.tsd-parent-kind-interface > .tsd-kind-icon:before { 1290 | background-position: -204px -119px; 1291 | } 1292 | .tsd-kind-index-signature.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1293 | background-position: -221px -119px; 1294 | } 1295 | 1296 | .tsd-kind-event > .tsd-kind-icon:before { 1297 | background-position: -136px -136px; 1298 | } 1299 | .tsd-kind-event.tsd-is-protected > .tsd-kind-icon:before { 1300 | background-position: -153px -136px; 1301 | } 1302 | .tsd-kind-event.tsd-is-private > .tsd-kind-icon:before { 1303 | background-position: -119px -136px; 1304 | } 1305 | .tsd-kind-event.tsd-parent-kind-class > .tsd-kind-icon:before { 1306 | background-position: -51px -136px; 1307 | } 1308 | .tsd-kind-event.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 1309 | background-position: -68px -136px; 1310 | } 1311 | .tsd-kind-event.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 1312 | background-position: -85px -136px; 1313 | } 1314 | .tsd-kind-event.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 1315 | background-position: -102px -136px; 1316 | } 1317 | .tsd-kind-event.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 1318 | background-position: -119px -136px; 1319 | } 1320 | .tsd-kind-event.tsd-parent-kind-enum > .tsd-kind-icon:before { 1321 | background-position: -170px -136px; 1322 | } 1323 | .tsd-kind-event.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1324 | background-position: -187px -136px; 1325 | } 1326 | .tsd-kind-event.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1327 | background-position: -119px -136px; 1328 | } 1329 | .tsd-kind-event.tsd-parent-kind-interface > .tsd-kind-icon:before { 1330 | background-position: -204px -136px; 1331 | } 1332 | .tsd-kind-event.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1333 | background-position: -221px -136px; 1334 | } 1335 | 1336 | .tsd-is-static > .tsd-kind-icon:before { 1337 | background-position: -136px -153px; 1338 | } 1339 | .tsd-is-static.tsd-is-protected > .tsd-kind-icon:before { 1340 | background-position: -153px -153px; 1341 | } 1342 | .tsd-is-static.tsd-is-private > .tsd-kind-icon:before { 1343 | background-position: -119px -153px; 1344 | } 1345 | .tsd-is-static.tsd-parent-kind-class > .tsd-kind-icon:before { 1346 | background-position: -51px -153px; 1347 | } 1348 | .tsd-is-static.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 1349 | background-position: -68px -153px; 1350 | } 1351 | .tsd-is-static.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 1352 | background-position: -85px -153px; 1353 | } 1354 | .tsd-is-static.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 1355 | background-position: -102px -153px; 1356 | } 1357 | .tsd-is-static.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 1358 | background-position: -119px -153px; 1359 | } 1360 | .tsd-is-static.tsd-parent-kind-enum > .tsd-kind-icon:before { 1361 | background-position: -170px -153px; 1362 | } 1363 | .tsd-is-static.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1364 | background-position: -187px -153px; 1365 | } 1366 | .tsd-is-static.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1367 | background-position: -119px -153px; 1368 | } 1369 | .tsd-is-static.tsd-parent-kind-interface > .tsd-kind-icon:before { 1370 | background-position: -204px -153px; 1371 | } 1372 | .tsd-is-static.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1373 | background-position: -221px -153px; 1374 | } 1375 | 1376 | .tsd-is-static.tsd-kind-function > .tsd-kind-icon:before { 1377 | background-position: -136px -170px; 1378 | } 1379 | .tsd-is-static.tsd-kind-function.tsd-is-protected > .tsd-kind-icon:before { 1380 | background-position: -153px -170px; 1381 | } 1382 | .tsd-is-static.tsd-kind-function.tsd-is-private > .tsd-kind-icon:before { 1383 | background-position: -119px -170px; 1384 | } 1385 | .tsd-is-static.tsd-kind-function.tsd-parent-kind-class > .tsd-kind-icon:before { 1386 | background-position: -51px -170px; 1387 | } 1388 | .tsd-is-static.tsd-kind-function.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 1389 | background-position: -68px -170px; 1390 | } 1391 | .tsd-is-static.tsd-kind-function.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 1392 | background-position: -85px -170px; 1393 | } 1394 | .tsd-is-static.tsd-kind-function.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 1395 | background-position: -102px -170px; 1396 | } 1397 | .tsd-is-static.tsd-kind-function.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 1398 | background-position: -119px -170px; 1399 | } 1400 | .tsd-is-static.tsd-kind-function.tsd-parent-kind-enum > .tsd-kind-icon:before { 1401 | background-position: -170px -170px; 1402 | } 1403 | .tsd-is-static.tsd-kind-function.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1404 | background-position: -187px -170px; 1405 | } 1406 | .tsd-is-static.tsd-kind-function.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1407 | background-position: -119px -170px; 1408 | } 1409 | .tsd-is-static.tsd-kind-function.tsd-parent-kind-interface > .tsd-kind-icon:before { 1410 | background-position: -204px -170px; 1411 | } 1412 | .tsd-is-static.tsd-kind-function.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1413 | background-position: -221px -170px; 1414 | } 1415 | 1416 | .tsd-is-static.tsd-kind-method > .tsd-kind-icon:before { 1417 | background-position: -136px -170px; 1418 | } 1419 | .tsd-is-static.tsd-kind-method.tsd-is-protected > .tsd-kind-icon:before { 1420 | background-position: -153px -170px; 1421 | } 1422 | .tsd-is-static.tsd-kind-method.tsd-is-private > .tsd-kind-icon:before { 1423 | background-position: -119px -170px; 1424 | } 1425 | .tsd-is-static.tsd-kind-method.tsd-parent-kind-class > .tsd-kind-icon:before { 1426 | background-position: -51px -170px; 1427 | } 1428 | .tsd-is-static.tsd-kind-method.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 1429 | background-position: -68px -170px; 1430 | } 1431 | .tsd-is-static.tsd-kind-method.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 1432 | background-position: -85px -170px; 1433 | } 1434 | .tsd-is-static.tsd-kind-method.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 1435 | background-position: -102px -170px; 1436 | } 1437 | .tsd-is-static.tsd-kind-method.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 1438 | background-position: -119px -170px; 1439 | } 1440 | .tsd-is-static.tsd-kind-method.tsd-parent-kind-enum > .tsd-kind-icon:before { 1441 | background-position: -170px -170px; 1442 | } 1443 | .tsd-is-static.tsd-kind-method.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1444 | background-position: -187px -170px; 1445 | } 1446 | .tsd-is-static.tsd-kind-method.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1447 | background-position: -119px -170px; 1448 | } 1449 | .tsd-is-static.tsd-kind-method.tsd-parent-kind-interface > .tsd-kind-icon:before { 1450 | background-position: -204px -170px; 1451 | } 1452 | .tsd-is-static.tsd-kind-method.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1453 | background-position: -221px -170px; 1454 | } 1455 | 1456 | .tsd-is-static.tsd-kind-call-signature > .tsd-kind-icon:before { 1457 | background-position: -136px -170px; 1458 | } 1459 | .tsd-is-static.tsd-kind-call-signature.tsd-is-protected > .tsd-kind-icon:before { 1460 | background-position: -153px -170px; 1461 | } 1462 | .tsd-is-static.tsd-kind-call-signature.tsd-is-private > .tsd-kind-icon:before { 1463 | background-position: -119px -170px; 1464 | } 1465 | .tsd-is-static.tsd-kind-call-signature.tsd-parent-kind-class > .tsd-kind-icon:before { 1466 | background-position: -51px -170px; 1467 | } 1468 | .tsd-is-static.tsd-kind-call-signature.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 1469 | background-position: -68px -170px; 1470 | } 1471 | .tsd-is-static.tsd-kind-call-signature.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 1472 | background-position: -85px -170px; 1473 | } 1474 | .tsd-is-static.tsd-kind-call-signature.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 1475 | background-position: -102px -170px; 1476 | } 1477 | .tsd-is-static.tsd-kind-call-signature.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 1478 | background-position: -119px -170px; 1479 | } 1480 | .tsd-is-static.tsd-kind-call-signature.tsd-parent-kind-enum > .tsd-kind-icon:before { 1481 | background-position: -170px -170px; 1482 | } 1483 | .tsd-is-static.tsd-kind-call-signature.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1484 | background-position: -187px -170px; 1485 | } 1486 | .tsd-is-static.tsd-kind-call-signature.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1487 | background-position: -119px -170px; 1488 | } 1489 | .tsd-is-static.tsd-kind-call-signature.tsd-parent-kind-interface > .tsd-kind-icon:before { 1490 | background-position: -204px -170px; 1491 | } 1492 | .tsd-is-static.tsd-kind-call-signature.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1493 | background-position: -221px -170px; 1494 | } 1495 | 1496 | .tsd-is-static.tsd-kind-event > .tsd-kind-icon:before { 1497 | background-position: -136px -187px; 1498 | } 1499 | .tsd-is-static.tsd-kind-event.tsd-is-protected > .tsd-kind-icon:before { 1500 | background-position: -153px -187px; 1501 | } 1502 | .tsd-is-static.tsd-kind-event.tsd-is-private > .tsd-kind-icon:before { 1503 | background-position: -119px -187px; 1504 | } 1505 | .tsd-is-static.tsd-kind-event.tsd-parent-kind-class > .tsd-kind-icon:before { 1506 | background-position: -51px -187px; 1507 | } 1508 | .tsd-is-static.tsd-kind-event.tsd-parent-kind-class.tsd-is-inherited > .tsd-kind-icon:before { 1509 | background-position: -68px -187px; 1510 | } 1511 | .tsd-is-static.tsd-kind-event.tsd-parent-kind-class.tsd-is-protected > .tsd-kind-icon:before { 1512 | background-position: -85px -187px; 1513 | } 1514 | .tsd-is-static.tsd-kind-event.tsd-parent-kind-class.tsd-is-protected.tsd-is-inherited > .tsd-kind-icon:before { 1515 | background-position: -102px -187px; 1516 | } 1517 | .tsd-is-static.tsd-kind-event.tsd-parent-kind-class.tsd-is-private > .tsd-kind-icon:before { 1518 | background-position: -119px -187px; 1519 | } 1520 | .tsd-is-static.tsd-kind-event.tsd-parent-kind-enum > .tsd-kind-icon:before { 1521 | background-position: -170px -187px; 1522 | } 1523 | .tsd-is-static.tsd-kind-event.tsd-parent-kind-enum.tsd-is-protected > .tsd-kind-icon:before { 1524 | background-position: -187px -187px; 1525 | } 1526 | .tsd-is-static.tsd-kind-event.tsd-parent-kind-enum.tsd-is-private > .tsd-kind-icon:before { 1527 | background-position: -119px -187px; 1528 | } 1529 | .tsd-is-static.tsd-kind-event.tsd-parent-kind-interface > .tsd-kind-icon:before { 1530 | background-position: -204px -187px; 1531 | } 1532 | .tsd-is-static.tsd-kind-event.tsd-parent-kind-interface.tsd-is-inherited > .tsd-kind-icon:before { 1533 | background-position: -221px -187px; 1534 | } 1535 | 1536 | @keyframes fade-in { 1537 | from { 1538 | opacity: 0; 1539 | } 1540 | to { 1541 | opacity: 1; 1542 | } 1543 | } 1544 | @keyframes fade-out { 1545 | from { 1546 | opacity: 1; 1547 | visibility: visible; 1548 | } 1549 | to { 1550 | opacity: 0; 1551 | } 1552 | } 1553 | @keyframes fade-in-delayed { 1554 | 0% { 1555 | opacity: 0; 1556 | } 1557 | 33% { 1558 | opacity: 0; 1559 | } 1560 | 100% { 1561 | opacity: 1; 1562 | } 1563 | } 1564 | @keyframes fade-out-delayed { 1565 | 0% { 1566 | opacity: 1; 1567 | visibility: visible; 1568 | } 1569 | 66% { 1570 | opacity: 0; 1571 | } 1572 | 100% { 1573 | opacity: 0; 1574 | } 1575 | } 1576 | @keyframes shift-to-left { 1577 | from { 1578 | transform: translate(0, 0); 1579 | } 1580 | to { 1581 | transform: translate(-25%, 0); 1582 | } 1583 | } 1584 | @keyframes unshift-to-left { 1585 | from { 1586 | transform: translate(-25%, 0); 1587 | } 1588 | to { 1589 | transform: translate(0, 0); 1590 | } 1591 | } 1592 | @keyframes pop-in-from-right { 1593 | from { 1594 | transform: translate(100%, 0); 1595 | } 1596 | to { 1597 | transform: translate(0, 0); 1598 | } 1599 | } 1600 | @keyframes pop-out-to-right { 1601 | from { 1602 | transform: translate(0, 0); 1603 | visibility: visible; 1604 | } 1605 | to { 1606 | transform: translate(100%, 0); 1607 | } 1608 | } 1609 | body { 1610 | background: var(--color-background); 1611 | font-family: "Segoe UI", sans-serif; 1612 | font-size: 16px; 1613 | color: var(--color-text); 1614 | } 1615 | 1616 | a { 1617 | color: var(--color-link); 1618 | text-decoration: none; 1619 | } 1620 | a:hover { 1621 | text-decoration: underline; 1622 | } 1623 | 1624 | code, pre { 1625 | font-family: Menlo, Monaco, Consolas, "Courier New", monospace; 1626 | padding: 0.2em; 1627 | margin: 0; 1628 | font-size: 14px; 1629 | background-color: var(--color-code-background); 1630 | } 1631 | 1632 | pre { 1633 | padding: 10px; 1634 | } 1635 | pre code { 1636 | padding: 0; 1637 | font-size: 100%; 1638 | background-color: transparent; 1639 | } 1640 | 1641 | blockquote { 1642 | margin: 1em 0; 1643 | padding-left: 1em; 1644 | border-left: 4px solid gray; 1645 | } 1646 | 1647 | .tsd-typography { 1648 | line-height: 1.333em; 1649 | } 1650 | .tsd-typography ul { 1651 | list-style: square; 1652 | padding: 0 0 0 20px; 1653 | margin: 0; 1654 | } 1655 | .tsd-typography h4, .tsd-typography .tsd-index-panel h3, .tsd-index-panel .tsd-typography h3, .tsd-typography h5, .tsd-typography h6 { 1656 | font-size: 1em; 1657 | margin: 0; 1658 | } 1659 | .tsd-typography h5, .tsd-typography h6 { 1660 | font-weight: normal; 1661 | } 1662 | .tsd-typography p, .tsd-typography ul, .tsd-typography ol { 1663 | margin: 1em 0; 1664 | } 1665 | 1666 | @media (min-width: 901px) and (max-width: 1024px) { 1667 | html.default .col-content { 1668 | width: 72%; 1669 | } 1670 | html.default .col-menu { 1671 | width: 28%; 1672 | } 1673 | html.default .tsd-navigation { 1674 | padding-left: 10px; 1675 | } 1676 | } 1677 | @media (max-width: 900px) { 1678 | html.default .col-content { 1679 | float: none; 1680 | width: 100%; 1681 | } 1682 | html.default .col-menu { 1683 | position: fixed !important; 1684 | overflow: auto; 1685 | -webkit-overflow-scrolling: touch; 1686 | z-index: 1024; 1687 | top: 0 !important; 1688 | bottom: 0 !important; 1689 | left: auto !important; 1690 | right: 0 !important; 1691 | width: 100%; 1692 | padding: 20px 20px 0 0; 1693 | max-width: 450px; 1694 | visibility: hidden; 1695 | background-color: var(--color-panel); 1696 | transform: translate(100%, 0); 1697 | } 1698 | html.default .col-menu > *:last-child { 1699 | padding-bottom: 20px; 1700 | } 1701 | html.default .overlay { 1702 | content: ""; 1703 | display: block; 1704 | position: fixed; 1705 | z-index: 1023; 1706 | top: 0; 1707 | left: 0; 1708 | right: 0; 1709 | bottom: 0; 1710 | background-color: rgba(0, 0, 0, 0.75); 1711 | visibility: hidden; 1712 | } 1713 | html.default.to-has-menu .overlay { 1714 | animation: fade-in 0.4s; 1715 | } 1716 | html.default.to-has-menu header, 1717 | html.default.to-has-menu footer, 1718 | html.default.to-has-menu .col-content { 1719 | animation: shift-to-left 0.4s; 1720 | } 1721 | html.default.to-has-menu .col-menu { 1722 | animation: pop-in-from-right 0.4s; 1723 | } 1724 | html.default.from-has-menu .overlay { 1725 | animation: fade-out 0.4s; 1726 | } 1727 | html.default.from-has-menu header, 1728 | html.default.from-has-menu footer, 1729 | html.default.from-has-menu .col-content { 1730 | animation: unshift-to-left 0.4s; 1731 | } 1732 | html.default.from-has-menu .col-menu { 1733 | animation: pop-out-to-right 0.4s; 1734 | } 1735 | html.default.has-menu body { 1736 | overflow: hidden; 1737 | } 1738 | html.default.has-menu .overlay { 1739 | visibility: visible; 1740 | } 1741 | html.default.has-menu header, 1742 | html.default.has-menu footer, 1743 | html.default.has-menu .col-content { 1744 | transform: translate(-25%, 0); 1745 | } 1746 | html.default.has-menu .col-menu { 1747 | visibility: visible; 1748 | transform: translate(0, 0); 1749 | } 1750 | } 1751 | 1752 | .tsd-page-title { 1753 | padding: 70px 0 20px 0; 1754 | margin: 0 0 40px 0; 1755 | background: var(--color-panel); 1756 | box-shadow: 0 0 5px rgba(0, 0, 0, 0.35); 1757 | } 1758 | .tsd-page-title h1 { 1759 | margin: 0; 1760 | } 1761 | 1762 | .tsd-breadcrumb { 1763 | margin: 0; 1764 | padding: 0; 1765 | color: var(--color-text-aside); 1766 | } 1767 | .tsd-breadcrumb a { 1768 | color: var(--color-text-aside); 1769 | text-decoration: none; 1770 | } 1771 | .tsd-breadcrumb a:hover { 1772 | text-decoration: underline; 1773 | } 1774 | .tsd-breadcrumb li { 1775 | display: inline; 1776 | } 1777 | .tsd-breadcrumb li:after { 1778 | content: " / "; 1779 | } 1780 | 1781 | html.minimal .container { 1782 | margin: 0; 1783 | } 1784 | html.minimal .container-main { 1785 | padding-top: 50px; 1786 | padding-bottom: 0; 1787 | } 1788 | html.minimal .content-wrap { 1789 | padding-left: 300px; 1790 | } 1791 | html.minimal .tsd-navigation { 1792 | position: fixed !important; 1793 | overflow: auto; 1794 | -webkit-overflow-scrolling: touch; 1795 | box-sizing: border-box; 1796 | z-index: 1; 1797 | left: 0; 1798 | top: 40px; 1799 | bottom: 0; 1800 | width: 300px; 1801 | padding: 20px; 1802 | margin: 0; 1803 | } 1804 | html.minimal .tsd-member .tsd-member { 1805 | margin-left: 0; 1806 | } 1807 | html.minimal .tsd-page-toolbar { 1808 | position: fixed; 1809 | z-index: 2; 1810 | } 1811 | html.minimal #tsd-filter .tsd-filter-group { 1812 | right: 0; 1813 | transform: none; 1814 | } 1815 | html.minimal footer { 1816 | background-color: transparent; 1817 | } 1818 | html.minimal footer .container { 1819 | padding: 0; 1820 | } 1821 | html.minimal .tsd-generator { 1822 | padding: 0; 1823 | } 1824 | @media (max-width: 900px) { 1825 | html.minimal .tsd-navigation { 1826 | display: none; 1827 | } 1828 | html.minimal .content-wrap { 1829 | padding-left: 0; 1830 | } 1831 | } 1832 | 1833 | dl.tsd-comment-tags { 1834 | overflow: hidden; 1835 | } 1836 | dl.tsd-comment-tags dt { 1837 | float: left; 1838 | padding: 1px 5px; 1839 | margin: 0 10px 0 0; 1840 | border-radius: 4px; 1841 | border: 1px solid var(--color-comment-tag); 1842 | color: var(--color-comment-tag); 1843 | font-size: 0.8em; 1844 | font-weight: normal; 1845 | } 1846 | dl.tsd-comment-tags dd { 1847 | margin: 0 0 10px 0; 1848 | } 1849 | dl.tsd-comment-tags dd:before, dl.tsd-comment-tags dd:after { 1850 | display: table; 1851 | content: " "; 1852 | } 1853 | dl.tsd-comment-tags dd pre, dl.tsd-comment-tags dd:after { 1854 | clear: both; 1855 | } 1856 | dl.tsd-comment-tags p { 1857 | margin: 0; 1858 | } 1859 | 1860 | .tsd-panel.tsd-comment .lead { 1861 | font-size: 1.1em; 1862 | line-height: 1.333em; 1863 | margin-bottom: 2em; 1864 | } 1865 | .tsd-panel.tsd-comment .lead:last-child { 1866 | margin-bottom: 0; 1867 | } 1868 | 1869 | .toggle-protected .tsd-is-private { 1870 | display: none; 1871 | } 1872 | 1873 | .toggle-public .tsd-is-private, 1874 | .toggle-public .tsd-is-protected, 1875 | .toggle-public .tsd-is-private-protected { 1876 | display: none; 1877 | } 1878 | 1879 | .toggle-inherited .tsd-is-inherited { 1880 | display: none; 1881 | } 1882 | 1883 | .toggle-externals .tsd-is-external { 1884 | display: none; 1885 | } 1886 | 1887 | #tsd-filter { 1888 | position: relative; 1889 | display: inline-block; 1890 | height: 40px; 1891 | vertical-align: bottom; 1892 | } 1893 | .no-filter #tsd-filter { 1894 | display: none; 1895 | } 1896 | #tsd-filter .tsd-filter-group { 1897 | display: inline-block; 1898 | height: 40px; 1899 | vertical-align: bottom; 1900 | white-space: nowrap; 1901 | } 1902 | #tsd-filter input { 1903 | display: none; 1904 | } 1905 | @media (max-width: 900px) { 1906 | #tsd-filter .tsd-filter-group { 1907 | display: block; 1908 | position: absolute; 1909 | top: 40px; 1910 | right: 20px; 1911 | height: auto; 1912 | background-color: var(--color-panel); 1913 | visibility: hidden; 1914 | transform: translate(50%, 0); 1915 | box-shadow: 0 0 4px rgba(0, 0, 0, 0.25); 1916 | } 1917 | .has-options #tsd-filter .tsd-filter-group { 1918 | visibility: visible; 1919 | } 1920 | .to-has-options #tsd-filter .tsd-filter-group { 1921 | animation: fade-in 0.2s; 1922 | } 1923 | .from-has-options #tsd-filter .tsd-filter-group { 1924 | animation: fade-out 0.2s; 1925 | } 1926 | #tsd-filter label, 1927 | #tsd-filter .tsd-select { 1928 | display: block; 1929 | padding-right: 20px; 1930 | } 1931 | } 1932 | 1933 | footer { 1934 | border-top: 1px solid var(--color-panel-divider); 1935 | background-color: var(--color-panel); 1936 | } 1937 | footer.with-border-bottom { 1938 | border-bottom: 1px solid var(--color-panel-divider); 1939 | } 1940 | footer .tsd-legend-group { 1941 | font-size: 0; 1942 | } 1943 | footer .tsd-legend { 1944 | display: inline-block; 1945 | width: 25%; 1946 | padding: 0; 1947 | font-size: 16px; 1948 | list-style: none; 1949 | line-height: 1.333em; 1950 | vertical-align: top; 1951 | } 1952 | @media (max-width: 900px) { 1953 | footer .tsd-legend { 1954 | width: 50%; 1955 | } 1956 | } 1957 | 1958 | .tsd-hierarchy { 1959 | list-style: square; 1960 | padding: 0 0 0 20px; 1961 | margin: 0; 1962 | } 1963 | .tsd-hierarchy .target { 1964 | font-weight: bold; 1965 | } 1966 | 1967 | .tsd-index-panel .tsd-index-content { 1968 | margin-bottom: -30px !important; 1969 | } 1970 | .tsd-index-panel .tsd-index-section { 1971 | margin-bottom: 30px !important; 1972 | } 1973 | .tsd-index-panel h3 { 1974 | margin: 0 -20px 10px -20px; 1975 | padding: 0 20px 10px 20px; 1976 | border-bottom: 1px solid var(--color-panel-divider); 1977 | } 1978 | .tsd-index-panel ul.tsd-index-list { 1979 | -webkit-column-count: 3; 1980 | -moz-column-count: 3; 1981 | -ms-column-count: 3; 1982 | -o-column-count: 3; 1983 | column-count: 3; 1984 | -webkit-column-gap: 20px; 1985 | -moz-column-gap: 20px; 1986 | -ms-column-gap: 20px; 1987 | -o-column-gap: 20px; 1988 | column-gap: 20px; 1989 | padding: 0; 1990 | list-style: none; 1991 | line-height: 1.333em; 1992 | } 1993 | @media (max-width: 900px) { 1994 | .tsd-index-panel ul.tsd-index-list { 1995 | -webkit-column-count: 1; 1996 | -moz-column-count: 1; 1997 | -ms-column-count: 1; 1998 | -o-column-count: 1; 1999 | column-count: 1; 2000 | } 2001 | } 2002 | @media (min-width: 901px) and (max-width: 1024px) { 2003 | .tsd-index-panel ul.tsd-index-list { 2004 | -webkit-column-count: 2; 2005 | -moz-column-count: 2; 2006 | -ms-column-count: 2; 2007 | -o-column-count: 2; 2008 | column-count: 2; 2009 | } 2010 | } 2011 | .tsd-index-panel ul.tsd-index-list li { 2012 | -webkit-page-break-inside: avoid; 2013 | -moz-page-break-inside: avoid; 2014 | -ms-page-break-inside: avoid; 2015 | -o-page-break-inside: avoid; 2016 | page-break-inside: avoid; 2017 | } 2018 | .tsd-index-panel a, 2019 | .tsd-index-panel .tsd-parent-kind-module a { 2020 | color: var(--color-ts); 2021 | } 2022 | .tsd-index-panel .tsd-parent-kind-interface a { 2023 | color: var(--color-ts-interface); 2024 | } 2025 | .tsd-index-panel .tsd-parent-kind-enum a { 2026 | color: var(--color-ts-enum); 2027 | } 2028 | .tsd-index-panel .tsd-parent-kind-class a { 2029 | color: var(--color-ts-class); 2030 | } 2031 | .tsd-index-panel .tsd-kind-module a { 2032 | color: var(--color-ts); 2033 | } 2034 | .tsd-index-panel .tsd-kind-interface a { 2035 | color: var(--color-ts-interface); 2036 | } 2037 | .tsd-index-panel .tsd-kind-enum a { 2038 | color: var(--color-ts-enum); 2039 | } 2040 | .tsd-index-panel .tsd-kind-class a { 2041 | color: var(--color-ts-class); 2042 | } 2043 | .tsd-index-panel .tsd-is-private a { 2044 | color: var(--color-ts-private); 2045 | } 2046 | 2047 | .tsd-flag { 2048 | display: inline-block; 2049 | padding: 1px 5px; 2050 | border-radius: 4px; 2051 | color: var(--color-comment-tag-text); 2052 | background-color: var(--color-comment-tag); 2053 | text-indent: 0; 2054 | font-size: 14px; 2055 | font-weight: normal; 2056 | } 2057 | 2058 | .tsd-anchor { 2059 | position: absolute; 2060 | top: -100px; 2061 | } 2062 | 2063 | .tsd-member { 2064 | position: relative; 2065 | } 2066 | .tsd-member .tsd-anchor + h3 { 2067 | margin-top: 0; 2068 | margin-bottom: 0; 2069 | border-bottom: none; 2070 | } 2071 | .tsd-member a[data-tsd-kind] { 2072 | color: var(--color-ts); 2073 | } 2074 | .tsd-member a[data-tsd-kind=Interface] { 2075 | color: var(--color-ts-interface); 2076 | } 2077 | .tsd-member a[data-tsd-kind=Enum] { 2078 | color: var(--color-ts-enum); 2079 | } 2080 | .tsd-member a[data-tsd-kind=Class] { 2081 | color: var(--color-ts-class); 2082 | } 2083 | .tsd-member a[data-tsd-kind=Private] { 2084 | color: var(--color-ts-private); 2085 | } 2086 | 2087 | .tsd-navigation { 2088 | margin: 0 0 0 40px; 2089 | } 2090 | .tsd-navigation a { 2091 | display: block; 2092 | padding-top: 2px; 2093 | padding-bottom: 2px; 2094 | border-left: 2px solid transparent; 2095 | color: var(--color-text); 2096 | text-decoration: none; 2097 | transition: border-left-color 0.1s; 2098 | } 2099 | .tsd-navigation a:hover { 2100 | text-decoration: underline; 2101 | } 2102 | .tsd-navigation ul { 2103 | margin: 0; 2104 | padding: 0; 2105 | list-style: none; 2106 | } 2107 | .tsd-navigation li { 2108 | padding: 0; 2109 | } 2110 | 2111 | .tsd-navigation.primary { 2112 | padding-bottom: 40px; 2113 | } 2114 | .tsd-navigation.primary a { 2115 | display: block; 2116 | padding-top: 6px; 2117 | padding-bottom: 6px; 2118 | } 2119 | .tsd-navigation.primary ul li a { 2120 | padding-left: 5px; 2121 | } 2122 | .tsd-navigation.primary ul li li a { 2123 | padding-left: 25px; 2124 | } 2125 | .tsd-navigation.primary ul li li li a { 2126 | padding-left: 45px; 2127 | } 2128 | .tsd-navigation.primary ul li li li li a { 2129 | padding-left: 65px; 2130 | } 2131 | .tsd-navigation.primary ul li li li li li a { 2132 | padding-left: 85px; 2133 | } 2134 | .tsd-navigation.primary ul li li li li li li a { 2135 | padding-left: 105px; 2136 | } 2137 | .tsd-navigation.primary > ul { 2138 | border-bottom: 1px solid var(--color-panel-divider); 2139 | } 2140 | .tsd-navigation.primary li { 2141 | border-top: 1px solid var(--color-panel-divider); 2142 | } 2143 | .tsd-navigation.primary li.current > a { 2144 | font-weight: bold; 2145 | } 2146 | .tsd-navigation.primary li.label span { 2147 | display: block; 2148 | padding: 20px 0 6px 5px; 2149 | color: var(--color-menu-label); 2150 | } 2151 | .tsd-navigation.primary li.globals + li > span, .tsd-navigation.primary li.globals + li > a { 2152 | padding-top: 20px; 2153 | } 2154 | 2155 | .tsd-navigation.secondary { 2156 | max-height: calc(100vh - 1rem - 40px); 2157 | overflow: auto; 2158 | position: -webkit-sticky; 2159 | position: sticky; 2160 | top: calc(.5rem + 40px); 2161 | transition: 0.3s; 2162 | } 2163 | .tsd-navigation.secondary.tsd-navigation--toolbar-hide { 2164 | max-height: calc(100vh - 1rem); 2165 | top: 0.5rem; 2166 | } 2167 | .tsd-navigation.secondary ul { 2168 | transition: opacity 0.2s; 2169 | } 2170 | .tsd-navigation.secondary ul li a { 2171 | padding-left: 25px; 2172 | } 2173 | .tsd-navigation.secondary ul li li a { 2174 | padding-left: 45px; 2175 | } 2176 | .tsd-navigation.secondary ul li li li a { 2177 | padding-left: 65px; 2178 | } 2179 | .tsd-navigation.secondary ul li li li li a { 2180 | padding-left: 85px; 2181 | } 2182 | .tsd-navigation.secondary ul li li li li li a { 2183 | padding-left: 105px; 2184 | } 2185 | .tsd-navigation.secondary ul li li li li li li a { 2186 | padding-left: 125px; 2187 | } 2188 | .tsd-navigation.secondary ul.current a { 2189 | border-left-color: var(--color-panel-divider); 2190 | } 2191 | .tsd-navigation.secondary li.focus > a, 2192 | .tsd-navigation.secondary ul.current li.focus > a { 2193 | border-left-color: var(--color-menu-divider-focus); 2194 | } 2195 | .tsd-navigation.secondary li.current { 2196 | margin-top: 20px; 2197 | margin-bottom: 20px; 2198 | border-left-color: var(--color-panel-divider); 2199 | } 2200 | .tsd-navigation.secondary li.current > a { 2201 | font-weight: bold; 2202 | } 2203 | 2204 | @media (min-width: 901px) { 2205 | .menu-sticky-wrap { 2206 | position: static; 2207 | } 2208 | } 2209 | 2210 | .tsd-panel { 2211 | margin: 20px 0; 2212 | padding: 20px; 2213 | background-color: var(--color-panel); 2214 | box-shadow: 0 0 4px rgba(0, 0, 0, 0.25); 2215 | } 2216 | .tsd-panel:empty { 2217 | display: none; 2218 | } 2219 | .tsd-panel > h1, .tsd-panel > h2, .tsd-panel > h3 { 2220 | margin: 1.5em -20px 10px -20px; 2221 | padding: 0 20px 10px 20px; 2222 | border-bottom: 1px solid var(--color-panel-divider); 2223 | } 2224 | .tsd-panel > h1.tsd-before-signature, .tsd-panel > h2.tsd-before-signature, .tsd-panel > h3.tsd-before-signature { 2225 | margin-bottom: 0; 2226 | border-bottom: 0; 2227 | } 2228 | .tsd-panel table { 2229 | display: block; 2230 | width: 100%; 2231 | overflow: auto; 2232 | margin-top: 10px; 2233 | word-break: normal; 2234 | word-break: keep-all; 2235 | } 2236 | .tsd-panel table th { 2237 | font-weight: bold; 2238 | } 2239 | .tsd-panel table th, .tsd-panel table td { 2240 | padding: 6px 13px; 2241 | border: 1px solid #ddd; 2242 | } 2243 | .tsd-panel table tr { 2244 | background-color: #fff; 2245 | border-top: 1px solid #ccc; 2246 | } 2247 | .tsd-panel table tr:nth-child(2n) { 2248 | background-color: #f8f8f8; 2249 | } 2250 | 2251 | .tsd-panel-group { 2252 | margin: 60px 0; 2253 | } 2254 | .tsd-panel-group > h1, .tsd-panel-group > h2, .tsd-panel-group > h3 { 2255 | padding-left: 20px; 2256 | padding-right: 20px; 2257 | } 2258 | 2259 | #tsd-search { 2260 | transition: background-color 0.2s; 2261 | } 2262 | #tsd-search .title { 2263 | position: relative; 2264 | z-index: 2; 2265 | } 2266 | #tsd-search .field { 2267 | position: absolute; 2268 | left: 0; 2269 | top: 0; 2270 | right: 40px; 2271 | height: 40px; 2272 | } 2273 | #tsd-search .field input { 2274 | box-sizing: border-box; 2275 | position: relative; 2276 | top: -50px; 2277 | z-index: 1; 2278 | width: 100%; 2279 | padding: 0 10px; 2280 | opacity: 0; 2281 | outline: 0; 2282 | border: 0; 2283 | background: transparent; 2284 | color: var(--color-text); 2285 | } 2286 | #tsd-search .field label { 2287 | position: absolute; 2288 | overflow: hidden; 2289 | right: -40px; 2290 | } 2291 | #tsd-search .field input, 2292 | #tsd-search .title { 2293 | transition: opacity 0.2s; 2294 | } 2295 | #tsd-search .results { 2296 | position: absolute; 2297 | visibility: hidden; 2298 | top: 40px; 2299 | width: 100%; 2300 | margin: 0; 2301 | padding: 0; 2302 | list-style: none; 2303 | box-shadow: 0 0 4px rgba(0, 0, 0, 0.25); 2304 | } 2305 | #tsd-search .results li { 2306 | padding: 0 10px; 2307 | background-color: var(--color-background); 2308 | } 2309 | #tsd-search .results li:nth-child(even) { 2310 | background-color: var(--color-panel); 2311 | } 2312 | #tsd-search .results li.state { 2313 | display: none; 2314 | } 2315 | #tsd-search .results li.current, 2316 | #tsd-search .results li:hover { 2317 | background-color: var(--color-panel-divider); 2318 | } 2319 | #tsd-search .results a { 2320 | display: block; 2321 | } 2322 | #tsd-search .results a:before { 2323 | top: 10px; 2324 | } 2325 | #tsd-search .results span.parent { 2326 | color: var(--color-text-aside); 2327 | font-weight: normal; 2328 | } 2329 | #tsd-search.has-focus { 2330 | background-color: var(--color-panel-divider); 2331 | } 2332 | #tsd-search.has-focus .field input { 2333 | top: 0; 2334 | opacity: 1; 2335 | } 2336 | #tsd-search.has-focus .title { 2337 | z-index: 0; 2338 | opacity: 0; 2339 | } 2340 | #tsd-search.has-focus .results { 2341 | visibility: visible; 2342 | } 2343 | #tsd-search.loading .results li.state.loading { 2344 | display: block; 2345 | } 2346 | #tsd-search.failure .results li.state.failure { 2347 | display: block; 2348 | } 2349 | 2350 | .tsd-signature { 2351 | margin: 0 0 1em 0; 2352 | padding: 10px; 2353 | border: 1px solid var(--color-panel-divider); 2354 | font-family: Menlo, Monaco, Consolas, "Courier New", monospace; 2355 | font-size: 14px; 2356 | overflow-x: auto; 2357 | } 2358 | .tsd-signature.tsd-kind-icon { 2359 | padding-left: 30px; 2360 | } 2361 | .tsd-signature.tsd-kind-icon:before { 2362 | top: 10px; 2363 | left: 10px; 2364 | } 2365 | .tsd-panel > .tsd-signature { 2366 | margin-left: -20px; 2367 | margin-right: -20px; 2368 | border-width: 1px 0; 2369 | } 2370 | .tsd-panel > .tsd-signature.tsd-kind-icon { 2371 | padding-left: 40px; 2372 | } 2373 | .tsd-panel > .tsd-signature.tsd-kind-icon:before { 2374 | left: 20px; 2375 | } 2376 | 2377 | .tsd-signature-symbol { 2378 | color: var(--color-text-aside); 2379 | font-weight: normal; 2380 | } 2381 | 2382 | .tsd-signature-type { 2383 | font-style: italic; 2384 | font-weight: normal; 2385 | } 2386 | 2387 | .tsd-signatures { 2388 | padding: 0; 2389 | margin: 0 0 1em 0; 2390 | border: 1px solid var(--color-panel-divider); 2391 | } 2392 | .tsd-signatures .tsd-signature { 2393 | margin: 0; 2394 | border-width: 1px 0 0 0; 2395 | transition: background-color 0.1s; 2396 | } 2397 | .tsd-signatures .tsd-signature:first-child { 2398 | border-top-width: 0; 2399 | } 2400 | .tsd-signatures .tsd-signature.current { 2401 | background-color: var(--color-panel-divider); 2402 | } 2403 | .tsd-signatures.active > .tsd-signature { 2404 | cursor: pointer; 2405 | } 2406 | .tsd-panel > .tsd-signatures { 2407 | margin-left: -20px; 2408 | margin-right: -20px; 2409 | border-width: 1px 0; 2410 | } 2411 | .tsd-panel > .tsd-signatures .tsd-signature.tsd-kind-icon { 2412 | padding-left: 40px; 2413 | } 2414 | .tsd-panel > .tsd-signatures .tsd-signature.tsd-kind-icon:before { 2415 | left: 20px; 2416 | } 2417 | .tsd-panel > a.anchor + .tsd-signatures { 2418 | border-top-width: 0; 2419 | margin-top: -20px; 2420 | } 2421 | 2422 | ul.tsd-descriptions { 2423 | position: relative; 2424 | overflow: hidden; 2425 | padding: 0; 2426 | list-style: none; 2427 | } 2428 | ul.tsd-descriptions.active > .tsd-description { 2429 | display: none; 2430 | } 2431 | ul.tsd-descriptions.active > .tsd-description.current { 2432 | display: block; 2433 | } 2434 | ul.tsd-descriptions.active > .tsd-description.fade-in { 2435 | animation: fade-in-delayed 0.3s; 2436 | } 2437 | ul.tsd-descriptions.active > .tsd-description.fade-out { 2438 | animation: fade-out-delayed 0.3s; 2439 | position: absolute; 2440 | display: block; 2441 | top: 0; 2442 | left: 0; 2443 | right: 0; 2444 | opacity: 0; 2445 | visibility: hidden; 2446 | } 2447 | ul.tsd-descriptions h4, ul.tsd-descriptions .tsd-index-panel h3, .tsd-index-panel ul.tsd-descriptions h3 { 2448 | font-size: 16px; 2449 | margin: 1em 0 0.5em 0; 2450 | } 2451 | 2452 | ul.tsd-parameters, 2453 | ul.tsd-type-parameters { 2454 | list-style: square; 2455 | margin: 0; 2456 | padding-left: 20px; 2457 | } 2458 | ul.tsd-parameters > li.tsd-parameter-signature, 2459 | ul.tsd-type-parameters > li.tsd-parameter-signature { 2460 | list-style: none; 2461 | margin-left: -20px; 2462 | } 2463 | ul.tsd-parameters h5, 2464 | ul.tsd-type-parameters h5 { 2465 | font-size: 16px; 2466 | margin: 1em 0 0.5em 0; 2467 | } 2468 | ul.tsd-parameters .tsd-comment, 2469 | ul.tsd-type-parameters .tsd-comment { 2470 | margin-top: -0.5em; 2471 | } 2472 | 2473 | .tsd-sources { 2474 | font-size: 14px; 2475 | color: var(--color-text-aside); 2476 | margin: 0 0 1em 0; 2477 | } 2478 | .tsd-sources a { 2479 | color: var(--color-text-aside); 2480 | text-decoration: underline; 2481 | } 2482 | .tsd-sources ul, .tsd-sources p { 2483 | margin: 0 !important; 2484 | } 2485 | .tsd-sources ul { 2486 | list-style: none; 2487 | padding: 0; 2488 | } 2489 | 2490 | .tsd-page-toolbar { 2491 | position: fixed; 2492 | z-index: 1; 2493 | top: 0; 2494 | left: 0; 2495 | width: 100%; 2496 | height: 40px; 2497 | color: var(--color-toolbar-text); 2498 | background: var(--color-toolbar); 2499 | border-bottom: 1px solid var(--color-panel-divider); 2500 | transition: transform 0.3s linear; 2501 | } 2502 | .tsd-page-toolbar a { 2503 | color: var(--color-toolbar-text); 2504 | text-decoration: none; 2505 | } 2506 | .tsd-page-toolbar a.title { 2507 | font-weight: bold; 2508 | } 2509 | .tsd-page-toolbar a.title:hover { 2510 | text-decoration: underline; 2511 | } 2512 | .tsd-page-toolbar .table-wrap { 2513 | display: table; 2514 | width: 100%; 2515 | height: 40px; 2516 | } 2517 | .tsd-page-toolbar .table-cell { 2518 | display: table-cell; 2519 | position: relative; 2520 | white-space: nowrap; 2521 | line-height: 40px; 2522 | } 2523 | .tsd-page-toolbar .table-cell:first-child { 2524 | width: 100%; 2525 | } 2526 | 2527 | .tsd-page-toolbar--hide { 2528 | transform: translateY(-100%); 2529 | } 2530 | 2531 | .tsd-select .tsd-select-list li:before, .tsd-select .tsd-select-label:before, .tsd-widget:before { 2532 | content: ""; 2533 | display: inline-block; 2534 | width: 40px; 2535 | height: 40px; 2536 | margin: 0 -8px 0 0; 2537 | background-image: url(../images/widgets.png); 2538 | background-repeat: no-repeat; 2539 | text-indent: -1024px; 2540 | vertical-align: bottom; 2541 | } 2542 | @media (-webkit-min-device-pixel-ratio: 1.5), (min-resolution: 144dpi) { 2543 | .tsd-select .tsd-select-list li:before, .tsd-select .tsd-select-label:before, .tsd-widget:before { 2544 | background-image: url(../images/widgets@2x.png); 2545 | background-size: 320px 40px; 2546 | } 2547 | } 2548 | 2549 | .tsd-widget { 2550 | display: inline-block; 2551 | overflow: hidden; 2552 | opacity: 0.6; 2553 | height: 40px; 2554 | transition: opacity 0.1s, background-color 0.2s; 2555 | vertical-align: bottom; 2556 | cursor: pointer; 2557 | } 2558 | .tsd-widget:hover { 2559 | opacity: 0.8; 2560 | } 2561 | .tsd-widget.active { 2562 | opacity: 1; 2563 | background-color: var(--color-panel-divider); 2564 | } 2565 | .tsd-widget.no-caption { 2566 | width: 40px; 2567 | } 2568 | .tsd-widget.no-caption:before { 2569 | margin: 0; 2570 | } 2571 | .tsd-widget.search:before { 2572 | background-position: 0 0; 2573 | } 2574 | .tsd-widget.menu:before { 2575 | background-position: -40px 0; 2576 | } 2577 | .tsd-widget.options:before { 2578 | background-position: -80px 0; 2579 | } 2580 | .tsd-widget.options, .tsd-widget.menu { 2581 | display: none; 2582 | } 2583 | @media (max-width: 900px) { 2584 | .tsd-widget.options, .tsd-widget.menu { 2585 | display: inline-block; 2586 | } 2587 | } 2588 | input[type=checkbox] + .tsd-widget:before { 2589 | background-position: -120px 0; 2590 | } 2591 | input[type=checkbox]:checked + .tsd-widget:before { 2592 | background-position: -160px 0; 2593 | } 2594 | 2595 | .tsd-select { 2596 | position: relative; 2597 | display: inline-block; 2598 | height: 40px; 2599 | transition: opacity 0.1s, background-color 0.2s; 2600 | vertical-align: bottom; 2601 | cursor: pointer; 2602 | } 2603 | .tsd-select .tsd-select-label { 2604 | opacity: 0.6; 2605 | transition: opacity 0.2s; 2606 | } 2607 | .tsd-select .tsd-select-label:before { 2608 | background-position: -240px 0; 2609 | } 2610 | .tsd-select.active .tsd-select-label { 2611 | opacity: 0.8; 2612 | } 2613 | .tsd-select.active .tsd-select-list { 2614 | visibility: visible; 2615 | opacity: 1; 2616 | transition-delay: 0s; 2617 | } 2618 | .tsd-select .tsd-select-list { 2619 | position: absolute; 2620 | visibility: hidden; 2621 | top: 40px; 2622 | left: 0; 2623 | margin: 0; 2624 | padding: 0; 2625 | opacity: 0; 2626 | list-style: none; 2627 | box-shadow: 0 0 4px rgba(0, 0, 0, 0.25); 2628 | transition: visibility 0s 0.2s, opacity 0.2s; 2629 | } 2630 | .tsd-select .tsd-select-list li { 2631 | padding: 0 20px 0 0; 2632 | background-color: var(--color-background); 2633 | } 2634 | .tsd-select .tsd-select-list li:before { 2635 | background-position: 40px 0; 2636 | } 2637 | .tsd-select .tsd-select-list li:nth-child(even) { 2638 | background-color: var(--color-panel); 2639 | } 2640 | .tsd-select .tsd-select-list li:hover { 2641 | background-color: var(--color-panel-divider); 2642 | } 2643 | .tsd-select .tsd-select-list li.selected:before { 2644 | background-position: -200px 0; 2645 | } 2646 | @media (max-width: 900px) { 2647 | .tsd-select .tsd-select-list { 2648 | top: 0; 2649 | left: auto; 2650 | right: 100%; 2651 | margin-right: -5px; 2652 | } 2653 | .tsd-select .tsd-select-label:before { 2654 | background-position: -280px 0; 2655 | } 2656 | } 2657 | 2658 | img { 2659 | max-width: 100%; 2660 | } 2661 | -------------------------------------------------------------------------------- /docs/assets/images/icons.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/AlenVelocity/spotifydl-core/6114130aa2ace2f43206eacc588304b176fd7939/docs/assets/images/icons.png -------------------------------------------------------------------------------- /docs/assets/images/icons@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/AlenVelocity/spotifydl-core/6114130aa2ace2f43206eacc588304b176fd7939/docs/assets/images/icons@2x.png -------------------------------------------------------------------------------- /docs/assets/images/widgets.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/AlenVelocity/spotifydl-core/6114130aa2ace2f43206eacc588304b176fd7939/docs/assets/images/widgets.png -------------------------------------------------------------------------------- /docs/assets/images/widgets@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/AlenVelocity/spotifydl-core/6114130aa2ace2f43206eacc588304b176fd7939/docs/assets/images/widgets@2x.png -------------------------------------------------------------------------------- /docs/assets/js/search.js: -------------------------------------------------------------------------------- 1 | window.searchData = {"kinds":{"1":"Module","32":"Variable","128":"Class","512":"Constructor","1024":"Property","2048":"Method","16777216":"Reference"},"rows":[{"id":0,"kind":1,"name":"index","url":"modules/index.html","classes":"tsd-kind-module"},{"id":1,"kind":32,"name":"Spotify","url":"modules/index.html#spotify","classes":"tsd-kind-variable tsd-parent-kind-module","parent":"index"},{"id":2,"kind":16777216,"name":"default","url":"modules/index.html#default","classes":"tsd-kind-reference tsd-parent-kind-module","parent":"index"},{"id":3,"kind":1,"name":"Spotify","url":"modules/spotify.html","classes":"tsd-kind-module"},{"id":4,"kind":128,"name":"default","url":"classes/spotify.default.html","classes":"tsd-kind-class tsd-parent-kind-module","parent":"Spotify"},{"id":5,"kind":512,"name":"constructor","url":"classes/spotify.default.html#constructor","classes":"tsd-kind-constructor tsd-parent-kind-class tsd-is-overwrite","parent":"Spotify.default"},{"id":6,"kind":2048,"name":"getTrack","url":"classes/spotify.default.html#gettrack","classes":"tsd-kind-method tsd-parent-kind-class","parent":"Spotify.default"},{"id":7,"kind":2048,"name":"getAlbum","url":"classes/spotify.default.html#getalbum","classes":"tsd-kind-method tsd-parent-kind-class","parent":"Spotify.default"},{"id":8,"kind":2048,"name":"getArtist","url":"classes/spotify.default.html#getartist","classes":"tsd-kind-method tsd-parent-kind-class","parent":"Spotify.default"},{"id":9,"kind":2048,"name":"getArtistAlbums","url":"classes/spotify.default.html#getartistalbums","classes":"tsd-kind-method tsd-parent-kind-class","parent":"Spotify.default"},{"id":10,"kind":2048,"name":"getPlaylist","url":"classes/spotify.default.html#getplaylist","classes":"tsd-kind-method tsd-parent-kind-class","parent":"Spotify.default"},{"id":11,"kind":2048,"name":"getID","url":"classes/spotify.default.html#getid","classes":"tsd-kind-method tsd-parent-kind-class","parent":"Spotify.default"},{"id":12,"kind":2048,"name":"downloadTrack","url":"classes/spotify.default.html#downloadtrack","classes":"tsd-kind-method tsd-parent-kind-class tsd-has-type-parameter","parent":"Spotify.default"},{"id":13,"kind":2048,"name":"downloadTrackFromInfo","url":"classes/spotify.default.html#downloadtrackfrominfo","classes":"tsd-kind-method tsd-parent-kind-class","parent":"Spotify.default"},{"id":14,"kind":2048,"name":"downloadPlaylist","url":"classes/spotify.default.html#downloadplaylist","classes":"tsd-kind-method tsd-parent-kind-class","parent":"Spotify.default"},{"id":15,"kind":2048,"name":"downloadAlbum","url":"classes/spotify.default.html#downloadalbum","classes":"tsd-kind-method tsd-parent-kind-class","parent":"Spotify.default"},{"id":16,"kind":2048,"name":"getTracksFromPlaylist","url":"classes/spotify.default.html#gettracksfromplaylist","classes":"tsd-kind-method tsd-parent-kind-class","parent":"Spotify.default"},{"id":17,"kind":2048,"name":"getTracksFromAlbum","url":"classes/spotify.default.html#gettracksfromalbum","classes":"tsd-kind-method tsd-parent-kind-class","parent":"Spotify.default"},{"id":18,"kind":1024,"name":"nextTokenRefreshTime","url":"classes/spotify.default.html#nexttokenrefreshtime","classes":"tsd-kind-property tsd-parent-kind-class tsd-is-inherited","parent":"Spotify.default"},{"id":19,"kind":2048,"name":"verifyCredentials","url":"classes/spotify.default.html#verifycredentials","classes":"tsd-kind-method tsd-parent-kind-class tsd-is-inherited","parent":"Spotify.default"},{"id":20,"kind":2048,"name":"checkCredentials","url":"classes/spotify.default.html#checkcredentials","classes":"tsd-kind-method tsd-parent-kind-class tsd-is-inherited","parent":"Spotify.default"},{"id":21,"kind":2048,"name":"requestTokens","url":"classes/spotify.default.html#requesttokens","classes":"tsd-kind-method tsd-parent-kind-class tsd-is-inherited","parent":"Spotify.default"},{"id":22,"kind":2048,"name":"refreshToken","url":"classes/spotify.default.html#refreshtoken","classes":"tsd-kind-method tsd-parent-kind-class tsd-is-inherited","parent":"Spotify.default"},{"id":23,"kind":2048,"name":"extractTrack","url":"classes/spotify.default.html#extracttrack","classes":"tsd-kind-method tsd-parent-kind-class tsd-is-inherited","parent":"Spotify.default"},{"id":24,"kind":2048,"name":"extractPlaylist","url":"classes/spotify.default.html#extractplaylist","classes":"tsd-kind-method tsd-parent-kind-class tsd-is-inherited","parent":"Spotify.default"},{"id":25,"kind":2048,"name":"extractAlbum","url":"classes/spotify.default.html#extractalbum","classes":"tsd-kind-method tsd-parent-kind-class tsd-is-inherited","parent":"Spotify.default"},{"id":26,"kind":2048,"name":"extractArtist","url":"classes/spotify.default.html#extractartist","classes":"tsd-kind-method tsd-parent-kind-class tsd-is-inherited","parent":"Spotify.default"},{"id":27,"kind":2048,"name":"extractArtistAlbums","url":"classes/spotify.default.html#extractartistalbums","classes":"tsd-kind-method tsd-parent-kind-class tsd-is-inherited","parent":"Spotify.default"}],"index":{"version":"2.3.9","fields":["name","parent"],"fieldVectors":[["name/0",[0,21.145]],["parent/0",[]],["name/1",[1,21.145]],["parent/1",[0,2.05]],["name/2",[2,24.51]],["parent/2",[0,2.05]],["name/3",[1,21.145]],["parent/3",[]],["name/4",[2,24.51]],["parent/4",[1,2.05]],["name/5",[3,29.618]],["parent/5",[4,0.204]],["name/6",[5,29.618]],["parent/6",[4,0.204]],["name/7",[6,29.618]],["parent/7",[4,0.204]],["name/8",[7,29.618]],["parent/8",[4,0.204]],["name/9",[8,29.618]],["parent/9",[4,0.204]],["name/10",[9,29.618]],["parent/10",[4,0.204]],["name/11",[10,29.618]],["parent/11",[4,0.204]],["name/12",[11,29.618]],["parent/12",[4,0.204]],["name/13",[12,29.618]],["parent/13",[4,0.204]],["name/14",[13,29.618]],["parent/14",[4,0.204]],["name/15",[14,29.618]],["parent/15",[4,0.204]],["name/16",[15,29.618]],["parent/16",[4,0.204]],["name/17",[16,29.618]],["parent/17",[4,0.204]],["name/18",[17,29.618]],["parent/18",[4,0.204]],["name/19",[18,29.618]],["parent/19",[4,0.204]],["name/20",[19,29.618]],["parent/20",[4,0.204]],["name/21",[20,29.618]],["parent/21",[4,0.204]],["name/22",[21,29.618]],["parent/22",[4,0.204]],["name/23",[22,29.618]],["parent/23",[4,0.204]],["name/24",[23,29.618]],["parent/24",[4,0.204]],["name/25",[24,29.618]],["parent/25",[4,0.204]],["name/26",[25,29.618]],["parent/26",[4,0.204]],["name/27",[26,29.618]],["parent/27",[4,0.204]]],"invertedIndex":[["checkcredentials",{"_index":19,"name":{"20":{}},"parent":{}}],["constructor",{"_index":3,"name":{"5":{}},"parent":{}}],["default",{"_index":2,"name":{"2":{},"4":{}},"parent":{}}],["downloadalbum",{"_index":14,"name":{"15":{}},"parent":{}}],["downloadplaylist",{"_index":13,"name":{"14":{}},"parent":{}}],["downloadtrack",{"_index":11,"name":{"12":{}},"parent":{}}],["downloadtrackfrominfo",{"_index":12,"name":{"13":{}},"parent":{}}],["extractalbum",{"_index":24,"name":{"25":{}},"parent":{}}],["extractartist",{"_index":25,"name":{"26":{}},"parent":{}}],["extractartistalbums",{"_index":26,"name":{"27":{}},"parent":{}}],["extractplaylist",{"_index":23,"name":{"24":{}},"parent":{}}],["extracttrack",{"_index":22,"name":{"23":{}},"parent":{}}],["getalbum",{"_index":6,"name":{"7":{}},"parent":{}}],["getartist",{"_index":7,"name":{"8":{}},"parent":{}}],["getartistalbums",{"_index":8,"name":{"9":{}},"parent":{}}],["getid",{"_index":10,"name":{"11":{}},"parent":{}}],["getplaylist",{"_index":9,"name":{"10":{}},"parent":{}}],["gettrack",{"_index":5,"name":{"6":{}},"parent":{}}],["gettracksfromalbum",{"_index":16,"name":{"17":{}},"parent":{}}],["gettracksfromplaylist",{"_index":15,"name":{"16":{}},"parent":{}}],["index",{"_index":0,"name":{"0":{}},"parent":{"1":{},"2":{}}}],["nexttokenrefreshtime",{"_index":17,"name":{"18":{}},"parent":{}}],["refreshtoken",{"_index":21,"name":{"22":{}},"parent":{}}],["requesttokens",{"_index":20,"name":{"21":{}},"parent":{}}],["spotify",{"_index":1,"name":{"1":{},"3":{}},"parent":{"4":{}}}],["spotify.default",{"_index":4,"name":{},"parent":{"5":{},"6":{},"7":{},"8":{},"9":{},"10":{},"11":{},"12":{},"13":{},"14":{},"15":{},"16":{},"17":{},"18":{},"19":{},"20":{},"21":{},"22":{},"23":{},"24":{},"25":{},"26":{},"27":{}}}],["verifycredentials",{"_index":18,"name":{"19":{}},"parent":{}}]],"pipeline":[]}} -------------------------------------------------------------------------------- /docs/classes/spotify.default.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | default | spotifydl-core 7 | 8 | 9 | 10 | 11 | 12 | 13 |
14 |
15 |
16 |
17 | 28 |
29 |
30 | Options 31 |
32 |
33 | All 34 |
    35 |
  • Public
  • 36 |
  • Public/Protected
  • 37 |
  • All
  • 38 |
39 |
40 | 41 | 42 |
43 |
44 | Menu 45 |
46 |
47 |
48 |
49 |
50 |
51 | 62 |

Class default

63 |
64 |
65 |
66 |
67 |
68 |
69 |
70 |

Hierarchy

71 |
    72 |
  • 73 | SpotifyApi 74 |
      75 |
    • 76 | default 77 |
    • 78 |
    79 |
  • 80 |
81 |
82 |
83 |

Index

84 |
85 |
86 |
87 |

Constructors

88 | 91 |
92 |
93 |

Properties

94 | 97 |
98 |
99 |

Methods

100 | 123 |
124 |
125 |
126 |
127 |
128 |

Constructors

129 |
130 | 131 |

constructor

132 |
    133 |
  • new default(auth: IAuth): default
  • 134 |
135 |
    136 |
  • 137 | 143 |

    Parameters

    144 |
      145 |
    • 146 |
      auth: IAuth
      147 |
    • 148 |
    149 |

    Returns default

    150 |
  • 151 |
152 |
153 |
154 |
155 |

Properties

156 |
157 | 158 |

nextTokenRefreshTime

159 |
nextTokenRefreshTime: Date
160 | 166 |
167 |
168 |
169 |

Methods

170 |
171 | 172 |

checkCredentials

173 |
    174 |
  • checkCredentials(): Promise<void>
  • 175 |
176 |
    177 |
  • 178 | 184 |

    Returns Promise<void>

    185 |
  • 186 |
187 |
188 |
189 | 190 |

downloadAlbum

191 |
    192 |
  • downloadAlbum(url: string): Promise<(string | Buffer)[]>
  • 193 |
194 |
    195 |
  • 196 | 201 |
    202 |
    203 |

    Downloads the tracks of a Album

    204 |
    205 |
    206 |

    Parameters

    207 |
      208 |
    • 209 |
      url: string
      210 |
      211 |

      URL of the Album

      212 |
      213 |
    • 214 |
    215 |

    Returns Promise<(string | Buffer)[]>

    216 |

    Promise<(string|Buffer)[]>

    217 |
  • 218 |
219 |
220 |
221 | 222 |

downloadPlaylist

223 |
    224 |
  • downloadPlaylist(url: string): Promise<(string | Buffer)[]>
  • 225 |
226 |
    227 |
  • 228 | 233 |
    234 |
    235 |

    Downloads the tracks of a playlist

    236 |
    237 |
    238 |

    Parameters

    239 |
      240 |
    • 241 |
      url: string
      242 |
      243 |

      URL of the playlist

      244 |
      245 |
    • 246 |
    247 |

    Returns Promise<(string | Buffer)[]>

    248 |

    Promise<(string|Buffer)[]>

    249 |
  • 250 |
251 |
252 |
253 | 254 |

downloadTrack

255 |
    256 |
  • downloadTrack<T>(url: string, filename?: T): Promise<T extends undefined ? Buffer : string>
  • 257 |
258 |
    259 |
  • 260 | 265 |
    266 |
    267 |

    Downloads the given spotify track

    268 |
    269 |
    270 |

    Type parameters

    271 |
      272 |
    • 273 |

      T: undefined | string

      274 |
    • 275 |
    276 |

    Parameters

    277 |
      278 |
    • 279 |
      url: string
      280 |
      281 |

      Url to download

      282 |
      283 |
    • 284 |
    • 285 |
      Optional filename: T
      286 |
      287 |

      file to save to

      288 |
      289 |
    • 290 |
    291 |

    Returns Promise<T extends undefined ? Buffer : string>

    292 |

    buffer if no filename is provided and string if it is

    293 |
  • 294 |
295 |
296 |
297 | 298 |

downloadTrackFromInfo

299 |
    300 |
  • downloadTrackFromInfo(info: default): Promise<Buffer>
  • 301 |
302 |
    303 |
  • 304 | 309 |
    310 |
    311 |

    Gets the Buffer of track from the info

    312 |
    313 |
    314 |

    Parameters

    315 |
      316 |
    • 317 |
      info: default
      318 |
      319 |

      info of the track got from spotify.getTrack()

      320 |
      321 |
    • 322 |
    323 |

    Returns Promise<Buffer>

    324 |
  • 325 |
326 |
327 |
328 | 329 |

extractAlbum

330 |
    331 |
  • extractAlbum(albumId: string): Promise<default>
  • 332 |
333 |
    334 |
  • 335 | 341 |

    Parameters

    342 |
      343 |
    • 344 |
      albumId: string
      345 |
    • 346 |
    347 |

    Returns Promise<default>

    348 |
  • 349 |
350 |
351 |
352 | 353 |

extractArtist

354 |
    355 |
  • extractArtist(artistId: string): Promise<default>
  • 356 |
357 |
    358 |
  • 359 | 365 |

    Parameters

    366 |
      367 |
    • 368 |
      artistId: string
      369 |
    • 370 |
    371 |

    Returns Promise<default>

    372 |
  • 373 |
374 |
375 |
376 | 377 |

extractArtistAlbums

378 |
    379 |
  • extractArtistAlbums(artistId: string): Promise<AlbumObjectSimplified[]>
  • 380 |
381 |
    382 |
  • 383 | 389 |

    Parameters

    390 |
      391 |
    • 392 |
      artistId: string
      393 |
    • 394 |
    395 |

    Returns Promise<AlbumObjectSimplified[]>

    396 |
  • 397 |
398 |
399 |
400 | 401 |

extractPlaylist

402 |
    403 |
  • extractPlaylist(playlistId: string): Promise<default>
  • 404 |
405 |
    406 |
  • 407 | 413 |

    Parameters

    414 |
      415 |
    • 416 |
      playlistId: string
      417 |
    • 418 |
    419 |

    Returns Promise<default>

    420 |
  • 421 |
422 |
423 |
424 | 425 |

extractTrack

426 |
    427 |
  • extractTrack(trackId: string): Promise<default>
  • 428 |
429 |
    430 |
  • 431 | 437 |

    Parameters

    438 |
      439 |
    • 440 |
      trackId: string
      441 |
    • 442 |
    443 |

    Returns Promise<default>

    444 |
  • 445 |
446 |
447 |
448 | 449 |

getAlbum

450 |
    451 |
  • getAlbum(url: string): Promise<default>
  • 452 |
453 |
    454 |
  • 455 | 460 |
    461 |
    462 |

    Gets the info the given album URL

    463 |
    464 |
    465 |

    Parameters

    466 |
      467 |
    • 468 |
      url: string
      469 |
    • 470 |
    471 |

    Returns Promise<default>

    472 |

    Album

    473 |
  • 474 |
475 |
476 |
477 | 478 |

getArtist

479 |
    480 |
  • getArtist(url: string): Promise<default>
  • 481 |
482 |
    483 |
  • 484 | 489 |
    490 |
    491 |

    Gets the info of the given Artist URL

    492 |
    493 |
    494 |

    Parameters

    495 |
      496 |
    • 497 |
      url: string
      498 |
    • 499 |
    500 |

    Returns Promise<default>

    501 |

    Artist

    502 |
  • 503 |
504 |
505 |
506 | 507 |

getArtistAlbums

508 |
    509 |
  • getArtistAlbums(url: string): Promise<{ albums: default[]; artist: default }>
  • 510 |
511 |
    512 |
  • 513 | 518 |
    519 |
    520 |

    Gets the list of albums from the given Artists URL

    521 |
    522 |
    523 |

    Parameters

    524 |
      525 |
    • 526 |
      url: string
      527 |
    • 528 |
    529 |

    Returns Promise<{ albums: default[]; artist: default }>

    530 |

    Albums

    531 |
  • 532 |
533 |
534 |
535 | 536 |

getID

537 |
    538 |
  • getID(url: string): string
  • 539 |
540 |
    541 |
  • 542 | 547 |

    Parameters

    548 |
      549 |
    • 550 |
      url: string
      551 |
    • 552 |
    553 |

    Returns string

    554 |
  • 555 |
556 |
557 |
558 | 559 |

getPlaylist

560 |
    561 |
  • getPlaylist(url: string): Promise<default>
  • 562 |
563 |
    564 |
  • 565 | 570 |
    571 |
    572 |

    Gets the playlist info from URL

    573 |
    574 |
    575 |

    Parameters

    576 |
      577 |
    • 578 |
      url: string
      579 |
      580 |

      URL of the playlist

      581 |
      582 |
    • 583 |
    584 |

    Returns Promise<default>

    585 |
  • 586 |
587 |
588 |
589 | 590 |

getTrack

591 |
    592 |
  • getTrack(url: string): Promise<default>
  • 593 |
594 |
    595 |
  • 596 | 601 |
    602 |
    603 |

    Get the track details of the given track URL

    604 |
    605 |
    606 |

    Parameters

    607 |
      608 |
    • 609 |
      url: string
      610 |
    • 611 |
    612 |

    Returns Promise<default>

    613 |

    Track

    614 |
  • 615 |
616 |
617 |
618 | 619 |

getTracksFromAlbum

620 |
    621 |
  • getTracksFromAlbum(url: string): Promise<{ name: string; total_tracks: number; tracks: default[] }>
  • 622 |
623 |
    624 |
  • 625 | 630 |
    631 |
    632 |

    Gets the info of tracks from Album URL

    633 |
    634 |
    635 |

    Parameters

    636 |
      637 |
    • 638 |
      url: string
      639 |
      640 |

      URL of the playlist

      641 |
      642 |
    • 643 |
    644 |

    Returns Promise<{ name: string; total_tracks: number; tracks: default[] }>

    645 |
  • 646 |
647 |
648 |
649 | 650 |

getTracksFromPlaylist

651 |
    652 |
  • getTracksFromPlaylist(url: string): Promise<{ name: string; total_tracks: number; tracks: default[] }>
  • 653 |
654 |
    655 |
  • 656 | 661 |
    662 |
    663 |

    Gets the info of tracks from playlist URL

    664 |
    665 |
    666 |

    Parameters

    667 |
      668 |
    • 669 |
      url: string
      670 |
      671 |

      URL of the playlist

      672 |
      673 |
    • 674 |
    675 |

    Returns Promise<{ name: string; total_tracks: number; tracks: default[] }>

    676 |
  • 677 |
678 |
679 |
680 | 681 |

refreshToken

682 |
    683 |
  • refreshToken(): Promise<void>
  • 684 |
685 |
    686 |
  • 687 | 693 |

    Returns Promise<void>

    694 |
  • 695 |
696 |
697 |
698 | 699 |

requestTokens

700 |
    701 |
  • requestTokens(): Promise<void>
  • 702 |
703 |
    704 |
  • 705 | 711 |

    Returns Promise<void>

    712 |
  • 713 |
714 |
715 |
716 | 717 |

verifyCredentials

718 |
    719 |
  • verifyCredentials(): Promise<void>
  • 720 |
721 |
    722 |
  • 723 | 729 |

    Returns Promise<void>

    730 |
  • 731 |
732 |
733 |
734 |
735 | 832 |
833 |
834 | 853 |
854 |

Generated using TypeDoc

855 |
856 |
857 | 858 | 859 | -------------------------------------------------------------------------------- /docs/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | spotifydl-core 7 | 8 | 9 | 10 | 11 | 12 | 13 |
14 |
15 |
16 |
17 | 28 |
29 |
30 | Options 31 |
32 |
33 | All 34 |
    35 |
  • Public
  • 36 |
  • Public/Protected
  • 37 |
  • All
  • 38 |
39 |
40 | 41 | 42 |
43 |
44 | Menu 45 |
46 |
47 |
48 |
49 |
50 |
51 |

spotifydl-core

52 |
53 |
54 |
55 |
56 |
57 |
58 |
59 |
60 | 61 |

Spotifydl-Core

62 |
63 | Never gonna give up, never gonna let you down 64 | 65 |

A simple package to download music tracks from spotify 🎵

66 |
67 |
68 | 69 |

Installation

70 |
71 |
> npm i spotifydl-core
 72 | 
73 | 74 |

Intialization

75 |
76 |

You need to intialize the Spotify Class before acessing the methods inside it.

77 |
const Spotify = require('spotifydl-core').default
 78 | //import Spotify from 'spotifydl-core'
 79 | 
 80 | const credentials = {
 81 |     clientId: 'your-client-id',
 82 |     clientSecret: 'your-client-secret'
 83 | }
 84 | const spotify = new Spotify(credentials)
 85 | 
86 | 87 |

Methods

88 |
89 |
90 |

NOTE: Only some methods are shown here. Checkout the docs depth

91 |
92 |

Get Track ⏭️

93 |
await spotify.getTrack(track_url) 
 94 | 
 95 | // For Example: track_url = 'https://open.spotify.com/track/1Ub6VfiTXgyV8HnsfzrZzC?si=4412ef4ebd8141ab'
 96 | 
 97 | // Input: url of the track, Type: string
 98 | 
99 |

Download Track/Song ⬇️

100 |
await spotify.downloadTrack(track_url, file_name)
101 | 
102 | // For Example: track_url = 'https://open.spotify.com/track/1Ub6VfiTXgyV8HnsfzrZzC?si=4412ef4ebd8141ab' & file_name = 'song.mp3'
103 | 
104 | // Input: url of the track and name of the filename, Both Type: string
105 | 
106 | // It'll return buffer (promise) if you don't provide any filename
107 | 
108 | 
109 |

Get Artist 👩‍🎤🧑‍🎤

110 |
await spotify.getArtist(artist_url)
111 | 
112 | // For Example: artist_url = 'https://open.spotify.com/artist/3B9O5mYYw89fFXkwKh7jCS'
113 | 
114 | // Input: url of the artist, Type: string
115 | 
116 |

Get Album 💽

117 |
await spotify.getAlbum(album_url)
118 | 
119 | // For Example: album_url = 'https://open.spotify.com/album/3u3WsbVPLT0fXiClx9GYD9?si=pfGAdL3VRiid0M3Ln_0DNg'
120 | 
121 | // Input: url of the album, Type: string
122 | 
123 |

Get Playlist 🎧

124 |
await spotify.getPlylist(playlist_url)
125 | 
126 | // Input: url of the playlist, Type: string
127 | 
128 |

Download an Entire playlist

129 |
await spotify.downloadPlaylist(playlist_url)
130 | 
131 | //It'll return an array containing the Buffer of the songs in the playlist
132 | 
133 | 134 |

Usage Example

135 |
136 |
const fs = require('fs-extra') 
137 | // Initialization and Authentication 
138 | const Spotify = require('spotifydl-core').default // Import the library 
139 | const spotify = new Spotify({ // Authentication
140 |     clientId: 'acc6302297e040aeb6e4ac1fbdfd62c3', // <-- add your own clientId 
141 |     clientSecret: '0e8439a1280a43aba9a5bc0a16f3f009', // <-- add your own clientSecret 
142 | })
143 | /* To learn more about clientId and Secret  , 
144 | visit https://developer.spotify.com/documentation/general/guides/app-settings/ 
145 | */
146 | 
147 | // Declaring the respective url in 'links' object 
148 | const links = {
149 |     artist: 'https://open.spotify.com/artist/7ky9g1jEjCsjNjZbYuflUJ?si=2To3fmc-T9KuyyrQ-Qp5KQ', // Url of the artist you want to gather info about
150 |     album: 'https://open.spotify.com/album/3u3WsbVPLT0fXiClx9GYD9?si=pfGAdL3VRiid0M3Ln_0DNg', // Url of the album you want to gather info about
151 |     song: 'https://open.spotify.com/track/1Ub6VfiTXgyV8HnsfzrZzC?si=4412ef4ebd8141ab' // Url of the song you want to gather info about or download
152 | };
153 | 
154 | // Engine 
155 | (async () => {
156 |     const data = await spotify.getTrack(links.song) // Waiting for the data 🥱
157 |     console.log('Downloading: ', data.name, 'by:', data.artists.join(' ')) // Keep an eye on the progress
158 |     const song = await spotify.downloadTrack(links.song) // Downloading goes brr brr 
159 |     fs.writeFileSync('song.mp3', song) // Let's write the buffer to the woofer (i mean file, hehehe) 
160 | })()
161 | 
162 | //spotify.verifyCredentials().then(() => Promise.all([spotify.getTrack(links.song), spotify.getAlbum(links.album), spotify.getArtistAlbums(links.artist)]).then(console.log))
163 | 
164 | 165 |

🙇‍ Special Thanks to them

166 |
167 | 171 |
172 |
173 | 192 |
193 |
194 | 207 |
208 |

Generated using TypeDoc

209 |
210 |
211 | 212 | 213 | -------------------------------------------------------------------------------- /docs/modules.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | spotifydl-core 7 | 8 | 9 | 10 | 11 | 12 | 13 |
14 |
15 |
16 |
17 | 28 |
29 |
30 | Options 31 |
32 |
33 | All 34 |
    35 |
  • Public
  • 36 |
  • Public/Protected
  • 37 |
  • All
  • 38 |
39 |
40 | 41 | 42 |
43 |
44 | Menu 45 |
46 |
47 |
48 |
49 |
50 |
51 |

spotifydl-core

52 |
53 |
54 |
55 |
56 |
57 |
58 |
59 |

Index

60 |
61 |
62 |
63 |

Modules

64 | 68 |
69 |
70 |
71 |
72 |
73 | 92 |
93 |
94 | 107 |
108 |

Generated using TypeDoc

109 |
110 |
111 | 112 | 113 | -------------------------------------------------------------------------------- /docs/modules/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | index | spotifydl-core 7 | 8 | 9 | 10 | 11 | 12 | 13 |
14 |
15 |
16 |
17 | 28 |
29 |
30 | Options 31 |
32 |
33 | All 34 |
    35 |
  • Public
  • 36 |
  • Public/Protected
  • 37 |
  • All
  • 38 |
39 |
40 | 41 | 42 |
43 |
44 | Menu 45 |
46 |
47 |
48 |
49 |
50 |
51 | 59 |

Module index

60 |
61 |
62 |
63 |
64 |
65 |
66 |
67 |

Index

68 |
69 |
70 |
71 |

References

72 | 75 |
76 |
77 |

Variables

78 | 81 |
82 |
83 |
84 |
85 |
86 |

References

87 |
88 | 89 |

default

90 | Renames and exports Spotify 91 |
92 |
93 |
94 |

Variables

95 |
96 | 97 |

Const Spotify

98 |
Spotify: typeof default = ...
99 | 104 |
105 |
106 |
107 | 132 |
133 |
134 | 147 |
148 |

Generated using TypeDoc

149 |
150 |
151 | 152 | 153 | -------------------------------------------------------------------------------- /docs/modules/spotify.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | Spotify | spotifydl-core 7 | 8 | 9 | 10 | 11 | 12 | 13 |
14 |
15 |
16 |
17 | 28 |
29 |
30 | Options 31 |
32 |
33 | All 34 |
    35 |
  • Public
  • 36 |
  • Public/Protected
  • 37 |
  • All
  • 38 |
39 |
40 | 41 | 42 |
43 |
44 | Menu 45 |
46 |
47 |
48 |
49 |
50 |
51 | 59 |

Module Spotify

60 |
61 |
62 |
63 |
64 |
65 |
66 |
67 |

Index

68 |
69 |
70 |
71 |

Classes

72 | 75 |
76 |
77 |
78 |
79 |
80 | 102 |
103 |
104 | 117 |
118 |

Generated using TypeDoc

119 |
120 |
121 | 122 | 123 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "spotifydl-core", 3 | "version": "0.2.0", 4 | "description": "Spotify downloader for node", 5 | "main": "dist/index.js", 6 | "files": [ 7 | "dist/**/*" 8 | ], 9 | "types": "dist", 10 | "scripts": { 11 | "build": "tsc -p .", 12 | "test": "node tests", 13 | "docs": "typedoc", 14 | "prepare": "npm run build", 15 | "prettier-format": "prettier --config .prettierrc \"src/**/*.ts\" --write" 16 | }, 17 | "repository": { 18 | "type": "git", 19 | "url": "git+https://github.com/alensaito1/spotifydl-core.git" 20 | }, 21 | "keywords": [ 22 | "spotify", 23 | "spotify-downloader", 24 | "music" 25 | ], 26 | "author": "Alen Yohannan", 27 | "license": "MIT", 28 | "bugs": { 29 | "url": "https://github.com/alensaito1/spotifydl-core/issues" 30 | }, 31 | "homepage": "https://github.com/alensaito1/spotifydl-core#readme", 32 | "devDependencies": { 33 | "@types/fluent-ffmpeg": "^2.1.21", 34 | "@types/fs-extra": "^11.0.1", 35 | "@types/node": "^15.3.0", 36 | "@types/spotify-web-api-node": "^5.0.7", 37 | "@types/yt-search": "^2.3.2", 38 | "@typescript-eslint/eslint-plugin": "^5.57.1", 39 | "@typescript-eslint/parser": "^5.57.1", 40 | "eslint": "^8.38.0", 41 | "prettier": "^2.8.7", 42 | "typedoc": "^0.24.0", 43 | "typescript": "^5.0.4" 44 | }, 45 | "dependencies": { 46 | "axios": "^1.3.5", 47 | "fluent-ffmpeg": "^2.1.2", 48 | "fs-extra": "^11.1.1", 49 | "spotify-web-api-node": "^5.0.2", 50 | "yt-search": "^2.10.4", 51 | "ytdl-core": "^4.11.3" 52 | } 53 | } 54 | -------------------------------------------------------------------------------- /src/Spotify.ts: -------------------------------------------------------------------------------- 1 | import { promises, unlink } from 'fs-extra' 2 | import SpotifyApi, { IAuth, UserObjectPublic } from './lib/API' 3 | import Artist from './lib/details/Atrist' 4 | import Playlist from './lib/details/Playlist' 5 | import SongDetails from './lib/details/Track' 6 | import { downloadYT, downloadYTAndSave } from './lib/download' 7 | import SpotifyDlError from './lib/Error' 8 | import getYtlink from './lib/getYtlink' 9 | import metadata from './lib/metadata' 10 | 11 | export default class SpotifyFetcher extends SpotifyApi { 12 | constructor(auth: IAuth) { 13 | super(auth) 14 | } 15 | 16 | /** 17 | * Get the track details of the given track URL 18 | * @param url 19 | * @returns {SongDetails} Track 20 | */ 21 | getTrack = async (url: string): Promise => { 22 | await this.verifyCredentials() 23 | return await this.extractTrack(this.getID(url)) 24 | } 25 | 26 | /** 27 | * Gets the info the given album URL 28 | * @param url 29 | * @returns {Playlist} Album 30 | */ 31 | getAlbum = async (url: string): Promise => { 32 | await this.verifyCredentials() 33 | return await this.extractAlbum(this.getID(url)) 34 | } 35 | 36 | /** 37 | * Gets the info of the given Artist URL 38 | * @param url 39 | * @returns {Artist} Artist 40 | */ 41 | getArtist = async (url: string): Promise => { 42 | await this.verifyCredentials() 43 | return await this.extractArtist(this.getID(url)) 44 | } 45 | 46 | /** 47 | * Gets the list of albums from the given Artists URL 48 | * @param url 49 | * @returns {Playlist[]} Albums 50 | */ 51 | getArtistAlbums = async ( 52 | url: string 53 | ): Promise<{ 54 | albums: Playlist[] 55 | artist: Artist 56 | }> => { 57 | await this.verifyCredentials() 58 | const artistResult = await this.getArtist(url) 59 | const albumsResult = await this.extractArtistAlbums(artistResult.id) 60 | const albumIds = albumsResult.map((album) => album.id) 61 | const albumInfos = [] 62 | for (let x = 0; x < albumIds.length; x++) { 63 | albumInfos.push(await this.extractAlbum(albumIds[x])) 64 | } 65 | return { 66 | albums: albumInfos, 67 | artist: artistResult 68 | } 69 | } 70 | 71 | /** 72 | * Gets the playlist info from URL 73 | * @param url URL of the playlist 74 | * @returns 75 | */ 76 | getPlaylist = async (url: string): Promise => { 77 | await this.verifyCredentials() 78 | return await this.extractPlaylist(this.getID(url)) 79 | } 80 | 81 | getID = (url: string): string => { 82 | const splits = url.split('/') 83 | return splits[splits.length - 1] 84 | } 85 | 86 | /** 87 | * Downloads the given spotify track 88 | * @param url Url to download 89 | * @param filename file to save to 90 | * @returns `buffer` if no filename is provided and `string` if it is 91 | */ 92 | downloadTrack = async ( 93 | url: string, 94 | filename?: T 95 | ): Promise => { 96 | await this.verifyCredentials() 97 | const info = await this.getTrack(url) 98 | const link = await getYtlink(`${info.name} ${info.artists[0]}`) 99 | if (!link) throw new SpotifyDlError(`Couldn't get a download URL for the track: ${info.name}`) 100 | const data = await downloadYTAndSave(link, filename) 101 | await metadata(info, data) 102 | if (!filename) { 103 | const buffer = await promises.readFile(data) 104 | unlink(data) 105 | /* eslint-disable @typescript-eslint/no-explicit-any */ 106 | return buffer as any 107 | } 108 | /* eslint-disable @typescript-eslint/no-explicit-any */ 109 | return data as any 110 | } 111 | 112 | /** 113 | * Gets the Buffer of track from the info 114 | * @param info info of the track got from `spotify.getTrack()` 115 | * @returns 116 | */ 117 | downloadTrackFromInfo = async (info: SongDetails): Promise => { 118 | const link = await getYtlink(`${info.name} ${info.artists[0]}`) 119 | if (!link) throw new SpotifyDlError(`Couldn't get a download URL for the track: ${info.name}`) 120 | return await downloadYT(link) 121 | } 122 | 123 | private downloadBatch = async (url: string, type: 'album' | 'playlist'): Promise<(string | Buffer)[]> => { 124 | await this.verifyCredentials() 125 | const playlist = await this[type === 'album' ? 'getAlbum' : 'getPlaylist'](url) 126 | return Promise.all( 127 | playlist.tracks.map(async (track) => { 128 | try { 129 | return await this.downloadTrack(track) 130 | } catch (err) { 131 | return '' 132 | } 133 | }) 134 | ) 135 | } 136 | 137 | /** 138 | * Downloads the tracks of a playlist 139 | * @param url URL of the playlist 140 | * @returns `Promise<(string|Buffer)[]>` 141 | */ 142 | downloadPlaylist = async (url: string): Promise<(string | Buffer)[]> => await this.downloadBatch(url, 'playlist') 143 | 144 | /** 145 | * Downloads the tracks of a Album 146 | * @param url URL of the Album 147 | * @returns `Promise<(string|Buffer)[]>` 148 | */ 149 | downloadAlbum = async (url: string): Promise<(string | Buffer)[]> => await this.downloadBatch(url, 'album') 150 | 151 | /** 152 | * Gets the info of tracks from playlist URL 153 | * @param url URL of the playlist 154 | */ 155 | getTracksFromPlaylist = async ( 156 | url: string 157 | ): Promise<{ name: string; total_tracks: number; tracks: SongDetails[] }> => { 158 | await this.verifyCredentials() 159 | const playlist = await this.getPlaylist(url) 160 | const tracks = await Promise.all(playlist.tracks.map((track) => this.getTrack(track))) 161 | return { 162 | name: playlist.name, 163 | total_tracks: playlist.total_tracks, 164 | tracks 165 | } 166 | } 167 | 168 | /** 169 | * Gets the info of tracks from Album URL 170 | * @param url URL of the playlist 171 | */ 172 | getTracksFromAlbum = async ( 173 | url: string 174 | ): Promise<{ name: string; total_tracks: number; tracks: SongDetails[] }> => { 175 | await this.verifyCredentials() 176 | const playlist = await this.getAlbum(url) 177 | const tracks = await Promise.all(playlist.tracks.map((track) => this.getTrack(track))) 178 | return { 179 | name: playlist.name, 180 | total_tracks: playlist.total_tracks, 181 | tracks 182 | } 183 | } 184 | 185 | getSpotifyUser = async (id: string): Promise => await this.getUser(id) 186 | } 187 | -------------------------------------------------------------------------------- /src/index.ts: -------------------------------------------------------------------------------- 1 | import SpotifyFetcher from './Spotify' 2 | 3 | export const Spotify = SpotifyFetcher 4 | export default Spotify 5 | -------------------------------------------------------------------------------- /src/lib/API.ts: -------------------------------------------------------------------------------- 1 | import SpotifyAPI from 'spotify-web-api-node' 2 | import Artist from './details/Atrist' 3 | import Playlist from './details/Playlist' 4 | import TrackDetails from './details/Track' 5 | 6 | const MAX_LIMIT_DEFAULT = 50 7 | const REFRESH_ACCESS_TOKEN_SECONDS = 55 * 60 8 | 9 | export default class SpotifyApi { 10 | private spotifyAPI: SpotifyAPI 11 | 12 | nextTokenRefreshTime!: Date 13 | 14 | constructor(private auth: IAuth) { 15 | this.spotifyAPI = new SpotifyAPI(this.auth) 16 | } 17 | 18 | verifyCredentials = async (): Promise => { 19 | if (!this.nextTokenRefreshTime || this.nextTokenRefreshTime < new Date()) { 20 | this.nextTokenRefreshTime = new Date() 21 | this.nextTokenRefreshTime.setSeconds(this.nextTokenRefreshTime.getSeconds() + REFRESH_ACCESS_TOKEN_SECONDS) 22 | await this.checkCredentials() 23 | } 24 | } 25 | 26 | checkCredentials = async (): Promise => { 27 | if (!(await this.spotifyAPI.getRefreshToken())) return void (await this.requestTokens()) 28 | await this.refreshToken() 29 | } 30 | 31 | requestTokens = async (): Promise => { 32 | const data = (await this.spotifyAPI.clientCredentialsGrant()).body 33 | this.spotifyAPI.setAccessToken(data['access_token']) 34 | this.spotifyAPI.setRefreshToken((data as ClientCredentialsGrantResponseEX)['refresh_token']) 35 | } 36 | 37 | refreshToken = async (): Promise => { 38 | const data = (await this.spotifyAPI.refreshAccessToken()).body 39 | this.spotifyAPI.setAccessToken(data['access_token']) 40 | } 41 | 42 | extractTrack = async (trackId: string): Promise => { 43 | const data = (await this.spotifyAPI.getTrack(trackId)).body 44 | const details = new TrackDetails() 45 | details.name = data.name 46 | data.artists.forEach((artist) => { 47 | details.artists.push(artist.name) 48 | }) 49 | details.album_name = data.album.name 50 | details.release_date = data.album.release_date 51 | details.cover_url = data.album.images[0].url 52 | return details 53 | } 54 | 55 | extractPlaylist = async (playlistId: string): Promise => { 56 | const data = (await this.spotifyAPI.getPlaylist(playlistId)).body 57 | const details = new Playlist( 58 | '', 59 | 0, 60 | data.tracks.items.map((item) => item.track!.id) 61 | ) 62 | 63 | details.name = data.name + ' - ' + data.owner.display_name 64 | details.total_tracks = data.tracks.total 65 | if (data.tracks.next) { 66 | let offset = details.tracks.length 67 | while (details.tracks.length < details.total_tracks) { 68 | const playlistTracksData = ( 69 | await this.spotifyAPI.getPlaylistTracks(playlistId, { limit: MAX_LIMIT_DEFAULT, offset: offset }) 70 | ).body 71 | details.tracks = details.tracks.concat(playlistTracksData.items.map((item) => item.track!.id)) 72 | offset += MAX_LIMIT_DEFAULT 73 | } 74 | } 75 | return details 76 | } 77 | 78 | extractAlbum = async (albumId: string): Promise => { 79 | const data = (await this.spotifyAPI.getAlbum(albumId)).body 80 | const details = new Playlist( 81 | '', 82 | 0, 83 | data.tracks.items.map((item) => item.id) 84 | ) 85 | details.name = data.name + ' - ' + data.label 86 | details.total_tracks = data.tracks.total 87 | if (data.tracks.next) { 88 | let offset = details.tracks.length 89 | while (details.tracks.length < data.tracks.total) { 90 | const albumTracks = ( 91 | await this.spotifyAPI.getAlbumTracks(albumId, { limit: MAX_LIMIT_DEFAULT, offset: offset }) 92 | ).body 93 | details.tracks = details.tracks.concat(albumTracks.items.map((item) => item.id)) 94 | offset += MAX_LIMIT_DEFAULT 95 | } 96 | } 97 | return details 98 | } 99 | 100 | extractArtist = async (artistId: string): Promise => { 101 | const data = (await this.spotifyAPI.getArtist(artistId)).body 102 | return new Artist(data.id, data.name, data.href) 103 | } 104 | 105 | extractArtistAlbums = async (artistId: string): Promise => { 106 | const artistAlbums = (await this.spotifyAPI.getArtistAlbums(artistId, { limit: MAX_LIMIT_DEFAULT })).body 107 | let albums = artistAlbums.items 108 | if (artistAlbums.next) { 109 | let offset = albums.length 110 | while (albums.length < artistAlbums.total) { 111 | const additionalArtistAlbums = ( 112 | await this.spotifyAPI.getArtistAlbums(artistId, { limit: MAX_LIMIT_DEFAULT, offset: offset }) 113 | ).body 114 | 115 | albums = albums.concat(additionalArtistAlbums.items) 116 | offset += MAX_LIMIT_DEFAULT 117 | } 118 | } 119 | return albums 120 | } 121 | 122 | getUser = async (id: string): Promise => { 123 | await this.verifyCredentials() 124 | return (await this.spotifyAPI.getUser(id)) as UserObjectPublic 125 | } 126 | } 127 | 128 | export interface IAuth { 129 | clientId: string 130 | clientSecret: string 131 | } 132 | 133 | interface ClientCredentialsGrantResponseEX { 134 | access_token: string 135 | expires_in: number 136 | token_type: string 137 | refresh_token: string 138 | } 139 | 140 | export interface UserObjectPublic { 141 | display_name?: string 142 | external_urls?: { 143 | spotify: string 144 | } 145 | followers?: { 146 | href?: null 147 | total: string 148 | } 149 | href?: string 150 | id?: string 151 | images?: ImageObject[] 152 | type?: 'user' 153 | uri?: string 154 | } 155 | 156 | export interface ImageObject { 157 | height?: number 158 | url: string 159 | width?: number 160 | } 161 | -------------------------------------------------------------------------------- /src/lib/Error.ts: -------------------------------------------------------------------------------- 1 | export default class SpotifyDlError extends Error { 2 | constructor(public message: string, public name = 'TypeError') { 3 | super() 4 | Error.captureStackTrace(this, this.constructor) 5 | } 6 | } 7 | -------------------------------------------------------------------------------- /src/lib/details/Atrist.ts: -------------------------------------------------------------------------------- 1 | import { IArtist } from '../../typings' 2 | 3 | export default class Artist implements IArtist { 4 | constructor(public id = '', public name = '', public herf = '') {} 5 | } 6 | -------------------------------------------------------------------------------- /src/lib/details/Playlist.ts: -------------------------------------------------------------------------------- 1 | import { IPlaylist } from '../../typings' 2 | 3 | export default class Playlist implements IPlaylist { 4 | constructor(public name = '', public total_tracks = 0, public tracks: string[] = []) {} 5 | } 6 | -------------------------------------------------------------------------------- /src/lib/details/Track.ts: -------------------------------------------------------------------------------- 1 | import { ITrack } from '../../typings' 2 | 3 | export default class TrackDetails implements ITrack { 4 | constructor( 5 | public name = '', 6 | public artists: string[] = [], 7 | public album_name = '', 8 | public release_date = '', 9 | public cover_url = '' 10 | ) {} 11 | } 12 | -------------------------------------------------------------------------------- /src/lib/download.ts: -------------------------------------------------------------------------------- 1 | import os from 'os' 2 | import ytdl from 'ytdl-core' 3 | import SpotifyDlError from './Error' 4 | import { readFile, unlink, writeFile } from 'fs-extra' 5 | import axios from 'axios' 6 | import Ffmpeg from 'fluent-ffmpeg' 7 | 8 | /** 9 | * Function to download the give `YTURL` 10 | * @param {string} url The youtube URL to download 11 | * @returns `Buffer` 12 | * @throws Error if the URL is invalid 13 | */ 14 | export const downloadYT = async (url: string): Promise => { 15 | if (!ytdl.validateURL(url)) throw new SpotifyDlError('Invalid YT URL', 'SpotifyDlError') 16 | const filename = `${os.tmpdir()}/${Math.random().toString(36).slice(-5)}.mp3` 17 | const stream = ytdl(url, { 18 | quality: 'highestaudio', 19 | filter: 'audioonly' 20 | }) 21 | return await new Promise((resolve, reject) => { 22 | Ffmpeg(stream) 23 | .audioBitrate(128) 24 | .save(filename) 25 | .on('error', (err) => reject(err)) 26 | .on('end', async () => { 27 | const buffer = await readFile(filename) 28 | unlink(filename) 29 | resolve(buffer) 30 | }) 31 | }) 32 | } 33 | 34 | /** 35 | * Function to download and save audio from youtube 36 | * @param url URL to download 37 | * @param filename the file to save to 38 | * @returns filename 39 | */ 40 | export const downloadYTAndSave = async (url: string, filename = (Math.random() + 1).toString(36).substring(7) + '.mp3'): Promise => { 41 | const audio = await downloadYT(url) 42 | try { 43 | await writeFile(filename, audio) 44 | return filename 45 | } catch (err) { 46 | throw new SpotifyDlError(`Error While writing to File: ${filename}`) 47 | } 48 | } 49 | 50 | /** 51 | * Function to get buffer of files with their URLs 52 | * @param url URL to get Buffer of 53 | * @returns Buffer 54 | */ 55 | export const getBufferFromUrl = async (url: string): Promise => 56 | (await axios.get(url, { responseType: 'arraybuffer' })).data 57 | -------------------------------------------------------------------------------- /src/lib/getYtlink.ts: -------------------------------------------------------------------------------- 1 | import yts from 'yt-search' 2 | 3 | export default async (term: string): Promise => { 4 | const { videos } = await yts.search(term) 5 | if (!videos || videos.length === 0) return '' 6 | return videos.filter((video) => video.seconds < 3600)[0].url 7 | } 8 | -------------------------------------------------------------------------------- /src/lib/metadata.ts: -------------------------------------------------------------------------------- 1 | import Ffmpeg from 'fluent-ffmpeg' 2 | import { renameSync, unlinkSync } from 'fs' 3 | import { IMetadata, ITrack } from '../typings' 4 | 5 | export default async (data: ITrack, file: string): Promise => { 6 | const outputOptions: string[] = ['-map', '0:0', '-codec', 'copy'] 7 | 8 | const metadata: IMetadata = { 9 | title: data.name, 10 | album: data.album_name, 11 | artist: data.artists, 12 | date: data.release_date 13 | //attachments: [] 14 | } 15 | 16 | Object.keys(metadata).forEach((key) => { 17 | outputOptions.push('-metadata', `${String(key)}=${metadata[key as 'title' | 'artist' | 'date' | 'album']}`) 18 | }) 19 | 20 | const out = `${file.split('.')[0]}_temp.mp3` 21 | await new Promise((resolve, reject) => { 22 | Ffmpeg() 23 | .input(file) 24 | .on('error', (err) => { 25 | reject(err) 26 | }) 27 | .on('end', () => resolve(file)) 28 | .addOutputOptions(...outputOptions) 29 | .saveToFile(out) 30 | }) 31 | unlinkSync(file) 32 | renameSync(out, file) 33 | return file 34 | } 35 | -------------------------------------------------------------------------------- /src/typings/index.d.ts: -------------------------------------------------------------------------------- 1 | export interface ITrack { 2 | name: string 3 | artists: string[] 4 | album_name: string 5 | release_date: string 6 | cover_url: string 7 | } 8 | 9 | export interface IPlaylist { 10 | name: string 11 | total_tracks: number 12 | tracks: string[] 13 | } 14 | 15 | export interface IArtist { 16 | id: string 17 | name: string 18 | herf: string 19 | } 20 | 21 | export interface IMetadata { 22 | title: string 23 | artist: string[] 24 | album: string 25 | date: string 26 | attachments?: string[] 27 | id3v1?: boolean 28 | 'id3v2.3'?: boolean 29 | } 30 | -------------------------------------------------------------------------------- /tests/index.js: -------------------------------------------------------------------------------- 1 | const Spotify = require('../dist/Spotify').default 2 | const spotify = new Spotify({ 3 | clientId: 'acc6302297e040aeb6e4ac1fbdfd62c3', 4 | clientSecret: '0e8439a1280a43aba9a5bc0a16f3f009', 5 | }) 6 | const fs = require('fs-extra') 7 | 8 | const links = { 9 | artist: 'https://open.spotify.com/artist/7ky9g1jEjCsjNjZbYuflUJ?si=2To3fmc-T9KuyyrQ-Qp5KQ', 10 | album: 'https://open.spotify.com/album/3u3WsbVPLT0fXiClx9GYD9?si=pfGAdL3VRiid0M3Ln_0DNg', 11 | song: 'https://open.spotify.com/track/1Ub6VfiTXgyV8HnsfzrZzC?si=4412ef4ebd8141ab' 12 | }; 13 | (async () => { 14 | const user = await spotify.getSpotifyUser('b9260b73960d470d') 15 | console.log(user) 16 | })() 17 | 18 | //spotify.verifyCredentials().then(() => Promise.all([spotify.getTrack(links.song), spotify.getAlbum(links.album), spotify.getArtistAlbums(links.artist)]).then(console.log)) -------------------------------------------------------------------------------- /tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "es5", 4 | "module": "commonjs", 5 | "lib": [ 6 | "ESNext" 7 | ], 8 | "declaration": true, 9 | "outDir": "./dist", 10 | "strict": true, 11 | "esModuleInterop": true, 12 | "skipLibCheck": true, 13 | "forceConsistentCasingInFileNames": true 14 | }, 15 | "include": [ 16 | "src/**/*" 17 | ] 18 | } 19 | -------------------------------------------------------------------------------- /typedoc.json: -------------------------------------------------------------------------------- 1 | { 2 | "entryPoints": ["./src/index.ts", "./src/Spotify.ts"], 3 | "excludePrivate": true, 4 | "excludeProtected": true, 5 | "excludeExternals": true, 6 | "includeVersion": false, 7 | "out": "docs" 8 | } --------------------------------------------------------------------------------