Skip to content

Commit bae5175

Browse files
quaglacopybara-github
authored andcommitted
Accumulate rotation after updating pos and quat in replicate.
Fixes #2501. PiperOrigin-RevId: 737929158 Change-Id: I0cad2de37190f1d30d427ae646acbde335b5be56
1 parent 1bf24e9 commit bae5175

File tree

3 files changed

+21
-11
lines changed

3 files changed

+21
-11
lines changed

model/humanoid/100_humanoids.xml

+2-2
Original file line numberDiff line numberDiff line change
@@ -37,8 +37,8 @@
3737
<light directional="true" diffuse=".9 .9 .9" specular="0.1 0.1 0.1" pos="0 0 5" dir="0 0 -1" castshadow="true"/>
3838
<light name="spotlight" mode="targetbodycom" target="world" diffuse="1 1 1" specular="0.3 0.3 0.3" pos="-6 -6 4" cutoff="60"/>
3939
<replicate count="10" euler="0 0 36" sep="-">
40-
<frame pos="1 0 0">
41-
<replicate count="10" euler="0 0 15" sep="-" offset="0.5 0 0">
40+
<frame pos="1.2 0 0">
41+
<replicate count="10" euler="0 0 17" sep="-" offset="0.6 0 0">
4242
<attach model="humanoid" body="torso" prefix="_"/>
4343
</replicate>
4444
</frame>

src/xml/xml_native_reader.cc

+6-4
Original file line numberDiff line numberDiff line change
@@ -3544,17 +3544,19 @@ void mjXReader::Body(XMLElement* section, mjsBody* body, mjsFrame* frame,
35443544

35453545
// update pframe and attach
35463546
for (int i = 0; i < count; i++) {
3547-
// accumulate rotation
3548-
mjuu_setvec(pframe->pos, pos[0], pos[1], pos[2]);
3549-
mjuu_frameaccum(pos, quat, offset, rotation);
3550-
35513547
// overwrite orientation to increase precision
35523548
alt.euler[0] = i*euler[0];
35533549
alt.euler[1] = i*euler[1];
35543550
alt.euler[2] = i*euler[2];
35553551
mjs_resolveOrientation(quat, spec->compiler.degree, spec->compiler.eulerseq, &alt);
3552+
3553+
// set position and orientation
3554+
mjuu_setvec(pframe->pos, pos[0], pos[1], pos[2]);
35563555
mjuu_setvec(pframe->quat, quat[0], quat[1], quat[2], quat[3]);
35573556

3557+
// accumulate rotation
3558+
mjuu_frameaccum(pos, quat, offset, rotation);
3559+
35583560
// process suffix
35593561
string suffix = separator;
35603562
UpdateString(suffix, count, i);

test/xml/xml_native_reader_test.cc

+13-5
Original file line numberDiff line numberDiff line change
@@ -1230,7 +1230,7 @@ TEST_F(XMLReaderTest, ParseReplicate) {
12301230
</asset>
12311231
12321232
<worldbody>
1233-
<replicate count="101" euler="0 0 1.8">
1233+
<replicate count="101" offset="3 0 .1" euler="0 0 1.8">
12341234
<body name="body" pos="0 -1 0">
12351235
<joint type="slide"/>
12361236
<geom name="g" size="1"/>
@@ -1260,6 +1260,7 @@ TEST_F(XMLReaderTest, ParseReplicate) {
12601260
EXPECT_THAT(m, testing::NotNull()) << error.data();
12611261
EXPECT_THAT(m->ngeom, 105);
12621262
EXPECT_THAT(m->nsensor, 4);
1263+
EXPECT_THAT(m->nbody, 102);
12631264

12641265
// check that the separator is used correctly
12651266
for (int i = 0; i < 2; ++i) {
@@ -1289,12 +1290,19 @@ TEST_F(XMLReaderTest, ParseReplicate) {
12891290
}
12901291
}
12911292

1293+
// check body positions
1294+
mjtNum pos[2] = {0, 0};
1295+
for (int i = 1; i < 102; ++i) {
1296+
mjtNum theta = (i-1) * 1.8 * mjPI / 180;
1297+
EXPECT_NEAR(m->body_pos[3*i+0], pos[0] + sin(theta), 1e-8) << i;
1298+
EXPECT_NEAR(m->body_pos[3*i+1], pos[1] - cos(theta), 1e-8) << i;
1299+
EXPECT_NEAR(m->body_pos[3*i+2], (i-1) * .1, 1e-8);
1300+
pos[0] += 3 * cos(theta);
1301+
pos[1] += 3 * sin(theta);
1302+
}
1303+
12921304
// check that the final pose is correct
12931305
int n = m->nbody-1;
1294-
EXPECT_THAT(m->nbody, 102);
1295-
EXPECT_NEAR(m->body_pos[3*n+0], 0, 1e-8);
1296-
EXPECT_NEAR(m->body_pos[3*n+1], 1, 1e-8);
1297-
EXPECT_EQ(m->body_pos[3*n+2], 0);
12981306
EXPECT_NEAR(m->body_quat[4*n+0], 0, 1e-8);
12991307
EXPECT_EQ(m->body_quat[4*n+1], 0);
13001308
EXPECT_EQ(m->body_quat[4*n+2], 0);

0 commit comments

Comments
 (0)