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

📄 po_man.c

📁 魔法师传奇源代码
💻 C
📖 第 1 页 / 共 3 页
字号:
		for(i = po->bbox[BOXLEFT]; i <= po->bbox[BOXRIGHT]; i++)		{			if(i >= 0 && i < bmapwidth && j >= 0 && j < bmapheight*bmapwidth)			{				link = &PolyBlockMap[j+i];				if(!(*link))				{ // Create a new link at the current block cell					*link = Z_Malloc(sizeof(polyblock_t), PU_LEVEL, 0);					(*link)->next = NULL;					(*link)->prev = NULL;					(*link)->polyobj = po;					continue;				}				else				{					tempLink = *link;					while(tempLink->next != NULL && tempLink->polyobj != NULL)					{						tempLink = tempLink->next;					}				}				if(tempLink->polyobj == NULL)				{					tempLink->polyobj = po;					continue;				}				else				{					tempLink->next = Z_Malloc(sizeof(polyblock_t), 						PU_LEVEL, 0);					tempLink->next->next = NULL;					tempLink->next->prev = tempLink;					tempLink->next->polyobj = po;				}			}			// else, don't link the polyobj, since it's off the map		}	}}//==========================================================================//// CheckMobjBlocking////==========================================================================static boolean CheckMobjBlocking(seg_t *seg, polyobj_t *po){	mobj_t *mobj;	int i, j;	int left, right, top, bottom;	int tmbbox[4];	line_t *ld;	boolean blocked;	ld = seg->linedef;	top = (ld->bbox[BOXTOP]-bmaporgy+MAXRADIUS)>>MAPBLOCKSHIFT;	bottom = (ld->bbox[BOXBOTTOM]-bmaporgy-MAXRADIUS)>>MAPBLOCKSHIFT;	left = (ld->bbox[BOXLEFT]-bmaporgx-MAXRADIUS)>>MAPBLOCKSHIFT;	right = (ld->bbox[BOXRIGHT]-bmaporgx+MAXRADIUS)>>MAPBLOCKSHIFT;	blocked = false;	bottom = bottom < 0 ? 0 : bottom;	bottom = bottom >= bmapheight ? bmapheight-1 : bottom;	top = top < 0 ? 0 : top;	top = top >= bmapheight  ? bmapheight-1 : top;	left = left < 0 ? 0 : left;	left = left >= bmapwidth ? bmapwidth-1 : left;	right = right < 0 ? 0 : right;	right = right >= bmapwidth ?  bmapwidth-1 : right;	for(j = bottom*bmapwidth; j <= top*bmapwidth; j += bmapwidth)	{		for(i = left; i <= right; i++)		{			for(mobj = blocklinks[j+i]; mobj; mobj = mobj->bnext)			{				if(mobj->flags&MF_SOLID || mobj->player)				{					tmbbox[BOXTOP] = mobj->y+mobj->radius;					tmbbox[BOXBOTTOM] = mobj->y-mobj->radius;					tmbbox[BOXLEFT] = mobj->x-mobj->radius;					tmbbox[BOXRIGHT] = mobj->x+mobj->radius;					if (tmbbox[BOXRIGHT] <= ld->bbox[BOXLEFT]						||      tmbbox[BOXLEFT] >= ld->bbox[BOXRIGHT]						||      tmbbox[BOXTOP] <= ld->bbox[BOXBOTTOM]						||      tmbbox[BOXBOTTOM] >= ld->bbox[BOXTOP])					{						continue;					}					if(P_BoxOnLineSide(tmbbox, ld) != -1)					{						continue;					}					ThrustMobj(mobj, seg, po);					blocked = true;				}			}		}	}	return blocked;}//==========================================================================//// InitBlockMap////==========================================================================static void InitBlockMap(void){	int i;	int j;	seg_t **segList;	int area;	int leftX, rightX;	int topY, bottomY;	PolyBlockMap = Z_Malloc(bmapwidth*bmapheight*sizeof(polyblock_t *),		PU_LEVEL, 0);	memset(PolyBlockMap, 0, bmapwidth*bmapheight*sizeof(polyblock_t *));	for(i = 0; i < po_NumPolyobjs; i++)	{		LinkPolyobj(&polyobjs[i]);		// calculate a rough area		// right now, working like shit...gotta fix this...		segList = polyobjs[i].segs;		leftX = rightX = (*segList)->v1->x;		topY = bottomY = (*segList)->v1->y;		for(j = 0; j < polyobjs[i].numsegs; j++, segList++)		{			if((*segList)->v1->x < leftX)			{				leftX = (*segList)->v1->x;			}			if((*segList)->v1->x > rightX)			{				rightX = (*segList)->v1->x;			}			if((*segList)->v1->y < bottomY)			{				bottomY = (*segList)->v1->y;			}			if((*segList)->v1->y > topY)			{				topY = (*segList)->v1->y;			}		}		area = ((rightX>>FRACBITS)-(leftX>>FRACBITS))*			((topY>>FRACBITS)-(bottomY>>FRACBITS));//    fprintf(stdaux, "Area of Polyobj[%d]: %d\n", polyobjs[i].tag, area);//    fprintf(stdaux, "\t[%d]\n[%d]\t\t[%d]\n\t[%d]\n", topY>>FRACBITS, //    		leftX>>FRACBITS,//    	rightX>>FRACBITS, bottomY>>FRACBITS);	}}//==========================================================================//// IterFindPolySegs////              Passing NULL for segList will cause IterFindPolySegs to//      count the number of segs in the polyobj//==========================================================================static void IterFindPolySegs(int x, int y, seg_t **segList){	int i;	if(x == PolyStartX && y == PolyStartY)	{		return;	}	for(i = 0; i < numsegs; i++)	{		if(segs[i].v1->x == x && segs[i].v1->y == y)		{			if(!segList)			{				PolySegCount++;			}			else			{				*segList++ = &segs[i];			}			IterFindPolySegs(segs[i].v2->x, segs[i].v2->y, segList);			return;		}	}	I_Error("IterFindPolySegs:  Non-closed Polyobj located.\n");}//==========================================================================//// SpawnPolyobj////==========================================================================static void SpawnPolyobj(int index, int tag, boolean crush){	int i;	int j;	int psIndex;	int psIndexOld;	seg_t *polySegList[PO_MAXPOLYSEGS];	for(i = 0; i < numsegs; i++)	{		if(segs[i].linedef->special == PO_LINE_START &&			segs[i].linedef->arg1 == tag)		{			if(polyobjs[index].segs)			{				I_Error("SpawnPolyobj:  Polyobj %d already spawned.\n", tag);			}			segs[i].linedef->special = 0;			segs[i].linedef->arg1 = 0;			PolySegCount = 1;			PolyStartX = segs[i].v1->x;			PolyStartY = segs[i].v1->y;			IterFindPolySegs(segs[i].v2->x, segs[i].v2->y, NULL);			polyobjs[index].numsegs = PolySegCount;			polyobjs[index].segs = Z_Malloc(PolySegCount*sizeof(seg_t *),				PU_LEVEL, 0);			*(polyobjs[index].segs) = &segs[i]; // insert the first seg			IterFindPolySegs(segs[i].v2->x, segs[i].v2->y,				polyobjs[index].segs+1);			polyobjs[index].crush = crush;			polyobjs[index].tag = tag;			polyobjs[index].seqType = segs[i].linedef->arg3;			if(polyobjs[index].seqType < 0 				|| polyobjs[index].seqType >= SEQTYPE_NUMSEQ)			{				polyobjs[index].seqType = 0;			}			break;		}	}	if(!polyobjs[index].segs)	{ // didn't find a polyobj through PO_LINE_START		psIndex = 0;		polyobjs[index].numsegs = 0;		for(j = 1; j < PO_MAXPOLYSEGS; j++)		{			psIndexOld = psIndex;			for (i = 0; i < numsegs; i++)			{				if(segs[i].linedef->special == PO_LINE_EXPLICIT &&					segs[i].linedef->arg1 == tag)				{					if(!segs[i].linedef->arg2)					{						I_Error("SpawnPolyobj:  Explicit line missing order number (probably %d) in poly %d.\n",							j+1, tag);					}					if(segs[i].linedef->arg2 == j)					{						polySegList[psIndex] = &segs[i];						polyobjs[index].numsegs++;						psIndex++;						if(psIndex > PO_MAXPOLYSEGS)						{							I_Error("SpawnPolyobj:  psIndex > PO_MAXPOLYSEGS\n");						}					}				}			}			// Clear out any specials for these segs...we cannot clear them out			// 	in the above loop, since we aren't guaranteed one seg per			//		linedef.			for(i = 0; i < numsegs; i++)			{				if(segs[i].linedef->special == PO_LINE_EXPLICIT &&					segs[i].linedef->arg1 == tag && segs[i].linedef->arg2 == j)				{					segs[i].linedef->special = 0;					segs[i].linedef->arg1 = 0;				}			}			if(psIndex == psIndexOld)			{ // Check if an explicit line order has been skipped				// A line has been skipped if there are any more explicit				// lines with the current tag value				for(i = 0; i < numsegs; i++)				{					if(segs[i].linedef->special == PO_LINE_EXPLICIT &&						segs[i].linedef->arg1 == tag)					{						I_Error("SpawnPolyobj:  Missing explicit line %d for poly %d\n",							j, tag);					}				}			}		}		if(polyobjs[index].numsegs)		{			PolySegCount = polyobjs[index].numsegs; // PolySegCount used globally			polyobjs[index].crush = crush;			polyobjs[index].tag = tag;			polyobjs[index].segs = Z_Malloc(polyobjs[index].numsegs				*sizeof(seg_t *), PU_LEVEL, 0);			for(i = 0; i < polyobjs[index].numsegs; i++)			{				polyobjs[index].segs[i] = polySegList[i];			}			polyobjs[index].seqType = (*polyobjs[index].segs)->linedef->arg4;		}		// Next, change the polyobjs first line to point to a mirror		//		if it exists		(*polyobjs[index].segs)->linedef->arg2 =			(*polyobjs[index].segs)->linedef->arg3;	}}//==========================================================================//// TranslateToStartSpot////==========================================================================static void TranslateToStartSpot(int tag, int originX, int originY){	seg_t **tempSeg;	seg_t **veryTempSeg;	vertex_t *tempPt;	subsector_t *sub;	polyobj_t *po;	int deltaX;	int deltaY;	vertex_t avg; // used to find a polyobj's center, and hence subsector	int i;	po = NULL;	for(i = 0; i < po_NumPolyobjs; i++)	{		if(polyobjs[i].tag == tag)		{			po = &polyobjs[i];			break;		}	}	if(!po)	{ // didn't match the tag with a polyobj tag		I_Error("TranslateToStartSpot:  Unable to match polyobj tag: %d\n",			tag);	}	if(po->segs == NULL)	{		I_Error("TranslateToStartSpot:  Anchor point located without a StartSpot point: %d\n", tag);	}	po->originalPts = Z_Malloc(po->numsegs*sizeof(vertex_t), PU_LEVEL, 0);	po->prevPts = Z_Malloc(po->numsegs*sizeof(vertex_t), PU_LEVEL, 0);	deltaX = originX-po->startSpot.x;	deltaY = originY-po->startSpot.y;	tempSeg = po->segs;	tempPt = po->originalPts;	avg.x = 0;	avg.y = 0;	validcount++;	for(i = 0; i < po->numsegs; i++, tempSeg++, tempPt++)	{		if((*tempSeg)->linedef->validcount != validcount)		{			(*tempSeg)->linedef->bbox[BOXTOP] -= deltaY;			(*tempSeg)->linedef->bbox[BOXBOTTOM] -= deltaY;			(*tempSeg)->linedef->bbox[BOXLEFT] -= deltaX;			(*tempSeg)->linedef->bbox[BOXRIGHT] -= deltaX;			(*tempSeg)->linedef->validcount = validcount;		}		for(veryTempSeg = po->segs; veryTempSeg != tempSeg; veryTempSeg++)		{			if((*veryTempSeg)->v1 == (*tempSeg)->v1)			{				break;			}		}		if(veryTempSeg == tempSeg)		{ // the point hasn't been translated, yet			(*tempSeg)->v1->x -= deltaX;			(*tempSeg)->v1->y -= deltaY;		}		avg.x += (*tempSeg)->v1->x>>FRACBITS;		avg.y += (*tempSeg)->v1->y>>FRACBITS;		// the original Pts are based off the startSpot Pt, and are		// unique to each seg, not each linedef		tempPt->x = (*tempSeg)->v1->x-po->startSpot.x;		tempPt->y = (*tempSeg)->v1->y-po->startSpot.y;	}	avg.x /= po->numsegs;	avg.y /= po->numsegs;	sub = R_PointInSubsector(avg.x<<FRACBITS, avg.y<<FRACBITS);	if(sub->poly != NULL)	{		I_Error("PO_TranslateToStartSpot:  Multiple polyobjs in a single subsector.\n");	}	sub->poly = po;}//==========================================================================//// PO_Init////==========================================================================void PO_Init(int lump){	byte                    *data;	int                             i;	mapthing_t              *mt;	int                             numthings;	int polyIndex;	polyobjs = Z_Malloc(po_NumPolyobjs*sizeof(polyobj_t), PU_LEVEL, 0);	memset(polyobjs, 0, po_NumPolyobjs*sizeof(polyobj_t));	data = W_CacheLumpNum(lump, PU_STATIC);	numthings = W_LumpLength(lump)/sizeof(mapthing_t);	mt = (mapthing_t *)data;	polyIndex = 0; // index polyobj number	// Find the startSpot points, and spawn each polyobj	for (i = 0; i < numthings; i++, mt++)	{		mt->x = SHORT(mt->x);		mt->y = SHORT(mt->y);		mt->angle = SHORT(mt->angle);		mt->type = SHORT(mt->type);		// 3001 = no crush, 3002 = crushing		if(mt->type == PO_SPAWN_TYPE || mt->type == PO_SPAWNCRUSH_TYPE)		{ // Polyobj StartSpot Pt.			polyobjs[polyIndex].startSpot.x = mt->x<<FRACBITS;			polyobjs[polyIndex].startSpot.y = mt->y<<FRACBITS;			SpawnPolyobj(polyIndex, mt->angle, (mt->type == PO_SPAWNCRUSH_TYPE));			polyIndex++;		}	}	mt = (mapthing_t *)data;	for (i = 0; i < numthings; i++, mt++)	{		mt->x = SHORT(mt->x);		mt->y = SHORT(mt->y);		mt->angle = SHORT(mt->angle);		mt->type = SHORT(mt->type);		if(mt->type == PO_ANCHOR_TYPE)		{ // Polyobj Anchor Pt.			TranslateToStartSpot(mt->angle, mt->x<<FRACBITS, mt->y<<FRACBITS);		}	}	Z_Free (data);	// check for a startspot without an anchor point	for(i = 0; i < po_NumPolyobjs; i++)	{		if(!polyobjs[i].originalPts)		{			I_Error("PO_Init:  StartSpot located without an Anchor point: %d\n",				polyobjs[i].tag);		}	}	InitBlockMap();}//==========================================================================//// PO_Busy////==========================================================================boolean PO_Busy(int polyobj){	polyobj_t *poly;	poly = GetPolyobj(polyobj);	if(!poly->specialdata)	{		return false;	}	else	{		return true;	}}

⌨️ 快捷键说明

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