My favorites | Sign in
Project Home Downloads Wiki Issues Source
Checkout   Browse   Changes    
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
import pygame
from pygame.locals import *
import numpy
import exceptions

import logging
verbose = True
# Todo replace with proper pythonic logging

logging.debug("Pygame Version: %s" % pygame.__version__)

class VideoCapturePlayer(object):
"""
A VideoCapturePlayer object is an encapsulation of
the display of a video stream.

A process can be given (as a function) that is run
on every frame between capture and display.

For example a filter function that takes and returns a
surface can be given. This player will take the webcam image,
pass it through the filter then display the result.

If the function takes significant computation time (>1second)
The VideoCapturePlayer takes 3 images between each, this flushes
the buffer, ensuring an updated picture is used in the next computation.

If a new version of pygame is installed - this class uses the pygame.camera module, otherwise
it uses opencv.
"""
#size = width,height = 640, 480
# For some reason this is the only resolution windows is accepting with my same camera...
size = width, height = 160, 120

def __init__(self, processFunction = None, forceOpenCv = False, displaySurface=None, show=True, **argd):
self.__dict__.update(**argd)
super(VideoCapturePlayer, self).__init__(**argd)

self.processFunction = processFunction
self.processRuns = 0

self.show = show

self.display = displaySurface
if self.display is None:
if show is True:
# create a display surface. standard pygame stuff
self.display = pygame.display.set_mode( self.size, 0 )
else:
pygame.display.init()
#pygame.display.set_mode((0,0),0)
self.display = pygame.surface.Surface(self.size)

if forceOpenCv:
import camera
else:
import pygame.camera as camera
camera.init()

# gets a list of available cameras.
self.clist = camera.list_cameras()
if not self.clist:
raise ValueError("Sorry, no cameras detected.")

print("Opening device %s, with video size (%s,%s)" % (self.clist[0],self.size[0],self.size[1]))

# creates the camera of the specified size and in RGB colorspace
if not forceOpenCv:
try:
self.camera = camera.Camera(self.clist[0], self.size, "RGB")
# starts the camera
self.camera.start()
except:
# Ignore that pygame camera failed - we will try opencv
forceOpenCv = True
del camera
import camera
self.clist = camera.list_cameras()
if forceOpenCv:
self.camera = camera.Camera(self.clist[0], self.size, "RGB", imageType="pygame")
self.camera.start()


self.waitForCam()

self.clock = pygame.time.Clock()
self.processClock = pygame.time.Clock()

# create a surface to capture to. for performance purposes, you want the
# bit depth to be the same as that of the display surface.
self.snapshot = pygame.surface.Surface(self.size, 0, self.display)

def get_and_flip(self):
"""We will take a snapshot, do some arbitrary process (eg in numpy/scipy)
then display it.
"""
# capture an image
self.snapshot = self.camera.get_image(self.snapshot)#.convert()
#self.snapshot = self.camera.get_image(self.snapshot) # if not use this line

if self.processFunction:
self.processClock.tick()
if self.processRuns > 5 and self.processClock.get_fps() < 2:
# The function is really slow so take a few frames.
if verbose:
print "Running your resource intensive process at %f fps" % self.processClock.get_fps()
# flush the camera buffer to get a new image...
# we have the time since the process is slow...
for i in range(5):
self.waitForCam()
self.snapshot = self.camera.get_image(self.snapshot)#.convert()
else:
self.waitForCam()
self.snapshot = self.camera.get_image(self.snapshot)
#try:
res = self.processFunction(self.snapshot)
if isinstance(res,pygame.Surface): self.snapshot = res
self.processRuns += 1

#except Exception, e:
# print e
# raise exceptions.RuntimeError("error while running the process function")
if self.show is not False:
# blit it to the display surface. simple!
self.display.blit(self.snapshot, (0,0))
pygame.display.flip()

def waitForCam(self):
# Wait until camera is ready to take image
# The windows pygame camera class doesn't seem to have this...
if hasattr(self.camera, "query_image"):
while not self.camera.query_image():
pass

def main(self):
if verbose:
print "Video Capture & Display Started... press Escape to quit"
going = True
fpslist = []
while going:
events = pygame.event.get()
for e in events:
if e.type == QUIT or (e.type == KEYDOWN and e.key == K_ESCAPE):
going = False

# if you don't want to tie the framerate to the camera, you can check and
# see if the camera has an image ready. note that while this works
# on most cameras, some will never return true.
# note seems to work on my camera at hitlab - Brian
if not hasattr(self.camera, "query_image") or self.camera.query_image():
self.get_and_flip()
self.clock.tick(60)
fpslist.append(self.clock.get_fps())
if verbose:
print "fps: ",fpslist[-1]
print "Video Capture & Display complete."
print "Average Frames Per Second "
avg = numpy.average(fpslist)
print avg
if self.processFunction:
print "Process ran at %f fps" % self.processClock.get_fps()

if __name__ == "__main__":
vcp = VideoCapturePlayer(processFunction=None,forceOpenCv=False)
vcp.main()
pygame.quit()

Change log

r95 by hardbyte on Oct 17, 2009   Diff
Updated the helloOpenCV code to work
without error.
Go to: 
Project members, sign in to write a code review

Older revisions

r39 by hardbyte on Aug 12, 2009   Diff
Minor mod to work with VidCap on
windows.
r36 by hardbyte on Aug 11, 2009   Diff
Adding a branch for porting to windows
r23 by hardbyte on Jul 28, 2009   Diff
Remove temp files
All revisions of this file

File info

Size: 6586 bytes, 166 lines
Powered by Google Project Hosting