1 // ============================================================================= 2 // PROJECT CHRONO - http://projectchrono.org 3 // 4 // Copyright (c) 2014 projectchrono.org 5 // All rights reserved. 6 // 7 // Use of this source code is governed by a BSD-style license that can be found 8 // in the LICENSE file at the top level of the distribution and at 9 // http://projectchrono.org/license-chrono.txt. 10 // 11 // ============================================================================= 12 // Authors: Rainer Gericke, Radu Serban 13 // ============================================================================= 14 // 15 // Base class for a coil-spring or air-spring solid axle suspension. 16 // Derived from ChSuspension, but still an abstract base class. 17 // 18 // Non steerable solid axle guided by a triangular and two longitudinal links. 19 // Sprung by coil springs and translational dampers. 20 // 21 // The suspension subsystem is modeled with respect to a right-handed frame, 22 // with X pointing towards the front, Y to the left, and Z up (ISO standard). 23 // The suspension reference frame is assumed to be always aligned with that of 24 // the vehicle. When attached to a chassis, only an offset is provided. 25 // 26 // All point locations are assumed to be given for the left half of the 27 // suspension and will be mirrored (reflecting the y coordinates) to construct 28 // the right side. 29 // 30 // ============================================================================= 31 32 #ifndef CH_SOLID_3LINK_AXLE_H 33 #define CH_SOLID_3LINK_AXLE_H 34 35 #include <vector> 36 37 #include "chrono/assets/ChColorAsset.h" 38 39 #include "chrono_vehicle/ChApiVehicle.h" 40 #include "chrono_vehicle/wheeled_vehicle/ChSuspension.h" 41 42 namespace chrono { 43 namespace vehicle { 44 45 /// @addtogroup vehicle_wheeled_suspension 46 /// @{ 47 48 /// Base class for a coil-spring or air-spring solid axle suspension. 49 /// 50 /// The suspension subsystem is modeled with respect to a right-handed frame, 51 /// with X pointing towards the front, Y to the left, and Z up (ISO standard). 52 /// The suspension reference frame is assumed to be always aligned with that of 53 /// the vehicle. When attached to a chassis, only an offset is provided. 54 /// 55 /// All point locations are assumed to be given for the left half of the 56 /// suspension and will be mirrored (reflecting the y coordinates) to construct 57 /// the right side. 58 class CH_VEHICLE_API ChSolidThreeLinkAxle : public ChSuspension { 59 public: 60 ChSolidThreeLinkAxle(const std::string& name ///< [in] name of the subsystem 61 ); 62 63 virtual ~ChSolidThreeLinkAxle(); 64 65 /// Get the name of the vehicle subsystem template. GetTemplateName()66 virtual std::string GetTemplateName() const override { return "SolidThreeLinkAxle"; } 67 68 /// Specify whether or not this suspension can be steered. IsSteerable()69 virtual bool IsSteerable() const final override { return false; } 70 71 /// Specify whether or not this is an independent suspension. IsIndependent()72 virtual bool IsIndependent() const final override { return false; } 73 74 /// Initialize this suspension subsystem. 75 /// The suspension subsystem is initialized by attaching it to the specified chassis and (if provided) to the 76 /// specified subchassis, at the specified location (with respect to and expressed in the reference frame of the 77 /// chassis). It is assumed that the suspension reference frame is always aligned with the chassis reference frame. 78 /// Since this suspension is non-steerable, the steering subsystem is always ignored. 79 virtual void Initialize( 80 std::shared_ptr<ChChassis> chassis, ///< [in] associated chassis subsystem 81 std::shared_ptr<ChSubchassis> subchassis, ///< [in] associated subchassis subsystem (may be null) 82 std::shared_ptr<ChSteering> steering, ///< [in] associated steering subsystem (may be null) 83 const ChVector<>& location, ///< [in] location relative to the chassis frame 84 double left_ang_vel = 0, ///< [in] initial angular velocity of left wheel 85 double right_ang_vel = 0 ///< [in] initial angular velocity of right wheel 86 ) override; 87 88 /// Add visualization assets for the suspension subsystem. 89 /// This default implementation uses primitives. 90 virtual void AddVisualizationAssets(VisualizationType vis) override; 91 92 /// Remove visualization assets for the suspension subsystem. 93 virtual void RemoveVisualizationAssets() override; 94 95 /// Get the total mass of the suspension subsystem. 96 virtual double GetMass() const override; 97 98 /// Get the current global COM location of the suspension subsystem. 99 virtual ChVector<> GetCOMPos() const override; 100 101 /// Get the wheel track for the suspension subsystem. 102 virtual double GetTrack() override; 103 104 /// Get a handle to the specified spring element. GetSpring(VehicleSide side)105 std::shared_ptr<ChLinkTSDA> GetSpring(VehicleSide side) const { return m_spring[side]; } 106 107 /// Get a handle to the specified shock (damper) element. GetShock(VehicleSide side)108 std::shared_ptr<ChLinkTSDA> GetShock(VehicleSide side) const { return m_shock[side]; } 109 110 /// Return current suspension forces (spring and shock) on the specified side. 111 virtual ChSuspension::Force ReportSuspensionForce(VehicleSide side) const override; 112 113 /// Get the force in the spring element. GetSpringForce(VehicleSide side)114 double GetSpringForce(VehicleSide side) const { return m_spring[side]->GetForce(); } 115 116 /// Get the current length of the spring element GetSpringLength(VehicleSide side)117 double GetSpringLength(VehicleSide side) const { return m_spring[side]->GetLength(); } 118 119 /// Get the current deformation of the spring element. GetSpringDeformation(VehicleSide side)120 double GetSpringDeformation(VehicleSide side) const { return m_spring[side]->GetDeformation(); } 121 122 /// Get the force in the shock (damper) element. GetShockForce(VehicleSide side)123 double GetShockForce(VehicleSide side) const { return m_shock[side]->GetForce(); } 124 125 /// Get the current length of the shock (damper) element. GetShockLength(VehicleSide side)126 double GetShockLength(VehicleSide side) const { return m_shock[side]->GetLength(); } 127 128 /// Get the current deformation velocity of the shock (damper) element. GetShockVelocity(VehicleSide side)129 double GetShockVelocity(VehicleSide side) const { return m_shock[side]->GetVelocity(); } 130 131 /// Log current constraint violations. 132 virtual void LogConstraintViolations(VehicleSide side) override; 133 134 void LogHardpointLocations(const ChVector<>& ref, bool inches = false); 135 136 protected: 137 /// Identifiers for the various hardpoints. 138 enum PointId { 139 SHOCK_A, ///< shock, axle 140 SHOCK_C, ///< shock, chassis 141 SPRING_A, ///< spring, axle 142 SPRING_C, ///< spring, chassis 143 SPINDLE, ///< spindle location 144 TRIANGLE_A, ///< triangle link location on the axle (single point y = 0) 145 TRIANGLE_C, ///< triangle link locationon the chassis (two points) 146 LINK_A, ///< longitudinal link location on the axle (two points) 147 LINK_C, ///< longitudinal link location on the chassis (two points) 148 NUM_POINTS 149 }; 150 151 /// Return the location of the specified hardpoint. 152 /// The returned location must be expressed in the suspension reference frame. 153 virtual const ChVector<> getLocation(PointId which) = 0; 154 155 /// Return the center of mass of the axle tube. 156 virtual const ChVector<> getAxleTubeCOM() const = 0; 157 158 /// Return the mass of the axle tube body. 159 virtual double getAxleTubeMass() const = 0; 160 /// Return the mass of the spindle body. 161 virtual double getSpindleMass() const = 0; 162 /// Return the mass of the triangle body. 163 virtual double getTriangleMass() const = 0; 164 /// Return the mass of the triangle body. 165 virtual double getLinkMass() const = 0; 166 167 /// Return the radius of the axle tube body (visualization only). 168 virtual double getAxleTubeRadius() const = 0; 169 170 /// Return the moments of inertia of the axle tube body. 171 virtual const ChVector<>& getAxleTubeInertia() const = 0; 172 /// Return the moments of inertia of the spindle body. 173 virtual const ChVector<>& getSpindleInertia() const = 0; 174 /// Return the moments of inertia of the triangle body. 175 virtual const ChVector<>& getTriangleInertia() const = 0; 176 /// Return the moments of inertia of the triangle body. 177 virtual const ChVector<>& getLinkInertia() const = 0; 178 179 /// Return the inertia of the axle shaft. 180 virtual double getAxleInertia() const = 0; 181 182 /// Return the free (rest) length of the spring element. 183 virtual double getSpringRestLength() const = 0; 184 /// Return the functor object for spring force. 185 virtual std::shared_ptr<ChLinkTSDA::ForceFunctor> getSpringForceFunctor() const = 0; 186 /// Return the functor object for shock force. 187 virtual std::shared_ptr<ChLinkTSDA::ForceFunctor> getShockForceFunctor() const = 0; 188 189 std::shared_ptr<ChBody> m_axleTube; ///< handles to the axle tube body 190 // //std::shared_ptr<ChBody> m_tierod; ///< handles to the tierod body 191 // //std::shared_ptr<ChLinkLockFree> m_axleTubeGuide; ///< allows all translations and rotations 192 std::shared_ptr<ChBody> m_triangleBody; ///< axle guide body with spherical link and rotary link 193 std::shared_ptr<ChLinkLockRevolute> m_triangleRev; ///< triangle to chassis revolute joint 194 std::shared_ptr<ChLinkLockSpherical> m_triangleSph; ///< triangle to axle tube spherical joint 195 196 std::shared_ptr<ChBody> m_linkBody[2]; ///< axle guide body with spherical link and universal link 197 std::shared_ptr<ChLinkUniversal> m_linkBodyToChassis[2]; 198 std::shared_ptr<ChLinkLockSpherical> m_linkBodyToAxleTube[2]; 199 200 std::shared_ptr<ChLinkTSDA> m_shock[2]; ///< handles to the spring links (L/R) 201 std::shared_ptr<ChLinkTSDA> m_spring[2]; ///< handles to the shock links (L/R) 202 203 private: 204 // Hardpoint absolute locations 205 std::vector<ChVector<>> m_pointsL; 206 std::vector<ChVector<>> m_pointsR; 207 208 // Points for axle tube visualization 209 ChVector<> m_axleOuterL; 210 ChVector<> m_axleOuterR; 211 212 // Points for triangle visualization 213 ChVector<> m_triangle_sph_point; 214 ChVector<> m_triangle_left_point; 215 ChVector<> m_triangle_right_point; 216 217 // Points for link visualization 218 ChVector<> m_link_axleL; 219 ChVector<> m_link_axleR; 220 ChVector<> m_link_chassisL; 221 ChVector<> m_link_chassisR; 222 223 // Points for tierod visualization 224 ChVector<> m_tierodOuterL; 225 ChVector<> m_tierodOuterR; 226 227 void InitializeSide(VehicleSide side, 228 std::shared_ptr<ChBodyAuxRef> chassis, 229 std::shared_ptr<ChBody> scbeam, 230 const std::vector<ChVector<>>& points, 231 double ang_vel); 232 233 static void AddVisualizationLink(std::shared_ptr<ChBody> body, 234 const ChVector<> pt_1, 235 const ChVector<> pt_2, 236 double radius, 237 const ChColor& color); 238 239 virtual void ExportComponentList(rapidjson::Document& jsonDocument) const override; 240 241 virtual void Output(ChVehicleOutput& database) const override; 242 243 static const std::string m_pointNames[NUM_POINTS]; 244 }; 245 246 /// @} vehicle_wheeled_suspension 247 248 } // end namespace vehicle 249 } // end namespace chrono 250 251 #endif 252