var rotateAngleParameter, rotateSpeed, rotateState, isMouseUp;
var rotateLine, rotateLineVector, nearClipNormal, rotateTask, rotatePlane;
//初始化旋转参数
function initRotateClipPlaneArgs() {
  rotateState = RotateState.None;
  isMouseUp = false;
  rotatePlane = new THREE.Plane();
  rotateAngleParameter = 0;
  rotateSpeed = 0.002;
}
//设置旋转相关信息
function addRotateInfo() {
  if (ClipPlaneManager.activeMeshInfo == undefined) return;
  if (ClipPlaneManager.isActivePlaneCompleteClipped()) {
    LinesDrawingManager.hideRotateLine();
    return;
  }
  let meshBorders = ClipPlaneManager.getActiveMeshBorders();
  if (meshBorders.length < 1) return;

  setRotateLine();
  LinesDrawingManager.showRotateLine(rotateLine);
  SpriteManager.showRotateSprite();
  nearClipNormal = ClipPlaneManager.getNeighbourPlaneNormal(
    rotateLine,
    ClipPlaneManager.activeMeshInfo.Mesh
  );

  //设置旋转轴
  function setRotateLine() {
    if (ClipPlaneManager.activeMeshInfo.Point == undefined) {
      rotateLine = meshBorders[0];
    } else {
      let pointDistance = -1;
      let projectivePoint = new THREE.Vector3();
      let mouseDownPoint = ClipPlaneManager.activeMeshInfo.Point;
      //取离鼠标按下点最近的边作为rotateLine
      meshBorders.forEach((meshBorder) => {
        meshBorder.closestPointToPoint(mouseDownPoint, false, projectivePoint);
        let distance = mouseDownPoint.distanceTo(projectivePoint);
        if (pointDistance > distance || pointDistance < 0) {
          pointDistance = distance;
          rotateLine = meshBorder;
        }
      });
    }
    rotateAngleParameter = 0;
  }
}

//移除旋转信息
function removeRotateInfo() {
  LinesDrawingManager.hideRotateLine();
  SpriteManager.hideRotateSprite();
  rotateLine = undefined;
  rotateStateReset();
}

//添加旋转线程开始旋转
function addRotateTask(direction) {
  rotateAngleParameter = 0;
  if (rotateState == RotateState.MaximumAngle) {
    rotateState = RotateState.None;
  }
  rotateLineVector = rotateLine.start.clone().sub(rotateLine.end).normalize();
  rotateClipPlane(direction);
  document.addEventListener(OSHelper.touchEnd, OnRotateMouseUp, false);
  rotateTask = setInterval(function () {
    rotateClipPlane(direction);
  }, 30);
}

//旋转切面
async function rotateClipPlane(direction) {
  resetMouseUpState();
  if (!canRotate()) return;
  let rotateAngle =
    direction > 0
      ? rotateAngleParameter + rotateSpeed
      : rotateAngleParameter - rotateSpeed;
  if (!isInRotateAngleRanges(rotateAngle)) return;

  //开始旋转
  rotateState = RotateState.Rotating;

  //获取旋转后平面的法向量
  let vector = getRotatedNormal();
  if (isRotateToMaximumAngle(vector)) {
    return;
  }

  //设置新切面
  rotatePlane.setFromNormalAndCoplanarPoint(vector, rotateLine.end);
  let success = await refreshClipMesh(
    rotatePlane,
    ClipPlaneManager.activeMeshInfo.Mesh.Object,
    ClipPlaneManager.activeMeshInfo.Mesh.ImageName,
    refreshClipMeshCallback
  );
  if (!success) {
    rotateState = RotateState.RotateEnd;
  }

  function canRotate() {
    if (
      rotateState === RotateState.Rotating ||
      rotateState === RotateState.MaximumAngle ||
      ClipPlaneManager.activeMeshInfo === undefined ||
      rotateLine === undefined
    ) {
      return false;
    }
    return true;
  }

  function resetMouseUpState() {
    if (rotateAngleParameter == 0) {
      isMouseUp = false;
    }
  }

  //旋转角参数是否在-1到1范围内
  function isInRotateAngleRanges(rotateAngle) {
    if (rotateAngle > 1 || rotateAngle < -1) {
      return false;
    }
    return true;
  }
  //获取旋转后平面的法向量
  function getRotatedNormal() {
    let vector = ClipPlaneManager.activeMeshInfo.Mesh.Normal.clone();
    let normalVector = new THREE.Vector3();
    //切面法向量与旋转轴叉乘得到旋转方向向量
    normalVector.crossVectors(rotateLineVector, vector);
    if (rotateAngle < 0) {
      normalVector.negate();
    }
    //设置旋转后的法向量（平面法向量沿叉乘方向旋转）
    vector.lerp(normalVector, Math.abs(rotateAngle)).normalize();
    return vector;
  }

  //判断是否旋转到了极限位置 （旋转后与相邻面的夹角是否超过了限定值）
  function isRotateToMaximumAngle(vector) {
    if (nearClipNormal == undefined) return false;
    if (!ClipPlaneManager.isWithinRotateRange(vector, nearClipNormal)) {
      rotateState = RotateState.MaximumAngle;
      return true;
    }
    return false;
  }

  function refreshClipMeshCallback() {
    if (rotateState == RotateState.Rotating) {
      ClipPlaneManager.activeMeshInfo.Mesh.Plane.set(
        rotatePlane.normal.clone(),
        rotatePlane.constant
      );
      if (isMouseUp) {
        ClipPlaneManager.activeMeshInfo.Mesh.Normal =
          ClipPlaneManager.activeMeshInfo.Mesh.Plane.normal.clone();
        rotateAngleParameter = 0;
        isMouseUp = false;
      } else {
        rotateAngleParameter = rotateAngle;
      }
      rotateState = RotateState.RotateEnd;
    }
  }
}

//旋转时鼠标抬起事件
function OnRotateMouseUp() {
  clearInterval(rotateTask);
  if (ClipPlaneManager.activeMeshInfo != undefined) {
    isMouseUp = true;
    ClipPlaneManager.activeMeshInfo.Mesh.Normal =
      ClipPlaneManager.activeMeshInfo.Mesh.Plane.normal.clone();
    ClipPlaneManager.activeMeshInfo.Mesh.Index = undefined;
  }

  rotateAngleParameter = 0;
  document.body.style.cursor = "default";
  document.removeEventListener(OSHelper.touchEnd, OnRotateMouseUp, false);
}

//重置旋转状态
function rotateStateReset() {
  clearInterval(rotateTask);
  rotateAngleParameter = 0;
  if (rotateState == RotateState.MaximumAngle) {
    rotateState = RotateState.None;
  }
}
