Hello,
thank you so much for the help, in the end I opted for the implementation
via the earthquake demo and it seems to work.
I have a few more questions:
- I need to not start the sinusoidal pulse immediately at the beginning
of the simulation but instead I would like the particles to have a certain
settling time before they start oscillating, how could I do this? I've
found something about ChFunction commands but I'm not sure how to go about
it.
- Then I'd like to analyze the ascent of a specific particle that I
define as an intruder, I'd need an array of data about its height relative
to the reference plane over time so that I can then plot it as various
physical parameters change. For this purpose I thought of defining a .csv
file to collect the data but I am not sure how to include it in the
simulation loop. Is there a better method for doing this? Is there a need
for the postprocessing module?
I enclose a copy of my script if it can be useful.
Thank you in advance.
~Alessio
Il giorno venerdì 14 giugno 2024 alle 16:36:57 UTC+2 Radu Serban ha scritto:
> You can use a linear motor with whatever activation function you want (at
> position, velocity, or force level). See demo_MBS_motors for examples.
> Alternatively, you can use a weld joint (ChLinkLockLock) which allows
> specifying a motion function along one of the constrained DOFs. See
> demo_MBS_earthquake.
>
> In either case, you would connect one of the “links” above between the box
> and the fixed ground body.
>
>
>
> --Radu
>
>
>
> *From:* [email protected] <[email protected]> *On
> Behalf Of *Alessio
> *Sent:* Friday, June 14, 2024 9:03 AM
> *To:* ProjectChrono <[email protected]>
> *Subject:* [chrono] Implementation of a vibrating system
>
>
>
> Hello everyone,
>
>
>
> I'm trying to simulate the behaviour of different non-spherical particles
> under varying gravity and some physical parameters like friction and
> restitution coefficients. I've modelled an open cubic container for the
> particles which rests on a reference floor which is fixed. I should now
> implement horizontal oscillations, in particular I was thinking about
> sinusoidal inputs. What could be the best way to do it? I was thinking of
> implementing an engine or a prismatic link to which the sinusoidal forcing
> is added, but I'm not sure if these are the best choices, as I am new to
> using Chrono. Also, I am undecided whether to make the reference floor move
> and then vibrate the box or to implement it directly on it, depending on
> which is the easiest way.
>
>
>
> Thanks to anyone who can give me some advice.
>
> --
> You received this message because you are subscribed to the Google Groups
> "ProjectChrono" group.
> To unsubscribe from this group and stop receiving emails from it, send an
> email to [email protected].
> To view this discussion on the web visit
> https://groups.google.com/d/msgid/projectchrono/2ca55747-33ae-4943-884b-29946a3430a5n%40googlegroups.com
>
> <https://urldefense.com/v3/__https:/groups.google.com/d/msgid/projectchrono/2ca55747-33ae-4943-884b-29946a3430a5n*40googlegroups.com?utm_medium=email&utm_source=footer__;JQ!!Mak6IKo!Ik1vQnrkR3RzjC9YLd42xcxafm2q5_1GWpjPZ2bHbDXwlQ7XmFzXdIQVaKIO-p9lTYDbAGcFO19zBddc3hzu_mHDXg$>
> .
>
--
You received this message because you are subscribed to the Google Groups
"ProjectChrono" group.
To unsubscribe from this group and stop receiving emails from it, send an email
to [email protected].
To view this discussion on the web visit
https://groups.google.com/d/msgid/projectchrono/a6733f1f-645c-4047-8d2c-0a09e46db5c0n%40googlegroups.com.
#include "chrono/physics/ChSystemNSC.h"
#include "chrono/physics/ChBodyEasy.h"
#include "chrono/assets/ChTexture.h"
#include "chrono/core/ChRealtimeStep.h"
#include "chrono/core/ChRandom.h"
#include "chrono/functions/ChFunctionSine.h"
#ifdef CHRONO_COLLISION
#include "chrono/collision/multicore/ChCollisionSystemMulticore.h"
#endif
#ifdef CHRONO_IRRLICHT
#include "chrono_irrlicht/ChVisualSystemIrrlicht.h"
using namespace chrono::irrlicht;
#endif
#ifdef CHRONO_VSG
#include "chrono_vsg/ChVisualSystemVSG.h"
using namespace chrono::vsg3d;
#endif
using namespace chrono;
ChVisualSystem::Type vis_type = ChVisualSystem::Type::VSG;
ChCollisionSystem::Type collision_type = ChCollisionSystem::Type::BULLET;
// Setting of the falling items
void AddFallingItems(ChSystemNSC& sys) {
// Generation of fixed-size intruders
auto intr_mat = chrono_types::make_shared<ChContactMaterialNSC>();
intr_mat->SetFriction(0.2f);
intr_mat->SetRollingFriction(0.2f);
intr_mat->SetRestitution(0.3f);
/* for (int bi = 0; bi < 7; bi++) {*/
auto intrBody = chrono_types::make_shared<ChBodyEasySphere>(0.7, 800,
intr_mat);
/*auto intrBody =
chrono_types::make_shared<ChBodyEasyCylinder>(ChAxis::Y,1.1, 1.1, 800.0, true,
true, intr_mat);*/
intrBody->SetPos(ChVector3d(-2.5 + ChRandom::Get() * 5, 1.2, -2.5 +
ChRandom::Get() * 5));
intrBody->GetVisualShape(0)->SetColor(ChColor(0.2f, 0.5f, 0.25f));
sys.Add(intrBody);
/* }*/
// Random generation of regular particles
int num_points = 10; // No. of points for each polyhedron
for (int bi = 0; bi < 1000; bi++) {
std::vector<ChVector3d> points;
for (int i = 0; i < num_points; ++i) {
double x = ChRandom::Get();
double y = ChRandom::Get();
double z = ChRandom::Get();
points.push_back(ChVector3d(x, y, z));
}
auto sph_mat = chrono_types::make_shared<ChContactMaterialNSC>();
sph_mat->SetFriction(0.2f);
auto sphereBody =
chrono_types::make_shared<ChBodyEasyConvexHull>(points, 1000, sph_mat);
sphereBody->SetPos(ChVector3d(-2.5 + ChRandom::Get() * 5, 1 + bi *
0.05, -2.5 + ChRandom::Get() * 5));
sphereBody->GetVisualShape(0)->SetColor(ChColor(0.8f, 0.8f, 0.0f));
sys.Add(sphereBody);
}
}
// Setting of the container and vibrating system
std::shared_ptr<ChBody> AddContainer(ChSystemNSC& sys) {
// Contact and visualization materials for container
auto ground_mat = chrono_types::make_shared<ChContactMaterialNSC>();
auto ground_mat_vis =
chrono_types::make_shared<ChVisualMaterial>(*ChVisualMaterial::Default());
ground_mat_vis->SetKdTexture(GetChronoDataFile("textures/concrete.jpg"));
// Create the five walls of the rectangular container, using fixed rigid
bodies of 'box' type
auto floorBody = chrono_types::make_shared<ChBodyEasyBox>(10, 1, 10, 1000,
ground_mat);
floorBody->SetPos(ChVector3d(0, -3, 0));
floorBody->SetFixed(false);
floorBody->GetVisualShape(0)->SetMaterial(0, ground_mat_vis);
sys.Add(floorBody);
auto wallBody1 = chrono_types::make_shared<ChBodyEasyBox>(1, 12, 10.48,
1000, ground_mat);
wallBody1->SetPos(ChVector3d(-5, 0, 0));
wallBody1->SetFixed(false);
wallBody1->GetVisualShape(0)->SetMaterial(0, ground_mat_vis);
sys.Add(wallBody1);
auto wallBody2 = chrono_types::make_shared<ChBodyEasyBox>(1, 12, 10.48,
1000, ground_mat);
wallBody2->SetPos(ChVector3d(5, 0, 0));
wallBody2->SetFixed(false);
wallBody2->GetVisualShape(0)->SetMaterial(0, ground_mat_vis);
sys.Add(wallBody2);
auto wallBody3 = chrono_types::make_shared<ChBodyEasyBox>(10.48, 12, 1,
1000, ground_mat);
wallBody3->SetPos(ChVector3d(0, 0, -5));
wallBody3->SetFixed(false);
wallBody3->GetVisualShape(0)->SetMaterial(0, ground_mat_vis);
sys.Add(wallBody3);
auto wallBody4 = chrono_types::make_shared<ChBodyEasyBox>(10.48, 12, 1,
1000, ground_mat);
wallBody4->SetPos(ChVector3d(0, 0, 5));
wallBody4->SetFixed(false);
wallBody4->GetVisualShape(0)->SetMaterial(0, ground_mat_vis);
sys.Add(wallBody4);
// Constraints between floor and walls
auto mate1 = chrono_types::make_shared<ChLinkMateFix>();
mate1->Initialize(floorBody, wallBody1);
sys.Add(mate1);
auto mate2 = chrono_types::make_shared<ChLinkMateFix>();
mate2->Initialize(floorBody, wallBody2);
sys.Add(mate2);
auto mate3 = chrono_types::make_shared<ChLinkMateFix>();
mate3->Initialize(floorBody, wallBody3);
sys.Add(mate3);
auto mate4 = chrono_types::make_shared<ChLinkMateFix>();
mate4->Initialize(floorBody, wallBody4);
sys.Add(mate4);
// Reference fixed floor
auto floorBodyRef = chrono_types::make_shared<ChBodyEasyBox>(15, 1.5, 15,
1000, ground_mat);
floorBodyRef->SetPos(ChVector3d(0, -4, 0));
floorBodyRef->SetFixed(true);
floorBodyRef->GetVisualShape(0)->SetMaterial(0, ground_mat_vis);
floorBodyRef->GetVisualShape(0)->SetTexture(GetChronoDataFile("textures/checker1.png"));
sys.Add(floorBodyRef);
// Sinusoidal input
auto linkEarthquake = chrono_types::make_shared<ChLinkLockLock>();
linkEarthquake->Initialize(floorBody, floorBodyRef, ChFrame<>(ChVector3d(0,
0, 0)));
auto mmotion_x = chrono_types::make_shared<ChFunctionSine>(1, 1.2, 0.5);
// phase freq ampl
linkEarthquake->SetMotionX(mmotion_x);
sys.Add(linkEarthquake);
sys.SetGravitationalAcceleration(ChVector3d(0, -1.81, 0));
}
std::shared_ptr<ChBody> intrBody;
int main(int argc, char* argv[]) {
std::cout << "Copyright (c) 2017 projectchrono.org\nChrono version: " <<
CHRONO_VERSION << std::endl;
// Create the physical system
ChSystemNSC sys;
sys.SetCollisionSystemType(collision_type);
// Settings specific to Chrono multicore collision system
if (collision_type == ChCollisionSystem::Type::MULTICORE) {
#ifdef CHRONO_COLLISION
auto collsys =
std::static_pointer_cast<ChCollisionSystemMulticore>(sys.GetCollisionSystem());
// Change the default number of broadphase bins
collsys->SetBroadphaseGridResolution(ChVector3i(10, 10, 2));
// Change default narrowphase algorithm
collsys->SetEnvelope(0.005);
// Enable active bounding box
collsys->EnableActiveBoundingBox(ChVector3d(-10, -10, -20),
ChVector3d(+10, +10, +10));
// Set number of threads used by the collision detection system
collsys->SetNumThreads(4);
#endif
}
// Add fixed and moving bodies
auto mixer = AddContainer(sys);
AddFallingItems(sys);
// Create the run-time visualization system
#ifndef CHRONO_IRRLICHT
if (vis_type == ChVisualSystem::Type::IRRLICHT)
vis_type = ChVisualSystem::Type::VSG;
#endif
#ifndef CHRONO_VSG
if (vis_type == ChVisualSystem::Type::VSG)
vis_type = ChVisualSystem::Type::IRRLICHT;
#endif
std::shared_ptr<ChVisualSystem> vis;
switch (vis_type) {
case ChVisualSystem::Type::IRRLICHT: {
#ifdef CHRONO_IRRLICHT
auto vis_irr = chrono_types::make_shared<ChVisualSystemIrrlicht>();
vis_irr->AttachSystem(&sys);
vis_irr->SetWindowSize(800, 600);
vis_irr->SetWindowTitle("NSC collision demo");
vis_irr->Initialize();
vis_irr->AddLogo();
vis_irr->AddSkyBox();
vis_irr->AddCamera(ChVector3d(0, 14, -20));
vis_irr->AddTypicalLights();
vis = vis_irr;
#endif
break;
}
default:
case ChVisualSystem::Type::VSG: {
#ifdef CHRONO_VSG
auto vis_vsg = chrono_types::make_shared<ChVisualSystemVSG>();
vis_vsg->AttachSystem(&sys);
vis_vsg->SetWindowTitle("SMC callbacks");
vis_vsg->AddCamera(ChVector3d(0, 18, -20));
vis_vsg->SetWindowSize(ChVector2i(800, 600));
vis_vsg->SetWindowPosition(ChVector2i(100, 100));
vis_vsg->SetClearColor(ChColor(0.8f, 0.85f, 0.9f));
vis_vsg->SetUseSkyBox(true); // use built-in path
vis_vsg->SetCameraVertical(CameraVerticalDir::Y);
vis_vsg->SetCameraAngleDeg(40.0);
vis_vsg->SetLightIntensity(1.0f);
vis_vsg->SetLightDirection(1.5 * CH_PI_2, CH_PI_4);
vis_vsg->SetShadows(true);
vis_vsg->SetWireFrameMode(false);
vis_vsg->Initialize();
vis = vis_vsg;
#endif
break;
}
}
// Modify some setting of the physical system for the simulation, if you
want
sys.SetSolverType(ChSolver::Type::PSOR);
sys.GetSolver()->AsIterative()->SetMaxIterations(50);
// File per salvare i dati
std::ofstream file("particle_height.csv");
file << "time,height\n";
// Simulation loop
ChRealtimeStepTimer rt;
double step_size = 0.003;
while (vis->Run()) {
vis->BeginScene();
vis->Render();
vis->EndScene();
sys.DoStepDynamics(step_size);
rt.Spin(step_size);
}
return 0;
}