diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml
index b67c3cbc..c9564a6a 100644
--- a/app/src/main/AndroidManifest.xml
+++ b/app/src/main/AndroidManifest.xml
@@ -26,6 +26,9 @@
+
diff --git a/app/src/main/kotlin/com/mapzen/erasermap/presenter/MainPresenter.kt b/app/src/main/kotlin/com/mapzen/erasermap/presenter/MainPresenter.kt
index c1fbe41f..806d635a 100644
--- a/app/src/main/kotlin/com/mapzen/erasermap/presenter/MainPresenter.kt
+++ b/app/src/main/kotlin/com/mapzen/erasermap/presenter/MainPresenter.kt
@@ -13,6 +13,7 @@ public interface MainPresenter {
public fun onSearchResultSelected(position: Int)
public fun onExpandSearchView()
public fun onCollapseSearchView()
+ public fun onShowDirectionList()
public fun onQuerySubmit()
public fun onViewAllSearchResults()
public fun onBackPressed()
diff --git a/app/src/main/kotlin/com/mapzen/erasermap/presenter/MainPresenterImpl.kt b/app/src/main/kotlin/com/mapzen/erasermap/presenter/MainPresenterImpl.kt
index 55cae212..67b4664a 100644
--- a/app/src/main/kotlin/com/mapzen/erasermap/presenter/MainPresenterImpl.kt
+++ b/app/src/main/kotlin/com/mapzen/erasermap/presenter/MainPresenterImpl.kt
@@ -77,4 +77,8 @@ public class MainPresenterImpl() : MainPresenter {
viewController?.shutDown()
}
}
+
+ override fun onShowDirectionList() {
+ viewController?.showDirectionList()
+ }
}
diff --git a/app/src/main/kotlin/com/mapzen/erasermap/util/DisplayHelper.kt b/app/src/main/kotlin/com/mapzen/erasermap/util/DisplayHelper.kt
new file mode 100644
index 00000000..4d198928
--- /dev/null
+++ b/app/src/main/kotlin/com/mapzen/erasermap/util/DisplayHelper.kt
@@ -0,0 +1,21 @@
+package com.mapzen.erasermap.util
+
+import android.content.Context
+import com.mapzen.erasermap.R
+
+public object DisplayHelper {
+
+ /**
+ * Fetch the resource drawable ID of the turn icon for the given instruction and style.
+
+ * @param context current context in which to display the icon.
+ * *
+ * @param turnInstruction the integer value representing this turn instruction.
+ * *
+ * @return the resource ID of the turn icon to display.
+ */
+ public fun getRouteDrawable(context: Context, turnInstruction: Int?): Int {
+ var drawableId = context.getResources().getIdentifier("ic_route_" + turnInstruction, "drawable", context.getPackageName())
+ return drawableId
+ }
+}
diff --git a/app/src/main/kotlin/com/mapzen/erasermap/view/InstructionListActivity.kt b/app/src/main/kotlin/com/mapzen/erasermap/view/InstructionListActivity.kt
new file mode 100644
index 00000000..4f95cc63
--- /dev/null
+++ b/app/src/main/kotlin/com/mapzen/erasermap/view/InstructionListActivity.kt
@@ -0,0 +1,136 @@
+package com.mapzen.erasermap.view
+
+import android.content.Context
+import android.opengl.Visibility
+import android.os.Bundle
+import android.support.v7.app.AppCompatActivity
+import android.view.MenuItem
+import android.view.View
+import android.view.ViewGroup
+import android.widget.BaseAdapter
+import android.widget.ListView
+import android.widget.TextView
+import android.widget.ImageView
+import com.mapzen.erasermap.R
+import com.mapzen.erasermap.util.DisplayHelper
+import com.mapzen.pelias.SimpleFeature
+import com.mapzen.valhalla.Instruction
+import com.mapzen.helpers.DistanceFormatter
+import java.util.ArrayList
+
+public class InstructionListActivity : AppCompatActivity() {
+ override fun onCreate(savedInstanceState: Bundle?) {
+ super.onCreate(savedInstanceState)
+ setContentView(R.layout.activity_instructions)
+ getSupportActionBar()?.hide()
+ val listView = findViewById(R.id.instruction_list_view) as ListView
+ findViewById(R.id.route_reverse).setVisibility(View.GONE)
+ val bundle = getIntent()?.getExtras()
+ val instruction_strings: ArrayList? = bundle?.getStringArrayList("instruction_strings")
+ val instruction_types: ArrayList? = bundle?.getIntegerArrayList("instruction_types")
+ val instruction_distances: ArrayList? = bundle?.getIntegerArrayList("instruction_distances")
+ val reverse : Boolean = bundle?.getBoolean("reverse") as Boolean
+ setHeaderOrigins(bundle, reverse)
+ if (instruction_strings != null) {
+ listView.setAdapter(DirectionListAdapter(this, instruction_strings, instruction_types, instruction_distances, reverse))
+ listView.setOnItemClickListener { parent, view, position, id ->
+ setResult(position)
+ finish()
+ }
+ }
+ }
+
+ private fun setHeaderOrigins(bundle: Bundle?, reverse: Boolean) {
+ if (reverse) {
+ (findViewById(R.id.starting_point) as TextView).setText(bundle?.getString("destination"))
+ (findViewById(R.id.destination) as TextView).setText(R.string.current_location)
+ findViewById(R.id.starting_location_icon).setVisibility(View.GONE)
+ findViewById(R.id.destination_location_icon).setVisibility(View.VISIBLE)
+ } else {
+ (findViewById(R.id.starting_point) as TextView).setText(R.string.current_location)
+ (findViewById(R.id.destination) as TextView).setText(bundle?.getString("destination"))
+ findViewById(R.id.starting_location_icon).setVisibility(View.VISIBLE)
+ findViewById(R.id.destination_location_icon).setVisibility(View.GONE)
+ }
+ }
+
+ override fun onOptionsItemSelected(item: MenuItem?): Boolean {
+ setResult(-1)
+ finish()
+ return true
+ }
+
+ private class DirectionListAdapter(context: Context, strings: ArrayList?,
+ types: ArrayList?, distances: ArrayList?,
+ reverse : Boolean) : BaseAdapter() {
+ private final var CURRENT_LOCATION_OFFSET = 1
+ private var instruction_strings: ArrayList? = strings
+ private var instruction_types: ArrayList? = types
+ private var instruction_distances: ArrayList? = distances
+ private var context: Context = context
+ private var reverse : Boolean = reverse
+
+ override fun getCount(): Int {
+ var size = if (instruction_strings != null) (instruction_strings!!.size()
+ + CURRENT_LOCATION_OFFSET) else 0
+ return size
+ }
+
+ override fun getItemId(position: Int): Long {
+ return 0
+ }
+
+ override fun getItem(position: Int): Any? {
+ return 0
+ }
+
+ override fun getView(position: Int, convertView: View?, parent: ViewGroup): View? {
+ var view: View = View.inflate(context, R.layout.direction_list_item, null)
+ if(reverse) {
+ setReversedDirectionListItem(position, view)
+ } else {
+ setDirectionListItem(position, view)
+ }
+ return view
+ }
+
+ private fun setReversedDirectionListItem(position : Int, view : View) {
+ if(position == instruction_strings?.size()) {
+ setListItemToCurrentLocation(view)
+ } else {
+ var distanceVal : Int? = instruction_distances?.get(position)
+ var formattedDistance : String = DistanceFormatter.format(
+ (distanceVal?.toInt() as Int))
+ var iconId : Int = DisplayHelper.getRouteDrawable(context,
+ instruction_types?.get(position))
+
+ (view.findViewById(R.id.simple_instruction) as TextView).setText(
+ instruction_strings?.get(position).toString())
+ (view.findViewById(R.id.distance) as TextView).setText(formattedDistance)
+ (view.findViewById(R.id.icon) as ImageView).setImageResource(iconId)
+ }
+ }
+
+ private fun setDirectionListItem(position : Int, view : View) {
+ if (position == 0 ) {
+ setListItemToCurrentLocation(view)
+ } else {
+ var distanceVal : Int? = instruction_distances?.get(position - CURRENT_LOCATION_OFFSET)
+ var formattedDistance : String = DistanceFormatter.format((distanceVal?.toInt() as Int))
+ var iconId : Int = DisplayHelper.getRouteDrawable(context,
+ instruction_types?.get(position - CURRENT_LOCATION_OFFSET))
+
+ (view.findViewById(R.id.simple_instruction) as TextView).setText(
+ instruction_strings?.get(position - CURRENT_LOCATION_OFFSET).toString())
+ (view.findViewById(R.id.distance) as TextView).setText(formattedDistance)
+ (view.findViewById(R.id.icon) as ImageView).setImageResource(iconId)
+ }
+ }
+
+ private fun setListItemToCurrentLocation(view : View) {
+ (view.findViewById(R.id.simple_instruction) as TextView).setText(R.string.current_location)
+ (view.findViewById(R.id.icon) as ImageView).setImageResource(R.drawable.ic_locate)
+ }
+ }
+
+}
diff --git a/app/src/main/kotlin/com/mapzen/erasermap/view/MainActivity.kt b/app/src/main/kotlin/com/mapzen/erasermap/view/MainActivity.kt
index f82543cb..37ed57e5 100644
--- a/app/src/main/kotlin/com/mapzen/erasermap/view/MainActivity.kt
+++ b/app/src/main/kotlin/com/mapzen/erasermap/view/MainActivity.kt
@@ -68,6 +68,7 @@ public class MainActivity : AppCompatActivity(), ViewController, Router.Callback
public val requestCodeSearchResults: Int = 0x01
+ private var route: Route? = null;
var locationClient: LostApiClient? = null
@Inject set
var tileCache: Cache? = null
@@ -89,6 +90,8 @@ public class MainActivity : AppCompatActivity(), ViewController, Router.Callback
var destination: Feature? = null
var path: PathLayer? = null
var markers: ItemizedLayer? = null
+ var type : Router.Type = Router.Type.DRIVING
+ var reverse : Boolean = false;
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
@@ -102,6 +105,7 @@ public class MainActivity : AppCompatActivity(), ViewController, Router.Callback
initPoiLayer()
initAutoCompleteAdapter()
initFindMeButton()
+ initreverseButton()
centerOnCurrentLocation()
presenter?.onRestoreViewState()
}
@@ -213,7 +217,6 @@ public class MainActivity : AppCompatActivity(), ViewController, Router.Callback
listView.setEmptyView(emptyView)
restoreCurrentSearchTerm()
}
-
return true
}
@@ -407,16 +410,11 @@ public class MainActivity : AppCompatActivity(), ViewController, Router.Callback
override fun showRoutePreview(feature: Feature) {
this.destination = feature
- val simpleFeature = SimpleFeature.fromFeature(feature)
- val location = LocationServices.FusedLocationApi?.getLastLocation();
- if (location is Location) {
- val start: DoubleArray = doubleArrayOf(location.getLatitude(), location.getLongitude())
- val dest: DoubleArray = doubleArrayOf(simpleFeature.getLat(), simpleFeature.getLon())
- getInitializedRouter().setLocation(start).setLocation(dest).setCallback(this).fetch()
- }
+ route()
}
override fun success(route: Route?) {
+ this.route = route;
runOnUiThread({
getSupportActionBar()?.hide()
findViewById(R.id.route_preview).setVisibility(View.VISIBLE)
@@ -478,7 +476,6 @@ public class MainActivity : AppCompatActivity(), ViewController, Router.Callback
} catch (e: Exception) {
Toast.makeText(this@MainActivity, "No route found", Toast.LENGTH_LONG).show()
}
-
}
private fun getMarkerItem(icon: Int, loc: Location, place: MarkerItem.HotspotPlace): MarkerItem {
@@ -496,44 +493,68 @@ public class MainActivity : AppCompatActivity(), ViewController, Router.Callback
findViewById(R.id.route_preview).setVisibility(View.GONE)
}
+ fun route() {
+ val simpleFeature = SimpleFeature.fromFeature(destination)
+ val location = LocationServices.FusedLocationApi?.getLastLocation()
+ if (reverse) {
+ if (location is Location) {
+ val start: DoubleArray = doubleArrayOf(simpleFeature.getLat(), simpleFeature.getLon())
+ val dest: DoubleArray = doubleArrayOf(location.getLatitude(), location.getLongitude())
+ getInitializedRouter().setLocation(start).setLocation(dest).setCallback(this).fetch()
+ }
+ } else {
+ if (location is Location) {
+ val start: DoubleArray = doubleArrayOf(location.getLatitude(), location.getLongitude())
+ val dest: DoubleArray = doubleArrayOf(simpleFeature.getLat(), simpleFeature.getLon())
+ getInitializedRouter().setLocation(start).setLocation(dest).setCallback(this).fetch()
+ }
+ }
+ }
fun updateRoutePreview(destination: Feature?) {
- val dest = SimpleFeature.fromFeature(destination)
(findViewById(R.id.by_car) as RadioButton).setOnCheckedChangeListener { compoundButton, b ->
if (b) {
- val location = LocationServices.FusedLocationApi?.getLastLocation();
- if (location is Location) {
- val start: DoubleArray = doubleArrayOf(location.getLatitude(), location.getLongitude())
- val dest: DoubleArray = doubleArrayOf(dest.getLat(), dest.getLon())
- getInitializedRouter().setDriving().setLocation(start).setCallback(this).setLocation(dest).fetch();
- }
+ type = Router.Type.DRIVING
+ route()
(findViewById(R.id.routing_circle) as ImageButton).setImageResource(R.drawable.ic_start_car_normal)
}
}
(findViewById(R.id.by_foot) as RadioButton).setOnCheckedChangeListener { compoundButton, b ->
if (b) {
- val location = LocationServices.FusedLocationApi?.getLastLocation();
- if (location is Location) {
- val start: DoubleArray = doubleArrayOf(location.getLatitude(), location.getLongitude())
- val dest: DoubleArray = doubleArrayOf(dest.getLat(), dest.getLon())
- getInitializedRouter().setWalking().setLocation(start).setLocation(dest).setCallback(this).fetch();
- }
+ type = Router.Type.WALKING
+ route()
(findViewById(R.id.routing_circle) as ImageButton).setImageResource(R.drawable.ic_start_walk_normal)
}
}
(findViewById(R.id.by_bike) as RadioButton).setOnCheckedChangeListener { compoundButton, b ->
if (b) {
- val location = LocationServices.FusedLocationApi?.getLastLocation();
- if (location is Location) {
- val start: DoubleArray = doubleArrayOf(location.getLatitude(), location.getLongitude())
- val dest: DoubleArray = doubleArrayOf(dest.getLat(), dest.getLon())
- getInitializedRouter().setBiking().setLocation(start).setLocation(dest).setCallback(this).fetch()
- }
+ type = Router.Type.BIKING
+ route()
(findViewById(R.id.routing_circle) as ImageButton).setImageResource(R.drawable.ic_start_bike_normal)
}
}
}
+ private fun reverse() {
+ reverse = !reverse;
+ (findViewById(R.id.route_preview) as RoutePreviewView).reverse = this.reverse
+ if(reverse) {
+ findViewById(R.id.starting_location_icon).setVisibility(View.GONE)
+ findViewById(R.id.destination_location_icon).setVisibility(View.VISIBLE)
+ } else {
+ findViewById(R.id.starting_location_icon).setVisibility(View.VISIBLE)
+ findViewById(R.id.destination_location_icon).setVisibility(View.GONE)
+ }
+ route()
+ }
+
+ private fun initreverseButton() {
+ (findViewById(R.id.route_reverse) as ImageButton).setOnClickListener({ reverse()})
+
+ (findViewById(R.id.routing_circle) as ImageButton).setOnClickListener (
+ {presenter?.onShowDirectionList()})
+ }
+
override fun onBackPressed() {
if ((findViewById(R.id.route_preview)).getVisibility() == View.VISIBLE) {
mapController?.getMap()?.layers()?.remove(path)
@@ -547,7 +568,31 @@ public class MainActivity : AppCompatActivity(), ViewController, Router.Callback
finish()
}
+ override fun showDirectionList() {
+ val instructionStrings = ArrayList()
+ val instructionType= ArrayList()
+ val instructionDistance= ArrayList()
+ for(instruction in route!!.getRouteInstructions() ) {
+ instructionStrings.add(instruction.getHumanTurnInstruction())
+ instructionType.add(instruction.turnInstruction)
+ instructionDistance.add(instruction.distance)
+ }
+ val simpleFeature = SimpleFeature.fromFeature(destination)
+ val intent = Intent(this, javaClass())
+ intent.putExtra("instruction_strings", instructionStrings)
+ intent.putExtra("instruction_types", instructionType)
+ intent.putExtra("instruction_distances", instructionDistance)
+ intent.putExtra("destination", simpleFeature.toString())
+ intent.putExtra("reverse", this.reverse)
+ startActivityForResult(intent, requestCodeSearchResults)
+ }
+
private fun getInitializedRouter(): Router {
- return Router().setApiKey(BuildConfig.VALHALLA_API_KEY);
+ when(type) {
+ Router.Type.DRIVING -> return Router().setApiKey(BuildConfig.VALHALLA_API_KEY).setDriving()
+ Router.Type.WALKING -> return Router().setApiKey(BuildConfig.VALHALLA_API_KEY).setWalking()
+ Router.Type.BIKING -> return Router().setApiKey(BuildConfig.VALHALLA_API_KEY).setBiking()
+ }
}
}
+
diff --git a/app/src/main/kotlin/com/mapzen/erasermap/view/RoutePreviewView.kt b/app/src/main/kotlin/com/mapzen/erasermap/view/RoutePreviewView.kt
index 606bae64..e80cb1d9 100644
--- a/app/src/main/kotlin/com/mapzen/erasermap/view/RoutePreviewView.kt
+++ b/app/src/main/kotlin/com/mapzen/erasermap/view/RoutePreviewView.kt
@@ -15,14 +15,23 @@ import com.mapzen.valhalla.Router
public class RoutePreviewView : RelativeLayout {
+ public var reverse : Boolean = false
public var destination: SimpleFeature? = null
set (destination) {
- (findViewById(R.id.destination) as TextView).setText(destination?.getTitle())
+ if(reverse) {
+ (findViewById(R.id.starting_point) as TextView).setText(destination?.getTitle())
+ } else {
+ (findViewById(R.id.destination) as TextView).setText(destination?.getTitle())
+ }
}
public var route: Route? = null
set (route) {
- (findViewById(R.id.starting_point) as TextView).setText(R.string.current_location)
+ if(reverse) {
+ (findViewById(R.id.destination) as TextView).setText(R.string.current_location)
+ } else {
+ (findViewById(R.id.starting_point) as TextView).setText(R.string.current_location)
+ }
}
public constructor(context: Context) : super(context) {
diff --git a/app/src/main/kotlin/com/mapzen/erasermap/view/ViewController.kt b/app/src/main/kotlin/com/mapzen/erasermap/view/ViewController.kt
index 530207bd..7598b2e9 100644
--- a/app/src/main/kotlin/com/mapzen/erasermap/view/ViewController.kt
+++ b/app/src/main/kotlin/com/mapzen/erasermap/view/ViewController.kt
@@ -4,6 +4,7 @@ import com.mapzen.pelias.gson.Feature
public interface ViewController {
public fun showSearchResults(features: List)
+ public fun showDirectionList()
public fun centerOnCurrentFeature(features: List)
public fun showAllSearchResults(features: List)
public fun hideSearchResults()
diff --git a/app/src/main/res/drawable-hdpi/ic_route_gr_1.png b/app/src/main/res/drawable-hdpi/ic_route_gr_1.png
new file mode 100644
index 00000000..ac7ff8c0
Binary files /dev/null and b/app/src/main/res/drawable-hdpi/ic_route_gr_1.png differ
diff --git a/app/src/main/res/drawable-mdpi/ic_route_gr_1.png b/app/src/main/res/drawable-mdpi/ic_route_gr_1.png
new file mode 100644
index 00000000..dbd5fda2
Binary files /dev/null and b/app/src/main/res/drawable-mdpi/ic_route_gr_1.png differ
diff --git a/app/src/main/res/drawable-xhdpi/ic_route_gr_1.png b/app/src/main/res/drawable-xhdpi/ic_route_gr_1.png
new file mode 100644
index 00000000..191f981d
Binary files /dev/null and b/app/src/main/res/drawable-xhdpi/ic_route_gr_1.png differ
diff --git a/app/src/main/res/drawable-xxhdpi/ic_route_gr_1.png b/app/src/main/res/drawable-xxhdpi/ic_route_gr_1.png
new file mode 100644
index 00000000..2d384220
Binary files /dev/null and b/app/src/main/res/drawable-xxhdpi/ic_route_gr_1.png differ
diff --git a/app/src/main/res/drawable/ic_route_0.png b/app/src/main/res/drawable/ic_route_0.png
new file mode 100644
index 00000000..9dba9a92
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_0.png differ
diff --git a/app/src/main/res/drawable/ic_route_1.png b/app/src/main/res/drawable/ic_route_1.png
new file mode 100644
index 00000000..5f58a6d2
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_1.png differ
diff --git a/app/src/main/res/drawable/ic_route_10.png b/app/src/main/res/drawable/ic_route_10.png
new file mode 100644
index 00000000..2079d5b9
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_10.png differ
diff --git a/app/src/main/res/drawable/ic_route_11.png b/app/src/main/res/drawable/ic_route_11.png
new file mode 100644
index 00000000..3548d3c1
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_11.png differ
diff --git a/app/src/main/res/drawable/ic_route_12.png b/app/src/main/res/drawable/ic_route_12.png
new file mode 100644
index 00000000..d0e18d43
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_12.png differ
diff --git a/app/src/main/res/drawable/ic_route_13.png b/app/src/main/res/drawable/ic_route_13.png
new file mode 100644
index 00000000..3460cc41
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_13.png differ
diff --git a/app/src/main/res/drawable/ic_route_14.png b/app/src/main/res/drawable/ic_route_14.png
new file mode 100644
index 00000000..bab9d3f6
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_14.png differ
diff --git a/app/src/main/res/drawable/ic_route_15.png b/app/src/main/res/drawable/ic_route_15.png
new file mode 100644
index 00000000..0a095a2c
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_15.png differ
diff --git a/app/src/main/res/drawable/ic_route_16.png b/app/src/main/res/drawable/ic_route_16.png
new file mode 100644
index 00000000..ea4303ce
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_16.png differ
diff --git a/app/src/main/res/drawable/ic_route_17.png b/app/src/main/res/drawable/ic_route_17.png
new file mode 100644
index 00000000..7a12b6e2
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_17.png differ
diff --git a/app/src/main/res/drawable/ic_route_18.png b/app/src/main/res/drawable/ic_route_18.png
new file mode 100644
index 00000000..40e89482
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_18.png differ
diff --git a/app/src/main/res/drawable/ic_route_19.png b/app/src/main/res/drawable/ic_route_19.png
new file mode 100644
index 00000000..7bc73e4d
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_19.png differ
diff --git a/app/src/main/res/drawable/ic_route_2.png b/app/src/main/res/drawable/ic_route_2.png
new file mode 100644
index 00000000..6fb3a388
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_2.png differ
diff --git a/app/src/main/res/drawable/ic_route_20.png b/app/src/main/res/drawable/ic_route_20.png
new file mode 100644
index 00000000..1f2b0f4d
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_20.png differ
diff --git a/app/src/main/res/drawable/ic_route_21.png b/app/src/main/res/drawable/ic_route_21.png
new file mode 100644
index 00000000..eaa9e749
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_21.png differ
diff --git a/app/src/main/res/drawable/ic_route_22.png b/app/src/main/res/drawable/ic_route_22.png
new file mode 100644
index 00000000..dfbd56cc
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_22.png differ
diff --git a/app/src/main/res/drawable/ic_route_23.png b/app/src/main/res/drawable/ic_route_23.png
new file mode 100644
index 00000000..bf618865
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_23.png differ
diff --git a/app/src/main/res/drawable/ic_route_24.png b/app/src/main/res/drawable/ic_route_24.png
new file mode 100644
index 00000000..8e9dea7d
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_24.png differ
diff --git a/app/src/main/res/drawable/ic_route_25.png b/app/src/main/res/drawable/ic_route_25.png
new file mode 100644
index 00000000..c4dc5620
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_25.png differ
diff --git a/app/src/main/res/drawable/ic_route_26.png b/app/src/main/res/drawable/ic_route_26.png
new file mode 100644
index 00000000..b7f11f9e
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_26.png differ
diff --git a/app/src/main/res/drawable/ic_route_27.png b/app/src/main/res/drawable/ic_route_27.png
new file mode 100644
index 00000000..2b978ab2
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_27.png differ
diff --git a/app/src/main/res/drawable/ic_route_28.png b/app/src/main/res/drawable/ic_route_28.png
new file mode 100644
index 00000000..53c854bb
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_28.png differ
diff --git a/app/src/main/res/drawable/ic_route_29.png b/app/src/main/res/drawable/ic_route_29.png
new file mode 100644
index 00000000..7f669fb9
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_29.png differ
diff --git a/app/src/main/res/drawable/ic_route_3.png b/app/src/main/res/drawable/ic_route_3.png
new file mode 100644
index 00000000..75b40001
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_3.png differ
diff --git a/app/src/main/res/drawable/ic_route_30.png b/app/src/main/res/drawable/ic_route_30.png
new file mode 100644
index 00000000..f216e2ed
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_30.png differ
diff --git a/app/src/main/res/drawable/ic_route_31.png b/app/src/main/res/drawable/ic_route_31.png
new file mode 100644
index 00000000..b8652a10
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_31.png differ
diff --git a/app/src/main/res/drawable/ic_route_32.png b/app/src/main/res/drawable/ic_route_32.png
new file mode 100644
index 00000000..2f184a30
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_32.png differ
diff --git a/app/src/main/res/drawable/ic_route_4.png b/app/src/main/res/drawable/ic_route_4.png
new file mode 100644
index 00000000..1a9e26ca
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_4.png differ
diff --git a/app/src/main/res/drawable/ic_route_5.png b/app/src/main/res/drawable/ic_route_5.png
new file mode 100644
index 00000000..e8413f84
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_5.png differ
diff --git a/app/src/main/res/drawable/ic_route_6.png b/app/src/main/res/drawable/ic_route_6.png
new file mode 100644
index 00000000..3188ed62
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_6.png differ
diff --git a/app/src/main/res/drawable/ic_route_7.png b/app/src/main/res/drawable/ic_route_7.png
new file mode 100644
index 00000000..2d3b658a
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_7.png differ
diff --git a/app/src/main/res/drawable/ic_route_8.png b/app/src/main/res/drawable/ic_route_8.png
new file mode 100644
index 00000000..f7d1e6b2
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_8.png differ
diff --git a/app/src/main/res/drawable/ic_route_9.png b/app/src/main/res/drawable/ic_route_9.png
new file mode 100644
index 00000000..a7a15ec0
Binary files /dev/null and b/app/src/main/res/drawable/ic_route_9.png differ
diff --git a/app/src/main/res/layout/activity_instructions.xml b/app/src/main/res/layout/activity_instructions.xml
new file mode 100644
index 00000000..a5e80d42
--- /dev/null
+++ b/app/src/main/res/layout/activity_instructions.xml
@@ -0,0 +1,22 @@
+
+
+
+
+
+
+
+
+
+
diff --git a/app/src/main/res/layout/direction_list_item.xml b/app/src/main/res/layout/direction_list_item.xml
new file mode 100644
index 00000000..42d145e0
--- /dev/null
+++ b/app/src/main/res/layout/direction_list_item.xml
@@ -0,0 +1,41 @@
+
+
+
+
+
+
+
+
+
+
+
diff --git a/app/src/main/res/layout/list_header_divider.xml b/app/src/main/res/layout/list_header_divider.xml
new file mode 100644
index 00000000..5ffebbbf
--- /dev/null
+++ b/app/src/main/res/layout/list_header_divider.xml
@@ -0,0 +1,18 @@
+
+
+
+
+
+
+
+
diff --git a/app/src/main/res/layout/list_item_instruction.xml b/app/src/main/res/layout/list_item_instruction.xml
new file mode 100644
index 00000000..c6fd91fc
--- /dev/null
+++ b/app/src/main/res/layout/list_item_instruction.xml
@@ -0,0 +1,11 @@
+
+
diff --git a/app/src/main/res/layout/route_header.xml b/app/src/main/res/layout/route_header.xml
index c2019822..164ba620 100644
--- a/app/src/main/res/layout/route_header.xml
+++ b/app/src/main/res/layout/route_header.xml
@@ -94,7 +94,7 @@
android:layout_height="wrap_content"
android:layout_gravity="center_vertical"
android:layout_marginLeft="4dp"
- android:src="@drawable/ic_pin_outline"
+ android:src="@drawable/ic_locate"
android:visibility="gone" />
No recent searches
%1$d of %2$d results
Search Results
+ Instructions
From:
To:
Current Location
diff --git a/app/src/test/java/com/mapzen/erasermap/presenter/MainPresenterTest.java b/app/src/test/java/com/mapzen/erasermap/presenter/MainPresenterTest.java
index b51cd43e..a2c49698 100644
--- a/app/src/test/java/com/mapzen/erasermap/presenter/MainPresenterTest.java
+++ b/app/src/test/java/com/mapzen/erasermap/presenter/MainPresenterTest.java
@@ -138,7 +138,12 @@ public void onBackPressed_shouldHideRoutePreview() throws Exception {
presenter.onRoutePreviewEvent(new RoutePreviewEvent(getTestFeature()));
presenter.onBackPressed();
assertThat(controller.isRoutePreviewVisible).isFalse();
+ }
+ @Test
+ public void onShowDirectionList_shouldMakeDirectionsVisible(){
+ presenter.onShowDirectionList();
+ assertThat(controller.isDirectionListVisible).isTrue();
}
private class TestViewController implements ViewController {
@@ -148,6 +153,7 @@ private class TestViewController implements ViewController {
private boolean isViewAllVisible;
private boolean isSearchVisible;
private boolean isRoutePreviewVisible;
+ private boolean isDirectionListVisible;
@Override public void showSearchResults(@NotNull List extends Feature> features) {
searchResults = (List) features;
@@ -201,5 +207,8 @@ private class TestViewController implements ViewController {
@Override public void shutDown() {
}
+
+ @Override
+ public void showDirectionList() { isDirectionListVisible = true;}
}
}
diff --git a/app/src/test/java/com/mapzen/erasermap/view/InstructionListActivityTest.java b/app/src/test/java/com/mapzen/erasermap/view/InstructionListActivityTest.java
new file mode 100644
index 00000000..878a2a39
--- /dev/null
+++ b/app/src/test/java/com/mapzen/erasermap/view/InstructionListActivityTest.java
@@ -0,0 +1,154 @@
+package com.mapzen.erasermap.view;
+
+import android.content.Intent;
+import android.os.Bundle;
+import android.view.MenuItem;
+import android.view.View;
+import android.view.ViewGroup;
+import android.widget.ImageView;
+import android.widget.ListView;
+import android.widget.TextView;
+
+import com.mapzen.erasermap.BuildConfig;
+import com.mapzen.erasermap.PrivateMapsTestRunner;
+import com.mapzen.erasermap.R;
+import com.mapzen.pelias.SimpleFeature;
+import com.mapzen.valhalla.Route;
+
+import org.jetbrains.annotations.NotNull;
+import org.json.JSONException;
+import org.junit.Before;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.robolectric.Robolectric;
+import org.robolectric.annotation.Config;
+import org.robolectric.fakes.RoboMenuItem;
+import org.robolectric.shadows.ShadowActivity;
+import org.robolectric.shadows.ShadowIntent;
+
+import java.io.IOException;
+
+import static com.mapzen.erasermap.dummy.TestHelper.getFixture;
+import static com.mapzen.erasermap.dummy.TestHelper.getTestFeature;
+import static org.assertj.core.api.Assertions.assertThat;
+import static org.robolectric.Shadows.shadowOf;
+
+@RunWith(PrivateMapsTestRunner.class)
+@Config(constants = BuildConfig.class, emulateSdk = 21)
+public class InstructionListActivityTest {
+ private static MainActivity startActivity = Robolectric.setupActivity(MainActivity.class);;
+ private InstructionListActivity activity;
+
+ @Before
+ public void setUp() throws Exception {
+ startActivity.setReverse(false);
+ startActivity.showRoutePreview(getTestFeature());
+ startActivity.success(new Route(getFixture("valhalla_route")));
+ startActivity.findViewById(R.id.routing_circle).performClick();
+ ShadowActivity shadowActivity = shadowOf(startActivity);
+ Intent startedIntent = shadowActivity.getNextStartedActivity();
+ activity = Robolectric.buildActivity(InstructionListActivity.class)
+ .withIntent(startedIntent).create().get();
+ }
+
+ public void setActivityToReverse() throws IOException, JSONException {
+ startActivity.setReverse(true);
+ startActivity.showRoutePreview(getTestFeature());
+ try {
+ startActivity.success(new Route(getFixture("valhalla_route")));
+ } catch (JSONException e) {
+ e.printStackTrace();
+ } catch (IOException e) {
+ e.printStackTrace();
+ }
+ startActivity.findViewById(R.id.routing_circle).performClick();
+ ShadowActivity shadowActivity = shadowOf(startActivity);
+ Intent startedIntent = shadowActivity.getNextStartedActivity();
+ activity = Robolectric.buildActivity(InstructionListActivity.class)
+ .withIntent(startedIntent).create().get();
+ }
+
+ @Test
+ public void shouldNotBeNull() throws Exception {
+ assertThat(activity).isNotNull();
+ }
+
+ @Test
+ public void shouldHaveListView() throws Exception {
+ assertThat(activity.findViewById(R.id.instruction_list_view)).isNotNull();
+ }
+
+ @Test
+ public void onDirectionListOpen_shouldHaveOriginSet() throws Exception {
+ assertThat(((TextView)activity.findViewById(R.id.destination)).getText())
+ .isEqualTo( SimpleFeature.fromFeature(startActivity.getDestination()).toString());
+ assertThat(((TextView)activity.findViewById(R.id.starting_point)).getText())
+ .isEqualTo(activity.getString(R.string.current_location));
+ }
+
+ @Test
+ public void onDirectionListOpenReversed_shouldHaveOriginSet() throws Exception {
+ setActivityToReverse();
+ assertThat(((TextView) activity.findViewById(R.id.starting_point)).getText())
+ .isEqualTo(SimpleFeature.fromFeature(startActivity.getDestination()).toString());
+ assertThat(((TextView)activity.findViewById(R.id.destination)).getText())
+ .isEqualTo(activity.getString(R.string.current_location));
+ }
+
+ @Test
+ public void onDirectionListOpen_shouldHaveCurrentLocationFirst() throws Exception {
+ View view = ((ListView) activity.findViewById(R.id.instruction_list_view)).getAdapter()
+ .getView(0, activity.findViewById(R.id.instruction_list_view),
+ getGenericViewGroup());
+
+ ImageView icon = (ImageView) view.findViewById(R.id.icon);
+ TextView instruction = (TextView) view.findViewById(R.id.simple_instruction);
+ TextView distance = (TextView) view.findViewById(R.id.distance);
+
+ assertThat(icon.getDrawable()).isEqualTo(activity.getDrawable(R.drawable.ic_locate));
+ assertThat(instruction.getText()).isEqualTo("Current Location");
+ assertThat(distance.getText()).isEqualTo("");
+ }
+
+ @Test
+ public void onDirectionListOpen_shouldHaveFirstInstructionFirst() throws Exception {
+ View view = ((ListView) activity.findViewById(R.id.instruction_list_view)).getAdapter()
+ .getView(1, activity.findViewById(R.id.instruction_list_view),
+ getGenericViewGroup());
+
+ ImageView icon = (ImageView) view.findViewById(R.id.icon);
+ TextView instruction = (TextView) view.findViewById(R.id.simple_instruction);
+ TextView distance = (TextView) view.findViewById(R.id.distance);
+
+ assertThat(icon.getDrawable()).isEqualTo(activity.getDrawable(R.drawable.ic_route_1));
+ assertThat(instruction.getText()).contains("Go north on Adalbertstraße.");
+ assertThat(distance.getText()).isEqualTo("0.2 mi");
+ }
+
+ @Test
+ public void onDirectionListOpen_shouldHaveLastInstructionLast() throws Exception {
+ int pos = ((ListView) activity.findViewById(R.id.instruction_list_view)).getAdapter()
+ .getCount() - 1;
+ View view = ((ListView) activity.findViewById(R.id.instruction_list_view)).getAdapter()
+ .getView(pos, activity.findViewById(R.id.instruction_list_view),
+ getGenericViewGroup());
+
+ ImageView icon = (ImageView) view.findViewById(R.id.icon);
+ TextView instruction = (TextView) view.findViewById(R.id.simple_instruction);
+ TextView distance = (TextView) view.findViewById(R.id.distance);
+
+ assertThat(icon.getDrawable()).isEqualTo(activity.getDrawable(R.drawable.ic_route_4));
+ assertThat(instruction.getText()).contains("You have arrived at your destination.");
+ assertThat(distance.getText()).isEqualTo("");
+ }
+
+ @NotNull
+ private ViewGroup getGenericViewGroup() {
+ return new ViewGroup(activity.getApplicationContext()) {
+ @Override
+ protected void onLayout(boolean changed, int l, int t, int r, int b) {
+
+ }
+ };
+ }
+}
diff --git a/app/src/test/java/com/mapzen/erasermap/view/MainActivityTest.java b/app/src/test/java/com/mapzen/erasermap/view/MainActivityTest.java
index 711ee66e..43736f62 100644
--- a/app/src/test/java/com/mapzen/erasermap/view/MainActivityTest.java
+++ b/app/src/test/java/com/mapzen/erasermap/view/MainActivityTest.java
@@ -27,15 +27,19 @@
import org.robolectric.Robolectric;
import org.robolectric.annotation.Config;
import org.robolectric.fakes.RoboMenu;
+import org.robolectric.shadows.ShadowActivity;
+import org.robolectric.shadows.ShadowIntent;
import org.robolectric.shadows.ShadowLocationManager;
import org.robolectric.util.ReflectionHelpers;
+import android.content.Intent;
import android.content.SharedPreferences;
import android.location.Location;
import android.location.LocationManager;
import android.preference.PreferenceManager;
import android.support.v7.widget.SearchView;
import android.view.Menu;
+import android.view.View;
import java.util.ArrayList;
import static android.content.Context.LOCATION_SERVICE;
@@ -379,6 +383,39 @@ public void onBack_shouldHideDrawnRoute() throws Exception {
assertThat(activity.getMapController().getMap().layers().contains(activity.getPath())).isFalse();
}
+ @Test
+ public void onRadioClick_shouldChangeType() throws Exception {
+ activity.showRoutePreview(getTestFeature());
+ activity.success(new Route(getFixture("valhalla_route")));
+ activity.findViewById(R.id.route_preview).findViewById(R.id.by_bike).performClick();
+ assertThat(activity.getType()).isEqualTo(Router.Type.BIKING);
+ activity.findViewById(R.id.route_preview).findViewById(R.id.by_foot).performClick();
+ assertThat(activity.getType()).isEqualTo(Router.Type.WALKING);
+ activity.findViewById(R.id.route_preview).findViewById(R.id.by_car).performClick();
+ assertThat(activity.getType()).isEqualTo(Router.Type.DRIVING);
+ }
+
+ @Test
+ public void onReverseClick_shouldSetReverse() throws Exception {
+ activity.showRoutePreview(getTestFeature());
+ activity.success(new Route(getFixture("valhalla_route")));
+ assertThat(activity.getReverse()).isFalse();
+ activity.findViewById(R.id.route_preview).findViewById(R.id.route_reverse).performClick();
+ assertThat(activity.getReverse()).isTrue();
+ }
+
+ @Test
+ public void onRoutingCircleClick_shouldOpenDirectionListActivity() throws Exception {
+ activity.showRoutePreview(getTestFeature());
+ activity.success(new Route(getFixture("valhalla_route")));
+ assertThat(activity.findViewById(R.id.instruction_list_view)).isNull();
+ activity.findViewById(R.id.routing_circle).performClick();
+ ShadowActivity shadowActivity = shadowOf(activity);
+ Intent startedIntent = shadowActivity.getNextStartedActivity();
+ ShadowIntent shadowIntent = shadowOf(startedIntent);
+ assertThat(shadowIntent.getComponent().getClassName()).contains("InstructionListActivity");
+ }
+
@Test
public void success_shouldAddMarkerLayer() throws Exception {
activity.showRoutePreview(getTestFeature());
diff --git a/app/src/test/java/com/mapzen/erasermap/view/RoutePreviewViewTest.java b/app/src/test/java/com/mapzen/erasermap/view/RoutePreviewViewTest.java
index f0ecc426..bba6d118 100644
--- a/app/src/test/java/com/mapzen/erasermap/view/RoutePreviewViewTest.java
+++ b/app/src/test/java/com/mapzen/erasermap/view/RoutePreviewViewTest.java
@@ -13,6 +13,7 @@
import org.junit.runner.RunWith;
import org.robolectric.annotation.Config;
+import android.view.View;
import android.widget.TextView;
import static com.mapzen.erasermap.dummy.TestHelper.getTestSimpleFeature;
diff --git a/circle.yml b/circle.yml
index 57f2960d..26a2f64e 100644
--- a/circle.yml
+++ b/circle.yml
@@ -8,6 +8,7 @@ machine:
M2_HOME: $HOME/.m2/apache-maven-3.1.1/
M2: $HOME/.m2/apache-maven-3.1.1/bin/
ANDROID_HOME: /usr/local/android-sdk-linux
+ JAVA_OPTS: "-Xms256m -Xmx512m"
dependencies:
diff --git a/gradle.properties b/gradle.properties
deleted file mode 100644
index 07194838..00000000
--- a/gradle.properties
+++ /dev/null
@@ -1 +0,0 @@
-org.gradle.jvmargs=-XX:MaxPermSize=1024m