diff Block.java @ 0:4031cbb02f08

Initial import. Ignore-this: 87317e384f22bde48db996355191fa5f
author Marcus Pearce <m.pearce@gold.ac.uk>
date Tue, 18 May 2010 11:37:10 +0100
parents
children 93ed757b9871
line wrap: on
line diff
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/Block.java	Tue May 18 11:37:10 2010 +0100
@@ -0,0 +1,330 @@
+/*=============================================================================
+ * File:       Block.java
+ * Author:     Marcus Pearce <m.pearce@gold.ac.uk>
+ * Created:    <2008-01-07 10:38:45 marcusp>
+ * Time-stamp: <2010-05-17 11:42:23 marcusp>
+ *=============================================================================
+ */
+
+import java.util.Collections;
+import java.util.ArrayList; 
+import java.util.Iterator;
+import java.io.*;
+
+public class Block { 
+    
+    /* Label */ 
+    private String label; 
+    private boolean writeResults; 
+
+    /* the list of midi files, the current midi file and the midi directory*/ 
+    private FileList filelist; 
+    private String filename; 
+    private int melodyNumber; 
+
+    /* The Experiment and GUI */ 
+    private ExperimentGui gui; 
+    private Experiment exp; 
+    
+    /* The MidiPlayer */ 
+    private MidiPlayer mp; 
+
+    /* Probe positions, note onsets, durations, IOIs and pitches */ 
+    private ArrayList probes, onsets, iois, durations, pitches, clockStartTimes; 
+    private long tatum; 
+
+    /* The start of the song in nanoseconds */ 
+    private long startTime; 
+    
+    /* Results */ 
+    private MelodyResults mResults; 
+    
+    /* whether the current song has run yet or not */ 
+    private boolean hasRun;
+
+    /*
+     * Accessors 
+     */ 
+    public String getLabel() { return label; }
+    public int getMelodyNumber() { return melodyNumber; }
+    public void setMelodyNumber(int n) { melodyNumber = n; }
+    public long getTatum() { return tatum; } 
+    public MelodyResults getMelodyResults() { return mResults; }
+    public ArrayList getProbePositions() { return probes; } 
+    public ArrayList getInterOnsetIntervals() { return iois; } 
+    public ArrayList getOnsets() { return onsets; } 
+    public ArrayList getClockStartTimes() { return clockStartTimes; } 
+
+    /* set the start time in nanoseconds to NOW */ 
+    public long getStartTime() { return startTime; }
+    public void setStartTime() { startTime = System.nanoTime(); } 
+    
+    /* 
+     * constructor 
+     */ 
+    public Block(Experiment e, ExperimentGui eg, String fl, String lab, 
+                 boolean wr) { 
+        // set-up variables 
+        exp = e; 
+        gui = eg; 
+        label = lab; 
+        filelist = new FileList(fl); 
+        filename = (String)filelist.currentFile(); 
+        melodyNumber = 1; 
+        writeResults = wr; 
+        // initialise the block 
+        hasRun = false; 
+        initialiseBlock();
+        // Write out stimulus structure for all melodies in block
+        //writeStimuli(); 
+    }
+
+    /* initialise the block */ 
+    public void initialiseBlock() { 
+        // Initialise the Midiplayer 
+        mp = new MidiPlayer(exp.getMidiDirectory().concat(filename)); 
+        // Set up the melody structure and the probe positions 
+        setupSong(); 
+        setupProbes(); 
+        // Set up the results object for this melody
+        mResults = new MelodyResults(filename, probes, 
+                                     onsets, iois, durations, pitches); 
+        mResults.setSubjectID(exp.getSubjectID()); 
+        hasRun = false; 
+    }
+
+    public void storeMelodyResult() { 
+        if (writeResults && hasRun)
+            exp.addToSubjectResults(mResults); 
+    }
+    
+    private void setupSong() { 
+        // Get the note IOI and Onset lists 
+        onsets = mp.getOnsets(); 
+        durations = mp.getDurations(); 
+        iois = mp.getInterOnsetIntervals(); 
+        pitches = mp.getPitches(); 
+        tatum = mp.getTatum(); 
+    }
+
+    private void setupProbes() { 
+        ArrayList probePos = filelist.currentProbes(); 
+        Iterator ppi = probePos.iterator(); 
+        
+        // By convention, the first probe position is the unexpected
+        // one and  the second is the expected one. 
+        //probeValues.add(ProbeID.PROBE_UNEX); 
+        //probeValues.add(ProbeID.PROBE_EX); 
+
+        ArrayList probeValues = new ArrayList(probePos.size()); 
+
+        for (int i = 0; i < probePos.size(); i++)
+            probeValues.add(ProbeID.PROBE);
+        Iterator pvi = probeValues.iterator(); 
+        
+
+        // Set up probes 
+        probes = new ArrayList(onsets.size()); 
+        for (int i = 0; i < onsets.size(); i++) 
+            probes.add(ProbeID.NOT_PROBE); 
+
+        while(ppi.hasNext()) { 
+            int probe = ((Integer)ppi.next()).intValue(); 
+            // probes.set(probe - numEvents, ProbeID.START_CLOCK); 
+            probes.set(probe - 1, ProbeID.BEFORE_PROBE); 
+            probes.set(probe, (ProbeID)pvi.next()); 
+            probes.set(probe + 1, ProbeID.AFTER_PROBE); 
+        }
+        
+        // Set up the clock start times 
+        clockStartTimes = new ArrayList(probePos.size()); 
+        long clockTimeInMicroseconds = 
+            (tatum * exp.getClockUnits() * exp.getNumUnits()); 
+        for (int i = 0; i < probePos.size(); i++) { 
+            int ppos = ((Integer)probePos.get(i)).intValue(); 
+            long onset = ((Long)(onsets.get(ppos))).longValue(); 
+            clockStartTimes.add(onset - clockTimeInMicroseconds); 
+        }
+        try { 
+            Collections.sort(clockStartTimes); 
+        } catch (Exception e) { 
+            e.printStackTrace(); 
+        }
+    }
+
+    public void printProbes() { 
+        Iterator pi = probes.iterator(); 
+
+        int i = 1; 
+        while(pi.hasNext()) { 
+            System.out.println(filename + " " + i + ": " + pi.next()); 
+            i++; 
+        }
+    }
+                
+    public String nextFile() {
+        filelist.incrementFileIndex(); 
+        filename = filelist.currentFile(); 
+        melodyNumber = melodyNumber + 1; 
+        return filename;
+    }
+
+    /* add a reponse i and time t (nanoseconds) */ 
+    public void addResponse(int i, long t) { 
+        // System.out.println("answer = " + i + 
+        //                    "; responseTime = " + t + 
+        //                    "; startTime = " + startTime + 
+        //                    "; answer = " + (t - startTime) / 1000); 
+        // add relative responseTime in microseconds 
+        mResults.addResponse(i, (t - startTime) / 1000); 
+    }
+
+    public void addMelodyQA(String q, String a) { 
+        mResults.addQuestion(q); 
+        mResults.addAnswer(a); 
+    }
+
+    public void presentStimulus() { 
+        // Start the experiment 
+        setStartTime(); 
+        mp.play(); 
+        hasRun = true; 
+        
+        // Wait for midi file to stop playing 
+        //try { Thread.sleep((mp.getLength() / 1000) + 2000); } 
+        //catch (InterruptedException e) {}
+    }
+
+    public boolean isRunning() { return mp.getSequencer().isRunning(); }
+    public boolean hasRun() { return hasRun; } 
+
+
+    /* 
+     * Write out stimulus onsets and probe positions 
+     */ 
+
+    public void writeStimuli() {
+        String midiFile; 
+        while((midiFile = filelist.currentFile()) != null) { 
+            
+            Writer writer = null;
+            String composition = midiFile.substring(0, midiFile.length() - 4);
+            String outFile = 
+                exp.RESULTS_DIRECTORY + File.separator + 
+                "stimuli" + File.separator + composition 
+                + ".onsets"; 
+            File outputFile = new File(outFile); 
+            
+            MidiPlayer midip = 
+                new MidiPlayer(exp.getMidiDirectory().concat(midiFile)); 
+
+            // Setup the probes 
+            ArrayList probePos = filelist.currentProbes(); 
+            // Write the data 
+            try {
+                writer = new FileWriter (outputFile, true);
+            } catch (IOException e) {
+                System.out.println("Could not write file: " + 
+                                   outputFile.getPath());
+                return;
+            }
+            try {
+                writeResults(writer, midip, probePos, composition); 
+                writer.close();
+            } catch (IOException e) {
+                System.out.println (e.getMessage());
+                return;
+            }
+            // increment the file index 
+            filelist.incrementFileIndex(); 
+        }
+        // Reset filelist 
+        filelist.setFileIndex(0); 
+    }
+
+    private void writeResults(Writer w, MidiPlayer mipl, ArrayList probePos, 
+                              String composition) 
+        throws IOException { 
+
+        System.out.println(composition); 
+
+        ArrayList ons = mipl.getOnsets(); 
+        ArrayList pits = mipl.getPitches(); 
+        
+        Iterator oi = ons.iterator(); 
+        Iterator piti = pits.iterator(); 
+
+        // setup probes 
+        Iterator ppi = probePos.iterator(); 
+            
+        // By convention, the first probe position is the unexpected
+        // one and  the second is the expected one. 
+        // probeValues.add(ProbeID.PROBE_UNEX);
+        // probeValues.add(ProbeID.PROBE_EX);
+
+        ArrayList probeValues = new ArrayList(probePos.size()); 
+        for (int i = 0; i < probePos.size(); i++)
+            probeValues.add(ProbeID.PROBE);
+
+        Iterator pvi = probeValues.iterator(); 
+        
+        ArrayList pprobes = new ArrayList(ons.size()); 
+        for (int i = 0; i < ons.size(); i++) 
+            pprobes.add(ProbeID.NOT_PROBE); 
+        
+        while(ppi.hasNext()) { 
+            int probe = ((Integer)ppi.next()).intValue(); 
+            pprobes.set(probe - 1, ProbeID.BEFORE_PROBE); 
+            pprobes.set(probe, (ProbeID)pvi.next()); 
+            pprobes.set(probe + 1, ProbeID.AFTER_PROBE); 
+        }
+        
+        Iterator pi = pprobes.iterator(); 
+        int eventIndex = 1; 
+        
+        //writeHeader(w); 
+        
+        while(oi.hasNext()) { 
+            long onset = ((Long)oi.next()).longValue();
+            int pitch = ((Integer)piti.next()).intValue(); 
+
+            ProbeID p = (ProbeID)pi.next(); 
+            
+            int probe = 0; 
+            
+            switch(p) { 
+            case NOT_PROBE: 
+            case START_CLOCK:
+            case BEFORE_PROBE: 
+            case AFTER_PROBE: 
+                break; 
+            case PROBE:
+            case PROBE_EX: 
+            case PROBE_UNEX:
+                if (p == ProbeID.PROBE_UNEX)
+                    probe = 1; 
+                else if (p == ProbeID.PROBE_EX)
+                    probe = 2;
+                else if (p == ProbeID.PROBE)
+                    probe = 1;
+                break; 
+            default: 
+                System.out.println("Unexpected probe id: " + p); 
+                break; 
+            }
+            w.write(composition + " " +  eventIndex + " " + 
+                    onset + " " + pitch + " " + 
+                    probe + "\n"); 
+            eventIndex++; 
+        }
+    }
+    
+    private void writeHeader(Writer w) throws IOException {
+        w.write("melody note " + 
+                "onset pitch " + 
+                "probe"); 
+        w.write("\n"); 
+    }
+
+}
+