All files / src/core core.js

71.79% Statements 28/39
50% Branches 10/20
72.73% Functions 8/11
71.79% Lines 28/39
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310                                                                                                                  31x                   56x 56x         56x                     56x                         56x 56x                     12x         12x         12x           12x                             227x         227x 169x           227x         227x             227x                               193x 7x   186x           193x         193x                                   1x 1x                                   2x                                                                                                         169x         169x           31x                            
/**
 * Imports the config module
 * @module config
 */
import config from "../config.js";
 
/**
 * Imports the Checks module.
 * @module utilities/checks
 */
import Checks from "../utilities/checks.js";
 
/**
 * Imports the Audio Navigation module.
 * @module utilities/audioNavigation
 */
import AudioNavigation from "../utilities/audioNavigation.js";
 
/**
 * Imports the Play/Pause Visual Elements module.
 * @module visual/playPauseElements
 */
import PlayPauseElements from "../visual/playPauseElements.js";
 
/**
 * Imports the Meta Data Visual Elements module.
 * @module visual/metaDataElements
 */
import MetaDataElements from "../visual/metaDataElements.js";
 
/**
 * Imports AmplitudeJS Callback Utility
 * @module utilities/callbacks
 */
import Callbacks from "../utilities/callbacks.js";
 
/**
 * Imports AmplitudeJS Debug Utility
 * @module utilities/debug
 */
import Debug from "../utilities/debug.js";
 
/**
 * Import the Visualizations from the FX module.
 * @module fx/visualizations
 */
import Visualizations from "../fx/visualizations.js";
 
/**
 * Interacts directly with native functions of the Audio element. Logic
 * leading up to these methods are handled by click handlers which call
 * helpers and visual synchronizers. These are the core functions of AmplitudeJS.
 * Every other function that leads to these prepare the information to be
 * acted upon by these functions.
 *
 * @module core/Core
 */
