Giter Site home page Giter Site logo

jessuni / shikwasa Goto Github PK

View Code? Open in Web Editor NEW
436.0 10.0 28.0 14.32 MB

An audio player born for podcast

Home Page: https://shikwasa.js.org

License: MIT License

JavaScript 65.37% CSS 18.05% HTML 16.58%
podcast audio player html5audio shikwasa playback podcasting webplayer music-player podcast-player

shikwasa's Introduction

shikwasa branding image


npm size dependency jsdelivr CI license

About

Shikwasa is an web audio player born for podcast. If you're tired of using music players as a substitute to play podcast, you've come to the right place. SAY NO to players that does not even support podcast common features!

  • ๐Ÿš€ Ultra lightweight
  • ๐Ÿฃ Dependency free
  • ๐ŸŽฌ Podcast chapters
  • ๐ŸŽ Playback speed control
  • ๐ŸŽฎ Skip forward/backward
  • ๐Ÿ‘“ Accessibility-aware
  • ๐ŸŒ™ Dark Mode
  • ๐Ÿ“ป Audio stream support
  • ๐Ÿ’ป SSR compatible
  • Direct audience to subscription pages
  • Playlist

โžก๏ธDEMO hereโฌ…๏ธ

๐Ÿ“–Table of Contents

Installation

npm install shikwasa

Also available on CDN: https://www.jsdelivr.com/package/npm/shikwasa

Usage

  1. include stylesheet and script

      import 'shikwasa/dist/style.css'
      import { Player } from 'shikwasa'
  2. Specify a container to inject the player component.

     <div class="element-of-your-choice">
       <!-- this is where the player will be injected -->
     </div>
  3. Create an instance of the player

     // an example with basic init options
    
     const player = new Player({
       container: () => document.querySelector('.element-of-your-choice'),
       audio: {
         title: 'Hello World!',
         artist: 'Shikwasa FM',
         cover: 'image.png',
         src: 'audio.mp3',
       },
     })
    
     // The library has also exposed a global variable `Shikwasa` in the UMD and IIFE build.
     // Then the usage would be:
     const { Player } = window.Shikwasa
     const player = new Player({ ... })

    Any child nodes inside container will be cleared upon the time Shiwkasa mounts.

Here's a fiddle to kickstart. To use the chapter feature, you need to import the chapter script and stylesheets as well. View details

API

Methods

play

play(): Promise | void

Start playing the current audio. In modern browsers and IE9+ it will return a promise while pre IE9 it will return nothing.

Updating audio via this method is deprecated, use update instead.

pause

pause(): void

Pause the current audio.

toggle

toggle(): Promise | void

Toggle audio play state between play and pause. Promise details.

seek

seek(time: number): void

Seek the audio to the new time. time is a number that specifies target playback time in seconds.

update

update(audio: TAudio): void

Passing TAudio in will replace the current audio source.

  player.update({
    title: 'Embrace the universe with a cup of shikwasa juice',
    artist: 'Shikwasa',
    cover: 'image.png',
    src: 'sourceAudio.mp3'
})

destroy

destroy(): void

Destroy the player instance.

on

on(event: string, callback: () => void): void

Register an event listener. Supported event names see: Events

Properties

currentTime

  • Read-only
  • type: number
  • default: 0

The current playback time. Inherits the native HTMLMediaElement.currentTime.

muted

The current mute state of the player. Similar to the native HTMLMediaElement.muted, except thatmuted's value will not be affected when audio source is updated.

playbackRate

  • type: number
  • default: 1

The current playbackRate of the player. Inherits the native HTMLMediaElement.playbackRate, except thatplaybackRate's value will not be affected when audio source is updated.

duration

Options

audio

  • required
  • type: TAudio | null
  • default: null
  TAudio {
    src: string,
    title?: string,
    artist?: string,
    cover?: string,
    duration?: number,
    album?: string,
    live?: boolean,
  }

The target audio to be played. If duration is passed along, players with preload option set to none will be able to display the custom duration in UI before the audio metadata is fetched. However, after the audio metadata is loaded, this prop will be ignored.

album is not visible in the UI. It will only display in the Chrome mini player and any other browsers/devices/operating systems that support MediaSession.

live is for audio stream.

container

(Optional) The container element for the player. If document is not available in the env, pass a function that will return the container element.

  • type: HTMLElement | () => HTMLElement
  • default: document.querySelector('body')

