// Path: dev/java/vocobox-api/src/main/java/org/vocobox/model/voice/pitch/evaluate/PitchPrecisionDistanceInSemitone.java
// public class PitchPrecisionDistanceInSemitone implements PitchPrecisionDistance {
//     public static final float NOTE_A4_FREQ = 440f;
//     public static final int SEMITONES = 12;
// 
//     /**
//      * 
//      * Return the semitone distance between the estimated and expected
//      * frequency.
//      * 
//      * Example : considering those three notes
//      * <ul>
//      * <li>A4 : 440.00 Hz
//      * <li>Ab4 : 415.30 Hz
//      * <li>A#4 : 466.16 Hz
//      * </ul>
//      * 
//      * Any frequency in the following range will be considered to be A4:
//      * <ul>
//      * <li>mean(freq(Ab4), freq(A4)) : A4 lower bound (also Ab4 upper bound)
//      * <li>mean(freq(A4), freq(A#4)) : A4 upper bound (also A#4 lower bound)
//      * </ul>
//      * 
//      * @param expectedFrequency
//      * @param estimatedFrequency
//      * @return
//      */
//     @Override
//     public double distance(float expectedFrequency, float estimatedFrequency) {
//         return noteSemitoneValue(expectedFrequency) - noteSemitoneValue(estimatedFrequency);
//     }
// 
//     public double noteSemitoneValue(float frequency) {
//         return SEMITONES * log2(frequency / NOTE_A4_FREQ);
//     }
//     
//     /** http://www.bibmath.net/dico/index.php3?action=affiche&quoi=./l/logarithme.html
//      * http://gilles.costantini.pagesperso-orange.fr/Lycee_fichiers/CoursT_fichiers/ExpLn03.pdf
//      * */
//     /*public float semitoneValueToFrequency(){
//         
//     }*/
// 
//     /**
//      * y=log2(x) <-> x=2^y
//      */
//     public double log2(float x) {
//         return Math.log(x) / Math.log(2);
//     }
// 
//     /**
//      * y=log2(x) <-> x=2^y
//      */
//     public double log2Inverse(float y) {
//         return Math.pow(2, y);
//     }
// 
//     /**
//      * Expect "clean" frequency as input, e.g. 440.0f for A4 Output : a lower
//      * limit to define a range around input frequency
//      */
//     public int noteLowerBound(float frequency) {
//         return 0;
//     }
// 
//     public int noteUpperBound(float frequency) {
//         return 0;
//     }
// }
// 
// Path: dev/java/vocobox-api/src/main/java/org/vocobox/ui/Palette.java
// public class Palette {
//     public static void apply(Chart chart){
//         IAxeLayout axe = chart.getAxeLayout();
//         axe.setMainColor(Color.WHITE);
//         chart.getView().setBackgroundColor(Color.BLACK);
//     }
//     
//     public static void apply(SynthMonitorCharts charts){
//         charts.settings.confiColor = Color.BLUE.clone();
//         charts.settings.pitchColor = Color.MAGENTA.clone();
//         charts.settings.ampliColor = Color.CYAN.clone();
//     }
// }


import java.util.ArrayList;
import java.util.List;
import org.apache.log4j.Logger;
import org.jzy3d.chart.Chart;
import org.jzy3d.chart2d.Chart2d;
import org.jzy3d.colors.Color;
import org.jzy3d.maths.BoundingBox3d;
import org.jzy3d.maths.Coord2d;
import org.jzy3d.maths.Coord3d;
import org.jzy3d.plot2d.primitives.Serie2d;
import org.jzy3d.plot3d.primitives.axes.AxeBox;
import org.jzy3d.plot3d.primitives.axes.AxeCrossAnnotation;
import org.jzy3d.plot3d.primitives.axes.AxeXLineAnnotation;
import org.jzy3d.plot3d.primitives.axes.AxeXRectangleAnnotation;
import org.jzy3d.plot3d.primitives.axes.IAxe;
import org.jzy3d.plot3d.primitives.axes.layout.IAxeLayout;
import org.jzy3d.plot3d.primitives.axes.layout.providers.PitchTickProvider;
import org.jzy3d.plot3d.primitives.axes.layout.providers.RegularTickProvider;
import org.jzy3d.plot3d.primitives.axes.layout.renderers.IntegerTickRenderer;
import org.jzy3d.plot3d.primitives.axes.layout.renderers.PitchTickRenderer;
import org.jzy3d.plot3d.rendering.view.View;
import org.jzy3d.plot3d.rendering.view.modes.ViewBoundMode;
import org.jzy3d.plot3d.transform.space.SpaceTransformLog2;
import org.jzy3d.plot3d.transform.space.SpaceTransformer;
import org.vocobox.model.synth.MonitorSettings;
import org.vocobox.model.synth.SynthMonitor;
import org.vocobox.model.synth.SynthMonitorDefault;
import org.vocobox.model.voice.pitch.evaluate.PitchPrecisionDistanceInSemitone;
import org.vocobox.ui.Palette;
    public float currentConfidenceReadOnly = 1;
    public float currentAmplitudeReadOnly = 1;
    protected float expectedFrequency;

    public PitchPrecisionDistanceInSemitone getPitchPrecisionEvaluator() {
        return new PitchPrecisionDistanceInSemitone();
    }

    /*
     * ###################################################################
     */

    public SynthMonitorCharts() {
        this(MonitorSettings.DEFAULT, true, true);
    }

    public SynthMonitorCharts(MonitorSettings settings) {
        this(settings, true, true);
    }

    public SynthMonitorCharts(MonitorSettings settings, boolean init, boolean startThreads) {
        super();
        this.settings = settings;
        if (init) {
            init(settings, settings.applyPalette);
        }
    }

    public void init(MonitorSettings settings, boolean applyPalette) {
        if (applyPalette)
// Path: dev/java/vocobox-api/src/main/java/org/vocobox/model/voice/pitch/evaluate/PitchPrecisionDistanceInSemitone.java
// public class PitchPrecisionDistanceInSemitone implements PitchPrecisionDistance {
//     public static final float NOTE_A4_FREQ = 440f;
//     public static final int SEMITONES = 12;
// 
//     /**
//      * 
//      * Return the semitone distance between the estimated and expected
//      * frequency.
//      * 
//      * Example : considering those three notes
//      * <ul>
//      * <li>A4 : 440.00 Hz
//      * <li>Ab4 : 415.30 Hz
//      * <li>A#4 : 466.16 Hz
//      * </ul>
//      * 
//      * Any frequency in the following range will be considered to be A4:
//      * <ul>
//      * <li>mean(freq(Ab4), freq(A4)) : A4 lower bound (also Ab4 upper bound)
//      * <li>mean(freq(A4), freq(A#4)) : A4 upper bound (also A#4 lower bound)
//      * </ul>
//      * 
//      * @param expectedFrequency
//      * @param estimatedFrequency
//      * @return
//      */
//     @Override
//     public double distance(float expectedFrequency, float estimatedFrequency) {
//         return noteSemitoneValue(expectedFrequency) - noteSemitoneValue(estimatedFrequency);
//     }
// 
//     public double noteSemitoneValue(float frequency) {
//         return SEMITONES * log2(frequency / NOTE_A4_FREQ);
//     }
//     
//     /** http://www.bibmath.net/dico/index.php3?action=affiche&quoi=./l/logarithme.html
//      * http://gilles.costantini.pagesperso-orange.fr/Lycee_fichiers/CoursT_fichiers/ExpLn03.pdf
//      * */
//     /*public float semitoneValueToFrequency(){
//         
//     }*/
// 
//     /**
//      * y=log2(x) <-> x=2^y
//      */
//     public double log2(float x) {
//         return Math.log(x) / Math.log(2);
//     }
// 
//     /**
//      * y=log2(x) <-> x=2^y
//      */
//     public double log2Inverse(float y) {
//         return Math.pow(2, y);
//     }
// 
//     /**
//      * Expect "clean" frequency as input, e.g. 440.0f for A4 Output : a lower
//      * limit to define a range around input frequency
//      */
//     public int noteLowerBound(float frequency) {
//         return 0;
//     }
// 
//     public int noteUpperBound(float frequency) {
//         return 0;
//     }
// }
// 
// Path: dev/java/vocobox-api/src/main/java/org/vocobox/ui/Palette.java
// public class Palette {
//     public static void apply(Chart chart){
//         IAxeLayout axe = chart.getAxeLayout();
//         axe.setMainColor(Color.WHITE);
//         chart.getView().setBackgroundColor(Color.BLACK);
//     }
//     
//     public static void apply(SynthMonitorCharts charts){
//         charts.settings.confiColor = Color.BLUE.clone();
//         charts.settings.pitchColor = Color.MAGENTA.clone();
//         charts.settings.ampliColor = Color.CYAN.clone();
//     }
// }


// Path: dev/java/vocobox-api/src/main/java/org/vocobox/ui/charts/synth/SynthMonitorCharts.java
import java.util.ArrayList;
import java.util.List;
import org.apache.log4j.Logger;
import org.jzy3d.chart.Chart;
import org.jzy3d.chart2d.Chart2d;
import org.jzy3d.colors.Color;
import org.jzy3d.maths.BoundingBox3d;
import org.jzy3d.maths.Coord2d;
import org.jzy3d.maths.Coord3d;
import org.jzy3d.plot2d.primitives.Serie2d;
import org.jzy3d.plot3d.primitives.axes.AxeBox;
import org.jzy3d.plot3d.primitives.axes.AxeCrossAnnotation;
import org.jzy3d.plot3d.primitives.axes.AxeXLineAnnotation;
import org.jzy3d.plot3d.primitives.axes.AxeXRectangleAnnotation;
import org.jzy3d.plot3d.primitives.axes.IAxe;
import org.jzy3d.plot3d.primitives.axes.layout.IAxeLayout;
import org.jzy3d.plot3d.primitives.axes.layout.providers.PitchTickProvider;
import org.jzy3d.plot3d.primitives.axes.layout.providers.RegularTickProvider;
import org.jzy3d.plot3d.primitives.axes.layout.renderers.IntegerTickRenderer;
import org.jzy3d.plot3d.primitives.axes.layout.renderers.PitchTickRenderer;
import org.jzy3d.plot3d.rendering.view.View;
import org.jzy3d.plot3d.rendering.view.modes.ViewBoundMode;
import org.jzy3d.plot3d.transform.space.SpaceTransformLog2;
import org.jzy3d.plot3d.transform.space.SpaceTransformer;
import org.vocobox.model.synth.MonitorSettings;
import org.vocobox.model.synth.SynthMonitor;
import org.vocobox.model.synth.SynthMonitorDefault;
import org.vocobox.model.voice.pitch.evaluate.PitchPrecisionDistanceInSemitone;
import org.vocobox.ui.Palette;

    public float currentConfidenceReadOnly = 1;
    public float currentAmplitudeReadOnly = 1;
    protected float expectedFrequency;

    public PitchPrecisionDistanceInSemitone getPitchPrecisionEvaluator() {
        return new PitchPrecisionDistanceInSemitone();
    }

    /*
     * ###################################################################
     */

    public SynthMonitorCharts() {
        this(MonitorSettings.DEFAULT, true, true);
    }

    public SynthMonitorCharts(MonitorSettings settings) {
        this(settings, true, true);
    }

    public SynthMonitorCharts(MonitorSettings settings, boolean init, boolean startThreads) {
        super();
        this.settings = settings;
        if (init) {
            init(settings, settings.applyPalette);
        }
    }

    public void init(MonitorSettings settings, boolean applyPalette) {
        if (applyPalette)
            Palette.apply(this); // fix default colors