Exemplo n.º 1
0
    def annotateFrame(self, frame, color='white'):
        '''
        Renders optical flow information to the frame.
        
        @param frame: the frame that will be annotated
        @type frame: pv.Image
        @keyword type:
        @ktype type: "TRACKING" 
        
        '''
        w, h = self.tile_size
        rect = pv.Rect(0, 0, w, h)
        affine = pv.AffineFromRect(rect, frame.size)
        for pt in affine.transformPoints(self.tracks[:self.n]):
            frame.annotatePoint(pt, color=color)

        for pt in affine.transformPoints(self.tracks[self.n:]):
            frame.annotatePoint(pt, color='red')

        for pt in affine.transformPoints(self.bad_points):
            frame.annotatePoint(pt, color='gray')

        if self.homography != None:
            matrix = pv.OpenCVToNumpy(self.homography)
            perspective = pv.PerspectiveTransform(matrix, frame.size)

            for pt in self.tracks[:self.n]:
                # Transform the point multiple times to amplify the track
                # for visualization
                old = perspective.invertPoint(pt)
                old = perspective.invertPoint(old)
                old = perspective.invertPoint(old)
                frame.annotateLine(pt, old, color=color)
Exemplo n.º 2
0
def onMouseEvent(event, x, y, flags, param):
    global startPointx
    global startPointy
    global flagDraw
    # print event
    if (event == 1):
        print "Position is: %d,%d", x, y
        startPointx = x
        startPointy = y
        flagDraw = True
    if (event == 0):
        if (flagDraw == True):
            image = cv.CloneImage(src)
            cv.Rectangle(image, (startPointx, startPointy), (x, y),
                         (255, 0, 0), 3)
            cv.ShowImage('window', image)

            print "EndPosition is: %d,%d", x, y
    if (event == 4):
        if (flagDraw == True):
            image = cv.CloneImage(src)
            cv.Rectangle(image, (startPointx, startPointy), (x, y),
                         (255, 0, 0), 3)
            cv.ShowImage('window', image)
            flagDraw = False
            global TAZ_RECT
            TAZ_RECT = pv.Rect(startPointx, startPointy, x - startPointx,
                               y - startPointy)
Exemplo n.º 3
0
    def _computeBGDiff(self):
        self._flow.update( self._imageBuffer.getLast() )
        
        n = len(self._imageBuffer)        
        prev_im = self._imageBuffer[0]
        forward = None
        for i in range(0,n/2):
            if forward == None:
                forward = self._imageBuffer[i].to_next
            else:
                forward = forward * self._imageBuffer[i].to_next
                
        w,h = size = prev_im.size
        mask = cv.CreateImage(size,cv.IPL_DEPTH_8U,1)
        cv.Set(mask,0)
        interior = cv.GetSubRect(mask, pv.Rect(2,2,w-4,h-4).asOpenCV()) 
        cv.Set(interior,255)
        mask = pv.Image(mask)

        prev_im = forward(prev_im)
        prev_mask = forward(mask)
        

        next_im = self._imageBuffer[n-1]
        back = None
        for i in range(n-1,n/2,-1):
            if back == None:
                back = self._imageBuffer[i].to_prev
            else:
                back = back * self._imageBuffer[i].to_prev
        
        next_im = back(next_im)
        next_mask = back(mask)
        
        curr_im = self._imageBuffer[n/2]

                
        prevImg = prev_im.asMatrix2D()
        curImg  = curr_im.asMatrix2D()
        nextImg = next_im.asMatrix2D()
        prevMask = prev_mask.asMatrix2D()
        nextMask = next_mask.asMatrix2D()

        # Compute transformed images
        delta1 = sp.absolute(curImg - prevImg)   #frame diff 1
        delta2 = sp.absolute(nextImg - curImg)   #frame diff 2
        
        delta1 = sp.minimum(delta1,prevMask)
        delta2 = sp.minimum(delta2,nextMask)
        
        #use element-wise minimum of the two difference images, which is what
        # gets compared to threshold to yield foreground mask
        return sp.minimum(delta1, delta2)
Exemplo n.º 4
0
    def _detectPeople(self, img):
        cvim = img.asOpenCV(
        )  #convert to OpenCV format before using OpenCV functions
        rect_list = []
        try:
            found = list(cv.HOGDetectMultiScale(cvim, cv.CreateMemStorage(0)))
            rect_list = [pv.Rect(x, y, w, h) for ((x, y), (w, h)) in found
                         ]  #python list comprehension
        except:
            #cv.HOGDetectMultiScale can throw exceptions, so return empty list
            return []

        return rect_list
