Surface Area method for portions of segment or from landmarks

Surface Area method for portions of segment or from landmarks

OS: Windows 10Pro
Slicer version: 4.11.20210226
Data file location: Google Drive: Sign-in

I am trying to get surface area of a portion of a segment, or model. I am working with hummingbird bills and hoping to create a workflow to determine surface area of the bill. The problem is some of these CT scans are of museum birds, and the inside of the maxilla has packing material, distorting the SA. I am hoping to find a way to get just the dorsal surface area of the bill, not the intraoral space.

  1. Imported CT scans, segmented out upper mandible.

    I was able to get SA from the Segment Statistics Module, but again, I’m missing the ability to only get the upper surface of the bill.

  2. Made a model out of the segment

    Again, could get SA here, but for the whole model.

  3. Used PseudoLM Module to create landmarks using a template.

  4. Created a open curve using Markups Module to make a border of the bill so landmark vertices included area of interest. Added those points to my landmark control point list.

  5. Get Surface area from these landmarks? This is where I’m hoping for some input. Perhaps it can even be done back in segment editor. I also considered “filling” the bill with a plane, getting the SA of that and then merging with the model, subtract ting that SA and getting the bill SA, but not sure how I’d execute that.

Thank you for any input!

As I understand you only want the SA of the dorsal (top) of the bill? Is that correct?

Probably the simplest solution is to use the Surface Cut effect in Segment editor, cut out the portion you want to retain via using closed curve markup, and then use the Segment Statistics module to calculate the SA.

Alternatively, there is a new markup type called patchMarkup available as a separate extension. I have not tried that, but that might give you an option of placing a patch over the region you want to measure.

Hi @muratmaga, thanks for the prompt reply.

