Skip to main content
added 12 characters in body
Source Link
Carl Lange
  • 13.2k
  • 1
  • 38
  • 70

First, let's get the scale bar out of the image. There are a few ways to do this (MorphologicalBinarize and friends), but I went with the more eye-bally approach of using ColorReplace. Here, we're replacing black pixels with white, and all other pixels with black, to get a mask. Note that ColorReplace has a third argument d, which you could use to fine-tune what it sees as "black".

i = Import["https://i.sstatic.net/yR6UY.gif"]

c = ColorReplace[i, {Black -> White, _ -> Black}]

enter image description here

Compare with a simple MorphologicalBinarize - the choice is yours:

enter image description here

Now we can get the bounding box of our rectangle, and simply take the difference:

box = ComponentMeasurements[c, "BoundingBox"][[1, 2]]

Differences /@ Transpose@box

box = ComponentMeasurements[c, "BoundingBox"][[1, 2]]

Differences /@ Transpose@box

{{38.}, {5.}}

So the longest dimension of our bounding box is 38 pixels long, and the short side is 5 pixels long.

Just to check, I counted the pixels another way, using SequenceCases on our replaced image, and each line of 1s, the pixels of the scale bar, had a length of 38.

SequenceCases[
 Flatten@MorphologicalComponents[c], {p : Repeated[1]} :> Length@{p}]

{38, 38, 38, 38, 38}

Either way, we get about 38 pixels, so now we know the length of the bar, and thus we can get the size of a pixel (assuming pixels are square here).

pixelLength = Quantity[3, "Microns"] / 38

Quantity[0.0789474, "Microns"]

and now if we get the Euclidean distance between your points and multiply it by our pixel length, we get the distance in microns.

EuclideanDistance[{5.5, 39.5}, {13.9828, 37.5345}] * pixelLength

Quantity[0.687437, "Microns"]

This answer will not hold up well if the bar is not always aligned perfectly to the image border, as it is in your test image. You could consider ComponentMeasurements[c, "Length"] or "CaliperLength" to get the length of the bar instead in that case. However, it may take the distances between opposite corners of the bar, which may not be what you want.

First, let's get the scale bar out of the image. There are a few ways to do this (MorphologicalBinarize and friends), but I went with the more eye-bally approach of using ColorReplace. Here, we're replacing black pixels with white, and all other pixels with black, to get a mask. Note that ColorReplace has a third argument d, which you could use to fine-tune what it sees as "black".

i = Import["https://i.sstatic.net/yR6UY.gif"]

c = ColorReplace[i, {Black -> White, _ -> Black}]

enter image description here

Compare with a simple MorphologicalBinarize - the choice is yours:

enter image description here

Now we can get the bounding box of our rectangle, and simply take the difference:

box = ComponentMeasurements[c, "BoundingBox"][[1, 2]]

Differences /@ Transpose@box

{{38.}, {5.}}

So the longest dimension of our bounding box is 38 pixels long, and the short side is 5 pixels long.

Just to check, I counted the pixels another way, using SequenceCases on our replaced image, and each line of 1s, the pixels of the scale bar, had a length of 38.

SequenceCases[
 Flatten@MorphologicalComponents[c], {p : Repeated[1]} :> Length@{p}]

{38, 38, 38, 38, 38}

Either way, we get about 38 pixels, so now we know the length of the bar, and thus we can get the size of a pixel (assuming pixels are square here).

pixelLength = Quantity[3, "Microns"] / 38

Quantity[0.0789474, "Microns"]

and now if we get the Euclidean distance between your points and multiply it by our pixel length, we get the distance in microns.

EuclideanDistance[{5.5, 39.5}, {13.9828, 37.5345}] * pixelLength

Quantity[0.687437, "Microns"]

This answer will not hold up well if the bar is not always aligned perfectly to the image border, as it is in your test image. You could consider ComponentMeasurements[c, "Length"] or "CaliperLength" to get the length of the bar instead in that case. However, it may take the distances between opposite corners of the bar, which may not be what you want.

First, let's get the scale bar out of the image. There are a few ways to do this (MorphologicalBinarize and friends), but I went with the more eye-bally approach of using ColorReplace. Here, we're replacing black pixels with white, and all other pixels with black, to get a mask. Note that ColorReplace has a third argument d, which you could use to fine-tune what it sees as "black".

i = Import["https://i.sstatic.net/yR6UY.gif"]

c = ColorReplace[i, {Black -> White, _ -> Black}]

enter image description here

Compare with a simple MorphologicalBinarize - the choice is yours:

enter image description here

Now we can get the bounding box of our rectangle, and simply take the difference:

box = ComponentMeasurements[c, "BoundingBox"][[1, 2]]

Differences /@ Transpose@box

{{38.}, {5.}}

So the longest dimension of our bounding box is 38 pixels long, and the short side is 5 pixels long.

Just to check, I counted the pixels another way, using SequenceCases on our replaced image, and each line of 1s, the pixels of the scale bar, had a length of 38.

SequenceCases[
 Flatten@MorphologicalComponents[c], {p : Repeated[1]} :> Length@{p}]

{38, 38, 38, 38, 38}

Either way, we get about 38 pixels, so now we know the length of the bar, and thus we can get the size of a pixel (assuming pixels are square here).

pixelLength = Quantity[3, "Microns"] / 38

Quantity[0.0789474, "Microns"]

and now if we get the Euclidean distance between your points and multiply it by our pixel length, we get the distance in microns.

EuclideanDistance[{5.5, 39.5}, {13.9828, 37.5345}] * pixelLength

Quantity[0.687437, "Microns"]

This answer will not hold up well if the bar is not always aligned perfectly to the image border, as it is in your test image. You could consider ComponentMeasurements[c, "Length"] or "CaliperLength" to get the length of the bar instead in that case. However, it may take the distances between opposite corners of the bar, which may not be what you want.

added 23 characters in body
Source Link
Carl Lange
  • 13.2k
  • 1
  • 38
  • 70

First, let's get the scale bar out of the image. There are a few ways to do this (MorphologicalBinarize and friends), but I went with the more eye-bally approach of using ColorReplace. Here, we're replacing black pixels with white, and all other pixels with black, to get a mask. Note that ColorReplace has a third argument d, which you could use to fine-tune what it sees as "black".

i = Import["https://i.sstatic.net/yR6UY.gif"]

c = ColorReplace[i, {Black -> White, _ -> Black}]

enter image description here

Compare with a simple MorphologicalBinarize - the choice is yours:

enter image description here

And nowNow we can simply get the ComponentMeasurementsbounding box of the single component we have in our resulting imagerectangle, and simply take the difference:

ComponentMeasurements[c, "CaliperLength"]

box = ComponentMeasurements[c, "BoundingBox"][[1, 2]]

Differences /@ Transpose@box

{1 -> {38.3275}, {5.}}

I'll be honest with youSo the longest dimension of our bounding box is 38 pixels long, I'm not quite sure why there's any numbers afterand the decimal hereshort side is 5 pixels long. 

Just to check, I counted the pixels another way, using SequenceCases on our replaced image, and each line of 1s, the pixels of the scale bar, had a length of 38.

SequenceCases[
 Flatten@MorphologicalComponents[c], {p : Repeated[1]} :> Length@{p}]

{38, 38, 38, 38, 38}

Either way, we get about 38 pixels, so now we know the length of the bar, and thus we can get the size of a pixel (assuming pixels are square here).

pixelLength = Quantity[3, "Microns"] / 38

Quantity[0.0789474, "Microns"]

and now if we get the Euclidean distance between your points and multiply it by our pixel length, we get the distance in microns.

EuclideanDistance[{5.5, 39.5}, {13.9828, 37.5345}] * pixelLength

Quantity[0.687437, "Microns"]

This answer will not hold up well if the bar is not always aligned perfectly to the image border, as it is in your test image. You could consider ComponentMeasurements[c, "Length"] or "CaliperLength" to get the length of the bar instead in that case. However, it may take the distances between opposite corners of the bar, which may not be what you want.

First, let's get the scale bar out of the image. There are a few ways to do this (MorphologicalBinarize and friends), but I went with the more eye-bally approach of using ColorReplace. Here, we're replacing black pixels with white, and all other pixels with black, to get a mask. Note that ColorReplace has a third argument d, which you could use to fine-tune what it sees as "black".

i = Import["https://i.sstatic.net/yR6UY.gif"]

c = ColorReplace[i, {Black -> White, _ -> Black}]

enter image description here

Compare with a simple MorphologicalBinarize - the choice is yours:

enter image description here

And now we can simply get the ComponentMeasurements of the single component we have in our resulting image:

ComponentMeasurements[c, "CaliperLength"]

