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 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 CreateSectorMesh(CollBase collider) { CollSector coll = collider as CollSector; float insideRaius = coll.inCircle; float radius = coll.outCircle; int segment = 60; float angleDegree = coll.angle; Mesh mesh = new Mesh(); int vlen = segment * 2 + 2; Vector3[] vertices = new Vector3[vlen]; float angle = Mathf.Deg2Rad * angleDegree; float currAngle = angle / 2; float deltaAngle = angle / segment; for (int i = 0; i < vlen; i += 2) { float cosA = Mathf.Cos(currAngle); float sinA = Mathf.Sin(currAngle); vertices[i] = new Vector3(cosA * insideRaius, 0, sinA * insideRaius); vertices[i + 1] = new Vector3(cosA * radius, 0, sinA * radius); currAngle -= deltaAngle; } int tlen = segment * 6; int[] triangles = new int[tlen]; for (int i = 0, vi = 0; i < tlen; i += 6, vi += 2) { triangles[i] = vi; triangles[i + 1] = vi + 1; triangles[i + 2] = vi + 3; triangles[i + 3] = vi + 3; triangles[i + 4] = vi + 2; triangles[i + 5] = vi; } mesh.vertices = vertices; mesh.triangles = triangles; return(mesh); }
//圆与扇形 (暂时不做扇形内圆过滤 如有必需 多算一次小扇形是否相交) public static bool RadiusToSector(CollRadius CollA, CollSector CollB) { //长轴距离过滤 if (Vector2.Distance(CollA.GetV2Pos(), CollB.GetV2Pos()) > CollB.outCircle + CollA.Radius) { return(false); } //扇形最远点 即中轴与x轴夹角 (不做旋转时 扇形对称分布 夹角0) float angle = CollB.GetCalRotate(); float cosA = Mathf.Cos(angle * Mathf.Deg2Rad); float sinA = Mathf.Sin(angle * Mathf.Deg2Rad); //计算最远点坐标 float x2 = CollB.x + cosA * CollB.outCircle; float y2 = CollB.y + sinA * CollB.outCircle; float theta = CollB.angle * Mathf.Deg2Rad; return(IsCircleIntersectFan(CollA.x, CollA.y, CollA.Radius, CollB.x, CollB.y, x2, y2, theta)); }
//扇形与扇形 public static bool SectorToSector(CollSector CollA, CollSector CollB) { return(false); }