PrintMgr.py 3.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137
  1. '''
  2. PrintMgr: functions for easy, consistent status printing to the screen with
  3. ANSI colors.
  4. PrintMgr is intended to print neatly-formatted status blocks to the screen,
  5. which are periodically updated (e.g. current fit parameters during a fit).
  6. pnew : start a new status block
  7. pstage : start a new status block with a nice header
  8. this is a decorator, and the decorated function is
  9. expected to do its own printing.
  10. pini / pdot / pend : new dotline / print dot / end dotline
  11. pstr : new status string
  12. prst : reset to beginning of block
  13. '''
  14. import sys, time
  15. #############
  16. _verbose = True
  17. _Ngap = 32 # Number of dots per line
  18. _Ndot = 0 # Number of calls to _pdot
  19. _Nline = 0 # number of lines (of dots) that have been printed
  20. _Nint = 1 # print a dot every Nint calls
  21. _Tloc = 54 # Column to print times
  22. _Ti = time.time() # Starting time.
  23. _str_bl = "\x1b[2K\r\x1b[1m%20s\x1b[0m: " # Emph (bold)
  24. str_el = "\x1b[2K\r\x1b[33;1m%20s\x1b[0m: " # Emph (yellow)
  25. str_nl = "\x1b[2K\r%20s: " # Normal (white)
  26. _str_sta = "\x1b[2K\r\x1b[1m[\x1b[32m %s \x1b[39m]\x1b[0m" # Block header
  27. _str_set = "\r\x1b[%dC" # Set cursor to loc
  28. #\x1b[2K\r == reset line
  29. def _str_ar(pfx, ar, pfmt, afmt, plen):
  30. str = pfmt % pfx
  31. for n, a in enumerate(ar):
  32. if n > 0 and n % 4 == 0:
  33. str += "\n" + " "*plen
  34. t = afmt % 0
  35. if a == 0:
  36. str += " "*(len(t)-2) + "- "
  37. elif not np.isfinite(a):
  38. u = "%f " % a
  39. str += " "*(len(t)-len(u)) + u
  40. else:
  41. str += afmt % a
  42. return str
  43. def pnew(str):
  44. global _Nline
  45. if not _verbose: return
  46. print str
  47. _Nline = 0
  48. def pini(str, interval = 1):
  49. global _Ndot, _Nline, _Nint, _Ti
  50. if not _verbose: return
  51. str = _str_bl % str
  52. print str,
  53. sys.stdout.flush()
  54. _Ndot = 0
  55. _Nint = interval
  56. _Ti = time.time()
  57. def pdot(x=None, pchar="."):
  58. global _Ndot, _Nline
  59. if not _verbose: return
  60. _Ndot += 1
  61. q, r = divmod(_Ndot, _Nint)
  62. if r != 0:
  63. return x
  64. sys.stdout.write(pchar)
  65. sys.stdout.flush()
  66. if q > 0 and q % _Ngap == 0:
  67. print " (%.2fs)" % (time.time() - _Ti)
  68. print " " * 22,
  69. _Nline += 1
  70. return x
  71. def pstr(str):
  72. global _Ndot, _Nline
  73. if not _verbose: return
  74. print str
  75. _Nline += len(str.split("\n"))
  76. def pend(str=""):
  77. global _Nline
  78. if not _verbose: return
  79. q, r = divmod(_Ndot, _Nint)
  80. loc = _Tloc - len(str) - 1
  81. if q > 0 and q % _Ngap == 0:
  82. return
  83. print _str_set % loc,
  84. print "%s (%.2fs)" % (str, time.time() - _Ti)
  85. _Nline += 1
  86. sys.stdout.flush()
  87. def prst():
  88. global _Nline
  89. if not _verbose: return
  90. if _Nline == 0: return
  91. print '\x1b[%dF' % _Nline,
  92. _Nline = 0
  93. def pstage(str):
  94. def decorator(func):
  95. def wrap(*arg, **kw):
  96. verbose = kw.get("verbose", True)
  97. if verbose:
  98. t1 = time.time()
  99. pnew(_str_sta % str)
  100. r = func(*arg, **kw)
  101. if verbose:
  102. t2 = time.time()
  103. print "Total time: %.2fs" % (t2 - t1)
  104. return r
  105. return wrap
  106. return decorator