Source code for Zoom
# CellTracking.py
# By MW, Jun 2013
# GPLv3+
#
# Class managing the zoom controls of a player.
import gtk, logging, cv2, numpy
[docs]class Zoom_state :
def __init__(self, state) :
"""A class managing zoom parameters"""
self.player_state = state.get_subclass('player')
# Thumbnail parameters (need to be duplicated from player to handle update)
self.current_channel = self.player_state.current_channel
self.current_frame = self.player_state.current_frame_index
self.current_window = self.player_state.current_window
self.current_pos = self.player_state.current_pos
self.current_zoom = self.player_state.current_zoom
self.zoom_initiated = False
self.zoom_img = None
self.zoom_factor = 100./self.player_state.get_current_frame().shape[0]
[docs] def set_zoom_img(self, img) :
self.zoom_img = img
[docs] def im2disp(self, tup) :
"""Function that convert a tuple (x,y) (or another format) in the coordinates of the display"""
return numpy.array(tup)*self.current_zoom
[docs] def disp2im(self, tup) :
"""Function that convert a tuple (x,y) (or another format) in the coordinates of the image (coming from the display)"""
return numpy.array(tup)/self.current_zoom
[docs]class Zoom :
def __init__(self, player) :
self.player = player
self.player_state = self.player.state.get_subclass("player")
self.zoom_state = Zoom_state(player.state)
self.zoom_state.set_zoom_img(self.get_zoom_img()[0])
self.player.state.add_subclass('zoom', self.zoom_state)
# Thumbnail parameters
#self.current_channel = player_state.current_channel
#self.current_frame = player_state.current_frame_index
#self.current_window = player_state.current_window
#self.current_pos = player_state.current_pos
#self.current_zoom = player_state.current_zoom
#self.zoom_initiated = False
#self.zoom_img = self.get_zoom_img()[0]
#self.zoom_factor = 100./player_state.get_current_frame().shape[0]
[docs] def get_zoom(self) :
"""Function that return an object to be inserted in the display window"""
# Set image
self.image = gtk.Image()
pixbuf = gtk.gdk.pixbuf_new_from_array(self.zoom_state.zoom_img, gtk.gdk.COLORSPACE_RGB, 8)
self.image.clear()
self.image.set_from_pixbuf(pixbuf)
# Create Event box
self.eventbox = gtk.EventBox()
self.eventbox.add(self.image)
# Set event (detect click)
self.eventbox.connect("button_press_event", self.clicked_zoom)
return self.eventbox
[docs] def get_zoom_img(self) :
"""Function that return a zoom thumbnail in OpenCV format"""
# See if regenerating is needed
player_state = self.player.state.get_subclass("player")
zs = self.zoom_state
if (zs.current_channel == player_state.current_channel) and \
(zs.current_frame == player_state.current_frame_index) and \
(zs.current_window == player_state.current_window) and \
(zs.current_pos == player_state.current_pos) and \
(zs.current_zoom == player_state.current_zoom) and \
zs.zoom_initiated :
return (zs.zoom_img, False)
else :
logging.debug("Generating new zoom image.")
# Updating parameters
zs.current_channel = player_state.current_channel
zs.current_frame = player_state.current_frame_index
zs.current_window = player_state.current_window
zs.current_pos = player_state.current_pos
zs.current_zoom = player_state.current_zoom
zs.zoom_initiated = True
# Getting image and resizing
f = player_state.get_current_frame()
size = f.shape
f_small = cv2.resize(f, dsize=(100, int(100./size[0]*size[1])))
zs.zoom_img = f_small
zs.zoom_img.dtype = numpy.uint8
# drawing on image
s = 100./size[0] # Scale factor
zs.zoom_factor = float(s)
z = player_state.current_zoom
top_left = (int(zs.current_pos[0]*s/z),
int(zs.current_pos[1]*s/z))
bottom_right = (int((zs.current_pos[0]+zs.current_window[0])*s/z),
int((zs.current_pos[1]+zs.current_window[1])*s/z))
cv2.rectangle(f_small, top_left, bottom_right, (255, 255, 0))
return (zs.zoom_img, True)
[docs] def update_zoom(self) :
"""Function that recompute the zooming window to update the display"""
img = self.get_zoom_img()
if img[1] :
pixbuf = gtk.gdk.pixbuf_new_from_array(self.zoom_state.zoom_img, gtk.gdk.COLORSPACE_RGB, 8)
self.image.clear()
self.image.set_from_pixbuf(pixbuf)
[docs] def clicked_zoom(self, w, event) :
"""Event called when the image representing the zoom display is clicked"""
logging.debug("click detected in zoom at: (%s, %s)", str(event.x), str(event.y))
zs = self.zoom_state
player = self.player.state.get_subclass('player')
self.player.viewer.set_scroll(
int(event.x/zs.zoom_factor*zs.current_zoom - player.current_window[0]/2.),
int(event.y/zs.zoom_factor*zs.current_zoom - player.current_window[1]/2.))