def feature_extraction_longitudinal(self, img_file):
        block_size = 16

        img = io.imread(img_file)
        #print img.shape
        img = preprocessing.adjust_image_size(img, block_size)
        h, w = img.shape
        texture_img = preprocessing.FastCartoonTexture(img,
                                                       sigma=2.5,
                                                       show=False)

        contrast_img_guassian = preprocessing.local_constrast_enhancement_gaussian(
            img)

        mask = get_maps.get_quality_map_intensity(img)
        #show.show_mask(mask, img, fname=None, block=True)
        quality_map, dir_map, fre_map = get_maps.get_quality_map_dict(
            texture_img,
            self.dict_all,
            self.dict_ori,
            self.dict_spacing,
            block_size=16,
            process=False)

        enh_constrast_img = filtering.gabor_filtering_pixel(
            contrast_img_guassian,
            dir_map + math.pi / 2,
            fre_map,
            mask=np.ones((h, w), np.int),
            block_size=16,
            angle_inc=3)

        mnt = self.minu_model.run(img, minu_thr=0.2)

        #show.show_minutiae(img,mnt)
        des = descriptor.minutiae_descriptor_extraction(img,
                                                        mnt,
                                                        self.patch_types,
                                                        self.des_models,
                                                        self.patchIndexV,
                                                        batch_size=128)

        blkH, blkW = dir_map.shape

        minu_template = template.MinuTemplate(h=h,
                                              w=w,
                                              blkH=blkH,
                                              blkW=blkW,
                                              minutiae=mnt,
                                              des=des,
                                              oimg=dir_map,
                                              mask=mask)

        rolled_template = template.Template()
        rolled_template.add_minu_template(minu_template)

        return rolled_template, texture_img, enh_constrast_img
