cam.py 3.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145
  1. #!/usr/bin/python3
  2. import sys
  3. import gi
  4. gi.require_version('Gst', '1.0')
  5. gi.require_version('GstNet', '1.0')
  6. from gi.repository import Gst, GstNet
  7. import time
  8. import threading
  9. import os
  10. import stat
  11. WIDTH = 1280
  12. HEIGHT = 720
  13. WIDTH = 1024
  14. HEIGHT = 576
  15. SCREEN_WIDTH = 800
  16. SCREEN_HEIGHT = 600
  17. SCREEN_WIDTH = 1280
  18. SCREEN_HEIGHT = 720
  19. SCREEN_WIDTH = 1920
  20. SCREEN_HEIGHT = 1080
  21. def bus_call(bus, msg, *args):
  22. if msg.type == Gst.MessageType.EOS:
  23. print("End-of-stream")
  24. loop.quit()
  25. return
  26. elif msg.type == Gst.MessageType.ERROR:
  27. print("GST ERROR", msg.parse_error())
  28. loop.quit()
  29. return
  30. return True
  31. zoom = 1
  32. def quit():
  33. pipeline.send_event(Gst.Event.new_eos())
  34. def set_preview(val):
  35. if val == 0:
  36. videosrc.set_property("preview-x", SCREEN_WIDTH)
  37. videosrc.set_property("preview-y", SCREEN_HEIGHT)
  38. else:
  39. videosrc.set_property("preview-x", 0)
  40. videosrc.set_property("preview-y", 0)
  41. def set_zoom(target):
  42. global zoom
  43. if target < zoom:
  44. direction = -1
  45. else:
  46. direction = 1
  47. target=min(target, 1)
  48. target=max(target, 0.40)
  49. while abs(target-zoom) > 0.01: #fuck IEEE floats
  50. zoom = zoom + direction*0.015
  51. zoom = min(zoom, 1)
  52. zoom = max(zoom, 0.4)
  53. videosrc.set_property("roi-x", (1-zoom)/2)
  54. videosrc.set_property("roi-y", (1-zoom)/2)
  55. videosrc.set_property("roi-w", zoom)
  56. videosrc.set_property("roi-h", zoom)
  57. time.sleep(0.03)
  58. def control():
  59. FIFO="/tmp/picamfifo"
  60. if os.path.exists(FIFO):
  61. if stat.S_ISFIFO(os.stat(FIFO).st_mode):
  62. pass
  63. else:
  64. os.remove(FIFO)
  65. os.mkfifo(FIFO)
  66. else:
  67. os.mkfifo(FIFO)
  68. while True:
  69. with open(FIFO) as fifo:
  70. line=fifo.read().strip()
  71. print("Got: ", line)
  72. if "=" not in line:
  73. print("Invalid line.")
  74. continue
  75. key = line.split("=")[0]
  76. val = line.split("=")[1]
  77. if key == "preview":
  78. set_preview(int(val))
  79. if key == "zoom":
  80. set_zoom(float(val))
  81. if __name__ == "__main__":
  82. if 'LD_LIBRARY_PATH' not in os.environ:
  83. os.environ['LD_LIBRARY_PATH'] = '/usr/local/lib'
  84. os.execv(sys.argv[0], sys.argv)
  85. # initialization
  86. Gst.init(None)
  87. videocodec = "video/x-h264, width=%d, height=%d, framerate=25/1, profile=high ! h264parse" % (WIDTH, HEIGHT)
  88. p = "rpicamsrc sensor-mode=4 bitrate=0 quantisation-parameter=12 do-timestamp=true keyframe-interval=5 name=src ! "+videocodec+" ! matroskamux streamable=true ! tcpserversink host=0.0.0.0 port=5000 sync-method=next-keyframe blocksize=16384"
  89. print(p)
  90. #
  91. pipeline = Gst.parse_launch (p)
  92. if pipeline == None:
  93. print ("Failed to create pipeline")
  94. sys.exit(0)
  95. clock = GstNet.NetClientClock.new('CamVoctoClock', '192.168.2.123', 9998, 0)
  96. #print("Waiting for clock sync")
  97. #clock.wait_for_sync(Gst.CLOCK_TIME_NONE)
  98. #clock.do_wait(Gst.CLOCK_TIME_NONE)
  99. #print("Clock synced")
  100. pipeline.set_start_time(Gst.CLOCK_TIME_NONE)
  101. if clock is not None:
  102. pass
  103. #pipeline.use_clock(clock)
  104. videosrc = pipeline.get_by_name ("src")
  105. videosrc.set_property("preview", 1)
  106. videosrc.set_property("preview-w", SCREEN_WIDTH)
  107. videosrc.set_property("preview-h", SCREEN_HEIGHT)
  108. videosrc.set_property("fullscreen", False)
  109. #videosrc.set_property("bitrate", 14000000)
  110. # videosrc.set_property("bitrate", 25000000)
  111. videosrc.set_property("rotation", 180)
  112. set_preview(0)
  113. # run
  114. pipeline.set_state(Gst.State.PLAYING)
  115. t = threading.Thread(target=control, daemon=True)
  116. t.start()
  117. while True:
  118. time.sleep(10000)
  119. # cleanup
  120. pipeline.set_state(Gst.State.NULL)