private CollBase GetOperaColliderInfo(ColliderInfo colliderInfo) { CollBase collider = null; float startX = SkillPlayer.MovePos.x + colliderInfo.StartX; float startZ = SkillPlayer.MovePos.z + colliderInfo.StartZ; float angle = colliderInfo.StartAngle; if (colliderInfo.CollPosType == CollBase.PosType.SKILL || colliderInfo.CollPosType == CollBase.PosType.SKILL_ROTATE) { startX = Command.TargetPos.x + colliderInfo.StartX; startZ = Command.TargetPos.z + colliderInfo.StartZ; //附加操作旋转 if (colliderInfo.CollPosType == CollBase.PosType.SKILL_ROTATE) { // 方向盘角度 与场景角度差异修正 修正符号(场景y轴 逆时针旋转 与方向盘顺时针旋转 一致) angle = Mathf.Atan2(-Command.SkillDir.z, Command.SkillDir.x) * Mathf.Rad2Deg + colliderInfo.StartAngle; } } switch (colliderInfo.ColliderType) { case CollBase.ColType.RECTANGLE: collider = new CollRectange(startX, startZ, angle, colliderInfo.Width, colliderInfo.Height); break; case CollBase.ColType.SECTOR: collider = new CollSector(startX, startZ, angle, colliderInfo.InCircle, colliderInfo.OutCircle, colliderInfo.Angle); break; default: collider = new CollRadius(startX, startZ, angle, colliderInfo.Radius); break; } return(collider); }
//圆与矩形 public static bool RadiusToRectangle(CollRadius CollA, CollRectange CollB) { //长轴距离过滤 if (Vector2.Distance(CollA.GetV2Pos(), CollB.GetV2Pos()) > CollB.GetLength() + CollA.Radius) { return(false); } //获得圆相对矩形中心的相对坐标 float newRx = CollA.x - CollB.x; float newRy = CollA.y - CollB.y; if (Mathf.RoundToInt(CollB.GetCalRotate()) != 0) { //计算最新角度(与X轴的角度),同数学X Y轴 以矩形中心为坐标中心 float rotate = Mathf.Atan((CollB.y - CollA.y) / (CollB.x - CollA.x)) * Mathf.Rad2Deg; float newrot = rotate - CollB.GetCalRotate(); //减去矩形旋转角度 与矩形同时旋转对应的角度 float distance = Vector2.Distance(CollA.GetV2Pos(), CollB.GetV2Pos()); //圆相对矩形的 x y newRx = Mathf.Cos(newrot * Mathf.Deg2Rad) * distance; newRy = Mathf.Sin(newrot * Mathf.Deg2Rad) * distance; } //矩形 与圆 相交公式 获得在矩形 x y范围内 与圆心最近的点 float dx = Mathf.Min(newRx, CollB.width * 0.5f); float dx1 = Mathf.Max(dx, -CollB.width * 0.5f); float dy = Mathf.Min(newRy, CollB.height * 0.5f); float dy1 = Mathf.Max(dy, -CollB.height * 0.5f); return((dx1 - newRx) * (dx1 - newRx) + (dy1 - newRy) * (dy1 - newRy) <= CollA.Radius * CollA.Radius); }
//矩形与扇形(分离轴 三角形碰撞) public static bool RectangleToSector(CollRectange CollA, CollSector CollB) { //长轴距离过滤 if (Vector2.Distance(CollA.GetV2Pos(), CollB.GetV2Pos()) > CollB.outCircle + CollA.GetLength()) { return(false); } //扇形两个顶点 float angle = CollB.angle + CollB.GetCalRotate(); float x1 = CollB.x + Mathf.Cos(angle * 0.5f * Mathf.Deg2Rad); float y1 = CollB.y + Mathf.Sin(angle * 0.5f * Mathf.Deg2Rad); float x2 = CollB.x + Mathf.Cos(-angle * 0.5f * Mathf.Deg2Rad); float y2 = CollB.y + Mathf.Sin(-angle * 0.5f * Mathf.Deg2Rad); //三角形三个顶点 Vector2[] secPos = new Vector2[] { CollB.GetV2Pos(), new Vector2(x1, y1), new Vector2(x2, y2) }; //三角形三条中轴 //Vector2[] secAxies = new Vector2[] { GetV2Nor(secPos[0] - secPos[1]), GetV2Nor(secPos[0] - secPos[2]), GetV2Nor(secPos[1] - secPos[2]) }; //矩形四个顶点 float rectR = CollA.extents.magnitude; float rotate = Mathf.Atan((CollA.width * 0.5f) / (CollA.height * 0.5f)) * Mathf.Rad2Deg + CollA.GetCalRotate(); float x = Mathf.Cos(rotate) * rectR; float y = Mathf.Sin(rotate) * rectR; Vector2[] rectPos = new Vector2[] { new Vector2(CollA.x + x, CollA.y + y), new Vector2(CollA.x + x, CollA.y - y), new Vector2(CollA.x - x, CollA.y + y), new Vector2(CollA.x - x, CollA.y - y) }; //矩形中轴 //Vector2[] rectAxies = new Vector2[] { GetV2Nor(secPos[0] - secPos[1]), GetV2Nor(secPos[0] - secPos[3]), GetV2Nor(secPos[1] - secPos[2]),GetV2Nor(secPos[2] - secPos[3]) }; Vector2[] axises = new Vector2[] { GetV2Nor(secPos[0] - secPos[1]), GetV2Nor(secPos[0] - secPos[2]), GetV2Nor(secPos[1] - secPos[2]), GetV2Nor(secPos[0] - secPos[1]), GetV2Nor(secPos[0] - secPos[3]), GetV2Nor(secPos[1] - secPos[2]), GetV2Nor(secPos[2] - secPos[3]) }; for (int i = 0, len = axises.Length; i < len; i++) { var axis = axises[i]; Vector2 proA = GetProjection(axis, secPos); Vector2 proB = GetProjection(axis, rectPos); if (IsOverlay(proA, proB)) { return(false); } } return(true); }
private static Mesh CreateRectangleMesh(CollBase collider) { CollRectange coll = collider as CollRectange; Mesh mesh = new Mesh(); Vector3[] vertices = new Vector3[4]; vertices[0] = new Vector3(-coll.width * 0.5f, 0, -coll.height * 0.5f); vertices[1] = new Vector3(coll.width * 0.5f, 0, -coll.height * 0.5f); vertices[2] = new Vector3(coll.width * 0.5f, 0, coll.height * 0.5f); vertices[3] = new Vector3(-coll.width * 0.5f, 0, coll.height * 0.5f); int[] triangles = new int[6] { 0, 3, 2, 2, 1, 0 }; mesh.vertices = vertices; mesh.triangles = triangles; return(mesh); }
//矩形与矩形 public static bool RectangleToRectangle(CollRectange CollA, CollRectange CollB) { //长轴距离过滤 //if (Vector2.Distance(CollA.GetV2Pos(), CollB.GetV2Pos()) > CollB.GetLength() + CollA.GetLength()) //{ // return false; //} //Debug.Log("========================================================================="); // GameTool.Log(CollA.x, CollA.y, CollA.extents.x, CollA.extents.y, CollA.axes[0], CollA.axes[1], CollA.GetCalRotate()); //GameTool.Log(CollB.x, CollB.y, CollB.extents.x, CollB.extents.y, CollB.axes[0], CollB.axes[1], CollB.GetCalRotate()); Vector2 nv = CollA.centerPoint - CollB.centerPoint; Vector2 axisA1 = CollA.axes[0]; if (CollA.GetProjectionRadius(axisA1) + CollB.GetProjectionRadius(axisA1) <= Mathf.Abs(Vector2.Dot(nv, axisA1))) { return(false); } Vector2 axisA2 = CollA.axes[1]; if (CollA.GetProjectionRadius(axisA2) + CollB.GetProjectionRadius(axisA2) <= Mathf.Abs(Vector2.Dot(nv, axisA2))) { return(false); } Vector2 axisB1 = CollB.axes[0]; if (CollA.GetProjectionRadius(axisB1) + CollB.GetProjectionRadius(axisB1) <= Mathf.Abs(Vector2.Dot(nv, axisB1))) { return(false); } Vector2 axisB2 = CollB.axes[1]; if (CollA.GetProjectionRadius(axisB2) + CollB.GetProjectionRadius(axisB2) <= Mathf.Abs(Vector2.Dot(nv, axisB2))) { return(false); } return(true); }
private static void CreateElement(Transform go, int offsetX, int offsetY) { if (go == null) { return; } for (int index = 0; index < go.childCount; index++) { Transform element = go.GetChild(index); if (element.name.Contains("Ele_")) { Transform colliderRoots = element.Find("ColliderRoot"); if (colliderRoots == null) { continue; } List <KeyValuePair <string, CollRectange> > goInCludeRects = GetGoIncludeBlocks(element, offsetX, offsetY); for (int rootIndex = 0; rootIndex < colliderRoots.childCount; rootIndex++) { Transform root = colliderRoots.GetChild(rootIndex); string[] datas = root.name.Split('_'); if (!Enum.IsDefined(typeof(eMapBlockType), datas[0])) { continue; } eMapBlockType blockType = (eMapBlockType)Enum.Parse(typeof(eMapBlockType), datas[0]); if ((int)fileData != (int)blockType && fileData != MapByteDataType.All) { continue; } string blockParam = datas.Length > 1 ? datas[1] : ""; Renderer[] colliderRenderers = root.GetComponentsInChildren <Renderer>(true); List <CollRectange> colliderRectList = new List <CollRectange>(); for (int colliderIndex = 0; colliderIndex < colliderRenderers.Length; colliderIndex++) { Renderer tempRenderer = colliderRenderers[colliderIndex]; CollRectange tempColl = new CollRectange(tempRenderer.transform.position.x, tempRenderer.transform.position.z, tempRenderer.transform.eulerAngles.y, Mathf.Abs(tempRenderer.transform.lossyScale.x), Mathf.Abs(tempRenderer.transform.lossyScale.z)); colliderRectList.Add(tempColl); } for (int blockIndex = goInCludeRects.Count - 1; blockIndex >= 0; blockIndex--) { for (int colliderIndex = 0; colliderIndex < colliderRectList.Count; colliderIndex++) { if (ZTCollider.CheckCollision(goInCludeRects[blockIndex].Value, colliderRectList[colliderIndex])) { if (blockType == eMapBlockType.Height) { blockParam = Mathf.Abs(colliderRenderers[colliderIndex].bounds.size.y) + ""; } AddColliderToDic(goInCludeRects[blockIndex].Key, blockType, blockParam); //goInCludeRects.RemoveAt(blockIndex); break; } } } } } else { CreateElement(element, offsetX, offsetY); } } }