2017-04-20 125 views
0

我正在为会员出席应记录的俱乐部开发应用程序。我无法在列表视图中正确获取它。正确获取Firebase数据

这里是数据库的一部分:

enter image description here

可能有不止一个运动参加像空手道或游泳某一天。我想在列表视图中获取该成员的出席人数。我会尽量在一天之后对其进行分区,但现在我需要正确地获取数据。 这里是我做出的模型:

public class MemberAttendance { 

private String day; 
private HashMap<String, Object> attendedSport; 


public MemberAttendance() { 

} 

public MemberAttendance(String day, HashMap<String, Object> attendedSport) { 

    this.day = day; 
    this.attendedSport = attendedSport; 

} 

public String getDay() { 
    return day; 
} 

public void setDay(String day) { 
    this.day = day; 
} 

public HashMap<String, Object> getAttendedSport() { 
    return attendedSport; 
} 

public void setAttendedSport(HashMap<String, Object> attendedSport) { 
    this.attendedSport = attendedSport; 
} 

}

这里是适配器:

public class MemberAttendanceAdapter extends FirebaseListAdapter<MemberAttendance> { 

public MemberAttendanceAdapter(Activity activity, Class<MemberAttendance> modelClass, int modelLayout, Query ref) { 
    super(activity, modelClass, modelLayout, ref); 
} 

@Override 
protected void populateView(View view, MemberAttendance memberAttendance, int i) { 

    // Get values from firebase database 
    String day = memberAttendance.getDay(); 

    HashMap<String, Object> hashMap = memberAttendance.getAttendedSport(); 
    String sport = (String) hashMap.get("attended"); 
    String date = (String) hashMap.get("timestamp"); 

    // Create views and assign values 
    TextView dayTxtView = (TextView) view.findViewById(R.id.dayTxtView); 
    dayTxtView.setText(day); 

    TextView sportTxtView = (TextView) view.findViewById(R.id.sportTxtView); 
    sportTxtView.setText(sport); 

    TextView dateTxtView = (TextView) view.findViewById(R.id.dateTxtView); 
    dateTxtView.setText(date); 

} 

}

在这里,我怎么尝试设置适配器:

 final FirebaseDatabase database = FirebaseDatabase.getInstance(); 

    final DatabaseReference attendanceRef = database.getReference() 
      .child(Constants.MEMBERS_NODE).child(userID).child("attendance"); 

    attendanceAdapter = new MemberAttendanceAdapter(getActivity(), MemberAttendance.class, 
      R.layout.attendance_list_item, attendanceRef); 

    attendanceListView.setAdapter(attendanceAdapter); 

到目前为止,没有工作,并就使用HashMap.get(..)对象引用空指针异常

String sport = (String) hashMap.get("attended"); 

任何帮助表示赞赏。

+0

的getAttendedSport HashMap试图获得一个名为“attendSport”的节点,但没有名为“attendSport”的节点,而只是看起来像一个随机ID。 – Linxy

回答

1

您可能要调整你的NoSQL数据库是这样的:

member 
---memberID 
------attendance 
---------attendance ID 
------------attended 
------------timestamp 
------------date 

例如:

member 
---member1 
------attendance 
---------attendance1 
------------soccer 
------------14938372834 
------------14-04-2017 
---------attendance2 
------------swimming 
------------14938374323 
------------14-04-2017 

你并不需要存储的日期,因为使用可以使用时间戳来创建Java中包含该信息的日期对象

Date date = new Date(timestamp); 

使用此结构y OU需要你的POJO改成这样:

public class MemberAttendance { 

    private String attended; 
    private long timestamp; 


    public MemberAttendance() { 

    } 

    public MemberAttendance(String attended, long timestamp) { 

     this.attended = attended; 
     this.timestamp = timestamp; 

    } 

    public String getAttended() { 
     return attended; 
    } 

    public void setAttended(String attended) { 
     this.attended = attended; 
    } 

    public long getTimestamp() { 
     return timestamp; 
    } 

    public void setTimestamp(long timestamp) { 
     this.attendedSport = attendedSport; 
    } 
} 

然后你可以与适配器以下更改使用相同的火力地堡查询:

public class MemberAttendanceAdapter extends FirebaseListAdapter<MemberAttendance> { 

    public MemberAttendanceAdapter(Activity activity, Class<MemberAttendance> modelClass, int modelLayout, Query ref) { 
     super(activity, modelClass, modelLayout, ref); 
    } 

    @Override 
    protected void populateView(View view, MemberAttendance memberAttendance, int i) { 

     String sport = memberAttendace.getAttended(); 
     Date date = new Date(memberAttendance.getTimestamp()); 

     // Create views and assign values 
     TextView dayTxtView = (TextView) view.findViewById(R.id.dayTxtView); 
     dayTxtView.setText(new SimpleDateFormat("dd-MM-yyyy").format(date);); 

     TextView sportTxtView = (TextView) view.findViewById(R.id.sportTxtView); 
     sportTxtView.setText(sport); 

     //I think you want to show the time here, not the date 
     TextView dateTxtView = (TextView) view.findViewById(R.id.dateTxtView); 
     dateTxtView.setText(new SimpleDateFormat("HH:mm:ss").format(date)); 

    } 
} 

编辑:关于你的评论在按日期查询出勤,检查I在上面的结构中做出的编辑,然后使用火力地堡查询像

ref.child("members") 
    .child(<memberIdHere>) 
    .child("attendance") 
    .orderByChild("date") 
    .equalTo(<yourDateHere>); 
+0

这是一个正确的方法,谢谢。你能想出一种方法,以便我可以将属于同一天的参加者组合到单个列表项目中吗? – fullMoon

+0

如果您想按日期查询它们,则可以使用Firebase查询,其日期等于特定日期。我已经编辑了我的答案。我修改了结构。 –

1

而不是使用HashMap的我会建议创建像AttendedSport另一个对象变量中MemberAttendance然后Firebase将数据映射为使用HashMappopulateView出来,你可以得到一个像

memberAttendance.getAttendedSport().getSport()memberAttendance.getAttendedSport().getTimeStamp()

数据我不能保证它能解决你的问题,但我认为它不太容易出错。