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

📄 randommapgenerator.java

📁 good project for programmer,,
💻 JAVA
📖 第 1 页 / 共 3 页
字号:
		return 675;		}	else if ("large".equals(boardSize))		{		return 850;		}	else if ("huge".equals(boardSize))		{		return 1000;		}	return 750;	}public static int getHeightForSize(String boardSize)	{	if ("tiny".equals(boardSize))		{		return 266;		}	else if ("small".equals(boardSize))		{		return 366;		}	else if ("large".equals(boardSize))		{		return 566;		}	else if ("huge".equals(boardSize))		{		return 666;		}	return 466;	}// gives the approximate wrapped distance between shapes i and jprivate double wrappedDistance( int i, int j)	{	int lower, higher;	// one shape will be near the left and onr near the right side of the board	if (shapeBounds[i].getX() < shapeBounds[j].getX())		{		lower = i;		higher = j;		}	else		{		lower = j;		higher = i;		}	// wrap a point on the bounds of the low shape to a position higher than the edge of the board	Point2D mapHigherPoint = new Point2D.Double(shapeBounds[lower].getX()+topx, shapeBounds[lower].getY());	Point2D highPoint = new Point2D.Double(shapeBounds[higher].getX()+shapeBounds[higher].getWidth(), shapeBounds[higher].getY());	return mapHigherPoint.distance(highPoint);	}// initialize must ONLY be called after numCountries has been setprivate void initialize()	{	shapeCount = 0;	// we set up a variety of data structures here	shapes = new GeneralPath[numCountries];	shapeBounds = new Rectangle2D[numCountries];	points = new Vector[numCountries];	// each shape also gets a vector of Point's that it is made of	allPoints = new Hashtable();	countries = new Country[numCountries];	lines = new Vector();	// it holds ExtraLines	distanceMemory = new int[numCountries][numCountries];	// distanceMemory[][] is our memory of computed distances	// it shouldn't be used until all the shapes are finished	for (int i = 0; i<numCountries; i++)		{		points[i] = new Vector();		countries[i] = new Country(i, -1, this);	// they have no continentCode yet		for (int j = 0; j < numCountries; j++)			distanceMemory[i][j] = -1;		}	}// connects any shapes whose distance < <level>private void connectShapesAt(int level)	{	for (int i = 0; i < numCountries; i++)		for (int j = 0; j < numCountries; j++)			{			if (i != j && !countries[i].canGoto(countries[j]) && distanceBetween(i,j) < level)				{				makeCountriesTouch(i, j);				addLineBetweenShapes(i, j);				}			}	}/** Connects any shapes that are in different continents and whose distance is below 'level'.	*/private void connectContinentsAt(int level)	{	for (int i = 0; i < numCountries; i++)		for (int j = 0; j < numCountries; j++)			{			if (i != j && !countries[i].canGoto(countries[j]) && countries[i].getContinent() != countries[j].getContinent() && distanceBetween(i,j) < level && lineCanExistBetween(i,j))				{				makeCountriesTouch(i, j);				addLineBetweenShapes(i, j);				}			}	}/** Generates a couple shapes close together. */private void generateNugget()	{	// pick a random point:	double x = 30 + rand.nextInt(topx-60);	double y = 30 + rand.nextInt(topy-60);	if (! createShapeAt( x, y ))		{		// bad shape. restart the nugget somewhere else		generateNugget();		return;		}	//debug("generateNugget put first shape at ("+x+", "+y+")");	// Otherwise a shape was created.	// now make some other shapes near to this nugget...	int nuggetBase = shapeCount-1;	Vector nuggetShapeIndexes = new Vector();	nuggetShapeIndexes.add(new Integer(nuggetBase));	int desiredContSize = 2 + rand.nextInt(8);	for (int tries = 0; nuggetShapeIndexes.size() < desiredContSize && tries < 30 && shapeCount < numCountries; tries++)		{		// to start with, we try shapes close to the first shape		int closeToShape = nuggetBase;		Point2D randPoint = (Point2D)points[closeToShape].get( rand.nextInt(points[closeToShape].size()) );		if (shapes[closeToShape].contains( randPoint.getX()-5, randPoint.getY() ) )			{			x = randPoint.getX()+(minRadius*2);			y = randPoint.getY();			}		else			{			x = randPoint.getX()-(minRadius*2);			y = randPoint.getY();			}		// we have the new point. try a shape there:		if (createShapeAt( x, y ))			{			// good shape			nuggetShapeIndexes.add(new Integer(shapeCount-1));			}		}	//debug(" -> placed "+(shapeCount-nuggetBase)+" shapes total in this nugget");	}private boolean createShapeAt( double x, double y )	{	generateNextShapeAroundPoint(x, y);	if (shapes[shapeCount] != null)		shapeBounds[shapeCount] = shapes[shapeCount].getBounds2D();	// keep it if a shape was drawn around this point and it is not too small and not too big	if (shapes[shapeCount] != null && 		shapeBounds[shapeCount].getWidth() > 40 && 		shapeBounds[shapeCount].getHeight() > 40 && 		shapeBounds[shapeCount].getWidth() < topx/3 && 		shapeBounds[shapeCount].getHeight() < topy/3) 		{		// because generateShapeAroundPoint() only sets up adjoingingLists one-way, we must add the reverse connections here:		addReverseLinks(countries[shapeCount]);		// Add the shapes point to the allPoints hashtable		for (int p = 0; p < points[shapeCount].size(); p++)			{			Object key = allPoints.get(points[shapeCount].get(p));			if (key == null)				allPoints.put(points[shapeCount].get(p), new Integer(1));			else				{				allPoints.put(points[shapeCount].get(p), new Integer( ((Integer)key).intValue() + 1 ));				}			}		shapeCount++;		loader.setLoadText("creating board. shapeCount -> "+shapeCount+"/"+numCountries);		return true;		}	else		{		// we are ditching the shape, so clear the adjoingList:		countries[shapeCount].clearAdjoiningList(this);		points[shapeCount] = new Vector();		return false;		}	}/** Generate the next country shape around the given point. It will fill in shapes[shapeCount] - possibly with null if it fails to make a shape. */public void generateNextShapeAroundPoint( double pointx, double pointy )	{	Point2D shapeOrigin = new Point2D.Double(pointx, pointy);	if ( isInShapes( shapeOrigin ) != -1)		{		//debug(" abort -> started in another shape");		shapes[shapeCount] = null;		return; // we don't want to start inside another shape		}	//debug("generateNextShapeAroundPoint called. shape="+shapeCount+", shapeOrigin="+shapeOrigin);	// We will return <shape>. create it here:	shapes[shapeCount] = new GeneralPath();	GeneralPath shape = shapes[shapeCount];	// The first point in the shape is a special case	double theta = 0.001;	double radius = 35 + rand.nextInt(30); // between 35 and 65	Point2D p = pointFromPolar(shapeOrigin, theta, radius);	// Make sure that putting the first point there won't jump over another shape	Point2D mid = getMiddlePoint(shapeOrigin, p);	if ( isInShapes(mid) != -1 )		{		p = mid;		radius = shapeOrigin.distance( p );		}	// Bring it closer until there is no conflict.	while ( radius >= minRadius && isInShapes(p) != -1 )		{		radius -= 5;		p = pointFromPolar(shapeOrigin, theta, radius);		}	if (radius < minRadius)		{		shapes[shapeCount] = null;		return;		}	if (! validPoint(p) )		{		shapes[shapeCount] = null;		return;		}	// So now we have a good first point	points[shapeCount].add(p);	shape.moveTo((float)p.getX(), (float)p.getY());	// used for radius convergence	double initialRadius = radius;	// Start drawing the circle...	while (theta < 6.2 && theta != 0)	// this is close to 2 pi		{		// Set the radius and theta to the correct values for the last point added		radius = shapeOrigin.distance( shape.getCurrentPoint() );		if (radius < minRadius)			{			//debug("ABORT -> radius was smaller than min");			// then we just placed a point with an invalid radius. abort			shapes[shapeCount] = null;			return;			}		theta = calcTheta(shapeOrigin, shape.getCurrentPoint());		if (theta == -1)			{			//debug(" abort -> calcTheta returned -1 (at start of circle loop)");			shapes[shapeCount] = null;			return;			}		// and get the next point to add		theta += thetaStep;		radius = Math.max( nearNumber(radius), minRadius); // a slightly random radius, above the minimum		if (theta > fullCircle-thetaStep || theta == 0)			{			// then we are done going around the circle. break out of the loop			break;			}		if (theta > 4.712)	// 4.712 ~= to PI*1.5			{			// then we are in the last quarter of the circle shape.			// ensure that the radius eventually converges to what it was for the first point.			// The maximum difference is limited to 1 per 2 degrees away from the start			// (ie when theta is 270 degrees, it is 90 degrees away from the start and the max difference is 45)			double maxDifference = (double)(((fullCircle-theta)*360)/(2*fullCircle));			maxDifference = Math.abs(maxDifference);			if (initialRadius - radius > maxDifference)				{				//debug("converging radius1 from "+radius+" to "+(initialRadius - maxDifference));				//debug("-> theta="+theta+", maxDifference="+maxDifference+", initialRadius="+initialRadius);				radius = initialRadius - maxDifference;				}			else if (radius - initialRadius > maxDifference)				{				//debug("converging radius2 from "+radius+" to "+(initialRadius + maxDifference));				radius = initialRadius + maxDifference;				}			}		p = pointFromPolar(shapeOrigin, theta, radius);		// Test to see if the new point conflicts with other shapes.		int conflict = isInShapes(p);		if (conflict == -1) 			{			// then there was no conflict with the point itself. 			// but drawing the line to the point could still cause overlap. test for that here.			mid = getMiddlePoint(shape.getCurrentPoint(), p);			conflict = isInShapes(mid);			}		if ( conflict == -1 )			{			if (! validPoint(p) )				{				shapes[shapeCount] = null;				return;				}//debug("      drawing the shape. adding a point with radius="+radius+", theta="+theta);			// there was no intersection with a shape. thus p is a valid point. Add it to the shape.			points[shapeCount].add(p);			shape.lineTo((float)p.getX(), (float)p.getY());			}		else			{			// Then there was a conflict. Now the fun really begins			// Since the point p has hit inside a shape, these two shapes will touch:			countries[shapeCount].addToAdjoiningList( countries[conflict], this );			// Make this shape follow the outline of the conflict shape for a bit.			// We start by finding the border-point closest to shape's last point:			int borderPoint = getClosestBorderNotInShape(shape.getCurrentPoint(), conflict, shapeCount);			if (borderPoint == -1)				{				//debug("getClosestBorderNotInShape returned -1. abort the shape");				shapes[shapeCount] = null;				return;				}			// make p be the same point as the closest borderPoint and add it to the shape 			p = (Point2D)points[conflict].get(borderPoint);			points[shapeCount].add(p);			shape.lineTo((float)p.getX(), (float)p.getY());//debug(" --> CONFLICT with shape "+conflict+", shifting to borderPoint "+borderPoint);			// So we have matched up one border point.			// continue to follow the border until we hit an exit condition			// Note: within the loop we need to know the radius and theta of the last point.			// Set the initial values here 			double lastRadius = shapeOrigin.distance(p);			double lastTheta = calcTheta(shapeOrigin, p );			if (lastTheta == -1)				{//debug(" abort -> calcTheta returned -1");				shapes[shapeCount] = null;				return;				}			boolean keepFollowingBorder = true;			while ( keepFollowingBorder && theta < fullCircle-thetaStep && theta != 0 )				{				borderPoint--;	// this will make us choose the previous border point.				if (borderPoint == -1)					{					borderPoint = points[conflict].size()-1; 					//debug("wrapping to first border point");					}				p = (Point2D)points[conflict].get(borderPoint);				// But we don't want to follow the border too far.				// We only allow theta to backtrack if the radius also gets smaller				// calculate the radius and theta:				radius = shapeOrigin.distance(p);				theta = calcTheta(shapeOrigin, p);				if (theta == -1)					{					//debug(" abort -> calcTheta returned -1 (in 2nd place)");					shapes[shapeCount] = null;					return;					}				if (theta < lastTheta && lastRadius < radius) {					// then theta is backtracking while the radius gets bigger.					// this is an exit condition for following the border					// NOTE: we don't even bother to add this point					keepFollowingBorder = false;//debug("exit condition 1");					}				else {					// add it to the shape					lastTheta = theta;					lastRadius = radius;					points[shapeCount].add(p);					shape.lineTo((float)p.getX(), (float)p.getY());//debug(" ---> keepFollowingBorder tick. borderPoint="+borderPoint);					// If the point we just added is also in 2 or more other shapes then 					// stop following this border					Object key = allPoints.get(p);					if (key != null && ((Integer)key).intValue() > 1)						{						//debug("exit condition 2");						keepFollowingBorder = false;						}					}				}	// end of keepFollowingBorder loop			// So we are done following that shape for now.			// We will continue drawing the circle now.			}	// end of dealing with conflict point		}	// end of stepTheta for-loop	// So now we are done drawing our circle-ish shape.	// the only thing left to do is close it.	shape.closePath();	// check if we swallowed an entire country	// check against a box that is slightly bigger then the new shape	Rectangle2D eatCheck = shape.getBounds2D();	eatCheck = new Rectangle2D.Double(eatCheck.getX()-2, eatCheck.getY()-2, eatCheck.getWidth()+4, eatCheck.getHeight()+4);	for (int i = 0; i < shapeCount; i++)		{

⌨️ 快捷键说明

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