1 2 3 /************************************************************************* 4 * * 5 * Open Dynamics Engine, Copyright (C) 2001,2002 Russell L. Smith. * 6 * All rights reserved. Email: russ@q12.org Web: www.q12.org * 7 * * 8 * This library is free software; you can redistribute it and/or * 9 * modify it under the terms of EITHER: * 10 * (1) The GNU Lesser General Public License as published by the Free * 11 * Software Foundation; either version 2.1 of the License, or (at * 12 * your option) any later version. The text of the GNU Lesser * 13 * General Public License is included with this library in the * 14 * file LICENSE.TXT. * 15 * (2) The BSD-style license that is included with this library in * 16 * the file LICENSE-BSD.TXT. * 17 * * 18 * This library is distributed in the hope that it will be useful, * 19 * but WITHOUT ANY WARRANTY; without even the implied warranty of * 20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the files * 21 * LICENSE.TXT and LICENSE-BSD.TXT for more details. * 22 * * 23 *************************************************************************/ 24 25 #ifndef _ODE_OBJECTS_H_ 26 #define _ODE_OBJECTS_H_ 27 28 #include <ode/common.h> 29 #include <ode/mass.h> 30 #include <ode/contact.h> 31 32 #ifdef __cplusplus 33 extern "C" { 34 #endif 35 36 /** 37 * @defgroup world World 38 * 39 * The world object is a container for rigid bodies and joints. Objects in 40 * different worlds can not interact, for example rigid bodies from two 41 * different worlds can not collide. 42 * 43 * All the objects in a world exist at the same point in time, thus one 44 * reason to use separate worlds is to simulate systems at different rates. 45 * Most applications will only need one world. 46 */ 47 48 49 /** 50 * @brief Create a new, empty world and return its ID number. 51 * @return an identifier 52 * @ingroup world 53 */ 54 ODE_API dWorldID dWorldCreate(void); 55 56 57 /** 58 * @brief Destroy a world and everything in it. 59 * 60 * This includes all bodies, and all joints that are not part of a joint 61 * group. Joints that are part of a joint group will be deactivated, and 62 * can be destroyed by calling, for example, dJointGroupEmpty(). 63 * @ingroup world 64 * @param world the identifier for the world the be destroyed. 65 */ 66 ODE_API void dWorldDestroy (dWorldID world); 67 68 69 /** 70 * @brief Set the world's global gravity vector. 71 * 72 * The units are m/s^2, so Earth's gravity vector would be (0,0,-9.81), 73 * assuming that +z is up. The default is no gravity, i.e. (0,0,0). 74 * 75 * @ingroup world 76 */ 77 ODE_API void dWorldSetGravity (dWorldID, dReal x, dReal y, dReal z); 78 79 80 /** 81 * @brief Get the gravity vector for a given world. 82 * @ingroup world 83 */ 84 ODE_API void dWorldGetGravity (dWorldID, dVector3 gravity); 85 86 87 /** 88 * @brief Set the global ERP value, that controls how much error 89 * correction is performed in each time step. 90 * @ingroup world 91 * @param dWorldID the identifier of the world. 92 * @param erp Typical values are in the range 0.1--0.8. The default is 0.2. 93 */ 94 ODE_API void dWorldSetERP (dWorldID, dReal erp); 95 96 /** 97 * @brief Get the error reduction parameter. 98 * @ingroup world 99 * @return ERP value 100 */ 101 ODE_API dReal dWorldGetERP (dWorldID); 102 103 104 /** 105 * @brief Set the global CFM (constraint force mixing) value. 106 * @ingroup world 107 * @param cfm Typical values are in the range @m{10^{-9}} -- 1. 108 * The default is 10^-5 if single precision is being used, or 10^-10 109 * if double precision is being used. 110 */ 111 ODE_API void dWorldSetCFM (dWorldID, dReal cfm); 112 113 /** 114 * @brief Get the constraint force mixing value. 115 * @ingroup world 116 * @return CFM value 117 */ 118 ODE_API dReal dWorldGetCFM (dWorldID); 119 120 121 /** 122 * @brief Step the world. 123 * 124 * This uses a "big matrix" method that takes time on the order of m^3 125 * and memory on the order of m^2, where m is the total number of constraint 126 * rows. For large systems this will use a lot of memory and can be very slow, 127 * but this is currently the most accurate method. 128 * @ingroup world 129 * @param stepsize The number of seconds that the simulation has to advance. 130 */ 131 ODE_API void dWorldStep (dWorldID, dReal stepsize); 132 133 134 /** 135 * @brief Converts an impulse to a force. 136 * @ingroup world 137 * @remarks 138 * If you want to apply a linear or angular impulse to a rigid body, 139 * instead of a force or a torque, then you can use this function to convert 140 * the desired impulse into a force/torque vector before calling the 141 * BodyAdd... function. 142 * The current algorithm simply scales the impulse by 1/stepsize, 143 * where stepsize is the step size for the next step that will be taken. 144 * This function is given a dWorldID because, in the future, the force 145 * computation may depend on integrator parameters that are set as 146 * properties of the world. 147 */ 148 ODE_API void dWorldImpulseToForce 149 ( 150 dWorldID, dReal stepsize, 151 dReal ix, dReal iy, dReal iz, dVector3 force 152 ); 153 154 155 /** 156 * @brief Step the world. 157 * @ingroup world 158 * @remarks 159 * This uses an iterative method that takes time on the order of m*N 160 * and memory on the order of m, where m is the total number of constraint 161 * rows N is the number of iterations. 162 * For large systems this is a lot faster than dWorldStep(), 163 * but it is less accurate. 164 * @remarks 165 * QuickStep is great for stacks of objects especially when the 166 * auto-disable feature is used as well. 167 * However, it has poor accuracy for near-singular systems. 168 * Near-singular systems can occur when using high-friction contacts, motors, 169 * or certain articulated structures. For example, a robot with multiple legs 170 * sitting on the ground may be near-singular. 171 * @remarks 172 * There are ways to help overcome QuickStep's inaccuracy problems: 173 * \li Increase CFM. 174 * \li Reduce the number of contacts in your system (e.g. use the minimum 175 * number of contacts for the feet of a robot or creature). 176 * \li Don't use excessive friction in the contacts. 177 * \li Use contact slip if appropriate 178 * \li Avoid kinematic loops (however, kinematic loops are inevitable in 179 * legged creatures). 180 * \li Don't use excessive motor strength. 181 * \liUse force-based motors instead of velocity-based motors. 182 * 183 * Increasing the number of QuickStep iterations may help a little bit, but 184 * it is not going to help much if your system is really near singular. 185 */ 186 ODE_API void dWorldQuickStep (dWorldID w, dReal stepsize); 187 188 189 /** 190 * @brief Set the number of iterations that the QuickStep method performs per 191 * step. 192 * @ingroup world 193 * @remarks 194 * More iterations will give a more accurate solution, but will take 195 * longer to compute. 196 * @param num The default is 20 iterations. 197 */ 198 ODE_API void dWorldSetQuickStepNumIterations (dWorldID, int num); 199 200 201 /** 202 * @brief Get the number of iterations that the QuickStep method performs per 203 * step. 204 * @ingroup world 205 * @return nr of iterations 206 */ 207 ODE_API int dWorldGetQuickStepNumIterations (dWorldID); 208 209 /** 210 * @brief Set the SOR over-relaxation parameter 211 * @ingroup world 212 * @param over_relaxation value to use by SOR 213 */ 214 ODE_API void dWorldSetQuickStepW (dWorldID, dReal over_relaxation); 215 216 /** 217 * @brief Get the SOR over-relaxation parameter 218 * @ingroup world 219 * @returns the over-relaxation setting 220 */ 221 ODE_API dReal dWorldGetQuickStepW (dWorldID); 222 223 /* World contact parameter functions */ 224 225 /** 226 * @brief Set the maximum correcting velocity that contacts are allowed 227 * to generate. 228 * @ingroup world 229 * @param vel The default value is infinity (i.e. no limit). 230 * @remarks 231 * Reducing this value can help prevent "popping" of deeply embedded objects. 232 */ 233 ODE_API void dWorldSetContactMaxCorrectingVel (dWorldID, dReal vel); 234 235 /** 236 * @brief Get the maximum correcting velocity that contacts are allowed 237 * to generated. 238 * @ingroup world 239 */ 240 ODE_API dReal dWorldGetContactMaxCorrectingVel (dWorldID); 241 242 /** 243 * @brief Set the depth of the surface layer around all geometry objects. 244 * @ingroup world 245 * @remarks 246 * Contacts are allowed to sink into the surface layer up to the given 247 * depth before coming to rest. 248 * @param depth The default value is zero. 249 * @remarks 250 * Increasing this to some small value (e.g. 0.001) can help prevent 251 * jittering problems due to contacts being repeatedly made and broken. 252 */ 253 ODE_API void dWorldSetContactSurfaceLayer (dWorldID, dReal depth); 254 255 /** 256 * @brief Get the depth of the surface layer around all geometry objects. 257 * @ingroup world 258 * @returns the depth 259 */ 260 ODE_API dReal dWorldGetContactSurfaceLayer (dWorldID); 261 262 /* StepFast1 functions */ 263 264 /** 265 * @brief Step the world using the StepFast1 algorithm. 266 * @param stepsize the nr of seconds to advance the simulation. 267 * @param maxiterations The number of iterations to perform. 268 * @ingroup world 269 */ 270 ODE_API void dWorldStepFast1(dWorldID, dReal stepsize, int maxiterations); 271 272 273 /** 274 * @defgroup disable Automatic Enabling and Disabling 275 * @ingroup world bodies 276 * 277 * Every body can be enabled or disabled. Enabled bodies participate in the 278 * simulation, while disabled bodies are turned off and do not get updated 279 * during a simulation step. New bodies are always created in the enabled state. 280 * 281 * A disabled body that is connected through a joint to an enabled body will be 282 * automatically re-enabled at the next simulation step. 283 * 284 * Disabled bodies do not consume CPU time, therefore to speed up the simulation 285 * bodies should be disabled when they come to rest. This can be done automatically 286 * with the auto-disable feature. 287 * 288 * If a body has its auto-disable flag turned on, it will automatically disable 289 * itself when 290 * @li It has been idle for a given number of simulation steps. 291 * @li It has also been idle for a given amount of simulation time. 292 * 293 * A body is considered to be idle when the magnitudes of both its 294 * linear average velocity and angular average velocity are below given thresholds. 295 * The sample size for the average defaults to one and can be disabled by setting 296 * to zero with 297 * 298 * Thus, every body has six auto-disable parameters: an enabled flag, a idle step 299 * count, an idle time, linear/angular average velocity thresholds, and the 300 * average samples count. 301 * 302 * Newly created bodies get these parameters from world. 303 */ 304 305 /** 306 * @brief Set the AutoEnableDepth parameter used by the StepFast1 algorithm. 307 * @ingroup disable 308 */ 309 ODE_API void dWorldSetAutoEnableDepthSF1(dWorldID, int autoEnableDepth); 310 311 /** 312 * @brief Get the AutoEnableDepth parameter used by the StepFast1 algorithm. 313 * @ingroup disable 314 */ 315 ODE_API int dWorldGetAutoEnableDepthSF1(dWorldID); 316 317 /** 318 * @brief Get auto disable linear threshold for newly created bodies. 319 * @ingroup disable 320 * @return the threshold 321 */ 322 ODE_API dReal dWorldGetAutoDisableLinearThreshold (dWorldID); 323 324 /** 325 * @brief Set auto disable linear threshold for newly created bodies. 326 * @param linear_threshold default is 0.01 327 * @ingroup disable 328 */ 329 ODE_API void dWorldSetAutoDisableLinearThreshold (dWorldID, dReal linear_threshold); 330 331 /** 332 * @brief Get auto disable angular threshold for newly created bodies. 333 * @ingroup disable 334 * @return the threshold 335 */ 336 ODE_API dReal dWorldGetAutoDisableAngularThreshold (dWorldID); 337 338 /** 339 * @brief Set auto disable angular threshold for newly created bodies. 340 * @param linear_threshold default is 0.01 341 * @ingroup disable 342 */ 343 ODE_API void dWorldSetAutoDisableAngularThreshold (dWorldID, dReal angular_threshold); 344 345 /** 346 * @brief Get auto disable linear average threshold for newly created bodies. 347 * @ingroup disable 348 * @return the threshold 349 */ 350 ODE_API dReal dWorldGetAutoDisableLinearAverageThreshold (dWorldID); 351 352 /** 353 * @brief Set auto disable linear average threshold for newly created bodies. 354 * @param linear_average_threshold default is 0.01 355 * @ingroup disable 356 */ 357 ODE_API void dWorldSetAutoDisableLinearAverageThreshold (dWorldID, dReal linear_average_threshold); 358 359 /** 360 * @brief Get auto disable angular average threshold for newly created bodies. 361 * @ingroup disable 362 * @return the threshold 363 */ 364 ODE_API dReal dWorldGetAutoDisableAngularAverageThreshold (dWorldID); 365 366 /** 367 * @brief Set auto disable angular average threshold for newly created bodies. 368 * @param linear_average_threshold default is 0.01 369 * @ingroup disable 370 */ 371 ODE_API void dWorldSetAutoDisableAngularAverageThreshold (dWorldID, dReal angular_average_threshold); 372 373 /** 374 * @brief Get auto disable sample count for newly created bodies. 375 * @ingroup disable 376 * @return number of samples used 377 */ 378 ODE_API int dWorldGetAutoDisableAverageSamplesCount (dWorldID); 379 380 /** 381 * @brief Set auto disable average sample count for newly created bodies. 382 * @ingroup disable 383 * @param average_samples_count Default is 1, meaning only instantaneous velocity is used. 384 * Set to zero to disable sampling and thus prevent any body from auto-disabling. 385 */ 386 ODE_API void dWorldSetAutoDisableAverageSamplesCount (dWorldID, unsigned int average_samples_count ); 387 388 /** 389 * @brief Get auto disable steps for newly created bodies. 390 * @ingroup disable 391 * @return nr of steps 392 */ 393 ODE_API int dWorldGetAutoDisableSteps (dWorldID); 394 395 /** 396 * @brief Set auto disable steps for newly created bodies. 397 * @ingroup disable 398 * @param steps default is 10 399 */ 400 ODE_API void dWorldSetAutoDisableSteps (dWorldID, int steps); 401 402 /** 403 * @brief Get auto disable time for newly created bodies. 404 * @ingroup disable 405 * @return nr of seconds 406 */ 407 ODE_API dReal dWorldGetAutoDisableTime (dWorldID); 408 409 /** 410 * @brief Set auto disable time for newly created bodies. 411 * @ingroup disable 412 * @param time default is 0 seconds 413 */ 414 ODE_API void dWorldSetAutoDisableTime (dWorldID, dReal time); 415 416 /** 417 * @brief Get auto disable flag for newly created bodies. 418 * @ingroup disable 419 * @return 0 or 1 420 */ 421 ODE_API int dWorldGetAutoDisableFlag (dWorldID); 422 423 /** 424 * @brief Set auto disable flag for newly created bodies. 425 * @ingroup disable 426 * @param do_auto_disable default is false. 427 */ 428 ODE_API void dWorldSetAutoDisableFlag (dWorldID, int do_auto_disable); 429 430 431 /** 432 * @defgroup damping Damping 433 * @ingroup bodies world 434 * 435 * Damping serves two purposes: reduce simulation instability, and to allow 436 * the bodies to come to rest (and possibly auto-disabling them). 437 * 438 * Bodies are constructed using the world's current damping parameters. Setting 439 * the scales to 0 disables the damping. 440 * 441 * Here is how it is done: after every time step linear and angular 442 * velocities are tested against the corresponding thresholds. If they 443 * are above, they are multiplied by (1 - scale). So a negative scale value 444 * will actually increase the speed, and values greater than one will 445 * make the object oscillate every step; both can make the simulation unstable. 446 * 447 * To disable damping just set the damping scale to zero. 448 * 449 * You can also limit the maximum angular velocity. In contrast to the damping 450 * functions, the angular velocity is affected before the body is moved. 451 * This means that it will introduce errors in joints that are forcing the body 452 * to rotate too fast. Some bodies have naturally high angular velocities 453 * (like cars' wheels), so you may want to give them a very high (like the default, 454 * dInfinity) limit. 455 * 456 * @note The velocities are damped after the stepper function has moved the 457 * object. Otherwise the damping could introduce errors in joints. First the 458 * joint constraints are processed by the stepper (moving the body), then 459 * the damping is applied. 460 * 461 * @note The damping happens right after the moved callback is called; this way 462 * it still possible use the exact velocities the body has acquired during the 463 * step. You can even use the callback to create your own customized damping. 464 */ 465 466 /** 467 * @brief Get the world's linear damping threshold. 468 * @ingroup damping 469 */ 470 ODE_API dReal dWorldGetLinearDampingThreshold (dWorldID w); 471 472 /** 473 * @brief Set the world's linear damping threshold. 474 * @param threshold The damping won't be applied if the linear speed is 475 * below this threshold. Default is 0.01. 476 * @ingroup damping 477 */ 478 ODE_API void dWorldSetLinearDampingThreshold(dWorldID w, dReal threshold); 479 480 /** 481 * @brief Get the world's angular damping threshold. 482 * @ingroup damping 483 */ 484 ODE_API dReal dWorldGetAngularDampingThreshold (dWorldID w); 485 486 /** 487 * @brief Set the world's angular damping threshold. 488 * @param threshold The damping won't be applied if the angular speed is 489 * below this threshold. Default is 0.01. 490 * @ingroup damping 491 */ 492 ODE_API void dWorldSetAngularDampingThreshold(dWorldID w, dReal threshold); 493 494 /** 495 * @brief Get the world's linear damping scale. 496 * @ingroup damping 497 */ 498 ODE_API dReal dWorldGetLinearDamping (dWorldID w); 499 500 /** 501 * @brief Set the world's linear damping scale. 502 * @param scale The linear damping scale that is to be applied to bodies. 503 * Default is 0 (no damping). Should be in the interval [0, 1]. 504 * @ingroup damping 505 */ 506 ODE_API void dWorldSetLinearDamping (dWorldID w, dReal scale); 507 508 /** 509 * @brief Get the world's angular damping scale. 510 * @ingroup damping 511 */ 512 ODE_API dReal dWorldGetAngularDamping (dWorldID w); 513 514 /** 515 * @brief Set the world's angular damping scale. 516 * @param scale The angular damping scale that is to be applied to bodies. 517 * Default is 0 (no damping). Should be in the interval [0, 1]. 518 * @ingroup damping 519 */ 520 ODE_API void dWorldSetAngularDamping(dWorldID w, dReal scale); 521 522 /** 523 * @brief Convenience function to set body linear and angular scales. 524 * @param linear_scale The linear damping scale that is to be applied to bodies. 525 * @param angular_scale The angular damping scale that is to be applied to bodies. 526 * @ingroup damping 527 */ 528 ODE_API void dWorldSetDamping(dWorldID w, 529 dReal linear_scale, 530 dReal angular_scale); 531 532 /** 533 * @brief Get the default maximum angular speed. 534 * @ingroup damping 535 * @sa dBodyGetMaxAngularSpeed() 536 */ 537 ODE_API dReal dWorldGetMaxAngularSpeed (dWorldID w); 538 539 540 /** 541 * @brief Set the default maximum angular speed for new bodies. 542 * @ingroup damping 543 * @sa dBodySetMaxAngularSpeed() 544 */ 545 ODE_API void dWorldSetMaxAngularSpeed (dWorldID w, dReal max_speed); 546 547 548 549 /** 550 * @defgroup bodies Rigid Bodies 551 * 552 * A rigid body has various properties from the point of view of the 553 * simulation. Some properties change over time: 554 * 555 * @li Position vector (x,y,z) of the body's point of reference. 556 * Currently the point of reference must correspond to the body's center of mass. 557 * @li Linear velocity of the point of reference, a vector (vx,vy,vz). 558 * @li Orientation of a body, represented by a quaternion (qs,qx,qy,qz) or 559 * a 3x3 rotation matrix. 560 * @li Angular velocity vector (wx,wy,wz) which describes how the orientation 561 * changes over time. 562 * 563 * Other body properties are usually constant over time: 564 * 565 * @li Mass of the body. 566 * @li Position of the center of mass with respect to the point of reference. 567 * In the current implementation the center of mass and the point of 568 * reference must coincide. 569 * @li Inertia matrix. This is a 3x3 matrix that describes how the body's mass 570 * is distributed around the center of mass. Conceptually each body has an 571 * x-y-z coordinate frame embedded in it that moves and rotates with the body. 572 * 573 * The origin of this coordinate frame is the body's point of reference. Some values 574 * in ODE (vectors, matrices etc) are relative to the body coordinate frame, and others 575 * are relative to the global coordinate frame. 576 * 577 * Note that the shape of a rigid body is not a dynamical property (except insofar as 578 * it influences the various mass properties). It is only collision detection that cares 579 * about the detailed shape of the body. 580 */ 581 582 583 /** 584 * @brief Get auto disable linear average threshold. 585 * @ingroup bodies disable 586 * @return the threshold 587 */ 588 ODE_API dReal dBodyGetAutoDisableLinearThreshold (dBodyID); 589 590 /** 591 * @brief Set auto disable linear average threshold. 592 * @ingroup bodies disable 593 * @return the threshold 594 */ 595 ODE_API void dBodySetAutoDisableLinearThreshold (dBodyID, dReal linear_average_threshold); 596 597 /** 598 * @brief Get auto disable angular average threshold. 599 * @ingroup bodies disable 600 * @return the threshold 601 */ 602 ODE_API dReal dBodyGetAutoDisableAngularThreshold (dBodyID); 603 604 /** 605 * @brief Set auto disable angular average threshold. 606 * @ingroup bodies disable 607 * @return the threshold 608 */ 609 ODE_API void dBodySetAutoDisableAngularThreshold (dBodyID, dReal angular_average_threshold); 610 611 /** 612 * @brief Get auto disable average size (samples count). 613 * @ingroup bodies disable 614 * @return the nr of steps/size. 615 */ 616 ODE_API int dBodyGetAutoDisableAverageSamplesCount (dBodyID); 617 618 /** 619 * @brief Set auto disable average buffer size (average steps). 620 * @ingroup bodies disable 621 * @param average_samples_count the nr of samples to review. 622 */ 623 ODE_API void dBodySetAutoDisableAverageSamplesCount (dBodyID, unsigned int average_samples_count); 624 625 626 /** 627 * @brief Get auto steps a body must be thought of as idle to disable 628 * @ingroup bodies disable 629 * @return the nr of steps 630 */ 631 ODE_API int dBodyGetAutoDisableSteps (dBodyID); 632 633 /** 634 * @brief Set auto disable steps. 635 * @ingroup bodies disable 636 * @param steps the nr of steps. 637 */ 638 ODE_API void dBodySetAutoDisableSteps (dBodyID, int steps); 639 640 /** 641 * @brief Get auto disable time. 642 * @ingroup bodies disable 643 * @return nr of seconds 644 */ 645 ODE_API dReal dBodyGetAutoDisableTime (dBodyID); 646 647 /** 648 * @brief Set auto disable time. 649 * @ingroup bodies disable 650 * @param time nr of seconds. 651 */ 652 ODE_API void dBodySetAutoDisableTime (dBodyID, dReal time); 653 654 /** 655 * @brief Get auto disable flag. 656 * @ingroup bodies disable 657 * @return 0 or 1 658 */ 659 ODE_API int dBodyGetAutoDisableFlag (dBodyID); 660 661 /** 662 * @brief Set auto disable flag. 663 * @ingroup bodies disable 664 * @param do_auto_disable 0 or 1 665 */ 666 ODE_API void dBodySetAutoDisableFlag (dBodyID, int do_auto_disable); 667 668 /** 669 * @brief Set auto disable defaults. 670 * @remarks 671 * Set the values for the body to those set as default for the world. 672 * @ingroup bodies disable 673 */ 674 ODE_API void dBodySetAutoDisableDefaults (dBodyID); 675 676 677 /** 678 * @brief Retrieves the world attached to te given body. 679 * @remarks 680 * 681 * @ingroup bodies 682 */ 683 ODE_API dWorldID dBodyGetWorld (dBodyID); 684 685 /** 686 * @brief Create a body in given world. 687 * @remarks 688 * Default mass parameters are at position (0,0,0). 689 * @ingroup bodies 690 */ 691 ODE_API dBodyID dBodyCreate (dWorldID); 692 693 /** 694 * @brief Destroy a body. 695 * @remarks 696 * All joints that are attached to this body will be put into limbo: 697 * i.e. unattached and not affecting the simulation, but they will NOT be 698 * deleted. 699 * @ingroup bodies 700 */ 701 ODE_API void dBodyDestroy (dBodyID); 702 703 /** 704 * @brief Set the body's user-data pointer. 705 * @ingroup bodies 706 * @param data arbitraty pointer 707 */ 708 ODE_API void dBodySetData (dBodyID, void *data); 709 710 /** 711 * @brief Get the body's user-data pointer. 712 * @ingroup bodies 713 * @return a pointer to the user's data. 714 */ 715 ODE_API void *dBodyGetData (dBodyID); 716 717 /** 718 * @brief Set position of a body. 719 * @remarks 720 * After setting, the outcome of the simulation is undefined 721 * if the new configuration is inconsistent with the joints/constraints 722 * that are present. 723 * @ingroup bodies 724 */ 725 ODE_API void dBodySetPosition (dBodyID, dReal x, dReal y, dReal z); 726 727 /** 728 * @brief Set the orientation of a body. 729 * @ingroup bodies 730 * @remarks 731 * After setting, the outcome of the simulation is undefined 732 * if the new configuration is inconsistent with the joints/constraints 733 * that are present. 734 */ 735 ODE_API void dBodySetRotation (dBodyID, const dMatrix3 R); 736 737 /** 738 * @brief Set the orientation of a body. 739 * @ingroup bodies 740 * @remarks 741 * After setting, the outcome of the simulation is undefined 742 * if the new configuration is inconsistent with the joints/constraints 743 * that are present. 744 */ 745 ODE_API void dBodySetQuaternion (dBodyID, const dQuaternion q); 746 747 /** 748 * @brief Set the linear velocity of a body. 749 * @ingroup bodies 750 */ 751 ODE_API void dBodySetLinearVel (dBodyID, dReal x, dReal y, dReal z); 752 753 /** 754 * @brief Set the angular velocity of a body. 755 * @ingroup bodies 756 */ 757 ODE_API void dBodySetAngularVel (dBodyID, dReal x, dReal y, dReal z); 758 759 /** 760 * @brief Get the position of a body. 761 * @ingroup bodies 762 * @remarks 763 * When getting, the returned values are pointers to internal data structures, 764 * so the vectors are valid until any changes are made to the rigid body 765 * system structure. 766 * @sa dBodyCopyPosition 767 */ 768 ODE_API const dReal * dBodyGetPosition (dBodyID); 769 770 771 /** 772 * @brief Copy the position of a body into a vector. 773 * @ingroup bodies 774 * @param body the body to query 775 * @param pos a copy of the body position 776 * @sa dBodyGetPosition 777 */ 778 ODE_API void dBodyCopyPosition (dBodyID body, dVector3 pos); 779 780 781 /** 782 * @brief Get the rotation of a body. 783 * @ingroup bodies 784 * @return pointer to a 4x3 rotation matrix. 785 */ 786 ODE_API const dReal * dBodyGetRotation (dBodyID); 787 788 789 /** 790 * @brief Copy the rotation of a body. 791 * @ingroup bodies 792 * @param body the body to query 793 * @param R a copy of the rotation matrix 794 * @sa dBodyGetRotation 795 */ 796 ODE_API void dBodyCopyRotation (dBodyID, dMatrix3 R); 797 798 799 /** 800 * @brief Get the rotation of a body. 801 * @ingroup bodies 802 * @return pointer to 4 scalars that represent the quaternion. 803 */ 804 ODE_API const dReal * dBodyGetQuaternion (dBodyID); 805 806 807 /** 808 * @brief Copy the orientation of a body into a quaternion. 809 * @ingroup bodies 810 * @param body the body to query 811 * @param quat a copy of the orientation quaternion 812 * @sa dBodyGetQuaternion 813 */ 814 ODE_API void dBodyCopyQuaternion(dBodyID body, dQuaternion quat); 815 816 817 /** 818 * @brief Get the linear velocity of a body. 819 * @ingroup bodies 820 */ 821 ODE_API const dReal * dBodyGetLinearVel (dBodyID); 822 823 /** 824 * @brief Get the angular velocity of a body. 825 * @ingroup bodies 826 */ 827 ODE_API const dReal * dBodyGetAngularVel (dBodyID); 828 829 /** 830 * @brief Set the mass of a body. 831 * @ingroup bodies 832 */ 833 ODE_API void dBodySetMass (dBodyID, const dMass *mass); 834 835 /** 836 * @brief Get the mass of a body. 837 * @ingroup bodies 838 */ 839 ODE_API void dBodyGetMass (dBodyID, dMass *mass); 840 841 /** 842 * @brief Add force at centre of mass of body in absolute coordinates. 843 * @ingroup bodies 844 */ 845 ODE_API void dBodyAddForce (dBodyID, dReal fx, dReal fy, dReal fz); 846 847 /** 848 * @brief Add torque at centre of mass of body in absolute coordinates. 849 * @ingroup bodies 850 */ 851 ODE_API void dBodyAddTorque (dBodyID, dReal fx, dReal fy, dReal fz); 852 853 /** 854 * @brief Add force at centre of mass of body in coordinates relative to body. 855 * @ingroup bodies 856 */ 857 ODE_API void dBodyAddRelForce (dBodyID, dReal fx, dReal fy, dReal fz); 858 859 /** 860 * @brief Add torque at centre of mass of body in coordinates relative to body. 861 * @ingroup bodies 862 */ 863 ODE_API void dBodyAddRelTorque (dBodyID, dReal fx, dReal fy, dReal fz); 864 865 /** 866 * @brief Add force at specified point in body in global coordinates. 867 * @ingroup bodies 868 */ 869 ODE_API void dBodyAddForceAtPos (dBodyID, dReal fx, dReal fy, dReal fz, 870 dReal px, dReal py, dReal pz); 871 /** 872 * @brief Add force at specified point in body in local coordinates. 873 * @ingroup bodies 874 */ 875 ODE_API void dBodyAddForceAtRelPos (dBodyID, dReal fx, dReal fy, dReal fz, 876 dReal px, dReal py, dReal pz); 877 /** 878 * @brief Add force at specified point in body in global coordinates. 879 * @ingroup bodies 880 */ 881 ODE_API void dBodyAddRelForceAtPos (dBodyID, dReal fx, dReal fy, dReal fz, 882 dReal px, dReal py, dReal pz); 883 /** 884 * @brief Add force at specified point in body in local coordinates. 885 * @ingroup bodies 886 */ 887 ODE_API void dBodyAddRelForceAtRelPos (dBodyID, dReal fx, dReal fy, dReal fz, 888 dReal px, dReal py, dReal pz); 889 890 /** 891 * @brief Return the current accumulated force vector. 892 * @return points to an array of 3 reals. 893 * @remarks 894 * The returned values are pointers to internal data structures, so 895 * the vectors are only valid until any changes are made to the rigid 896 * body system. 897 * @ingroup bodies 898 */ 899 ODE_API const dReal * dBodyGetForce (dBodyID); 900 901 /** 902 * @brief Return the current accumulated torque vector. 903 * @return points to an array of 3 reals. 904 * @remarks 905 * The returned values are pointers to internal data structures, so 906 * the vectors are only valid until any changes are made to the rigid 907 * body system. 908 * @ingroup bodies 909 */ 910 ODE_API const dReal * dBodyGetTorque (dBodyID); 911 912 /** 913 * @brief Set the body force accumulation vector. 914 * @remarks 915 * This is mostly useful to zero the force and torque for deactivated bodies 916 * before they are reactivated, in the case where the force-adding functions 917 * were called on them while they were deactivated. 918 * @ingroup bodies 919 */ 920 ODE_API void dBodySetForce (dBodyID b, dReal x, dReal y, dReal z); 921 922 /** 923 * @brief Set the body torque accumulation vector. 924 * @remarks 925 * This is mostly useful to zero the force and torque for deactivated bodies 926 * before they are reactivated, in the case where the force-adding functions 927 * were called on them while they were deactivated. 928 * @ingroup bodies 929 */ 930 ODE_API void dBodySetTorque (dBodyID b, dReal x, dReal y, dReal z); 931 932 /** 933 * @brief Get world position of a relative point on body. 934 * @ingroup bodies 935 * @param result will contain the result. 936 */ 937 ODE_API void dBodyGetRelPointPos 938 ( 939 dBodyID, dReal px, dReal py, dReal pz, 940 dVector3 result 941 ); 942 943 /** 944 * @brief Get velocity vector in global coords of a relative point on body. 945 * @ingroup bodies 946 * @param result will contain the result. 947 */ 948 ODE_API void dBodyGetRelPointVel 949 ( 950 dBodyID, dReal px, dReal py, dReal pz, 951 dVector3 result 952 ); 953 954 /** 955 * @brief Get velocity vector in global coords of a globally 956 * specified point on a body. 957 * @ingroup bodies 958 * @param result will contain the result. 959 */ 960 ODE_API void dBodyGetPointVel 961 ( 962 dBodyID, dReal px, dReal py, dReal pz, 963 dVector3 result 964 ); 965 966 /** 967 * @brief takes a point in global coordinates and returns 968 * the point's position in body-relative coordinates. 969 * @remarks 970 * This is the inverse of dBodyGetRelPointPos() 971 * @ingroup bodies 972 * @param result will contain the result. 973 */ 974 ODE_API void dBodyGetPosRelPoint 975 ( 976 dBodyID, dReal px, dReal py, dReal pz, 977 dVector3 result 978 ); 979 980 /** 981 * @brief Convert from local to world coordinates. 982 * @ingroup bodies 983 * @param result will contain the result. 984 */ 985 ODE_API void dBodyVectorToWorld 986 ( 987 dBodyID, dReal px, dReal py, dReal pz, 988 dVector3 result 989 ); 990 991 /** 992 * @brief Convert from world to local coordinates. 993 * @ingroup bodies 994 * @param result will contain the result. 995 */ 996 ODE_API void dBodyVectorFromWorld 997 ( 998 dBodyID, dReal px, dReal py, dReal pz, 999 dVector3 result 1000 ); 1001 1002 /** 1003 * @brief controls the way a body's orientation is updated at each timestep. 1004 * @ingroup bodies 1005 * @param mode can be 0 or 1: 1006 * \li 0: An ``infinitesimal'' orientation update is used. 1007 * This is fast to compute, but it can occasionally cause inaccuracies 1008 * for bodies that are rotating at high speed, especially when those 1009 * bodies are joined to other bodies. 1010 * This is the default for every new body that is created. 1011 * \li 1: A ``finite'' orientation update is used. 1012 * This is more costly to compute, but will be more accurate for high 1013 * speed rotations. 1014 * @remarks 1015 * Note however that high speed rotations can result in many types of 1016 * error in a simulation, and the finite mode will only fix one of those 1017 * sources of error. 1018 */ 1019 ODE_API void dBodySetFiniteRotationMode (dBodyID, int mode); 1020 1021 /** 1022 * @brief sets the finite rotation axis for a body. 1023 * @ingroup bodies 1024 * @remarks 1025 * This is axis only has meaning when the finite rotation mode is set 1026 * If this axis is zero (0,0,0), full finite rotations are performed on 1027 * the body. 1028 * If this axis is nonzero, the body is rotated by performing a partial finite 1029 * rotation along the axis direction followed by an infinitesimal rotation 1030 * along an orthogonal direction. 1031 * @remarks 1032 * This can be useful to alleviate certain sources of error caused by quickly 1033 * spinning bodies. For example, if a car wheel is rotating at high speed 1034 * you can call this function with the wheel's hinge axis as the argument to 1035 * try and improve its behavior. 1036 */ 1037 ODE_API void dBodySetFiniteRotationAxis (dBodyID, dReal x, dReal y, dReal z); 1038 1039 /** 1040 * @brief Get the way a body's orientation is updated each timestep. 1041 * @ingroup bodies 1042 * @return the mode 0 (infitesimal) or 1 (finite). 1043 */ 1044 ODE_API int dBodyGetFiniteRotationMode (dBodyID); 1045 1046 /** 1047 * @brief Get the finite rotation axis. 1048 * @param result will contain the axis. 1049 * @ingroup bodies 1050 */ 1051 ODE_API void dBodyGetFiniteRotationAxis (dBodyID, dVector3 result); 1052 1053 /** 1054 * @brief Get the number of joints that are attached to this body. 1055 * @ingroup bodies 1056 * @return nr of joints 1057 */ 1058 ODE_API int dBodyGetNumJoints (dBodyID b); 1059 1060 /** 1061 * @brief Return a joint attached to this body, given by index. 1062 * @ingroup bodies 1063 * @param index valid range is 0 to n-1 where n is the value returned by 1064 * dBodyGetNumJoints(). 1065 */ 1066 ODE_API dJointID dBodyGetJoint (dBodyID, int index); 1067 1068 1069 1070 1071 /** 1072 * @brief Set rigid body to dynamic state (default). 1073 * @param dBodyID identification of body. 1074 * @ingroup bodies 1075 */ 1076 ODE_API void dBodySetDynamic (dBodyID); 1077 1078 /** 1079 * @brief Set rigid body to kinematic state. 1080 * When in kinematic state the body isn't simulated as a dynamic 1081 * body (it's "unstoppable", doesn't respond to forces), 1082 * but can still affect dynamic bodies (e.g. in joints). 1083 * Kinematic bodies can be controlled by position and velocity. 1084 * @note A kinematic body has infinite mass. If you set its mass 1085 * to something else, it loses the kinematic state and behaves 1086 * as a normal dynamic body. 1087 * @param dBodyID identification of body. 1088 * @ingroup bodies 1089 */ 1090 ODE_API void dBodySetKinematic (dBodyID); 1091 1092 /** 1093 * @brief Check wether a body is in kinematic state. 1094 * @ingroup bodies 1095 * @return 1 if a body is kinematic or 0 if it is dynamic. 1096 */ 1097 ODE_API int dBodyIsKinematic (dBodyID); 1098 1099 /** 1100 * @brief Manually enable a body. 1101 * @param dBodyID identification of body. 1102 * @ingroup bodies 1103 */ 1104 ODE_API void dBodyEnable (dBodyID); 1105 1106 /** 1107 * @brief Manually disable a body. 1108 * @ingroup bodies 1109 * @remarks 1110 * A disabled body that is connected through a joint to an enabled body will 1111 * be automatically re-enabled at the next simulation step. 1112 */ 1113 ODE_API void dBodyDisable (dBodyID); 1114 1115 /** 1116 * @brief Check wether a body is enabled. 1117 * @ingroup bodies 1118 * @return 1 if a body is currently enabled or 0 if it is disabled. 1119 */ 1120 ODE_API int dBodyIsEnabled (dBodyID); 1121 1122 /** 1123 * @brief Set whether the body is influenced by the world's gravity or not. 1124 * @ingroup bodies 1125 * @param mode when nonzero gravity affects this body. 1126 * @remarks 1127 * Newly created bodies are always influenced by the world's gravity. 1128 */ 1129 ODE_API void dBodySetGravityMode (dBodyID b, int mode); 1130 1131 /** 1132 * @brief Get whether the body is influenced by the world's gravity or not. 1133 * @ingroup bodies 1134 * @return nonzero means gravity affects this body. 1135 */ 1136 ODE_API int dBodyGetGravityMode (dBodyID b); 1137 1138 /** 1139 * @brief Set the 'moved' callback of a body. 1140 * 1141 * Whenever a body has its position or rotation changed during the 1142 * timestep, the callback will be called (with body as the argument). 1143 * Use it to know which body may need an update in an external 1144 * structure (like a 3D engine). 1145 * 1146 * @param b the body that needs to be watched. 1147 * @param callback the callback to be invoked when the body moves. Set to zero 1148 * to disable. 1149 * @ingroup bodies 1150 */ 1151 ODE_API void dBodySetMovedCallback(dBodyID b, void (*callback)(dBodyID)); 1152 1153 1154 /** 1155 * @brief Return the first geom associated with the body. 1156 * 1157 * You can traverse through the geoms by repeatedly calling 1158 * dBodyGetNextGeom(). 1159 * 1160 * @return the first geom attached to this body, or 0. 1161 * @ingroup bodies 1162 */ 1163 ODE_API dGeomID dBodyGetFirstGeom (dBodyID b); 1164 1165 1166 /** 1167 * @brief returns the next geom associated with the same body. 1168 * @param g a geom attached to some body. 1169 * @return the next geom attached to the same body, or 0. 1170 * @sa dBodyGetFirstGeom 1171 * @ingroup bodies 1172 */ 1173 ODE_API dGeomID dBodyGetNextGeom (dGeomID g); 1174 1175 1176 /** 1177 * @brief Resets the damping settings to the current world's settings. 1178 * @ingroup bodies damping 1179 */ 1180 ODE_API void dBodySetDampingDefaults(dBodyID b); 1181 1182 /** 1183 * @brief Get the body's linear damping scale. 1184 * @ingroup bodies damping 1185 */ 1186 ODE_API dReal dBodyGetLinearDamping (dBodyID b); 1187 1188 /** 1189 * @brief Set the body's linear damping scale. 1190 * @param scale The linear damping scale. Should be in the interval [0, 1]. 1191 * @ingroup bodies damping 1192 * @remarks From now on the body will not use the world's linear damping 1193 * scale until dBodySetDampingDefaults() is called. 1194 * @sa dBodySetDampingDefaults() 1195 */ 1196 ODE_API void dBodySetLinearDamping(dBodyID b, dReal scale); 1197 1198 /** 1199 * @brief Get the body's angular damping scale. 1200 * @ingroup bodies damping 1201 * @remarks If the body's angular damping scale was not set, this function 1202 * returns the world's angular damping scale. 1203 */ 1204 ODE_API dReal dBodyGetAngularDamping (dBodyID b); 1205 1206 /** 1207 * @brief Set the body's angular damping scale. 1208 * @param scale The angular damping scale. Should be in the interval [0, 1]. 1209 * @ingroup bodies damping 1210 * @remarks From now on the body will not use the world's angular damping 1211 * scale until dBodyResetAngularDamping() is called. 1212 * @sa dBodyResetAngularDamping() 1213 */ 1214 ODE_API void dBodySetAngularDamping(dBodyID b, dReal scale); 1215 1216 /** 1217 * @brief Convenience function to set linear and angular scales at once. 1218 * @param linear_scale The linear damping scale. Should be in the interval [0, 1]. 1219 * @param angular_scale The angular damping scale. Should be in the interval [0, 1]. 1220 * @ingroup bodies damping 1221 * @sa dBodySetLinearDamping() dBodySetAngularDamping() 1222 */ 1223 ODE_API void dBodySetDamping(dBodyID b, dReal linear_scale, dReal angular_scale); 1224 1225 /** 1226 * @brief Get the body's linear damping threshold. 1227 * @ingroup bodies damping 1228 */ 1229 ODE_API dReal dBodyGetLinearDampingThreshold (dBodyID b); 1230 1231 /** 1232 * @brief Set the body's linear damping threshold. 1233 * @param threshold The linear threshold to be used. Damping 1234 * is only applied if the linear speed is above this limit. 1235 * @ingroup bodies damping 1236 */ 1237 ODE_API void dBodySetLinearDampingThreshold(dBodyID b, dReal threshold); 1238 1239 /** 1240 * @brief Get the body's angular damping threshold. 1241 * @ingroup bodies damping 1242 */ 1243 ODE_API dReal dBodyGetAngularDampingThreshold (dBodyID b); 1244 1245 /** 1246 * @brief Set the body's angular damping threshold. 1247 * @param threshold The angular threshold to be used. Damping is 1248 * only used if the angular speed is above this limit. 1249 * @ingroup bodies damping 1250 */ 1251 ODE_API void dBodySetAngularDampingThreshold(dBodyID b, dReal threshold); 1252 1253 /** 1254 * @brief Get the body's maximum angular speed. 1255 * @ingroup damping bodies 1256 * @sa dWorldGetMaxAngularSpeed() 1257 */ 1258 ODE_API dReal dBodyGetMaxAngularSpeed (dBodyID b); 1259 1260 /** 1261 * @brief Set the body's maximum angular speed. 1262 * @ingroup damping bodies 1263 * @sa dWorldSetMaxAngularSpeed() dBodyResetMaxAngularSpeed() 1264 * The default value is dInfinity, but it's a good idea to limit 1265 * it at less than 500 if the body has the gyroscopic term 1266 * enabled. 1267 */ 1268 ODE_API void dBodySetMaxAngularSpeed(dBodyID b, dReal max_speed); 1269 1270 1271 1272 /** 1273 * @brief Get the body's gyroscopic state. 1274 * 1275 * @return nonzero if gyroscopic term computation is enabled (default), 1276 * zero otherwise. 1277 * @ingroup bodies 1278 */ 1279 ODE_API int dBodyGetGyroscopicMode(dBodyID b); 1280 1281 1282 /** 1283 * @brief Enable/disable the body's gyroscopic term. 1284 * 1285 * Disabling the gyroscopic term of a body usually improves 1286 * stability. It also helps turning spining objects, like cars' 1287 * wheels. 1288 * 1289 * @param enabled nonzero (default) to enable gyroscopic term, 0 1290 * to disable. 1291 * @ingroup bodies 1292 */ 1293 ODE_API void dBodySetGyroscopicMode(dBodyID b, int enabled); 1294 1295 1296 1297 1298 /** 1299 * @defgroup joints Joints 1300 * 1301 * In real life a joint is something like a hinge, that is used to connect two 1302 * objects. 1303 * In ODE a joint is very similar: It is a relationship that is enforced between 1304 * two bodies so that they can only have certain positions and orientations 1305 * relative to each other. 1306 * This relationship is called a constraint -- the words joint and 1307 * constraint are often used interchangeably. 1308 * 1309 * A joint has a set of parameters that can be set. These include: 1310 * 1311 * 1312 * \li dParamLoStop Low stop angle or position. Setting this to 1313 * -dInfinity (the default value) turns off the low stop. 1314 * For rotational joints, this stop must be greater than -pi to be 1315 * effective. 1316 * \li dParamHiStop High stop angle or position. Setting this to 1317 * dInfinity (the default value) turns off the high stop. 1318 * For rotational joints, this stop must be less than pi to be 1319 * effective. 1320 * If the high stop is less than the low stop then both stops will 1321 * be ineffective. 1322 * \li dParamVel Desired motor velocity (this will be an angular or 1323 * linear velocity). 1324 * \li dParamFMax The maximum force or torque that the motor will use to 1325 * achieve the desired velocity. 1326 * This must always be greater than or equal to zero. 1327 * Setting this to zero (the default value) turns off the motor. 1328 * \li dParamFudgeFactor The current joint stop/motor implementation has 1329 * a small problem: 1330 * when the joint is at one stop and the motor is set to move it away 1331 * from the stop, too much force may be applied for one time step, 1332 * causing a ``jumping'' motion. 1333 * This fudge factor is used to scale this excess force. 1334 * It should have a value between zero and one (the default value). 1335 * If the jumping motion is too visible in a joint, the value can be 1336 * reduced. 1337 * Making this value too small can prevent the motor from being able to 1338 * move the joint away from a stop. 1339 * \li dParamBounce The bouncyness of the stops. 1340 * This is a restitution parameter in the range 0..1. 1341 * 0 means the stops are not bouncy at all, 1 means maximum bouncyness. 1342 * \li dParamCFM The constraint force mixing (CFM) value used when not 1343 * at a stop. 1344 * \li dParamStopERP The error reduction parameter (ERP) used by the 1345 * stops. 1346 * \li dParamStopCFM The constraint force mixing (CFM) value used by the 1347 * stops. Together with the ERP value this can be used to get spongy or 1348 * soft stops. 1349 * Note that this is intended for unpowered joints, it does not really 1350 * work as expected when a powered joint reaches its limit. 1351 * \li dParamSuspensionERP Suspension error reduction parameter (ERP). 1352 * Currently this is only implemented on the hinge-2 joint. 1353 * \li dParamSuspensionCFM Suspension constraint force mixing (CFM) value. 1354 * Currently this is only implemented on the hinge-2 joint. 1355 * 1356 * If a particular parameter is not implemented by a given joint, setting it 1357 * will have no effect. 1358 * These parameter names can be optionally followed by a digit (2 or 3) 1359 * to indicate the second or third set of parameters, e.g. for the second axis 1360 * in a hinge-2 joint, or the third axis in an AMotor joint. 1361 */ 1362 1363 1364 /** 1365 * @brief Create a new joint of the ball type. 1366 * @ingroup joints 1367 * @remarks 1368 * The joint is initially in "limbo" (i.e. it has no effect on the simulation) 1369 * because it does not connect to any bodies. 1370 * @param dJointGroupID set to 0 to allocate the joint normally. 1371 * If it is nonzero the joint is allocated in the given joint group. 1372 */ 1373 ODE_API dJointID dJointCreateBall (dWorldID, dJointGroupID); 1374 1375 /** 1376 * @brief Create a new joint of the hinge type. 1377 * @ingroup joints 1378 * @param dJointGroupID set to 0 to allocate the joint normally. 1379 * If it is nonzero the joint is allocated in the given joint group. 1380 */ 1381 ODE_API dJointID dJointCreateHinge (dWorldID, dJointGroupID); 1382 1383 /** 1384 * @brief Create a new joint of the slider type. 1385 * @ingroup joints 1386 * @param dJointGroupID set to 0 to allocate the joint normally. 1387 * If it is nonzero the joint is allocated in the given joint group. 1388 */ 1389 ODE_API dJointID dJointCreateSlider (dWorldID, dJointGroupID); 1390 1391 /** 1392 * @brief Create a new joint of the contact type. 1393 * @ingroup joints 1394 * @param dJointGroupID set to 0 to allocate the joint normally. 1395 * If it is nonzero the joint is allocated in the given joint group. 1396 */ 1397 ODE_API dJointID dJointCreateContact (dWorldID, dJointGroupID, const dContact *); 1398 1399 /** 1400 * @brief Create a new joint of the hinge2 type. 1401 * @ingroup joints 1402 * @param dJointGroupID set to 0 to allocate the joint normally. 1403 * If it is nonzero the joint is allocated in the given joint group. 1404 */ 1405 ODE_API dJointID dJointCreateHinge2 (dWorldID, dJointGroupID); 1406 1407 /** 1408 * @brief Create a new joint of the universal type. 1409 * @ingroup joints 1410 * @param dJointGroupID set to 0 to allocate the joint normally. 1411 * If it is nonzero the joint is allocated in the given joint group. 1412 */ 1413 ODE_API dJointID dJointCreateUniversal (dWorldID, dJointGroupID); 1414 1415 /** 1416 * @brief Create a new joint of the PR (Prismatic and Rotoide) type. 1417 * @ingroup joints 1418 * @param dJointGroupID set to 0 to allocate the joint normally. 1419 * If it is nonzero the joint is allocated in the given joint group. 1420 */ 1421 ODE_API dJointID dJointCreatePR (dWorldID, dJointGroupID); 1422 1423 /** 1424 * @brief Create a new joint of the PU (Prismatic and Universal) type. 1425 * @ingroup joints 1426 * @param dJointGroupID set to 0 to allocate the joint normally. 1427 * If it is nonzero the joint is allocated in the given joint group. 1428 */ 1429 ODE_API dJointID dJointCreatePU (dWorldID, dJointGroupID); 1430 1431 /** 1432 * @brief Create a new joint of the Piston type. 1433 * @ingroup joints 1434 * @param dJointGroupID set to 0 to allocate the joint normally. 1435 * If it is nonzero the joint is allocated in the given 1436 * joint group. 1437 */ 1438 ODE_API dJointID dJointCreatePiston (dWorldID, dJointGroupID); 1439 1440 /** 1441 * @brief Create a new joint of the fixed type. 1442 * @ingroup joints 1443 * @param dJointGroupID set to 0 to allocate the joint normally. 1444 * If it is nonzero the joint is allocated in the given joint group. 1445 */ 1446 ODE_API dJointID dJointCreateFixed (dWorldID, dJointGroupID); 1447 1448 ODE_API dJointID dJointCreateNull (dWorldID, dJointGroupID); 1449 1450 /** 1451 * @brief Create a new joint of the A-motor type. 1452 * @ingroup joints 1453 * @param dJointGroupID set to 0 to allocate the joint normally. 1454 * If it is nonzero the joint is allocated in the given joint group. 1455 */ 1456 ODE_API dJointID dJointCreateAMotor (dWorldID, dJointGroupID); 1457 1458 /** 1459 * @brief Create a new joint of the L-motor type. 1460 * @ingroup joints 1461 * @param dJointGroupID set to 0 to allocate the joint normally. 1462 * If it is nonzero the joint is allocated in the given joint group. 1463 */ 1464 ODE_API dJointID dJointCreateLMotor (dWorldID, dJointGroupID); 1465 1466 /** 1467 * @brief Create a new joint of the plane-2d type. 1468 * @ingroup joints 1469 * @param dJointGroupID set to 0 to allocate the joint normally. 1470 * If it is nonzero the joint is allocated in the given joint group. 1471 */ 1472 ODE_API dJointID dJointCreatePlane2D (dWorldID, dJointGroupID); 1473 1474 /** 1475 * @brief Destroy a joint. 1476 * @ingroup joints 1477 * 1478 * disconnects it from its attached bodies and removing it from the world. 1479 * However, if the joint is a member of a group then this function has no 1480 * effect - to destroy that joint the group must be emptied or destroyed. 1481 */ 1482 ODE_API void dJointDestroy (dJointID); 1483 1484 1485 /** 1486 * @brief Create a joint group 1487 * @ingroup joints 1488 * @param max_size deprecated. Set to 0. 1489 */ 1490 ODE_API dJointGroupID dJointGroupCreate (int max_size); 1491 1492 /** 1493 * @brief Destroy a joint group. 1494 * @ingroup joints 1495 * 1496 * All joints in the joint group will be destroyed. 1497 */ 1498 ODE_API void dJointGroupDestroy (dJointGroupID); 1499 1500 /** 1501 * @brief Empty a joint group. 1502 * @ingroup joints 1503 * 1504 * All joints in the joint group will be destroyed, 1505 * but the joint group itself will not be destroyed. 1506 */ 1507 ODE_API void dJointGroupEmpty (dJointGroupID); 1508 1509 /** 1510 * @brief Return the number of bodies attached to the joint 1511 * @ingroup joints 1512 */ 1513 ODE_API int dJointGetNumBodies(dJointID); 1514 1515 /** 1516 * @brief Attach the joint to some new bodies. 1517 * @ingroup joints 1518 * 1519 * If the joint is already attached, it will be detached from the old bodies 1520 * first. 1521 * To attach this joint to only one body, set body1 or body2 to zero - a zero 1522 * body refers to the static environment. 1523 * Setting both bodies to zero puts the joint into "limbo", i.e. it will 1524 * have no effect on the simulation. 1525 * @remarks 1526 * Some joints, like hinge-2 need to be attached to two bodies to work. 1527 */ 1528 ODE_API void dJointAttach (dJointID, dBodyID body1, dBodyID body2); 1529 1530 /** 1531 * @brief Manually enable a joint. 1532 * @param dJointID identification of joint. 1533 * @ingroup joints 1534 */ 1535 ODE_API void dJointEnable (dJointID); 1536 1537 /** 1538 * @brief Manually disable a joint. 1539 * @ingroup joints 1540 * @remarks 1541 * A disabled joint will not affect the simulation, but will maintain the anchors and 1542 * axes so it can be enabled later. 1543 */ 1544 ODE_API void dJointDisable (dJointID); 1545 1546 /** 1547 * @brief Check wether a joint is enabled. 1548 * @ingroup joints 1549 * @return 1 if a joint is currently enabled or 0 if it is disabled. 1550 */ 1551 ODE_API int dJointIsEnabled (dJointID); 1552 1553 /** 1554 * @brief Set the user-data pointer 1555 * @ingroup joints 1556 */ 1557 ODE_API void dJointSetData (dJointID, void *data); 1558 1559 /** 1560 * @brief Get the user-data pointer 1561 * @ingroup joints 1562 */ 1563 ODE_API void *dJointGetData (dJointID); 1564 1565 /** 1566 * @brief Get the type of the joint 1567 * @ingroup joints 1568 * @return the type, being one of these: 1569 * \li dJointTypeBall 1570 * \li dJointTypeHinge 1571 * \li dJointTypeSlider 1572 * \li dJointTypeContact 1573 * \li dJointTypeUniversal 1574 * \li dJointTypeHinge2 1575 * \li dJointTypeFixed 1576 * \li dJointTypeNull 1577 * \li dJointTypeAMotor 1578 * \li dJointTypeLMotor 1579 * \li dJointTypePlane2D 1580 * \li dJointTypePR 1581 * \li dJointTypePU 1582 * \li dJointTypePiston 1583 */ 1584 ODE_API dJointType dJointGetType (dJointID); 1585 1586 /** 1587 * @brief Return the bodies that this joint connects. 1588 * @ingroup joints 1589 * @param index return the first (0) or second (1) body. 1590 * @remarks 1591 * If one of these returned body IDs is zero, the joint connects the other body 1592 * to the static environment. 1593 * If both body IDs are zero, the joint is in ``limbo'' and has no effect on 1594 * the simulation. 1595 */ 1596 ODE_API dBodyID dJointGetBody (dJointID, int index); 1597 1598 /** 1599 * @brief Sets the datastructure that is to receive the feedback. 1600 * 1601 * The feedback can be used by the user, so that it is known how 1602 * much force an individual joint exerts. 1603 * @ingroup joints 1604 */ 1605 ODE_API void dJointSetFeedback (dJointID, dJointFeedback *); 1606 1607 /** 1608 * @brief Gets the datastructure that is to receive the feedback. 1609 * @ingroup joints 1610 */ 1611 ODE_API dJointFeedback *dJointGetFeedback (dJointID); 1612 1613 /** 1614 * @brief Set the joint anchor point. 1615 * @ingroup joints 1616 * 1617 * The joint will try to keep this point on each body 1618 * together. The input is specified in world coordinates. 1619 */ 1620 ODE_API void dJointSetBallAnchor (dJointID, dReal x, dReal y, dReal z); 1621 1622 /** 1623 * @brief Set the joint anchor point. 1624 * @ingroup joints 1625 */ 1626 ODE_API void dJointSetBallAnchor2 (dJointID, dReal x, dReal y, dReal z); 1627 1628 /** 1629 * @brief Param setting for Ball joints 1630 * @ingroup joints 1631 */ 1632 ODE_API void dJointSetBallParam (dJointID, int parameter, dReal value); 1633 1634 /** 1635 * @brief Set hinge anchor parameter. 1636 * @ingroup joints 1637 */ 1638 ODE_API void dJointSetHingeAnchor (dJointID, dReal x, dReal y, dReal z); 1639 1640 ODE_API void dJointSetHingeAnchorDelta (dJointID, dReal x, dReal y, dReal z, dReal ax, dReal ay, dReal az); 1641 1642 /** 1643 * @brief Set hinge axis. 1644 * @ingroup joints 1645 */ 1646 ODE_API void dJointSetHingeAxis (dJointID, dReal x, dReal y, dReal z); 1647 1648 /** 1649 * @brief Set the Hinge axis as if the 2 bodies were already at angle appart. 1650 * @ingroup joints 1651 * 1652 * This function initialize the Axis and the relative orientation of each body 1653 * as if body1 was rotated around the axis by the angle value. \br 1654 * Ex: 1655 * <PRE> 1656 * dJointSetHingeAxis(jId, 1, 0, 0); 1657 * // If you request the position you will have: dJointGetHingeAngle(jId) == 0 1658 * dJointSetHingeAxisDelta(jId, 1, 0, 0, 0.23); 1659 * // If you request the position you will have: dJointGetHingeAngle(jId) == 0.23 1660 * </PRE> 1661 1662 * @param j The Hinge joint ID for which the axis will be set 1663 * @param x The X component of the axis in world frame 1664 * @param y The Y component of the axis in world frame 1665 * @param z The Z component of the axis in world frame 1666 * @param angle The angle for the offset of the relative orientation. 1667 * As if body1 was rotated by angle when the Axis was set (see below). 1668 * The rotation is around the new Hinge axis. 1669 * 1670 * @note Usually the function dJointSetHingeAxis set the current position of body1 1671 * and body2 as the zero angle position. This function set the current position 1672 * as the if the 2 bodies where \b angle appart. 1673 * @warning Calling dJointSetHingeAnchor or dJointSetHingeAxis will reset the "zero" 1674 * angle position. 1675 */ 1676 ODE_API void dJointSetHingeAxisOffset (dJointID j, dReal x, dReal y, dReal z, dReal angle); 1677 1678 /** 1679 * @brief set joint parameter 1680 * @ingroup joints 1681 */ 1682 ODE_API void dJointSetHingeParam (dJointID, int parameter, dReal value); 1683 1684 /** 1685 * @brief Applies the torque about the hinge axis. 1686 * 1687 * That is, it applies a torque with specified magnitude in the direction 1688 * of the hinge axis, to body 1, and with the same magnitude but in opposite 1689 * direction to body 2. This function is just a wrapper for dBodyAddTorque()} 1690 * @ingroup joints 1691 */ 1692 ODE_API void dJointAddHingeTorque(dJointID joint, dReal torque); 1693 1694 /** 1695 * @brief set the joint axis 1696 * @ingroup joints 1697 */ 1698 ODE_API void dJointSetSliderAxis (dJointID, dReal x, dReal y, dReal z); 1699 1700 /** 1701 * @ingroup joints 1702 */ 1703 ODE_API void dJointSetSliderAxisDelta (dJointID, dReal x, dReal y, dReal z, dReal ax, dReal ay, dReal az); 1704 1705 /** 1706 * @brief set joint parameter 1707 * @ingroup joints 1708 */ 1709 ODE_API void dJointSetSliderParam (dJointID, int parameter, dReal value); 1710 1711 /** 1712 * @brief Applies the given force in the slider's direction. 1713 * 1714 * That is, it applies a force with specified magnitude, in the direction of 1715 * slider's axis, to body1, and with the same magnitude but opposite 1716 * direction to body2. This function is just a wrapper for dBodyAddForce(). 1717 * @ingroup joints 1718 */ 1719 ODE_API void dJointAddSliderForce(dJointID joint, dReal force); 1720 1721 /** 1722 * @brief set anchor 1723 * @ingroup joints 1724 */ 1725 ODE_API void dJointSetHinge2Anchor (dJointID, dReal x, dReal y, dReal z); 1726 1727 /** 1728 * @brief set axis 1729 * @ingroup joints 1730 */ 1731 ODE_API void dJointSetHinge2Axis1 (dJointID, dReal x, dReal y, dReal z); 1732 1733 /** 1734 * @brief set axis 1735 * @ingroup joints 1736 */ 1737 ODE_API void dJointSetHinge2Axis2 (dJointID, dReal x, dReal y, dReal z); 1738 1739 /** 1740 * @brief set joint parameter 1741 * @ingroup joints 1742 */ 1743 ODE_API void dJointSetHinge2Param (dJointID, int parameter, dReal value); 1744 1745 /** 1746 * @brief Applies torque1 about the hinge2's axis 1, torque2 about the 1747 * hinge2's axis 2. 1748 * @remarks This function is just a wrapper for dBodyAddTorque(). 1749 * @ingroup joints 1750 */ 1751 ODE_API void dJointAddHinge2Torques(dJointID joint, dReal torque1, dReal torque2); 1752 1753 /** 1754 * @brief set anchor 1755 * @ingroup joints 1756 */ 1757 ODE_API void dJointSetUniversalAnchor (dJointID, dReal x, dReal y, dReal z); 1758 1759 /** 1760 * @brief set axis 1761 * @ingroup joints 1762 */ 1763 ODE_API void dJointSetUniversalAxis1 (dJointID, dReal x, dReal y, dReal z); 1764 1765 /** 1766 * @brief Set the Universal axis1 as if the 2 bodies were already at 1767 * offset1 and offset2 appart with respect to axis1 and axis2. 1768 * @ingroup joints 1769 * 1770 * This function initialize the axis1 and the relative orientation of 1771 * each body as if body1 was rotated around the new axis1 by the offset1 1772 * value and as if body2 was rotated around the axis2 by offset2. \br 1773 * Ex: 1774 * <PRE> 1775 * dJointSetHuniversalAxis1(jId, 1, 0, 0); 1776 * // If you request the position you will have: dJointGetUniversalAngle1(jId) == 0 1777 * // If you request the position you will have: dJointGetUniversalAngle2(jId) == 0 1778 * dJointSetHuniversalAxis1Offset(jId, 1, 0, 0, 0.2, 0.17); 1779 * // If you request the position you will have: dJointGetUniversalAngle1(jId) == 0.2 1780 * // If you request the position you will have: dJointGetUniversalAngle2(jId) == 0.17 1781 * </PRE> 1782 * 1783 * @param j The Hinge joint ID for which the axis will be set 1784 * @param x The X component of the axis in world frame 1785 * @param y The Y component of the axis in world frame 1786 * @param z The Z component of the axis in world frame 1787 * @param angle The angle for the offset of the relative orientation. 1788 * As if body1 was rotated by angle when the Axis was set (see below). 1789 * The rotation is around the new Hinge axis. 1790 * 1791 * @note Usually the function dJointSetHingeAxis set the current position of body1 1792 * and body2 as the zero angle position. This function set the current position 1793 * as the if the 2 bodies where \b offsets appart. 1794 * 1795 * @note Any previous offsets are erased. 1796 * 1797 * @warning Calling dJointSetUniversalAnchor, dJointSetUnivesalAxis1, 1798 * dJointSetUniversalAxis2, dJointSetUniversalAxis2Offset 1799 * will reset the "zero" angle position. 1800 */ 1801 ODE_API void dJointSetUniversalAxis1Offset (dJointID, dReal x, dReal y, dReal z, 1802 dReal offset1, dReal offset2); 1803 1804 /** 1805 * @brief set axis 1806 * @ingroup joints 1807 */ 1808 ODE_API void dJointSetUniversalAxis2 (dJointID, dReal x, dReal y, dReal z); 1809 1810 /** 1811 * @brief Set the Universal axis2 as if the 2 bodies were already at 1812 * offset1 and offset2 appart with respect to axis1 and axis2. 1813 * @ingroup joints 1814 * 1815 * This function initialize the axis2 and the relative orientation of 1816 * each body as if body1 was rotated around the axis1 by the offset1 1817 * value and as if body2 was rotated around the new axis2 by offset2. \br 1818 * Ex: 1819 * <PRE> 1820 * dJointSetHuniversalAxis2(jId, 0, 1, 0); 1821 * // If you request the position you will have: dJointGetUniversalAngle1(jId) == 0 1822 * // If you request the position you will have: dJointGetUniversalAngle2(jId) == 0 1823 * dJointSetHuniversalAxis2Offset(jId, 0, 1, 0, 0.2, 0.17); 1824 * // If you request the position you will have: dJointGetUniversalAngle1(jId) == 0.2 1825 * // If you request the position you will have: dJointGetUniversalAngle2(jId) == 0.17 1826 * </PRE> 1827 1828 * @param j The Hinge joint ID for which the axis will be set 1829 * @param x The X component of the axis in world frame 1830 * @param y The Y component of the axis in world frame 1831 * @param z The Z component of the axis in world frame 1832 * @param angle The angle for the offset of the relative orientation. 1833 * As if body1 was rotated by angle when the Axis was set (see below). 1834 * The rotation is around the new Hinge axis. 1835 * 1836 * @note Usually the function dJointSetHingeAxis set the current position of body1 1837 * and body2 as the zero angle position. This function set the current position 1838 * as the if the 2 bodies where \b offsets appart. 1839 * 1840 * @note Any previous offsets are erased. 1841 * 1842 * @warning Calling dJointSetUniversalAnchor, dJointSetUnivesalAxis1, 1843 * dJointSetUniversalAxis2, dJointSetUniversalAxis2Offset 1844 * will reset the "zero" angle position. 1845 */ 1846 1847 1848 ODE_API void dJointSetUniversalAxis2Offset (dJointID, dReal x, dReal y, dReal z, 1849 dReal offset1, dReal offset2); 1850 1851 /** 1852 * @brief set joint parameter 1853 * @ingroup joints 1854 */ 1855 ODE_API void dJointSetUniversalParam (dJointID, int parameter, dReal value); 1856 1857 /** 1858 * @brief Applies torque1 about the universal's axis 1, torque2 about the 1859 * universal's axis 2. 1860 * @remarks This function is just a wrapper for dBodyAddTorque(). 1861 * @ingroup joints 1862 */ 1863 ODE_API void dJointAddUniversalTorques(dJointID joint, dReal torque1, dReal torque2); 1864 1865 1866 /** 1867 * @brief set anchor 1868 * @ingroup joints 1869 */ 1870 ODE_API void dJointSetPRAnchor (dJointID, dReal x, dReal y, dReal z); 1871 1872 /** 1873 * @brief set the axis for the prismatic articulation 1874 * @ingroup joints 1875 */ 1876 ODE_API void dJointSetPRAxis1 (dJointID, dReal x, dReal y, dReal z); 1877 1878 /** 1879 * @brief set the axis for the rotoide articulation 1880 * @ingroup joints 1881 */ 1882 ODE_API void dJointSetPRAxis2 (dJointID, dReal x, dReal y, dReal z); 1883 1884 /** 1885 * @brief set joint parameter 1886 * @ingroup joints 1887 * 1888 * @note parameterX where X equal 2 refer to parameter for the rotoide articulation 1889 */ 1890 ODE_API void dJointSetPRParam (dJointID, int parameter, dReal value); 1891 1892 /** 1893 * @brief Applies the torque about the rotoide axis of the PR joint 1894 * 1895 * That is, it applies a torque with specified magnitude in the direction 1896 * of the rotoide axis, to body 1, and with the same magnitude but in opposite 1897 * direction to body 2. This function is just a wrapper for dBodyAddTorque()} 1898 * @ingroup joints 1899 */ 1900 ODE_API void dJointAddPRTorque (dJointID j, dReal torque); 1901 1902 1903 /** 1904 * @brief set anchor 1905 * @ingroup joints 1906 */ 1907 ODE_API void dJointSetPUAnchor (dJointID, dReal x, dReal y, dReal z); 1908 1909 /** 1910 * @brief set anchor 1911 * @ingroup joints 1912 */ 1913 ODE_API_DEPRECATED ODE_API void dJointSetPUAnchorDelta (dJointID, dReal x, dReal y, dReal z, 1914 dReal dx, dReal dy, dReal dz); 1915 1916 /** 1917 * @brief Set the PU anchor as if the 2 bodies were already at [dx, dy, dz] appart. 1918 * @ingroup joints 1919 * 1920 * This function initialize the anchor and the relative position of each body 1921 * as if the position between body1 and body2 was already the projection of [dx, dy, dz] 1922 * along the Piston axis. (i.e as if the body1 was at its current position - [dx,dy,dy] when the 1923 * axis is set). 1924 * Ex: 1925 * <PRE> 1926 * dReal offset = 3; 1927 * dVector3 axis; 1928 * dJointGetPUAxis(jId, axis); 1929 * dJointSetPUAnchor(jId, 0, 0, 0); 1930 * // If you request the position you will have: dJointGetPUPosition(jId) == 0 1931 * dJointSetPUAnchorOffset(jId, 0, 0, 0, axis[X]*offset, axis[Y]*offset, axis[Z]*offset); 1932 * // If you request the position you will have: dJointGetPUPosition(jId) == offset 1933 * </PRE> 1934 * @param j The PU joint for which the anchor point will be set 1935 * @param x The X position of the anchor point in world frame 1936 * @param y The Y position of the anchor point in world frame 1937 * @param z The Z position of the anchor point in world frame 1938 * @param dx A delta to be substracted to the X position as if the anchor was set 1939 * when body1 was at current_position[X] - dx 1940 * @param dx A delta to be substracted to the Y position as if the anchor was set 1941 * when body1 was at current_position[Y] - dy 1942 * @param dx A delta to be substracted to the Z position as if the anchor was set 1943 * when body1 was at current_position[Z] - dz 1944 */ 1945 ODE_API void dJointSetPUAnchorOffset (dJointID, dReal x, dReal y, dReal z, 1946 dReal dx, dReal dy, dReal dz); 1947 1948 /** 1949 * @brief set the axis for the first axis or the universal articulation 1950 * @ingroup joints 1951 */ 1952 ODE_API void dJointSetPUAxis1 (dJointID, dReal x, dReal y, dReal z); 1953 1954 /** 1955 * @brief set the axis for the second axis or the universal articulation 1956 * @ingroup joints 1957 */ 1958 ODE_API void dJointSetPUAxis2 (dJointID, dReal x, dReal y, dReal z); 1959 1960 /** 1961 * @brief set the axis for the prismatic articulation 1962 * @ingroup joints 1963 */ 1964 ODE_API void dJointSetPUAxis3 (dJointID, dReal x, dReal y, dReal z); 1965 1966 /** 1967 * @brief set the axis for the prismatic articulation 1968 * @ingroup joints 1969 * @note This function was added for convenience it is the same as 1970 * dJointSetPUAxis3 1971 */ 1972 ODE_API void dJointSetPUAxisP (dJointID id, dReal x, dReal y, dReal z); 1973 1974 1975 1976 /** 1977 * @brief set joint parameter 1978 * @ingroup joints 1979 * 1980 * @note parameterX where X equal 2 refer to parameter for second axis of the 1981 * universal articulation 1982 * @note parameterX where X equal 3 refer to parameter for prismatic 1983 * articulation 1984 */ 1985 ODE_API void dJointSetPUParam (dJointID, int parameter, dReal value); 1986 1987 /** 1988 * @brief Applies the torque about the rotoide axis of the PU joint 1989 * 1990 * That is, it applies a torque with specified magnitude in the direction 1991 * of the rotoide axis, to body 1, and with the same magnitude but in opposite 1992 * direction to body 2. This function is just a wrapper for dBodyAddTorque()} 1993 * @ingroup joints 1994 */ 1995 ODE_API void dJointAddPUTorque (dJointID j, dReal torque); 1996 1997 1998 1999 2000 /** 2001 * @brief set the joint anchor 2002 * @ingroup joints 2003 */ 2004 ODE_API void dJointSetPistonAnchor (dJointID, dReal x, dReal y, dReal z); 2005 2006 /** 2007 * @brief Set the Piston anchor as if the 2 bodies were already at [dx,dy, dz] appart. 2008 * @ingroup joints 2009 * 2010 * This function initialize the anchor and the relative position of each body 2011 * as if the position between body1 and body2 was already the projection of [dx, dy, dz] 2012 * along the Piston axis. (i.e as if the body1 was at its current position - [dx,dy,dy] when the 2013 * axis is set). 2014 * Ex: 2015 * <PRE> 2016 * dReal offset = 3; 2017 * dVector3 axis; 2018 * dJointGetPistonAxis(jId, axis); 2019 * dJointSetPistonAnchor(jId, 0, 0, 0); 2020 * // If you request the position you will have: dJointGetPistonPosition(jId) == 0 2021 * dJointSetPistonAnchorOffset(jId, 0, 0, 0, axis[X]*offset, axis[Y]*offset, axis[Z]*offset); 2022 * // If you request the position you will have: dJointGetPistonPosition(jId) == offset 2023 * </PRE> 2024 * @param j The Piston joint for which the anchor point will be set 2025 * @param x The X position of the anchor point in world frame 2026 * @param y The Y position of the anchor point in world frame 2027 * @param z The Z position of the anchor point in world frame 2028 * @param dx A delta to be substracted to the X position as if the anchor was set 2029 * when body1 was at current_position[X] - dx 2030 * @param dx A delta to be substracted to the Y position as if the anchor was set 2031 * when body1 was at current_position[Y] - dy 2032 * @param dx A delta to be substracted to the Z position as if the anchor was set 2033 * when body1 was at current_position[Z] - dz 2034 */ 2035 ODE_API void dJointSetPistonAnchorOffset(dJointID j, dReal x, dReal y, dReal z, 2036 dReal dx, dReal dy, dReal dz); 2037 2038 /** 2039 * @brief set the joint axis 2040 * @ingroup joints 2041 */ 2042 ODE_API void dJointSetPistonAxis (dJointID, dReal x, dReal y, dReal z); 2043 2044 /** 2045 * This function set prismatic axis of the joint and also set the position 2046 * of the joint. 2047 * 2048 * @ingroup joints 2049 * @param j The joint affected by this function 2050 * @param x The x component of the axis 2051 * @param y The y component of the axis 2052 * @param z The z component of the axis 2053 * @param dx The Initial position of the prismatic join in the x direction 2054 * @param dy The Initial position of the prismatic join in the y direction 2055 * @param dz The Initial position of the prismatic join in the z direction 2056 */ 2057 ODE_API_DEPRECATED ODE_API void dJointSetPistonAxisDelta (dJointID j, dReal x, dReal y, dReal z, dReal ax, dReal ay, dReal az); 2058 2059 /** 2060 * @brief set joint parameter 2061 * @ingroup joints 2062 */ 2063 ODE_API void dJointSetPistonParam (dJointID, int parameter, dReal value); 2064 2065 /** 2066 * @brief Applies the given force in the slider's direction. 2067 * 2068 * That is, it applies a force with specified magnitude, in the direction of 2069 * prismatic's axis, to body1, and with the same magnitude but opposite 2070 * direction to body2. This function is just a wrapper for dBodyAddForce(). 2071 * @ingroup joints 2072 */ 2073 ODE_API void dJointAddPistonForce (dJointID joint, dReal force); 2074 2075 2076 /** 2077 * @brief Call this on the fixed joint after it has been attached to 2078 * remember the current desired relative offset and desired relative 2079 * rotation between the bodies. 2080 * @ingroup joints 2081 */ 2082 ODE_API void dJointSetFixed (dJointID); 2083 2084 /* 2085 * @brief Sets joint parameter 2086 * 2087 * @ingroup joints 2088 */ 2089 ODE_API void dJointSetFixedParam (dJointID, int parameter, dReal value); 2090 2091 /** 2092 * @brief set the nr of axes 2093 * @param num 0..3 2094 * @ingroup joints 2095 */ 2096 ODE_API void dJointSetAMotorNumAxes (dJointID, int num); 2097 2098 /** 2099 * @brief set axis 2100 * @ingroup joints 2101 */ 2102 ODE_API void dJointSetAMotorAxis (dJointID, int anum, int rel, 2103 dReal x, dReal y, dReal z); 2104 2105 /** 2106 * @brief Tell the AMotor what the current angle is along axis anum. 2107 * 2108 * This function should only be called in dAMotorUser mode, because in this 2109 * mode the AMotor has no other way of knowing the joint angles. 2110 * The angle information is needed if stops have been set along the axis, 2111 * but it is not needed for axis motors. 2112 * @ingroup joints 2113 */ 2114 ODE_API void dJointSetAMotorAngle (dJointID, int anum, dReal angle); 2115 2116 /** 2117 * @brief set joint parameter 2118 * @ingroup joints 2119 */ 2120 ODE_API void dJointSetAMotorParam (dJointID, int parameter, dReal value); 2121 2122 /** 2123 * @brief set mode 2124 * @ingroup joints 2125 */ 2126 ODE_API void dJointSetAMotorMode (dJointID, int mode); 2127 2128 /** 2129 * @brief Applies torque0 about the AMotor's axis 0, torque1 about the 2130 * AMotor's axis 1, and torque2 about the AMotor's axis 2. 2131 * @remarks 2132 * If the motor has fewer than three axes, the higher torques are ignored. 2133 * This function is just a wrapper for dBodyAddTorque(). 2134 * @ingroup joints 2135 */ 2136 ODE_API void dJointAddAMotorTorques (dJointID, dReal torque1, dReal torque2, dReal torque3); 2137 2138 /** 2139 * @brief Set the number of axes that will be controlled by the LMotor. 2140 * @param num can range from 0 (which effectively deactivates the joint) to 3. 2141 * @ingroup joints 2142 */ 2143 ODE_API void dJointSetLMotorNumAxes (dJointID, int num); 2144 2145 /** 2146 * @brief Set the AMotor axes. 2147 * @param anum selects the axis to change (0,1 or 2). 2148 * @param rel Each axis can have one of three ``relative orientation'' modes 2149 * \li 0: The axis is anchored to the global frame. 2150 * \li 1: The axis is anchored to the first body. 2151 * \li 2: The axis is anchored to the second body. 2152 * @remarks The axis vector is always specified in global coordinates 2153 * regardless of the setting of rel. 2154 * @ingroup joints 2155 */ 2156 ODE_API void dJointSetLMotorAxis (dJointID, int anum, int rel, dReal x, dReal y, dReal z); 2157 2158 /** 2159 * @brief set joint parameter 2160 * @ingroup joints 2161 */ 2162 ODE_API void dJointSetLMotorParam (dJointID, int parameter, dReal value); 2163 2164 /** 2165 * @ingroup joints 2166 */ 2167 ODE_API void dJointSetPlane2DXParam (dJointID, int parameter, dReal value); 2168 2169 /** 2170 * @ingroup joints 2171 */ 2172 2173 ODE_API void dJointSetPlane2DYParam (dJointID, int parameter, dReal value); 2174 2175 /** 2176 * @ingroup joints 2177 */ 2178 ODE_API void dJointSetPlane2DAngleParam (dJointID, int parameter, dReal value); 2179 2180 /** 2181 * @brief Get the joint anchor point, in world coordinates. 2182 * 2183 * This returns the point on body 1. If the joint is perfectly satisfied, 2184 * this will be the same as the point on body 2. 2185 */ 2186 ODE_API void dJointGetBallAnchor (dJointID, dVector3 result); 2187 2188 /** 2189 * @brief Get the joint anchor point, in world coordinates. 2190 * 2191 * This returns the point on body 2. You can think of a ball and socket 2192 * joint as trying to keep the result of dJointGetBallAnchor() and 2193 * dJointGetBallAnchor2() the same. If the joint is perfectly satisfied, 2194 * this function will return the same value as dJointGetBallAnchor() to 2195 * within roundoff errors. dJointGetBallAnchor2() can be used, along with 2196 * dJointGetBallAnchor(), to see how far the joint has come apart. 2197 */ 2198 ODE_API void dJointGetBallAnchor2 (dJointID, dVector3 result); 2199 2200 /** 2201 * @brief get joint parameter 2202 * @ingroup joints 2203 */ 2204 ODE_API dReal dJointGetBallParam (dJointID, int parameter); 2205 2206 /** 2207 * @brief Get the hinge anchor point, in world coordinates. 2208 * 2209 * This returns the point on body 1. If the joint is perfectly satisfied, 2210 * this will be the same as the point on body 2. 2211 * @ingroup joints 2212 */ 2213 ODE_API void dJointGetHingeAnchor (dJointID, dVector3 result); 2214 2215 /** 2216 * @brief Get the joint anchor point, in world coordinates. 2217 * @return The point on body 2. If the joint is perfectly satisfied, 2218 * this will return the same value as dJointGetHingeAnchor(). 2219 * If not, this value will be slightly different. 2220 * This can be used, for example, to see how far the joint has come apart. 2221 * @ingroup joints 2222 */ 2223 ODE_API void dJointGetHingeAnchor2 (dJointID, dVector3 result); 2224 2225 /** 2226 * @brief get axis 2227 * @ingroup joints 2228 */ 2229 ODE_API void dJointGetHingeAxis (dJointID, dVector3 result); 2230 2231 /** 2232 * @brief get joint parameter 2233 * @ingroup joints 2234 */ 2235 ODE_API dReal dJointGetHingeParam (dJointID, int parameter); 2236 2237 /** 2238 * @brief Get the hinge angle. 2239 * 2240 * The angle is measured between the two bodies, or between the body and 2241 * the static environment. 2242 * The angle will be between -pi..pi. 2243 * Give the relative rotation with respect to the Hinge axis of Body 1 with 2244 * respect to Body 2. 2245 * When the hinge anchor or axis is set, the current position of the attached 2246 * bodies is examined and that position will be the zero angle. 2247 * @ingroup joints 2248 */ 2249 ODE_API dReal dJointGetHingeAngle (dJointID); 2250 2251 /** 2252 * @brief Get the hinge angle time derivative. 2253 * @ingroup joints 2254 */ 2255 ODE_API dReal dJointGetHingeAngleRate (dJointID); 2256 2257 /** 2258 * @brief Get the slider linear position (i.e. the slider's extension) 2259 * 2260 * When the axis is set, the current position of the attached bodies is 2261 * examined and that position will be the zero position. 2262 2263 * The position is the distance, with respect to the zero position, 2264 * along the slider axis of body 1 with respect to 2265 * body 2. (A NULL body is replaced by the world). 2266 * @ingroup joints 2267 */ 2268 ODE_API dReal dJointGetSliderPosition (dJointID); 2269 2270 /** 2271 * @brief Get the slider linear position's time derivative. 2272 * @ingroup joints 2273 */ 2274 ODE_API dReal dJointGetSliderPositionRate (dJointID); 2275 2276 /** 2277 * @brief Get the slider axis 2278 * @ingroup joints 2279 */ 2280 ODE_API void dJointGetSliderAxis (dJointID, dVector3 result); 2281 2282 /** 2283 * @brief get joint parameter 2284 * @ingroup joints 2285 */ 2286 ODE_API dReal dJointGetSliderParam (dJointID, int parameter); 2287 2288 /** 2289 * @brief Get the joint anchor point, in world coordinates. 2290 * @return the point on body 1. If the joint is perfectly satisfied, 2291 * this will be the same as the point on body 2. 2292 * @ingroup joints 2293 */ 2294 ODE_API void dJointGetHinge2Anchor (dJointID, dVector3 result); 2295 2296 /** 2297 * @brief Get the joint anchor point, in world coordinates. 2298 * This returns the point on body 2. If the joint is perfectly satisfied, 2299 * this will return the same value as dJointGetHinge2Anchor. 2300 * If not, this value will be slightly different. 2301 * This can be used, for example, to see how far the joint has come apart. 2302 * @ingroup joints 2303 */ 2304 ODE_API void dJointGetHinge2Anchor2 (dJointID, dVector3 result); 2305 2306 /** 2307 * @brief Get joint axis 2308 * @ingroup joints 2309 */ 2310 ODE_API void dJointGetHinge2Axis1 (dJointID, dVector3 result); 2311 2312 /** 2313 * @brief Get joint axis 2314 * @ingroup joints 2315 */ 2316 ODE_API void dJointGetHinge2Axis2 (dJointID, dVector3 result); 2317 2318 /** 2319 * @brief get joint parameter 2320 * @ingroup joints 2321 */ 2322 ODE_API dReal dJointGetHinge2Param (dJointID, int parameter); 2323 2324 /** 2325 * @brief Get angle 2326 * @ingroup joints 2327 */ 2328 ODE_API dReal dJointGetHinge2Angle1 (dJointID); 2329 2330 /** 2331 * @brief Get time derivative of angle 2332 * @ingroup joints 2333 */ 2334 ODE_API dReal dJointGetHinge2Angle1Rate (dJointID); 2335 2336 /** 2337 * @brief Get time derivative of angle 2338 * @ingroup joints 2339 */ 2340 ODE_API dReal dJointGetHinge2Angle2Rate (dJointID); 2341 2342 /** 2343 * @brief Get the joint anchor point, in world coordinates. 2344 * @return the point on body 1. If the joint is perfectly satisfied, 2345 * this will be the same as the point on body 2. 2346 * @ingroup joints 2347 */ 2348 ODE_API void dJointGetUniversalAnchor (dJointID, dVector3 result); 2349 2350 /** 2351 * @brief Get the joint anchor point, in world coordinates. 2352 * @return This returns the point on body 2. 2353 * @remarks 2354 * You can think of the ball and socket part of a universal joint as 2355 * trying to keep the result of dJointGetBallAnchor() and 2356 * dJointGetBallAnchor2() the same. If the joint is 2357 * perfectly satisfied, this function will return the same value 2358 * as dJointGetUniversalAnchor() to within roundoff errors. 2359 * dJointGetUniversalAnchor2() can be used, along with 2360 * dJointGetUniversalAnchor(), to see how far the joint has come apart. 2361 * @ingroup joints 2362 */ 2363 ODE_API void dJointGetUniversalAnchor2 (dJointID, dVector3 result); 2364 2365 /** 2366 * @brief Get axis 2367 * @ingroup joints 2368 */ 2369 ODE_API void dJointGetUniversalAxis1 (dJointID, dVector3 result); 2370 2371 /** 2372 * @brief Get axis 2373 * @ingroup joints 2374 */ 2375 ODE_API void dJointGetUniversalAxis2 (dJointID, dVector3 result); 2376 2377 2378 /** 2379 * @brief get joint parameter 2380 * @ingroup joints 2381 */ 2382 ODE_API dReal dJointGetUniversalParam (dJointID, int parameter); 2383 2384 /** 2385 * @brief Get both angles at the same time. 2386 * @ingroup joints 2387 * 2388 * @param joint The universal joint for which we want to calculate the angles 2389 * @param angle1 The angle between the body1 and the axis 1 2390 * @param angle2 The angle between the body2 and the axis 2 2391 * 2392 * @note This function combine getUniversalAngle1 and getUniversalAngle2 together 2393 * and try to avoid redundant calculation 2394 */ 2395 ODE_API void dJointGetUniversalAngles (dJointID, dReal *angle1, dReal *angle2); 2396 2397 /** 2398 * @brief Get angle 2399 * @ingroup joints 2400 */ 2401 ODE_API dReal dJointGetUniversalAngle1 (dJointID); 2402 2403 /** 2404 * @brief Get angle 2405 * @ingroup joints 2406 */ 2407 ODE_API dReal dJointGetUniversalAngle2 (dJointID); 2408 2409 /** 2410 * @brief Get time derivative of angle 2411 * @ingroup joints 2412 */ 2413 ODE_API dReal dJointGetUniversalAngle1Rate (dJointID); 2414 2415 /** 2416 * @brief Get time derivative of angle 2417 * @ingroup joints 2418 */ 2419 ODE_API dReal dJointGetUniversalAngle2Rate (dJointID); 2420 2421 2422 2423 /** 2424 * @brief Get the joint anchor point, in world coordinates. 2425 * @return the point on body 1. If the joint is perfectly satisfied, 2426 * this will be the same as the point on body 2. 2427 * @ingroup joints 2428 */ 2429 ODE_API void dJointGetPRAnchor (dJointID, dVector3 result); 2430 2431 /** 2432 * @brief Get the PR linear position (i.e. the prismatic's extension) 2433 * 2434 * When the axis is set, the current position of the attached bodies is 2435 * examined and that position will be the zero position. 2436 * 2437 * The position is the "oriented" length between the 2438 * position = (Prismatic axis) dot_product [(body1 + offset) - (body2 + anchor2)] 2439 * 2440 * @ingroup joints 2441 */ 2442 ODE_API dReal dJointGetPRPosition (dJointID); 2443 2444 /** 2445 * @brief Get the PR linear position's time derivative 2446 * 2447 * @ingroup joints 2448 */ 2449 ODE_API dReal dJointGetPRPositionRate (dJointID); 2450 2451 2452 /** 2453 * @brief Get the PR angular position (i.e. the twist between the 2 bodies) 2454 * 2455 * When the axis is set, the current position of the attached bodies is 2456 * examined and that position will be the zero position. 2457 * @ingroup joints 2458 */ 2459 ODE_API dReal dJointGetPRAngle (dJointID); 2460 2461 /** 2462 * @brief Get the PR angular position's time derivative 2463 * 2464 * @ingroup joints 2465 */ 2466 ODE_API dReal dJointGetPRAngleRate (dJointID); 2467 2468 2469 /** 2470 * @brief Get the prismatic axis 2471 * @ingroup joints 2472 */ 2473 ODE_API void dJointGetPRAxis1 (dJointID, dVector3 result); 2474 2475 /** 2476 * @brief Get the Rotoide axis 2477 * @ingroup joints 2478 */ 2479 ODE_API void dJointGetPRAxis2 (dJointID, dVector3 result); 2480 2481 /** 2482 * @brief get joint parameter 2483 * @ingroup joints 2484 */ 2485 ODE_API dReal dJointGetPRParam (dJointID, int parameter); 2486 2487 2488 2489 /** 2490 * @brief Get the joint anchor point, in world coordinates. 2491 * @return the point on body 1. If the joint is perfectly satisfied, 2492 * this will be the same as the point on body 2. 2493 * @ingroup joints 2494 */ 2495 ODE_API void dJointGetPUAnchor (dJointID, dVector3 result); 2496 2497 /** 2498 * @brief Get the PU linear position (i.e. the prismatic's extension) 2499 * 2500 * When the axis is set, the current position of the attached bodies is 2501 * examined and that position will be the zero position. 2502 * 2503 * The position is the "oriented" length between the 2504 * position = (Prismatic axis) dot_product [(body1 + offset) - (body2 + anchor2)] 2505 * 2506 * @ingroup joints 2507 */ 2508 ODE_API dReal dJointGetPUPosition (dJointID); 2509 2510 /** 2511 * @brief Get the PR linear position's time derivative 2512 * 2513 * @ingroup joints 2514 */ 2515 ODE_API dReal dJointGetPUPositionRate (dJointID); 2516 2517 /** 2518 * @brief Get the first axis of the universal component of the joint 2519 * @ingroup joints 2520 */ 2521 ODE_API void dJointGetPUAxis1 (dJointID, dVector3 result); 2522 2523 /** 2524 * @brief Get the second axis of the Universal component of the joint 2525 * @ingroup joints 2526 */ 2527 ODE_API void dJointGetPUAxis2 (dJointID, dVector3 result); 2528 2529 /** 2530 * @brief Get the prismatic axis 2531 * @ingroup joints 2532 */ 2533 ODE_API void dJointGetPUAxis3 (dJointID, dVector3 result); 2534 2535 /** 2536 * @brief Get the prismatic axis 2537 * @ingroup joints 2538 * 2539 * @note This function was added for convenience it is the same as 2540 * dJointGetPUAxis3 2541 */ 2542 ODE_API void dJointGetPUAxisP (dJointID id, dVector3 result); 2543 2544 2545 2546 2547 /** 2548 * @brief Get both angles at the same time. 2549 * @ingroup joints 2550 * 2551 * @param joint The Prismatic universal joint for which we want to calculate the angles 2552 * @param angle1 The angle between the body1 and the axis 1 2553 * @param angle2 The angle between the body2 and the axis 2 2554 * 2555 * @note This function combine dJointGetPUAngle1 and dJointGetPUAngle2 together 2556 * and try to avoid redundant calculation 2557 */ 2558 ODE_API void dJointGetPUAngles (dJointID, dReal *angle1, dReal *angle2); 2559 2560 /** 2561 * @brief Get angle 2562 * @ingroup joints 2563 */ 2564 ODE_API dReal dJointGetPUAngle1 (dJointID); 2565 2566 /** 2567 * @brief * @brief Get time derivative of angle1 2568 * 2569 * @ingroup joints 2570 */ 2571 ODE_API dReal dJointGetPUAngle1Rate (dJointID); 2572 2573 2574 /** 2575 * @brief Get angle 2576 * @ingroup joints 2577 */ 2578 ODE_API dReal dJointGetPUAngle2 (dJointID); 2579 2580 /** 2581 * @brief * @brief Get time derivative of angle2 2582 * 2583 * @ingroup joints 2584 */ 2585 ODE_API dReal dJointGetPUAngle2Rate (dJointID); 2586 2587 /** 2588 * @brief get joint parameter 2589 * @ingroup joints 2590 */ 2591 ODE_API dReal dJointGetPUParam (dJointID, int parameter); 2592 2593 2594 2595 2596 2597 /** 2598 * @brief Get the Piston linear position (i.e. the piston's extension) 2599 * 2600 * When the axis is set, the current position of the attached bodies is 2601 * examined and that position will be the zero position. 2602 * @ingroup joints 2603 */ 2604 ODE_API dReal dJointGetPistonPosition (dJointID); 2605 2606 /** 2607 * @brief Get the piston linear position's time derivative. 2608 * @ingroup joints 2609 */ 2610 ODE_API dReal dJointGetPistonPositionRate (dJointID); 2611 2612 /** 2613 * @brief Get the Piston angular position (i.e. the twist between the 2 bodies) 2614 * 2615 * When the axis is set, the current position of the attached bodies is 2616 * examined and that position will be the zero position. 2617 * @ingroup joints 2618 */ 2619 ODE_API dReal dJointGetPistonAngle (dJointID); 2620 2621 /** 2622 * @brief Get the piston angular position's time derivative. 2623 * @ingroup joints 2624 */ 2625 ODE_API dReal dJointGetPistonAngleRate (dJointID); 2626 2627 2628 /** 2629 * @brief Get the joint anchor 2630 * 2631 * This returns the point on body 1. If the joint is perfectly satisfied, 2632 * this will be the same as the point on body 2 in direction perpendicular 2633 * to the prismatic axis. 2634 * 2635 * @ingroup joints 2636 */ 2637 ODE_API void dJointGetPistonAnchor (dJointID, dVector3 result); 2638 2639 /** 2640 * @brief Get the joint anchor w.r.t. body 2 2641 * 2642 * This returns the point on body 2. You can think of a Piston 2643 * joint as trying to keep the result of dJointGetPistonAnchor() and 2644 * dJointGetPistonAnchor2() the same in the direction perpendicular to the 2645 * pirsmatic axis. If the joint is perfectly satisfied, 2646 * this function will return the same value as dJointGetPistonAnchor() to 2647 * within roundoff errors. dJointGetPistonAnchor2() can be used, along with 2648 * dJointGetPistonAnchor(), to see how far the joint has come apart. 2649 * 2650 * @ingroup joints 2651 */ 2652 ODE_API void dJointGetPistonAnchor2 (dJointID, dVector3 result); 2653 2654 /** 2655 * @brief Get the prismatic axis (This is also the rotoide axis. 2656 * @ingroup joints 2657 */ 2658 ODE_API void dJointGetPistonAxis (dJointID, dVector3 result); 2659 2660 /** 2661 * @brief get joint parameter 2662 * @ingroup joints 2663 */ 2664 ODE_API dReal dJointGetPistonParam (dJointID, int parameter); 2665 2666 2667 /** 2668 * @brief Get the number of angular axes that will be controlled by the 2669 * AMotor. 2670 * @param num can range from 0 (which effectively deactivates the 2671 * joint) to 3. 2672 * This is automatically set to 3 in dAMotorEuler mode. 2673 * @ingroup joints 2674 */ 2675 ODE_API int dJointGetAMotorNumAxes (dJointID); 2676 2677 /** 2678 * @brief Get the AMotor axes. 2679 * @param anum selects the axis to change (0,1 or 2). 2680 * @param rel Each axis can have one of three ``relative orientation'' modes. 2681 * \li 0: The axis is anchored to the global frame. 2682 * \li 1: The axis is anchored to the first body. 2683 * \li 2: The axis is anchored to the second body. 2684 * @ingroup joints 2685 */ 2686 ODE_API void dJointGetAMotorAxis (dJointID, int anum, dVector3 result); 2687 2688 /** 2689 * @brief Get axis 2690 * @remarks 2691 * The axis vector is always specified in global coordinates regardless 2692 * of the setting of rel. 2693 * There are two GetAMotorAxis functions, one to return the axis and one to 2694 * return the relative mode. 2695 * 2696 * For dAMotorEuler mode: 2697 * \li Only axes 0 and 2 need to be set. Axis 1 will be determined 2698 automatically at each time step. 2699 * \li Axes 0 and 2 must be perpendicular to each other. 2700 * \li Axis 0 must be anchored to the first body, axis 2 must be anchored 2701 to the second body. 2702 * @ingroup joints 2703 */ 2704 ODE_API int dJointGetAMotorAxisRel (dJointID, int anum); 2705 2706 /** 2707 * @brief Get the current angle for axis. 2708 * @remarks 2709 * In dAMotorUser mode this is simply the value that was set with 2710 * dJointSetAMotorAngle(). 2711 * In dAMotorEuler mode this is the corresponding euler angle. 2712 * @ingroup joints 2713 */ 2714 ODE_API dReal dJointGetAMotorAngle (dJointID, int anum); 2715 2716 /** 2717 * @brief Get the current angle rate for axis anum. 2718 * @remarks 2719 * In dAMotorUser mode this is always zero, as not enough information is 2720 * available. 2721 * In dAMotorEuler mode this is the corresponding euler angle rate. 2722 * @ingroup joints 2723 */ 2724 ODE_API dReal dJointGetAMotorAngleRate (dJointID, int anum); 2725 2726 /** 2727 * @brief get joint parameter 2728 * @ingroup joints 2729 */ 2730 ODE_API dReal dJointGetAMotorParam (dJointID, int parameter); 2731 2732 /** 2733 * @brief Get the angular motor mode. 2734 * @param mode must be one of the following constants: 2735 * \li dAMotorUser The AMotor axes and joint angle settings are entirely 2736 * controlled by the user. This is the default mode. 2737 * \li dAMotorEuler Euler angles are automatically computed. 2738 * The axis a1 is also automatically computed. 2739 * The AMotor axes must be set correctly when in this mode, 2740 * as described below. 2741 * When this mode is initially set the current relative orientations 2742 * of the bodies will correspond to all euler angles at zero. 2743 * @ingroup joints 2744 */ 2745 ODE_API int dJointGetAMotorMode (dJointID); 2746 2747 /** 2748 * @brief Get nr of axes. 2749 * @ingroup joints 2750 */ 2751 ODE_API int dJointGetLMotorNumAxes (dJointID); 2752 2753 /** 2754 * @brief Get axis. 2755 * @ingroup joints 2756 */ 2757 ODE_API void dJointGetLMotorAxis (dJointID, int anum, dVector3 result); 2758 2759 /** 2760 * @brief get joint parameter 2761 * @ingroup joints 2762 */ 2763 ODE_API dReal dJointGetLMotorParam (dJointID, int parameter); 2764 2765 /** 2766 * @brief get joint parameter 2767 * @ingroup joints 2768 */ 2769 ODE_API dReal dJointGetFixedParam (dJointID, int parameter); 2770 2771 2772 /** 2773 * @ingroup joints 2774 */ 2775 ODE_API dJointID dConnectingJoint (dBodyID, dBodyID); 2776 2777 /** 2778 * @ingroup joints 2779 */ 2780 ODE_API int dConnectingJointList (dBodyID, dBodyID, dJointID*); 2781 2782 /** 2783 * @brief Utility function 2784 * @return 1 if the two bodies are connected together by 2785 * a joint, otherwise return 0. 2786 * @ingroup joints 2787 */ 2788 ODE_API int dAreConnected (dBodyID, dBodyID); 2789 2790 /** 2791 * @brief Utility function 2792 * @return 1 if the two bodies are connected together by 2793 * a joint that does not have type @arg{joint_type}, otherwise return 0. 2794 * @param body1 A body to check. 2795 * @param body2 A body to check. 2796 * @param joint_type is a dJointTypeXXX constant. 2797 * This is useful for deciding whether to add contact joints between two bodies: 2798 * if they are already connected by non-contact joints then it may not be 2799 * appropriate to add contacts, however it is okay to add more contact between- 2800 * bodies that already have contacts. 2801 * @ingroup joints 2802 */ 2803 ODE_API int dAreConnectedExcluding (dBodyID body1, dBodyID body2, int joint_type); 2804 2805 2806 #ifdef __cplusplus 2807 } 2808 #endif 2809 2810 #endif 2811