fixed

(Optional) Whether player should be fixed to viewport.

  • type: TFixed
    TFixed {
      type: 'auto' | 'fixed' | 'static',
      position: 'bottom' | 'top',
    }
  • default:
    {
      type: 'auto',
      position: 'bottom',
    }
  • details:
Property Type Description
type String either auto, static or fixed
auto: player position is controlled by media queries. Normally the player stays static, but on small screens it will be fixed to viewport
static: force the player to remain static regardless of screen width
fixed: force the player to fix to viewport
position String either bottom or top
โš ๏ธNote: position will be ignored when type is set to static

themeColor

(Optional) Theme color of the player.

  • type: string
  • default: '#00869B'

theme

(Optional)

  • type: 'auto' | 'dark' | 'light'
  • default: 'auto'

autoplay

(Optional) If audio should autoplay on load. โš ๏ธNote: Chrome and Safari disable audio autoplay unless muted is set to true by default. To comply with this policy, see details in Chrome Developers and Webkit Announcement.

  • type: boolean
  • default: false

muted

Whether audio should be muted by default. Similar to HTMLMediaElement's defaultMuted.

  • type: boolean
  • default: false

preload

(Optional) Choose from auto, metadata and none. For details view MDN Doumentation.

If a parser is used, the audio will be requested immediately on page load for the parser to work properly, even if preload is set to none.

  • type: 'auto' | 'metadata' | 'none'
  • default: 'metadata'

speedOptions

(Optional) The playback speed range. Each value of the array should be between the range of 0.25 to 5.0, or will likely be ignored by certain browsers.

  • type: Array<number>
  • default: [0.5, 0.75, 1.25, 1.5]

download

(Optional) Whether the current audio source is download-able. When set to true, the player will provide an anchor with download attribute and href set to audio.src. Cross-origin href will not prompt download due to anchor's nature, but you can offer an alternative blob:, data: url or a same-origin direct download link(DDL).

  • type: string | boolean
  • default: false
  • alternatives:
// direct user to the source url
download: true
// direct user to a custom url, preferrably one configured to generate download
download: 'data:audio/mp3;base64,...'

parser

(Optional) To focus on the player itself as well as to maintain Shikwasa as efficient as possible, we don't extract data from audio files. If you don't have control over the chapter data but would like to implement chapter feature, we support using jsmediatags as an external parser to parse the current audio's metadata.

It will read the audio's title, artist, duration and chapters, meaning you don't have to provide these four properties into audio manually unless you preferred your own. Priority: property values passed to audio > parsed data.

  • type: null | JSMediatags
  • default: null
  • usage:
  npm install jsmediatags // https://github.com/aadsm/jsmediatags
  import { Player } from 'shikwasa'
  import jsmediatags from 'jsmediatags'

  new Player({
    ...
    parser: jsmediatags,
    audio: { src: ... },
  })

โš ๏ธNote: If audio.src is not of the same origin, proper CORS configuration will be needed to use the parser. Due to jsmediatags limitation, relative urls are not supported. Please use absolute urls for audio.src.

Events

Support all HTMLMediaElement native events.

Plus player events:

audioupdate: fired when audio source is updated.

audioparse: fired when audio file data is parsed.

Style

Although Shikwasa have not yet provided a full customization support of its styles, some CSS variables are available and should cover basic needs.

  --background-body                           /* background of the player body */
  --color-title                               /* color of the title text */
  --color-artist                              /* color of the artist text */
  --color-button: var(--color-primary);       /* color of the buttons, defaults to `themeColor` */
  --color-button-disabled                     /* color of button:disabled */
  --color-button-active-background            /* color of the background of button:active` */
  --color-handle: var(--color-primary);       /* color of the playback progress handle, defaults to `themeColor` */
  --color-handle-disabled                     /* color of the handle:disabled */
  --color-bar-loaded                          /* color of the loaded playback progress, defaults to `themeColor` */
  --color-bar-played: var(--color-primary);   /* color of the loaded playback progress, defaults to `themeColor` */
  --color-time                                /* color of the playback time */
  --color-spinner: var(--color-primary);      /* color of the playback loading indicator, defaults to `themeColor` */
  --color-live-symbol: var(--color-primary);  /* color of the live indicator symbol, defaults to `themeColor` */
  --color-live-text: var(--color-primary);    /* color of the live indicator text, defaults to `themeColor` */
  --shadow-body                               /* box shadow of the player body */
  --shadow-body-mobile                        /* box shadow of the player body in small screens */
  --shadow-handle                             /* box shadow of the playback progress handle */
  --shadow-handle-mobile                      /* box shadow of the playback progress handle in small screens */