Esempio n. 2
0
def demo_minutiae_extraction(img_path,minu_model_dir):

    img_files = glob.glob(img_path+'*.bmp')
    img_files.sort()
    minu_model = (minutiae_AEC.ImportGraph(minu_model_dir))
    block = True
    for i, img_file in enumerate(img_files):
        if i<11:
            continue
        img = io.imread(img_file)
        name = os.path.basename(img_file)
        h, w = img.shape
        mask = np.ones((h,w),dtype=np.uint8)

        minu_thr = 0.3

        texture_img = preprocessing.FastCartoonTexture(img)
        contrast_img = preprocessing.local_constrast_enhancement_gaussian(img)

        dir_map, fre_map = get_maps.get_maps_STFT(contrast_img, patch_size=64, block_size=16, preprocess=True)

        dict, spacing,_ = get_maps.construct_dictionary(ori_num=60)
        quality_map, fre_map = get_maps.get_quality_map_ori_dict(contrast_img, dict, spacing,
                                                                 dir_map=dir_map,
                                                                 block_size=16)
        enh_texture_img = filtering.gabor_filtering_pixel(contrast_img, dir_map + math.pi / 2, fre_map,
                                                          mask=mask,
                                                          block_size=16, angle_inc=3)

        mnt = minu_model.run(contrast_img, minu_thr=0.1)
        #mnt = minu_model.remove_spurious_minutiae(mnt, mask)
        #minutiae_sets.append(mnt)
        #fname = output_path + os.path.splitext(name)[0] + '_texture_img.jpeg'
        show.show_minutiae(contrast_img, mnt, block=block, fname=None)

        mnt = minu_model.run(texture_img, minu_thr=0.1)
        # mnt = minu_model.remove_spurious_minutiae(mnt, mask)
        # minutiae_sets.append(mnt)
        # fname = output_path + os.path.splitext(name)[0] + '_texture_img.jpeg'
        show.show_minutiae(texture_img, mnt, block=block, fname=None)

        print(i)
    def feature_extraction_single_rolled_enhancement(self, img_file):
        block_size = 16

        img = io.imread(img_file)
        # print img.shape

        img = preprocessing.adjust_image_size(img, block_size)

        h, w = img.shape
        #texture_img = preprocessing.FastCartoonTexture(img, sigma=2.5, show=False)

        contrast_img_guassian = preprocessing.local_constrast_enhancement_gaussian(
            img)

        mask = get_maps.get_quality_map_intensity(img)

        #show.show_mask(mask, img, fname=None, block=True)
        start = timeit.default_timer()
        quality_map, dir_map, fre_map = get_maps.get_quality_map_dict(
            contrast_img_guassian,
            self.dict_all,
            self.dict_ori,
            self.dict_spacing,
            block_size=16,
            process=False)
        stop = timeit.default_timer()
        OF_time = stop - start
        print 'of estimate time: %f' % (OF_time)
        start = timeit.default_timer()
        enh_constrast_img = filtering.gabor_filtering_pixel2(
            contrast_img_guassian,
            dir_map + math.pi / 2,
            fre_map,
            mask=mask,
            gabor_filters=self.gabor_filters)
        stop = timeit.default_timer()
        filtering_time = stop - start
        print 'filtering time: %f' % (filtering_time)
        mnt = self.minu_model.run_whole_image(img, minu_thr=0.2)

        # show.show_minutiae(img,mnt)
        des = descriptor.minutiae_descriptor_extraction(img,
                                                        mnt,
                                                        self.patch_types,
                                                        self.des_models,
                                                        self.patchIndexV,
                                                        batch_size=128)

        blkH, blkW = dir_map.shape

        minu_template = template.MinuTemplate(h=h,
                                              w=w,
                                              blkH=blkH,
                                              blkW=blkW,
                                              minutiae=mnt,
                                              des=des,
                                              oimg=dir_map,
                                              mask=mask)

        rolled_template = template.Template()
        rolled_template.add_minu_template(minu_template)

        # texture templates
        stride = 32
        x = np.arange(24, w - 24, stride)
        y = np.arange(24, h - 24, stride)

        virtual_minutiae = []
        distFromBg = scipy.ndimage.morphology.distance_transform_edt(mask)
        for y_i in y:
            for x_i in x:
                if (distFromBg[y_i][x_i] <= 16):
                    continue
                ofY = int(y_i / 16)
                ofX = int(x_i / 16)

                ori = -dir_map[ofY][ofX]
                # print("ori = " + str(ori))
                virtual_minutiae.append([x_i, y_i,
                                         ori])  #, distFromBg[y_i,x_i]
        virtual_minutiae = np.asarray(virtual_minutiae)
        if len(virtual_minutiae) > 3:
            virtual_des = descriptor.minutiae_descriptor_extraction(
                img,
                virtual_minutiae,
                self.patch_types,
                self.des_models,
                self.patchIndexV,
                batch_size=128)
            #show.show_minutiae(img,virtual_minutiae)
            texture_template = template.TextureTemplate(
                h=h,
                w=w,
                minutiae=virtual_minutiae,
                des=virtual_des,
                mask=mask)
            rolled_template.add_texture_template(texture_template)
        return rolled_template, enh_constrast_img
