【问题标题】:Android - Inserting multiple markers using push()Android - 使用 push() 插入多个标记
【发布时间】:2020-01-22 01:57:50
【问题描述】:

我可以在我的地图上插入多个标记。但是当我插入到我的 Firebase 数据库时,它只是插入的最后一个标记。我在想我必须使用某种列表或哈希图。

POJO 类:

public class FirebaseMarker {

  String address;
  String time;
  double latitude;
  double longitude;
  String routeId;

  public FirebaseMarker() {
  }

  public FirebaseMarker(String address, String time, double latitude, double longitude, String routerId) {
      this.address = address;
      this.time = time;
      this.latitude = latitude;
      this.longitude = longitude;
      this.routeId = routerId;
  }

  public String getRouterId() {
    return routeId;
  }

  public void setRouterId(String routerId) {
    this.routeId = routerId;
  }

  public String getAddress() {
    return address;
  }

  public void setAddress(String address) {
    this.address = address;
  }

  public String getTime() {
    return time;
  }

  public void setTime(String time) {
    this.time = time;
  }

  public double getLatitude() {
    return latitude;
  }

  public void setLatitude(double latitude) {
    this.latitude = latitude;
  }

  public double getLongitude() {
    return longitude;
  }

  public void setLongitude(double longitude) {
    this.longitude = longitude;
  }
}

标记创建:

List<Marker> markers;
markers = new ArrayList<>();

Marker marker =  mMap.addMarker(new MarkerOptions()
                 .position(latLng)
                 .title(address)
                 .snppet(time)
                 .icon(BitmapDescriptorFactory.defaultMarker(BitmapDescriptorFactory.HUE_RED)));

 markers.add(marker);

我是如何插入的:

//FirebaseMarker marker = new FirebaseMarker(address, time, latitude, longitude, routeId); 

 markerId = userRef.push().getKey();
userRef.child(sharedPreferences.getString("school",null)).child("markers").child(markerId).setValue(markers);

参数来自用户输入和地理编码器

【问题讨论】:

  • 您能分享将标记添加到地图的代码吗?我认为您需要在创建时将此标记添加到ListHashMap,然后在按下按钮时将该列表保存到数据库中。
  • 我已经编辑了我的帖子。我有一个列表,我在其中添加我的标记并将列表插入到我的数据库中。这行得通吗?

标签: java android firebase firebase-realtime-database


【解决方案1】:

看起来您有正确将标记保存到数据库的一般前提,但您需要先将每个标记存储在内存中,以便以后能够将它们保存到数据库中。

为此,您可以使用HashMap 来简化保存:

HashMap<String, Object> markers = new HashMap<>();

public void createMarker(String routeId, LatLng latLng, String address, String time) {    
    // Create a unique ID for this marker (but don't actually store it yet)
    String markerId = schoolReference.child("markers").push().getKey();

    // Add the marker to the HashMap
    FirebaseMarker marker = new FirebaseMarker(address, time, latLng.getLatitude(), latLng.getLongitude(), routeId);
    markers.put(markerId, marker);

    // Add an actual map marker to the map
    mMap.addMarker(new MarkerOptions()
        .position(latLng)
        .title(address)
        .snppet(time)
        .icon(BitmapDescriptorFactory.defaultMarker(BitmapDescriptorFactory.HUE_RED))
    );
}

在此示例中,当您创建标记时(在 createMarker() 方法中),您在实际将标记添加到地图之前执行 3 个附加操作:

  • 使用push()为这个标记生成一个唯一的ID(这不会联系数据库)
  • 创建一个以后可以使用的FirebaseMarker 实例
  • 将此唯一 ID 和 FirebaseMarker 对添加到 HashMap

然后,当您想将这些保存到数据库中时,只需将整个 HashMap 通过 performing a multi-location update using updateChildren() 推送到数据库中即可:

public void saveToDatabase() {
    // Do your thing to save the route

    // Save the markers to the database in one write operation
    schoolReference.child("markers").updateChildren(markers);
}

【讨论】:

  • 我刚刚注意到这与@AlexMamo 发布的修改后的答案相似,所以两者都应该有效。
  • 我会尝试这样做的。
  • 快速提问:当您编写 schoolReference 时,您的意思是作为 databaseReference 还是我保存在 sharedPreferences 中的实际学校变量?
  • 抱歉 schoolReference 是您的“某些学校名称”节点的数据库引用。
  • 这行得通。我在@AlexMamo 给出的答案中犯的错误是String markerId = schoolReference.child("markers").push().getKey(); 被放置在 onCreatedView 方法中。
【解决方案2】:

要解决这个问题,您需要为每次插入设置一个唯一标识符。因为 Firebase 数据库是一个 NoSQL 数据库并且结构为键和值对,所以每个节点都是一个 Map,这意味着在 Map 的情况下,它会用新值替换旧值。所以,你需要修改这行代码:

userRef.child(sharedPreferences.getString("school",null)).child("markers").child(markerId).setValue(marker);

userRef.push().child(sharedPreferences.getString("school",null)).child("markers").child(markerId).setValue(marker);

如您所见,我在您的userRef 之后添加了push() 方法。如果您需要将该按键放在另一个位置,只需将该方法移动到正确的位置即可。

编辑:要更新 Firebase 数据库中的节点,您需要使用 updateChildren() 方法而不是 setValue(),如下所示:

markerId = userRef.push().getKey();
Map<String, Object> map = new HashMap<>();
map.put(markerId, marker);
userRef.child(sharedPreferences.getString("school",null)).child("markers").updateChildren(map);

【讨论】:

  • 这不是我想要的。 markerId 孩子是 push()。我已经编辑了我的代码。问题是,当我的地图中有 3 个标记时。当我按下保存按钮时,只会保存最后一个标记。
  • markerId 孩子之前没有出现在您的代码中。所以请看我更新的答案。
  • 我不想更新儿童。如果我的地图中有 3 个标记,我想用 push() 插入三个新节点。
  • 抱歉以错误的方式实现您的代码。我的错。您的代码运行良好
  • 很高兴听到这个消息。如果您认为我的回答对您有所帮助,请考虑采纳。谢谢!
【解决方案3】:
FirebaseMarker marker = new FirebaseMarker(address, time, latitude, 
longitude, routeId); 

DatabaseReference userRef=FirebaseDatabase.getInstance().getReference().child("sharedPreferences.getString("school",null)").child("markers").push().setValue(marker);

【讨论】:

  • 这会在根节点添加一个节点,而不是在学校节点内。但它仍然只添加了一个节点
  • 我试过了。这没用。我用我的数据库图片编辑了我的帖子。只添加了一个 push() id。
  • "Some School Name" 孩子和 "sharedPreferences.getString("school",null) 孩子是一回事
  • @JDoe 好的,我更新了它,这应该为每个标记生成一个随机 id
  • 还是一样
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2012-12-25
  • 2012-09-26
  • 1970-01-01
  • 2010-11-21
相关资源
最近更新 更多