Java Sound 背景噪音消除

标签 java sockets audio javasound noise

每当我使用 Java 中的 SourceDataLine 类读取构成音频的字节时,我都会在播放时听到烦人的嗡嗡声背景噪音。谁能告诉我如何才能完全摆脱它?提前致谢。

更新:我已经发布了代码,但我的实际目标是从麦克风获取字节数据并将其传输到另一个客户端。我正在为客户放置代码。服务器在这里并不重要,因为它的唯一作用是将字节数组转发到另一个客户端。

import javax.sound.sampled.AudioFormat;
import javax.sound.sampled.AudioSystem;
import javax.sound.sampled.DataLine;
import javax.sound.sampled.SourceDataLine;
import javax.sound.sampled.TargetDataLine;

import java.net.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.io.*;

import javax.swing.*;

public class Client001 extends JFrame implements ActionListener {

    JButton startButton = new JButton("Open Microphone");
    DataInputStream fromServer;
    DataOutputStream toServer;
    AudioFormat format = new AudioFormat(44100, 16, 1, true, true);
    DataLine.Info targetInfo = new DataLine.Info(TargetDataLine.class, format);
    DataLine.Info sourceInfo = new DataLine.Info(SourceDataLine.class, format);
    TargetDataLine targetLine; 
    SourceDataLine sourceLine;

    public static void main(String[] args) {


        final Client001 c = new Client001();
        c.connect2Server();
        c.initializeSoundParams();
        c.initGUI();

        Thread receiver = new Thread(){
            public void run(){

                c.startSoundReceiver();
            }

        };
        receiver.start();







    }

    public void connect2Server(){

        try{


            Socket socket = new Socket("108.61.181.112",8000);
            fromServer = new DataInputStream(socket.getInputStream());
            toServer = new DataOutputStream(socket.getOutputStream());



        }

        catch(Exception e){

            e.printStackTrace();
        }
    }


    public void initializeSoundParams(){

        try{
            targetLine = (TargetDataLine) AudioSystem.getLine(targetInfo);
            sourceLine = (SourceDataLine) AudioSystem.getLine(sourceInfo);
        }
        catch(Exception e){

        }

    }


    public byte[] filterNoise(byte[] data,int range){

        byte value = data[0];
        for (int i=1; i<data.length; i++){
                byte currentValue = data[i];
                value += (currentValue - value) / range;
                data[i] = value;
        }

        return data;
    }



    public void startSoundReceiver(){

        try{

            toServer.writeUTF("1");
            sourceLine.open(format);
            sourceLine.start();

            while(true){

                int dataSize = fromServer.readInt();                        
                System.out.println("Length = " + dataSize);                 
                byte[] targetData = new byte[dataSize];
                fromServer.readFully(targetData,0,dataSize);
                //targetData = filterNoise(targetData,60);
                sourceLine.write(targetData, 0, targetData.length);
            }


        }
        catch(Exception e){

            e.printStackTrace();
        }



    }

    public void startSoundSender(){


        try{

            targetLine.open(format);
            targetLine.start();

            int numBytesRead;
            byte[] targetData = new byte[targetLine.getBufferSize() / 5];

            //toServer.writeUTF("1");

            while (true) {
                numBytesRead = targetLine.read(targetData, 0, targetData.length);

                System.out.println("Length = " + numBytesRead);

                if (numBytesRead == -1) break;

                toServer.writeInt(numBytesRead);
                toServer.write(targetData,0,numBytesRead);

                //sourceLine.write(targetData, 0, numBytesRead);
            }
        }
        catch(Exception e){

            e.printStackTrace();
        }

    }





    public void initGUI(){


        setLayout(null);
        startButton.setBounds(30, 30, 180, 70);
        add(startButton);
        setTitle("Sound GUI");
        setSize(300,300);
        startButton.addActionListener(this);
        setVisible(true);
    }

    @Override
    public void actionPerformed(ActionEvent e) {

        if(e.getSource() == startButton){
            Thread sender = new Thread(){
                public void run(){

                    startSoundSender();
                }

            };
            sender.start();


        }



    }




}


import javax.sound.sampled.AudioFormat;
import javax.sound.sampled.AudioSystem;
import javax.sound.sampled.DataLine;
import javax.sound.sampled.SourceDataLine;
import javax.sound.sampled.TargetDataLine;

