Skip to content

Commit e15ecd8

Browse files
kbayescopybara-github
authored andcommitted
Support margin with nativeccd multicontact.
PiperOrigin-RevId: 1000723014 Change-Id: I411e1e346b8e26e4857c321d08e7e8e77a69feff
1 parent f640345 commit e15ecd8

9 files changed

Lines changed: 501 additions & 120 deletions

‎doc/changelog.rst‎

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@ Engine
99
^^^^^^
1010
- Trees marked :ref:`sleep="init"<body-sleep>` which cannot be put to sleep now cause a warning rather than an error,
1111
and start awake. See :ref:`Sleeping<siSleepSleeping>` for details.
12+
- Added single-shot :ref:`multicontact<coMultiCCD>` for geoms with positive contact :ref:`margins<body-geom-margin>`.
1213

1314
Python bindings
1415
^^^^^^^^^^^^^^^

‎doc/computation/index.rst‎

Lines changed: 5 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -1860,14 +1860,13 @@ multi-run pipeline (legacy)
18601860
Multiple contact points are found by rotating the two geoms by ±1e-3 radians around the tangential axes and
18611861
re-running the collision routine. If a new contact is detected it is added, allowing for up to 4 additional contact
18621862
points. This method is effective, but increases the cost of each collision call by a factor of 5. This method is
1863-
used when the :ref:`nativeccd<option-flag-nativeccd>` flag is disabled, and for geom collisions involving capsules
1864-
or with :ref:`positive contact margins<body-geom-margin>`.
1863+
used when the :ref:`nativeccd<option-flag-nativeccd>` flag is disabled.
18651864

18661865
single-shot pipeline
18671866
The single-shot pipeline is used in conjunction with the native CCD pipeline, i.e., when the
18681867
:ref:`nativeccd<option-flag-nativeccd>` flag is enabled. As this pipeline is one-shot and most of the geom analysis
1869-
is done at compilation time, there is very little performance overhead. Supported geoms are boxes, cylinders, and meshes
1870-
without :ref:`positive contact margins<body-geom-margin>`.
1868+
is done at compilation time, there is very little performance overhead. Supported geoms are capsules, cylinders,
1869+
boxes, and meshes.
18711870

18721871
.. _coDistance:
18731872

@@ -1913,8 +1912,7 @@ Pair-wise colliders
19131912

19141913
The table below provides information about the colliders used for different geom pairs. These values can be computed
19151914
dynamically by the :ref:`mj_maxContact` function. Use the toggles to see the max number of contacts returned with the
1916-
parameters :ref:`nativeccd<option-flag-nativeccd>`, :ref:`multiccd<option-flag-multiccd>`, and
1917-
:ref:`margin<body-geom-margin>`.
1915+
parameters :ref:`nativeccd<option-flag-nativeccd>` and :ref:`multiccd<option-flag-multiccd>`.
19181916

19191917
.. raw:: html
19201918

