Skip to content

Commit

Permalink
[WIP] Huge camera refactory
Browse files Browse the repository at this point in the history
  • Loading branch information
Dad0u committed Jan 25, 2017
1 parent dcc875a commit a72afa1
Show file tree
Hide file tree
Showing 14 changed files with 531 additions and 326 deletions.
25 changes: 22 additions & 3 deletions Examples/displayer.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,13 +6,32 @@
"""
Very simple program that displays the output of a camera
"""
class Print_val(crappy.links.Condition):
def evaluate(self,data):
print("GOT:",type(data))
try:
print("shape:",data.shape)
except AttributeError:
pass
return data

if __name__ == "__main__":
#camera = crappy.blocks.StreamerCamera("Ximea", numdevice=0, freq=20, save=False,save_directory="CHANGEME",xoffset=0, yoffset=0, width=2048, height=2048)
#camera = crappy.blocks.StreamerCamera(camera="Ximea", freq=20, save=False)
#camera = crappy.blocks.StreamerCamera(camera="Ximea", save=False, show_fps=True)
#camera = crappy.blocks.FakeCamera(512,512)
camera = crappy.blocks.StreamerCamera("Webcam", save=False, save_directory='CHANGEME')
cam_list = crappy.sensor._meta.MetaCam.classes.keys()
cam_list.remove("MasterCam")
#camera = crappy.blocks.StreamerCamera(camera="Fake_camera")
for i,c in enumerate(cam_list):
print i,c
r = int(raw_input("What cam do you want to use ?> "))
cam = cam_list[r]
camera = crappy.blocks.StreamerCamera(camera=cam)

disp = crappy.blocks.CameraDisplayer(framerate=None)
#disp = crappy.blocks.Sink()

crappy.links.Link(camera,disp)
crappy.link(camera,disp)
#crappy.links.Link(camera,disp,condition=Print_val())

crappy.start()
139 changes: 58 additions & 81 deletions crappy/blocks/_streamerCamera.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
# @author V1ctor Couty, Robin Siemiatkowski
# @version 0.2
# @date 10/01/2017
from __future__ import print_function

from _masterblock import MasterBlock
import os
Expand All @@ -27,61 +28,45 @@ class StreamerCamera(MasterBlock):
def __init__(self,**kwargs):
"""
This block fetch images from a camera object, can save and/or transmit them to another block.
No need to create the technical, this block will take care of it.
It can be triggered by a Link or internally
by defining the frequency.
It can be triggered by an other block, internally,
or run as fast as possible
Args:
camera : {"Ximea","Jai"}
See sensor.cameraSensor documentation.
kwargs:
camera : {"Ximea","Jai","Webcam",...}
See crappy.sensor._meta.MasterCam.classes for a full list
numdevice : int, default = 0
If you have several camera plugged, choose the right one.
freq : float or int or None, default=None
Wanted acquisition frequency. Cannot exceed acquisition device capability.
max_fps : float or int or None, default=None
Wanted acquisition frequency.
Cannot exceed acquisition device capability.
If None, will go as fast as possible.
save : boolean, default =False
Set to True if you want to save images.
save_directory : directory, default = "./images/"
directory to the saving folder. If inexistant, will be created.
It is not named fps to avoid interfering with cameras with embedded
framerate settings
save_directory : directory, default = None
directory to save the images. If inexistant, will be created.
If None, will not save the images
label : string, default="cycle"
label of the input data you want to save in the name of the saved image, in
case of external trigger.
xoffset: int, default = 0
Offset on the x axis.
yoffset: int, default = 0
Offset on the y axis.
width: int, default = 2048
Width of the image.
height: int, default = 2048
Height of the image.
If using external trigger, the name of the saved images will
include the data from this label. (Useful to keep track of the
differents stages of an experiment).
See below for default values
"""
MasterBlock.__init__(self)
for arg,default in [("camera","ximea"),
("numdevice",0),
("freq",None),
("save",False),
("save_directory","./images/"),
("max_fps",None),
("save_directory",None),
("label","cycle"),
("xoffset",0),
("yoffset",0),
("width",2048),
("height",2048),
("show_fps",False)]:
setattr(self,arg,kwargs.get(arg,default))
self.camera_name = self.camera

if self.save and not os.path.exists(self.save_directory):
os.makedirs(self.save_directory)