import java.net.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.io.*;

import javax.swing.*;

public class Client002 extends JFrame implements ActionListener {

    JButton startButton = new JButton("Open Microphone");
    DataInputStream fromServer;
    DataOutputStream toServer;
    AudioFormat format = new AudioFormat(44100, 8, 2, true, true);
    DataLine.Info targetInfo = new DataLine.Info(TargetDataLine.class, format);
    DataLine.Info sourceInfo = new DataLine.Info(SourceDataLine.class, format);
    TargetDataLine targetLine; 
    SourceDataLine sourceLine;

    public static void main(String[] args) {


        final Client002 c = new Client002();
        c.connect2Server();
        c.initializeSoundParams();
        c.initGUI();

        Thread receiver = new Thread(){
            public void run(){

                c.startSoundReceiver();
            }

        };
        receiver.start();







    }

    public void connect2Server(){

        try{


            Socket socket = new Socket("192.168.0.102",8000);
            fromServer = new DataInputStream(socket.getInputStream());
            toServer = new DataOutputStream(socket.getOutputStream());



        }

        catch(Exception e){

            e.printStackTrace();
        }
    }


    public void initializeSoundParams(){

        try{
            targetLine = (TargetDataLine) AudioSystem.getLine(targetInfo);
            sourceLine = (SourceDataLine) AudioSystem.getLine(sourceInfo);
        }
        catch(Exception e){

        }

    }

    public byte[] filterNoise(byte[] data,int range){

        byte value = data[0];
        for (int i=1; i<data.length; i++){
                byte currentValue = data[i];
                value += (currentValue - value) / range;
                data[i] = value;
        }

        return data;
    }

    public void startSoundReceiver(){

        try{

            toServer.writeUTF("2");
            sourceLine.open(format);
            sourceLine.start();

            while(true){

                int dataSize = fromServer.readInt();                        
                System.out.println("Length = " + dataSize);                 
                byte[] targetData = new byte[dataSize];
                fromServer.readFully(targetData,0,dataSize);
                targetData = filterNoise(targetData,20);
                sourceLine.write(targetData, 0, targetData.length);
            }


        }
        catch(Exception e){

            e.printStackTrace();
        }



    }

    public void startSoundSender(){


        try{

            targetLine.open(format);
            targetLine.start();

            int numBytesRead;
            byte[] targetData = new byte[targetLine.getBufferSize() / 5];

            //toServer.writeUTF("1");

            while (true) {
                numBytesRead = targetLine.read(targetData, 0, targetData.length);

                System.out.println("Length = " + numBytesRead);

                if (numBytesRead == -1) break;

                toServer.writeInt(numBytesRead);
                toServer.write(targetData,0,numBytesRead);

                //sourceLine.write(targetData, 0, numBytesRead);
            }
        }
        catch(Exception e){

            e.printStackTrace();
        }

    }





    public void initGUI(){


        setLayout(null);
        startButton.setBounds(30, 30, 180, 70);
        add(startButton);
        setTitle("Sound GUI");
        setSize(300,300);
        startButton.addActionListener(this);
        setVisible(true);
    }

    @Override
    public void actionPerformed(ActionEvent e) {

        if(e.getSource() == startButton){
            Thread sender = new Thread(){
                public void run(){

                    startSoundSender();
                }

            };
            sender.start();


        }



    }




}

最佳答案

如果您的样本大小是16 位“AudioFormat(44100, 16, 1, true, true);”

那么,你就不能用单个字节来制作过滤器

您应该尝试使用 8 位的样本大小,或者尝试组合两个字节来进行过滤操作。

关于Java Sound 背景噪音消除,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/31125159/

相关文章:

java - OSGi 类似请求的服务? (多个实例)

java - JAVA/C++ 中尾随字符的使用

audio - Bot 在离开前没有完成播放音频

java - 如何控制很多java线程?

javascript - Js 音频音量 slider

python - 使用python从USB输入线程(麦克风)捕获一个音频样本

java - 从 xml 文件中提取信息作为 RDF 三元组

java - 在 Java 中,您可以在另一个类的构造函数中调用一个类的 setter 吗?

c - 唯一标识套接字

perl - 在perl中通过套接字传递文件名