Quads flipping after convert

Hello all.



I am having some trouble loading a scene I put together in AC3D. It is a simple scene made up by rects to create a tile map – it is for a Tactical RPG scene, if you’ve played a Tactical RPG you get the picture. :slight_smile:



In AC3D all the normals are pointing in the correct direction. I wrote a simple converter that translates the AC3D file into a JME binary file – it is very simple, expecting that everything sent to it is a rect and creates only Quads out to produce the scene.



My trouble is that some of the resulting Quads point the correct way, while others are flipped 180 degrees. I had this problem once before and fixed it (or so I thought) by altering the vertex order in the converter, but the problem seems to have come back.



How can I be sure that the Quad will point the correct way?



Here is the top of the AC3D file:

AC3Db
MATERIAL "ac3dmat2" rgb 0.627451 0.25098 0.25098  amb 0.2 0.2 0.2  emis 0 0 0  spec 0.5 0.5 0.5  shi 10  trans 0
MATERIAL "ac3dmat7" rgb 0.270588 0.52549 0.454902  amb 0.2 0.2 0.2  emis 0 0 0 spec 0.5 0.5 0.5  shi 10  trans 0
OBJECT world
kids 360
OBJECT poly
name "rect"
loc -0.5 1.5 -0.5
texture "data/texture/geffen/gef_field-04.png"
crease 45.000000
numvert 4
0 0 0
1 0 0
1 0 1
0 0 1
numsurf 1
SURF 0x0
mat 1
refs 4
3 0 0
2 1 0
1 1 1
0 0 1
kids 0
OBJECT poly
name "rect"
loc -0.5 0.5 0.5
crease 45.000000
numvert 4
1 0 5.96046e-08
0 0 0
0 1 0
1 1 5.96046e-08
numsurf 1
SURF 0x0
mat 0
refs 4
3 0 0
2 1 0
1 1 1
0 0 1
kids 0



Here is the function that actually builds the Quad in my converter, though I am not sure how useful it is w/o the rest of the program:

  private Quad buildQuad(AC3DObject inObject) {
    if (inObject.getVertexCount() != 4)
      return null;

    AC3DMaterial tmpMaterial;
    AC3DSurface tmpSurface;

    Quad tmpQuad = new Quad(inObject.getName(), 0.25f, 0.25f);

    Vector3f[] verts = new Vector3f[inObject.getVerticies().length];
    for (int i=0; i < inObject.getVerticies().length; i++) {
      verts[3-i] = new Vector3f(inObject.getVerticies()[i][0] + inObject.getLocation()[0],
                              inObject.getVerticies()[i][1] + inObject.getLocation()[1],
                              inObject.getVerticies()[i][2] + inObject.getLocation()[2]);
      System.out.println("Built Vert " + i + ": " + verts[i]);
    }
    tmpQuad.setVertices(verts);

    /** construct the color, texture coordinate vector and indexes array */
    ColorRGBA[] colors = new ColorRGBA[inObject.getVerticies().length];
    Vector2f[] texCoords = new Vector2f[inObject.getVerticies().length];

    int[] indexes = new int[inObject.getSurfaces().size() * inObject.getVertexCount()];
    int surfIndex = 0;
    for (int j=0; j < inObject.getSurfaces().size(); j++) {
      tmpSurface = (AC3DSurface)inObject.getSurfaces().get(j);
      tmpMaterial = (AC3DMaterial)materials.get(tmpSurface.material);

      for (int k=0; k < tmpSurface.surfVerts.length; k++) {
        /** assign the color attributes to the vertex */
        if (colors[tmpSurface.surfVerts[k]] == null)
          colors[tmpSurface.surfVerts[k]] = new ColorRGBA(tmpMaterial.getColor().getRed(),
                                                          tmpMaterial.getColor().getGreen(),
                                                          tmpMaterial.getColor().getBlue(),
                                                          1);

        /** if we haven't assigned the texture coordinate, do so */
        if (texCoords[tmpSurface.surfVerts[k]] == null) {
          texCoords[tmpSurface.surfVerts[k]] = new Vector2f(tmpSurface.textCoords[k][0], tmpSurface.textCoords[k][1]);
          System.out.println("Texture Coord " + tmpSurface.surfVerts[k] + " set: " + tmpSurface.textCoords[k][0] + ", " + tmpSurface.textCoords[k][1]);
        }

        /** add the vertex order to the indexes array */
        indexes[surfIndex] = tmpSurface.surfVerts[k];

        surfIndex++;
      }

      /** set the cull state for single sided polys */
      if (!tmpSurface.isTwoSided()) {
        CullState cs = DisplaySystem.getDisplaySystem().getRenderer().createCullState();
        cs.setCullMode(CullState.CS_BACK);
        tmpQuad.setRenderState(cs);
      }

    }

    /** apply the texture if one exists */
    if (inObject.textureName != null) {
      TextureState ts = DisplaySystem.getDisplaySystem().getRenderer().createTextureState();
      Texture texture = TextureManager.loadTexture(inObject.textureName, Texture.MM_LINEAR, Texture.FM_LINEAR, true);
      ts.setTexture(texture);
      ts.setEnabled(true);

      tmpQuad.setTextures(texCoords);
      tmpQuad.setRenderState(ts);
    }

    return tmpQuad;
  }



Thanks for any help!

Sorry, I’m not going to be much help, I’m assuming that you are having trouble with backface culling occuring when it shouldn’t and vice versa? This is purely based on the widing of the vertices, the normals of the Quad (as set by the Quad object) might be ignored. I’m uncertain, but the OpenGL backface culling might completely base it off the vertices. Make sure you are setting the vertices counter-clockwise.

groan



I thought it was the vertex order the first tme I ran into this problem, and when I saw it again I was getting really mad. So I trimmed down my geomtry count and checked out all the vertexs in the file… the bloody order changes from object to object. -_-



sigh



They never make it easy. :stuck_out_tongue:



Thanks Mojo.

Didn

I don’t know… did he? :?

i did indeed, it was blazzingly fast if i say so myself. But its in XML and that XML format is not for everyone.



Boiler, are you still interested in this?



DP

Sure, I’d like to give it a look see. One of my goals is to let users create their own maps, so anything that might make it easier for them would be great.