Commit 5934cd22aca58a417ccbbc2476661c773387e4f2

Authored by Daniel Bourgault
1 parent 972d1377
Exists in master

g_stabilize rewritten and simplified

Showing 1 changed file with 128 additions and 74 deletions   Show diff stats
src/g_stabilize/g_stabilize.m
1   -function g_stabilize(root_img_name,ext,id_img_ref,id_img_first,id_img_last,precision,varargin)
2   -% Function that calls the stabilization algorithm. The stabilized files
  1 +function g_stabilize(img_ref_fname,varargin)
  2 +% This function and its sub-functions stabilize all images found in the
  3 +% working folder against a reference image. The stabilized files
3 4 % contain the datetime values stored in the 'DateTime' or the 'Comment'
4 5 % field of the unstabilized images.
5 6 %
6 7 % Input:
7   -% root_img_fname: The root name of the images before the id number.
8   -% ext: The image extension (.jpg .png etc), is case
9   -% insensitive
10   -% id_img_ref: The id number of the reference image
11   -% id_img_first: The id number of the first image of the sequence to
12   -% be stabilized
13   -% id_img_last: The id number of the last image of the sequence to
14   -% be stabilized
15   -% precision: The number of digit for the file name
16   -% (e.g.: IMG_0400.JPG would be 4).
  8 +% img_ref_fname: The complete image name, with extension (and path if
  9 +% necessary), of the reference image in the current
  10 +% directory.
  11 +%