Esempio n. 4
0
    def feature_extraction_single_latent(self,img_file, output_path = None, show_processes=False ):
        #block = True
        img = io.imread(img_file)

        name = os.path.basename(img_file)
        mask_CNN,_ = self.ROI_model.run(img)
        h,w = mask_CNN.shape
        #mask = mask_dilation(mask, block_size=16)
        latent_template = template.Template()

        minu_thr = 0.3

        # template set 1: no ROI and enhancement are required
        # texture image is used for coase segmentation

        descriptor_imgs = []
        texture_img = preprocessing.FastCartoonTexture(img, sigma=2.5, show=False)




        descriptor_imgs.append(texture_img)

        contrast_img_guassian = preprocessing.local_constrast_enhancement_gaussian(img)

        quality_map, _, _ = get_maps.get_quality_map_dict(texture_img, self.dict_all, self.dict_ori,
                                                                      self.dict_spacing, block_size=16, process=False)
        quality_map_pixel = cv2.resize(quality_map, (0, 0), fx=16, fy=16)
        #plt.imshow(quality_map_pixel,cmap='gray')
        #plt.show()
        mask_coarse = quality_map_pixel > 0.3
        mask_coarse = mask_coarse.astype(np.int)
        mask = mask_coarse * mask_CNN
        # show.show_mask(mask_CNN, img, fname='mask_RCNN.jpeg',block=block)
        # show.show_mask(mask_coarse,img,fname = 'mask_coarse.jpeg',block=block)
        # show.show_mask(mask, img, fname='mask.jpeg',block=block)




        #show.show_mask(mask, AEC_img, fname='mask_AEC.jpeg',block=block)
        # plt.imshow(AEC_img,cmap = 'gray')
        # plt.show(block=block)
        # plt.close()



        #show.show_mask(mask_CNN, img, fname='mask_RCNN.jpeg',block=block)

        # AEC_img[mask == 0] = 128
        # plt.imshow(AEC_img, cmap='gray')
        # plt.show(block=block)
        # plt.close()

        AEC_img = self.enhancement_model.run(texture_img)
        quality_map, dir_map, fre_map = get_maps.get_quality_map_dict(AEC_img, self.dict_all, self.dict_ori,self.dict_spacing, block_size=16, process=False)

        blkH, blkW = dir_map.shape

        if show_processes:
            show.show_orientation_field(img, dir_map,mask = mask,fname='OF.jpeg')




        # mnt = self.minu_model.run(contrast_img_mean, minu_thr=0.1)
        # mnt = self.remove_spurious_minutiae(mnt, mask)
        # minutiae_sets.append(mnt)
        #
        # fname = output_path + os.path.splitext(name)[0] + '_contrast_img_mean.jpeg'
        # show.show_minutiae(contrast_img_mean, mnt, block=block, fname=fname)


        enh_contrast_img = filtering.gabor_filtering_pixel(contrast_img_guassian, dir_map + math.pi / 2, fre_map,
                                                          mask=mask,
                                                          block_size=16, angle_inc=3)

        enh_texture_img = filtering.gabor_filtering_pixel(texture_img, dir_map + math.pi / 2, fre_map,
                                                          mask=mask,
                                                          block_size=16, angle_inc=3)

        if show_processes:
            show.show_image(texture_img, mask=mask, block=True, fname='cropped_texture_image.jpeg')
            show.show_image(AEC_img, mask=mask, block=True, fname='cropped_AEC_image.jpeg')
            show.show_image(enh_contrast_img, mask=mask, block=True, fname='cropped_enh_image.jpeg')

        #np.ones((h, w), np.int)
        descriptor_imgs.append(enh_contrast_img)


        quality_map2, _ , _ = get_maps.get_quality_map_dict(enh_contrast_img, self.dict_all,self.dict_ori,self.dict_spacing, block_size=16,
                                                                      process=False)
        quality_map_pixel2 = cv2.resize(quality_map2, (0, 0), fx=16, fy=16)

        mask2 = quality_map_pixel2 > 0.50

        #mask = mask*mask2

        minutiae_sets = []
        mnt = self.minu_model.run(contrast_img_guassian, minu_thr=0.05)
        mnt = self.remove_spurious_minutiae(mnt, mask)
        minutiae_sets.append(mnt)
        if show_processes:
            fname = 'minutiae_texture_img.jpeg'
            show.show_minutiae(texture_img, mnt, mask=mask,block=block, fname=fname)

        mnt = self.minu_model.run(AEC_img, minu_thr=0.3)
        mnt = self.remove_spurious_minutiae(mnt, mask2)
        minutiae_sets.append(mnt)
        if show_processes:
            fname = 'minutiae_AEC_img.jpeg'
            show.show_minutiae(AEC_img, mnt, mask=mask, block=block, fname=fname)

        mnt = self.minu_model.run(enh_contrast_img, minu_thr=0.3)
        mnt = self.remove_spurious_minutiae(mnt, mask2)
        minutiae_sets.append(mnt)
        if show_processes:
            fname = 'minutiae_enh_contrast_img.jpeg'
            show.show_minutiae(enh_contrast_img, mnt, mask=mask,block=block, fname=fname)

        mnt = self.minu_model.run(enh_texture_img, minu_thr=0.3)
        mnt = self.remove_spurious_minutiae(mnt, mask2)
        minutiae_sets.append(mnt)

        # minutiae template 1
        des = descriptor.minutiae_descriptor_extraction(texture_img, minutiae_sets[0], self.patch_types, self.des_models,
                                                         self.patchIndexV, batch_size=128)

        minu_template = template.MinuTemplate(h=h, w=w, blkH=blkH, blkW=blkW, minutiae=minutiae_sets[0],
                                                   des=des, oimg=dir_map, mask=mask)
        latent_template.add_minu_template(minu_template)

        # minutiae template 2
        des = descriptor.minutiae_descriptor_extraction(texture_img, minutiae_sets[1], self.patch_types,
                                                        self.des_models,
                                                        self.patchIndexV, batch_size=128)

        minu_template = template.MinuTemplate(h=h, w=w, blkH=blkH, blkW=blkW, minutiae=minutiae_sets[1],
                                              des=des, oimg=dir_map, mask=mask)
        latent_template.add_minu_template(minu_template)

        # minutiae template 3
        des = descriptor.minutiae_descriptor_extraction(enh_texture_img, minutiae_sets[2], self.patch_types,
                                                        self.des_models,
                                                        self.patchIndexV, batch_size=128)

        minu_template = template.MinuTemplate(h=h, w=w, blkH=blkH, blkW=blkW, minutiae=minutiae_sets[2],
                                              des=des, oimg=dir_map, mask=mask)
        latent_template.add_minu_template(minu_template)

        # minutiae template 4
        des = descriptor.minutiae_descriptor_extraction(enh_texture_img, minutiae_sets[3], self.patch_types,
                                                        self.des_models,
                                                        self.patchIndexV, batch_size=128)

        minu_template = template.MinuTemplate(h=h, w=w, blkH=blkH, blkW=blkW, minutiae=minutiae_sets[3],
                                              des=des, oimg=dir_map, mask=mask)
        latent_template.add_minu_template(minu_template)



        return latent_template
