This lesson covers four of the scaling laws available in AnyBody
- ScalingStandard (do not scale)
- ScalingUniform (scale equally in all directions; input is joint to joint distances)
- ScalingLengthMass (scale taking mass into account input is joint to joint distances and mass)
- ScalingLengthMassFat (scale taking mass and fat into account; input is joint to joint distances)
ScalingStandard
This scaling law produces a model with default parameters for mass and size (corresponding roughly to the 50th percentile European male). It is used by default for non-specific models, or when there is no data available about the modeled subject. This law does not use the AnyMan file because there is no parameter to modify.
With the AnyBody Modeling System you already have a repository of models available, for details please see the AnyBody Assistant available from the menu, so lets practice1, as a starting point for this tutorial please find the model
Application/Examples/StandingModelScalingDisplay/StandingModelScalingDisplay.main.
This tutorial has been written using the AnyBody Managed Model Repository Ver. 1.5 (AMMRV1.5) if you see differences between the tutorial text and your own results please download AMMRV1.5 from http://forge.anyscript.org/gf/project/ammr/frs/
To use this law choose the include file ScalingStandard.any in the Main file you just opened as following:
// This section below offers the choice between
// several scaling strategies
#include "<ANYBODY_PATH_BODY> \Scaling\ScalingStandard.any"
// Scaling laws using joint to joint measures
//#include "<ANYBODY_PATH_BODY>\Scaling\ScalingUniform.any"
//#include "<ANYBODY_PATH_BODY>\Scaling\ScalingLengthMass.any"
//#include "<ANYBODY_PATH_BODY>\Scaling\ScalingLengthMassFat.any"
// Scaling laws using external measures
//#include "<ANYBODY_PATH_BODY>\Scaling\ScalingUniformExt.any"
//#include "<ANYBODY_PATH_BODY>\Scaling\ScalingLengthMassExt.any"
//#include "<ANYBODY_PATH_BODY>\Scaling\ScalingLengthMassFatExt.any"
//#include "DrawExternalMeasures.any"
Scaling = {
//#include "<ANYBODY_PATH_BODY>\Scaling\AnyFamily\AnyMan.any"
//#include "<ANYBODY_PATH_BODY>\Scaling\AnyFamily\AnyManUniform.any"
//#include "<ANYBODY_PATH_BODY>\Scaling\AnyFamily\AnyManExternal.any"
//#include "<ANYBODY_PATH_BODY>\Scaling\AnyFamily\AnyManExtPercentile.any"
//#include "<ANYBODY_PATH_BODY>\Scaling\AnyFamily\AnyWomanExtPercentile.any"
};
Now load the model and open a ModelView window, you will see the standing model with the standard size.
ScalingUniform
This law allows you to define the total weight of the model and the individual sizes of the bones. The length of each bone is defined as a joint to joint distance and the bone is then scaled in three dimensions proportionally to its length. To use this law you must include the ScalingUniform.any file with the AnyMan.any file in the Main:
// This section below offers the choice between several scaling strategies
//#include "<ANYBODY_PATH_BODY>\Scaling\ScalingStandard.any"
// Scaling laws using joint to joint measures
#include "<ANYBODY_PATH_BODY>\Scaling\ScalingUniform.any"
//#include "<ANYBODY_PATH_BODY>\Scaling\ScalingLengthMass.any"
//#include "<ANYBODY_PATH_BODY>\Scaling\ScalingLengthMassFat.any"
...
Scaling = {
#include "<ANYBODY_PATH_BODY>\Scaling\AnyFamily\AnyMan.any"
//#include "<ANYBODY_PATH_BODY>\Scaling\AnyFamily\AnyManUniform.any"
...
};
AnyMan.any is the file in which you can modify the
mass and size parameters. We will now try to use it. Please
load the model and have a look at the ModelView window.
Notice that the body size did not change from the
ScalingStandard version. This is because the default values
for segment masses and sizes in this file are the same as
the standard values. But if you change them the model will
scale according to your specifications.
Double click on the line #include
"<ANYBODY_PATH_BODY>\Scaling\AnyFamily\AnyMan.any" to
open the AnyMan file and have a closer look at it. The
total body weight is expressed in kilograms by the variable
Body_Mass at the top of the file:
AnyVar Body_Mass = 75 ;
Try changing it to 90 kg and load the model again. Once again the size of the body did not change. In the ScalingUniform law, the Body_Mass parameter controls the mass of the segments but not their sizes. Further down in the AnyMan file you can see that the Body_Mass parameter is distributed to the segments according to some coefficients:
//Segment masses in kg from Winter ("Biomechanics and motor control of human movement." David A. Winter)
AnyVar lumbar = 0.139*Body_Mass; // T12-L1 to L5-Sacrum
AnyVar thorax = 0.1894*Body_Mass; // C7-T1 to T12-L1 (modified from 0.216 Winter to separate scapula)
AnyVar pelvis = 0.142*Body_Mass;
AnyVar clavicle_r = 0.0133*Body_Mass;
AnyVar upper_arm_r = 0.028*Body_Mass;
AnyVar lower_arm_r = 0.016*Body_Mass;
AnyVar hand_r = 0.006*Body_Mass;
AnyVar clavicle_l = 0.0133*Body_Mass;
AnyVar upper_arm_l = 0.028*Body_Mass;
AnyVar lower_arm_l = 0.016*Body_Mass;
AnyVar hand_l = 0.006*Body_Mass;
AnyVar head = 0.081*Body_Mass; // head and cervical
AnyVar thigh_r = 0.1*Body_Mass;
AnyVar lower_leg_r = 0.0465*Body_Mass;
AnyVar foot_r = 0.0145*Body_Mass;
AnyVar ball_r = 0.000;
AnyVar thigh_l = 0.1*Body_Mass;
AnyVar lower_leg_l = 0.0465*Body_Mass;
AnyVar foot_l = 0.0145*Body_Mass;
AnyVar ball_l = 0.000;
So the Body_Mass parameter only controls the segment masses. The size of the model is controlled by another list of variables defining the lengths of the different bones:
AnyFolder AnthroSegmentLengths = {
AnyVar ThighLength = 0.45579;
AnyVar ShankLength = 0.46;
AnyVar FootLength = 0.200771;
AnyVar PelvisWidth = 0.16;
//distance between hip joints
AnyVar HeadHeight = 0.14;
//height in neutral position from C1HatNode to top of head
AnyVar TrunkHeight = 0.620233;
//height in neutral position from C1HatNode to L5SacrumJnt
AnyVar UpperArmLength = 0.340079;
AnyVar LowerArmLength =0.2690167;
AnyVar HandLength = 0.182;
AnyVar HandBreadth = 0.085;
};
The length of each segment can be set independently, for example we can increase the length of the thigh by modifying this line:
AnyVar ThighLength = 0.626;
Load the model again and have a look at the Model View window. The femur bone is now bigger. It has been scaled uniformly in 3 directions according to the defined length. Notice that we only changed the size of the femur and not the other bones, so the femur looks unreasonably big compared to the rest of the body. To avoid results such as this it is important to feed those variables with consistent data rooted in real anthropometry.
Let us apply a more reasonable size. Please change
the default values to the following set of consistent
measures:
AnyFolder AnthroSegmentLengths = {
AnyVar ThighLength = 0.548;
AnyVar ShankLength = 0.551;
AnyVar FootLength = 0.243;
AnyVar PelvisWidth = 0.180;
//distance between hip joints
AnyVar HeadHeight = 0.169;
//height in neutral position from C1HatNode to top of head
AnyVar TrunkHeight = 0.754;
//height in neutral position fromC1HatNode to L5SacrumJnt
AnyVar UpperArmLength = 0.405;
AnyVar LowerArmLength =0.316;
AnyVar HandLength = 0.182;
AnyVar HandBreadth = 0.085;
};
When you reload the model you should see a tall body and with proportionate sizes of the segments. If you can't see the difference from the standard size model notice how the feet are now stickingdown below the reference frame.
It should be obvious that this type of scaling requires good anthropometric data to give reasonable results. But such data is not always easily available. So there is a version of the AnyMan file called AnyManUniform.any. This file only takes as input the body mass and the body height and subsequently scales all the segment lengths uniformly according to the defined body height. This may not give you a model where each bone matches a given subject, but it can be a reasonable estimate in cases where only the overall mass and height of the body is known. Try including the AnyManUniform.any file:
Scaling = {
//#include "<ANYBODY_PATH_BODY>\Scaling\AnyFamily\AnyMan.any"
#include "<ANYBODY_PATH_BODY>\Scaling\AnyFamily\AnyManUniform.any"
...
};
Now it is easy to scale the body down to represent a small person. Open the AnyManUniform file and change the mass and height variable as following:
AnyFolder AnthroData = {
AnyVar Body_Mass = 60;
AnyVar body_height = 165/100;
When you load the model you will see all the segments automatically scaling down. The mass is also scaled, but as we said previously this is not visible graphically with this scaling law.
ScalingLengthMass
This law scales the size of the body according not only to the segment lengths but also to the segments masses, so unlike the ScalingUniform law it provides the opportunity to define tall and skinny people or small and squat people. Like in the ScalingUniform law, the total body mass is defined by the variable Body_Mass. Just as previously, this total mass is then divided between the segments by means of coefficients, but the size scaling is different. Lets investigate it. In the main file, please choose the ScalingLengthMass law and switch back to the AnyMan file:
// Scaling laws using joint to joint measures
//#include "<ANYBODY_PATH_BODY>\Scaling\ScalingUniform.any"
#include "<ANYBODY_PATH_BODY>\Scaling\ScalingLengthMass.any"
//#include "<ANYBODY_PATH_BODY>\Scaling\ScalingLengthMassFat.any"
Scaling = {
#include "<ANYBODY_PATH_BODY>\Scaling\AnyFamily\AnyMan.any"
//#include "<ANYBODY_PATH_BODY>\Scaling\AnyFamily\AnyManUniform.any"
...
};
In the AnyMan file, switch back the segment length values to the initial ones and increase the body mass to 110 kg:
AnyVar Body_Mass = 110;
...
AnyFolder AnthroSegmentLengths = {
AnyVar ThighLength = 0.45579;
AnyVar ShankLength = 0.46;
AnyVar FootLength = 0.200771;
AnyVar PelvisWidth = 0.16;
//distance between hip joints
AnyVar HeadHeight = 0.14;
//height in neutral position from C1HatNode to top of head
AnyVar TrunkHeight = 0.620233;
//height in neautral position from C1HatNode to L5SacrumJnt
AnyVar UpperArmLength = 0.340079;
AnyVar LowerArmLength = 0.2690167;
AnyVar HandLength = 0.182;
AnyVar HandBreadth = 0.085;
};
Load the model and look at the ModelView. Our model looks strange! The body is deformed and looks a bit like a Neanderthal.
What really happens is that the ScalingLengthMass law scales the sizes of the segments according to their masses, but only in two directions. The third scaling direction is controlled by the segment length variables. Unlike in the ScalingUniform law, the segment length variables just control one scaling direction and not the two others.
So to have a normal-looking model we have to adjust segment mass and length simultaneously. As the mass we defined is 110 kg, a height of 1.98 m could be reasonable. As we dont have a clear idea of the individual segment lengths, we shall simply multiply all of them by a single coefficient (it is also a good opportunity to use the AnyManUniform file and directly enter the 1.98 m height, you can try it). The initial segment lengths correspond to a body of 1.80 m so the ratio we are going to multiply the segment length with is 1.1:
AnyFolder AnthroSegmentLengths = {
AnyVar ThighLength = 0.45579*1.1;
AnyVar ShankLength = 0.46*1.1;
AnyVar FootLength = 0.200771*1.1;
AnyVar PelvisWidth = 0.16*1.1;
//distance between hip joints
AnyVar HeadHeight = 0.14*1.1;
//height in neutral position from C1HatNode to top of head
AnyVar TrunkHeight = 0.620233*1.1;
//height in neautral position from C1HatNode to L5SacrumJnt
AnyVar UpperArmLength = 0.340079*1.1;
AnyVar LowerArmLength =0.2690167*1.1;
AnyVar HandLength = 0.182*1.1;
AnyVar HandBreadth = 0.085*1.1;
};
When you load the model you will see a more Homo sapiens -looking figure corresponding to a large 110kg and 1.98 m person.
We mentioned at the beginning of the tutorial that the muscle strength is also scaled. It is time to have a look at it and compare muscle forces from different scaled models. To do so we need a body with muscles. Please include the body model with muscles this way:
// Use only ONE of the three include files below at any time
// --------------------------------------------------------
// Selecting the include file below results in a body model without muscles.
// Instead, the model is equipped with joint moment providers. This version
// loads and run much faster than versions with anatomical muscles.
// #include "BodyPartsSetupGeneric.any"
// Selecting the include file below results in a body model with simple
// constant stength muscles. They are adequate for many purposes and have the
// advantage of not requiring calibration
#include "BodyPartsSetupSimpleMuscle.any"
// The include file below selects the three-element Hill-type muscles.
// They require calibration before they can be used, and this can be done
// by the HumanModel.Calibration.CalibrationSequence operation. This must
// be executed every time the model is reloaded.
//#include "BodyPartsSetupMuscle3E.any"
We also need to add some forces to model in order to make it react and see some muscle activity. This can be done by adding those lines in the Environment.any file. This piece of code creates a force of 50 N on each hand and display it in the model view:
AnyFolder EnvironmentModel = {
/* **********************************************************
This folder contains the definition of the Environment
- GlobalRefFrame
********************************************************** */
AnyFixedRefFrame GlobalRef = {
Origin ={0.0,0.0,0.0};
#include "drawcoorsystem.any"
AnyDrawRefFrame drw={};
};//GlobalRef
AnyForce3D RightHandLoad = {
F = {0, -50, 0};
AnyRefFrame &Hand = Main.HumanModel.BodyModel.Right.ShoulderArm.Seg.Glove;
};
AnyForce3D LeftHandLoad = {
F = {0, -50, 0};
AnyRefFrame &Hand = Main.HumanModel.BodyModel.Left.ShoulderArm.Seg.Glove;
};
AnyDrawVector DrawRightLoad = {
Vec = .RightHandLoad.F*0.015;
PointAway = On;
GlobalCoord = On;
Line = {
Style = Line3DStyleFull;
Thickness = 0.01;
RGB = {0, 0, 0};
End = {
Style = Line3DCapStyleArrow;
RGB = {0, 0, 0};
Thickness = 0.025;
Length = 0.025;
};
};
AnyRefFrame &Hand = .RightHandLoad.Hand;
};
AnyDrawVector DrawLeftLoad = {
Vec = .LeftHandLoad.F*0.015;
PointAway = On;
GlobalCoord = On;
Line = {
Style = Line3DStyleFull;
Thickness = 0.01;
RGB = {0, 0, 0};
End = {
Style = Line3DCapStyleArrow;
RGB = {0, 0, 0};
Thickness = 0.025;
Length = 0.025;
};
};
AnyRefFrame &Hand = .LeftHandLoad.Hand;
};
};
We are now ready to run an inverse dynamic analysis with our large 110kg model. Please load the model and run the InverseDynamicAnalysis from the operation tree. Then open a new ChartFX window to investigate the results. By browsing your way to the MaxMuscleActivity output you should get this:
We will now try to model a small person to compare his muscle activity with the one we have just plotted. In the AnyMan file lets enter the parameters for a 65kg and 1.70 m person:
AnyVar Body_Mass = 65 ;
AnyFolder AnthroSegmentLengths = {
AnyVar ThighLength = 0.45579*0.95;
AnyVar ShankLength = 0.46*0.95;
AnyVar FootLength = 0.200771*0.95;
AnyVar PelvisWidth = 0.16*0.95; //distance between hip joints
AnyVar HeadHeight = 0.14*0.95;//height in neutral position from C1HatNode to top of head
AnyVar TrunkHeight = 0.620233*0.95;//height in neutral position from C1HatNode to L5SacrumJnt
AnyVar UpperArmLength = 0.340079*0.95;
AnyVar LowerArmLength =0.2690167*0.95;
AnyVar HandLength = 0.182*0.95;
AnyVar HandBreadth = 0.085*0.95;
};
We can load the model, run a new InverseDynamicAnalysis and investigate the results in the ChartFX window.
For the same load on the hands (50 N) the tall heavy model has a muscle activity of 30.8 % whereas the short model reaches 42.3 % of muscle activity. So our small model is definitely weaker than the tall one.
ScalingLengthMassFat
Most scaled models used for practical investigations
use the ScalingLengthMassFat law. It works exactly like the
ScalingLengthMass but with an additional parameter: It
takes the fat percentage of the body into account. The
argument is that the fat percentage adds to the mass of
each segment and in the ScalingLengthMass law would lead an
estimation of more muscle tissue rather than fat tissue. So
the fat percentage in this scaling model does not modify
the mass or the size of the body. It is only used to
calculate the strength of the muscles. Between two persons
of similar segment masses, the one with higher fat
percentage will have less muscle strength because the
volume otherwise occupied by the muscles is replaced by
inactive fat.
So the mass and size scales are controlled as in the
ScalingLengthMass model by the Body_Mass variable and all
the segment length variables respectively. The fat
percentage is controlled in concert by the variables
Body_Height and Body_Mass. These two variables are used to
calculate the BMI (Body-Mass Index), and the BMI is used to
calculate the fat percentage of the body according to
Frankenfield, D. C.; Rowe, W. A.; Cooney, R. N.; Smith, J.
S. & Becker, D. (2001): Limits of body mass index to
detect obesity and predict body composition, Nutrition
17(1), 26-30.
AnyVar BMI = AnthroData.Body_Mass/(AnthroData.body_height^2);
AnyVar FatPercent = (-0.09 + 0.0149*BMI - 0.00009*BMI^2)*100;
//Estimation from Frankenfield et al. (2001) valid for men
The resulting value for the fat percentage is then directly used to compute an estimate of the strength of each muscle in the model.
This advanced strength scaling makes of course a particular difference for model that is short and heavy. The ScalingLengthMass law tends to over-estimate the strength of those models because they are often corresponding to a high fat percentage that is not taken into account by the law.
We will try to illustrate this by plotting the muscle activity of the same short and heavy model with both ScalingLengthMass and ScalingLengthMassFat laws. We will begin by adjusting the AnyMan file by to fit a 85kg and 1.70 m person:
AnyVar Body_Mass = 85;
Then please load the model and run an InverseDynamicAnalysis. Notice that we should still be using the ScalingLengthMass law. You should now get the following graph for the maximum muscle activity.
The next step is to run an analysis with the same
body but with the ScalingLengthMassFat law:
// Scaling laws using joint to joint measures
//#include "<ANYBODY_PATH_BODY>\Scaling\ScalingUniform.any"
//#include "<ANYBODY_PATH_BODY>\Scaling\ScalingLengthMass.any"
#include "<ANYBODY_PATH_BODY>\Scaling\ScalingLengthMassFat.any"
If we compare the two activity graph the difference is
clear. The ScalingLengthMassFat law is increasing the
muscle activity of almost 10 % in this case, from 31 % to
39 %. This shows the limits of the ScalingLengthMass law
for extreme cases. ScalingLengthMassFat is able to cover a
wider range of cases while keeping its accuracy.
Just like the ScalingLengthMass law this law can also be
used with the AnyManUniform file.
This completes scaling Lesson 1: Joint to joint scaling
methods.
Now move on to Lesson
2: Scaling based on external body measurements.
