Domanda

voglio usare jFugue per riprodurre musica MIDI in un applet. C'è una classe per il MIDI modello - Pattern - e l'unico metodo per caricare il modello è da un file. Ora, io non so come applet file di carico e cosa no, ma sto usando un quadro (PulpCore) che rende le attività di carico di un compito semplice. Se ho bisogno di afferrare un bene da un catalogo postale, posso utilizzare la classe Assets che fornisce get() e getAsStream() metodi. get() restituisce la risorsa dato come ByteArray, l'altro come InputStream.

Ho bisogno jFugue per caricare il modello sia da ByteArray o InputStream. In pseudo-codice, vorrei fare questo:

Pattern.load(new File(Assets.get("mymidifile.midi")));

Tuttavia non v'è nessun costruttore di file che avrebbe preso un ByteArray. Suggerimenti, per favore?

È stato utile?

Soluzione

E 'vero che jFugue non permette di caricare qualsiasi cosa, ma un file, il che è un peccato perché impedisce nulla con qualsiasi altro tipo di flusso:

public static final String TITLE = "Title";

public static Pattern loadPattern(File file) throws IOException {
    InputStream in = new FileInputStream(file);
    try {
        return loadPattern(in);
    } finally {
        in.close();
    }
}

public static Pattern loadPattern(URL url) throws IOException {
    InputStream in = url.openStream();
    try {
        return loadPattern(in);
    } finally {
        in.close();
    }
}

public static Pattern loadPattern(InputStream in) throws IOException {
    return loadPattern(new InputStreamReader(in, "UTF-8")); // or ISO-8859-1 ?
}

public static Pattern loadPattern(Reader reader) throws IOException {
    if (reader instanceof BufferedReader) {
        return loadPattern(reader);
    } else {
        return loadPattern(new BufferedReader(reader));
    }
}

public static Pattern loadPattern(BufferedReader bread) throws IOException {
    StringBuffer buffy = new StringBuffer();

    Pattern pattern = new Pattern();
    while (bread.ready()) {
        String s = bread.readLine();
        if ((s != null) && (s.length() > 1)) {
            if (s.charAt(0) != '#') {
                buffy.append(" ");
                buffy.append(s);
            } else {
                String key = s.substring(1, s.indexOf(':')).trim();
                String value = s.substring(s.indexOf(':')+1, s.length()).trim();
                if (key.equalsIgnoreCase(TITLE)) {
                    pattern.setTitle(value);
                } else {
                    pattern.setProperty(key, value);
                }
            }
        }
    }
    return pattern;
}

UPDATE (per loadMidi)

public static Pattern loadMidi(InputStream in) throws IOException, InvalidMidiDataException
{
    MidiParser parser = new MidiParser();
    MusicStringRenderer renderer = new MusicStringRenderer();
    parser.addParserListener(renderer);
    parser.parse(MidiSystem.getSequence(in));
    Pattern pattern = new Pattern(renderer.getPattern().getMusicString());
    return pattern;
}

public static Pattern loadMidi(URL url) throws IOException, InvalidMidiDataException
{
    MidiParser parser = new MidiParser();
    MusicStringRenderer renderer = new MusicStringRenderer();
    parser.addParserListener(renderer);
    parser.parse(MidiSystem.getSequence(url));
    Pattern pattern = new Pattern(renderer.getPattern().getMusicString());
    return pattern;
}

Altri suggerimenti

Se non mi sbaglio, i file di pattern contengono solo testo. Caricare il file usando getAsStream (), quindi convertirlo in una stringa utilizzando

BufferedReader br = new BufferedReader(new InputStreamReader(yourStream));
//...
String pattern = convertToString(br); // you should implement convertToString yourself. It's easy. Read the java.io APIs.

Dove yourStream è l'InputStream restituito da getAsStream (). Quindi utilizzare l'add (String ... modelli) metodo per caricare il modello:

add(pattern);

È possibile utilizzare questo codice (tratto dal implementazione del metodo Pattern.loadPattern()):

    InputStream is = ...; // Get a stream from the Asset object

    // Prepare a pattern object
    Pattern pattern = new Pattern();

    // Now start reaing from the stream
    StringBuffer buffy = new StringBuffer();
    BufferedReader bread = new BufferedReader(new InputStreamReader(is));
    while (bread.ready()) {
        String s = bread.readLine();
        if ((s != null) && (s.length() > 1)) {
            if (s.charAt(0) != '#') {
                buffy.append(" ");
                buffy.append(s);
            } else {
                String key = s.substring(1, s.indexOf(':')).trim();
                String value = s.substring(s.indexOf(':')+1, s.length()).trim();
                if (key.equalsIgnoreCase(TITLE)) {
                    pattern.setTitle(value);
                } else {
                    pattern.setProperty(key, value);
                }
            }
        }
    }
    bread.close();
    pattern.setMusicString(buffy.toString());

    // Your pattern is now ready

Si potrebbe leggere l'array di byte e di trasformarlo in una stringa.

Il problema sarà l'InputStream. C'è uno StringBufferInputStream, ma è sconsigliato a favore StringReader.

byte [] b = Assets.get();
InputStream is = new StringBufferInputStream(new String(b));
Pattern.load(is);

Non si vuole utilizzare File, si desidera utilizzare java.io.ByteArrayInputStream

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top