Sound.js 3.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189
  1. /**
  2. * @author mikael emtinger / http://gomo.se/
  3. */
  4. THREE.Sound = function ( sources, radius, volume, loop ) {
  5. THREE.Object3D.call( this );
  6. this.isLoaded = false;
  7. this.isAddedToDOM = false;
  8. this.isPlaying = false;
  9. this.duration = -1;
  10. this.radius = radius !== undefined ? Math.abs( radius ) : 100;
  11. this.volume = Math.min( 1, Math.max( 0, volume !== undefined ? volume : 1 ) );
  12. this.domElement = document.createElement( 'audio' );
  13. this.domElement.volume = 0;
  14. this.domElement.pan = 0;
  15. this.domElement.loop = loop !== undefined ? loop : true;
  16. // init sources
  17. this.sources = sources instanceof Array ? sources : [ sources ];
  18. var element, source, type, s, sl = this.sources.length;
  19. for ( s = 0; s < sl; s++ ) {
  20. source = this.sources[ s ];
  21. source.toLowerCase();
  22. if ( source.indexOf( ".mp3" ) !== -1 ) {
  23. type = "audio/mpeg";
  24. } else if( source.indexOf( ".ogg" ) !== -1 ) {
  25. type = "audio/ogg";
  26. } else if( source.indexOf( ".wav" ) !== -1 ) {
  27. type = "audio/wav";
  28. }
  29. if ( this.domElement.canPlayType( type ) ) {
  30. element = document.createElement( "source" );
  31. element.src = this.sources[ s ];
  32. this.domElement.THREESound = this;
  33. this.domElement.appendChild( element );
  34. this.domElement.addEventListener( "canplay", this.onLoad, true );
  35. this.domElement.load();
  36. break;
  37. }
  38. }
  39. };
  40. THREE.Sound.prototype = new THREE.Object3D();
  41. THREE.Sound.prototype.constructor = THREE.Sound;
  42. THREE.Sound.prototype.supr = THREE.Object3D.prototype;
  43. THREE.Sound.prototype.onLoad = function () {
  44. var sound = this.THREESound;
  45. if ( sound.isLoaded ) {
  46. return;
  47. }
  48. this.removeEventListener( "canplay", this.onLoad, true );
  49. sound.isLoaded = true;
  50. sound.duration = this.duration;
  51. if ( sound.isPlaying ) {
  52. sound.play();
  53. }
  54. };
  55. THREE.Sound.prototype.addToDOM = function ( parent ) {
  56. this.isAddedToDOM = true;
  57. parent.appendChild( this.domElement );
  58. };
  59. THREE.Sound.prototype.play = function ( startTime ) {
  60. this.isPlaying = true;
  61. if ( this.isLoaded ) {
  62. this.domElement.play();
  63. if ( startTime ) {
  64. this.domElement.currentTime = startTime % this.duration;
  65. }
  66. }
  67. };
  68. THREE.Sound.prototype.pause = function () {
  69. this.isPlaying = false;
  70. this.domElement.pause();
  71. };
  72. THREE.Sound.prototype.stop = function (){
  73. this.isPlaying = false;
  74. this.domElement.pause();
  75. this.domElement.currentTime = 0;
  76. };
  77. THREE.Sound.prototype.calculateVolumeAndPan = function ( cameraRelativePosition ) {
  78. var distance = cameraRelativePosition.length();
  79. if( distance <= this.radius ) {
  80. this.domElement.volume = this.volume * ( 1 - distance / this.radius );
  81. } else {
  82. this.domElement.volume = 0;
  83. }
  84. };
  85. THREE.Sound.prototype.update = function ( parentMatrixWorld, forceUpdate, camera ) {
  86. // update local (rotation/scale is not used)
  87. if ( this.matrixAutoUpdate ) {
  88. this.matrix.setPosition( this.position );
  89. forceUpdate = true;
  90. }
  91. // update global
  92. if ( forceUpdate || this.matrixNeedsUpdate ) {
  93. if ( parentMatrixWorld ) {
  94. this.matrixWorld.multiply( parentMatrixWorld, this.matrix );
  95. } else {
  96. this.matrixWorld.copy( this.matrix );
  97. }
  98. this.matrixNeedsUpdate = false;
  99. forceUpdate = true;
  100. }
  101. // update children
  102. var i, l = this.children.length;
  103. for ( i = 0; i < l; i++ ) {
  104. this.children[ i ].update( this.matrixWorld, forceUpdate, camera );
  105. }
  106. };
粤ICP备19079148号