Android 单击按钮时回收站视图未更新
Android recycler view not updating when I click button
我有这个片段,我在其中编辑文本、一个按钮和一个回收站视图。当我第一次单击该按钮时,它具有预期的行为,但如果我更改编辑文本内容并再次单击该按钮,它不会更新我的回收站视图。我究竟做错了什么?因为我在重复这个过程
每次点击 Api 调用
片段
public class SearchFragment extends Fragment implements View.OnClickListener {
private RestaurantAdapter mAdapter;
private RecyclerView mRecyclerView;
protected static List<Restaurant_> restaurantsList;
private Context context;
private static OnRestaurantClickedListener listener;
private FirebaseAuth mAuth;
private EditText keyword;
private FusedLocationProviderClient mFusedLocationClient;
public SearchFragment() {
}
public static OnRestaurantClickedListener getListener() {
return listener;
}
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
context = getContext();
mAuth = FirebaseAuth.getInstance();
restaurantsList = new ArrayList<>();
mAdapter = new RestaurantAdapter(context, restaurantsList, getActivity());
}
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View mContentView = inflater.inflate(R.layout.fragment_search, container, false);
mRecyclerView = mContentView.findViewById(R.id.recycler_view);
mRecyclerView.setLayoutManager(new LinearLayoutManager(mContentView.getContext()));
mRecyclerView.setAdapter(mAdapter);
keyword = mContentView.findViewById(R.id.keyword);
keyword.setOnEditorActionListener(new TextView.OnEditorActionListener() {
@Override
public boolean onEditorAction(TextView textView, int actionId, KeyEvent keyEvent) {
if ((keyEvent != null && keyEvent.getKeyCode() == KeyEvent.KEYCODE_ENTER) || (actionId == EditorInfo.IME_ACTION_SEARCH))
getRestaurants();
return false;
}
});
ImageButton searchButton = mContentView.findViewById(R.id.search);
searchButton.setOnClickListener(this);
return mContentView;
}
@Override
public void onResume() {
super.onResume();
}
@Override
public void onAttach(Activity activity) {
super.onAttach(activity);
try {
listener = (OnRestaurantClickedListener) activity;
} catch (ClassCastException e) {
throw new ClassCastException(activity.toString() + " must implement OnButtonClicked");
}
}
@SuppressLint("MissingPermission")
private void getRestaurants() {
mFusedLocationClient = LocationServices.getFusedLocationProviderClient(getActivity());
mFusedLocationClient.getLastLocation().addOnSuccessListener(getActivity(), new OnSuccessListener<Location>() {
@Override
public void onSuccess(final Location location) {
if (location != null) {
SharedPreferences mSettings = PreferenceManager.getDefaultSharedPreferences(context);
String sort = mSettings.getString("sort", "rating");
String order = mSettings.getString("order", "desc");
double radius = Double.parseDouble(mSettings.getString("radius", "10"));
radius = radius * 1000;
RetrofitZomato.getApi().searchByName(keyword.getText().toString(), location.getLatitude(), location.getLongitude(),
20, radius, sort, order, getActivity().getResources().getString(R.string.user_key))
.enqueue(new Callback<SearchResponse>() {
@Override
public void onResponse(Call<SearchResponse> call, Response<SearchResponse> response) {
if (restaurantsList.size() != 0) {
restaurantsList.clear();
mAdapter.notifyDataSetChanged();
}
List<Restaurant> restaurants = response.body().getRestaurants();
for (int i = 0; i < restaurants.size(); i++) {
double distance = calculateDistance(Double.parseDouble(restaurants.get(i).getRestaurant().getLocation().getLatitude()),
Double.parseDouble(restaurants.get(i).getRestaurant().getLocation().getLongitude()),
location.getLatitude(), location.getLongitude());
distance = (double) Math.round(distance * 100d) / 100d;
restaurants.get(i).getRestaurant().setDistance(distance);
restaurantsList.add(restaurants.get(i).getRestaurant());
mAdapter.notifyItemInserted(i);
}
}
@Override
public void onFailure(Call<SearchResponse> call, Throwable t) {
AlertDialog.Builder builder = new AlertDialog.Builder(getActivity());
builder.setMessage("Couldn't find any nearby restaurants");
AlertDialog mDialog = builder.create();
mDialog.show();
}
});
}
}
}).addOnFailureListener(getActivity(), new OnFailureListener() {
@Override
public void onFailure(@NonNull Exception e) {
Toast.makeText(getActivity(), "It wasn't possible to determine your location", Toast.LENGTH_LONG).show();
}
});
}
private double calculateDistance(double latRestaurant, double lonRestaurant, double myLat, double myLon) {
if ((myLat == latRestaurant) && (myLon == lonRestaurant)) {
return 0;
} else {
double theta = myLon - lonRestaurant;
double dist = Math.sin(Math.toRadians(myLat)) * Math.sin(Math.toRadians(latRestaurant))
+ Math.cos(Math.toRadians(myLat)) * Math.cos(Math.toRadians(latRestaurant)) * Math.cos(Math.toRadians(theta));
dist = Math.acos(dist);
dist = Math.toDegrees(dist);
dist = dist * 60 * 1.1515;
dist = dist * 1.609344;
return dist;
}
}
@Override
public void onClick(View view) {
int id = view.getId();
if (id == R.id.search) {
getRestaurants();
}
}
// @Override
// public void onActivityCreated(@Nullable Bundle savedInstanceState) {
// super.onActivityCreated(savedInstanceState);
// searchViewModel = ViewModelProviders.of(this).get(SearchViewModel.class);
// // TODO: Use the ViewModel
// }
}
请注意,对于每个 getRestaurants
调用,您都在调用 getFusedLocationProviderClient
和 addOnSuccessListener
,保持旧的注册和离开...也许这些多个侦听器实例是此行为的原因?
将此行移至 onAttach
mFusedLocationClient = LocationServices.getFusedLocationProviderClient(getActivity());
因为被调用一次。然后让你的 SearchFragment
实现 OnSuccessListener
并设置为 FusedLocationProviderClient
。您的点击应该触发对新位置的请求,您当前使用 getLastLocation
的代码也可能在 onAttach
中处理
编辑:真实答案-评论复制
尝试删除 mAdapter.notifyItemInserted(i);
行并将 mAdapter.notifyDataSetChanged();
移出方法结束时的 if
条件(在 for 循环之后)。我在您的代码中没有发现任何可疑之处,看起来不错...
我有这个片段,我在其中编辑文本、一个按钮和一个回收站视图。当我第一次单击该按钮时,它具有预期的行为,但如果我更改编辑文本内容并再次单击该按钮,它不会更新我的回收站视图。我究竟做错了什么?因为我在重复这个过程 每次点击 Api 调用
片段
public class SearchFragment extends Fragment implements View.OnClickListener {
private RestaurantAdapter mAdapter;
private RecyclerView mRecyclerView;
protected static List<Restaurant_> restaurantsList;
private Context context;
private static OnRestaurantClickedListener listener;
private FirebaseAuth mAuth;
private EditText keyword;
private FusedLocationProviderClient mFusedLocationClient;
public SearchFragment() {
}
public static OnRestaurantClickedListener getListener() {
return listener;
}
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
context = getContext();
mAuth = FirebaseAuth.getInstance();
restaurantsList = new ArrayList<>();
mAdapter = new RestaurantAdapter(context, restaurantsList, getActivity());
}
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View mContentView = inflater.inflate(R.layout.fragment_search, container, false);
mRecyclerView = mContentView.findViewById(R.id.recycler_view);
mRecyclerView.setLayoutManager(new LinearLayoutManager(mContentView.getContext()));
mRecyclerView.setAdapter(mAdapter);
keyword = mContentView.findViewById(R.id.keyword);
keyword.setOnEditorActionListener(new TextView.OnEditorActionListener() {
@Override
public boolean onEditorAction(TextView textView, int actionId, KeyEvent keyEvent) {
if ((keyEvent != null && keyEvent.getKeyCode() == KeyEvent.KEYCODE_ENTER) || (actionId == EditorInfo.IME_ACTION_SEARCH))
getRestaurants();
return false;
}
});
ImageButton searchButton = mContentView.findViewById(R.id.search);
searchButton.setOnClickListener(this);
return mContentView;
}
@Override
public void onResume() {
super.onResume();
}
@Override
public void onAttach(Activity activity) {
super.onAttach(activity);
try {
listener = (OnRestaurantClickedListener) activity;
} catch (ClassCastException e) {
throw new ClassCastException(activity.toString() + " must implement OnButtonClicked");
}
}
@SuppressLint("MissingPermission")
private void getRestaurants() {
mFusedLocationClient = LocationServices.getFusedLocationProviderClient(getActivity());
mFusedLocationClient.getLastLocation().addOnSuccessListener(getActivity(), new OnSuccessListener<Location>() {
@Override
public void onSuccess(final Location location) {
if (location != null) {
SharedPreferences mSettings = PreferenceManager.getDefaultSharedPreferences(context);
String sort = mSettings.getString("sort", "rating");
String order = mSettings.getString("order", "desc");
double radius = Double.parseDouble(mSettings.getString("radius", "10"));
radius = radius * 1000;
RetrofitZomato.getApi().searchByName(keyword.getText().toString(), location.getLatitude(), location.getLongitude(),
20, radius, sort, order, getActivity().getResources().getString(R.string.user_key))
.enqueue(new Callback<SearchResponse>() {
@Override
public void onResponse(Call<SearchResponse> call, Response<SearchResponse> response) {
if (restaurantsList.size() != 0) {
restaurantsList.clear();
mAdapter.notifyDataSetChanged();
}
List<Restaurant> restaurants = response.body().getRestaurants();
for (int i = 0; i < restaurants.size(); i++) {
double distance = calculateDistance(Double.parseDouble(restaurants.get(i).getRestaurant().getLocation().getLatitude()),
Double.parseDouble(restaurants.get(i).getRestaurant().getLocation().getLongitude()),
location.getLatitude(), location.getLongitude());
distance = (double) Math.round(distance * 100d) / 100d;
restaurants.get(i).getRestaurant().setDistance(distance);
restaurantsList.add(restaurants.get(i).getRestaurant());
mAdapter.notifyItemInserted(i);
}
}
@Override
public void onFailure(Call<SearchResponse> call, Throwable t) {
AlertDialog.Builder builder = new AlertDialog.Builder(getActivity());
builder.setMessage("Couldn't find any nearby restaurants");
AlertDialog mDialog = builder.create();
mDialog.show();
}
});
}
}
}).addOnFailureListener(getActivity(), new OnFailureListener() {
@Override
public void onFailure(@NonNull Exception e) {
Toast.makeText(getActivity(), "It wasn't possible to determine your location", Toast.LENGTH_LONG).show();
}
});
}
private double calculateDistance(double latRestaurant, double lonRestaurant, double myLat, double myLon) {
if ((myLat == latRestaurant) && (myLon == lonRestaurant)) {
return 0;
} else {
double theta = myLon - lonRestaurant;
double dist = Math.sin(Math.toRadians(myLat)) * Math.sin(Math.toRadians(latRestaurant))
+ Math.cos(Math.toRadians(myLat)) * Math.cos(Math.toRadians(latRestaurant)) * Math.cos(Math.toRadians(theta));
dist = Math.acos(dist);
dist = Math.toDegrees(dist);
dist = dist * 60 * 1.1515;
dist = dist * 1.609344;
return dist;
}
}
@Override
public void onClick(View view) {
int id = view.getId();
if (id == R.id.search) {
getRestaurants();
}
}
// @Override
// public void onActivityCreated(@Nullable Bundle savedInstanceState) {
// super.onActivityCreated(savedInstanceState);
// searchViewModel = ViewModelProviders.of(this).get(SearchViewModel.class);
// // TODO: Use the ViewModel
// }
}
请注意,对于每个 getRestaurants
调用,您都在调用 getFusedLocationProviderClient
和 addOnSuccessListener
,保持旧的注册和离开...也许这些多个侦听器实例是此行为的原因?
将此行移至 onAttach
mFusedLocationClient = LocationServices.getFusedLocationProviderClient(getActivity());
因为被调用一次。然后让你的 SearchFragment
实现 OnSuccessListener
并设置为 FusedLocationProviderClient
。您的点击应该触发对新位置的请求,您当前使用 getLastLocation
的代码也可能在 onAttach
编辑:真实答案-评论复制
尝试删除 mAdapter.notifyItemInserted(i);
行并将 mAdapter.notifyDataSetChanged();
移出方法结束时的 if
条件(在 for 循环之后)。我在您的代码中没有发现任何可疑之处,看起来不错...