【问题标题】:Change markers position base on Realtime Firebase lat and lang values根据实时 Firebase lat 和 lang 值更改标记位置
【发布时间】:2019-04-08 09:27:08
【问题描述】:

我试图用实时数据库的值来改变谷歌地图中标记的位置

我尝试 mMap.clear 到,但这不是正确的解决方案,因为如果我有 100 个标记并更改 1 个标记的位置,则 100 是清晰的并重新定位以更改 1 个标记

    myRef.addValueEventListener(new ValueEventListener() {
    @Override
    public void onDataChange(DataSnapshot dataSnapshot) {
      mMap.clear();           
 for (DataSnapshot ds : dataSnapshot.getChildren()) {

            Double lang = ds.child("lang").getValue(Double.class);
            Double lat = ds.child("lat").getValue(Double.class);
            save = new model(lat, lang);
            ll = new LatLng(save.getLat(), save.getLang());

            mCurrLocationMarker = mMap.addMarker(options
                    .position(ll));

        }

    }

    @Override
    public void onCancelled(DatabaseError databaseError) {

    }
});

我尝试更改标记的位置,但如果我不写 mMap.clear 并清除所有标记,实际结果会添加一个新标记,如果我写 mMap.clear 则添加它们以更改一个标记

【问题讨论】:

标签: java android firebase-realtime-database google-maps-markers


【解决方案1】:

不删除标记更新谷歌地图中的新位置()

1.最初创建的标记:

        Double lang = ds.child("lang").getValue(Double.class);
        Double lat = ds.child("lat").getValue(Double.class);
          LatLng latLng=new latLng(lang ,lat )
     // Creating a marker

      Marker marker= mMap.addMarker(new MarkerOptions()
                      .position(latLng)
                      .draggable(true));

2.获取更新位置时

   LatLng oldLocation, newLocaation;

float bearing = (float) bearingBetweenLocations(oldLocation, newLocaation);
rotateMarker(marker, bearing);

private double bearingBetweenLocations(LatLng perviousPos,LatLng newPos) {

    double PI = 3.14159;
    double lat1 = perviousPos.latitude * PI / 180;
    double long1 = perviousPos.longitude * PI / 180;
    double lat2 = newPos.latitude * PI / 180;
    double long2 = newPos.longitude * PI / 180;

    double dLon = (long2 - long1);

    double y = Math.sin(dLon) * Math.cos(lat2);
    double x = Math.cos(lat1) * Math.sin(lat2) - Math.sin(lat1)
            * Math.cos(lat2) * Math.cos(dLon);

    double brng = Math.atan2(y, x);

    brng = Math.toDegrees(brng);
    brng = (brng + 360) % 360;

    return brng;
}


   .To rotate marker using above bearing angle i have used this code

 Here isMarkerRotating is a boolean value. Add isMarkerRotating = false in OnCreate 
method

private void rotateMarker(final Marker marker, final float toRotation) {
    if(!isMarkerRotating) {
        final Handler handler = new Handler();
        final long start = SystemClock.uptimeMillis();
        final float startRotation = marker.getRotation();
        final long duration = 2000;

        final Interpolator interpolator = new LinearInterpolator();

        handler.post(new Runnable() {
            @Override
            public void run() {
                isMarkerRotating = true;

                long elapsed = SystemClock.uptimeMillis() - start;
                float t = interpolator.getInterpolation((float) elapsed / duration);

                float rot = t * toRotation + (1 - t) * startRotation;

                float bearing =  -rot > 180 ? rot / 2 : rot;

                marker.setRotation(bearing);

                if (t < 1.0) {
                    // Post again 16ms later.
                    handler.postDelayed(this, 16);
                } else {
                    isMarkerRotating = false;
                }
            }
        });
    }
}

【讨论】:

  • 你能把这个和我的代码合并吗?我看不懂,所以我在我的代码中接受它有问题
  • 收到新的 latlong 后,只需通过 previous 和 newlatlon float bearing = (float) BearingBetweenLocations(previous , newlatlon); rotateMarker(标记,轴承);
  • 最初你已经设置了标记,一旦你有了新的位置,只需按照上面的代码
  • 我做了什么但没有结果
  • 检查我更新的答案,你必须相应地改变
【解决方案2】:

我建议将标记存储在数组或 Hashmap throw 中,您可以随时更新,如下所示。

//            code for ploat and store marker
            HashMap<String, Marker> mPlotedMarker = new HashMap<>();
            if (mMap != null) {
                mMap.clear();
                ArrayList<MarkerDataModel> mDataList = new ArrayList<>();
                //With Hash map

                for (int positon = 0; positon < mDataList.size(); positon++) {
                    LatLng markerPosition = new LatLng(mDataList.get(positon).getMarkerLat(), mDataList.get(positon).getMarkerLong());
                    Marker marker = mMap.addMarker(new MarkerOptions().position(markerPosition)
                            .title(mDataList.get(positon).getMarkerTitle()));
                    mPlotedMarker.put(mDataList.get(positon).getMarkerId(), marker);
                }
            }

            //Now whenever you want to update
            String markerId="1"; // replace which you want to update
            if(mPlotedMarker.containsKey(markerId)){
                Marker marker=mPlotedMarker.get(markerId);
                if(marker!=null){
                    marker.setPosition(newPostion); //Specifie new position
                }
            }

【讨论】:

  • 谢谢,我现在试试看,并在您的评论中回复发生了什么
  • 好的,如果不行,我们会找到新的。
【解决方案3】:

您可以将标记对象存储为全局变量,并在位置更改时更改选定标记的位置。

喜欢,

if (mCurrLocationMarker == null)
    mCurrLocationMarker = mGoogleMap.addMarker(new MarkerOptions().icon(BitmapDescriptorFactory.fromResource(R.drawable.ic_pin_red)).position(location));
else
    mCurrLocationMarker.setPosition(location);

由于您有多个标记,您可以使用 ArrayList 或 LinkedHashMap 尝试相同的逻辑。

请检查此文件:https://filebin.net/m2vgvcms6g73kef2/TestFragment.java?t=e9g0tdki

希望对您有所帮助.. :)

【讨论】:

  • 我有很多标记,如果我只有一个标记并且我尝试了数组,那么这个解决方案是正确的>
  • 好的@mohamedgaber。让我检查一下我是否可以为您提供适当的细节来实现这一目标。
猜你喜欢
  • 2019-08-29
  • 2018-08-24
  • 1970-01-01
  • 2021-03-01
  • 2021-08-24
  • 1970-01-01
  • 2018-07-08
  • 2015-07-08
  • 1970-01-01
相关资源
最近更新 更多