2
2
import numpy as np
3
3
import time
4
4
5
- from threading import Lock
6
5
from enum import Enum
7
6
from OpenGL .GL import * # all prefixed with gl so OK to import *
8
7
@@ -244,8 +243,8 @@ def __init__(self, args=VisualizerArgs()):
244
243
self .shouldQuit = False
245
244
self .shouldPause = False
246
245
self .displayInitialized = False
247
- self .outputQueue = []
248
- self .outputQueueMutex = Lock ()
246
+ self .vioOutputQueue = []
247
+ self .mapperOutputQueue = []
249
248
self .clock = pygame .time .Clock ()
250
249
251
250
# Window
@@ -455,7 +454,8 @@ def onVioOutput(self, cameraPose, image=None, width=None, height=None, colorForm
455
454
"image" : None ,
456
455
"width" : self .targetResolution [0 ],
457
456
"height" : self .targetResolution [1 ],
458
- "colorFormat" : None
457
+ "colorFormat" : None ,
458
+ "time" : time .time ()
459
459
}
460
460
if image is not None :
461
461
# Flip the image upside down for OpenGL.
@@ -464,9 +464,15 @@ def onVioOutput(self, cameraPose, image=None, width=None, height=None, colorForm
464
464
output ['width' ] = width
465
465
output ['height' ] = height
466
466
output ['colorFormat' ] = colorFormat
467
+ self .vioOutputQueue .append (output )
467
468
468
- with self .outputQueueMutex :
469
- self .outputQueue .append (output )
469
+ MAX_VIO_OUTPUT_QUEUE_SIZE = 25
470
+ while len (self .vioOutputQueue ) > MAX_VIO_OUTPUT_QUEUE_SIZE :
471
+ if self .args .targetFps == 0 :
472
+ time .sleep (0.01 ) # Blocks replay, avoids dropping vio outputs
473
+ else :
474
+ self .vioOutputQueue .pop (0 )
475
+ print ("Warning: Dropping vio output in visualizer (processing too slow!)" )
470
476
471
477
# In live mode, future vio outputs are discarded
472
478
# In replay mode, Replay API is blocked -> no more vio outputs
@@ -479,59 +485,79 @@ def onMappingOutput(self, mapperOutput):
479
485
480
486
output = {
481
487
"type" : "slam" ,
482
- "mapperOutput" : mapperOutput
488
+ "mapperOutput" : mapperOutput ,
489
+ "time" : time .time ()
483
490
}
491
+ self .mapperOutputQueue .append (output )
484
492
485
- with self .outputQueueMutex :
486
- self .outputQueue .append (output )
493
+ MAX_MAPPER_OUTPUT_QUEUE_SIZE = 10
494
+ if len (self .mapperOutputQueue ) > MAX_MAPPER_OUTPUT_QUEUE_SIZE :
495
+ self .mapperOutputQueue .pop (0 )
496
+ print ("Warning: Dropping mapper output in visualizer (processing too slow!)" )
487
497
488
498
def run (self ):
489
499
vioOutput = None
490
500
prevVioOutput = None
491
501
wasTracking = False
492
502
503
+ def getNextOutput ():
504
+ vioOutputTime = None if len (self .vioOutputQueue ) == 0 else self .vioOutputQueue [0 ]["time" ]
505
+ mapperOutputTime = None if len (self .mapperOutputQueue ) == 0 else self .mapperOutputQueue [0 ]["time" ]
506
+ if vioOutputTime is None :
507
+ if mapperOutputTime is None : return None
508
+ return self .mapperOutputQueue .pop (0 )
509
+ if mapperOutputTime is None :
510
+ return self .vioOutputQueue .pop (0 )
511
+ return self .vioOutputQueue .pop (0 ) if vioOutputTime < mapperOutputTime else self .mapperOutputQueue .pop (0 )
512
+
513
+ def processVioOutput (output ):
514
+ nonlocal vioOutput , prevVioOutput , wasTracking
515
+ vioOutput = output
516
+ if vioOutput ['isTracking' ]:
517
+ wasTracking = True
518
+ cameraPose = vioOutput ["cameraPose" ]
519
+ self .poseTrail .append (cameraPose .getPosition ())
520
+ else :
521
+ vioOutput = None
522
+ if wasTracking :
523
+ self .__resetAfterLost ()
524
+ wasTracking = False
525
+
526
+ def processMapperOutput (output ):
527
+ nonlocal vioOutput , prevVioOutput , wasTracking
528
+
529
+ mapperOutput = output ["mapperOutput" ]
530
+ if wasTracking : # Don't render if not tracking. Messes up this visualization easily
531
+ self .map .onMappingOutput (mapperOutput )
532
+ if mapperOutput .finalMap :
533
+ if self .args .keepOpenAfterFinalMap :
534
+ self .showCameraFrustum = False
535
+ self .showCameraModel = False
536
+ if self .args .targetFps == 0 : self .args .targetFps = 30 # No vio outputs -> set 30fps mode instead
537
+ if self .cameraSmooth : self .cameraSmooth .reset () # Stop camera moving automatically
538
+ vioOutput = prevVioOutput
539
+ else :
540
+ self .shouldQuit = True
541
+
493
542
while not self .shouldQuit :
494
543
self .__processUserInput ()
495
544
496
545
# Process VIO & Mapping API outputs
497
546
while True :
498
547
if self .shouldPause : break
499
548
500
- with self .outputQueueMutex :
501
- if len (self .outputQueue ) > 0 :
502
- output = self .outputQueue .pop (0 )
503
- else :
504
- break
549
+ output = getNextOutput ()
550
+ if output is None : break
505
551
506
552
if output ["type" ] == "vio" :
507
- vioOutput = output
508
- if vioOutput ['isTracking' ]:
509
- wasTracking = True
510
- cameraPose = vioOutput ["cameraPose" ]
511
- self .poseTrail .append (cameraPose .getPosition ())
512
- else :
513
- vioOutput = None
514
- if wasTracking :
515
- self .__resetAfterLost ()
516
- wasTracking = False
553
+ processVioOutput (output )
517
554
518
555
# Render on all outputs if using target fps 0 (i.e. render on vio output mode)
519
- # unless they were dropped because visualization is running too slow.
520
556
if self .args .targetFps == 0 : break
521
557
522
558
elif output ["type" ] == "slam" :
523
- mapperOutput = output ["mapperOutput" ]
524
- if wasTracking : # Don't render if not tracking. Messes up this visualization easily
525
- self .map .onMappingOutput (mapperOutput )
526
- if mapperOutput .finalMap :
527
- if self .args .keepOpenAfterFinalMap :
528
- self .showCameraFrustum = False
529
- self .showCameraModel = False
530
- if self .args .targetFps == 0 : self .args .targetFps = 30 # No vio outputs -> set 30fps mode instead
531
- if self .cameraSmooth : self .cameraSmooth .reset () # Stop camera moving automatically
532
- vioOutput = prevVioOutput
533
- else :
534
- self .shouldQuit = True
559
+ processMapperOutput (output )
560
+
535
561
else :
536
562
print ("Unknown output type: {}" .format (output ["type" ]))
537
563
0 commit comments