let Core = (function() {
  /**
   * Plays the active song. If the current song is live, it reconnects
   * the stream before playing.
   *
   * Public Accessor: Amplitude.play()
   *
   * @access public
   */
  function play() {
    Visualizations.stop();
    Visualizations.run();
 
    /*
			If the audio is live we re-conenct the stream.
		*/
    Iif (config.active_metadata.live) {
      reconnectStream();
    }
 
    /*
			Mobile remote sources need to be reconnected on play. I think this is
			because mobile browsers are optimized not to load all resources
			for speed reasons. We only do this if mobile and the paused button
			is not clicked. If the pause button was clicked then we don't reconnect
			or the user will lose their place in the stream.
		*/
    Iif (
      /Android|webOS|iPhone|iPad|iPod|BlackBerry|IEMobile|Opera Mini/i.test(
        navigator.userAgent
      ) &&
      !config.paused
    ) {
      reconnectStream();
    }
 
    /*
			Play the song and set the playback rate to the playback
			speed.
		*/
    config.audio.play();
    config.audio.playbackRate = config.playback_speed;
  }
 
  /**
   * Pauses the active song. If it's live, it disconnects the stream.
   *
   * Public Accessor: Amplitude.pause()
   *
   * @access public
   */
  function pause() {
    Visualizations.stop();
 
    /*
			Pause the active song.
		*/
    config.audio.pause();
 
    /*
			Flag that pause button was clicked.
		*/
    config.paused = true;
 
    /*
			If the song is live, we disconnect the stream so we aren't
			saving it to memory.
		*/
    Iif (config.active_metadata.live) {
      disconnectStream();
    }
  }
 
  /**
   * Stops the active song by setting the current song time to 0.
   * When the user resumes, it will be from the beginning.
   * If it's a live stream it disconnects.
   *
   * Public Accessor: Amplitude.stop()
   *
   * @access public
   */
  function stop() {
    Visualizations.stop();
 
    /*
			Set the current time of the song to 0 which will reset the song.
		*/
    if (config.audio.currentTime != 0) {
      config.audio.currentTime = 0;
    }
 
    /*
			Run pause so the song will stop
		*/
    config.audio.pause();
 
    /*
			If the song is live, disconnect the stream.
		*/
    Iif (config.active_metadata.live) {
      disconnectStream();
    }
 
    /*
			Run the stop callback
		*/
    Callbacks.run("stop");
  }
 
  /**
   * Sets the song volume.
   *
   * Public Accessor: Amplitude.setVolume( volumeLevel )
   *
   * @access public
   * @param {number} volumeLevel - A number between 1 and 100 as a percentage of
   * min to max for a volume level.
   */
  function setVolume(volumeLevel) {
    /*
			If the volume is set to mute somewhere else, we sync the display.
		*/
    if (volumeLevel == 0) {
      config.audio.muted = true;
    } else {
      config.audio.muted = false;
    }
 
    /*
			Sets the volume in the config so we can reference it later on.
		*/
    config.volume = volumeLevel;
 
    /*
			Set the volume of the active song.
		*/
    config.audio.volume = volumeLevel / 100;
  }
 
  /**
   * Sets the song percentage. If it's a live song, we ignore this because
   * we can't skip ahead. This is an issue if you have a playlist with
   * a live source.
   *
   * Public Accessor: Amplitude.setSongLocation( songPercentage )
   *
   * @access public
   * @param {number} songPercentage - A number between 1 and 100 as a percentage of song completion.
   */
  function setSongLocation(songPercentage) {
    /*
			As long as the song is not live, we can set the current time of the
			song to the percentage the user passed in.
		*/
    Eif (!config.active_metadata.live) {
      config.audio.currentTime = config.audio.duration * (songPercentage / 100);
    }
  }
 
  /**
   * Skips to a location in a song
   *
   * Public Accessor: Amplitude.skipToLocation( seconds )
   *
   * @access public
   * @param {number} seconds - An integer containing the seconds to skip to
   */
  function skipToLocation(seconds) {
    /*
			When the active song can be played through, we can check to
			see if the seconds will work. We only bind the event handler
			once and remove it once it's fired.
		*/
    config.audio.addEventListener(
      "canplaythrough",
      function() {
        /*
				If the active song duration is greater than or equal to the
				amount of seconds the user wants to skip to and the seconds
				is greater than 0, we skip to the seconds defined.
			*/
        if (config.audio.duration >= seconds && seconds > 0) {
          config.audio.currentTime = seconds;
        } else {
          Debug.writeMessage(
            "Amplitude can't skip to a location greater than the duration of the audio or less than 0"
          );
        }
      },
      { once: true }
    );
  }
 
  /**
   * Disconnects the live stream
   *
   * Public Accessor: Amplitude.disconnectStream()
   *
   * @access public
   */
  function disconnectStream() {
    config.audio.src = "";
    config.audio.load();
  }
 
  /**
   * Reconnects the live stream
   *
   * Public Accessor: Amplitude.reconnectStream()
   *
   * @access public\
   */
  function reconnectStream() {
    config.audio.src = config.active_metadata.url;
    config.audio.load();
  }
 
  /**
   * Sets the playback speed for the song.
   *
   * @param {number} playbackSpeed The speed we want the song to play back at.
   */
  function setPlaybackSpeed(playbackSpeed) {
    /*
			Set the config playback speed.
		*/
    config.playback_speed = playbackSpeed;
 
    /*
			Set the active song playback rate.
		*/
    config.audio.playbackRate = config.playback_speed;
  }
 
  /*
		Return publically facing functions
	*/
  return {
    play: play,
    pause: pause,
    stop: stop,
    setVolume: setVolume,
    setSongLocation: setSongLocation,
    skipToLocation: skipToLocation,
    disconnectStream: disconnectStream,
    reconnectStream: reconnectStream,
    setPlaybackSpeed: setPlaybackSpeed
  };
})();
 
export default Core;