Code covered by the BSD License  

Highlights from
Hatchfill

4.875
4.9 | 9 ratings Rate this file 121 Downloads (last 30 days) File Size: 55.1 KB File ID: #30733 Version: 1.11
image thumbnail

Hatchfill

by

Neil Tandon (view profile)

 

13 Mar 2011 (Updated )

Fills an area with hatching or speckling.

Editor's Notes:

This file was selected as MATLAB Central Pick of the Week

| Watch this File

File Information
Description

In MATLAB, there are many functions that create regions filled with solid colors (e.g. contourf, area, bar). To do this, a function creates "patch objects" and assigns a single color to each one. Instead of a solid fill, one often wants to fill a patch with a hatch or speckle pattern instead. MATLAB has no built-in way to do this.

The hatchfill function fills patch objects with hatching or speckling. In most cases, adding hatching to a 2D plot requires only three lines of code. For example:

[c,h] = contourf(x,y,z,[0 0]);
hp = findobj(h,'type','patch');
hatchfill(hp);

This fills the zero contour with hatching. Hatchfill takes additional parameters if custom patterns are desired. This package incorporates code from Rich Pawlowicz, Iram Weinstein, and Kirill Pankratov.

Acknowledgements

Hatch.M inspired this file.

MATLAB release MATLAB 7.11 (R2010b)
Tags for This File   Please login to tag files.
Please login to add a comment or rating.
Comments and Ratings (24)
29 Jun 2015 BC

BC (view profile)

Has anyone come across this issue and found a fix:

I can fill, speckle, and outspeckle but single and cross don't work and are accompanied by the below error message:

Improper assignment with rectangular empty matrix.
Error in hatchfill (line 176)
H(j) = line(xhatch,yhatch);

All help is greatly appreciated!

Comment only
10 Apr 2015 Drecalde

