js realizes 3D sound effects through audioContext

js realizes 3D sound effects through audioContext

This article shares the specific code of js to achieve 3D sound effects through audioContext for your reference. The specific content is as follows

Preface

AudioContext's setPosition implements 3D sound effects

Effect display

Code Showcase

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>3D Audio</title>
    <style>
        body, div{
            margin: 0px;
            padding: 0px;
            text-align: center;
        }

        #cav{
            border: 1px solid black;
            border-radius: 4px;
            margin: 10px auto;
        }
    </style>
</head>
<body>
<canvas id="cav" width="320" height="200"></canvas>
</body>
<script>
    let Aud = function (ctx, url) {
        this.ctx = ctx;
        this.url = url;

// source node this.src = ctx.createBufferSource();

//Multiple processing node groups this.pNode = [];
    };

    Aud.prototype = {
        output(){
            for (let i = 0; i < this.pNode.length; i++){
                let tNode = this.src;
                for (let j = 0; j < this.pNode[i].length; j++){
                    tNode.connect(this.pNode[i][j]);
                    tNode = this.pNode[i][j];
                }
                tNode.connect(this.ctx.destination);
            }
        },

        play(loop){
            this.src.loop = loop || false;
            this.output();
            this.src.start(0);
        },

        stop() {
            this.src.stop();
        },

        addNode(node, groupIdx = 0){
            this.pNode[groupIdx] = this.pNode[groupIdx] || [];
            this.pNode[groupIdx].push(node);
        }
    };

    //Set the node type Aud.NODETYPE = {
        GNODE: 0 // represents gainNode node}

    //Aud management object AudManager = {
        urls: [],
        items: [],
        ctx: null,
        init(){
            try{
                this.ctx = new AudioContext();
            }catch (e) {
                console.log(`${e}`);
            }
        },
        load(callback){
            for (let i = 0; i < this.urls.length; i++){
                this.loadSingle(this.urls[i], callback);
            }
        },

        loadSingle(url, callback){
            let req = new XMLHttpRequest();
            req.open('GET', url, true);
            req.responseType = 'arraybuffer';
            let self = this;
            req.onload = function () {
                self.ctx.decodeAudioData(this.response)
                    .then(
                        buf => {
                            let aud = new Aud(self.ctx, url);
                            aud.src.buffer = buf;
                            self.items.push(aud);

                            if (self.items.length == self.urls.length){
                                callback();
                            }
                        },
                        err => {
                            console.log(`decode error:${err}`);
                        }
                    )
            };

            req.send();
        },

        createNode(nodeType, param){
            let node = null;
            switch (nodeType) {
                case 1:
                    node = this.ctx.createPanner();
                    break;
                case 2:
                    node = this.ctx.createScriptProcessor(param[0], param[1], param[2]);
                    break;
                default:
                    node = this.ctx.createGain();
            }
            return node;
        }
    };

    let ctx = document.getElementById('cav').getContext('2d');
// Define the coordinates of the moving point let cX = 190,
        cY = 100,
        deg = 0;

    window.onload = function (){
        init();
    }

    function renderCir(x, y, r, col){
        ctx.save();
        ctx.beginPath();
        ctx.arc(x, y, r, 0, Math.PI*2);
        ctx.closePath();

        ctx.fillStyle = col;
        ctx.fill();
        ctx.restore();
    }

    function renderCenter(){
        renderCir(160, 100, 8, "red");
    }

    function renderCat() {
        renderCir(cX, cY, 8, "blue");
    }

    function init(){
        AudManager.urls = ["test.mp3"];
        AudManager.init();

        AudManager.load(()=>{
            let pNod1 = AudManager.createNode(1);
            let sound1 = AudManager.items[0];

            sound1.addNode(pNod1);
            sound1.play(true);
            timeHandle();
        });
    }

    function timeHandle() {
        window.setInterval(()=>{
            ctx.clearRect(0,0,320,200);
            let rad = Math.PI*deg / 180;
            let sx = 90*Math.cos(rad),
                sy = 90*Math.sin(rad);
            cX = 160 + sx;
            cY = 100 + sy;

            AudManager.items[0].pNode[0][0].setPosition(sx*0.1, -sy*0.1, 0);
            renderCenter();
            renderCat();
            deg++;
        }, 30);
    }
</script>
</html>

The above is the full content of this article. I hope it will be helpful for everyone’s study. I also hope that everyone will support 123WORDPRESS.COM.

You may also be interested in:
  • Realizing the alarm sound effect based on JavaScript
  • How to add background music and select sound effects to web pages using js

<<:  Explanation of Linux kernel optimization configuration for high-concurrency nginx server

>>:  MYSQL subquery and nested query optimization example analysis

Recommend

Linux virtual memory settings tutorial and practice

What is Virtual Memory? First, I will directly qu...

Summary of MySQL development standards and usage skills

1. Naming conventions 1. Database names, table na...

Detailed explanation of various ways to merge javascript objects

Table of contents Various ways to merge objects (...

Unbind SSH key pairs from one or more Linux instances

DetachKeyPair Unbind SSH key pairs from one or mo...

Vendor Prefix: Why do we need a browser engine prefix?

What is the Vendor Prefix? Vendor prefix—Browser ...

Basic usage of @Font-face and how to make it compatible with all browsers

@Font-face basic introduction: @font-face is a CSS...

Introduction to Docker Quick Deployment of SpringBoot Project

1. Install Docker First open the Linux environmen...

Implementation of Nginx forwarding matching rules

1. Regular expression matching ~ for case-sensiti...

HTML Tutorial: Ordered Lists

<br />Original text: http://andymao.com/andy...

MySQL 8.0.12 decompression version installation tutorial personal test!

Mysql8.0.12 decompression version installation me...

6 Ways to Elegantly Handle Objects in JavaScript

Table of contents Preface 1. Object.freeze() 2. O...

Font references and transition effects outside the system

Copy code The code is as follows: <span style=...