So I would:

  1. Isolate the upper bill with Surface cut (directly from CT scan?) >
  2. Use closed curve to choose the area on the segment I’d like to keep (line along the edge of the bill to circle around the dorsal side of the bill). Btw can I constrain a resampled closed curve to the surface of a segment, or only a model?>
  3. Measure the SA of that segment that falls within the closed curve? (I don’t see an option in segment statistics to use a closed curve as the source for the SA.

Maybe I’m missing something here and the closed curve is to portion out a new segment from the entire bill segment, in which case, which module would I use?

Thank you!

@muratmaga I did find a potential solution to my own question for 3 using the second code chunk that Andras gave in this link.

Attached is what it looks like it’s measuring, which is within the closed curve, but is unfortunately the under side of the bill.

It also seems like it’s adding a “cap” here, to the end of the bill, which might resolve when we’re measuring the dorsal area

Is there a way to change which surface of the segment it is measuring. Has there has been an updated method to do this beyond the Python console?


If you use a Closed Curve, the surface area is available right away in the Markups module. It seems that’s what you are looking for, right ?

I am not sure why it is recapping only a portion of the closed surface. As I recall it should visualize entire area that’s encompassed by the curve, and that’s where the SA comes from.

Your issue is you want the outer surface of the bill, but all your points on the curve is roughly coplanar, and only covers the inner side. You won’t be able to do that with this approach. That’s why I think new surfaceMarkup type (which allows you draw a surface patch, as opposed to a curve) will be more flexible and usable. Here is an example. The gray is the surface patch generated by this 3x3 grid, and it follows the curvature of the skull roof closely.

The issue is it looks like measurement calculations are not enabled for this markup type. @lassoan @RafaelPalomar is that correct, or do I have an old version?

If you search for surfaceMarkup extension in a recent preview version, you can experiment with it.

Otherwise, I think the surface cut in segment editor would work too.

More or less I think until step 3 you are on your way.

You could use this tool New Dynamic Modeler Tool: Select by Points to extract the surface

Then use the this filter VTK: vtkMassProperties Class Reference to calculate the surface area.

Also try to take a look at how the surface area calculation is implemented on the Models module of Slicer as I think you may need to preprocess your input with the triangle filter with some non-default option

Or you could just simply check the surface area of the (cropped) selectByPointsModel on the information panel of the Models module. I think that would be enough

Hope it helps

@chir.set I didn’t know I could get this data from a closed curve in markups— thank you!

@muratmaga This worked pretty well too. Here is my original segment, with a new segment of the surface, whose points I modified in both 3D and 3D views.

This is what the segment looks like:

I am curious when I measure in Segment Statistics, it looks like this segment is more of a modified cylinder than planar.

That makes me wonder if it measuring the SA of this whole column. Is there a setting I can use to make this more planar and only measure the SA of the dorsal side of the bill from this segment cut? Perhaps this is just what happens when I’m measuring a curved surface where the points do not exist on one consistent plane longitudinally.

@muratmaga I was able to replicate your point locations, more or less, with the surfaceMarkup method.

I am having trouble constraining the points to the model. I have attached a screen shot of what my settings are. I’m wondering if it is something with my projection distance, or something limiting it from “snapping” to my model. Would love any input on this with the sample data, then I’ll try it on the bill.

I tried the method you outlined. From a model, I was able to use the dynamic modeler to create a new model from selected points

The issue is, because there are other surfaces within my sphere size (0.5), I am getting multiple surfaces from this method

Model SA measurements work great, but having trouble with this as it is likely giving me SA of all these surfaces.
Let me know if you have any thoughts to pursue this method. I think Murat has some other ideas too, I’m trying them all right now to create a helpful workflow.

I really appreciate the help!

I think you could change the algorithm to ‘geodesic’ on the selectByPoints tool options to avoid the problem you show.

Let me know if you achieve it

Points will snap to the surface once they are close enough. Most of your points are currently inside the model. Turn the model so that you are seeing lateral view approximately, Turn off the model, and drag the points that are inside the skull such that they are way outside, then reposition them. Particularly the ones that are in the middle of the patch.

@muratmaga This helped with getting the points on the surface, thank you! It looks like I can start with a small grid, then “resample” with a larger grid to get more points and adjust them to the surface. I assume when this is a stable release the SA measurements might be available?

@mau_igna_06 Geodesic did help! Thank you. The only small barrier I still have is getting the circles around the points to go to the edge of the bill, but not spill into the intraoral space (currently looks “scalloped” on the edge. Still multitudes better than the other methods I’ve been trying, but let me know if you have any thoughts there.

The dynamic modeler tool is based on a vtk geodesic filter.

There is the option “exclusion region” that you could use around your area of interest drawn with a markups closed curve. You just need to put a seed point inside it using a fiducial.
You just need to use the filter inside Slicer on python by slicer.vtkFastMarchingGeodesicFilter and set the proper inputs by converting the data. You should be able to get your surface of interest extracted and then assing it to a model, after that you can check on the Models module the surface area.

If you need more help you can contact me privately and I think I could work on a reusable script for this

I don’t know the answer to that. Maybe @lassoan @RafaelPalomar can tell if and when that would be available.

Use the latest Slicer Preview Release, as it contains many fixes and improvements that you’ll need.

I would recommend the following steps:

  • Make your segment solid (get rid of internal holes due to air and packing material) to make all subsequent processing steps faster and more robust. You can use SurfaceWrapSolidify extension for this.
  • Export the segmentation to a model. Segmentation is always a closed surface, so segment statistics would provide the surface area as the sum of the upper beak + lower beak + capping, which would not be useful. If you export the segmentation to a model then you can trim the surface model to the surface region that you want to measure.
  • Separate the lower and upper beak and remove the capping using Dynamic modeler module. The best is to use the Curve cut tool as it allows you to draw the boundary using a couple of control points, so the edge will be clean and straight. You can constrain the cutting curve to the model (in Markups module → Curve settings → Constrain to model → select the model exported from the segmentation) to make editing easier. For fine-tuning the curve you may resample the control points at equal distances along the curve (Markups module → Resample).
  • Go to Models module → Information section to get the surface area.

@lassoan This workflow is fantastic for my project, thank you! I just successfully created a model of the dorsal surface of this bill. Thanks to you all for the catered help, I really appreciate this forum and learning some new tools.

1 Like