vertex[normalIndex - 1].cross(vertex[normalIndex - 2]).normalize();
vertex[normalIndex - 1].subtract(vertex[normalIndex]) .cross(vertex[normalIndex - 2].subtract(vertex[normalIndex])).normalizeLocal();
    public void tessellate() {        if(patch == null) {            return;        }        int u = 0, v;        float py, px, pyold;        int detailLevel = patch.getDetailLevel();        Vector3f[] temp = new Vector3f[4];        Vector3f[] last = new Vector3f[detailLevel + 1];        temp[0] = patch.getAnchor(0, 3);        temp[1] = patch.getAnchor(1, 3);        temp[2] = patch.getAnchor(2, 3);        temp[3] = patch.getAnchor(3, 3);        for (v = 0; v <= detailLevel; v++) {            px = ((float) v) / ((float) detailLevel);            last[v] = calcBerstein(px, temp);        }        u = 1;        Vector3f[] vertex = new Vector3f[((detailLevel * 2) + 2) * detailLevel];        Vector2f[] texture =            new Vector2f[((detailLevel * 2) + 2) * detailLevel];        Vector3f[] normal = new Vector3f[vertex.length];        int[] indices = new int[detailLevel * detailLevel * 6];        int count = 0;        for (u = 1; u <= detailLevel; u++) {            py = ((float) u) / ((float) detailLevel);            pyold = (u - 1.0f) / (detailLevel);            temp[0] = calcBerstein(py, patch.getAnchors()[0]);            temp[1] = calcBerstein(py, patch.getAnchors()[1]);            temp[2] = calcBerstein(py, patch.getAnchors()[2]);            temp[3] = calcBerstein(py, patch.getAnchors()[3]);            for (v = 0; v <= detailLevel; v++) {                px = ((float) v) / ((float) detailLevel);                texture[count] = new Vector2f(pyold, px);                vertex[count] = new Vector3f(last[v].x, last[v].y, last[v].z);                count++;                last[v] = calcBerstein(px, temp);                texture[count] = new Vector2f(py, px);                vertex[count] = new Vector3f(last[v].x, last[v].y, last[v].z);                count++;            }        }        int index = -1;        for (int i = 0; i < detailLevel * detailLevel * 6; i = i + 6) {            index++;            if (i > 0 && i % (detailLevel * 6) == 0) {                index += 1;            }            indices[i] = 2 * index;            indices[(i + 1)] = (2 * index) + 1;            indices[(i + 2)] = (2 * index) + 2;            indices[(i + 3)] = (2 * index) + 3;            indices[(i + 4)] = (2 * index) + 2;            indices[(i + 5)] = (2 * index) + 1;        }        int normalIndex = 0;        for (int i = 0; i < detailLevel; i++) {            for (int j = 0; j < (detailLevel * 2) + 2; j++) {                if (j % 2 == 0) {                    if (i == 0) {                        if (j < (detailLevel * 2)) {                            //right cross up                            normal[normalIndex] =                                vertex[normalIndex                                    + 1]                                        .cross(vertex[normalIndex + 2])                                        .normalize();                        } else {                            //down cross right                            normal[normalIndex] =                                vertex[normalIndex                                    - 2]                                        .cross(vertex[normalIndex + 1])                                        .normalize();                        }                    } else {                        normal[normalIndex] =                            normal[normalIndex                                - (detailLevel * 2 + 1)].normalize();                    }                } else {                    if (j < (detailLevel * 2) + 1) {                        //up cross left                        normal[normalIndex] =                            vertex[normalIndex                                + 2].cross(vertex[normalIndex - 1]).normalize();                    } else {                        //left cross down                        normal[normalIndex] =                            vertex[normalIndex                                - 1].cross(vertex[normalIndex - 2]).normalize();                    }                }                normalIndex++;            }        }        setVertices(vertex);        setTextures(texture);        setIndices(indices);        setNormals(normal);    }