xxxxxxxxxx
100
// Daniel Shiffman
// https://thecodingtrain.com/CodingChallenges/151-ukulele-tuner.html
// https://youtu.be/F1OkDTUkKFo
// https://editor.p5js.org/codingtrain/sketches/8io2zvT03
//
// Modified Solution by Lokesh Kumar
// if you have android use this app for signal generation:
// https://play.google.com/store/apps/details?id=com.xyz.signal&hl=en
//
const model_url = 'https://cdn.jsdelivr.net/gh/ml5js/ml5-data-and-models/models/pitch-detection/crepe/';
let pitch;
let mic;
let freq = 0;
let threshold = 1;
let loaded = false;
let target = {note:"X",freq:Infinity};
let limit = 20;
let notes = [{
note: 'A',
freq: 440
},
{
note: 'E',
freq: 329.6276
},
{
note: 'C',
freq: 261.6256
},
{
note: 'G',
freq: 391.9954
}
];
function setup() {
createCanvas(400, 400);
audioContext = getAudioContext();
mic = new p5.AudioIn();
mic.start(listening);
}
function listening() {
console.log('listening');
pitch = ml5.pitchDetection(
model_url,
audioContext,
mic.stream,
modelLoaded
);
}
function draw() {
let markHeight = 10;
let markWidth = 5;
let markX = width/2;
let markY = height/3;
if(loaded){
freq = pitch.frequency?pitch.frequency : freq;
if(pitch.frequency){
target = notes.reduce((min,current)=>{
return (Math.abs(min.freq-freq)<=Math.abs(current.freq-freq))?min:current;
},target)}
}
let diff = (freq - target.freq);
let adiff = Math.abs(diff);
background(0);
textAlign(CENTER, CENTER);
fill(255);
textSize(32);
text("Current: "+freq.toFixed(2), width / 2, height - 130);
text("Target: "+target.freq.toFixed(2)+` (${target.note})`, width / 2, height - 80);
push();
strokeWeight(2);
stroke(255,200,0);
line(0,height/3,width,height/3);
stroke(0,255,0);
line(width/2,height/3-10,width/2,height/3+3);
line()
noStroke();
if (diff < -limit){markX = 0; fill(255,0,0);}
else if (diff > limit){markX = width;fill(255,0,0);}
else{markX =width/2 + (diff*((width/2)/limit)); fill(adiff*10,255-adiff*10,0);}
triangle(markX,markY,markX-markWidth,markY+markHeight,markX+markWidth,markY+markHeight);
text("Difference: "+diff.toFixed(2), width / 2, height - 180);
pop();
}
function modelLoaded() {
console.log('model loaded');
loaded = true;
}