17 12 % Parameters, Name, Value
18 13 % roiFile, [Defaults: roi.mat] Name of the file with roi
19 14 % information.
... ... @@ -23,14 +18,34 @@ function g_stabilize(root_img_name,ext,id_img_ref,id_img_first,id_img_last,preci
23 18 % stabilized images.
24 19 %
25 20 % Output:
26   -% All stabilized images are rewritten as image files.
  21 +% All stabilized images are rewritten as image files in the subfolder
  22 +% /stable.
27 23 %
28 24 % Example:
29   -% g_stabilize('IMG_', '.JPG', 1, 2, 20, 4);
  25 +% g_stabilize('IMG_4018.jpg');
30 26 %
31   -% Will run the stabilization reference to IMG_0001.JPG, on
32   -% IMG_0002.JPG to IMG_0020.JPG
33 27  
  28 +%% Some parameters
  29 +% Pyramid level for the stabilization.
  30 +% See documentation in the g_stabilize folder.
  31 +% L = 4 worked well on initial application but may require adjustments for
  32 +% particular application.
  33 +L = 4;
  34 +
  35 +% Number of iterative improvement. Probably ok just 1 iteration.
  36 +niter = 1;
  37 +
  38 +% Parameters for equalization. See help clahs for details.
  39 +% This may not be needed fpr most application but may help other cases.
  40 +% Need to play with it if problems.
  41 +equalize = false;
  42 +nry = 4;
  43 +nrx = 4;
  44 +
  45 +% Extract the path and extension of the reference image
  46 +[pathstr,name,ext] = fileparts(img_ref_fname);
  47 +
  48 +% Check for optional options
34 49 fname_suffix = '_stable';
35 50 auto = 0;
36 51 roifile = 'roi.mat';
... ... @@ -47,64 +62,55 @@ if length(varargin) > 1
47 62 end
48 63  
49 64 hw = waitbar(0,'Preparing images');
50   -% Region of interest
51   -display(' Loading the roi.mat file containing the region of interest (roi)');
52   -load(roifile);
53   -
54 65  
55   -ndigit = ['%',num2str(precision),'.',num2str(precision),'i']
  66 +%% Load the Region of interest (roi) file
  67 +display(' Loading the roi.mat file containing the region of interest (roi)');
  68 +if length(pathstr) == 0 % Images are in the current folder
  69 + load(roifile);
  70 +else
  71 + load([pathstr,'/',roifile]);
  72 +end
56 73  
57 74 % Read the reference image
58   -try
59   - img_ref = [root_img_name,num2str(id_img_ref,ndigit),lower(ext)];
60   - im2 = double(imread(img_ref))/255;
61   -catch
62   - img_ref = [root_img_name,num2str(id_img_ref,ndigit),upper(ext)];
63   - im2 = double(imread(img_ref))/255;
64   -end
  75 +im2 = imread(img_ref_fname);
65 76  
  77 +% Convert into gray scale if not already a B/W image
66 78 if size(im2,3) ~= 1
67   - im2 = uint8(g_rgb2gray(im2)*255);
  79 + im2 = g_rgb2gray(im2);
68 80 end
69 81  
  82 +% May equalize with this equalizer. Careful this doesn't always work well
  83 +% and may compromise the stabilization. Use with care.
  84 +if equalize
  85 + im2 = clahs(im2,nry,nrx);
  86 +end
70 87  
71   -% Pyramid level for the stabilization.
72   -% See documentation in the g_stabilize folder.
73   -% L = 4 worked well on initial application but may require adjustments.
74   -L = 4;
75   -
76   -% Number of iterative improvement. Probably ok just 1 iteration.
77   -niter = 1;
78   -
79   -% Parameters for equalization. See help clahs for details.
80   -nry = 4;
81   -nrx = 4;
82   -im2 = clahs(im2,nry,nrx);
83 88 im2 = double(im2);
84 89  
85 90 % Remove mean and divide by the standard deviation.
86   -inorm = find(roi > 0);
  91 +% This generally help the algorithm to compare images
  92 +inorm = find(roi > 0);
87 93 im2_norm = (im2 - nanmean(im2(inorm)))./nanstd(im2(inorm));
88 94  
89 95 % Take the norm of the gradient of the image. This helps the
90   -% stabilization algorithm
  96 +% stabilization algorithm, nut again you may want to explore
  97 +% without it
91 98 [im2x, im2y] = gradient(im2_norm);
92   -grad_im2 = sqrt(im2x.^2 + im2y.^2);
  99 +grad_im2 = sqrt(im2x.^2 + im2y.^2);
93 100  
94   -% This is the referecne frame for the stabilization algorithm.
  101 +% The second frame is the reference frame for the stabilization algorithm.
95 102 frames(2).im = grad_im2;
96 103  
97   -
  104 +%% Some figures to make sure everything seems ok
98 105 figure(1);
99 106 imagesc(im2);
100 107 colormap(gray);
101   -title('Reference image normalized intensity');
  108 +title('Reference image. Intensity normalized over ROI');
102 109  
103 110 figure(2);
104   -imagesc(grad_im2);
  111 +imagesc(log10(grad_im2+eps));
105 112 colormap(gray);
106   -title('Gradient of the referemce image');
107   -
  113 +title('Gradient of the reference image on a log scale');
108 114  
109 115 figure(3);
110 116 imagesc(roi);
... ... @@ -116,45 +122,84 @@ if ~auto
116 122 return
117 123 end
118 124 end
119   -num_img = id_img_last-id_img_first;
  125 +
  126 +%% Create the folder where to write the stable images
  127 +if length(pathstr) == 0 % Images are in the current folder
  128 + [status,message,messageid] = mkdir('stable');
  129 +else
  130 + [status,message,messageid] = mkdir([pathstr,'/stable']);
  131 +end
  132 +
  133 +% Check for images already stablilized that would be found in the
  134 +% stable folder. This is not yet fully implemeted. The goal would
  135 +% be not to perform the stabilization to images already stabilized
  136 +%if strcmp(message,'Directory already exists.')
  137 +% if length(pathstr) == 0
  138 +% img_done = dir(['stable/*',ext]);
  139 +% else
  140 +% img_done = dir([pathstr,'/stable/','*',ext]);
  141 +% end
  142 +%end
  143 +
  144 +%% Read all filemanes in the current directory with the same extension as the ref img
  145 +if length(pathstr) == 0 % Images are in the current folder
  146 + all_img = dir(['*',ext]);
  147 +else
  148 + all_img = dir([pathstr,'/','*',ext]);
  149 +end
  150 +
  151 +% Number of images to proceed
  152 +N = length(all_img);
  153 +
120 154 time_per_img = 0;
121   -for i = id_img_first:id_img_last
122   - time_rem = (id_img_last-i+1)*time_per_img;
123   - waitbar((i-id_img_first)/num_img,hw,sprintf('Stabilizing image #%d. %.0fh%02.2fmn remaining',i,fix(time_rem/3600),rem(time_rem,3600)/60));
  155 +
  156 +for i = 1:N
  157 +
  158 +
  159 + time_rem = (N-i+1)*time_per_img;
  160 + if i > 1
  161 + waitbar((i-1)/N,hw,sprintf('Stabilizing image #%d. %.0fh%02.2fmn remaining',...
  162 + i,fix(time_rem/3600),rem(time_rem,3600)/60));
  163 + else
  164 + waitbar((i-1)/N,hw,sprintf('Stabilizing image #%d.',...
  165 + i,fix(time_rem/3600),rem(time_rem,3600)/60));
  166 + end
124 167 total = tic;
125   - %Reading current image;
126   - try
127   - img_to_stabilize = [root_img_name,num2str(i,ndigit),lower(ext)];
128   - im1 = imread(img_to_stabilize);
129   -
130   - catch
131   - img_to_stabilize = [root_img_name,num2str(i,ndigit),upper(ext)];
132   - im1 = imread(img_to_stabilize);
  168 +
  169 + if length(pathstr) == 0
  170 + im1 = imread(all_img(i).name);
  171 + im_info = imfinfo(all_img(i).name);
  172 + else
  173 + im1 = imread([pathstr,'/',all_img(i).name]);
  174 + im_info = imfinfo([pathstr,'/',all_img(i).name]);
133 175 end
134   - im_info = imfinfo(img_to_stabilize);
  176 +
  177 + % Convert into gray scale if not already a B/W image
135 178 if size(im1,3) ~= 1
136   - im1 = uint8(g_rgb2gray(double(im1)/255)*255);
  179 + im1 = g_rgb2gray(im1);
  180 + end
  181 +
  182 + % May equalize with this equalizer.
  183 + if equalize
  184 + im1 = clahs(im1,nry,nrx);
137 185 end
138 186  
139   - im1 = clahs(im1,nry,nrx);
140 187 im1 = double(im1);
141 188  
142   - im1_norm = (im1 - nanmean(im1(inorm)))./nanstd(im1(inorm));
  189 + im1_norm = (im1 - nanmean(im1(inorm)))./nanstd(im1(inorm));
143 190 [im1x, im1y] = gradient(im1_norm);
144   - grad_im1 = sqrt(im1x.^2 + im1y.^2);
  191 + grad_im1 = sqrt(im1x.^2 + im1y.^2);
145 192  
146 193 frames(1).im = grad_im1;
  194 +
147 195 for iter = 1:niter
148 196 [motion,stable] = g_videostabilize(frames,roi,L);
149   - frames(1).im = stable(1).im;
150   - %motion.A
151   - %motion.T
  197 + frames(1).im = stable(1).im;
152 198 end
153 199  
154 200 im_stable = g_warp(im1,motion.A,motion.T);
155 201 im_stable = uint8(im_stable);
156   - %frames(2).im = stable(1).im;
157   -
  202 +
158 203 if isfield(im_info,'DateTime')
159 204 datetime = im_info.DateTime;
160 205 elseif isfield(im_info,'Comment')
... ... @@ -162,8 +207,17 @@ for i = id_img_first:id_img_last
162 207 else
163 208 datetime = '';
164 209 end
165   - imwrite(im_stable,[img_to_stabilize(1:end-4) fname_suffix '.jpg'],'Quality',100,'Comment',datetime);
166   -
  210 +
  211 + if length(pathstr) == 0
  212 + stable_img_fname = ['stable/',all_img(i).name(1:end-4)]
  213 + else
  214 + stable_img_fname = [pathstr,'/stable/',all_img(i).name(1:end-4)]
  215 + end
  216 +
  217 + imwrite(im_stable,[stable_img_fname fname_suffix ext],...
  218 + 'Quality',100,'Comment',datetime);
  219 +
167 220 time_per_img = toc(total);
168 221 end
  222 +
169 223 close(hw)
170 224 \ No newline at end of file
... ...