20
$\begingroup$

I have a picture:

enter image description here

The sunk area is a phase,and the bulged area in another phase.I want count the proportion of this two area.this is my method.First I get the mask by Image-Tool.

enter image description here

you can download to use it.

enter image description here

gra = GradientFilter[img, 2]; ImageCompose[img, {(comp = WatershedComponents[gra, mask]) // Colorize[#, ColorRules -> {13 -> Transparent}] &, 0.6}] 

enter image description here

Then the result is appear:

ComponentMeasurements[comp, "Count"] // SortBy[#, Last] & // Values // {Total[Most[#]], Last[#]} & // #/Total[#] & // N 

{0.547061, 0.452939}

But as you see,some unsatisfactory place like this place lead to the result is imprecise.:

enter image description here

BTW,the use of Image-Tool to pick so many component is very unadvisable.Can anybody give a more smart and more precise solution?

Update:

As the @SimonWoods 's request,I process the origional picture by PhotoShop and upload it:

enter image description here

$\endgroup$
3
  • 1
    $\begingroup$ Do you have a version of the image without the text and arrows overlay? $\endgroup$ Commented Feb 13, 2016 at 14:56
  • $\begingroup$ @SimonWoods I'm sorry.This is original picture I get. $\endgroup$ Commented Feb 13, 2016 at 15:23
  • 1
    $\begingroup$ @SimonWoods I uploaded the image without the text and arrows overlay just now. $\endgroup$ Commented Feb 13, 2016 at 16:03

1 Answer 1

17
+50
$\begingroup$

Here's an idea that could work: The "Ferrite" areas have a border that's slightly darker than the background, while the area in between has a border that's slightly brighter than its neighborhood. So a filter that compares each pixel with the average brightness in the neighborhood, like an LoG filter should be a good start:

img = Import["https://i.sstatic.net/dMLH5.png"]; (log = LaplacianGaussianFilter[img, 2]) // ImageAdjust 

enter image description here

In this image, the border around the Fe-Areas is a bit lower than 0, the border around the "background" areas is a bit larger than 0, and the rest is around 0. So we can binarize this image to get the interior border:

filter = SelectComponents[#, "Length", # > 10 &] &; bin = filter@MorphologicalBinarize[log, {0.05, 0.1}] 

enter image description here

(Where I've used SelectComponents to remove some of the "noise" - you can play with additional criteria to get better results.)

And we can do the same thing with the sign flipped to get the "outer" border:

binO = filter@ MorphologicalBinarize[ImageMultiply[log, -1], {0.05, 0.1}] 

enter image description here

Now, pixels closer to the outer border are "background" pixels, and pixels closer to the inner border area "ferrite" pixels. So we simply calculate a Distance transform of the two border masks, and take the difference:

dt = DistanceTransform[ColorNegate[bin]]; dtO = DistanceTransform[ColorNegate[binO]]; (dtDiff = Image[ImageData[dtO] - ImageData[dt]]) // ImageAdjust 

enter image description here

And mark pixels with distance difference < 0

HighlightImage[img, Binarize[dtDiff, 0]] 

enter image description here

$\endgroup$
1
  • $\begingroup$ Wonderful work! $\endgroup$ Commented Feb 14, 2016 at 3:31

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.