def prepare(self):
if self.save_directory and not os.path.exists(self.save_directory):
os.makedirs(self.save_directory)
self.camera = tc(self.camera_name, self.numdevice)
for attr in ['gain','exposure','width','height']:
setattr(self,attr,getattr(self.camera,attr))
self.xoffset = self.camera.x_offset
self.yoffset = self.camera.y_offset
self.camera.sensor.new(exposure=self.exposure, width=self.width,
height=self.height, xoffset=self.xoffset,
yoffset=self.yoffset, gain=self.gain)
self.trigger = "internal" if len(self.inputs) == 0 else "external"

def main(self):
Expand All @@ -90,46 +75,38 @@ def main(self):
data = {}
last_index = 0
loops = 0
try:
while True:
if self.show_fps and timer - fps_timer > 2:
sys.stdout.write("\r[StreamerCamera] FPS: %2.2f" % (
(loops - last_index) / (timer - fps_timer)))
sys.stdout.flush()
fps_timer = timer
last_index = loops
if self.trigger == "internal":
if self.freq is not None:
while time.time() - timer < 1. / self.freq:
pass
timer = time.time()
img = self.camera.sensor.get_image()
elif self.trigger == "external":
data = self.inputs[0].recv() # wait for a signal
if data is None:
continue
img = self.camera.sensor.get_image()
t = time.time() - self.t0
else:
print "[streamCamera] What kind of trigger si that ?", self.trigger
raise NotImplementedError
if self.save:
image = sitk.GetImageFromArray(img)
try:
cycle = data[self.label] # If we received a data to add in the name
sitk.WriteImage(image,
self.save_directory + "img_%.6d_cycle%09.1f_%.5f.tiff" % (
loops, cycle, time.time() - self.t0))
except KeyError: # If we did not
sitk.WriteImage(image,
self.save_directory + "img_%.6d_%.5f.tiff" % (
loops, time.time() - self.t0))
loops += 1
self.send(img)
except KeyboardInterrupt:
self.camera.sensor.close()
raise
except Exception as e:
print "Exception in streamerCamera : ", e
self.camera.sensor.close()
raise
while True:
if self.show_fps and timer - fps_timer > 2:
sys.stdout.write("\r[StreamerCamera] FPS: %2.2f" % (
(loops - last_index) / (timer - fps_timer)))
sys.stdout.flush()
fps_timer = timer
last_index = loops
if self.trigger == "internal":
if self.max_fps is not None:
while time.time() - timer < 1. / self.max_fps:
pass
timer = time.time()
img = self.camera.sensor.get_image()
elif self.trigger == "external":
data = self.inputs[0].recv() # wait for a signal
if data is None:
continue
img = self.camera.sensor.get_image()
t = time.time() - self.t0
if self.save_directory:
image = sitk.GetImageFromArray(img)
try:
cycle = data[self.label] # If we received a data to add in the name
sitk.WriteImage(image,
self.save_directory + "img_%.6d_cycle%09.1f_%.5f.tiff" % (
loops, cycle, time.time() - self.t0))
except KeyError: # If we did not
sitk.WriteImage(image,
self.save_directory + "img_%.6d_%.5f.tiff" % (
loops, time.time() - self.t0))
loops += 1
self.send(img)

def __repr__(self):
return "Streamer Camera (%s)"%self.camera_name
9 changes: 5 additions & 4 deletions crappy/sensor/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@
## @file __init__.py
# @brief Import classes to put them in the current namespace.
#
# @author Robin Siemiatkowski
# @author Robin Siemiatkowski, Victor Couty
# @version 0.1
# @date 21/06/2016

Expand All @@ -27,15 +27,16 @@
from _variateurTriboSensor import VariateurTriboSensor
from _lal300Sensor import Lal300Sensor, SensorLal300
from _PISensor import PISensor
from _webcamSensor import Webcam

#Cameras
try:
import ximeaModule as ximeaModule
from _ximeaSensor import Ximea
except Exception as e:
import_error(e.message)

from _fakeCameraSensor import FakeCameraSensor as Dummy
from _webcamSensor import Webcam
from _fakeCameraSensor import Fake_camera
from _ximeaCV import XimeaCV

if _platform.system() == "Linux":
try:
Expand Down
Loading

0 comments on commit a72afa1

Please sign in to comment.