英文:
LiveData observer not getting triggered
问题
我正在尝试从Firebase获取数据并显示它,但观察者未正常工作。我正在使用MVVM架构,因此我有一个 MainActivityViewModel
,在其中从Firestore获取数据(一个 FirestoreMenu
),然后在 MainActivity
中提供和观察它。但是,观察者从未触发。我按照一些解释LiveData如何工作的教程,但我不知道我做错了什么。有人能帮我找出问题吗?
MainActivity
public class MainActivity extends AppCompatActivity {
private FirebaseAuth mAuth;
private MainActivityViewModel mainActivityViewModel;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mAuth = FirebaseAuth.getInstance();
FirebaseUser currentUser = mAuth.getCurrentUser();
RecyclerView recyclerView = findViewById(R.id.recycle_view);
recyclerView.setLayoutManager(new LinearLayoutManager(this));
recyclerView.setHasFixedSize(true);
final MenuAdapter adapter = new MenuAdapter();
recyclerView.setAdapter(adapter);
mainActivityViewModel = new ViewModelProvider(this).get(MainActivityViewModel.class);
mainActivityViewModel.getMenus().observe(this, new Observer<List<FirestoreMenu>>() {
@Override
public void onChanged(List<FirestoreMenu> firestoreMenus) {
// 更新RecyclerView
adapter.setFirestoreMenus(firestoreMenus);
}
});
// ... 其他部分
}
@Override
public void onStart() {
super.onStart();
FirebaseUser currentUser = mAuth.getCurrentUser();
signInAnonymously();
}
private void signInAnonymously() {
// 实现匿名登录的代码
}
}
MainActivityViewModel
public class MainActivityViewModel extends ViewModel {
private MutableLiveData<List<FirestoreMenu>> mMenus;
public MutableLiveData<List<FirestoreMenu>> getMenus() {
if (mMenus == null) {
mMenus = new MutableLiveData<>();
}
return mMenus;
}
public void setMenusCollection(String location) {
FirebaseFirestore db = FirebaseFirestore.getInstance();
CollectionReference menusRef = FirebaseFirestore.getInstance().collection("locations/" + location + "/menus");
menusRef.get().addOnSuccessListener(new OnSuccessListener<QuerySnapshot>() {
@Override
public void onSuccess(QuerySnapshot queryDocumentSnapshots) {
ArrayList<FirestoreMenu> dataSet = new ArrayList<>();
for (DocumentSnapshot document : queryDocumentSnapshots.getDocuments()) {
FirestoreMenu menu = document.toObject(FirestoreMenu.class);
dataSet.add(menu);
}
mMenus.setValue(dataSet);
}
});
}
}
MenuAdapter
public class MenuAdapter extends RecyclerView.Adapter<MenuAdapter.MenuHolder> {
private List<FirestoreMenu> firestoreMenus = new ArrayList<>();
@NonNull
@Override
public MenuHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
View itemView = LayoutInflater.from(parent.getContext())
.inflate(R.layout.menu_item, parent, false);
return new MenuHolder(itemView);
}
@Override
public void onBindViewHolder(@NonNull MenuHolder holder, int position) {
FirestoreMenu currentMenu = firestoreMenus.get(position);
holder.textViewTitle.setText(currentMenu.getName());
holder.textViewDescritpion.setText(currentMenu.getId());
holder.textViewDescritpion.setText(currentMenu.getImage());
}
@Override
public int getItemCount() {
return firestoreMenus.size();
}
public void setFirestoreMenus(List<FirestoreMenu> menus) {
this.firestoreMenus = menus;
notifyDataSetChanged();
}
class MenuHolder extends RecyclerView.ViewHolder {
private TextView textViewTitle;
private TextView textViewDescritpion;
private TextView textViewPriority;
public MenuHolder(View itemView) {
super(itemView);
textViewTitle = itemView.findViewById(R.id.text_view_title);
textViewDescritpion = itemView.findViewById(R.id.text_view_description);
textViewPriority = itemView.findViewById(R.id.text_view_priority);
}
}
}
英文:
I am trying to take data from the firebase and display it but the observer is not working. I am using a mvvm architecture , so I have a MainActivityViewModel
where the data (a FirestoreMenu
) is taken from the firestore and then it is provided and observed in the MainActivity
. However, the observer is never triggered. I followed some tutorials that explain how LiveData works, but I have no idea what I am doing wrong. Can someone help me figure the problem out?
MainActivity
public class MainActivity extends AppCompatActivity {
private FirebaseAuth mAuth;
private MainActivityViewModel mainActivityViewModel;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mAuth = FirebaseAuth.getInstance();
FirebaseUser currentUser = mAuth.getCurrentUser();
RecyclerView recyclerView = findViewById(R.id.recycle_view);
recyclerView.setLayoutManager(new LinearLayoutManager(this));
recyclerView.setHasFixedSize(true);
final MenuAdapter adapter = new MenuAdapter();
recyclerView.setAdapter(adapter);
mainActivityViewModel = new ViewModelProvider(this).get(MainActivityViewModel.class);
mainActivityViewModel.getMenus().observe(this, new Observer<List<FirestoreMenu>>() {
@Override
public void onChanged(List<FirestoreMenu> firestoreMenus) {
//update recycle view
adapter.setFirestoreMenus(firestoreMenus);
}
});
/* I also have tried this approach
final MainActivityViewModel mMainActivityViewModel = new ViewModelProvider(this).get(MainActivityViewModel.class);
LiveData<List<FirestoreMenu>> mMenusList = mMainActivityViewModel.getMenus() ;
final MenuListAdapter mAdapter = new MenuListAdapter(this, R.layout.adaptive_view_layout, mMainActivityViewModel.getMenus().getValue());
mMenusList.observe(this, new Observer<List<FirestoreMenu>>() {
@Override
public void onChanged(List<FirestoreMenu> firestoreMenus) {
mMainActivityViewModel.setMenusCollection("XmyTebpsvEyeBYBp2TUB");
menusListView.setAdapter(mAdapter);
}
});
*/
}
@Override
public void onStart() {
super.onStart();
FirebaseUser currentUser = mAuth.getCurrentUser();
signInAnonymously();
}
private void signInAnonymously() {
...
}
}
MainActivityViewModel
public class MainActivityViewModel extends ViewModel {
private MutableLiveData<List<FirestoreMenu>> mMenus;
public MutableLiveData<List<FirestoreMenu>> getMenus(){
if (mMenus == null){
mMenus = new MutableLiveData<>();
}
return mMenus;
}
public void setMenusCollection(String location){
FirebaseFirestore db = FirebaseFirestore.getInstance();
CollectionReference menusRef = FirebaseFirestore.getInstance().collection("locations/"+location+"/menus");
menusRef.get().addOnSuccessListener(new OnSuccessListener<QuerySnapshot>() {
@Override
public void onSuccess(QuerySnapshot queryDocumentSnapshots) {
ArrayList<FirestoreMenu> dataSet = new ArrayList<>();
for (DocumentSnapshot document : queryDocumentSnapshots.getDocuments()) {
FirestoreMenu menu = document.toObject(FirestoreMenu.class);
dataSet.add(menu);
}
mMenus.setValue(dataSet);
}
});
}
}
MenuAdapter
public class MenuAdapter extends RecyclerView.Adapter<MenuAdapter.MenuHolder> {
private List<FirestoreMenu> firestoreMenus= new ArrayList<>();
@NonNull
@Override
public MenuHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
View itemView = LayoutInflater.from(parent.getContext())
.inflate(R.layout.menu_item,parent,false);
return new MenuHolder(itemView);
}
@Override
public void onBindViewHolder(@NonNull MenuHolder holder, int position) {
FirestoreMenu currentMenu = firestoreMenus.get(position);
holder.textViewTitle.setText(currentMenu.getName());
holder.textViewDescritpion.setText(currentMenu.getId());
holder.textViewDescritpion.setText(currentMenu.getImage());
}
@Override
public int getItemCount() {
return firestoreMenus.size();
}
public void setFirestoreMenus (List<FirestoreMenu> menus){
this.firestoreMenus = menus;
notifyDataSetChanged();
}
class MenuHolder extends RecyclerView.ViewHolder{
private TextView textViewTitle;
private TextView textViewDescritpion;
private TextView textViewPriority;
public MenuHolder(View itemView){
super(itemView);
textViewTitle = itemView.findViewById(R.id.text_view_title);
textViewDescritpion = itemView.findViewById(R.id.text_view_description);
textViewPriority = itemView.findViewById(R.id.text_view_priority);
}
}
}
答案1
得分: 1
问题不在于观察者,我认为你的 Firebase 引用存在问题。
这就是为什么它没有进入你的成功回调中的 .collection("locations/" + location + "/menus")
--> 检查这个引用,你应该使用 .document
导航到特定文档。
英文:
The problem is not in the observer, I think you have a problem with your Firebase reference.
That's why it does not enter in your onSuccess .collection("locations/"+location+"/menus")
--> check this reference you should use .document
to navigate to a certain document.
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论