Returns the point on the great circle segment ab closest to x.

def GetClosestPoint(x, a, b):
  """
  Returns the point on the great circle segment ab closest to x.
  """
  assert(x.IsUnitLength())
  assert(a.IsUnitLength())
  assert(b.IsUnitLength())

  a_cross_b = a.RobustCrossProd(b)
  # project to the great circle going through a and b
  p = x.Minus(
      a_cross_b.Times(
      x.DotProd(a_cross_b) / a_cross_b.Norm2()))

  # if p lies between a and b, return it
  if SimpleCCW(a_cross_b, a, p) and SimpleCCW(p, b, a_cross_b):
    return p.Normalize()

  # otherwise return the closer of a or b
  if x.Minus(a).Norm2() <= x.Minus(b).Norm2():
    return a
  else:
    return b