update method 
    
    
    
  Implementation
  bool update() {
  final position = scope.object.position;
  offset.setFrom(position).sub(scope.target);
  // rotate offset to "y-axis-is-up" space
  offset.applyQuaternion(quat);
  // angle from z-axis around y-axis
  spherical.setFromVector3(offset);
  if (scope.autoRotate && state == OrbitState.none) {
    rotateLeft(getAutoRotationAngle);
  }
  if (scope.enableDamping) {
    spherical.theta += sphericalDelta.theta * scope.dampingFactor;
    spherical.phi += sphericalDelta.phi * scope.dampingFactor;
  }
  else {
    spherical.theta += sphericalDelta.theta;
    spherical.phi += sphericalDelta.phi;
  }
  // restrict theta to be between desired limits
  double min = scope.minAzimuthAngle;
  double max = scope.maxAzimuthAngle;
  if (min.isFinite && max.isFinite) {
    if (min < -math.pi){
      min += twoPI;
    }
    else if (min > math.pi){
      min -= twoPI;
    }
    if (max < -math.pi){
      max += twoPI;
    }
    else if (max > math.pi){
      max -= twoPI;
    }
    if (min <= max) {
      spherical.theta = math.max(min, math.min(max, spherical.theta));
    }
    else {
      spherical.theta = (spherical.theta > (min + max) / 2)
          ? math.max(min, spherical.theta)
          : math.min(max, spherical.theta);
    }
  }
  // restrict phi to be between desired limits
  spherical.phi = math.max(
      scope.minPolarAngle, math.min(scope.maxPolarAngle, spherical.phi));
  spherical.makeSafe();
  spherical.radius *= scale;
  // restrict radius to be between desired limits
  spherical.radius = math.max(
      scope.minDistance, math.min(scope.maxDistance, spherical.radius));
  // move target to panned location
  if (scope.enableDamping == true) {
    scope.target.addScaled(panOffset, scope.dampingFactor);
  }
  else {
    scope.target.add(panOffset);
  }
  offset.setFromSpherical(spherical);
  // rotate offset back to "camera-up-vector-is-up" space
  offset.applyQuaternion(quatInverse);
  position.setFrom(scope.target).add(offset);
  scope.object.lookAt(scope.target);
  if (scope.enableDamping == true) {
    sphericalDelta.theta *= (1 - scope.dampingFactor);
    sphericalDelta.phi *= (1 - scope.dampingFactor);
    panOffset.scale(1 - scope.dampingFactor);
  }
  else {
    sphericalDelta.set(0, 0, 0);
    panOffset.setValues(0, 0, 0);
  }
  scale = 1;
  // update condition is:
  // min(camera displacement, camera rotation in radians)^2 > eps
  // using small-angle approximation cos(x/2) = 1 - x^2 / 8
  if (
    zoomChanged ||
    lastPosition.distanceToSquared(scope.object.position) > eps ||
    8 * (1 - lastQuaternion.dot(scope.object.quaternion)) > eps
  ) {
    scope.dispatchEvent(_changeEvent);
    lastPosition.setFrom(scope.object.position);
    lastQuaternion.setFrom(scope.object.quaternion);
    zoomChanged = false;
    return true;
  }
  return false;
}