Esempio n. 5
0
    def feature_extraction_single_latent_evaluation_AEM18T(self,img_file, mask_file, AEC_img_file,output_path = None ):

        img = io.imread(img_file)
        name = os.path.basename(img_file)
        AEC_img = io.imread(AEC_img_file)
        mask_CNN = io.imread(mask_file)
        h,w = mask_CNN.shape
        #mask = mask_dilation(mask, block_size=16)
        latent_template = template.Template()
        block = False
        minu_thr = 0.3

        # template set 1: no ROI and enhancement are required
        # texture image is used for coase segmentation

        descriptor_imgs = []
        texture_img = preprocessing.FastCartoonTexture(img, sigma=2.5, show=False)
        descriptor_imgs.append(texture_img)
        contrast_img_mean = preprocessing.local_constrast_enhancement(img)
        contrast_img_guassian = preprocessing.local_constrast_enhancement_gaussian(img)

        quality_map, dir_map, fre_map = get_maps.get_quality_map_dict(texture_img, self.dict_all, self.dict_ori,
                                                                      self.dict_spacing, block_size=16, process=False)
        quality_map_pixel = cv2.resize(quality_map, (0, 0), fx=16, fy=16)
        mask_coarse = quality_map_pixel > 0.3
        mask_coarse = mask_coarse.astype(np.int)
        quality_map, dir_map, fre_map = get_maps.get_quality_map_dict(AEC_img, self.dict_all, self.dict_ori,self.dict_spacing, block_size=16, process=False)


        minutiae_sets = []
        mnt = self.minu_model.run(texture_img, minu_thr=0.1)
        mnt = self.remove_spurious_minutiae(mnt, mask_coarse)
        minutiae_sets.append(mnt)
        fname = output_path + os.path.splitext(name)[0] + '_texture_img.jpeg'
        show.show_minutiae(texture_img, mnt, block=block, fname=fname)

        mnt = self.minu_model.run(contrast_img_mean, minu_thr=0.1)
        mnt = self.remove_spurious_minutiae(mnt, mask_coarse)
        minutiae_sets.append(mnt)

        fname = output_path + os.path.splitext(name)[0] + '_contrast_img_mean.jpeg'
        show.show_minutiae(contrast_img_mean, mnt, block=block, fname=fname)


        mnt = self.minu_model.run(contrast_img_guassian, minu_thr=0.1)
        mnt = self.remove_spurious_minutiae(mnt, mask_coarse)
        minutiae_sets.append(mnt)
        fname = output_path + os.path.splitext(name)[0] + '_contrast_img_guassian.jpeg'
        show.show_minutiae(contrast_img_guassian, mnt, block=block, fname=fname)

        #show.show_orientation_field(AEC_img,dir_map)

        enh_texture_img = filtering.gabor_filtering_pixel(texture_img, dir_map + math.pi / 2, fre_map,
                                                          mask=np.ones((h, w), np.int),
                                                          block_size=16, angle_inc=3)

        descriptor_imgs.append(enh_texture_img)

        enh_constrast_img = filtering.gabor_filtering_pixel(contrast_img_guassian, dir_map + math.pi / 2, fre_map,
                                                          mask=np.ones((h,w),np.int),
                                                          block_size=16, angle_inc=3)

        descriptor_imgs.append(enh_constrast_img)

        quality_map2, _ , _ = get_maps.get_quality_map_dict(enh_texture_img, self.dict_all,self.dict_ori,self.dict_spacing, block_size=16,
                                                                      process=False)
        quality_map_pixel2 = cv2.resize(quality_map2, (0, 0), fx=16, fy=16)

        mask = quality_map_pixel2 > 0.55


        mask = mask.astype(np.int)
        mask = mask_coarse * mask
        mask = mask * mask_CNN

        mnt = self.minu_model.run(AEC_img, minu_thr=0.3)
        mnt = self.remove_spurious_minutiae(mnt, mask)
        minutiae_sets.append(mnt)
        fname = output_path + os.path.splitext(name)[0] + '_AEC_img.jpeg'
        show.show_minutiae(AEC_img, mnt, block=block, fname=fname)

        mnt = self.minu_model.run(enh_texture_img, minu_thr=0.3)
        mnt = self.remove_spurious_minutiae(mnt, mask)
        minutiae_sets.append(mnt)

        fname = output_path + os.path.splitext(name)[0] + '_enh_texture_img.jpeg'
        show.show_minutiae(enh_texture_img, mnt, block=block, fname=fname)

        mnt = self.minu_model.run(enh_constrast_img, minu_thr=0.3)
        mnt = self.remove_spurious_minutiae(mnt, mask)
        minutiae_sets.append(mnt)
        fname = output_path + os.path.splitext(name)[0] + '_enh_constrast_img.jpeg'
        show.show_minutiae(enh_constrast_img, mnt, block=block, fname=fname)


        blkH, blkW = dir_map.shape
        for mnt in minutiae_sets:
            for des_img in descriptor_imgs:
                des = descriptor.minutiae_descriptor_extraction(des_img, mnt, self.patch_types, self.des_models,
                                                        self.patchIndexV, batch_size=128)
                minu_template = template.MinuTemplate(h=h, w=w, blkH=blkH, blkW=blkW, minutiae=mnt,
                                                  des=des, oimg=dir_map, mask=mask)
                latent_template.add_minu_template(minu_template)

        return latent_template
    def feature_extraction_single_latent(self,
                                         img_file,
                                         output_dir=None,
                                         ppi=500,
                                         show_processes=False,
                                         show_minutiae=False,
                                         minu_file=None):
        block = False
        block_size = 16
        img0 = io.imread(img_file, mode='L')  # / 255.0

        img = img0.copy()

        if ppi != 500:
            img = cv2.resize(img, (0, 0), fx=500.0 / ppi, fy=500.0 / ppi)
        img = preprocessing.adjust_image_size(img, block_size)
        name = os.path.basename(img_file)
        start = timer()
        h, w = img.shape

        if h > 1000 and w > 1000:
            return None, None

        # cropping using two dictionary based approach
        if minu_file is not None:
            manu_minu = np.loadtxt(minu_file)
            # #     # remove low quality minutiae points
            input_minu = np.array(manu_minu)
            input_minu[:, 2] = input_minu[:, 2] / 180.0 * np.pi
        else:
            input_minu = []

        descriptor_imgs = []
        texture_img = preprocessing.FastCartoonTexture(img,
                                                       sigma=2.5,
                                                       show=False)
        STFT_texture_img = preprocessing.STFT(texture_img)

        contrast_img_guassian = preprocessing.local_constrast_enhancement_gaussian(
            img)
        STFT_img = preprocessing.STFT(img)
        constrast_STFT_img = preprocessing.STFT(contrast_img_guassian)

        # step 1: enhance the latent based on our autoencoder
        AEC_img = self.enhancement_model.run_whole_image(STFT_texture_img)
        quality_map_AEC, dir_map_AEC, fre_map_AEC = get_maps.get_quality_map_dict(
            AEC_img, self.dict_all, self.dict_ori, self.dict_spacing, R=500.0)
        blkmask_AEC = quality_map_AEC > 0.45
        blkmask_AEC = binary_closing(blkmask_AEC, np.ones(
            (3, 3))).astype(np.int)
        blkmask_AEC = binary_opening(blkmask_AEC, np.ones(
            (3, 3))).astype(np.int)
        blkmask_SSIM = get_maps.SSIM(STFT_texture_img, AEC_img, thr=0.2)
        blkmask = blkmask_SSIM * blkmask_AEC
        blkH, blkW = blkmask.shape
        mask = cv2.resize(blkmask.astype(float),
                          (block_size * blkW, block_size * blkH),
                          interpolation=cv2.INTER_LINEAR)
        mask[mask > 0] = 1

        minutiae_sets = []

        mnt_STFT = self.minu_model[0].run_whole_image(STFT_img, minu_thr=0.05)
        minutiae_sets.append(mnt_STFT)
        if show_minutiae:
            fname = output_dir + os.path.splitext(name)[0] + '_STFT_img.jpeg'
            show.show_minutiae_sets(STFT_img, [input_minu, mnt_STFT],
                                    mask=None,
                                    block=block,
                                    fname=fname)

        mnt_STFT = self.minu_model[0].run_whole_image(constrast_STFT_img,
                                                      minu_thr=0.1)
        minutiae_sets.append(mnt_STFT)

        mnt_AEC = self.minu_model[1].run_whole_image(AEC_img, minu_thr=0.25)
        mnt_AEC = self.remove_spurious_minutiae(mnt_AEC, mask)
        minutiae_sets.append(mnt_AEC)
        if show_minutiae:
            fname = output_dir + os.path.splitext(name)[0] + '_AEC_img.jpeg'
            show.show_minutiae_sets(AEC_img, [input_minu, mnt_AEC],
                                    mask=mask,
                                    block=block,
                                    fname=fname)

        enh_contrast_img = filtering.gabor_filtering_pixel2(
            contrast_img_guassian,
            dir_map_AEC + math.pi / 2,
            fre_map_AEC,
            mask=np.ones((h, w)),
            block_size=16,
            angle_inc=3)
        mnt_contrast = self.minu_model[1].run_whole_image(enh_contrast_img,
                                                          minu_thr=0.25)
        mnt_contrast = self.remove_spurious_minutiae(mnt_contrast, mask)
        minutiae_sets.append(mnt_contrast)

        enh_texture_img = filtering.gabor_filtering_pixel2(
            texture_img,
            dir_map_AEC + math.pi / 2,
            fre_map_AEC,
            mask=np.ones((h, w)),
            block_size=16,
            angle_inc=3)

        mnt_texture = self.minu_model[1].run_whole_image(enh_texture_img,
                                                         minu_thr=0.25)
        mnt_texture = self.remove_spurious_minutiae(mnt_texture, mask)
        minutiae_sets.append(mnt_texture)

        h, w = img.shape
        latent_template = template.Template()

        # template set 1: no ROI and enhancement are required
        # texture image is used for coase segmentation
        descriptor_imgs = []

        descriptor_imgs.append(STFT_img)
        descriptor_imgs.append(texture_img)
        descriptor_imgs.append(enh_texture_img)
        descriptor_imgs.append(enh_contrast_img)

        mnt2 = self.get_common_minutiae(minutiae_sets, thr=2)

        mnt3 = self.get_common_minutiae(minutiae_sets, thr=3)

        minutiae_sets.append(mnt3)
        minutiae_sets.append(mnt2)
        if show_minutiae:
            fname = output_dir + os.path.splitext(name)[0] + '_common_2.jpeg'
            show.show_minutiae_sets(img, [input_minu, mnt2],
                                    mask=mask,
                                    block=block,
                                    fname=fname)
        end = timer()
        print('Time for minutiae extraction: %f' % (end - start))

        start = timer()
        for mnt in minutiae_sets:
            for des_img in descriptor_imgs:
                des = descriptor.minutiae_descriptor_extraction(
                    des_img,
                    mnt,
                    self.patch_types,
                    self.des_models,
                    self.patchIndexV,
                    batch_size=128)
                minu_template = template.MinuTemplate(h=h,
                                                      w=w,
                                                      blkH=blkH,
                                                      blkW=blkW,
                                                      minutiae=mnt,
                                                      des=des,
                                                      oimg=dir_map_AEC,
                                                      mask=mask)
                latent_template.add_minu_template(minu_template)
        end = timer()
        print('Time for minutiae descriptor generation: %f' % (end - start))

        start = timer()
        # texture templates
        stride = 16
        x = np.arange(24, w - 24, stride)
        y = np.arange(24, h - 24, stride)

        virtual_minutiae = []
        distFromBg = scipy.ndimage.morphology.distance_transform_edt(mask)
        for y_i in y:
            for x_i in x:
                if (distFromBg[y_i][x_i] <= 16):
                    continue
                ofY = int(y_i / 16)
                ofX = int(x_i / 16)

                ori = -dir_map_AEC[ofY][ofX]
                virtual_minutiae.append([x_i, y_i, ori])
                virtual_minutiae.append([x_i, y_i, math.pi + ori])
        virtual_minutiae = np.asarray(virtual_minutiae)

        texture_template = []
        if len(virtual_minutiae) > 3:
            virtual_des = descriptor.minutiae_descriptor_extraction(
                enh_contrast_img,
                virtual_minutiae,
                self.patch_types,
                self.des_models,
                self.patchIndexV,
                batch_size=128,
                patch_size=96)

            texture_template = template.TextureTemplate(
                h=h,
                w=w,
                minutiae=virtual_minutiae,
                des=virtual_des,
                mask=None)
            latent_template.add_texture_template(texture_template)

        end = timer()

        print('Time for texture template generation: %f' % (end - start))
        return latent_template, texture_template