three.js WebAudio -3 PositionalAudio(位置音频)

PositionalAudio(位置音频)

在这里插入图片描述

创建一个位置相关的音频对象.
实例化:(传入listener对象)

var sound=new THREE.PositionalAudio(listener);

属性:
继承Audio类的属性.

方法:
继承Audio类的方法.

(1).setDirectionalCone ( coneInnerAngle : Float, coneOuterAngle : Float, coneOuterGain : Float ) :PositionalAudio
设置方向线
这个方法用来把环绕声音转换为定向声音。

(2).getRefDistance () : Float
返回panner.refDistance的值.

(3).setRefDistance ( value : Float ) : PositionalAudio
距离物体多远时声音开始减弱
设置panner.refDistance的值.

(4).getRolloffFactor () : Float
获得声音下降的速度
返回panner.rolloffFactor的值.

(5).setRolloffFactor ( value : Float ) : PositionalAudio
设置声音下降的速度
设置panner.rolloffFactor的值.

效果例子查看地址(音频加载需要一定时间!)

示例代码:

<!DOCTYPE html>
<html>
	<head>
		<meta charset="UTF-8">
		<title>方向性音频</title>
		<script type="text/javascript" src="js/three.js" ></script>
		<script type="text/javascript" src="js/WebGL.js" ></script>
		<script type="text/javascript" src="js/libs/stats.min.js" ></script>
		<script type="text/javascript" src="js/libs/dat.gui.min.js" ></script>
		<script type="text/javascript" src="js/controls/OrbitControls.js" ></script>
		<script type="text/javascript" src="js/loaders/GLTFLoader.js" ></script>
		<style>
			body{
				padding: 0;
				margin: 0;
				overflow: hidden;
				/*background: #777;*/
			}
			#overlay{
				position:absolute;
				z-index: 100;
				width: 100%;
				height: 100%;
				background-color: #000000;
				color:#ffffff;
				text-align: center;
			}
			#start_btn{
				margin-top: 300px;
				height: 20px;
				width: 100px;
				color:#ffffff;
				border:0px;
				outline: 1px solid #ffffff;
				background: transparent;
				cursor: pointer;
			}			
			#mask{
				padding-top: 200px;
				position: absolute;
				width: 100%;
				height: 100%;
				text-align: center;	
				color: #000000;
				font-size: 20px;		
			}
			#model_progress{
				width: 200px;
				height: 15px;
			}
		</style>
	</head>
	<body>
		<audio loop id="music" preload="auto" style="display: none;">
			<source src="sounds/test1.ogg"></source>
		</audio>
		<div id="overlay">
			<button id="start_btn">点击播放</button>
			<p>Automatic audio playback requires a user interaction.</p>
		</div>
		
		<div id="mask">
			<div id="loading">loading</div><br>
			<progress max="100" id="model_progress"></progress>
		</div>
		
		<script>
			if(WEBGL.isWebGLAvailable()===false){alert("该浏览器不支持webGL!");document.body.appendChild(WEBGL.getWebGLErrorMessage());}
		
			document.getElementById("start_btn").addEventListener("click",init,false);
			
			var scene,renderer,camera,controls,stats;
			function init(){
				document.getElementById("overlay").remove();
				
				scene=new THREE.Scene();
				scene.background=new THREE.Color(0xa0a0a0);
				scene.fog=new THREE.Fog(0xa0a0a0,2,20);
				
				renderer=new THREE.WebGLRenderer({
					antialias:true
				});
				renderer.setSize(window.innerHeight,window.innerHeight);
				renderer.setPixelRatio(window.devicePixelRatio);
				renderer.shadowMap.enabled=true;
				renderer.shadowMap.type=THREE.PCFSoftShadowMap;
				document.body.appendChild(renderer.domElement);
				
				camera=new THREE.PerspectiveCamera(60,window.innerWidth/window.innerHeight,0.1,100);
				camera.position.set(3,2,3);
				
				controls=new THREE.OrbitControls(camera,renderer.domElement);
				controls.minDistance=0.5;
				controls.maxDistance=10;
				controls.enableDamping=true;
				controls.dampingFactor=0.5;
				
				stats=new Stats();
				document.body.appendChild(stats.dom);
				
				var hLight=new THREE.HemisphereLight(0xffffff,0x404040);
				hLight.position.set(0,20,0);
				scene.add(hLight);
				
				var dLight=new THREE.DirectionalLight(0xffffff);
				dLight.position.set(5,5,0);
				dLight.castShadow = true;
				dLight.shadow.camera.top = 1;
				dLight.shadow.camera.bottom = - 1;
				dLight.shadow.camera.left = - 1;
				dLight.shadow.camera.right = 1;
				dLight.shadow.camera.near = 0.1;
				dLight.shadow.camera.far = 20;
				scene.add(dLight);
								
				initModel();
				initGui();
				animate();
			}
			
			var axes;
			function initModel(){
				axes=new THREE.AxesHelper(2);
				scene.add(axes);
				axes.visible=false;
				
				var grid=new THREE.GridHelper(50,50,0x888888, 0x888888);
				scene.add(grid);
				
				var plane=new THREE.Mesh(new THREE.PlaneBufferGeometry(50,50),new THREE.MeshPhongMaterial({
					color:0x999999
				}));
				plane.rotation.x=-Math.PI/2;
				plane.receiveShadow=true;
				scene.add(plane);
				
				var music=document.getElementById("music");
				music.play();
				
				var listener=new THREE.AudioListener();
				camera.add(listener);
				
				var pa=new THREE.PositionalAudio(listener);
				pa.setMediaElementSource(music);
				pa.setRefDistance(1);
				pa.setDirectionalCone(180,230,0.1);
				
				//音频辅助线
				var helper=new THREE.PositionalAudioHelper(pa,0.1);
				pa.add(helper);
				
				var loader=new THREE.GLTFLoader();
				loader.load("models/gltf1/BoomBox.glb",function(gltf){
					//console.log(gltf);
					var boomBox=gltf.scene;
					boomBox.traverse(function(obj){
						if(obj.isMesh){
							obj.geometry.rotateY(Math.PI);
							obj.castShadow=true;
						}
					});
					
					boomBox.position.y=0.2;
					boomBox.scale.set(20,20,20);
					
					boomBox.add(pa);
					
					scene.add(boomBox);
				},function(xhr){
					var loading=xhr.loaded/xhr.total*100;
					console.log(Math.ceil(loading)+"% is loaded");
					document.getElementById("loading").innerHTML=Math.ceil(loading)+"% is loaded";
					document.getElementById("model_progress").value=loading;
					if(loading===100){
						document.getElementById('loading').style.display = 'none';
						document.getElementById('model_progress').style.display = 'none';
						document.getElementById('mask').style.display = 'none';
					}
				},function(error){
					console.error("an error happened!"); 
				});
				
				var wall=new THREE.Mesh(new THREE.BoxBufferGeometry(2,1,0.1),new THREE.MeshBasicMaterial({
					color:0xff0000,
					transparent:true,
					opacity:0.6
				}));
				wall.position.set(0,0.5,-0.5);
				scene.add(wall);				
			}
			
			var setting;
			function initGui(){
				setting={
					axesVisible:false,
				}
				
				var gui=new dat.GUI();
				gui.add(setting,"axesVisible").onChange(function(e){
					axes.visible=e;
				});
			}
			
			function onWindowResize(){
				camera.aspect=window.innerWidth/window.innerHeight;
				camera.updateProjectionMatrix();
				renderer.setSize(window.innerWidth,window.innerHeight);
			}
			
			function animate(){
				renderer.render(scene,camera);
				controls.update();
				stats.update();
				window.onWindowResize();
				requestAnimationFrame(animate);
			}
		</script>
	</body>
</html>

猜你喜欢

转载自blog.csdn.net/qq_41741576/article/details/88970985
今日推荐