⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 earclip.java

📁 JAVA3D矩陈的相关类
💻 JAVA
字号:
/* * $RCSfile: EarClip.java,v $ * * Copyright (c) 2007 Sun Microsystems, Inc. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistribution of source code must retain the above copyright *   notice, this list of conditions and the following disclaimer. * * - Redistribution in binary form must reproduce the above copyright *   notice, this list of conditions and the following disclaimer in *   the documentation and/or other materials provided with the *   distribution. * * Neither the name of Sun Microsystems, Inc. or the names of * contributors may be used to endorse or promote products derived * from this software without specific prior written permission. * * This software is provided "AS IS," without a warranty of any * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY * EXCLUDED. SUN MICROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE * POSSIBILITY OF SUCH DAMAGES. * * You acknowledge that this software is not designed, licensed or * intended for use in the design, construction, operation or * maintenance of any nuclear facility. * * $Revision: 1.4 $ * $Date: 2007/02/09 17:20:18 $ * $State: Exp $ */// ----------------------------------------------------------------------//// The reference to Fast Industrial Strength Triangulation (FIST) code// in this release by Sun Microsystems is related to Sun's rewrite of// an early version of FIST. FIST was originally created by Martin// Held and Joseph Mitchell at Stony Brook University and is// incorporated by Sun under an agreement with The Research Foundation// of SUNY (RFSUNY). The current version of FIST is available for// commercial use under a license agreement with RFSUNY on behalf of// the authors and Stony Brook University.  Please contact the Office// of Technology Licensing at Stony Brook, phone 631-632-9009, for// licensing information.//// ----------------------------------------------------------------------package com.sun.j3d.utils.geometry;import java.io.*;import java.util.*;import javax.vecmath.*;class EarClip {    /**     * Classifies all the internal angles of the loop referenced by  ind.     * the following classification is used:     *            0 ... if angle is 180 degrees     *            1 ... if angle between 0 and 180 degrees     *            2 ... if angle is 0 degrees     *           -1 ... if angle between 180 and 360 degrees     *           -2 ... if angle is 360 degrees     */    static void classifyAngles(Triangulator triRef, int ind) {	int ind0, ind1, ind2;	int i0, i1, i2;	int angle;	ind1 = ind;	i1 = triRef.fetchData(ind1);	ind0 = triRef.fetchPrevData(ind1);	i0 = triRef.fetchData(ind0);	do {	    ind2 = triRef.fetchNextData(ind1);	    i2 = triRef.fetchData(ind2);	    angle = Numerics.isConvexAngle(triRef, i0, i1, i2, ind1);	    triRef.setAngle(ind1, angle);	    i0   = i1;	    i1   = i2;	    ind1 = ind2;	} while (ind1 != ind);    }    static void classifyEars(Triangulator triRef, int ind) {	int ind1;	int i1;	int[] ind0, ind2;	double[] ratio;	ind0 = new int[1];	ind2 = new int[1];	ratio = new double[1];	Heap.initHeap(triRef);	ind1 = ind;	i1 = triRef.fetchData(ind1);	do {	    if ((triRef.getAngle(ind1) > 0)  &&		isEar(triRef, ind1, ind0, ind2, ratio))   {		Heap.dumpOnHeap(triRef, ratio[0], ind1, ind0[0], ind2[0]);	    }	    ind1 = triRef.fetchNextData(ind1);	    i1 = triRef.fetchData(ind1);	} while (ind1 != ind);	// Not using sorted_ear so don't have to do MakeHeap();	// MakeHeap();	// Heap.printHeapData(triRef);    }    /**                                                                              * This function checks whether a diagonal is valid, that is, whether it is     * locally within the polygon, and whether it does not intersect any other     * segment of the polygon. also, some degenerate cases get a special     * handling.     */    static boolean isEar(Triangulator triRef, int ind2, int[] ind1, int[] ind3,			 double[] ratio) {	int i0, i1, i2, i3, i4;	int ind0, ind4;	BBox bb;	boolean convex, coneOk;	i2 = triRef.fetchData(ind2);	ind3[0] = triRef.fetchNextData(ind2);	i3 = triRef.fetchData(ind3[0]);	ind4 = triRef.fetchNextData(ind3[0]);	i4 = triRef.fetchData(ind4);	ind1[0] = triRef.fetchPrevData(ind2);	i1 = triRef.fetchData(ind1[0]);	ind0 = triRef.fetchPrevData(ind1[0]);	i0 = triRef.fetchData(ind0);	/*	  System.out.println("isEar : i0 " + i0 + " i1 " + i1 + " i2 " + i2 +	  " i3 " + i3 + " i4 " + i4);	*/	if ((i1 == i3)  ||  (i1 == i2)  ||  (i2 == i3)  ||  (triRef.getAngle(ind2) == 2)) {	    // oops, this is not a simple polygon!	    ratio[0] = 0.0;	    return  true;	}	if (i0 == i3) {	    // again, this is not a simple polygon!	    if ((triRef.getAngle(ind0) < 0)  ||  (triRef.getAngle(ind3[0]) < 0)) {		ratio[0] = 0.0;		return  true;	    }	    else		return  false;	}	if (i1 == i4) {	    // again, this is not a simple polygon!	    if ((triRef.getAngle(ind1[0]) < 0)  ||  (triRef.getAngle(ind4) < 0)) {		ratio[0] = 0.0;		return  true;	    }	    else		return  false;	}	// check whether the new diagonal  i1, i3  locally is within the polygon	convex = triRef.getAngle(ind1[0]) > 0;	coneOk = Numerics.isInCone(triRef, i0, i1, i2, i3, convex);	// System.out.println("isEar :(1) convex " + convex + " coneOk " + coneOk );	if (!coneOk)  return false;	convex = triRef.getAngle(ind3[0]) > 0;	coneOk = Numerics.isInCone(triRef, i2, i3, i4, i1, convex);	// System.out.println("isEar :(2) convex " + convex + " coneOk " + coneOk );	if (coneOk) {	    // check whether this diagonal is a valid diagonal. this translates to	    // checking either condition CE1 or CE2 (see my paper). If CE1 is to	    // to be checked, then we use a BV-tree or a grid. Otherwise, we use	    // "buckets" (i.e., a grid) or no hashing at all.	    bb = new BBox(triRef, i1, i3);	    // use CE2 + no_hashing	    if(!NoHash.noHashIntersectionExists(triRef, i2, ind2, i3, i1, bb)) {		if (triRef.earsSorted)  {		    // determine the quality of the triangle		    ratio[0] = Numerics.getRatio(triRef, i1, i3, i2);		}		else {		    ratio[0] = 1.0;		}		return true;	    }	}	// System.out.println("isEar : false");	return  false;    }    /**     * This is the main function that drives the ear-clipping. it obtains an ear     * from set of ears maintained in a priority queue, clips this ear, and     * updates all data structures appropriately. (ears are arranged in the     * priority queue (i.e., heap) according to a quality criterion that tries     * to avoid skinny triangles.)     */    static boolean clipEar(Triangulator triRef, boolean[] done) {	int ind0, ind1, ind3, ind4;	int i0, i1, i2, i3, i4;	int angle1, angle3;	double ratio[] = new double[1];	int index0[] = new int[1];	int index1[] = new int[1];	int index2[] = new int[1];	int index3[] = new int[1];	int index4[] = new int[1];	int ind2[] = new int[1];	int testCnt = 0;	// Heap.printHeapData(triRef);	do {	    //	System.out.println("In clipEarloop " + testCnt++);	    if (!Heap.deleteFromHeap(triRef, ind2, index1, index3))		// no ear exists?!		return false;	    // get the successors and predecessors in the list of nodes and check	    // whether the ear still is part of the boundary	    ind1 = triRef.fetchPrevData(ind2[0]);	    i1 = triRef.fetchData(ind1);	    ind3 = triRef.fetchNextData(ind2[0]);	    i3 = triRef.fetchData(ind3);	} while ((index1[0] != ind1)  ||  (index3[0] != ind3));	//System.out.println("Out of clipEarloop ");	i2 = triRef.fetchData(ind2[0]);	// delete the clipped ear from the list of nodes, and update the bv-tree	triRef.deleteLinks(ind2[0]);	// store the ear in a list of ears which have already been clipped	// StoreTriangle(GetOriginal(ind1), GetOriginal(ind2), GetOriginal(ind3));	triRef.storeTriangle(ind1, ind2[0], ind3);	/*                                                                        */	/* update the angle classification at  ind1  and  ind3                    */	/*                                                                        */	ind0 = triRef.fetchPrevData(ind1);	i0 = triRef.fetchData(ind0);	if (ind0 == ind3) {	    // nothing left	    done[0] = true;	    return  true;	}	angle1 = Numerics.isConvexAngle(triRef, i0, i1, i3, ind1);	ind4 = triRef.fetchNextData(ind3);	i4 = triRef.fetchData(ind4);	angle3 = Numerics.isConvexAngle(triRef, i1, i3, i4, ind3);	if (i1 != i3) {	    if ((angle1 >= 0)  &&  (triRef.getAngle(ind1) < 0))		NoHash.deleteReflexVertex(triRef, ind1);	    if ((angle3 >= 0)  &&  (triRef.getAngle(ind3) < 0))		NoHash.deleteReflexVertex(triRef, ind3);	}	else {	    if ((angle1 >= 0)  &&  (triRef.getAngle(ind1) < 0))		NoHash.deleteReflexVertex(triRef, ind1);	    else if ((angle3 >= 0)  &&  (triRef.getAngle(ind3) < 0))		NoHash.deleteReflexVertex(triRef, ind3);	}	triRef.setAngle(ind1, angle1);	triRef.setAngle(ind3, angle3);	// check whether either of  ind1  and  ind3  is an ear. (the "ratio" is	// the length of the triangle's longest side divided by the length of the	// height normal onto this side; it is used as a quality criterion.)	if (angle1 > 0) {	    if (isEar(triRef, ind1, index0, index2, ratio)) {		// insert the new ear into the priority queue of ears		Heap.insertIntoHeap(triRef, ratio[0], ind1, index0[0], index2[0]);	    }	}	if (angle3 > 0) {	    if(isEar(triRef, ind3, index2, index4, ratio)) {		Heap.insertIntoHeap(triRef, ratio[0], ind3, index2[0], index4[0]);	    }	}	// check whether the triangulation is finished.	ind0 = triRef.fetchPrevData(ind1);	i0 = triRef.fetchData(ind0);	ind4 = triRef.fetchNextData(ind3);	i4 = triRef.fetchData(ind4);	if (ind0 == ind4) {	    // only one triangle left -- clip it!	    triRef.storeTriangle(ind1, ind3, ind4);	    done[0] = true;	}	else {	    done[0] = false;	}	return true;    }}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -