在Java中生成噪声的颜色

时间:2014-11-16 23:29:27

标签: java audio noise noise-generator

我想使用Java创建一个彩色噪声生成器,它可以生成本文中定义的所有颜色:http://en.wikipedia.org/wiki/Colors_of_noise

  1. 从最简单的一个,White Noise开始,我如何产生噪音,以便无限期播放?
  2. 从那里,我如何修改我的生成器以生成任何颜色?
  3. 我对如何产生噪音本身感到困惑,并且对于一旦产生我可以通过扬声器输出它感到困惑。

    非常感谢任何链接或提示!

    我还看了另一个问题:Java generating sound

    但我不完全理解其中一条评论中给出的代码中发生了什么。它也没有告诉我该代码会产生什么样的噪音,所以我不知道如何修改它会产生白噪声。

2 个答案:

答案 0 :(得分:3)

这是一个用纯Java生成白噪声的程序。它可以很容易地改变以产生其他颜色的噪音。

import javax.sound.sampled.*;
import javax.swing.*;
import java.awt.*;
import java.awt.event.WindowAdapter;
import java.awt.event.WindowEvent;
import java.nio.ByteBuffer;
import java.util.Random;

public class WhiteNoise extends JFrame {

    private GeneratorThread generatorThread;

    public static void main(String[] args) {
        EventQueue.invokeLater(new Runnable() {
            public void run() {
                try {
                    WhiteNoise frame = new WhiteNoise();
                    frame.setVisible(true);
                } catch (Exception e) {
                    e.printStackTrace();
                }
            }
        });
    }

    public WhiteNoise() {
        addWindowListener(new WindowAdapter() {
            @Override
            public void windowClosing(WindowEvent e) {
                generatorThread.exit();
                System.exit(0);
            }
        });

        setTitle("White Noise Generator");
        setResizable(false);
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        setBounds(100, 100, 200, 50);
        setLocationRelativeTo(null);
        getContentPane().setLayout(new BorderLayout(0, 0));
        generatorThread = new GeneratorThread();
        generatorThread.start();
    }

    class GeneratorThread extends Thread {

        final static public int SAMPLE_SIZE = 2;
        final static public int PACKET_SIZE = 5000;

        SourceDataLine line;
        public boolean exitExecution = false;

        public void run() {

            try {
                AudioFormat format = new AudioFormat(44100, 16, 1, true, true);
                DataLine.Info info = new DataLine.Info(SourceDataLine.class, format, PACKET_SIZE * 2);

                if (!AudioSystem.isLineSupported(info)) {
                    throw new LineUnavailableException();
                }

                line = (SourceDataLine)AudioSystem.getLine(info);
                line.open(format);
                line.start();
            } catch (LineUnavailableException e) {
                e.printStackTrace();
                System.exit(-1);
            }

            ByteBuffer buffer = ByteBuffer.allocate(PACKET_SIZE);

            Random random = new Random();
            while (exitExecution == false) {
                buffer.clear();
                for (int i=0; i < PACKET_SIZE /SAMPLE_SIZE; i++) {
                    buffer.putShort((short) (random.nextGaussian() * Short.MAX_VALUE));
                }
                line.write(buffer.array(), 0, buffer.position());
            }

            line.drain();
            line.close();
        }

        public void exit() {
            exitExecution =true;
        }
    }
}

答案 1 :(得分:1)

我实际上正在开展一个项目,用于获取白噪声并对其进行采样以产生随机数。你需要的是相反的!

声音是压力与时间的关系。基本上从0压力开始,并从 - (最大振幅)到(最大振幅)添加随机量的压力。白噪声的幅度是随机的并且是正态分布的,因此您可以使用Random.nextGaussian()来生成随机z分数。将z分数乘以标准偏差(您可能需要进行一些测试以找到您喜欢的振幅的标准偏差),然后将其作为音频文件中每个样本的振幅。

至于生成声音文件本身,如果你还没有,你应该调查Java Sound API。它有很多很好的方法可用于创建声音文件和播放。

问题的下一部分,非白噪声,我担心我不确定波形是什么样的。它可能遵循相似的生成随机z分数并将它们乘以某个幅度标准差(或者更可能通过随时间变化的某个幅度函数)。