Mercurial > hg > camir-aes2014
comparison toolboxes/FullBNT-1.0.7/KPMtools/exportfig.m @ 0:e9a9cd732c1e tip
first hg version after svn
author | wolffd |
---|---|
date | Tue, 10 Feb 2015 15:05:51 +0000 |
parents | |
children |
comparison
equal
deleted
inserted
replaced
-1:000000000000 | 0:e9a9cd732c1e |
---|---|
1 function varargout = exportfig(varargin) | |
2 %EXPORTFIG Export a figure. | |
3 % EXPORTFIG(H, FILENAME) writes the figure H to FILENAME. H is | |
4 % a figure handle and FILENAME is a string that specifies the | |
5 % name of the output file. | |
6 % | |
7 % EXPORTFIG(H, FILENAME, OPTIONS) writes the figure H to FILENAME | |
8 % with options initially specified by the structure OPTIONS. The | |
9 % field names of OPTIONS must be legal parameters listed below | |
10 % and the field values must be legal values for the corresponding | |
11 % parameter. Default options can be set in releases prior to R12 | |
12 % by storing the OPTIONS structure in the root object's appdata | |
13 % with the command | |
14 % setappdata(0,'exportfigdefaults', OPTIONS) | |
15 % and for releases after R12 by setting the preference with the | |
16 % command | |
17 % setpref('exportfig', 'defaults', OPTIONS) | |
18 % | |
19 % EXPORTFIG(...,PARAM1,VAL1,PARAM2,VAL2,...) specifies | |
20 % parameters that control various characteristics of the output | |
21 % file. Any parameter value can be the string 'auto' which means | |
22 % the parameter uses the default factory behavior, overriding | |
23 % any other default for the parameter. | |
24 % | |
25 % Format Paramter: | |
26 % 'Format' a string | |
27 % specifies the output format. Defaults to 'eps'. For a | |
28 % list of export formats type 'help print'. | |
29 % 'Preview' one of the strings 'none', 'tiff' | |
30 % specifies a preview for EPS files. Defaults to 'none'. | |
31 % | |
32 % Size Parameters: | |
33 % 'Width' a positive scalar | |
34 % specifies the width in the figure's PaperUnits | |
35 % 'Height' a positive scalar | |
36 % specifies the height in the figure's PaperUnits | |
37 % 'Bounds' one of the strings 'tight', 'loose' | |
38 % specifies a tight or loose bounding box. Defaults to 'tight'. | |
39 % 'Reference' an axes handle or a string | |
40 % specifies that the width and height parameters | |
41 % are relative to the given axes. If a string is | |
42 % specified then it must evaluate to an axes handle. | |
43 % | |
44 % Specifying only one dimension sets the other dimension | |
45 % so that the exported aspect ratio is the same as the | |
46 % figure's or reference axes' current aspect ratio. | |
47 % If neither dimension is specified the size defaults to | |
48 % the width and height from the figure's or reference | |
49 % axes' size. Tight bounding boxes are only computed for | |
50 % 2-D views and in that case the computed bounds enclose all | |
51 % text objects. | |
52 % | |
53 % Rendering Parameters: | |
54 % 'Color' one of the strings 'bw', 'gray', 'cmyk' | |
55 % 'bw' specifies that lines and text are exported in | |
56 % black and all other objects in grayscale | |
57 % 'gray' specifies that all objects are exported in grayscale | |
58 % 'rgb' specifies that all objects are exported in color | |
59 % using the RGB color space | |
60 % 'cmyk' specifies that all objects are exported in color | |
61 % using the CMYK color space | |
62 % 'Renderer' one of 'painters', 'zbuffer', 'opengl' | |
63 % specifies the renderer to use | |
64 % 'Resolution' a positive scalar | |
65 % specifies the resolution in dots-per-inch. | |
66 % 'LockAxes' one of 0 or 1 | |
67 % specifies that all axes limits and ticks should be fixed | |
68 % while exporting. | |
69 % | |
70 % The default color setting is 'bw'. | |
71 % | |
72 % Font Parameters: | |
73 % 'FontMode' one of the strings 'scaled', 'fixed' | |
74 % 'FontSize' a positive scalar | |
75 % in 'scaled' mode multiplies with the font size of each | |
76 % text object to obtain the exported font size | |
77 % in 'fixed' mode specifies the font size of all text | |
78 % objects in points | |
79 % 'DefaultFixedFontSize' a positive scalar | |
80 % in 'fixed' mode specified the default font size in | |
81 % points | |
82 % 'FontSizeMin' a positive scalar | |
83 % specifies the minimum font size allowed after scaling | |
84 % 'FontSizeMax' a positive scalar | |
85 % specifies the maximum font size allowed after scaling | |
86 % 'FontEncoding' one of the strings 'latin1', 'adobe' | |
87 % specifies the character encoding of the font | |
88 % 'SeparateText' one of 0 or 1 | |
89 % specifies that the text objects are stored in separate | |
90 % file as EPS with the base filename having '_t' appended. | |
91 % | |
92 % If FontMode is 'scaled' but FontSize is not specified then a | |
93 % scaling factor is computed from the ratio of the size of the | |
94 % exported figure to the size of the actual figure. | |
95 % | |
96 % The default 'FontMode' setting is 'scaled'. | |
97 % | |
98 % Line Width Parameters: | |
99 % 'LineMode' one of the strings 'scaled', 'fixed' | |
100 % 'LineWidth' a positive scalar | |
101 % 'DefaultFixedLineWidth' a positive scalar | |
102 % 'LineWidthMin' a positive scalar | |
103 % specifies the minimum line width allowed after scaling | |
104 % 'LineWidthMax' a positive scalar | |
105 % specifies the maximum line width allowed after scaling | |
106 % The semantics of 'Line' parameters are exactly the | |
107 % same as the corresponding 'Font' parameters, except that | |
108 % they apply to line widths instead of font sizes. | |
109 % | |
110 % Style Map Parameter: | |
111 % 'LineStyleMap' one of [], 'bw', or a function name or handle | |
112 % specifies how to map line colors to styles. An empty | |
113 % style map means styles are not changed. The style map | |
114 % 'bw' is a built-in mapping that maps lines with the same | |
115 % color to the same style and otherwise cycles through the | |
116 % available styles. A user-specified map is a function | |
117 % that takes as input a cell array of line objects and | |
118 % outputs a cell array of line style strings. The default | |
119 % map is []. | |
120 % | |
121 % Examples: | |
122 % exportfig(gcf,'fig1.eps','height',3); | |
123 % Exports the current figure to the file named 'fig1.eps' with | |
124 % a height of 3 inches (assuming the figure's PaperUnits is | |
125 % inches) and an aspect ratio the same as the figure's aspect | |
126 % ratio on screen. | |
127 % | |
128 % opts = struct('FontMode','fixed','FontSize',10,'height',3); | |
129 % exportfig(gcf, 'fig2.eps', opts, 'height', 5); | |
130 % Exports the current figure to 'fig2.eps' with all | |
131 % text in 10 point fonts and with height 5 inches. | |
132 % | |
133 % See also PREVIEWFIG, APPLYTOFIG, RESTOREFIG, PRINT. | |
134 | |
135 % Copyright 2000 Ben Hinkle | |
136 % Email bug reports and comments to bhinkle@mathworks.com | |
137 | |
138 if (nargin < 2) | |
139 error('Too few input arguments'); | |
140 end | |
141 | |
142 % exportfig(H, filename, [options,] ...) | |
143 H = varargin{1}; | |
144 if ~LocalIsHG(H,'figure') | |
145 error('First argument must be a handle to a figure.'); | |
146 end | |
147 filename = varargin{2}; | |
148 if ~ischar(filename) | |
149 error('Second argument must be a string.'); | |
150 end | |
151 paramPairs = {varargin{3:end}}; | |
152 if nargin > 2 | |
153 if isstruct(paramPairs{1}) | |
154 pcell = LocalToCell(paramPairs{1}); | |
155 paramPairs = {pcell{:}, paramPairs{2:end}}; | |
156 end | |
157 end | |
158 verstr = version; | |
159 majorver = str2num(verstr(1)); | |
160 defaults = []; | |
161 if majorver > 5 | |
162 if ispref('exportfig','defaults') | |
163 defaults = getpref('exportfig','defaults'); | |
164 end | |
165 elseif exist('getappdata') | |
166 defaults = getappdata(0,'exportfigdefaults'); | |
167 end | |
168 if ~isempty(defaults) | |
169 dcell = LocalToCell(defaults); | |
170 paramPairs = {dcell{:}, paramPairs{:}}; | |
171 end | |
172 | |
173 % Do some validity checking on param-value pairs | |
174 if (rem(length(paramPairs),2) ~= 0) | |
175 error(['Invalid input syntax. Optional parameters and values' ... | |
176 ' must be in pairs.']); | |
177 end | |
178 | |
179 auto.format = 'eps'; | |
180 auto.preview = 'none'; | |
181 auto.width = -1; | |
182 auto.height = -1; | |
183 auto.color = 'bw'; | |
184 auto.defaultfontsize=10; | |
185 auto.fontsize = -1; | |
186 auto.fontmode='scaled'; | |
187 auto.fontmin = 8; | |
188 auto.fontmax = 60; | |
189 auto.defaultlinewidth = 1.0; | |
190 auto.linewidth = -1; | |
191 auto.linemode=[]; | |
192 auto.linemin = 0.5; | |
193 auto.linemax = 100; | |
194 auto.fontencoding = 'latin1'; | |
195 auto.renderer = []; | |
196 auto.resolution = []; | |
197 auto.stylemap = []; | |
198 auto.applystyle = 0; | |
199 auto.refobj = -1; | |
200 auto.bounds = 'tight'; | |
201 explicitbounds = 0; | |
202 auto.lockaxes = 1; | |
203 auto.separatetext = 0; | |
204 opts = auto; | |
205 | |
206 % Process param-value pairs | |
207 args = {}; | |
208 for k = 1:2:length(paramPairs) | |
209 param = lower(paramPairs{k}); | |
210 if ~ischar(param) | |
211 error('Optional parameter names must be strings'); | |
212 end | |
213 value = paramPairs{k+1}; | |
214 | |
215 switch (param) | |
216 case 'format' | |
217 opts.format = LocalCheckAuto(lower(value),auto.format); | |
218 if strcmp(opts.format,'preview') | |
219 error(['Format ''preview'' no longer supported. Use PREVIEWFIG' ... | |
220 ' instead.']); | |
221 end | |
222 case 'preview' | |
223 opts.preview = LocalCheckAuto(lower(value),auto.preview); | |
224 if ~strcmp(opts.preview,{'none','tiff'}) | |
225 error('Preview must be ''none'' or ''tiff''.'); | |
226 end | |
227 case 'width' | |
228 opts.width = LocalToNum(value, auto.width); | |
229 if ~ischar(value) | ~strcmp(value,'auto') | |
230 if ~LocalIsPositiveScalar(opts.width) | |
231 error('Width must be a numeric scalar > 0'); | |
232 end | |
233 end | |
234 case 'height' | |
235 opts.height = LocalToNum(value, auto.height); | |
236 if ~ischar(value) | ~strcmp(value,'auto') | |
237 if(~LocalIsPositiveScalar(opts.height)) | |
238 error('Height must be a numeric scalar > 0'); | |
239 end | |
240 end | |
241 case 'color' | |
242 opts.color = LocalCheckAuto(lower(value),auto.color); | |
243 if ~strcmp(opts.color,{'bw','gray','rgb','cmyk'}) | |
244 error('Color must be ''bw'', ''gray'',''rgb'' or ''cmyk''.'); | |
245 end | |
246 case 'fontmode' | |
247 opts.fontmode = LocalCheckAuto(lower(value),auto.fontmode); | |
248 if ~strcmp(opts.fontmode,{'scaled','fixed'}) | |
249 error('FontMode must be ''scaled'' or ''fixed''.'); | |
250 end | |
251 case 'fontsize' | |
252 opts.fontsize = LocalToNum(value,auto.fontsize); | |
253 if ~ischar(value) | ~strcmp(value,'auto') | |
254 if ~LocalIsPositiveScalar(opts.fontsize) | |
255 error('FontSize must be a numeric scalar > 0'); | |
256 end | |
257 end | |
258 case 'defaultfixedfontsize' | |
259 opts.defaultfontsize = LocalToNum(value,auto.defaultfontsize); | |
260 if ~ischar(value) | ~strcmp(value,'auto') | |
261 if ~LocalIsPositiveScalar(opts.defaultfontsize) | |
262 error('DefaultFixedFontSize must be a numeric scalar > 0'); | |
263 end | |
264 end | |
265 case 'fontsizemin' | |
266 opts.fontmin = LocalToNum(value,auto.fontmin); | |
267 if ~ischar(value) | ~strcmp(value,'auto') | |
268 if ~LocalIsPositiveScalar(opts.fontmin) | |
269 error('FontSizeMin must be a numeric scalar > 0'); | |
270 end | |
271 end | |
272 case 'fontsizemax' | |
273 opts.fontmax = LocalToNum(value,auto.fontmax); | |
274 if ~ischar(value) | ~strcmp(value,'auto') | |
275 if ~LocalIsPositiveScalar(opts.fontmax) | |
276 error('FontSizeMax must be a numeric scalar > 0'); | |
277 end | |
278 end | |
279 case 'fontencoding' | |
280 opts.fontencoding = LocalCheckAuto(lower(value),auto.fontencoding); | |
281 if ~strcmp(opts.fontencoding,{'latin1','adobe'}) | |
282 error('FontEncoding must be ''latin1'' or ''adobe''.'); | |
283 end | |
284 case 'linemode' | |
285 opts.linemode = LocalCheckAuto(lower(value),auto.linemode); | |
286 if ~strcmp(opts.linemode,{'scaled','fixed'}) | |
287 error('LineMode must be ''scaled'' or ''fixed''.'); | |
288 end | |
289 case 'linewidth' | |
290 opts.linewidth = LocalToNum(value,auto.linewidth); | |
291 if ~ischar(value) | ~strcmp(value,'auto') | |
292 if ~LocalIsPositiveScalar(opts.linewidth) | |
293 error('LineWidth must be a numeric scalar > 0'); | |
294 end | |
295 end | |
296 case 'defaultfixedlinewidth' | |
297 opts.defaultlinewidth = LocalToNum(value,auto.defaultlinewidth); | |
298 if ~ischar(value) | ~strcmp(value,'auto') | |
299 if ~LocalIsPositiveScalar(opts.defaultlinewidth) | |
300 error(['DefaultFixedLineWidth must be a numeric scalar >' ... | |
301 ' 0']); | |
302 end | |
303 end | |
304 case 'linewidthmin' | |
305 opts.linemin = LocalToNum(value,auto.linemin); | |
306 if ~ischar(value) | ~strcmp(value,'auto') | |
307 if ~LocalIsPositiveScalar(opts.linemin) | |
308 error('LineWidthMin must be a numeric scalar > 0'); | |
309 end | |
310 end | |
311 case 'linewidthmax' | |
312 opts.linemax = LocalToNum(value,auto.linemax); | |
313 if ~ischar(value) | ~strcmp(value,'auto') | |
314 if ~LocalIsPositiveScalar(opts.linemax) | |
315 error('LineWidthMax must be a numeric scalar > 0'); | |
316 end | |
317 end | |
318 case 'linestylemap' | |
319 opts.stylemap = LocalCheckAuto(value,auto.stylemap); | |
320 case 'renderer' | |
321 opts.renderer = LocalCheckAuto(lower(value),auto.renderer); | |
322 if ~ischar(value) | ~strcmp(value,'auto') | |
323 if ~strcmp(opts.renderer,{'painters','zbuffer','opengl'}) | |
324 error(['Renderer must be ''painters'', ''zbuffer'' or' ... | |
325 ' ''opengl''.']); | |
326 end | |
327 end | |
328 case 'resolution' | |
329 opts.resolution = LocalToNum(value,auto.resolution); | |
330 if ~ischar(value) | ~strcmp(value,'auto') | |
331 if ~(isnumeric(value) & (prod(size(value)) == 1) & (value >= 0)); | |
332 error('Resolution must be a numeric scalar >= 0'); | |
333 end | |
334 end | |
335 case 'applystyle' % means to apply the options and not export | |
336 opts.applystyle = 1; | |
337 case 'reference' | |
338 if ischar(value) | |
339 if strcmp(value,'auto') | |
340 opts.refobj = auto.refobj; | |
341 else | |
342 opts.refobj = eval(value); | |
343 end | |
344 else | |
345 opts.refobj = value; | |
346 end | |
347 if ~LocalIsHG(opts.refobj,'axes') | |
348 error('Reference object must evaluate to an axes handle.'); | |
349 end | |
350 case 'bounds' | |
351 opts.bounds = LocalCheckAuto(lower(value),auto.bounds); | |
352 explicitbounds = 1; | |
353 if ~strcmp(opts.bounds,{'tight','loose'}) | |
354 error('Bounds must be ''tight'' or ''loose''.'); | |
355 end | |
356 case 'lockaxes' | |
357 opts.lockaxes = LocalToNum(value,auto.lockaxes); | |
358 case 'separatetext' | |
359 opts.separatetext = LocalToNum(value,auto.separatetext); | |
360 otherwise | |
361 error(['Unrecognized option ' param '.']); | |
362 end | |
363 end | |
364 | |
365 % make sure figure is up-to-date | |
366 drawnow; | |
367 | |
368 allLines = findall(H, 'type', 'line'); | |
369 allText = findall(H, 'type', 'text'); | |
370 allAxes = findall(H, 'type', 'axes'); | |
371 allImages = findall(H, 'type', 'image'); | |
372 allLights = findall(H, 'type', 'light'); | |
373 allPatch = findall(H, 'type', 'patch'); | |
374 allSurf = findall(H, 'type', 'surface'); | |
375 allRect = findall(H, 'type', 'rectangle'); | |
376 allFont = [allText; allAxes]; | |
377 allColor = [allLines; allText; allAxes; allLights]; | |
378 allMarker = [allLines; allPatch; allSurf]; | |
379 allEdge = [allPatch; allSurf]; | |
380 allCData = [allImages; allPatch; allSurf]; | |
381 | |
382 old.objs = {}; | |
383 old.prop = {}; | |
384 old.values = {}; | |
385 | |
386 % Process format | |
387 if strncmp(opts.format,'eps',3) & ~strcmp(opts.preview,'none') | |
388 args = {args{:}, ['-' opts.preview]}; | |
389 end | |
390 | |
391 hadError = 0; | |
392 oldwarn = warning; | |
393 try | |
394 | |
395 % lock axes limits, ticks and labels if requested | |
396 if opts.lockaxes | |
397 old = LocalManualAxesMode(old, allAxes, 'TickMode'); | |
398 old = LocalManualAxesMode(old, allAxes, 'TickLabelMode'); | |
399 old = LocalManualAxesMode(old, allAxes, 'LimMode'); | |
400 end | |
401 | |
402 % Process size parameters | |
403 figurePaperUnits = get(H, 'PaperUnits'); | |
404 oldFigureUnits = get(H, 'Units'); | |
405 oldFigPos = get(H,'Position'); | |
406 set(H, 'Units', figurePaperUnits); | |
407 figPos = get(H,'Position'); | |
408 refsize = figPos(3:4); | |
409 if opts.refobj ~= -1 | |
410 oldUnits = get(opts.refobj, 'Units'); | |
411 set(opts.refobj, 'Units', figurePaperUnits); | |
412 r = get(opts.refobj, 'Position'); | |
413 refsize = r(3:4); | |
414 set(opts.refobj, 'Units', oldUnits); | |
415 end | |
416 aspectRatio = refsize(1)/refsize(2); | |
417 if (opts.width == -1) & (opts.height == -1) | |
418 opts.width = refsize(1); | |
419 opts.height = refsize(2); | |
420 elseif (opts.width == -1) | |
421 opts.width = opts.height * aspectRatio; | |
422 elseif (opts.height == -1) | |
423 opts.height = opts.width / aspectRatio; | |
424 end | |
425 wscale = opts.width/refsize(1); | |
426 hscale = opts.height/refsize(2); | |
427 sizescale = min(wscale,hscale); | |
428 old = LocalPushOldData(old,H,'PaperPositionMode', ... | |
429 get(H,'PaperPositionMode')); | |
430 set(H, 'PaperPositionMode', 'auto'); | |
431 newPos = [figPos(1) figPos(2)+figPos(4)*(1-hscale) ... | |
432 wscale*figPos(3) hscale*figPos(4)]; | |
433 set(H, 'Position', newPos); | |
434 set(H, 'Units', oldFigureUnits); | |
435 | |
436 % process line-style map | |
437 if ~isempty(opts.stylemap) & ~isempty(allLines) | |
438 oldlstyle = LocalGetAsCell(allLines,'LineStyle'); | |
439 old = LocalPushOldData(old, allLines, {'LineStyle'}, ... | |
440 oldlstyle); | |
441 newlstyle = oldlstyle; | |
442 if ischar(opts.stylemap) & strcmpi(opts.stylemap,'bw') | |
443 newlstyle = LocalMapColorToStyle(allLines); | |
444 else | |
445 try | |
446 newlstyle = feval(opts.stylemap,allLines); | |
447 catch | |
448 warning(['Skipping stylemap. ' lasterr]); | |
449 end | |
450 end | |
451 set(allLines,{'LineStyle'},newlstyle); | |
452 end | |
453 | |
454 % Process rendering parameters | |
455 switch (opts.color) | |
456 case {'bw', 'gray'} | |
457 if ~strcmp(opts.color,'bw') & strncmp(opts.format,'eps',3) | |
458 opts.format = [opts.format 'c']; | |
459 end | |
460 args = {args{:}, ['-d' opts.format]}; | |
461 | |
462 %compute and set gray colormap | |
463 oldcmap = get(H,'Colormap'); | |
464 newgrays = 0.30*oldcmap(:,1) + 0.59*oldcmap(:,2) + 0.11*oldcmap(:,3); | |
465 newcmap = [newgrays newgrays newgrays]; | |
466 old = LocalPushOldData(old, H, 'Colormap', oldcmap); | |
467 set(H, 'Colormap', newcmap); | |
468 | |
469 %compute and set ColorSpec and CData properties | |
470 old = LocalUpdateColors(allColor, 'color', old); | |
471 old = LocalUpdateColors(allAxes, 'xcolor', old); | |
472 old = LocalUpdateColors(allAxes, 'ycolor', old); | |
473 old = LocalUpdateColors(allAxes, 'zcolor', old); | |
474 old = LocalUpdateColors(allMarker, 'MarkerEdgeColor', old); | |
475 old = LocalUpdateColors(allMarker, 'MarkerFaceColor', old); | |
476 old = LocalUpdateColors(allEdge, 'EdgeColor', old); | |
477 old = LocalUpdateColors(allEdge, 'FaceColor', old); | |
478 old = LocalUpdateColors(allCData, 'CData', old); | |
479 | |
480 case {'rgb','cmyk'} | |
481 if strncmp(opts.format,'eps',3) | |
482 opts.format = [opts.format 'c']; | |
483 args = {args{:}, ['-d' opts.format]}; | |
484 if strcmp(opts.color,'cmyk') | |
485 args = {args{:}, '-cmyk'}; | |
486 end | |
487 else | |
488 args = {args{:}, ['-d' opts.format]}; | |
489 end | |
490 otherwise | |
491 error('Invalid Color parameter'); | |
492 end | |
493 if (~isempty(opts.renderer)) | |
494 args = {args{:}, ['-' opts.renderer]}; | |
495 end | |
496 if (~isempty(opts.resolution)) | ~strncmp(opts.format,'eps',3) | |
497 if isempty(opts.resolution) | |
498 opts.resolution = 0; | |
499 end | |
500 args = {args{:}, ['-r' int2str(opts.resolution)]}; | |
501 end | |
502 | |
503 % Process font parameters | |
504 if ~isempty(opts.fontmode) | |
505 oldfonts = LocalGetAsCell(allFont,'FontSize'); | |
506 oldfontunits = LocalGetAsCell(allFont,'FontUnits'); | |
507 set(allFont,'FontUnits','points'); | |
508 switch (opts.fontmode) | |
509 case 'fixed' | |
510 if (opts.fontsize == -1) | |
511 set(allFont,'FontSize',opts.defaultfontsize); | |
512 else | |
513 set(allFont,'FontSize',opts.fontsize); | |
514 end | |
515 case 'scaled' | |
516 if (opts.fontsize == -1) | |
517 scale = sizescale; | |
518 else | |
519 scale = opts.fontsize; | |
520 end | |
521 newfonts = LocalScale(oldfonts,scale,opts.fontmin,opts.fontmax); | |
522 set(allFont,{'FontSize'},newfonts); | |
523 otherwise | |
524 error('Invalid FontMode parameter'); | |
525 end | |
526 old = LocalPushOldData(old, allFont, {'FontSize'}, oldfonts); | |
527 old = LocalPushOldData(old, allFont, {'FontUnits'}, oldfontunits); | |
528 end | |
529 if strcmp(opts.fontencoding,'adobe') & strncmp(opts.format,'eps',3) | |
530 args = {args{:}, '-adobecset'}; | |
531 end | |
532 | |
533 % Process line parameters | |
534 if ~isempty(opts.linemode) | |
535 oldlines = LocalGetAsCell(allMarker,'LineWidth'); | |
536 old = LocalPushOldData(old, allMarker, {'LineWidth'}, oldlines); | |
537 switch (opts.linemode) | |
538 case 'fixed' | |
539 if (opts.linewidth == -1) | |
540 set(allMarker,'LineWidth',opts.defaultlinewidth); | |
541 else | |
542 set(allMarker,'LineWidth',opts.linewidth); | |
543 end | |
544 case 'scaled' | |
545 if (opts.linewidth == -1) | |
546 scale = sizescale; | |
547 else | |
548 scale = opts.linewidth; | |
549 end | |
550 newlines = LocalScale(oldlines, scale, opts.linemin, opts.linemax); | |
551 set(allMarker,{'LineWidth'},newlines); | |
552 end | |
553 end | |
554 | |
555 % adjust figure bounds to surround axes | |
556 if strcmp(opts.bounds,'tight') | |
557 if (~strncmp(opts.format,'eps',3) & LocalHas3DPlot(allAxes)) | ... | |
558 (strncmp(opts.format,'eps',3) & opts.separatetext) | |
559 if (explicitbounds == 1) | |
560 warning(['Cannot compute ''tight'' bounds. Using ''loose''' ... | |
561 ' bounds.']); | |
562 end | |
563 opts.bounds = 'loose'; | |
564 end | |
565 end | |
566 warning('off'); | |
567 if ~isempty(allAxes) | |
568 if strncmp(opts.format,'eps',3) | |
569 if strcmp(opts.bounds,'loose') | |
570 args = {args{:}, '-loose'}; | |
571 end | |
572 old = LocalPushOldData(old,H,'Position', oldFigPos); | |
573 elseif strcmp(opts.bounds,'tight') | |
574 oldaunits = LocalGetAsCell(allAxes,'Units'); | |
575 oldapos = LocalGetAsCell(allAxes,'Position'); | |
576 oldtunits = LocalGetAsCell(allText,'units'); | |
577 oldtpos = LocalGetAsCell(allText,'Position'); | |
578 set(allAxes,'units','points'); | |
579 apos = LocalGetAsCell(allAxes,'Position'); | |
580 oldunits = get(H,'Units'); | |
581 set(H,'units','points'); | |
582 origfr = get(H,'position'); | |
583 fr = []; | |
584 for k=1:length(allAxes) | |
585 if ~strcmpi(get(allAxes(k),'Tag'),'legend') | |
586 axesR = apos{k}; | |
587 r = LocalAxesTightBoundingBox(axesR, allAxes(k)); | |
588 r(1:2) = r(1:2) + axesR(1:2); | |
589 fr = LocalUnionRect(fr,r); | |
590 end | |
591 end | |
592 if isempty(fr) | |
593 fr = [0 0 origfr(3:4)]; | |
594 end | |
595 for k=1:length(allAxes) | |
596 ax = allAxes(k); | |
597 r = apos{k}; | |
598 r(1:2) = r(1:2) - fr(1:2); | |
599 set(ax,'Position',r); | |
600 end | |
601 old = LocalPushOldData(old, allAxes, {'Position'}, oldapos); | |
602 old = LocalPushOldData(old, allText, {'Position'}, oldtpos); | |
603 old = LocalPushOldData(old, allText, {'Units'}, oldtunits); | |
604 old = LocalPushOldData(old, allAxes, {'Units'}, oldaunits); | |
605 old = LocalPushOldData(old, H, 'Position', oldFigPos); | |
606 old = LocalPushOldData(old, H, 'Units', oldFigureUnits); | |
607 r = [origfr(1) origfr(2)+origfr(4)-fr(4) fr(3:4)]; | |
608 set(H,'Position',r); | |
609 else | |
610 args = {args{:}, '-loose'}; | |
611 old = LocalPushOldData(old,H,'Position', oldFigPos); | |
612 end | |
613 end | |
614 | |
615 % Process text in a separate file if needed | |
616 if opts.separatetext & ~opts.applystyle | |
617 % First hide all text and export | |
618 oldtvis = LocalGetAsCell(allText,'visible'); | |
619 set(allText,'visible','off'); | |
620 oldax = LocalGetAsCell(allAxes,'XTickLabel',1); | |
621 olday = LocalGetAsCell(allAxes,'YTickLabel',1); | |
622 oldaz = LocalGetAsCell(allAxes,'ZTickLabel',1); | |
623 null = cell(length(oldax),1); | |
624 [null{:}] = deal([]); | |
625 set(allAxes,{'XTickLabel'},null); | |
626 set(allAxes,{'YTickLabel'},null); | |
627 set(allAxes,{'ZTickLabel'},null); | |
628 print(H, filename, args{:}); | |
629 set(allText,{'Visible'},oldtvis); | |
630 set(allAxes,{'XTickLabel'},oldax); | |
631 set(allAxes,{'YTickLabel'},olday); | |
632 set(allAxes,{'ZTickLabel'},oldaz); | |
633 % Now hide all non-text and export as eps in painters | |
634 [path, name, ext] = fileparts(filename); | |
635 tfile = fullfile(path,[name '_t.eps']); | |
636 tfile2 = fullfile(path,[name '_t2.eps']); | |
637 foundRenderer = 0; | |
638 for k=1:length(args) | |
639 if strncmp('-d',args{k},2) | |
640 args{k} = '-deps'; | |
641 elseif strncmp('-zbuffer',args{k},8) | ... | |
642 strncmp('-opengl', args{k},6) | |
643 args{k} = '-painters'; | |
644 foundRenderer = 1; | |
645 end | |
646 end | |
647 if ~foundRenderer | |
648 args = {args{:}, '-painters'}; | |
649 end | |
650 allNonText = [allLines; allLights; allPatch; ... | |
651 allImages; allSurf; allRect]; | |
652 oldvis = LocalGetAsCell(allNonText,'visible'); | |
653 oldc = LocalGetAsCell(allAxes,'color'); | |
654 oldaxg = LocalGetAsCell(allAxes,'XGrid'); | |
655 oldayg = LocalGetAsCell(allAxes,'YGrid'); | |
656 oldazg = LocalGetAsCell(allAxes,'ZGrid'); | |
657 [null{:}] = deal('off'); | |
658 set(allAxes,{'XGrid'},null); | |
659 set(allAxes,{'YGrid'},null); | |
660 set(allAxes,{'ZGrid'},null); | |
661 set(allNonText,'Visible','off'); | |
662 set(allAxes,'Color','none'); | |
663 print(H, tfile2, args{:}); | |
664 set(allNonText,{'Visible'},oldvis); | |
665 set(allAxes,{'Color'},oldc); | |
666 set(allAxes,{'XGrid'},oldaxg); | |
667 set(allAxes,{'YGrid'},oldayg); | |
668 set(allAxes,{'ZGrid'},oldazg); | |
669 %hack up the postscript file | |
670 fid1 = fopen(tfile,'w'); | |
671 fid2 = fopen(tfile2,'r'); | |
672 line = fgetl(fid2); | |
673 while ischar(line) | |
674 if strncmp(line,'%%Title',7) | |
675 fprintf(fid1,'%s\n',['%%Title: ', tfile]); | |
676 elseif (length(line) < 3) | |
677 fprintf(fid1,'%s\n',line); | |
678 elseif ~strcmp(line(end-2:end),' PR') & ... | |
679 ~strcmp(line(end-1:end),' L') | |
680 fprintf(fid1,'%s\n',line); | |
681 end | |
682 line = fgetl(fid2); | |
683 end | |
684 fclose(fid1); | |
685 fclose(fid2); | |
686 delete(tfile2); | |
687 | |
688 elseif ~opts.applystyle | |
689 drawnow; | |
690 print(H, filename, args{:}); | |
691 end | |
692 warning(oldwarn); | |
693 | |
694 catch | |
695 warning(oldwarn); | |
696 hadError = 1; | |
697 end | |
698 | |
699 % Restore figure settings | |
700 if opts.applystyle | |
701 varargout{1} = old; | |
702 else | |
703 for n=1:length(old.objs) | |
704 if ~iscell(old.values{n}) & iscell(old.prop{n}) | |
705 old.values{n} = {old.values{n}}; | |
706 end | |
707 set(old.objs{n}, old.prop{n}, old.values{n}); | |
708 end | |
709 end | |
710 | |
711 if hadError | |
712 error(deblank(lasterr)); | |
713 end | |
714 | |
715 % | |
716 % Local Functions | |
717 % | |
718 | |
719 function outData = LocalPushOldData(inData, objs, prop, values) | |
720 outData.objs = {objs, inData.objs{:}}; | |
721 outData.prop = {prop, inData.prop{:}}; | |
722 outData.values = {values, inData.values{:}}; | |
723 | |
724 function cellArray = LocalGetAsCell(fig,prop,allowemptycell); | |
725 cellArray = get(fig,prop); | |
726 if nargin < 3 | |
727 allowemptycell = 0; | |
728 end | |
729 if ~iscell(cellArray) & (allowemptycell | ~isempty(cellArray)) | |
730 cellArray = {cellArray}; | |
731 end | |
732 | |
733 function newArray = LocalScale(inArray, scale, minv, maxv) | |
734 n = length(inArray); | |
735 newArray = cell(n,1); | |
736 for k=1:n | |
737 newArray{k} = min(maxv,max(minv,scale*inArray{k}(1))); | |
738 end | |
739 | |
740 function gray = LocalMapToGray1(color) | |
741 gray = color; | |
742 if ischar(color) | |
743 switch color(1) | |
744 case 'y' | |
745 color = [1 1 0]; | |
746 case 'm' | |
747 color = [1 0 1]; | |
748 case 'c' | |
749 color = [0 1 1]; | |
750 case 'r' | |
751 color = [1 0 0]; | |
752 case 'g' | |
753 color = [0 1 0]; | |
754 case 'b' | |
755 color = [0 0 1]; | |
756 case 'w' | |
757 color = [1 1 1]; | |
758 case 'k' | |
759 color = [0 0 0]; | |
760 end | |
761 end | |
762 if ~ischar(color) | |
763 gray = 0.30*color(1) + 0.59*color(2) + 0.11*color(3); | |
764 end | |
765 | |
766 function newArray = LocalMapToGray(inArray); | |
767 n = length(inArray); | |
768 newArray = cell(n,1); | |
769 for k=1:n | |
770 color = inArray{k}; | |
771 if ~isempty(color) | |
772 color = LocalMapToGray1(color); | |
773 end | |
774 if isempty(color) | ischar(color) | |
775 newArray{k} = color; | |
776 else | |
777 newArray{k} = [color color color]; | |
778 end | |
779 end | |
780 | |
781 function newArray = LocalMapColorToStyle(inArray); | |
782 inArray = LocalGetAsCell(inArray,'Color'); | |
783 n = length(inArray); | |
784 newArray = cell(n,1); | |
785 styles = {'-','--',':','-.'}; | |
786 uniques = []; | |
787 nstyles = length(styles); | |
788 for k=1:n | |
789 gray = LocalMapToGray1(inArray{k}); | |
790 if isempty(gray) | ischar(gray) | gray < .05 | |
791 newArray{k} = '-'; | |
792 else | |
793 if ~isempty(uniques) & any(gray == uniques) | |
794 ind = find(gray==uniques); | |
795 else | |
796 uniques = [uniques gray]; | |
797 ind = length(uniques); | |
798 end | |
799 newArray{k} = styles{mod(ind-1,nstyles)+1}; | |
800 end | |
801 end | |
802 | |
803 function newArray = LocalMapCData(inArray); | |
804 n = length(inArray); | |
805 newArray = cell(n,1); | |
806 for k=1:n | |
807 color = inArray{k}; | |
808 if (ndims(color) == 3) & isa(color,'double') | |
809 gray = 0.30*color(:,:,1) + 0.59*color(:,:,2) + 0.11*color(:,:,3); | |
810 color(:,:,1) = gray; | |
811 color(:,:,2) = gray; | |
812 color(:,:,3) = gray; | |
813 end | |
814 newArray{k} = color; | |
815 end | |
816 | |
817 function outData = LocalUpdateColors(inArray, prop, inData) | |
818 value = LocalGetAsCell(inArray,prop); | |
819 outData.objs = {inData.objs{:}, inArray}; | |
820 outData.prop = {inData.prop{:}, {prop}}; | |
821 outData.values = {inData.values{:}, value}; | |
822 if (~isempty(value)) | |
823 if strcmp(prop,'CData') | |
824 value = LocalMapCData(value); | |
825 else | |
826 value = LocalMapToGray(value); | |
827 end | |
828 set(inArray,{prop},value); | |
829 end | |
830 | |
831 function bool = LocalIsPositiveScalar(value) | |
832 bool = isnumeric(value) & ... | |
833 prod(size(value)) == 1 & ... | |
834 value > 0; | |
835 | |
836 function value = LocalToNum(value,auto) | |
837 if ischar(value) | |
838 if strcmp(value,'auto') | |
839 value = auto; | |
840 else | |
841 value = str2num(value); | |
842 end | |
843 end | |
844 | |
845 %convert a struct to {field1,val1,field2,val2,...} | |
846 function c = LocalToCell(s) | |
847 f = fieldnames(s); | |
848 v = struct2cell(s); | |
849 opts = cell(2,length(f)); | |
850 opts(1,:) = f; | |
851 opts(2,:) = v; | |
852 c = {opts{:}}; | |
853 | |
854 function c = LocalIsHG(obj,hgtype) | |
855 c = 0; | |
856 if (length(obj) == 1) & ishandle(obj) | |
857 c = strcmp(get(obj,'type'),hgtype); | |
858 end | |
859 | |
860 function c = LocalHas3DPlot(a) | |
861 zticks = LocalGetAsCell(a,'ZTickLabel'); | |
862 c = 0; | |
863 for k=1:length(zticks) | |
864 if ~isempty(zticks{k}) | |
865 c = 1; | |
866 return; | |
867 end | |
868 end | |
869 | |
870 function r = LocalUnionRect(r1,r2) | |
871 if isempty(r1) | |
872 r = r2; | |
873 elseif isempty(r2) | |
874 r = r1; | |
875 elseif max(r2(3:4)) > 0 | |
876 left = min(r1(1),r2(1)); | |
877 bot = min(r1(2),r2(2)); | |
878 right = max(r1(1)+r1(3),r2(1)+r2(3)); | |
879 top = max(r1(2)+r1(4),r2(2)+r2(4)); | |
880 r = [left bot right-left top-bot]; | |
881 else | |
882 r = r1; | |
883 end | |
884 | |
885 function c = LocalLabelsMatchTicks(labs,ticks) | |
886 c = 0; | |
887 try | |
888 t1 = num2str(ticks(1)); | |
889 n = length(ticks); | |
890 tend = num2str(ticks(n)); | |
891 c = strncmp(labs(1),t1,length(labs(1))) & ... | |
892 strncmp(labs(n),tend,length(labs(n))); | |
893 end | |
894 | |
895 function r = LocalAxesTightBoundingBox(axesR, a) | |
896 r = []; | |
897 atext = findall(a,'type','text','visible','on'); | |
898 if ~isempty(atext) | |
899 set(atext,'units','points'); | |
900 res=LocalGetAsCell(atext,'extent'); | |
901 for n=1:length(atext) | |
902 r = LocalUnionRect(r,res{n}); | |
903 end | |
904 end | |
905 if strcmp(get(a,'visible'),'on') | |
906 r = LocalUnionRect(r,[0 0 axesR(3:4)]); | |
907 oldunits = get(a,'fontunits'); | |
908 set(a,'fontunits','points'); | |
909 label = text(0,0,'','parent',a,... | |
910 'units','points',... | |
911 'fontsize',get(a,'fontsize'),... | |
912 'fontname',get(a,'fontname'),... | |
913 'fontweight',get(a,'fontweight'),... | |
914 'fontangle',get(a,'fontangle'),... | |
915 'visible','off'); | |
916 fs = get(a,'fontsize'); | |
917 | |
918 % handle y axis tick labels | |
919 ry = [0 -fs/2 0 axesR(4)+fs]; | |
920 ylabs = get(a,'yticklabels'); | |
921 yticks = get(a,'ytick'); | |
922 maxw = 0; | |
923 if ~isempty(ylabs) | |
924 for n=1:size(ylabs,1) | |
925 set(label,'string',ylabs(n,:)); | |
926 ext = get(label,'extent'); | |
927 maxw = max(maxw,ext(3)); | |
928 end | |
929 if ~LocalLabelsMatchTicks(ylabs,yticks) & ... | |
930 strcmp(get(a,'xaxislocation'),'bottom') | |
931 ry(4) = ry(4) + 1.5*ext(4); | |
932 end | |
933 if strcmp(get(a,'yaxislocation'),'left') | |
934 ry(1) = -(maxw+5); | |
935 else | |
936 ry(1) = axesR(3); | |
937 end | |
938 ry(3) = maxw+5; | |
939 r = LocalUnionRect(r,ry); | |
940 end | |
941 | |
942 % handle x axis tick labels | |
943 rx = [0 0 0 fs+5]; | |
944 xlabs = get(a,'xticklabels'); | |
945 xticks = get(a,'xtick'); | |
946 if ~isempty(xlabs) | |
947 if strcmp(get(a,'xaxislocation'),'bottom') | |
948 rx(2) = -(fs+5); | |
949 if ~LocalLabelsMatchTicks(xlabs,xticks); | |
950 rx(4) = rx(4) + 2*fs; | |
951 rx(2) = rx(2) - 2*fs; | |
952 end | |
953 else | |
954 rx(2) = axesR(4); | |
955 % exponent is still below axes | |
956 if ~LocalLabelsMatchTicks(xlabs,xticks); | |
957 rx(4) = rx(4) + axesR(4) + 2*fs; | |
958 rx(2) = -2*fs; | |
959 end | |
960 end | |
961 set(label,'string',xlabs(1,:)); | |
962 ext1 = get(label,'extent'); | |
963 rx(1) = -ext1(3)/2; | |
964 set(label,'string',xlabs(size(xlabs,1),:)); | |
965 ext2 = get(label,'extent'); | |
966 rx(3) = axesR(3) + (ext2(3) + ext1(3))/2; | |
967 r = LocalUnionRect(r,rx); | |
968 end | |
969 set(a,'fontunits',oldunits); | |
970 delete(label); | |
971 end | |
972 | |
973 function c = LocalManualAxesMode(old, allAxes, base) | |
974 xs = ['X' base]; | |
975 ys = ['Y' base]; | |
976 zs = ['Z' base]; | |
977 oldXMode = LocalGetAsCell(allAxes,xs); | |
978 oldYMode = LocalGetAsCell(allAxes,ys); | |
979 oldZMode = LocalGetAsCell(allAxes,zs); | |
980 old = LocalPushOldData(old, allAxes, {xs}, oldXMode); | |
981 old = LocalPushOldData(old, allAxes, {ys}, oldYMode); | |
982 old = LocalPushOldData(old, allAxes, {zs}, oldZMode); | |
983 set(allAxes,xs,'manual'); | |
984 set(allAxes,ys,'manual'); | |
985 set(allAxes,zs,'manual'); | |
986 c = old; | |
987 | |
988 function val = LocalCheckAuto(val, auto) | |
989 if ischar(val) & strcmp(val,'auto') | |
990 val = auto; | |
991 end |