I am pretty new to modelica. I would like to model a rigid body (as a long cylinder), with a point mass attached to it via a spring.
Imagine the body-fixed frame of the rigid body, where the x-axis is the long axis of the cylinder. The slosh mass should be constrained to translate only in the y-z plane.
How can I model this system in modelica using the standard library?
For reference, here is my attempt (does not build). Thank you.
model RigidBody6DOFWithSpring
// Parameters
parameter Real mass_slosh = 90; // Mass of a single slosh mass
parameter Real springStiffness = 1e4; // Spring stiffness
parameter Real springRestLength = 1; // Spring rest length
// Rigid body properties
parameter Real mass_rigid = 10; // Mass of the rigid body
parameter Modelica.Units.SI.Position r_CM[3](start={4,0,0});
parameter Modelica.Units.SI.Inertia Ixx = 100;
parameter Modelica.Units.SI.Inertia Iyy = 100;
parameter Modelica.Units.SI.Inertia Izz = Iyy;
// Model a world with no gravity
inner Modelica.Mechanics.MultiBody.World world(g=0);
// Rocket structure
Modelica.Mechanics.MultiBody.Parts.Body rigidBody(m=mass_rigid,
r_CM = r_CM,
cylinderDiameter = 0.0, // Disable vis
sphereDiameter=0.5, // Disable vis
I_11 = Ixx,
I_22 = Iyy,
I_33 = Izz);
// Joints to constrain point mass motion to body frame y-z motion only
import Modelica.Mechanics.MultiBody.Joints;
Joints.Constraints.Prismatic slosh1_constraint(
x_locked=true,
y_locked=false,
z_locked=false);
// Point masses
parameter Real slosh1_x = 8;
Modelica.Mechanics.MultiBody.Parts.Body sloshMass1(m=mass_slosh,
sphereDiameter=1);
Modelica.Mechanics.MultiBody.Forces.Spring spring1(c=springStiffness,
s_unstretched=springRestLength);
Modelica.Mechanics.MultiBody.Parts.FixedTranslation attachmentPoint1(
r={slosh1_x,0,0}
);
initial equation
// Initial rigid body state
rigidBody.w_0_start = {0, 0, 0};
// Initial slosh positions in world space
sloshMass1.r_0 = {slosh1_x, 0, 0};
// Spring lengths
spring1.length = 2;
equation
// Define translation of spring mounting frame w.r.t rigid body frame
connect(rigidBody.frame_a, attachmentPoint1.frame_a);
connect(spring1.frame_a, attachmentPoint1.frame_b);
connect(spring1.frame_b, sloshMass1.frame_a);
connect(slosh1_constraint.frame_a, rigidBody.frame_a);
connect(slosh1_constraint.frame_b, sloshMass1.frame_a);
connect(slosh1_constraint.frame_b, attachmentPoint1.frame_b);
connect(slosh1_constraint.frame_b, spring1.frame_b);
end RigidBody6DOFWithSpring;
I'm not sure if I correctly understood what you would want to build, but here are some remarks for your model:
Modelica.Mechanics.MultiBody.Joints.Constraints.Prismatic
is not used to constrain the movement in one direction. It is rather used in "complex multibody systems with closed loops this may help to simplify the system of non-linear equations" (from the documentation of the model). Comparably simple examples can be found here: Modelica.Mechanics.MultiBody.Examples.Constraints
.From you description I have built the following:
The resulting animation is the this:
Note that the point-mass is not constrained to a movement on the y-z-plane.
Here is the code (including the annotations for graphical description etc.):
model ZylinderSpringMass
Modelica.Mechanics.MultiBody.Joints.Planar planar(
animation=false,
n(displayUnit="1") = {1,0,0},
n_x(displayUnit="1") = {0,1,0}) annotation (Placement(transformation(extent={{-10,-10},{10,10}})));
Modelica.Mechanics.MultiBody.Parts.Fixed fixed annotation (Placement(transformation(extent={{-40,-10},{-20,10}})));
Modelica.Mechanics.MultiBody.Parts.BodyCylinder bodyCylinder(
r={0.5,0,0},
r_shape={-0.5,0,0},
r_0(start={0,-0.1,-0.1}, fixed=true)) annotation (Placement(transformation(extent={{40,-10},{60,10}})));
inner Modelica.Mechanics.MultiBody.World world(n(displayUnit="1") = {-1,0,0})
annotation (Placement(transformation(extent={{-40,40},{-20,60}})));
Modelica.Mechanics.MultiBody.Parts.Body body(
r_CM={0,0,0},
m=3,
r_0(fixed=true, start={0,0.1,0}),
v_0(fixed=true, start={0,0,1})) annotation (Placement(transformation(extent={{40,30},{60,50}})));
Modelica.Mechanics.MultiBody.Forces.Spring spring(c=100)
annotation (Placement(transformation(
extent={{-10,-10},{10,10}},
rotation=90,
origin={20,20})));
equation
connect(fixed.frame_b, planar.frame_a)
annotation (Line(
points={{-20,0},{-10,0}},
color={95,95,95},
thickness=0.5));
connect(bodyCylinder.frame_a, planar.frame_b)
annotation (Line(
points={{40,0},{10,0}},
color={95,95,95},
thickness=0.5));
connect(spring.frame_a, planar.frame_b)
annotation (Line(
points={{20,10},{20,0},{10,0}},
color={95,95,95},
thickness=0.5));
connect(spring.frame_b, body.frame_a)
annotation (Line(
points={{20,30},{20,40},{40,40}},
color={95,95,95},
thickness=0.5));
annotation (
Icon(coordinateSystem(preserveAspectRatio=false)),
Diagram(coordinateSystem(preserveAspectRatio=false)),
uses(Modelica(version="4.0.0")),
experiment(
StopTime=3,
Interval=0.001,
__Dymola_Algorithm="Dassl"));
end ZylinderSpringMass;
Not sure if that does what you need, but it should be a starting point at least.
Note: I have built that using Dymola 2024x, assuming it will work in other tools as well, as it does only use standard components...