-
Notifications
You must be signed in to change notification settings - Fork 3
/
RollingGuidanceFilter.m
103 lines (75 loc) · 2.84 KB
/
RollingGuidanceFilter.m
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
function result = RollingGuidanceFilter(I, sigma_s, sigma_r, ...
iteration,GaussianPrecision)
%function result = RollingGuidanceFilter(I, sigma_s, sigma_r, iteration,GaussianPrecision)
%is executed a Rolling Guidance Filter.
%site:http://www.cse.cuhk.edu.hk/leojia/projects/rollguidance
%input I:the origic image; sigma_s: the Gaussian standard deviation; sigma_r: control the spatial and range weights respectively
iteration: the number of iteration; GaussianPrecision: contorl the size of Block.
%output result: generate a new image
if ~exist('iteration','var')
iteration = 4;
end
if ~exist('sigma_s','var')
sigma_s = 3;
end
if ~exist('sigma_r','var')
sigma_r = 0.1;
end
if ~exist('GaussianPrecision','var')
GaussianPrecision = 0.08;
end
[a b c] = size(I);
GaussianWindow = WindowBlock(sigma_s, GaussianPrecision);
N = ( size(GaussianWindow,1) -1)/2;
J_plus = zeros(size(I));
I = ExpandBorder(I, N);
J = ones(size(I));
for l = 1 : iteration
for k = 1 : c
for j = 1+N : b+N
for i = 1+N : a+N
H = GaussianWindow .* exp( -(J(i-N:i+N,j-N:j+N,k) - J(i,j,k)).^2/2/sigma_r^2 );
K_p = sum(sum(H));
J_plus(i-N,j-N,k) = 1/K_p*sum(sum(H .* I(i-N:i+N,j-N:j+N,k)));
end
end
end
%figure; image(J_plus);
J = ExpandBorder(J_plus, N);
end
result = J_plus;
end
%==================================================================
function GaussianWindow = WindowBlock(sigma_s, GaussianPrecision)
%function GaussianWindow = WindowBlock(sigma_s, GaussianPrecision)
%product a Block of 2D Gaussian.
%input sigma_s: the Gaussian standard deviation; GaussianPrecision: contorl the size of Block.
%output GaussianWindow: a square matrix of 2D Gaussian.
%right below
pq = bsxfun(@plus, ([0:sigma_s*3].^2)', [0:sigma_s*3].^2);
% gaussian distribution
pqrb = exp(-pq/2/sigma_s^2);
% element that is less than GaussianPrecision ar equal zero
pqrb = pqrb .* (pqrb>GaussianPrecision);
% remove all zero column
pqrb(:, pqrb(1,:)==0) = [];
% remove all zero row
pqrb(pqrb(:,1)==0, :) = [];
%left below
pqlb = fliplr(pqrb);
%right upper
pqru = flipud(pqrb);
%left upper
pqlu = fliplr(pqru);
GaussianWindow = [pqlu(:, 1:end-1) pqru;
pqlb(2:end, 1:end-1) pqrb(2:end, :)];
end
%==================================================================
function imageExpand = ExpandBorder(image, N)
%function imageExpand = ExpandBorder(image, N)
%is On the edge of the pixels extend outward N pixels.
%input image: the origic image; N: the number of expansion need.
%output imageExpand: generate a new image
imageExpand = [repmat(image(1,:,:), [N,1,1]) ; image ; repmat(image(end,:,:), [N,1,1])];
imageExpand = [repmat(imageExpand(:,1,:), [1,N,1]) imageExpand repmat(imageExpand(:,end,:), [1,N,1])];
end