i come up with a scheme to correct timings, but it is hard to assess if it will work, and have not dared to try it.
copyEv is an array of timing distances between notes. "TIME"
plannedTime=0;
LoadTIME=performance.now();
STARTPLAY();
function STARTPLAY(){
if (keepGoing) {
stopRec=setTimeout(STARTPLAY,copyEv[playPos]);
//While still notes
if (playPos<copyEv.length) {
//******* CORRECT, THE FUTURE TIMING OF NEXT EVENT
//copyEv[] is an array of setTimeut timings between notes
plannedTime=copyEv[playpos]+plannedTime;
latency=plannedTime-(performance.now()-LoadTIME);
copyEv[playpos+1]=copyEv[playpos+1]-latency;
//*******************************************************
if (echo && mode=="Play"

{
pianoKeypressOut();
}
outportarr[outportindex].send(noteMessage[playPos]);
playPos++;
} else { stop();}
}
}
Basicly the scheme look at the current note and its "realtime playup time performance.now()-LoadTIME" compare it with the "planned/scheduled time" and remove the assesed latency time from next note planned to play.
At least that is my initial thought about what it should do.
And i think i see that i am really should not compare with current note "playpos", because that is planned in the future it must be playpos-1 that have latency.
Well the logic of passed and future events gets rather hairy.