Sto riscontrando discrepanze significative tra le pose dal callback onPoseAvailable()
e Tango.getPoseAtTime()
. Ho scritto un programma di test in cui nel onPoseAvailable()
ho registrato la posa consegnata e ho utilizzato getPoseAtTime()
per richiedere la posa utilizzando il timestamp da 2 richiamate in precedenza. KEY_BOOLEAN_SMOOTH_POSE
è configurato false
. Ecco il codice che lo fa (la variabile timestamps_
membro è un LinkedList<Double>
):Discrepanze Project Tango onPoseAvailable() e getPoseAtTime()
@Override
public void onPoseAvailable(TangoPoseData poseData) {
if (poseData != null && poseData.statusCode == TangoPoseData.POSE_VALID) {
Log.v("bug",
String.format("onPoseAvailable t: %f, base: %d, target %d, p: (%f, %f, %f)",
poseData.timestamp,
poseData.baseFrame,
poseData.targetFrame,
poseData.translation[0], poseData.translation[1], poseData.translation[2]));
timestamps_.add(poseData.timestamp);
if (timestamps_.size() > 3)
timestamps_.remove();
}
if (timestamps_.isEmpty())
return;
TangoCoordinateFramePair framePair = new TangoCoordinateFramePair(
TangoPoseData.COORDINATE_FRAME_START_OF_SERVICE,
TangoPoseData.COORDINATE_FRAME_DEVICE);
poseData = tango_.getPoseAtTime(timestamps_.getFirst(), framePair);
if (poseData != null && poseData.statusCode == TangoPoseData.POSE_VALID) {
Log.v("bug",
String.format("getPoseAtTime t: %f, base: %d, target %d, p: (%f, %f, %f)",
poseData.timestamp,
poseData.baseFrame,
poseData.targetFrame,
poseData.translation[0], poseData.translation[1], poseData.translation[2]));
}
}
Ecco un estratto da un registro effettivo (ho deinterleaved le chiamate registrate per chiarezza):
onPoseAvailable t: 2732.762486, base: 2, target 4, p: (0.280245, 0.412468, 0.562201)
onPoseAvailable t: 2732.802553, base: 2, target 4, p: (0.296951, 0.420919, 0.599938)
onPoseAvailable t: 2732.852638, base: 2, target 4, p: (0.317444, 0.429809, 0.646445)
onPoseAvailable t: 2732.882689, base: 2, target 4, p: (0.330845, 0.434106, 0.676810)
onPoseAvailable t: 2732.932774, base: 2, target 4, p: (0.350995, 0.439777, 0.723639)
onPoseAvailable t: 2732.962825, base: 2, target 4, p: (0.363319, 0.442731, 0.754508)
onPoseAvailable t: 2732.992875, base: 2, target 4, p: (0.373911, 0.445289, 0.784786)
onPoseAvailable t: 2733.032943, base: 2, target 4, p: (0.387709, 0.448182, 0.822682)
onPoseAvailable t: 2733.062994, base: 2, target 4, p: (0.398502, 0.450481, 0.852662)
onPoseAvailable t: 2733.073011, base: 2, target 4, p: (0.401869, 0.451084, 0.862530)
onPoseAvailable t: 2733.103062, base: 2, target 4, p: (0.411136, 0.452486, 0.890441)
getPoseAtTime t: 2732.712401, base: 2, target 4, p: (0.269301, 0.410911, 0.549182)
getPoseAtTime t: 2732.732435, base: 2, target 4, p: (0.277217, 0.415130, 0.567040)
getPoseAtTime t: 2732.762486, base: 2, target 4, p: (0.288928, 0.421914, 0.595162)
getPoseAtTime t: 2732.802553, base: 2, target 4, p: (0.305241, 0.429648, 0.632158)
getPoseAtTime t: 2732.852638, base: 2, target 4, p: (0.324359, 0.437655, 0.680300)
getPoseAtTime t: 2732.882689, base: 2, target 4, p: (0.332997, 0.442538, 0.712727)
getPoseAtTime t: 2732.932774, base: 2, target 4, p: (0.353665, 0.447269, 0.759725)
getPoseAtTime t: 2732.962825, base: 2, target 4, p: (0.369174, 0.451645, 0.790263)
getPoseAtTime t: 2732.992875, base: 2, target 4, p: (0.382584, 0.454754, 0.819555)
getPoseAtTime t: 2733.032943, base: 2, target 4, p: (0.396857, 0.456922, 0.856626)
getPoseAtTime t: 2733.062994, base: 2, target 4, p: (0.409672, 0.460060, 0.888748)
Dai un'occhiata all'ultimo dato getPoseAtTime()
, con timestamp 2733.062994. Si noti che i suoi valori di posizione non corrispondono alla posa da onPoseAvailable
con lo stesso timestamp. Qualcosa non è giusto qui.
Ho preso in considerazione il fatto che una posizione di posa spline non avrebbe necessariamente bisogno di passare attraverso i punti di controllo, ma non penso che sia una spiegazione accettabile. Prima di tutto non ha molto senso avere un'API che fornisca valori diversi per la stessa misura. Ma in più i numeri reali non sostengono quella congettura.
Controllare il valore di getPoseAtTime()
Y, 0,460060. Questo è al di fuori dell'intervallo Y di tutti i valori di onPoseAvailable()
Y, sia prima che dopo (sull'intero registro di fatto). Nessun modello di interpolazione ragionevole può produrre questo valore.
Immagino che la domanda sia: cosa sta succedendo qui? Le pose sono incoerenti quindi almeno una di esse è sbagliata (se non entrambe). La mia ipotesi sarebbe che il onPoseAvailable()
è più probabile che sia corretto.
Qui è un grafico della posizione Y in funzione del tempo dei due posa metodi (rilascio Nash) con il fermo tablet nel dock:
La linea blu è la onPoseAvailable()
callback e la linea rossa è il polling getPoseAtTime()
. Questi risultati sono piuttosto strani. Se le pose dovessero essere diverse, mi aspetto che il valore di polling sia più agevole perché potrebbe essere filtrato utilizzando i contributi dei campioni prima e dopo il tempo di polling, mentre il valore di callback non sarà filtrato o filtrato usando solo campioni. Ma questo non è ciò che vediamo - il valore del sondaggio appare molto più rumoroso.
Ecco un grafico simile catturato mentre spostavo il tablet su e giù. Il valore del polling ha ancora più alte frequenze e i due segnali non seguono particolarmente da vicino.
C'è qualcosa di nuovo da aggiungere? – bashbug