Exemplo n.º 5
0
    def test_from_rect(self):

        transform = pv.AffineFromRect(pv.Rect(100, 100, 300, 300), (100, 100))
        _ = transform.transformImage(self.test_image)
        #im_a.show()

        pt = transform.transformPoint(pv.Point(320, 240))
        self.assertAlmostEqual(pt.X(), 73.333333333333329)
        self.assertAlmostEqual(pt.Y(), 46.666666666666671)

        pt = transform.invertPoint(pv.Point(50., 50.))
        self.assertAlmostEqual(pt.X(), 250.0)
        self.assertAlmostEqual(pt.Y(), 250.0)
Exemplo n.º 6
0
    def _checkClickRegion(self, x, y):
        """
        internal method to determine the clicked region of the montage.
        @return: -1 for decrement region, 1 for increment region, and 0 otherwise.
        If a select handler function was defined (via setSelectHandler), then
        this function will be called when the user clicks within the region
        of one of the tiles of the montage. Signature of selectHandler function
        is f(img, imgNum, dict). As of now, the only key/value pair passed
        into the dict is "imgLabel":<label>.
        """
        if self._by_row:
            #scroll up/down to expose next/prev row
            decr_rect = pv.Rect(0, 0, self._size[0], self._ypad)
            incr_rect = pv.Rect(0, self._size[1] - self._ypad, self._size[0], self._ypad)
        else:
            #scroll left/right to expose next/prev col
            decr_rect = pv.Rect(0, 0, self._xpad, self._size[1])
            incr_rect = pv.Rect(self._size[0] - self._xpad, 0, self._xpad, self._size[1])

        pt = pv.Point(x, y)
        if incr_rect.containsPoint(pt):
            #print "DEBUG: Increment Region"
            return 1
        elif decr_rect.containsPoint(pt):
            #print "DEBUG: Decrement Region"
            return -1
        else:
            #print "DEBUG: Neither Region"
            for img, imgNum, rect in self._image_positions:
                if rect.containsPoint(pt):
                    if imgNum in self._selected_tiles:
                        self._selected_tiles.remove(imgNum)
                    else:
                        self._selected_tiles.append(imgNum)
                    if self._select_handler != None:
                        imgLabel = self._labels[imgNum] if type(self._labels) == list else str(imgNum)
                        self._select_handler(img, imgNum, {"imgLabel":imgLabel})
            return 0
Exemplo n.º 7
0
    def extract(self,img,face_records):
        '''Extract a template that allows the face to be matched.'''
        # Compute the 128D vector that describes the face in img identified by
        # shape.  In general, if two face descriptor vectors have a Euclidean
        # distance between them less than 0.6 then they are from the same
        # person, otherwise they are from different people. Here we just print
        # the vector to the screen.
        
        # TODO: Make this an option
        JITTER_COUNT = 5
        
        for face_record in face_records.face_records:
            rect = pt.rect_proto2pv(face_record.detection.location)
            x,y,w,h = rect.asTuple()

            # Extract view
            rect = pv.Rect()
            cx,cy = x+0.5*w,y+0.5*h
            tmp = 1.5*max(w,h)
            cw,ch = tmp,tmp
            crop = pv.AffineFromRect(pv.CenteredRect(cx,cy,cw,ch),(256,256))
            #print (x,y,w,h,cx,cy,cw,ch,crop)
            pvim = pv.Image(img[:,:,::-1]) # convert rgb to bgr
            pvim = crop(pvim)
            view = pt.image_pv2proto(pvim)
            face_record.view.CopyFrom(view)
            
            # Extract landmarks
            l,t,r,b = [int(tmp) for tmp in [x,y,x+w,y+h]]
            d = dlib.rectangle(l,t,r,b)
            shape = self.shape_pred(img, d)
            #print('s',dir(shape))
            #print(shape.parts()[0])
            
            for i in range(len(shape.parts())):
                loc = shape.parts()[i]
                landmark = face_record.landmarks.add()
                landmark.landmark_id = "point_%02d"%i
                landmark.location.x = loc.x
                landmark.location.y = loc.y
            
            #print('fr',face_record)

            #print('shape:',face_records.face_records[0].landmarks)
            face_descriptor = self.face_rec.compute_face_descriptor(img, shape, JITTER_COUNT)
            face_descriptor = np.array(face_descriptor)
            
            vec = face_descriptor.flatten()
            face_record.template.data.CopyFrom(pt.vector_np2proto(vec))