For those who have problems using this for legends after 2014b update. Please consider legendflex(http://www.mathworks.com/matlabcentral/fileexchange/31092-legendflex-m--a-more-flexible--customizable-legend) for plotting.
Works like a charm.

17 Feb 2015 Linus

Linus (view profile)

How can I make this work in R2014b?
"findobj(h1, 'Type', 'patch')" does not see work on handles created by contourf (it returns an empty handle)

Comment only
24 Nov 2014 dpb

dpb (view profile)

ADDENDUM/ERRATUM -- Spoke slightly too soon...
The fixup given below _does_ solve the legend handle; it for some reason I don't yet full understand trashes the patch regions in the figure, however. Best I've done to date is to add yet another conditional...replace the calls to line() w/ the conditional

if gca==hax
H(j) = line(xhatch,yhatch);
else
H(j) = plot(hax,xhatch,yhatch);
end

Also, to prevent changes in y-scale found it necessary to clip the yhatch array returned from hatch_xy(). I put it after the call in the calling routine rather than take the time/trouble to pass the limits or handle to hatch_xy()

[xhatch,yhatch] = hatch_xy(x,y,STYL,ANGLE,SPACING);
% clip limits within the axes limits
ylm=ylim(hax);
yhatch(yhatch<ylm(1))=ylm(1);
yhatch(yhatch>ylm(2))=ylm(2);

This was necessary in my case as there were -eps or thereabouts values returned and with the lower axis at 0 for the bar chart it turned the lower axis limit to -1 instead. That's just rude... :)

Don't think it can hurt in general altho is only needed for cases like this of hatching the boundary region.

Comment only
23 Nov 2014 dpb

dpb (view profile)

R2012b doesn't draw legends correctly; not sure about earlier releases or later.

Fails owing to use of line() primitive which can't take an axis object and uses current axes by default. Can't force legend object to be current axes.

Fixup is to turn the two line() calls

H(j) = line(xhatch,yhatch,'marker','.','linest','none', ... 'markersize',specksize,'color',linec);

with

H(j) = plot(hax,xhatch,yhatch,'marker','.','linest','none', ...
'markersize',specksize,'color',linec);

Still needs the fixup of twimmeh as well, of course.

24 Oct 2014 Ben

Ben (view profile)

It would be great if there was a mapping version of Hatchfill, perhaps "Hatchfillm" for hatching "patchm" objects? Hatchfill doesn't appear to work on map axes.

Comment only
13 Mar 2014 Edward Byers

Modifications that twimmeh describes are highly recommended - thanks!

12 Sep 2013 David

David (view profile)

Very useful file, but I'm having some trouble with the speckling. I'd like to be able to fill a contour with dots, not just outline it. It would be nice if the function were able to do this by itself instead of the user having to, through trial and error.

12 Sep 2013 David

David (view profile)

 
26 Jul 2013 Taylor Sansom

After a little more editing to hatch_xy as twimmeh described, the legend looks great and the angles work fine.

Cheers!

Comment only
26 Jul 2013 Taylor Sansom

Thank you very much for this, seems to work like a charm in most applications except for the legend.

I can get the hatching in the legend by doing what twimmeh said (May 2), however the angle doesn't work when hatching in the legend. I can only get horizontal or vertical lines instead of the 45 degree angle that is on my bars.

leg=legend('1-Month','1-Year','5-Year');
legpatch=findobj(leg,'type','patch');
hatchfill(legpatch(3),'single',45,1,'blue')
hatchfill(legpatch(2),'single',45,1,'green')
hatchfill(legpatch(1),'single',45,1,'red')

Any idea how to get the 45 degree angle in the legend?

03 May 2013 Bendix

Bendix (view profile)

Seems like a really great tool but unfortunately I don't manage to get it working for the problem I needed it for:

I have a 2D-matrix of linear trends (slopes) and a logical 2D-matrix of the same size telling whether the trend is significant at position xy. Now I'd like to hatch the regions of (no) significance in a contourf or pcolor plot.
Has anyone any hint why it does not work in this case although I get it working in other cases?

Would be very grateful for help.
Cheers

Comment only
02 May 2013 twimmeh

aaaand if you want the aspect ratio of the hatch pattern to be correct you need to pass the axes handle to the hatch_xy function and replace calls to gca.

nasty, but works:

function [xi,yi,x,y]=hatch_xy(hax,x,y,varargin);
gca = hax;

(and of course updating the relevant hatch_xy call line)

Comment only
02 May 2013 twimmeh

I _believe_ the problem with legend hatching is that the lines are being drawn on the wrong axes.

If you adjust the calls to 'line' in the function to specify the axes parent then it seems to work... at least for me (R2011b).

-----------------------------------------

H(j) = line(xhatch,yhatch,'marker','.','linest','none', ...
'markersize',specksize,'color',linec,'parent',hax);

and

H(j) = line(xhatch,yhatch,'parent',hax);

-----------------------------------------

%My legend code:

hLegend = legend(...);
hp = findobj(hLegend, 'Type', 'patch');
hatchfill(hp)

This assumes you have only one patch; you need to specify hp(i) in the hatchfill call when there are multiple patches. Also, I've found you need to increase the SPACING parameter for it to look good.

22 Feb 2013 Grey Nearing

I am also curious whether it is possible to get a hatch symbol in the legend. The fix Neil suggested on Jul 17 is not working for me.

Comment only
18 Dec 2012 Neil Tandon

Neil Tandon (view profile)

Thank you Dan, I added an additional check for axes that are only one level up.

Comment only
17 Dec 2012 Dan K

Dan K (view profile)

In order for this to work for my patches (created using jbfill.m, a FileExchange script), I needed to modify line 95 because the axis handle was only one level up from the patch handle. Perhaps there should be a warning issued or some kind of additional handling if the handle two levels up is not an axis (in my case it was the figure handle).

Then this worked great! Thank you for a terrific m file!

09 Nov 2012 Bruno

Bruno (view profile)

How do I use this for 'bar'?

Comment only
09 Nov 2012 Bruno

Bruno (view profile)

@Neil and Matt: It still does not work! How do I get a hatched patch symbol in the legend?

Comment only
17 Jul 2012 Neil Tandon

Neil Tandon (view profile)

Matt - you could try something like...
h = legend('patch1','patch2');
hp = findobj(h,'type','patch');
hatchfill(hp(1));
hatchfill(hp(2));

Comment only
17 Jul 2012 Matt

Matt (view profile)

The legend doesn't work they way i'd like. for example:

figure;hold on;patch([rand(4,1)],[rand(4,1)],'r','facealpha',.2)
h = patch(rand(4,1),rand(4,1),'b');
hatchfill(h);
legend('patch1','patch2')

can you get a little hatched patch symbol in the legend?

Comment only
06 Oct 2011 Andrew

Andrew (view profile)

Great script, the latest update functions perfectly for my needs. Thank you.

25 Jul 2011 Neil Tandon

Neil Tandon (view profile)

Thanks Dmytro. I fixed this bug.

Comment only
11 Jul 2011 Dmytro Lituiev

I tried:
% =============================
f = figure;
MyColor2fade = 0.6*[1 1 1];
x0d = 3;
ulims = [1 2];
p(1) = patch([x0d,x0d,1,1],[ulims(1),ulims(2),ulims(2), ulims(1)], MyColor2fade,'EdgeColor', 'none','Parent',gca);
hatchfill(p(1))
% =============================
Result: only the left top part of the patch is hatched

Comment only
Updates
14 Mar 2011 1.1

A little housecleaning...

15 Mar 2011 1.2

Polished the examples/documentation a little.

02 Jul 2011 1.3

Now is compatible with logarithmic axes.

03 Jul 2011 1.4

Minor bug fix.

07 Jul 2011 1.5

Updated description

11 Jul 2011 1.6

Fixed bug reported by Dmytro Lituiev.

14 Jul 2011 1.7

Updated description.

15 Jul 2011 1.9

Simplified code.

08 Oct 2011 1.10

Consolidated code into single file.

19 Dec 2012 1.11

Added additional check for axes that are only one level up. (Suggested by Dan K.)

Contact us