chiark / gitweb /
1f3099838694fa7168e02533cb96e9a980a06dc7
[cura.git] / Cura / gui / webcam.py
1 import os, glob, subprocess, platform\r
2 import wx\r
3 \r
4 try:\r
5         #Try to find the OpenCV library for video capture.\r
6         from opencv import cv\r
7         from opencv import highgui\r
8 except:\r
9         cv = None\r
10 \r
11 try:\r
12         #Use the vidcap library directly from the VideoCapture package. (Windows only)\r
13         #       http://videocapture.sourceforge.net/\r
14         # We're using the binary interface, not the python interface, so we don't depend on PIL\r
15         import vidcap as win32vidcap\r
16 except:\r
17         win32vidcap = None\r
18 \r
19 def hasWebcamSupport():\r
20         if cv == None and win32vidcap == None:\r
21                 return False\r
22         if not os.path.exists(getFFMPEGpath()):\r
23                 return False\r
24         return True\r
25 \r
26 def getFFMPEGpath():\r
27         if platform.system() == "Windows":\r
28                 return os.path.normpath(os.path.join(os.path.split(__file__)[0], "../ffmpeg.exe"))\r
29         elif os.path.exists('/usr/bin/ffmpeg'):\r
30                 return '/usr/bin/ffmpeg'\r
31         return os.path.normpath(os.path.join(os.path.split(__file__)[0], "../ffmpeg"))\r
32 \r
33 class webcam(object):\r
34         def __init__(self):\r
35                 self._cam = None\r
36                 if cv != None:\r
37                         self._cam = highgui.cvCreateCameraCapture(-1)\r
38                 elif win32vidcap != None:\r
39                         try:\r
40                                 self._cam = win32vidcap.new_Dev(0, False)\r
41                         except:\r
42                                 pass\r
43                 \r
44                 self._doTimelaps = False\r
45                 self._bitmap = None\r
46         \r
47         def hasCamera(self):\r
48                 return self._cam != None\r
49         \r
50         def propertyPages(self):\r
51                 if self._cam == None:\r
52                         return []\r
53                 if cv != None:\r
54                         #TODO Make an OpenCV property page\r
55                         return []\r
56                 elif win32vidcap != None:\r
57                         return ['Image properties', 'Format properties']\r
58 \r
59         def openPropertyPage(self, pageType = 0):\r
60                 if self._cam == None:\r
61                         return\r
62                 if cv != None:\r
63                         pass\r
64                 elif win32vidcap != None:\r
65                         if pageType == 0:\r
66                                 self._cam.displaycapturefilterproperties()\r
67                         else:\r
68                                 del self._cam\r
69                                 self._cam = None\r
70                                 tmp = win32vidcap.new_Dev(0, False)\r
71                                 tmp.displaycapturepinproperties()\r
72                                 self._cam = tmp\r
73         \r
74         def takeNewImage(self):\r
75                 if self._cam == None:\r
76                         return\r
77                 if cv != None:\r
78                         frame = cv.QueryFrame(self._cam)\r
79                         cv.CvtColor(frame, frame, cv.CV_BGR2RGB)\r
80                         self._bitmap = wx.BitmapFromBuffer(frame.width, frame.height, frame.imageData)\r
81                 elif win32vidcap != None:\r
82                         buffer, width, height = self._cam.getbuffer()\r
83                         wxImage = wx.EmptyImage(width, height)\r
84                         wxImage.SetData(buffer[::-1])\r
85                         if self._bitmap != None:\r
86                                 del self._bitmap\r
87                         self._bitmap = wxImage.ConvertToBitmap()\r
88                         del wxImage\r
89                         del buffer\r
90 \r
91                 if self._doTimelaps:\r
92                         filename = os.path.normpath(os.path.join(os.path.split(__file__)[0], "../__tmp_snap", "__tmp_snap_%04d.jpg" % (self._snapshotCount)))\r
93                         self._snapshotCount += 1\r
94                         self._bitmap.SaveFile(filename, wx.BITMAP_TYPE_JPEG)\r
95 \r
96                 return self._bitmap\r
97         \r
98         def getLastImage(self):\r
99                 return self._bitmap\r
100         \r
101         def startTimelaps(self, filename):\r
102                 if self._cam == None:\r
103                         return\r
104                 self._cleanTempDir()\r
105                 self._timelapsFilename = filename\r
106                 self._snapshotCount = 0\r
107                 self._doTimelaps = True\r
108                 print "startTimelaps"\r
109         \r
110         def endTimelaps(self):\r
111                 if self._doTimelaps:\r
112                         ffmpeg = getFFMPEGpath()\r
113                         basePath = os.path.normpath(os.path.join(os.path.split(__file__)[0], "../__tmp_snap", "__tmp_snap_%04d.jpg"))\r
114                         subprocess.call([ffmpeg, '-r', '12.5', '-i', basePath, '-vcodec', 'mpeg2video', '-pix_fmt', 'yuv420p', '-r', '25', '-y', '-b:v', '1500k', '-f', 'vob', self._timelapsFilename])\r
115                 self._doTimelaps = False\r
116         \r
117         def _cleanTempDir(self):\r
118                 basePath = os.path.normpath(os.path.join(os.path.split(__file__)[0], "../__tmp_snap"))\r
119                 try:\r
120                         os.makedirs(basePath)\r
121                 except:\r
122                         pass\r
123                 for filename in glob.iglob(basePath + "/*.jpg"):\r
124                         os.remove(filename)\r