Exemplo n.º 8
0
 def _checkClickRegion(self, x,y):
     '''
     internal method to determine the clicked region of the montage.
     @return: -1 for decrement region, 1 for increment region, and 0 otherwise
     '''
     if self._byrow:
         #scroll up/down to expose next/prev row
         decr_rect = pv.Rect(0,0, self._size[0], self._ypad)
         incr_rect = pv.Rect(0, self._size[1]-self._ypad, self._size[0], self._ypad)
     else:
         #scroll left/right to expose next/prev col
         decr_rect = pv.Rect(0,0, self._xpad, self._size[1])
         incr_rect = pv.Rect(self._size[0]-self._xpad, 0, self._xpad, self._size[1])
         
     pt = pv.Point(x,y)
     if incr_rect.containsPoint(pt):
         #print "DEBUG: Increment Region"
         return 1
     elif decr_rect.containsPoint(pt):
         #print "DEBUG: Decrement Region"
         return -1
     else:
         #print "DEBUG: Neither Region"
         return 0
Exemplo n.º 9
0
    def getBoundingRects(self):
        '''
        @return: the bounding boxes of the external contours of the foreground mask.
        @note: You must call detect() before getBoundingRects() to see updated results.
        '''
        #create a list of the top-level contours found in the contours (cv.Seq) structure
        rects = []
        if len(self._contours) < 1: return (rects)
        seq = self._contours
        while not (seq == None):
            (x, y, w, h) = cv.BoundingRect(seq)
            if (cv.ContourArea(seq) > self._minArea):
                r = pv.Rect(x, y, w, h)
                rects.append(r)
            seq = seq.h_next()

        if self._filter != None:
            rects = self._filter(rects)

        return rects
Exemplo n.º 10
0
 def crop(self, rect, size=None, interpolation=None, return_affine=False):
     '''
     Crops an image to the given rectangle. Rectangle parameters are rounded to nearest 
     integer values.  High quality resampling.  The default behavior is to use cv.GetSubRect
     to crop the image.  This returns a slice the OpenCV image so modifying the resulting
     image data will also modify the data in this image.  If a size is provide a new OpenCV
     image is created for that size and cv.Resize is used to copy the image data. If the 
     bounds of the rectangle are outside the image, an affine transform (pv.AffineFromRect)
     is used to produce the croped image to properly handle regions outside the image.
     In this case the downsampling quality may not be as good. #
     
     @param rect: a Rectangle defining the region to be cropped.
     @param size: a new size for the returned image.  If None the result is not resized.
     @param interpolation: None = Autoselect or one of CV_INTER_AREA, CV_INTER_NN, CV_INTER_LINEAR, CV_INTER_BICUBIC
     @param return_affine: If True, also return an affine transform that can be used to transform points.
     @returns: a cropped version of the image or if return affine a tuple of (image,affine)
     @rtype: pv.Image
     '''
     # Notes: pv.Rect(0,0,w,h) should return the entire image. Since pixel values
     # are indexed by zero this means that upper limits are not inclusive: x from [0,w)
     # and y from [0,h)
     x,y,w,h = rect.asTuple()
    
     x = int(np.round(x))
     y = int(np.round(y))
     w = int(np.round(w))
     h = int(np.round(h))
     
     # Check the bounds for cropping
     if size is None:
         size = (w,h)
     
     affine = pv.AffineFromRect(pv.Rect(x,y,w,h),size)
     im = affine(self)
     if return_affine:
         return im,affine
     else:
         return im
Exemplo n.º 11
0
    def _selectTrackingPoints(self, frame):
        '''
        This uses the OpenCV get good features to track to initialize a set of tracking points.
        '''
        quality = 0.01
        min_distance = 15

        w, h = self.tile_size
        tw = w // self.grid
        th = h // self.grid

        for i in range(self.grid):
            for j in range(self.grid):
                ul = pv.Point(i * tw, j * th)
                rect = pv.Rect(i * tw, j * th, tw, th)
                count = 0
                for pt in self.tracks:
                    if rect.containsPoint(pt):
                        count += 1

                if count < self.min_points:
                    gray = cv.CreateImage((tw, th), 8, 1)

                    faceim = cv.GetSubRect(frame, rect.asOpenCV())
                    cv.Resize(faceim, gray)

                    eig = cv.CreateImage((tw, th), 32, 1)
                    temp = cv.CreateImage((tw, th), 32, 1)

                    # search the good points
                    points = cv.GoodFeaturesToTrack(gray, eig, temp,
                                                    2 * self.min_points,
                                                    quality, min_distance,
                                                    None, 3, 0, 0.04)

                    for pt in points:
                        self.tracks.append(ul + pv.Point(pt))
