¿Cómo animar una polilínea en android?

2 minutos de lectura

Avatar de usuario de Sandip
Sandip

¿Cómo dibujar una polilínea animada en el mapa de Google de Android? Ya había implementado la biblioteca de senderos para la animación. Quiero crear una polilínea como en Lyft en Android.

Captura de pantalla

  • Esto podría ayudar a stackoverflow.com/questions/17425499/…

    – Ismail

    9 de enero de 2020 a las 4:44

Cree dos listas de arreglos de latlng y luego cree una polilínea con el método dado

private fun createPolyLine() {

        val lineOptions = PolylineOptions()
        lineOptions.width(6f)
        lineOptions.color(ContextCompat.getColor(act!!, R.color.colorPrimary))
        lineOptions.startCap(SquareCap())
        lineOptions.endCap(SquareCap())
        lineOptions.jointType(JointType.ROUND)
        blackPolyLine = googleMap!!.addPolyline(lineOptions)

        val greyOptions = PolylineOptions()
        greyOptions.width(6f)
        greyOptions.color(Color.GRAY)
        greyOptions.startCap(SquareCap())
        greyOptions.endCap(SquareCap())
        greyOptions.jointType(JointType.ROUND)
        greyPolyLine = googleMap!!.addPolyline(greyOptions)

        animatePolyLine()
    }

después de eso, cree una animación de estas polilíneas

private fun animatePolyLine() {
        val animator = ValueAnimator.ofInt(0, 100)
        animator.duration = 1500
        animator.interpolator = LinearInterpolator()
        animator.addUpdateListener { animator ->
            val latLngList =
                blackPolyLine!!.points
            val initialPointSize = latLngList.size
            val animatedValue = animator.animatedValue as Int
            val newPoints = animatedValue * decodedPath.size / 100
            if (initialPointSize < newPoints) {
                latLngList.addAll(decodedPath.subList(initialPointSize, newPoints))
                blackPolyLine!!.points = latLngList
            }
        }
        animator.addListener(polyLineAnimationListener)
        animator.start()
    }

private var polyLineAnimationListener: Animator.AnimatorListener =
        object : Animator.AnimatorListener {
            override fun onAnimationStart(animator: Animator) {}
            override fun onAnimationEnd(animator: Animator) {
                val blackLatLng: MutableList<LatLng> = blackPolyLine!!.points
                val greyLatLng: MutableList<LatLng> = greyPolyLine!!.points
                greyLatLng.clear()
                greyLatLng.addAll(blackLatLng)
                blackLatLng.clear()
                blackPolyLine!!.points = blackLatLng
                greyPolyLine!!.points = greyLatLng
                blackPolyLine!!.zIndex = 2f
                animator.start()
            }

            override fun onAnimationCancel(animator: Animator) {}
            override fun onAnimationRepeat(animator: Animator) {}
        }

  • está funcionando, pero quiero eliminar el color de la ruta anterior cuando aumenta el progreso. ¿Hay alguna solución?

    – Sandip

    9 de enero de 2020 a las 5:39

  • @Sandip, entonces puede eliminar la ruta anterior y crear una nueva

    – Divyanshu

    9 de enero de 2020 a las 6:06

  • para eliminar la parte del círculo rojo, elimine latlng de su lista

    – Divyanshu

    9 de enero de 2020 a las 6:16

  • ¿Podría mostrar cómo se puede hacer usando Java? Gracias

    – Arjun

    11 de diciembre de 2020 a las 10:18

  • @Sandip, para eliminar la ruta anterior en Java: if (animator!= null) { animator.removeAllListeners(); animador.cancel(); }

    – Ashwin H.

    16 de julio de 2022 a las 4:15

 private fun plotPolyline() {

    var polyline = "encoded_pyline"
 
    var list = PolyUtil.decode(polyline)
  

    val blackOptions = PolylineOptions()
    blackOptions.startCap(RoundCap())
    blackOptions.endCap(RoundCap())
    blackOptions.width(10.0f)
    blackOptions.color(Color.BLACK)
    blackOptions.zIndex(2.0f)

    var blackPolyline = googleMap.addPolyline(blackOptions)


    val greyOptions = PolylineOptions()
    greyOptions.startCap(RoundCap())
    greyOptions.endCap(RoundCap())
    greyOptions.width(8.0f)
    greyOptions.addAll(list)
    greyOptions.color(ContextCompat.getColor(this, R.color.gray_dark))
    var greyPolyline = googleMap.addPolyline(greyOptions)

    val valueAnimator = ValueAnimator.ofInt(0, 100)
    valueAnimator.duration = 1500
    valueAnimator.interpolator = LinearInterpolator()
    valueAnimator.addUpdateListener {
        val points: List<LatLng> = greyPolyline.getPoints()
        val percentValue = valueAnimator.animatedValue as Int
        val size = points.size
        val newPoints = (size * (percentValue / 100.0f)).toInt()
       
        val p = points.subList(0, newPoints)
        blackPolyline.points = p


    }

    valueAnimator.addListener(object: Animator.AnimatorListener{
        override fun onAnimationStart(animation: Animator?) {

        }

        override fun onAnimationEnd(animation: Animator?) {
            animation?.start()
        }

        override fun onAnimationCancel(animation: Animator?) {
        }

        override fun onAnimationRepeat(animation: Animator?) {
        }
    })

    googleMap.animateCamera(CameraUpdateFactory.newLatLngZoom(list.get(0), 15.0f))
    valueAnimator.start()
}

¿Ha sido útil esta solución?