-
Notifications
You must be signed in to change notification settings - Fork 1
/
applyhatch_pluscolor.m
executable file
·266 lines (239 loc) · 9.82 KB
/
applyhatch_pluscolor.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
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
function [im_hatch,colorlist] = applyhatch_pluscolor(h,patterns,CvBW,Hinvert,colorlist, ...
dpi,hatchsc,lw)
%APPLYHATCH_PLUSCOLOR Apply hatched patterns to a figure in BW or Color
% APPLYHATCH_PLUSCOLOR(H,PATTERNS) creates a new figure from the figure H by
% replacing distinct colors in H with the black and white
% patterns in PATTERNS. The format for PATTERNS can be
% a string of the characters:
% '/', '\', '|', '-', '+', 'x', '.', 'c', 'w', 'k'
% (see makehatch_plus.m for more details) or
% a cell array of matrices of zeros (white) and ones (black)
%
% In addition, H can alternatively be a uint8 NxMx3 matrix of the type
% produced by imread. In this case, colors in this image will be
% replaced with patterns as if it was a figure. A final figure window
% will be generated that displays the result. The DPI argument
% discussed below will be ignored if H is an image matrix.
%
% APPLYHATCH_PLUSCOLOR(H,PATTERNS,CVBW) binary value for choice of Color or Black
% and White plots. If color is chosen the color will match that of the
% current fill. 1 -> Color, anything else -> BW
%
% APPLYHATCH_PLUSCOLOR(H,PATTERNS,CVBW,HINVERT) binary value to invert the hatch.
% i.e., if it is black lines with a white background, that becomes white
% lines with a black background. This can either be a scalar value or a
% 1xN array equal to the length of PATTERNS. When used as an array each
% PATTERNS(i) will be inverted according to Hinvert(i). 1 -> Invert,
% anything else -> Non Inverted
%
% APPLYHATCH_PLUSCOLOR(H,PATTERNS,CVBW,HINVERT,COLORS) maps the colors in the n by 3
% matrix COLORS to PATTERNS. Each row of COLORS specifies an RGB
% color value.
%
% Note this function makes a bitmap image of H and so is limited
% to bitmap output.
%
% Additional arguments:
%
% [im_hatch,colorlist] = applyhatch_plus(h,patterns,CvBW,Hinvert,colorlist,dpi,hatchsc,linewidth)
%
% input DPI allows specification of bitmap resolution, making plot resolution
% better for printing. Ignored if H is an image matrix.
% HATCHSC multiplier for hatch scale to increase size of pattern for better operation
% at higher resolutions
% default [] uses screen resolution as in
% APPLYHATCH
% LINEWIDTH A scaling factor to apply to line and dot sizes
% in hatching. Defaults to 1.
% output IM_HATCH RGB bitmap matrix of new figure
% use IMWRITE to output in desired format
% COLORLIST List of colors actually replaced. Useful info if
% no colorlist initially given to function.
% Colorlist will be uint8, not 0-1 scale as
% originally specified.
%
% Example 1:
% bar(rand(3,4));
% [im_hatch,colorlist] = applyhatch_pluscolor(gcf,'\-x.',0,0,[],150);
% imwrite(im_hatch,'im_hatch.png','png')
%
% Example 2:
% bar(rand(3,4));
% [im_hatch,colorlist] = applyhatch_pluscolor(gcf,'\-x.',1,[],[],150);
% imwrite(im_hatch,'im_hatch.png','png')
%
% Example 3:
% colormap(cool(6));
% pie(rand(6,1));
% legend('Jan','Feb','Mar','Apr','May','Jun');
% im_hatch = applyhatch_pluscolor(gcf,'|-.+\/',1,[1 1 0 1 0 0],cool(6),200,3,2);
% imwrite(im_hatch,'im_hatch.png','png')
%
% Example 4: Produces roughly the same thing as example 1
% bar(rand(3,4));
% print -dtiff -r150 im.tiff
% im = imread( 'im.tiff', 'tiff' );
% [im_hatch,colorlist] = applyhatch_pluscolor(im,'\-x.');
% imwrite(im_hatch,'im_hatch.tiff','tiff')
%
%
% Modification of APPLYHATCH to allow higher resolution output
% Modified Brian FG Katz 8-aout-03
% Modified David M Kaplan 19-fevrier-08
%
% Modification of APPLYHATCH_PLUS to allow for color and inverted hatch
% Modified Brandon Levey May 6, 2009
%
% See also: APPLYHATCH, APPLYHATCH_PLUS, MAKEHATCH, MAKEHATCH_PLUS
% By Ben Hinkle, bhinkle@mathworks.com
% This code is in the public domain.
if ~exist('CvBW','var'); CvBW = 0 ; end % defaults to black and white
if isempty(CvBW); CvBW = 0 ; end % defaults to black and white
if (CvBW ~= 0 && CvBW ~= 1); CvBW = 0 ; end % defaults to black and white
if ~exist('Hinvert','var'); Hinvert = 0 ; end % defaults to not inverted
if isempty(Hinvert); Hinvert = 0 ; end % defaults to not inverted
if length(Hinvert) == length(patterns) || length(Hinvert) == 1
for i = 1:length(Hinvert)
if Hinvert(i) ~= 0 && Hinvert(i) ~= 1; Hinvert(i) = 0 ; end
end
else
error(['The length of Hinvert must be 1 or equal to the length of PATTERNS']);
end
if ~exist('hatchsc','var'); hatchsc = 1 ; end
if ~exist('dpi','var'); dpi = 0 ; end % defaults to screen resolution
if ~exist('colorlist','var'); colorlist = [] ; end
if ~exist('lw','var'); lw=1; end
if numel(h) == 1 % Assume it is a figure window
oldppmode = get(h,'paperpositionmode');
oldunits = get(h,'units');
oldcolor = get(h,'color');
oldpos = get(h,'position');
set(h,'paperpositionmode','auto');
set(h,'units','pixels');
set(h,'color',[1 1 1]);
figsize = get(h,'position');
bits = hardcopy(h,'-dzbuffer',['-r' num2str(dpi)]);
% % Try a different approach using a temporary file - use this if having probs
% tn = [ tempname '.tif' ];
% print( '-dtiff', [ '-r' num2str(dpi) ], tn )
% bits = uint8( imread( tn, 'TIFF' ) );
% delete(tn)
set(h,'paperpositionmode',oldppmode);
set(h,'color',oldcolor);
elseif size(h,3) == 3 % Assume it is an image matrix
bits = h;
oldunits='pixels';
oldpos = [ 0, 0, size(bits,2), size(bits,1) ];
figsize = oldpos;
else
error( 'Bad first argument.' );
end
bwidth = size(bits,2);
bheight = size(bits,1);
bsize = bwidth * bheight;
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% The next bit basically modernizes the original
% version of this function using things like unique
% and for loops
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% Make bitmap one long matrix with 3 columns
bits = reshape(bits,[bsize,3]);
% Convert original color scale to 255 scale
if ~isempty(colorlist)
% NOTE: Added "floor" below because this seems to better pick out
% correct colors produced by "hardcopy above better than uint8 by itself
%colorlist = uint8(255*colorlist);
colorlist = uint8(floor(255*colorlist));
else
% Find unique colors in image - this takes a long time at high resolution
[B,I,J] = unique( bits, 'rows' );
switch CvBW
case 0 % BW plot
% Find just "colored" colors
C = find( B(:,1)~=B(:,2) | B(:,1)~=B(:,3) );
case 1 % color plot
% Find all non black and white
B = sortrows(B);
C = 1:size(B,1);
C = C(2:end-1)';
end
colorlist = B( C , : );
end
% Loop over list of colors and find matches
for k = 1:size(colorlist,1)
% Find points that match color
if exist('B','var') % Use unique colors if around
I = C(k) == J;
else % Otherwise test each point
cc = colorlist(k,:);
I = bits(:,1)==cc(1) & bits(:,2)==cc(2) & bits(:,3)==cc(3);
if ~any(I(:)), continue, end
end
% What pattern to use
pati = mod( k-1, numel(patterns) ) + 1;
if iscell(patterns)
pattern = patterns{pati};
elseif isa(patterns,'char')
pattern = makehatch_plus(patterns(pati),6*hatchsc,lw);
else
pattern = patterns;
end
pattern = uint8(1-pattern);
if length(Hinvert) == 1
invertHatch = logical(Hinvert);
else
invertHatch = logical(Hinvert(pati));
end
% Make a big pattern matching size of bits
pheight = size(pattern,2);
pwidth = size(pattern,1);
ratioh = ceil(bheight/pheight);
ratiow = ceil(bwidth/pwidth);
bigpattern = repmat(pattern,[ratioh ratiow]);
if ratioh*pheight > bheight
bigpattern(bheight+1:end,:) = [];
end
if ratiow*pwidth > bwidth
bigpattern(:,bwidth+1:end) = [];
end
% Put that pattern into bits and logical values based on CvBW and Hinvert
switch CvBW
case 0 % BW
if invertHatch
bits(find(I),:) = repmat(~bigpattern(I)*255,[1,3]);
else
bits(find(I),:) = repmat(bigpattern(I)*255,[1,3]);
end
case 1 % Color
if invertHatch
bits(find(I),:) = [ ...
(uint8(bigpattern(I)) * colorlist(k,1)) + uint8((~bigpattern(I)) * 255), ...
(uint8(bigpattern(I)) * colorlist(k,2)) + uint8((~bigpattern(I)) * 255), ...
(uint8(bigpattern(I)) * colorlist(k,3)) + uint8((~bigpattern(I)) * 255)];
else
bits(find(I),:) = [ ...
(uint8(~bigpattern(I)) * colorlist(k,1)) + uint8((bigpattern(I)) * 255), ...
(uint8(~bigpattern(I)) * colorlist(k,2)) + uint8((bigpattern(I)) * 255), ...
(uint8(~bigpattern(I)) * colorlist(k,3)) + uint8((bigpattern(I)) * 255)];
end
end
end
% Put bits back into its normal shape
bits = reshape( bits, [bheight,bwidth,3] );
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% Replot
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
newfig = figure('units',oldunits,'visible','off');
imaxes = axes('parent',newfig,'units','pixels');
im = image(bits,'parent',imaxes);
%fpos = get(newfig,'position');
%set(newfig,'position',[fpos(1:2) figsize(3) figsize(4)+1]);
set(newfig,'position',oldpos)
set(newfig,'units','pixels')
set(imaxes,'position',[0 0 figsize(3) figsize(4)+1],'visible','off');
set(newfig,'visible','on');
set(newfig,'units','normalized');
set(imaxes,'units','normalized');
set(imaxes,'DataAspectRatio',[1 1 1],'DataAspectRatioMode','manual');
if nargout > 0, im_hatch = bits; end
if nargout < 2, clear colorlist; end