Exemplo n.º 12
0
        
        im = pv.Image(pathname)

        scale = options.log_scale
        log_im = pv.AffineScale(scale,(int(scale*im.width),int(scale*im.height))).transformImage(im)
        
            
 
        results = processFaces(im,face_detect,locate_eyes)

        if options.rotate:
            
            rot_image = pv.Image(im.asPIL().transpose(PIL.Image.ROTATE_90))
            more_results = processFaces(rot_image,face_detect,locate_eyes)
            for face,eye1,eye2 in more_results:
                results.append([pv.Rect(im.width-face.y-face.h, face.x, face.h, face.w),
                               pv.Point(im.width-eye1.Y(),eye1.X()),
                               pv.Point(im.width-eye2.Y(),eye2.X())])

            rot_image = pv.Image(im.asPIL().transpose(PIL.Image.ROTATE_180))
            more_results = processFaces(rot_image,face_detect,locate_eyes)            
            for face,eye1,eye2 in more_results:
                results.append([pv.Rect(im.width - face.x - face.w, im.height-face.y-face.h, face.w, face.h),
                               pv.Point(im.width-eye1.X(),im.height-eye1.Y()),
                               pv.Point(im.width-eye2.X(),im.height-eye2.Y())])
                
            rot_image = pv.Image(im.asPIL().transpose(PIL.Image.ROTATE_270))
            more_results = processFaces(rot_image,face_detect,locate_eyes)
            for face,eye1,eye2 in more_results:
                results.append([pv.Rect(face.y, im.height-face.x-face.w, face.h, face.w),
                               pv.Point(eye1.Y(),im.height-eye1.X()),
Exemplo n.º 13
0
def CenteredRect(cx, cy, w, h):
    return pv.Rect(cx - 0.5 * w, cy - 0.5 * h, w, h)
Exemplo n.º 14
0
def rect_proto2pv(proto_rect):
    return pv.Rect(proto_rect.x, proto_rect.y, proto_rect.width,
                   proto_rect.height)
Exemplo n.º 15
0
Created on Sep 16, 2010

@author: bolme
'''

import pyvision as pv
from pyvision.types.Video import Video
import ocof
import os.path
import cv
import time
import copy

TAZ_FILENAME = os.path.join(ocof.__path__[0], 'test', 'data', 'capture1.mp4')
global TAZ_RECT
TAZ_RECT = pv.Rect(200, 200, 120, 120)

# print TAZ_FILENAME
video = pv.Video(TAZ_FILENAME)
webcam = pv.Webcam()

tracker = None

global startPointx
global startPointy
global flagDraw
global src
startPointx = 0
startPointy = 0
flagDraw = False
Exemplo n.º 16
0
    def visualize_detection(self, img, dets, classes=[], thresh=0.6):

        height = img.shape[0]
        width = img.shape[1]
        global colors
        global img_depth
        global trackpos
        # print dets.shape[0]
        acc_flag = False
        for i in range(dets.shape[0]):
            cls_id = int(dets[i, 0])
            # if cls_id >= 0:

            if cls_id == 14:
                score = dets[i, 1]
                if score > thresh:
                    if cls_id not in colors:
                        colors[cls_id] = (self.randomRGB(), self.randomRGB(),
                                          self.randomRGB())
                    if trackpos == 0:
                        trackpos = int(0.5 * (int(dets[i, 4] * width) +
                                              int(dets[i, 2] * width)))
                    if abs(trackpos - (int(0.5 *
                                           (int(dets[i, 4] * width) +
                                            int(dets[i, 2] * width))))) < 30:
                        xmin = int(dets[i, 2] * width)
                        ymin = int(dets[i, 3] * height)
                        xmax = int(dets[i, 4] * width)
                        ymax = int(dets[i, 5] * height)
                        img_roi = img_depth[ymin:ymax, xmin:xmax]
                        temp_height = img_roi.shape[0]
                        temp_width = img_roi.shape[1]
                        # print("high:{} width:{} ".format(height, width ))
                        # print("xmin:{} xmax:{} ymin:{} ymax:{}".format(xmin, xmax, ymin, ymax))
                        biggest = np.amin(img_roi)
                        required = (img_roi[int(0.5 * (ymax - ymin)),
                                            int(0.5 * (xmax - xmin))])
                        # global TAZ_RECT
                        trackpos = int(0.5 * (xmax + xmin))
                        acc_flag = True

                        global tracker
                        TAZ_RECT = pv.Rect(xmin, ymax, xmax - xmin,
                                           ymax - ymin)
                        uFrame = pv.Image(img.copy())
                        tracker = ocof.MOSSETrack(uFrame, TAZ_RECT)

                        global acc_pub
                        accCmd = ACCCommand()
                        accCmd.logtitudeErr = required
                        accCmd.lateralErr = trackpos
                        acc_pub.publish(accCmd)

                        cv2.rectangle(img, (xmin, ymin), (xmax, ymax),
                                      color=colors[cls_id])
                        class_name = str(cls_id)
                        if classes and len(classes) > cls_id:
                            class_name = classes[cls_id]
                        # text = '{:s} {:.2f} {:.2f}'.format(class_name, score, required)
                        text = '{:s} {:.2f}m'.format(class_name, required)
                        texSize, baseline = cv2.getTextSize(
                            text, cv2.FONT_HERSHEY_DUPLEX, 1, 1)
                        cv2.rectangle(img, (xmin, ymin - 2),
                                      (xmin + texSize[0], ymin - texSize[1]),
                                      colors[cls_id], -1)
                        cv2.putText(img, text, (xmin, ymin - 2),
                                    cv2.FONT_HERSHEY_DUPLEX, 1,
                                    self.colorInv(colors[cls_id]), 1)

        acc_enable.publish(acc_flag)
        # cv2.namedWindow("stra")
        cv2.imshow("stra", img)
Exemplo n.º 17
0
    def extract(self, img, face_records):
        '''Extract a template that allows the face to be matched.'''
        # Compute the 128D vector that describes the face in img identified by
        # shape.  In general, if two face descriptor vectors have a Euclidean
        # distance between them less than 0.6 then they are from the same
        # person, otherwise they are from different people. Here we just print
        # the vector to the screen.

        im = pv.Image(img[:, :, ::-1])

        for face_record in face_records.face_records:
            rect = pt.rect_proto2pv(face_record.detection.location)
            x, y, w, h = rect.asTuple()

            # Extract view
            rect = pv.Rect()
            cx, cy = x + 0.5 * w, y + 0.5 * h
            tmp = 1.5 * max(w, h)
            cw, ch = tmp, tmp
            crop = pv.AffineFromRect(pv.CenteredRect(cx, cy, cw, ch),
                                     (256, 256))

            pvim = pv.Image(img[:, :, ::-1])  # convert rgb to bgr
            pvim = crop(pvim)
            view = pt.image_pv2proto(pvim)
            face_record.view.CopyFrom(view)

            # Extract landmarks
            l, t, r, b = [int(tmp) for tmp in [x, y, x + w, y + h]]
            d = dlib.rectangle(l, t, r, b)
            shape = self.shape_pred(img, d)

            for i in range(len(shape.parts())):
                loc = shape.parts()[i]
                landmark = face_record.landmarks.add()
                landmark.landmark_id = "point_%02d" % i
                landmark.location.x = loc.x
                landmark.location.y = loc.y

            # Get detection rectangle and crop the face
            #rect = pt.rect_proto2pv(face_record.detection.location).rescale(1.5)
            #tile = im.crop(rect)
            tile = pvim.resize((224, 224))

            #tile.show(delay=1000)

            face_im = tile.asOpenCV2()
            face_im = face_im[:, :, ::-1]  # Convert BGR to RGB
            #mat_ = cv2.cvtColor(mat,cv2.COLOR_RGB2GRAY)
            #mat = cv2.cvtColor(mat_,cv2.COLOR_GRAY2RGB)

            #img = image.load_img('../image/ajb.jpg', target_size=(224, 224))

            from keras_vggface import utils
            from keras.preprocessing import image

            face_im = image.img_to_array(face_im)
            face_im = np.expand_dims(face_im, axis=0)
            face_im = utils.preprocess_input(face_im,
                                             version=2)  # or version=2

            # Needed in multithreaded applications
            with self.graph.as_default():
                tmp = self.recognizer.predict(face_im)

            face_descriptor = pv.meanUnit(tmp.flatten())

            #print('shape:',face_records.face_records[0].landmarks)
            #face_descriptor = self.face_rec.compute_face_descriptor(img, shape, JITTER_COUNT)
            #face_descriptor = np.array(face_descriptor)

            #vec = face_descriptor.flatten()
            face_record.template.data.CopyFrom(
                pt.vector_np2proto(face_descriptor))
Exemplo n.º 18
0
    def crop(self, rect, size=None, interpolation=None, return_affine=False):
        '''
        Crops an image to the given rectangle. Rectangle parameters are rounded to nearest 
        integer values.  High quality resampling.  The default behavior is to use cv.GetSubRect
        to crop the image.  This returns a slice the OpenCV image so modifying the resulting
        image data will also modify the data in this image.  If a size is provide a new OpenCV
        image is created for that size and cv.Resize is used to copy the image data. If the 
        bounds of the rectangle are outside the image, an affine transform (pv.AffineFromRect)
        is used to produce the croped image to properly handle regions outside the image.
        In this case the downsampling quality may not be as good. #
        
        @param rect: a Rectangle defining the region to be cropped.
        @param size: a new size for the returned image.  If None the result is not resized.
        @param interpolation: None = Autoselect or one of CV_INTER_AREA, CV_INTER_NN, CV_INTER_LINEAR, CV_INTER_BICUBIC
        @param return_affine: If True, also return an affine transform that can be used to transform points.
        @returns: a cropped version of the image or if return affine a tuple of (image,affine)
        @rtype: pv.Image
        '''
        # Notes: pv.Rect(0,0,w,h) should return the entire image. Since pixel values
        # are indexed by zero this means that upper limits are not inclusive: x from [0,w)
        # and y from [0,h)
        x, y, w, h = rect.asTuple()

        x = int(np.round(x))
        y = int(np.round(y))
        w = int(np.round(w))
        h = int(np.round(h))

        # Check the bounds for cropping
        if x < 0 or y < 0 or x + w > self.size[0] or y + h > self.size[1]:
            if size is None:
                size = (w, h)

            affine = pv.AffineFromRect(pv.Rect(x, y, w, h), size)
            im = affine(self)
            if return_affine:
                return im, affine
            else:
                return im

        # Get the image as opencv
        cvim = self.asOpenCV()

        # Set up ROI
        subim = cv.GetSubRect(cvim, (x, y, w, h))

        affine = pv.AffineTranslate(-x, -y, (w, h))

        if size is None:
            size = (w, h)

        # Copy to new image
        new_image = cv.CreateImage(size, cvim.depth, cvim.nChannels)
        if interpolation is None:

            if size[0] < w or size[1] < y:
                # Downsampling so use area interpolation
                interpolation = cv.CV_INTER_AREA
            else:
                # Upsampling so use linear
                interpolation = cv.CV_INTER_CUBIC

        # Resize to the correct size
        cv.Resize(subim, new_image, interpolation)

        affine = pv.AffineNonUniformScale(
            float(size[0]) / w,
            float(size[1]) / h, size) * affine

        # Return the result as a pv.Image
        if return_affine:
            return pv.Image(new_image), affine
        else:
            return pv.Image(new_image)
Exemplo n.º 19
0
    def update(self,frame):
        '''
        This is the main work function for the tracker.  After initialization, 
        this function should be called on each new frame.  This function:
        
            1. Extracts the tracking window from the new frame.
            2. Applies the filter to locate the new center of the target.
            3. Updates the filter (if PSR exceeds the threshold).
            4. Updates the internal state of the tracker to reflect the new location and status.
            
        @param frame: a new frame from the video.
        @type frame: pv.Image 
        '''
        
        start = time.time()
        
        self.frame += 1

        self.psr_cache = None
        
        tile,affine = frame.crop(self.rect,size=self.tile_size,return_affine=True)
        #affine = pv.AffineFromRect(self.rect,self.tile_size)
        self.prevRect=copy.deepcopy(self.rect)
        
        #tile = affine.transformImage(frame)
        self.input = tile
        
        corr = self.filter.correlate(tile)
        self.corr = corr
        
        # Find the peak
        _,cols = self.corr.shape
        i = self.corr.argmax()
        x,y = i/cols, i%cols
        target = pv.Point(x,y)
        
        self.best_estimate = affine.invert(target)
        
        if self.subpixel:
            dx,dy = common.subpixel(self.corr[x-3:x+4,y-3:y+4])
            target = pv.Point(x+dx, y+dy)
        
        # check status
        target_rect = pv.CenteredRect(target.X(),target.Y(),self.rect.w,self.rect.h)
        frame_rect = pv.Rect(0,0,frame.size[0],frame.size[1])
        self.in_bounds = frame_rect.containsRect(target_rect)
        status = self.getStatus()
        
        # Status == Good: Update the filter
        psr = self.psr()
        if self.frame <= self.init_time or status == STATUS_GOOD and (self.max_psr == None or psr < self.max_psr):
            self.filter.addTraining(tile,target,rate=self.update_rate)
                
            # Recenter the affine
            target = affine.invertPoint(target)
            dx = target.X() - self.rect.center().X()
            dy = target.Y() - self.rect.center().Y()
            if self.update_location:
                self.rect.x = self.rect.x + dx
                self.rect.y = self.rect.y + dy
            #self.center = target
                                
        stop = time.time()
        self.update_time = stop - start
Exemplo n.º 20
0
def CenteredRect(cx,cy,w,h):
    '''Specify a rectangle using a center point and a width and height.'''
    return pv.Rect(cx-0.5*w,cy-0.5*h,w,h)
Exemplo n.º 21
0
 def annotateFrame(self,frame,color="red",show_images=True):
     '''
     Annotates the image with tracking information including the frame 
     number, psr, and update time. It also displays the input, filter, 
     and output. This method requires quite a bit of time.
     
     @param frame: The frame to annotate this should be the frame that was just passed to the L{update} method.
     @type frame:  pv.Image
     '''        
     
     # Add some text data fto the frame
     frame.annotateLabel(pv.Point(10,10),"FRAME:       %4d"%self.frame)
     frame.annotateLabel(pv.Point(10,20),"PSR:         %6.2f"%self.psr())
     frame.annotateLabel(pv.Point(10,30),"UPDATE TIME: %6.2f ms"%(1000.0*self.updateTime()))
     
     # Show the new estimated center of the track
     estimate = self.asPoint()
     if estimate != None:
         frame.annotateCircle(estimate,5,color=color,fill=color)
     
     # Show the previous tracking location as a gray rectangle
     rect = self.prevRect
     if rect != None:
         w,h = self.tile_size
         tl = pv.Point(rect.x,rect.y)
         tr = pv.Point(rect.x+rect.w,rect.y)
         br = pv.Point(rect.x+rect.w,rect.y+rect.h)
         bl = pv.Point(rect.x,rect.y+rect.h)
         frame.annotateLine(tl,tr,color='gray',width=1)
         frame.annotateLine(tr,br,color='gray',width=1)
         frame.annotateLine(br,bl,color='gray',width=1)
         frame.annotateLine(bl,tl,color='gray',width=1)
 
     # Draw a rectangle for the new location of the track.
     rect = self.rect
     if rect != None:
         w,h = self.tile_size
         tl = pv.Point(rect.x,rect.y)
         tr = pv.Point(rect.x+rect.w,rect.y)
         br = pv.Point(rect.x+rect.w,rect.y+rect.h)
         bl = pv.Point(rect.x,rect.y+rect.h)
         frame.annotateLine(tl,tr,color=color,width=3)
         frame.annotateLine(tr,br,color=color,width=3)
         frame.annotateLine(br,bl,color=color,width=3)
         frame.annotateLine(bl,tl,color=color,width=3)
                     
         if self.getStatus() == STATUS_DROPPED:
             frame.annotateLine(tl,br,color=color,width=3)
             frame.annotateLine(bl,tr,color=color,width=3)
             
     # Show images of the input, filter, and output
     if  show_images:
         pil = frame.asAnnotated()
         x = 10
         y = frame.size[1] - 10
         
         # The input images
         input = self.inputAsImage()
         w,h = input.size
         pil.paste(input.asAnnotated(),(x,y-h))
         frame.annotateRect(pv.Rect(x,y-h,w,h),color=color)
         frame.annotateLabel(pv.Point(x,y-h-10),"INPUT")
         x = x + w + 10
         
         # The correlation filter
         filter = self.filterAsImage()
         w,h = filter.size
         pil.paste(filter.asAnnotated(),(x,y-h))
         frame.annotateRect(pv.Rect(x,y-h,w,h),color=color)
         frame.annotateLabel(pv.Point(x,y-h-10),"FILTER")
         x = x + w + 10
         
         # The correlation output
         corr = self.correlationAsImage()
         w,h = corr.size
         pil.paste(corr.asAnnotated(),(x,y-h))
         frame.annotateRect(pv.Rect(x,y-h,w,h),color=color)
         frame.annotateLabel(pv.Point(x,y-h-10),"OUTPUT")
         x = x + w + 10
Exemplo n.º 22
0
    def _composite(self, img, pos, imgNum):
        """
        Internal method to composite the thumbnail of a given image into the
        correct position, given by (row,col).
        @param img: The image from which a thumbnail will be composited onto the montage
        @param pos: A tuple (row,col) for the position in the montage layout
        @param imgNum: The image index of the tile being drawn, this helps us display the
        appropriate label in the lower left corner if self._labels is not None.
        """
        (row, col) = pos

        if self._keep_aspect:
            # Get the current size
            w, h = img.size

            # Find the scale
            scale = min(1.0 * self._tileSize[1] / w,
                        1.0 * self._tileSize[0] / h)
            w = int(scale * w)
            h = int(scale * h)

            # Resize preserving aspect
            img2 = img.resize((w, h)).asPIL()

            # Create a new image with the old image centered
            x = (self._tileSize[0] - w) / 2
            y = (self._tileSize[1] - h) / 2
            pil = PIL.Image.new('RGB', self._tileSize, "#000000")
            pil.paste(img2, (x, y, x + w, y + h))

            # Generate the tile
            tile = pv.Image(pil)
        else:
            tile = img.resize(self._tileSize)

        pos_x = col * (self._tileSize[0] +
                       self._gutter) + self._gutter + self._xpad
        pos_y = row * (self._tileSize[1] +
                       self._gutter) + self._gutter + self._ypad

        cvImg = self._cvMontageImage
        cvTile = tile.asOpenCV2()
        cvImg[pos_x:pos_x + self._tileSize[0],
              pos_y:pos_y + self._tileSize[1], :] = np.transpose(cvTile,
                                                                 axes=(1, 0,
                                                                       2))

        # Save the position of this image
        self._image_positions.append([
            self._images[imgNum], imgNum,
            pv.Rect(pos_x, pos_y, self._tileSize[0], self._tileSize[1])
        ])

        depth = cvTile.shape[2]
        #if depth == 1:
        #    cvTileBGR = cv.CreateImage(self._tileSize, cv.IPL_DEPTH_8U, 3)
        #    cv.CvtColor(cvTile, cvTileBGR, cv.CV_GRAY2BGR)
        #    cv.Copy(cvTileBGR, cvImg)  #should respect the ROI
        #else:
        #    cv.Copy(cvTile, cvImg)  #should respect the ROI

        if self._labels == 'index':
            #draw image number in lower left corner, respective to ROI
            lbltext = "%d" % imgNum
        elif type(self._labels) == list:
            lbltext = str(self._labels[imgNum])
        else:
            lbltext = None

        if not lbltext is None:
            ((tw, th), _) = cv2.getTextSize(lbltext, *self._txtfont)
            #print "DEBUG: tw, th = %d,%d"%(tw,th)
            if tw > 0 and th > 0:
                cv2.rectangle(cvImg, (0, self._tileSize[1] - 1),
                              (tw + 1, self._tileSize[1] -
                               (th + 1) - self._gutter), (0, 0, 0),
                              thickness=cv2.FILLED)
                font = self._txtfont[0]
                font_size = self._txtfont[1]
                font_thick = self._txtfont[2]
                color = self._txtcolor
                cv2.putText(cvImg, lbltext,
                            (1, self._tileSize[1] - self._gutter - 2), font,
                            font_size, color, font_thick)

        if self._highlighted and (imgNum in self._selected_tiles):
            #draw a highlight around this image
            cv2.rectangle(cvImg, (0, 0),
                          (self._tileSize[0], self._tileSize[1]),
                          (0, 255, 255),
                          thickness=4)
Exemplo n.º 23
0
        im = pv.Image(pathname)

        scale = options.log_scale
        log_im = pv.AffineScale(
            scale,
            (int(scale * im.width), int(scale * im.height))).transformImage(im)

        results = processFaces(im, face_detect, locate_eyes)

        if options.rotate:

            rot_image = pv.Image(im.asPIL().transpose(PIL.Image.ROTATE_90))
            more_results = processFaces(rot_image, face_detect, locate_eyes)
            for face, eye1, eye2 in more_results:
                results.append([
                    pv.Rect(im.width - face.y - face.h, face.x, face.h,
                            face.w),
                    pv.Point(im.width - eye1.Y(), eye1.X()),
                    pv.Point(im.width - eye2.Y(), eye2.X())
                ])

            rot_image = pv.Image(im.asPIL().transpose(PIL.Image.ROTATE_180))
            more_results = processFaces(rot_image, face_detect, locate_eyes)
            for face, eye1, eye2 in more_results:
                results.append([
                    pv.Rect(im.width - face.x - face.w,
                            im.height - face.y - face.h, face.w, face.h),
                    pv.Point(im.width - eye1.X(), im.height - eye1.Y()),
                    pv.Point(im.width - eye2.X(), im.height - eye2.Y())
                ])

            rot_image = pv.Image(im.asPIL().transpose(PIL.Image.ROTATE_270))