如何在nodejs中使用nvidia jarvis tts

How to use nvidia jarvis tts in nodejs

我正在尝试将 python jarvis tts 示例转换为 nodejs。 我可以从 jarvis 取回音频,但播放时噪音很大

在 python 示例中,他们使用 16 位作为位深度,但在相同的情况下,我在节点上获得非常拉伸的音频。

音频是未压缩的 16 位带符号小端样本(线性 PCM)。据我从他们的原型文件中了解到

                   datalen = len(resp.audio) // 4
                   data32 = np.ndarray(buffer=resp.audio, dtype=np.float32, shape=(datalen, 1))
                   data16 = np.int16(data32 * 23173.26)  # / 1.414 * 32767.0)
                   speech = bytes(data16.data)
                   print(speech)

我曾尝试将类型化数组转换为 float32array,然后再转换为 int16array,但没有成功。

从 python 实现听起来不错,但从节点来看它有太多噪音。

传递给 tts grpc 的参数在两者上是相同的。

编辑:

我能够使用此代码以 16 位深度以最小噪音播放音频。但还是有一些干扰。

this.ttsClient.Synthesize(SynthesizeSpeechRequest, (err, resp) => {
                console.log(err);
                const b16 = new Float32Array(resp.audio.length / 4);
                const v = new DataView(resp.audio.buffer);

                for (let i = 0; i < resp.audio.byteLength; i += 4) {
                    const element = v.getFloat32(i);
                    b16[i / 4] = element;
                }
                let l = b16.length;
                const buf = new Int16Array(l);

                while (l--) {
                    const s = Math.max(-1, Math.min(1, b16[l]));
                    buf[l] = s < 0 ? s * 0x8000 : s * 0x7fff;
                    // buf[l] = s[l] * 0x7fff; //old   //convert to 16 bit
                }

                buf.map((x) => x * 23173.26);
                
                
                console.log("buf", buf);
                // // // new Int16Array().BYTES_PER_ELEMENT
                cb(Buffer.from(buf.buffer));
            });

我能够通过使用 readFloatLE 而不是数据视图来读取来解决这个问题。

        this.ttsClient.Synthesize(SynthesizeSpeechRequest, (err, resp) => {
                if (err) console.log(err);
                const b16 = new Float32Array(Math.floor(resp.audio.length));

                for (let i = 0; i < resp.audio.byteLength; i += 4) {
                    const element = resp.audio.readFloatLE(i);
                    b16[i / 4] = element;
                }
                let l = b16.length;

                const buf = new Uint16Array(l);

                while (l--) {
                    const s = Math.max(-1, Math.min(1, b16[l]));
                    buf[l] = s < 0 ? s * 0x8000 : s * 0x7fff;
                }
                b16.map((x) => x * 23173.26);
                cb(Buffer.from(buf.buffer));
            });