Overblog
Editer l'article Suivre ce blog Administration + Créer mon blog

Synthé en Java

21 Novembre 2015 , Rédigé par Ghislain Martin Publié dans #SYNTHES, #DEVELOP, #MUSIQUE, #APPLET, #JAVA

Bonjour,

Second article d'une série de 3, aujourd'hui, code source minimaliste pour générer une sinusoïde infinie à 440 hertz via une applet directement dans votre navigateur. Et attention les gars, on est sur du son en 16 bits ! Modifiez la méthode "getShort" pour obtenir des timbres un peu plus riches et variés. Bref, voici le squelette de base, je peux pas faire beaucoup plus court :

import java.applet.Applet;
import java.awt.Color;
import java.awt.Graphics;
import java.awt.Image;
import java.nio.ByteBuffer;

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

public class minimal extends Applet implements Runnable {

    public void init() {
        setSize(LARGEUR, HAUTEUR);
        
        tr = new Thread(this);
        tr.start();
    }

    @Override
    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) {
            System.out.println("Line of that type is not available");
            e.printStackTrace();            
            System.exit(-1);
        }

        ByteBuffer cBuf = ByteBuffer.allocate(PACKET_SIZE);

        while (bExitThread == false) {
            cBuf.clear();

            for (int i = 0; i < PACKET_SIZE / SAMPLE_SIZE; i++) {
                cBuf.putShort(getShort());
            }

            line.write(cBuf.array(), 0, cBuf.position());    

            try {
                while (line.getBufferSize() - line.available() > PACKET_SIZE)
                    Thread.sleep(5);
            }
            catch (InterruptedException e) {

            }
        }

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

    public void exit() {
        bExitThread = true;
    }
    
    private short getShort() {
        iTimeLine++;
        double phase = 2.0 * Math.PI * (double)((iTimeLine * dFrequence) % SAMPLING_RATE) / (double)SAMPLING_RATE;
        return (short)(25000.0 * Math.sin(phase));
    }
    
    //variables graphiques
    int LARGEUR = 800;
    int HAUTEUR = 400;
    
    //variables musicales
    int iTimeLine = 0;
    double dFrequence = 440.0;
    int SAMPLING_RATE = 44100;
    int SAMPLE_SIZE = 2;
    double BUFFER_DURATION = 0.050;
    int PACKET_SIZE = (int)(BUFFER_DURATION * SAMPLING_RATE * SAMPLE_SIZE);
    boolean bExitThread = false;
    SourceDataLine line;
    int bufferSize = 2200;
    
    //variables autres
    Thread tr;
    static final long serialVersionUID = 1L;
}

A+

GhisMart

Partager cet article

Commenter cet article