@@ -1933,13 +1931,6 @@ parameters :ref:`nativeccd<option-flag-nativeccd>`, :ref:`multiccd<option-flag-m
19331931
</label>
19341932
<span>multiccd</span>
19351933
</div>
1936-
<div class="pairwise-toggle-item">
1937-
<label class="pairwise-switch">
1938-
<input type="checkbox" id="margin-checkbox">
1939-
<span class="pairwise-slider"></span>
1940-
</label>
1941-
<span>with margin</span>
1942-
</div>
19431934
</div>
19441935

19451936
.. list-table::
@@ -2134,8 +2125,7 @@ parameters :ref:`nativeccd<option-flag-nativeccd>`, :ref:`multiccd<option-flag-m
21342125
const table = document.querySelector('.table-pairwise');
21352126
const toggles = [
21362127
{id: 'nativeccd-checkbox', cls: 'nativeccd-enabled'},
2137-
{id: 'multiccd-checkbox', cls: 'multiccd-enabled'},
2138-
{id: 'margin-checkbox', cls: 'margin-enabled'}
2128+
{id: 'multiccd-checkbox', cls: 'multiccd-enabled'}
21392129
];
21402130
21412131
toggles.forEach(toggle => {

‎doc/css/theme_overrides.css‎

Lines changed: 2 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -124,24 +124,11 @@ body[data-theme="dark"] table.docutils:not(.mjcf-attributes) {
124124
display: none;
125125
}
126126

127-
.multiccd-enabled.nativeccd-enabled:not(.margin-enabled) .multiccd-native {
127+
.multiccd-enabled.nativeccd-enabled .multiccd-native {
128128
display: inline;
129129
}
130130

131-
.multiccd-enabled:not(.nativeccd-enabled) .multiccd-legacy,
132-
.multiccd-enabled.nativeccd-enabled.margin-enabled .multiccd-legacy {
133-
display: inline;
134-
}
135-
136-
.margin-show {
137-
display: none;
138-
}
139-
140-
.margin-enabled .margin-hide {
141-
display: none;
142-
}
143-
144-
.margin-enabled .margin-show {
131+
.multiccd-enabled:not(.nativeccd-enabled) .multiccd-legacy {
145132
display: inline;
146133
}
147134

‎src/engine/engine_collision_convex.c‎

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -903,8 +903,8 @@ static void mju_rotateFrame(const mjtNum origin[3], const mjtNum rot[9],
903903

904904
// return number of contacts supported by a single pass of narrowphase
905905
static int maxContacts(const mjModel* m, const mjCCDObj* obj1, const mjCCDObj* obj2) {
906-
// single pass not supported for margins nor libccd
907-
if (obj1->margin > 0 || obj2->margin > 0 || mjDISABLED(mjDSBL_NATIVECCD)) {
906+
// single pass not supported for libccd
907+
if (mjDISABLED(mjDSBL_NATIVECCD)) {
908908
return 1;
909909
}
910910

‎src/engine/engine_collision_driver.c‎

Lines changed: 1 addition & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -64,8 +64,7 @@ mjfCollision mjCOLLISIONFUNC[mjNGEOMTYPES][mjNGEOMTYPES] = {
6464

6565

6666
// return the maximum number of contacts that can be generated between two geoms
67-
// if has_margin is -1, then the margin is pulled from the model, otherwise if has_margin > 0
68-
// indicates that the geoms have a positive margin
67+
// has_margin is ignored
6968
int mj_maxContact(const mjModel* m, int g1, int g2, int has_margin) {
7069
int type1 = m->geom_type[g1];
7170
int type2 = m->geom_type[g2];
@@ -129,34 +128,6 @@ int mj_maxContact(const mjModel* m, int g1, int g2, int has_margin) {
129128
return 5;
130129
}
131130

132-
// check margin from model
133-
if (has_margin < 0) {
134-
has_margin = 0;
135-
if (mjENABLED(mjENBL_OVERRIDE)) {
136-
has_margin = m->opt.o_margin > 0.0;
137-
} else {
138-
int npair = m->npair;
139-
int ipair = -1;
140-
for (int k=0; k < npair; k++) {
141-
if ((m->pair_geom1[k] == g1 && m->pair_geom2[k] == g2) ||
142-
(m->pair_geom1[k] == g2 && m->pair_geom2[k] == g1)) {
143-
ipair = k;
144-
break;
145-
}
146-
}
147-
148-
if (ipair > -1) {
149-
has_margin = m->pair_margin[ipair] > 0.0;
150-
} else {
151-
has_margin = m->geom_margin[g1] > 0.0 || m->geom_margin[g2] > 0.0;
152-
}
153-
}
154-
}
155-
156-
if (has_margin) {
157-
return 5;
158-
}
159-
160131
// colliding geoms with flat faces
161132
if (hasface1 && hasface2) {
162133
return 4;

‎src/engine/engine_collision_driver.h‎

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -28,8 +28,7 @@ extern "C" {
2828
MJAPI extern mjfCollision mjCOLLISIONFUNC[mjNGEOMTYPES][mjNGEOMTYPES];
2929

3030
// return the maximum number of contacts that can be generated between two geoms
31-
// if has_margin is -1, then the margin is pulled from the model, otherwise if has_margin > 0
32-
// indicates that the geoms have a positive margin
31+
// has_margin is ignored
3332
MJAPI int mj_maxContact(const mjModel* m, int g1, int g2, int has_margin);
3433

3534
// collision detection entry point

0 commit comments

Comments
 (0)
⌂ 换网址