Usage: overwrite the style property in your player container:

  .container .shk {
    --background-body: linear-gradient(-45deg, #84ccff, #b8e8ff);
  }

Chapters

Shikwasa supports chapters display and playback control with the help of its external chapter plugin. To use this feature:

  1. Register the chapter plugin before creating a Shikwasa instance.

     import { Chapter } from 'shikwasa'
    
     Player.use(Chapter)
     const player = new Player({...})
  2. This does not guarantee that the audio will display chapters. To display chapters, you need to provide chapter data to the player.

    If you don't have direct access to the chapter data, Shikwasa has built-in support to work with jsmediatags to read and extract the data from the audio file;

    • (1) To manually provide chapters, add the chapters property when passing audio into options or .update(audio).

        audio: {
          ...
          // manually provide chapters
          chapters: [
            { title, startTime, endTime }, // the first chapter
            { title, startTime, endTime }, // the second chatper
          ],
        }

      The structure of a single chapter object:

      Property Type Description
      title string chapter title
      startTime number chapter start time in seconds
      endTime number chapter end time in seconds

      โš ๏ธNote: endTime should be the same as startTime of the next chapter.

    • (2) To use an external parser, pass jsmediatags in the parser options. How to use a parser?

(1) will take the higher priority.

Registering Chapter plugin will empower Shikwasa instance with the following API:

Methods:

updateChapter

updateChapter(index: number): void

Seek the audio to the target chapter. index is the index of of chapters array.

Properties:

chapters

<property>

  • Read-only
  • type: Array<TChapter> | []
  • default: []
  TChapter {
    title: string,
    startTime: number,
    endTime: number,
  }

Chapter metadata of the current audio, if any. See Chapter.

currentChapter

  • Read-only
  • type: Null | TChapter
  • default: null

Indicate which chapter is currently on play, if any. See Chapter.

Events:

chapterchange: fired when currentChapter changes.

Roadmap

๐ŸŸก v2.3.0:

  • In-player subscription feature that direct the audience to your subsciption pages in major podcasting platforms

๐ŸŸก v2.2.0:

  • rewritten in Typescript ๐Ÿ‘‰ finished but not tested, contribution welcomed

โœ… v2.1.0:

  • live mode
  • safely update audio metadata
  • offer more UI customization options

โœ… v2.0.0:

  • supporting audio id3 metadata
  • cleaner & sleeker interface
  • dark mode
  • a complete rewrite
  • keyboard support

What about the weird name of this project?

Shikwasa is the name of a popular citrus fruit from Okinawa, Japan. ๐ŸŠ

Love it, name after it.

License

MIT

shikwasa's People

Contributors

alexs7zzh avatar dependabot[bot] avatar jessuni avatar lgiki avatar lloyyd-weng avatar travisvn avatar yenche123 avatar zhuangya avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

shikwasa's Issues

How to build this project ?

Hey, thanks for this cool project. I tried to run an example and it was working great but I was not able to change theme color or theme using options. To test it out I tried to build the project but the build is failing.

Can you kindly let me know the way to build the project ? I tried to run "npm run build" but it gives me the below error

[email protected] build C:\Users\srini\Downloads\shikwasa
npm run build:main && npm run build:chapter

[email protected] build:main C:\Users\srini\Downloads\shikwasa
TARGET=main rollup -c

'TARGET' is not recognized as an internal or external command,
operable program or batch file.

Weird layout in my react project

image

import React, { Component } from 'react';
import Shikwasa from 'shikwasa';

export default class TestPage extends Component {
constructor(props) {
super(props);
this.myRef = React.createRef();
}
componentDidMount() {
let player = new Shikwasa({
fixed: {
type: 'auto',
position: 'bottom',
},
container: this.myRef.current,
transitionSpeed: 3,
themeColor: '#00869B',
autoPlay: false,
muted: false,
preload: 'metadata',
speedOptions: [0.5, 0.75, 1.25, 1.5],
audio: {
title: 'Hello World!',
artist: 'Shikwasa FM',
src: 'http://www.music.helsinki.fi/tmt/opetus/uusmedia/esim/a2002011001-e02-128k.mp3',
},
})
}

render() {
return (




)
}
}

Progress bar hidden by default?

I just installed this through npm, and by default the progress bar seems to be set at display: none. The "live" button is also visible, even though I've set live to false.

I will be fixing this with some CSS overrides, but it seems like weird behavior.

Playlist

Hi! This is the most beautiful podcast player I have seen! I didn't find mentions about playlists in the roadmap, will be they added? This will be really wonderful!

Hiding/obscuring audio file from Network tab in Developer Tools?

Hey!

Thank you for making this incredible player. I've been searching for one that hides the file from the DOM and this one served that purpose but now I'm curious if it might be possible to also hide or obscure the file from the Network tab. I've seen a lot of people saying that this is basically impossible, however, I've also seen people seemingly falsifying that hypothesis: https://preventdirectaccess.com/extensions/protect-wordpress-videos/

Try opening the network tab, then playing that video. You'll see a link to a .ts video. If you try opening it won't play, nor download the video - rather a file with that name.

If the video keeps playing you see it seems to be pieces of the video that are being streamed.

  1. I wonder how they're doing that...
  2. I wonder if I could do something similar with shikwasa?

Or rather just preventing direct access to the file, such that if the user opens the direct link, they're redirected to the page with the player.

[Bug Report] player icons destroy unexpected

Hi @jessuni

I came across one issue in my project, the buttons of the player was missing when another player destroyed.

And I found the issue is that the icons will only has one instance in DOM tree, and when one player destory, the icons' svg will also destroy, therefor will affect another player in the page.

constructor(options) {
    this.mounted = false

    // because of this line, can only has one icons in dom tree.
    if (!document.querySelector('.shk-icons')) {
      this.icons = createElement({
        className: 'shk-icons',
        innerHTML: IconComp,
      })
    }
    this.initEl()
    this.initOptions(options)
}

mount(container, supportsPassive) {
    // ...
    if (this.icons) {
      container.append(this.icons)
    }
   // ...
  }

Shikwasa is awesome, thanks for your work. ๐Ÿ™

[feature request] Customizable player templates

It would be a very handy feature to make the player templates customizable.

The player is based on templates already:
https://github.com/jessuni/shikwasa/tree/main/src/templates
But it's referenced internally at the moment.

I could imagine the following:

const TemplateChapter = `... my fancy markup ...`
const TemplateIcon = `...`
const TemplatePlayer = `...`

// or with an import (a bit cleaner)
import { TemplateChapter, TemplateIcon, TemplatePlayer  } from './shikwasa-templates.js';

const player = new Shikwasa({
    container: () => document.querySelector('.shikwasa-player'),
    tplChapter: TemplateChapter,
    tplIcon: TemplateIcon,
    tplPlayer: TemplatePlayer,
    audio: {
        title: '...', 
        artist: '...',
        cover: '...',
        src: '...',
        },
});

Sometimes it is necessary to change the icons or change the structure of the layout fundamentally, which would be easy to do in this case.

no controls on increase/decrese the volume

In the demo (https://shikwasa.js.org/), I don't see a way to increase/decrease the volume. The only thing I can do is to mute/unmute. I wonder if this feature (adjusting volume) is not supported by the player, or it's just that the demo didn't cover it.

PS: This player is quite sleek and handy for podcast. Well done.

Iframe embed has no cover image displaying

Hi @jessuni ,

I am trying to create an embed of the Shikwasa audio player and then use an iframe to play it on my website similar to how other podcast players work.

But I see an issue happening here, whenever I create an iframe of the page containing Shikwasa player, the cover is not being show. For example this is the normal webpage with only shikwasa player http://api.peervadoo.com/embed_audio . Then I have created a new page using iframe of the above webpage here http://api.peervadoo.com/test_embed_audio .

As you can see, test_embed_audio has no cover image and some white space is added to top while the normal webpage version works fine. Can you kindly let me know what could be the issue here and if any workaround ?

Using loop in options to iterate and add chapters data

My function is declared as follow for my hexo podcast. Shikwasa is fabulous. Love the design.

hexo.extend.tag.register('podplayer', function (args) {
    return `
    <div class="podcast"></div>\
    <script>\
        const player = new Shikwasa({
            container: () => document.querySelector('.podcast'),\
            audio: {\
                title: '${this.title}',\
                artist: '${this.author}',\
                cover: '${this.image}',\
                src: '${this.media}',\
            },\
            fixed: {\
                type: 'static',\
            },\
        });\
    </script>`
});

Then, I want to add my chapters options. They are in a nested array of ${this.chapters}, the data structure look like this:

chapters:
  [
    ["00:00:00.000", "Title 1"],
    ["00:00:30.000", "Another title"]
  ]

I can access them by index, e.g. ${this.chapters[0][1]} ,${this.chapters[0][0]} and ${this.chapters[1][0]}, etc.

By substituting the corresponding element with title, startTime, endTime.

chapters: [
      { title, startTime, endTime }, // the first chapter
      { title, startTime, endTime }, // the second chatper
],

I get something like this โฌ‡๏ธ

chapters: [
  { ${this.chapters[0][1]}, ${this.chapters[0][0]}, ${this.chapters[1][0]} }, // the first chapter
  { ${this.chapters[1][1]}, ${this.chapters[1][0]}, ${this.chapters[2][0]} }, // the second chapter
{ ${this.chapters[1][1]}, ${this.chapters[1][0]}, ${this.chapters[2][0]} }, // the second chatper
  { title, startTime, endTime }, // the third chatper
],

Is there a way I can use a for loop to iterate my chapters? So that one line of code would be able to generate all my chapters automatically.

chapters: [
   { ${this.chapters[i][1]}, ${this.chapters[i][0]}, ${this.chapters[i+1][0]} }, // i to n chapter
],

I've tried using <% %> tags but have no luck.

<script type="text/javascript">
    <% ${this.chapters}.forEach(function(row) { %>
        console.log("<%= row[1] %>, <%= row[0] %>"); // or anything you want to do.    
    <% }) %>
</script>

It would just output my loop code.

image-20211214022927603

Is this even possible? Any tips or hints will be appreciated. Thx.

Seeking jumps to beginning

I've tried with multiple mp3 files. Whenever I click in the seeking bar, the audio jumps to the start.
Any idea why this could be?

Seek control

Hello. Please excuse me, but I'm quite new to JavaScript.

I made my first player Shikwasa for the Survivor Memories website. However, I have absolutely no idea how I can add timecodes.

For example, how can I add the timecode "05:06 She talks about herself"?

https://codepen.io/andriy-smkhtkn/pen/PoezOQr

I don't know how to use that:

anchor.addEventListener('click', (e) => {
    const href = e.target.getAttribute('href')
    const time = formatTime(href)
    instance.seek(time)
    instance.play()
  })

Excuse me again!

Have a good day.

Feature request: Populating Player/Playlist Using RSS Feed

Hi there! I'm a longtime admirer of this project, and have been waiting for an opportunity to use it.

I recommended the player to someone on a forum, and the person asked about a media player that could update automatically when the RSS feed is changed.

I don't know of any media player libraries that do this, and thought that the feature would be a good idea for this player since it's focused on podcasts.

Piggybacking on the playlist feature request #28: I would love if the playlist updated automatically using the podcast RSS, and if the latest "track" was the newest episode (or the first episode -- however the dev decides to set it up).

Cannot redefine chapters when creating a second player

When I create the first player everything works fine but trying to create a second player causes an error TypeError: Cannot redefine property: chapters this stops a second player from being created.
Full stack trace
Uncaught TypeError: Cannot redefine property: chapters at Function.defineProperties (<anonymous>) at Chapter.patchPlayer (bundle.js:102149:12) at Chapter.init (bundle.js:102092:10) at bundle.js:102103:14 at bundle.js:103025:39 at Array.forEach (<anonymous>) at Events.trigger (bundle.js:103025:25) at Player.update (bundle.js:103421:19) at Player.initAudio (bundle.js:103244:12) at new Player (bundle.js:103082:10)

An example of how I am creating the player, this is triggered by button press when a user needs to create a player.

const chapters = [
      { title: 'First Chapter', startTime: 0, endTime: 2 },
      { title: 'Second Chapter', startTime: 2, endTime: 4 },
]


Shikwasa.use(Chapter)
      const player = new Shikwasa({
        container: () => document.querySelector('#e' + widgetID),
        audio: {
          title: titleTmp,
          artist: artist,
          cover: require('./testPic.jpeg'),
          src: require('./testFile.mov'),
          Chapter: chapters
        },
        theme: theme,
        themeColor: themeColour,
      })

I've checked all the variables exist and so do the test files. Thanks

Chapters are always shown and can't be closed

After getting this project working with TS and React i have managed to create the audio widget and everything works fine except for chapters which are always shown below the audio player and the close button dosen't seem to work and neither does the view chapters btn.
I have checked to make sure that no other styles are being applied accidentally and I have made sure that the start and end time for the chapters is less than the duration of the file and just in case I have tried using the position and type properties.
Thanks

z-index

When player position is set to fixed I have to set z-index on .shk otherwise content behind the player is visible.

Example:

.container .shk {
   z-index: 1;
}

I notice that .shk-player has z-index: 10 but it doesn't seem to make a difference....

I'm using Firefox 108 on Fedora Linux.

Live stream support?

First, thank you for this wonderful package! I love this player and I'm planning to use it on a project that allows the user to switch between live streams and on-demand podcasts. The player works with some modifications, namely disabling the seek bar and time display. Currently I'm doing this in Vue.js using a computed state property that sets an .is-live class to the wrapper div and adding this CSS to hide the components:

.is-live .shk-bar_wrap, 
.is-live .shk-display {
  display: none;
}

This works somewhat well but I'd like to see official support. I also have to use the internal updateAudioData method instead of the update method to change the track display because update interrupts playback.

How to import Shikwasa in a typescript project?

I have installed the latest version of shikwasa with npm but we are currently using TS and I have seen on your roadmap that TS is something you are working on, is it possible to get early access to the TS version. Thanks

cannot import css in `v2.2.0`

greetings!

I am trying to upgrade shikwasa to v2.2.0 at here, but I noticed that the css file cannot be imported properly with the following error msg

import "shikwasa/dist/style.css";
import { Chapter, Player } from "shikwasa";

...
...
ERROR in ./src/podcastPlayer/index.js 1:0-33
[30](https://github.com/IvanWoo/subjpop.github.io/actions/runs/4157082134/jobs/7191312599#step:7:31)
Module not found: Error: Package path ./dist/style.css is not exported from package /home/runner/work/subjpop.github.io/subjpop.github.io/node_modules/shikwasa (see exports field in /home/runner/work/subjpop.github.io/subjpop.github.io/node_modules/shikwasa/package.json)
[31](https://github.com/IvanWoo/subjpop.github.io/actions/runs/4157082134/jobs/7191312599#step:7:32)
 @ ./src/index.js 5:0-50 11:2-21

seems like it's related to the exports field of package.json

shikwasa/package.json

Lines 10 to 14 in ecf7a3e

"exports": {
".": {
"import": "./dist/shikwasa.es.js",
"require": "./dist/shikwasa.cjs.js"
}

I can import the css after removing the exports part based on the discussion at here

I don't mind opening a pr for it, but not sure if it's the right way going forward b/c it might break commonjs import

thanks!

Some SVG icons not visible

Using /dist the svg images for download, rewind, forward, and volume are not visible in the player. ThemeColor has been declared in the script creating an instance of the player and is correctly applied to all other elements. Same faulty behavior using Safari 12 and Chrome build 77.0.3865.120. Can you please help?

seek not working

Thanks for the player!

I'd like to start playing from a particular position as soon as the player is ready but I had an issue where calling seek on a newly loaded player wasn't working. I found I had to delay the seek to give the player time to load enough audio to get a duration value e.g.

                       let ss = setInterval(() => {
				if(player.duration > 0) {
					clearInterval(ss);
					player.seek(lastPlayTimeSec);
				}
			},500);

Could an additional seek property be added to TAudio to specify the start position?

Extending the player further

Hello,

Amazing work! Very impressed. Please excuse my noob questions as I`m quite new to podcasts and I am trying to setup a PoC project.

  1. Is it possible to add these "waveforms" (like SoundCloud has)?

image

  1. Is it possible to add volume control?
  2. Is it possible to add download button?
  3. Ultimately, some sharing buttons?

Happy to pitch in with whatever I can, cashflow or code (need to learn more about audio files first lol).

Many thanks!

Waveform animation in audio player

Is it possible to add a waveform animation for the audio player similar to other popular podcasting players ?

This would provide a great boost to the look of the player.

Thanks in advance.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.