如何使用 viewModel 中的观察者方法解决 "anonymous class derived from observer" 错误
How do I solve "anonymous class derived from observer" error with observer method in viewModel
我已经在 MainActivity()
中成功使用了如下所示的观察者方法:
public void inputNameTest(String inputName) {
myViewModel.inputNameTesting(inputName).observe( this, new Observer<List<MyRoomEntity>>() {
@Override
public void onChanged(@Nullable List<MyRoomEntity> myRoomEntities) {
//Sets data in RecyclerView
myAdapter.setList( myRoomEntities );
}
} );
}
这会将用户输入的数据设置为 Room
查询并在 RecyclerView
中显示查询。但是,我想将该功能移至 ViewModel
,以防止 View
混乱。
在 ViewModel
中,我在 new Observer<List<MyRoomEntity>>()
上有一条红色下划线,上面写着 anonymous class must either be declared abstract or implement abstract method
如果我将 Observer
更改为 new android.arch.lifecycle.Observer<List<MyRoomEntity>>()
(如 Android-Studio
所建议),红色下划线将消失。
我还需要传递一个 owner
参数而不是 this
。我通过从 MainActivity()
传递 this
来管理这个
myViewModel.setOwner( this );
给我的 ViewModel
public void setOwner(LifecycleOwner owner) {
this.mOwner = owner;
}
完成后,ViewModel
中的 Observer
方法如下所示:
public void getUserInputName(String inputName) {
repository.getUserInputName(inputName).observe( mOwner, new android.arch.lifecycle.Observer<List<MyRoomEntity>>() {
@Override
public void onChanged(@Nullable List<MyRoomEntity> myRoomEntities) {
Log.d("TAG", "OBSERVED INPUT NAME");
if(myRoomEntities != null) {
for(MyRoomEntity item: myRoomEntities) {
Log.d("TAG ROOM ", "Input Name: " + item.toString());
}
}
myAdapter.setList( myRoomEntities );
}
} );
}
没有产生错误,但由于某种原因,RecyclerView
中没有显示任何内容。我确实从 Observer
方法得到了正确的 Log
输出:
Input Name: MyRoomEntity{id=2, name='Joe', date='1/3/2015', from='12.30', until='13:00'}
因此,如果我在 EditText
框中输入 "Joe" 并按下按钮,RecyclerView
中什么也没有显示,但我确实得到了正确的 Log
。如果我在 MainActivity()
中保留 Observer
方法,我会得到正确的 Log
和 RecyclerView
输出。
不知道出了什么问题,但一定是我用 Observer
方法所做的两个更改引起的。
通过此实现,您将 google 的所有工作都扔到垃圾桶中,因为您所做的是提供对 ViewModel class 的 MainActivity 引用,而使用 MVVM 的要点是避免此问题在您的 activity 或片段被破坏的情况下是安全的,并且能够在屏幕评级的情况下保存数据状态。
所以不要在 ViewModel class 中移动观察者代码,它不是 "cluttering up" activity。
我已经在 MainActivity()
中成功使用了如下所示的观察者方法:
public void inputNameTest(String inputName) {
myViewModel.inputNameTesting(inputName).observe( this, new Observer<List<MyRoomEntity>>() {
@Override
public void onChanged(@Nullable List<MyRoomEntity> myRoomEntities) {
//Sets data in RecyclerView
myAdapter.setList( myRoomEntities );
}
} );
}
这会将用户输入的数据设置为 Room
查询并在 RecyclerView
中显示查询。但是,我想将该功能移至 ViewModel
,以防止 View
混乱。
在 ViewModel
中,我在 new Observer<List<MyRoomEntity>>()
上有一条红色下划线,上面写着 anonymous class must either be declared abstract or implement abstract method
如果我将 Observer
更改为 new android.arch.lifecycle.Observer<List<MyRoomEntity>>()
(如 Android-Studio
所建议),红色下划线将消失。
我还需要传递一个 owner
参数而不是 this
。我通过从 MainActivity()
this
来管理这个
myViewModel.setOwner( this );
给我的 ViewModel
public void setOwner(LifecycleOwner owner) {
this.mOwner = owner;
}
完成后,ViewModel
中的 Observer
方法如下所示:
public void getUserInputName(String inputName) {
repository.getUserInputName(inputName).observe( mOwner, new android.arch.lifecycle.Observer<List<MyRoomEntity>>() {
@Override
public void onChanged(@Nullable List<MyRoomEntity> myRoomEntities) {
Log.d("TAG", "OBSERVED INPUT NAME");
if(myRoomEntities != null) {
for(MyRoomEntity item: myRoomEntities) {
Log.d("TAG ROOM ", "Input Name: " + item.toString());
}
}
myAdapter.setList( myRoomEntities );
}
} );
}
没有产生错误,但由于某种原因,RecyclerView
中没有显示任何内容。我确实从 Observer
方法得到了正确的 Log
输出:
Input Name: MyRoomEntity{id=2, name='Joe', date='1/3/2015', from='12.30', until='13:00'}
因此,如果我在 EditText
框中输入 "Joe" 并按下按钮,RecyclerView
中什么也没有显示,但我确实得到了正确的 Log
。如果我在 MainActivity()
中保留 Observer
方法,我会得到正确的 Log
和 RecyclerView
输出。
不知道出了什么问题,但一定是我用 Observer
方法所做的两个更改引起的。
通过此实现,您将 google 的所有工作都扔到垃圾桶中,因为您所做的是提供对 ViewModel class 的 MainActivity 引用,而使用 MVVM 的要点是避免此问题在您的 activity 或片段被破坏的情况下是安全的,并且能够在屏幕评级的情况下保存数据状态。 所以不要在 ViewModel class 中移动观察者代码,它不是 "cluttering up" activity。