{1 -> 38.3275}

I'll be honest with you, I'm not quite sure why there's any numbers after the decimal here. Just to check, I counted the pixels another way, using SequenceCases on our replaced image, and each line of 1s, the pixels of the scale bar, had a length of 38.

SequenceCases[
 Flatten@MorphologicalComponents[c], {p : Repeated[1]} :> Length@{p}]

{38, 38, 38, 38, 38}

Either way, we get about 38 pixels, so now we know the length of the bar, and thus we can get the size of a pixel (assuming pixels are square here).

pixelLength = Quantity[3, "Microns"] / 38

Quantity[0.0789474, "Microns"]

and now if we get the Euclidean distance between your points and multiply it by our pixel length, we get the distance in microns.

EuclideanDistance[{5.5, 39.5}, {13.9828, 37.5345}] * pixelLength

Quantity[0.687437, "Microns"]

First, let's get the scale bar out of the image. There are a few ways to do this (MorphologicalBinarize and friends), but I went with the more eye-bally approach of using ColorReplace. Here, we're replacing black pixels with white, and all other pixels with black, to get a mask. Note that ColorReplace has a third argument d, which you could use to fine-tune what it sees as "black".

i = Import["https://i.sstatic.net/yR6UY.gif"]

c = ColorReplace[i, {Black -> White, _ -> Black}]

enter image description here

Compare with a simple MorphologicalBinarize - the choice is yours:

enter image description here

Now we can get the bounding box of our rectangle, and simply take the difference:

box = ComponentMeasurements[c, "BoundingBox"][[1, 2]]

Differences /@ Transpose@box

{{38.}, {5.}}

So the longest dimension of our bounding box is 38 pixels long, and the short side is 5 pixels long. 

Just to check, I counted the pixels another way, using SequenceCases on our replaced image, and each line of 1s, the pixels of the scale bar, had a length of 38.

SequenceCases[
 Flatten@MorphologicalComponents[c], {p : Repeated[1]} :> Length@{p}]

{38, 38, 38, 38, 38}

Either way, we get about 38 pixels, so now we know the length of the bar, and thus we can get the size of a pixel (assuming pixels are square here).

pixelLength = Quantity[3, "Microns"] / 38

Quantity[0.0789474, "Microns"]

and now if we get the Euclidean distance between your points and multiply it by our pixel length, we get the distance in microns.

EuclideanDistance[{5.5, 39.5}, {13.9828, 37.5345}] * pixelLength

Quantity[0.687437, "Microns"]

This answer will not hold up well if the bar is not always aligned perfectly to the image border, as it is in your test image. You could consider ComponentMeasurements[c, "Length"] or "CaliperLength" to get the length of the bar instead in that case. However, it may take the distances between opposite corners of the bar, which may not be what you want.

Source Link
Carl Lange
  • 13.2k
  • 1
  • 38
  • 70

First, let's get the scale bar out of the image. There are a few ways to do this (MorphologicalBinarize and friends), but I went with the more eye-bally approach of using ColorReplace. Here, we're replacing black pixels with white, and all other pixels with black, to get a mask. Note that ColorReplace has a third argument d, which you could use to fine-tune what it sees as "black".

i = Import["https://i.sstatic.net/yR6UY.gif"]

c = ColorReplace[i, {Black -> White, _ -> Black}]

enter image description here

Compare with a simple MorphologicalBinarize - the choice is yours:

enter image description here

And now we can simply get the ComponentMeasurements of the single component we have in our resulting image:

ComponentMeasurements[c, "CaliperLength"]

{1 -> 38.3275}

I'll be honest with you, I'm not quite sure why there's any numbers after the decimal here. Just to check, I counted the pixels another way, using SequenceCases on our replaced image, and each line of 1s, the pixels of the scale bar, had a length of 38.

SequenceCases[
 Flatten@MorphologicalComponents[c], {p : Repeated[1]} :> Length@{p}]

{38, 38, 38, 38, 38}

Either way, we get about 38 pixels, so now we know the length of the bar, and thus we can get the size of a pixel (assuming pixels are square here).

pixelLength = Quantity[3, "Microns"] / 38

Quantity[0.0789474, "Microns"]

and now if we get the Euclidean distance between your points and multiply it by our pixel length, we get the distance in microns.

EuclideanDistance[{5.5, 39.5}, {13.9828, 37.5345}] * pixelLength

Quantity[0.687437, "Microns"]