### Question:
RouteUtils { @Nullable public String[] calculateRemainingWaypointNames(RouteProgress routeProgress) { RouteOptions routeOptions = routeProgress.directionsRoute().routeOptions(); if (routeOptions == null || TextUtils.isEmpty(routeOptions.waypointNames())) { return null; } String allWaypointNames = routeOptions.waypointNames(); String[] names = allWaypointNames.split(SEMICOLON); int coordinatesSize = routeProgress.directionsRoute().routeOptions().coordinates().size(); String[] remainingWaypointNames = Arrays.copyOfRange(names, coordinatesSize - routeProgress.remainingWaypoints(), coordinatesSize); String[] waypointNames = new String[remainingWaypointNames.length + ORIGIN_WAYPOINT_NAME_THRESHOLD]; waypointNames[ORIGIN_WAYPOINT_NAME] = names[ORIGIN_WAYPOINT_NAME]; System.arraycopy(remainingWaypointNames, FIRST_POSITION, waypointNames, SECOND_POSITION, remainingWaypointNames.length); return waypointNames; }  boolean isNewRoute(@Nullable RouteProgress previousRouteProgress,
                            @NonNull RouteProgress routeProgress); boolean isNewRoute(@Nullable RouteProgress previousRouteProgress,
                            @NonNull DirectionsRoute directionsRoute); boolean isArrivalEvent(@NonNull RouteProgress routeProgress, @NonNull Milestone milestone); boolean isLastLeg(RouteProgress routeProgress); @Nullable List<Point> calculateRemainingWaypoints(RouteProgress routeProgress); @Nullable String[] calculateRemainingWaypointNames(RouteProgress routeProgress); Location createFirstLocationFromRoute(DirectionsRoute route); boolean isValidRouteProfile(String routeProfile); @Nullable BannerInstructions findCurrentBannerInstructions(LegStep currentStep, double stepDistanceRemaining); @Nullable BannerText findCurrentBannerText(LegStep currentStep, double stepDistanceRemaining,
                                          boolean findPrimary); @Nullable VoiceInstructions findCurrentVoiceInstructions(LegStep currentStep, double stepDistanceRemaining);  }### Answer:
@Test public void calculateRemainingWaypointNames() { DirectionsRoute route = mock(DirectionsRoute.class); RouteOptions routeOptions = mock(RouteOptions.class); when(routeOptions.coordinates()).thenReturn(buildCoordinateList()); when(routeOptions.waypointNames()).thenReturn("first;second;third;fourth"); when(route.routeOptions()).thenReturn(routeOptions); RouteProgress routeProgress = mock(RouteProgress.class); when(routeProgress.remainingWaypoints()).thenReturn(2); when(routeProgress.directionsRoute()).thenReturn(route); RouteUtils routeUtils = new RouteUtils(); String[] remainingWaypointNames = routeUtils.calculateRemainingWaypointNames(routeProgress); assertEquals(3, remainingWaypointNames.length); assertEquals("first", remainingWaypointNames[0]); assertEquals("third", remainingWaypointNames[1]); assertEquals("fourth", remainingWaypointNames[2]); }
@Test public void calculateRemainingWaypointNames_handlesNullOptions() { DirectionsRoute route = mock(DirectionsRoute.class); when(route.routeOptions()).thenReturn(null); RouteProgress routeProgress = mock(RouteProgress.class); when(routeProgress.remainingWaypoints()).thenReturn(2); when(routeProgress.directionsRoute()).thenReturn(route); RouteUtils routeUtils = new RouteUtils(); String[] remainingWaypointNames = routeUtils.calculateRemainingWaypointNames(routeProgress); assertNull(remainingWaypointNames); }