ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/radiance/ray/src/common/objutil.c
(Generate patch)

Comparing ray/src/common/objutil.c (file contents):
Revision 2.10 by greg, Fri Dec 18 00:15:47 2020 UTC vs.
Revision 2.11 by greg, Fri Feb 12 01:57:49 2021 UTC

# Line 710 | Line 710 | addFace(Scene *sc, VNDX vid[], int nv)
710          return(f);
711   }
712  
713 < /* Duplicate a scene */
713 > /* Duplicate a scene, optionally selecting faces */
714   Scene *
715 < dupScene(const Scene *osc)
715 > dupScene(const Scene *osc, int flreq, int flexc)
716   {
717 +        int             fltest = flreq | flexc;
718          Scene           *sc;
719          const Face      *fo;
720          Face            *f;
# Line 762 | Line 763 | dupScene(const Scene *osc)
763                  sc->nnorms = osc->nnorms;
764          }
765          for (fo = osc->flist; fo != NULL; fo = fo->next) {
766 +                if ((fo->flags & fltest) != flreq)
767 +                        continue;
768                  f = (Face *)emalloc(sizeof(Face) +
769                                  sizeof(VertEnt)*(fo->nv-3));
770                  memcpy((void *)f, (const void *)fo, sizeof(Face) +
# Line 772 | Line 775 | dupScene(const Scene *osc)
775                  sc->flist = f;
776                  sc->nfaces++;
777          }
778 +        deleteUnreferenced(sc);         /* jetsam */
779          return(sc);
780   }
781  
# Line 853 | Line 857 | xfmScene(Scene *sc, const char *xfm)
857          return(i);
858   }
859   #undef MAXAC
860 +
861 + /* Delete unreferenced vertices, normals, texture coords */
862 + void
863 + deleteUnreferenced(Scene *sc)
864 + {
865 +        int     *vmap;
866 +        Face    *f;
867 +        int     nused, i;
868 +                                                /* allocate index map */
869 +        if (!sc->nverts)
870 +                return;
871 +        i = sc->nverts;
872 +        if (sc->ntex > i)
873 +                i = sc->ntex;
874 +        if (sc->nnorms > i)
875 +                i = sc->nnorms;
876 +        vmap = (int *)emalloc(sizeof(int)*i);
877 +                                                /* remap positions */
878 +        for (i = nused = 0; i < sc->nverts; i++) {
879 +                if (sc->vert[i].vflist == NULL) {
880 +                        vmap[i] = -1;
881 +                        continue;
882 +                }
883 +                if (nused != i)
884 +                        sc->vert[nused] = sc->vert[i];
885 +                vmap[i] = nused++;
886 +        }
887 +        if (nused == sc->nverts)
888 +                goto skip_pos;
889 +        sc->vert = (Vertex *)erealloc((char *)sc->vert,
890 +                                sizeof(Vertex)*(nused+(CHUNKSIZ-1)));
891 +        sc->nverts = nused;
892 +        for (f = sc->flist; f != NULL; f = f->next)
893 +                for (i = f->nv; i--; )
894 +                        if ((f->v[i].vid = vmap[f->v[i].vid]) < 0)
895 +                                error(CONSISTENCY,
896 +                                        "Link error in del_unref_verts()");
897 + skip_pos:
898 +                                                /* remap texture coord's */
899 +        if (!sc->ntex)
900 +                goto skip_tex;
901 +        memset((void *)vmap, 0, sizeof(int)*sc->ntex);
902 +        for (f = sc->flist; f != NULL; f = f->next)
903 +                for (i = f->nv; i--; )
904 +                        if (f->v[i].tid >= 0)
905 +                                vmap[f->v[i].tid] = 1;
906 +        for (i = nused = 0; i < sc->ntex; i++) {
907 +                if (!vmap[i])
908 +                        continue;
909 +                if (nused != i)
910 +                        sc->tex[nused] = sc->tex[i];
911 +                vmap[i] = nused++;
912 +        }
913 +        if (nused == sc->ntex)
914 +                goto skip_tex;
915 +        sc->tex = (TexCoord *)erealloc((char *)sc->tex,
916 +                                sizeof(TexCoord)*(nused+(CHUNKSIZ-1)));
917 +        sc->ntex = nused;
918 +        for (f = sc->flist; f != NULL; f = f->next)
919 +                for (i = f->nv; i--; )
920 +                        if (f->v[i].tid >= 0)
921 +                                f->v[i].tid = vmap[f->v[i].tid];
922 + skip_tex:
923 +                                                /* remap normals */
924 +        if (!sc->nnorms)
925 +                goto skip_norms;
926 +        memset((void *)vmap, 0, sizeof(int)*sc->nnorms);
927 +        for (f = sc->flist; f != NULL; f = f->next)
928 +                for (i = f->nv; i--; )
929 +                        if (f->v[i].nid >= 0)
930 +                                vmap[f->v[i].nid] = 1;
931 +        for (i = nused = 0; i < sc->nnorms; i++) {
932 +                if (!vmap[i])
933 +                        continue;
934 +                if (nused != i)
935 +                        memcpy((void *)sc->norm[nused],
936 +                                        (void *)sc->norm[i],
937 +                                        sizeof(Normal));
938 +                vmap[i] = nused++;
939 +        }
940 +        if (nused == sc->nnorms)
941 +                goto skip_norms;
942 +        sc->norm = (Normal *)erealloc((char *)sc->norm,
943 +                                sizeof(Normal)*(nused+(CHUNKSIZ-1)));
944 +        sc->nnorms = nused;
945 +        for (f = sc->flist; f != NULL; f = f->next)
946 +                for (i = f->nv; i--; )
947 +                        if (f->v[i].nid >= 0)
948 +                                f->v[i].nid = vmap[f->v[i].nid];
949 + skip_norms:
950 +                                                /* clean up */
951 +        efree((char *)vmap);
952 + }
953  
954   /* Free a scene */
955   void

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines