JSON onResponse - 列表不会填充数据
Posted
技术标签:
【中文标题】JSON onResponse - 列表不会填充数据【英文标题】:JSON onResponse - List will not populate with data 【发布时间】:2021-07-23 08:08:42 【问题描述】:我正在获得一个工作应用程序(有点)。它旨在从对 JSON 数据的请求中填充屏幕。我认为到目前为止我所拥有的会起作用,但我想不会。
onResponse
似乎从未被调用过,因此数据从未分配给要处理的变量,我不知道如何解决这个问题。非常感谢任何和所有帮助。
下面是我的相关代码:
我的 JSON 数据是:
"popular":[
"name":"Pizza",
"imageURL":"https://static4.depositphotos.com/1016418/315/i/600/depositphotos_3158962-stock-photo-pepperoni-pizza-isolated.jpg",
"rating":"4.8",
"deliveryTime":"45 min",
"deliveryCharges":"Free Delivery",
"price":"15",
"note":"Delicious"
,
"name":"Chick-Fil-A",
"imageURL":"https://media.istockphoto.com/photos/chicken-bacon-club-sandwich-picture-id585602032?k=6&m=585602032&s=612x612&w=0&h=DzlMVMOaqC25Zf78NPGzr9nLOf7wANEgv9u_vScu4d8=",
"rating":"5.0",
"deliveryTime":"15 min",
"deliveryCharges":"3",
"price":"7",
"note":"Classic"
,
"name":"Mac & Cheese",
"imageURL":"https://media.istockphoto.com/photos/homemade-baked-creamy-macaroni-and-cheese-picture-id483485720?k=6&m=483485720&s=612x612&w=0&h=u2Wb4hR0cIqNAm8q_4j-oFPrtC4hT_YXaq2srA2zmqI=",
"rating":"4.7",
"deliveryTime":"20 min",
"deliveryCharges":"1",
"price":"4",
"note":"Homestyle"
],
"recommended":[
"name":"Chicken Tikka Masala",
"imageURL":"https://media.istockphoto.com/photos/chicken-tikka-masala-curry-with-rice-and-naan-bread-picture-id1143530019?k=6&m=1143530019&s=612x612&w=0&h=aOCxTVcwi88NHCX9-xgNu7cmPX9rq5AGtEVYblNTnGc=",
"rating":"4.8",
"deliveryTime":"25 min",
"deliveryCharges":"2",
"price":"14",
"note":"Fan Favorite"
,
"name":"Strawberry Milkshake",
"imageURL":"https://thumbs.dreamstime.com/b/strawberry-milkshake-covered-whipped-cream-plastic-glass-isolated-white-background-44432579.jpg",
"rating":"4.5",
"deliveryTime":"10 min",
"deliveryCharges":"0",
"price":"4",
"note":"Chilly"
,
"name":"3 Tacos",
"imageURL":"https://previews.123rf.com/images/gdolgikh/gdolgikh1703/gdolgikh170300221/74432760-mexican-tacos-with-beef.jpg",
"rating":"4.6",
"deliveryTime":"17 min",
"deliveryCharges":"1",
"price":"12",
"note":"Hard or Soft Shell"
],
"allmenu":[
"name":"Pizza",
"imageURL":"https://static4.depositphotos.com/1016418/315/i/600/depositphotos_3158962-stock-photo-pepperoni-pizza-isolated.jpg",
"rating":"4.8",
"deliveryTime":"45 min",
"deliveryCharges":"Free Delivery",
"price":"15",
"note":"Delicious"
,
"name":"Chick-Fil-A",
"imageURL":"https://media.istockphoto.com/photos/chicken-bacon-club-sandwich-picture-id585602032?k=6&m=585602032&s=612x612&w=0&h=DzlMVMOaqC25Zf78NPGzr9nLOf7wANEgv9u_vScu4d8=",
"rating":"5.0",
"deliveryTime":"15 min",
"deliveryCharges":"3",
"price":"7",
"note":"Classic"
,
"name":"Mac & Cheese",
"imageURL":"https://media.istockphoto.com/photos/homemade-baked-creamy-macaroni-and-cheese-picture-id483485720?k=6&m=483485720&s=612x612&w=0&h=u2Wb4hR0cIqNAm8q_4j-oFPrtC4hT_YXaq2srA2zmqI=",
"rating":"4.7",
"deliveryTime":"20 min",
"deliveryCharges":"1",
"price":"4",
"note":"Homestyle"
,
"name":"Chicken Tikka Masala",
"imageURL":"https://media.istockphoto.com/photos/chicken-tikka-masala-curry-with-rice-and-naan-bread-picture-id1143530019?k=6&m=1143530019&s=612x612&w=0&h=aOCxTVcwi88NHCX9-xgNu7cmPX9rq5AGtEVYblNTnGc=",
"rating":"4.8",
"deliveryTime":"25 min",
"deliveryCharges":"2",
"price":"14",
"note":"Fan Favorite"
,
"name":"Strawberry Milkshake",
"imageURL":"https://thumbs.dreamstime.com/b/strawberry-milkshake-covered-whipped-cream-plastic-glass-isolated-white-background-44432579.jpg",
"rating":"4.5",
"deliveryTime":"10 min",
"deliveryCharges":"0",
"price":"4",
"note":"Chilly"
,
"name":"3 Tacos",
"imageURL":"https://previews.123rf.com/images/gdolgikh/gdolgikh1703/gdolgikh170300221/74432760-mexican-tacos-with-beef.jpg",
"rating":"4.6",
"deliveryTime":"17 min",
"deliveryCharges":"1",
"price":"12",
"note":"Hard or Soft Shell"
]
我有 Allmenu
、FoodData
、Popular
和 Recommended
的模型。
所有菜单:
package com.example.bearcateats.model;
import javax.annotation.Generated;
import com.google.gson.annotations.Expose;
import com.google.gson.annotations.SerializedName;
@Generated("jsonschema2pojo")
public class Allmenu
@SerializedName("name")
@Expose
private String name;
@SerializedName("imageURL")
@Expose
private String imageURL;
@SerializedName("rating")
@Expose
private String rating;
@SerializedName("deliveryTime")
@Expose
private String deliveryTime;
@SerializedName("deliveryCharges")
@Expose
private String deliveryCharges;
@SerializedName("price")
@Expose
private String price;
@SerializedName("note")
@Expose
private String note;
public String getName()
return name;
public void setName(String name)
this.name = name;
public String getImageURL()
return imageURL;
public void setImageURL(String imageURL)
this.imageURL = imageURL;
public String getRating()
return rating;
public void setRating(String rating)
this.rating = rating;
public String getDeliveryTime()
return deliveryTime;
public void setDeliveryTime(String deliveryTime)
this.deliveryTime = deliveryTime;
public String getDeliveryCharges()
return deliveryCharges;
public void setDeliveryCharges(String deliveryCharges)
this.deliveryCharges = deliveryCharges;
public String getPrice()
return price;
public void setPrice(String price)
this.price = price;
public String getNote()
return note;
public void setNote(String note)
this.note = note;
食物数据:
package com.example.bearcateats.model;
import java.util.List;
import javax.annotation.Generated;
import com.google.gson.annotations.Expose;
import com.google.gson.annotations.SerializedName;
@Generated("jsonschema2pojo")
public class FoodData
@SerializedName("popular")
@Expose
private List<Popular> popular = null;
@SerializedName("recommended")
@Expose
private List<Recommended> recommended = null;
@SerializedName("allmenu")
@Expose
private List<Allmenu> allmenu = null;
public List<Popular> getPopular()
return popular;
public void setPopular(List<Popular> popular)
this.popular = popular;
public List<Recommended> getRecommended()
return recommended;
public void setRecommended(List<Recommended> recommended)
this.recommended = recommended;
public List<Allmenu> getAllmenu()
return allmenu;
public void setAllmenu(List<Allmenu> allmenu)
this.allmenu = allmenu;
流行:
package com.example.bearcateats.model;
import javax.annotation.Generated;
import com.google.gson.annotations.Expose;
import com.google.gson.annotations.SerializedName;
@Generated("jsonschema2pojo")
public class Popular
@SerializedName("name")
@Expose
private String name;
@SerializedName("imageURL")
@Expose
private String imageURL;
@SerializedName("rating")
@Expose
private String rating;
@SerializedName("deliveryTime")
@Expose
private String deliveryTime;
@SerializedName("deliveryCharges")
@Expose
private String deliveryCharges;
@SerializedName("price")
@Expose
private String price;
@SerializedName("note")
@Expose
private String note;
public String getName()
return name;
public void setName(String name)
this.name = name;
public String getImageURL()
return imageURL;
public void setImageURL(String imageURL)
this.imageURL = imageURL;
public String getRating()
return rating;
public void setRating(String rating)
this.rating = rating;
public String getDeliveryTime()
return deliveryTime;
public void setDeliveryTime(String deliveryTime)
this.deliveryTime = deliveryTime;
public String getDeliveryCharges()
return deliveryCharges;
public void setDeliveryCharges(String deliveryCharges)
this.deliveryCharges = deliveryCharges;
public String getPrice()
return price;
public void setPrice(String price)
this.price = price;
public String getNote()
return note;
public void setNote(String note)
this.note = note;
推荐:
package com.example.bearcateats.model;
import javax.annotation.Generated;
import com.google.gson.annotations.Expose;
import com.google.gson.annotations.SerializedName;
@Generated("jsonschema2pojo")
public class Recommended
@SerializedName("name")
@Expose
private String name;
@SerializedName("imageURL")
@Expose
private String imageURL;
@SerializedName("rating")
@Expose
private String rating;
@SerializedName("deliveryTime")
@Expose
private String deliveryTime;
@SerializedName("deliveryCharges")
@Expose
private String deliveryCharges;
@SerializedName("price")
@Expose
private String price;
@SerializedName("note")
@Expose
private String note;
public String getName()
return name;
public void setName(String name)
this.name = name;
public String getImageURL()
return imageURL;
public void setImageURL(String imageURL)
this.imageURL = imageURL;
public String getRating()
return rating;
public void setRating(String rating)
this.rating = rating;
public String getDeliveryTime()
return deliveryTime;
public void setDeliveryTime(String deliveryTime)
this.deliveryTime = deliveryTime;
public String getDeliveryCharges()
return deliveryCharges;
public void setDeliveryCharges(String deliveryCharges)
this.deliveryCharges = deliveryCharges;
public String getPrice()
return price;
public void setPrice(String price)
this.price = price;
public String getNote()
return note;
public void setNote(String note)
this.note = note;
主要:
package com.example.bearcateats;
import android.os.Bundle;
import android.widget.Toast;
import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;
import androidx.appcompat.app.AppCompatActivity;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
import com.example.bearcateats.adapters.PopularAdapter;
import com.example.bearcateats.adapters.RecommendedAdapter;
import com.example.bearcateats.model.Allmenu;
import com.example.bearcateats.model.FoodData;
import com.example.bearcateats.model.Popular;
import com.example.bearcateats.model.Recommended;
import com.example.bearcateats.retrofit.ApiInterface;
import com.example.bearcateats.retrofit.RetrofitClient;
import com.example.bearcateats.adapters.AllMenuAdapter;
import java.util.List;
public class MainActivity extends AppCompatActivity
ApiInterface apiInterface;
RecyclerView popularRecyclerView, recommendedRecyclerView, allMenuRecyclerView;
PopularAdapter popularAdapter;
RecommendedAdapter recommendedAdapter;
AllMenuAdapter allMenuAdapter;
@Override
protected void onCreate(Bundle savedInstanceState)
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
apiInterface = RetrofitClient.getRetrofitInstance().create(ApiInterface.class);
Call<List<FoodData>> call = apiInterface.getAllData();
call.enqueue(new Callback<List<FoodData>>()
@Override
public void onResponse(Call<List<FoodData>> call, Response<List<FoodData>> response)
System.out.println("TEST!!!!!!!!!!!!!!");
List<FoodData> MenuList;
MenuList = response.body();
if(MenuList == null)
System.out.println("MenuList!!!!!!!!!!!!!!");
List <FoodData> test1 = (List<FoodData>) MenuList.get(0);
List<Popular> popular = ((FoodData) test1).getPopular();
getPopularData(popular);
System.out.println("GET POPULAR RAN!!!!!!!!!!!!!!");
getRecommendedData(MenuList.get(0).getRecommended());
@Override
public void onFailure(Call<List<FoodData>> call, Throwable t)
Toast.makeText(MainActivity.this, "Server is not responding.", Toast.LENGTH_SHORT).show();
);
private void getPopularData(List<Popular> popularList)
popularRecyclerView = findViewById(R.id.popular_recycler);
popularAdapter = new PopularAdapter(this, popularList);
RecyclerView.LayoutManager layoutManager = new LinearLayoutManager(this, LinearLayoutManager.HORIZONTAL, false);
popularRecyclerView.setLayoutManager(layoutManager);
popularRecyclerView.setAdapter(popularAdapter);
private void getRecommendedData(List<Recommended> recommendedList)
recommendedRecyclerView = findViewById(R.id.recommended_recycler);
recommendedAdapter = new RecommendedAdapter(this, recommendedList);
RecyclerView.LayoutManager layoutManager = new LinearLayoutManager(this, LinearLayoutManager.HORIZONTAL, false);
recommendedRecyclerView.setLayoutManager(layoutManager);
recommendedRecyclerView.setAdapter(recommendedAdapter);
private void getAllMenu(List<Allmenu> allmenuList)
allMenuRecyclerView = findViewById(R.id.all_menu_recycler);
allMenuAdapter = new AllMenuAdapter(this, allmenuList);
RecyclerView.LayoutManager layoutManager = new LinearLayoutManager(this, LinearLayoutManager.VERTICAL, false);
allMenuRecyclerView.setLayoutManager(layoutManager);
allMenuRecyclerView.setAdapter(allMenuAdapter);
allMenuAdapter.notifyDataSetChanged();
食物详情
// now we will get data from intent and set to UI
ImageView imageView;
TextView itemName, itemPrice, itemRating;
RatingBar ratingBar;
String name, price, rating, imageUrl;
@Override
protected void onCreate(Bundle savedInstanceState)
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_food_details);
Intent intent = getIntent();
name = intent.getStringExtra("name");
price = intent.getStringExtra("price");
rating = intent.getStringExtra("rating");
imageUrl = intent.getStringExtra("image");
imageView = findViewById(R.id.imageView5);
itemName = findViewById(R.id.name);
itemPrice = findViewById(R.id.price);
itemRating = findViewById(R.id.rating);
ratingBar = findViewById(R.id.ratingBar);
Glide.with(getApplicationContext()).load(imageUrl).into(imageView);
itemName.setText(name);
itemPrice.setText("$ "+price);
itemRating.setText(rating);
ratingBar.setRating(Float.parseFloat(rating));
【问题讨论】:
你是否 100% 确定call.enqueue
确实 被调用并且 onResponse
和 onFailure
没有?
使用 log.d("tag","message") 记录您的错误和消息,而不是 system.out.print。
@HenryTwist 我至少 100% 确定 onResponse
没有。在对代码运行一些测试后,我相信 call.enqueue
没有运行。
很高兴您发现了问题。您总是想在发布问题之前进行测试,如果您能自己发现问题,它将为您节省大量时间。然后,如果您仍然需要提出问题,可以让我们确切知道问题出在哪里。
@henrytwist 所以你会建议我写一个新问题吗?
【参考方案1】:
有几个愚蠢的错误。我已经修复了你所有的错误。您的 JSON
或 Response
数据类没有问题。在onResponse()
回调中收到正确的response
。问题存在于代码的其他部分。一步一步来。
第一步
在解析来自api
调用的response
数据时替换以下代码,如下所示:
call.enqueue(new Callback<List<FoodData>>()
@Override
public void onResponse(Call<List<FoodData>> call, Response<List<FoodData>> response)
if (response.isSuccessful())
if (response.body() != null)
List<Popular> popular = response.body().get(0).getPopular();
getPopularData(popular);
getRecommendedData(response.body().get(0).getRecommended());
@Override
public void onFailure(Call<List<FoodData>> call, Throwable t)
Toast.makeText(MainActivity.this, "Server is not responding.", Toast.LENGTH_SHORT).show();
);
第二步
在PopularAdapter
类里面替换getItemCount()
方法如下:
@Override
public int getItemCount()
//return 0; // Returning 0 will show nothing in RecyclerView.
return popularList.size();
第三步:
在RecommendedAdapter
类中,您将xml
错误地用于ViewHolder
。替换如下:
@NonNull
@Override
public RecommendedViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType)
//View view = LayoutInflater.from(context).inflate(R.layout.popular_recycler_items, parent, false);
View view = LayoutInflater.from(context).inflate(R.layout.recommended_recyvler_items, parent, false);
return new RecommendedViewHolder(view);
同时替换getItemCount()
方法如下:
@Override
public int getItemCount()
return recommendedList.size();
更新:-
你为什么在 onSuccess()
的 api
调用中调用相同的 api
?我已经更新了您的 onCreate()
方法,如下所示:
@Override
protected void onCreate(Bundle savedInstanceState)
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
apiInterface = RetrofitClient.getRetrofitInstance().create(ApiInterface.class);
Call<List<FoodData>> call = apiInterface.getAllData();
call.enqueue(new Callback<List<FoodData>>()
@Override
public void onResponse(Call<List<FoodData>> call, Response<List<FoodData>> response)
if (response.isSuccessful())
if (response.body() != null)
getPopularData(response.body().get(0).getPopular());
getRecommendedData(response.body().get(0).getRecommended());
getAllMenu(response.body().get(0).getAllmenu());
/*
call.clone().enqueue(new Callback<List<FoodData>>()
@Override
public void onResponse(Call<List<FoodData>> call, Response<List<FoodData>> response)
if (response.isSuccessful())
if (response.body() != null)
response.code();
getPopularData(response.body().get(0).getPopular());
getRecommendedData(response.body().get(0).getRecommended());
getAllMenu(response.body().get(0).getAllmenu());
@Override
public void onFailure(Call<List<FoodData>> call, Throwable t)
response.code();
Toast.makeText(MainActivity.this, t.getLocalizedMessage(), Toast.LENGTH_SHORT).show();
);*/
@Override
public void onFailure(Call<List<FoodData>> call, Throwable t)
Toast.makeText(MainActivity.this, t.getLocalizedMessage(), Toast.LENGTH_SHORT).show();
);
【讨论】:
感谢您的帮助!我能够解决所有这些问题和其他一些语法错误。现在我遇到了其他我不知道的事情。你介意帮忙吗?代码在 GitHub 上是最新的。 ``` 进程:com.example.bearcateats,PID:9332 java.lang.IllegalStateException:已经执行。在 retrofit2.OkHttpCall.enqueue(OkHttpCall.java:88) 在 retrofit2.ExecutorCallAdapterFactory$ExecutorCallbackCall.enqueue(ExecutorCallAdapterFactory.java:62) 在 com.example.bearcateats.MainActivity$1.onResponse(MainActivity.java:49) ``` 我的回答已经改了,请查收。【参考方案2】:我看到您在 https://francescainfranca.github.io/menuJSON/index.json 中的 JSON 是单个 FoodData JSON 对象,而不是 JSONArray。
这会在我们运行应用程序时导致以下异常。因此,要么更改 JSON 结构,要么让应用程序直接使用 FoodData 而不是 List
Toast 消息(服务器没有响应)也在运行时显示,您已在失败响应中添加。
希望这对您有所帮助。谢谢。
【讨论】:
谢谢,我对 JSON 语法有点怀疑。我通过在文件的开头和结尾添加方括号将 JSON 编辑为数组,但它似乎仍然不起作用。 用此代码替换您的响应正文List<FoodData> MenuList = response.body(); if (MenuList != null && MenuList.size() > 0) FoodData foodData = MenuList.get(0); getPopularData(foodData.getPopular()); getRecommendedData(foodData.getRecommended()); else System.out.println("No Items Found!");
和 RecommendedAdapter.java 将布局文件“popular_recycler_items”替换为“recommended_recyvler_items”这应该可以解决您的问题。以上是关于JSON onResponse - 列表不会填充数据的主要内容,如果未能解决你的问题,请参考以下文章
Android Volley 为啥 JsonObjectRequest 不调用 onResponse
Volley Post 请求在 onResponse 内没有返回响应
Android Volley 的 onResponse 方法未执行