主要活动
public class MainActivity extends AppCompatActivity {
private RecyclerView mRecyclerView;
private EmployeeRecyclerViewAdapter mRecyclerViewAdapter;
private List<Employee> employeeList;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
employeeList = DummyEmployeeDataUtils.getEmployeeList();
mRecyclerViewAdapter = new EmployeeRecyclerViewAdapter(
employeeList);
mRecyclerView = (RecyclerView) findViewById(R.id.recycler_view);
mRecyclerView.setLayoutManager(new LinearLayoutManager(this));
mRecyclerView.setAdapter(mRecyclerViewAdapter);
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.sort_menu, menu);
return super.onCreateOptionsMenu(menu);
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
switch (item.getItemId()) {
case R.id.age_above_employees:
mRecyclerViewAdapter.updateEmployeeListItems(DummyEmployeeDataUtils.getEmployessWithAgeAbove50());
return true;
}
return super.onOptionsItemSelected(item);
}
}
根据年龄创建虚拟员工列表
public class DummyEmployeeDataUtils {
public static List<Employee> getEmployessWithAgeAbove50() {
final List<Employee> employeeList = getEmployeeList();
final List<Employee> filteredEmployees = new ArrayList<>();
for (int i = 0; i < employeeList.size(); i++) {
if (employeeList.get(i).getAge() > 50)
filteredEmployees.add(employeeList.get(i));
}
return filteredEmployees;
}
public static List<Employee> getEmployeeList() {
final List<Employee> employees = new ArrayList<>();
employees.add(new Employee(1, "Employee 1", "Developer", 12));
employees.add(new Employee(2, "Employee 2", "Tester", 52));
employees.add(new Employee(3, "Employee 3", "Support", 72));
employees.add(new Employee(4, "Employee 4", "Sales Manager", 11));
employees.add(new Employee(5, "Employee 5", "Manager", 64));
employees.add(new Employee(6, "Employee 6", "Team lead", 99));
employees.add(new Employee(7, "Employee 7", "Scrum Master", 89));
employees.add(new Employee(8, "Employee 8", "Sr. Tester", 23));
employees.add(new Employee(9, "Employee 9", "Sr. Developer", 21));
return employees;
}
}
这是我们的适配器
public class EmployeeRecyclerViewAdapter extends
RecyclerView.Adapter<EmployeeRecyclerViewAdapter
.ViewHolder> {
private List<Employee> mEmployees = new ArrayList<>();
public EmployeeRecyclerViewAdapter(List<Employee> employeeList) {
this.mEmployees.addAll(employeeList);
}
@Override
public ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
final LayoutInflater inflater = LayoutInflater.from(parent.getContext());
final View view = inflater.inflate(R.layout.list_item, parent, false);
return new ViewHolder(view);
}
@Override
public void onBindViewHolder(ViewHolder holder, int position) {
final Employee employee = mEmployees.get(position);
holder.bindView(employee);
}
public void updateEmployeeListItems(List<Employee> employees) {
final EmployeeDiffCallback diffCallback = new EmployeeDiffCallback(this.mEmployees, employees);
final DiffUtil.DiffResult diffResult = DiffUtil.calculateDiff(diffCallback);
this.mEmployees.clear();
this.mEmployees.addAll(employees);
diffResult.dispatchUpdatesTo(this);
}
@Override
public int getItemCount() {
return mEmployees.size();
}
public static class ViewHolder extends RecyclerView.ViewHolder {
private final TextView role;
private final TextView name;
private final TextView age;
public ViewHolder(View itemView) {
super(itemView);
name = (TextView) itemView.findViewById(R.id.employee_name);
role = (TextView) itemView.findViewById(R.id.employee_role);
age = (TextView) itemView.findViewById(R.id.employee_age);
}
void bindView(Employee employee) {
name.setText(employee.getName());
role.setText(employee.getRole());
age.setText("Age ".concat(employee.getAge()+""));
}
}
}
这是 DiffUtil 适配器
public class EmployeeDiffCallback extends DiffUtil.Callback {
private final List<Employee> mOldEmployeeList;
private final List<Employee> mNewEmployeeList;
public EmployeeDiffCallback(List<Employee> oldEmployeeList, List<Employee> newEmployeeList) {
this.mOldEmployeeList = oldEmployeeList;
this.mNewEmployeeList = newEmployeeList;
}
@Override
public int getOldListSize() {
return mOldEmployeeList.size();
}
@Override
public int getNewListSize() {
return mNewEmployeeList.size();
}
@Override
public boolean areItemsTheSame(int oldItemPosition, int newItemPosition) {
return mOldEmployeeList.get(oldItemPosition).getId() == mNewEmployeeList.get(
newItemPosition).getId();
}
@Override
public boolean areContentsTheSame(int oldItemPosition, int newItemPosition) {
final Employee oldEmployee = mOldEmployeeList.get(oldItemPosition);
final Employee newEmployee = mNewEmployeeList.get(newItemPosition);
return oldEmployee.getName().equals(newEmployee.getName());
}
@Nullable
@Override
public Object getChangePayload(int oldItemPosition, int newItemPosition) {
// Implement method if you're going to use ItemAnimator
return super.getChangePayload(oldItemPosition, newItemPosition);
}
}
更新的答案
编辑 Manoj 的答案。由作者更新以供将来参考
在没有 ViewModels 的 RecyclerView 的情况下,上述答案可以正常工作。一旦 viewmodel 出现并且 RecyclerView 监听 VM 中的变化,逻辑应该是用 ViewModel 本身的新结果更新过滤列表。这样回收站视图就会一直监听更新并保持数据更新。
在这种情况下,Diff Utils可能不会派上用场。相当有效的方法(因为问题在 Kotlin 中)是使用过滤器
我发现过滤器比 Diff Util 实现简单得多。
为了将来参考,具有多个谓词的示例过滤方法如下
mViewModelObject 是 View Model 对象的实例
val valueOne = mViewModelObject.criteriaOne.value
val valueTwo = mViewModelObject.criteriaTwo.value
val newList = originalList.filter {
it.listVariableABC == valueOne
&&
it.listVariablePQR == valueTwo
}
根据多个条件创建新列表后,在 ViewModel 中更新相同的列表。这样 Recycler View 将获得更新的列表。