Bug 1206 - OBJ file <assign> options not behaving as expected when the same OBJ is used multiple times
Summary: OBJ file <assign> options not behaving as expected when the same OBJ is used ...
Status: RESOLVED FIXED
Alias: None
Product: DIRSIG4
Classification: Unclassified
Component: Geometry (show other bugs)
Version: 4.7.0-release
Hardware: Intel x86-64 Linux 64-bit
: P5 normal
Assignee: Scott D. Brown
URL:
Depends on:
Blocks:
 
Reported: 2016-01-14 16:15 EST by Rolando Raqueno
Modified: 2016-02-26 14:15 EST (History)
1 user (show)

See Also:


Attachments
Summary of Observations (806.56 KB, image/png)
2016-01-14 16:18 EST, Rolando Raqueno
Details

Note You need to log in before you can comment on or make changes to this bug.
Description Rolando Raqueno 2016-01-14 16:15:55 EST
Attached is a tarball (CarColorBug.tar.gz) containing the following cases

Case1 - Two similar vehicles listed in a glist in order of white then red.  D47 renders them as both red

Case2 - Same as Case 2 except lists red then white. D47 renders them as both white

Case3 - Similar to Case1 except glist references glist->white then glist->red.  D47 renders them both as white

Case4 - glist references obj->white then obj->red.  D47 renders AS EXPECTED.

Attached is 2nd tarball (CarColorBugReproduce.tgz) containing augmented cases 

CaseA - Expands on Case1 but adds 3rd vehicle white to end of glist.  D47 renders all three as white.

CaseB - Expands on Case2 but adds 3rd vehicle red to end of glist. D47 renders all three as red.

CaseC - Expands on Case3 but adds 3rd vehicle red to end of glist. D47 renders all three as white.

Image attached shows image summary of cases above.
Comment 1 Rolando Raqueno 2016-01-14 16:18:49 EST
Created attachment 379 [details]
Summary of Observations
Comment 2 Rolando Raqueno 2016-01-14 16:22:03 EST
Bugzilla won't let me attach CarColorBugReproduce.tgz, but the directory can be accessed at ~rvrpci/DirsigTesting/CarColorBugReproduce

The actual order of the glist may have changed from the descriptions because I was trying to test other combinations to give more data points.

RR
Comment 3 Scott D. Brown 2016-01-15 12:29:26 EST
I'm looking at "cars_case1.glist" and "cars_case2.glist" and they clearly have XML structure issues.  The first <object> is never closed before starting a second: 

  <!--white car-->
  <object> 
    <basegeometry>
      <obj swapyz="false">
        <filename>infiniti_g35.obj</filename>
        <assign id="505" name="paint">default</assign>
        ...
      </obj>
    </basegeometry>
   <dynamicinstance> 
     <keyframemovement>
       <filename>$SCENE_DIR/motion/car1.mov</filename></keyframemovement> 
     </dynamicinstance>
  <!--white car-->
  <object> 
    <basegeometry>
    ...
   </dynamicinstance>
  </object>

  </object>
  <!--red car-->
  <object>
    ...

So before your "white car" comment you needed to close the <object> before starting another object. Because we don't do schema validation, it doesn't say "Hey you can't start a <object> within an <object>!" And it looks like you were trying to setup 3 cars, but you only got two when you ran, so that should have alerted you to something right there.

Fix those GLIST files before we go any further.
Comment 4 Scott D. Brown 2016-01-15 15:39:55 EST
The underlying issue is that when you request an OBJ file, that file is only loaded once regardless of how many <object> sections it is defined in.  This is done to save memory (why have multiple copies of the same base geometry loaded into memory?).  Consider the following GLIST file:

<geometrylist>
  <object>
    <basegeometry>
      <obj><filename>infiniti_g35.obj</filename></obj>
    </basegeometry>
   <dynamicinstance>
     <keyframemovement><filename>$SCENE_DIR/motion/car1.mov</filename></keyframemovement>
   </dynamicinstance>
  </object>

  ...

  <object>
    <basegeometry>
      <obj><filename>infiniti_g35.obj</filename></obj>
    </basegeometry>
   <dynamicinstance>
     <keyframemovement><filename>$SCENE_DIR/motion/car2.mov</filename></keyframemovement>
   </dynamicinstance>
  </object>
</geometrylist>

Here you see two places where "infiniti_g35.obj" is supplied. But when the second occurrence is found the code says "I already loaded that, we'll just use it again".

The problem is that there is nothing stopping the user from specifying different options for the same OBJ file in multiple <object> locations. For example, the units of the file, if the YZ axis should be flipped, or material assignments. In the case of the problem reported here, the user requested the same car in two (or more) locations and each one had a unique set of material assignments. Unfortunately, these assignments are only processed when the file is read in. Hence, only one of these sets of assignments will be utilized.

We should point out that creating two (or more) <object> entries that use the same OBJ but have different material assignments seems like a completely logical thing to do.  And the code does not detect that you are have specified <assign> options on an OBJ file that was already loaded and assignments were already performed. Furthermore, the documentation doesn't clarify this "load once, assign once" limitation.

We are looking at ways to address the issues highlighted by this example.
Comment 5 Scott D. Brown 2016-02-26 14:15:04 EST
For the 4.7.1 release, we changed it so that an OBJ loaded from a GLIST file is always a unique geometry. That means all the options for each <obj> base geometry are used. It also means that if you repeatedly use the same OBJ file over and over across separate <object> descriptions, that each one will be a unique copy in memory. This will lead to more memory usage than before this change. If a scene does this, it probably should be using a single <object> and many instances of that object, which would avoid loading copies of the OBJ multiple times.