RecyclerView 不显示从本地主机发送的 JSON 只是空白屏幕
Posted
技术标签:
【中文标题】RecyclerView 不显示从本地主机发送的 JSON 只是空白屏幕【英文标题】:RecyclerView not showing JSON sent from localhost just blank screen 【发布时间】:2018-11-20 19:07:13 【问题描述】:大家好,我对 AsyncTask 没有太多经验,这是我第一次使用 RecyclerView,除了我为了解它而完成的几个教程。
如果我在 EventActivity 中使用虚拟数据,一切正常,并且屏幕上会显示一个列表。但是当我创建一个 EventItems 的 ArrayList 并将其传递给适配器时,它只是一个空白屏幕。来自 localhost 的 JSON 正在被解析并发送到 EventItem 类。我已经尝试了几件事来让它工作,但由于我对 AsyncTask 和 RecyclerView 的经验有限,我最终只是让应用程序崩溃并得到一个空指针异常。
我认为 RecyclerView 是在从 localhost 检索 JSON 之前创建的,这就是导致空白屏幕或空指针异常的原因,但我不是 100% 确定,如果我不知道如何解决这个问题正确。
感谢任何帮助。
事件活动
public class EventActivity extends AppCompatActivity
private RecyclerView mRecyclerView;
private RecyclerView.Adapter mAdapter;
private RecyclerView.LayoutManager mLayoutManager;
@Override
protected void onCreate(Bundle savedInstanceState)
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_event);
fetchEvents();//call EventBackgroundWorker
//ArrayList<EventItem> eventList = new EventItem().getRecyclerList();//causes java null pointer exception
ArrayList<EventItem> eventList = new ArrayList<>();
//Dummie data
// eventList.add(new EventItem (1, "Title1", "Date", "endDate", "Location1", 5, 1111));
// eventList.add(new EventItem (R.drawable.ic_favourite, "Title2", "11/07/2018", "11/07/2018", "Wales", 10, 5));
// eventList.add(new EventItem (R.drawable.ramspeed_custom, "Title3", "11/01/2018", "11/09/2018", "Paris, France", 0, 90));
// eventList.add(new EventItem (R.drawable.ramspeed_custom, "Title4", "12/01/2018", "11/09/2018", "New York", 20, 500));
// eventList.add(new EventItem (R.drawable.ic_favourite, "Title5", "Mon 11/05/2015", "11/09/2018", "London, England", 5, 500));
// eventList.add(new EventItem (R.drawable.biker, "Title6", "Mon 11/05/2018", "20/07/2018", "Swords Dublin", 0, 500));
mRecyclerView = (RecyclerView) findViewById(R.id.event_recycler_view);
mRecyclerView.setHasFixedSize(true);//increase performance of app if recyclerView does not increase in size
mLayoutManager = new LinearLayoutManager(this);
// mAdapter = new EventAdapter(eventList);
mAdapter = new EventAdapter(eventList);//context added for testing //////////////////////////////
// mAdapter = new EventAdapter(new ArrayList<EventItem>(0));
mRecyclerView.setLayoutManager(mLayoutManager);
mRecyclerView.setAdapter(mAdapter);
// buildRecyclerView();
//run background thread
private void fetchEvents()
// String username = "user";
// String userPassword = "password";
String startConnectionCondition = "event";
//this passes the context
EventBackgroundWorker backgroundWorker = new EventBackgroundWorker(this);
backgroundWorker.execute(startConnectionCondition, null);
/* private void buildRecyclerView()
ArrayList<EventItem> eventList = new EventItem().getRecyclerList();
mRecyclerView = (RecyclerView) findViewById(R.id.event_recycler_view);
mRecyclerView.setHasFixedSize(true);//increase performance of app if recyclerView does not increase in size
mLayoutManager = new LinearLayoutManager(this);
// mAdapter = new EventAdapter(eventList);
mAdapter = new EventAdapter(eventList);//context added for testing
// mAdapter = new EventAdapter(new ArrayList<EventItem>(0));
mRecyclerView.setLayoutManager(mLayoutManager);
mRecyclerView.setAdapter(mAdapter);
*/
/* public void showEventList(boolean b)
ArrayList<EventItem> eventList = new ArrayList<>();
for(int i =0; i< eventList.size(); i++)
eventList.get(i);
Log.d("tag","eventList from main " + eventList);
mAdapter = new EventAdapter(eventList);
mRecyclerView.setLayoutManager(mLayoutManager);
mRecyclerView.setAdapter(mAdapter);
*/
//MainActivity
事件适配器
public class EventAdapter extends RecyclerView.Adapter<EventAdapter.EventViewHolder>
private ArrayList<EventItem> mEventList;
Context context;
//constructor for EventAdapter
public EventAdapter(ArrayList<EventItem> eventList)
// context =c;
mEventList = eventList;
Log.d("tag","EventAdapter eventlist variable called from constructor " + eventList);
public static class EventViewHolder extends RecyclerView.ViewHolder
public ImageView mPromoImage;
public TextView mTitle;
public TextView mStartDate;
public TextView mEndDate;
public TextView mLocation;
public TextView mFee;
public ImageView mFavourite;
//constructor for EventViewHolder class
public EventViewHolder(View itemView)
super(itemView);
// mPromoImage = (ImageView) itemView.findViewById(R.id.event_promotional_image);
mTitle = (TextView) itemView.findViewById(R.id.event_title_textView);
mStartDate = (TextView) itemView.findViewById(R.id.event_start_textView);
mEndDate = (TextView) itemView.findViewById(R.id.event_end_textView);
mLocation = (TextView) itemView.findViewById(R.id.event_location_textView);
mFee = (TextView) itemView.findViewById(R.id.event_fee_textView);
// mFavourite = (ImageView) itemView.findViewById(R.id.event_favourite_image);
Log.d("tag", "EventViewHolder being called");
//EventViewHolder class
@Override
public EventViewHolder onCreateViewHolder(ViewGroup parent, int viewType)
View v = LayoutInflater.from(parent.getContext()).inflate(R.layout.item_event, parent, false);
//create view holder
EventViewHolder viewHolder = new EventViewHolder(v);
return viewHolder;
//pass values to inflated XML Views in item_event.xml
@Override
public void onBindViewHolder(EventViewHolder holder, int position)
EventItem currentEvent = mEventList.get(position);
// holder.mPromoImage.setImageResource(currentEvent.getEventPromoImage());
holder.mTitle.setText(currentEvent.getEventTitle());
holder.mStartDate.setText(currentEvent.getEventStartDate());
holder.mEndDate.setText(currentEvent.getEventEndDate());
holder.mLocation.setText(currentEvent.getEventLocation());
holder.mFee.setText(String.valueOf(currentEvent.getEventFee()));//int value passed
// holder.mFavourite.setImageResource(currentEvent.getEventFavourite());
//Log.d("tag", "position" + position );
Log.d("tag","eventAdapter " + currentEvent.getEventTitle());
//how many items there will be
@Override
public int getItemCount()
return mEventList.size();
事件项
public class EventItem
private int mEventPromoImage;
private int mId;
private String mEventTitle;
private String mEventStartDate;
private String mEventEndDate;
private String mEventLocation;
private int mEventFee;
private int mEventViews;
// public EventItem()
public EventItem(int id, String eventTitle, String eventStartDate,
String eventEndDate, String eventLocation, int eventFee, int eventViews)
// mEventPromoImage = eventPromoImage;
mId = id;
mEventTitle = eventTitle;
mEventStartDate = eventStartDate;
mEventEndDate = eventEndDate;
mEventLocation = eventLocation;
mEventFee = eventFee;
mEventViews = eventViews;
Log.d("tag","EVENTITEM title EventItem" + mEventTitle);
// Log.d("tag","EVENTITEM startDate EventItem" + mEventStartDate );
// Log.d("tag","EVENTITEM endDate EventItem" + mEventEndDate );
// Log.d("tag","EVENTITEM address EventItem" + mEventLocation);
// Log.d("tag","EVENTITEM fee EventItem" + mEventFee);
public int getEventPromoImage()
return mEventPromoImage;
public void setEventPromoImage(int mEventPromoImage)
this.mEventPromoImage = mEventPromoImage;
public int getEventId()
return mId;
public void setEventId(int mId)
this.mId = mId;
public String getEventTitle()
Log.d("tag","getEventTitle() " + mEventTitle);
return mEventTitle;
public void setEventTitle(String mEventTitle)
this.mEventTitle = mEventTitle;
public String getEventStartDate()
return mEventStartDate;
public void setEventStartDate(String mEventStartDate)
this.mEventStartDate = mEventStartDate;
public String getEventEndDate()
return mEventEndDate;
public void setEventEndDate(String mEventEndDate)
this.mEventEndDate = mEventEndDate;
public String getEventLocation()
return mEventLocation;
public void setEventLocation(String mEventLocation)
this.mEventLocation = mEventLocation;
public int getEventFee()
return mEventFee;
public void setEventFee(int mEventFee)
this.mEventFee = mEventFee;
public int getEventViews()
return mEventViews;
public void getEventViews(int mEventViews)
this.mEventViews = mEventViews;
public ArrayList<EventItem> getRecyclerList()
ArrayList event = new ArrayList();
event.add(mEventTitle);
event.add(mEventStartDate);
event.add(mEventEndDate);
event.add(mEventLocation);
event.add(mEventFee);
event.add(mEventViews);
return event;
EventBackgroundWorker
public class EventBackgroundWorker extends AsyncTask<String, Void, String>
Context context;
AlertDialog alert;
public static final String REQUEST_URL = "http://10.0.2.2/m/event/";
public EventBackgroundWorker(Context ctxt)
context = ctxt;
//Invoked on UI thread before doInBackground is called
@Override
protected void onPreExecute()
alert = new AlertDialog.Builder(context).create();
alert.setTitle("Result from server");
@Override
protected String doInBackground(String... params)
String type = params[0];//eventList
//String login_url = "http://10.0.2.2/m/event/";
if(type.equals("event"))
try
String user_name = params[1];
URL url = new URL(REQUEST_URL);
HttpURLConnection httpURLConnection = (HttpURLConnection) url.openConnection();
httpURLConnection.setRequestMethod("POST");
httpURLConnection.setDoOutput(true);
httpURLConnection.setDoInput(true);
httpURLConnection.connect();//works without this connect Find out why
OutputStream outputStream = httpURLConnection.getOutputStream();
BufferedWriter bufferedWriter = new BufferedWriter(new OutputStreamWriter(outputStream, "UTF-8"));
String post_data = URLEncoder.encode("getEvents", "UTF-8");
bufferedWriter.write(post_data);
bufferedWriter.flush();
bufferedWriter.close();
outputStream.close();
//read response
InputStream inputStream = httpURLConnection.getInputStream();
BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(inputStream, "iso-8859-1"));
String result = "";
String line;
while((line = bufferedReader.readLine()) != null)
result += line;
//parse JSON event Array
// Create an empty ArrayList that we can start adding events to
ArrayList<EventItem> eventArray = new ArrayList<>();
JSONArray baseJsonResponse = new JSONArray(result);
for(int i =0; i < baseJsonResponse.length(); i++)
JSONObject event = baseJsonResponse.getJSONObject(i);
int id = event.getInt("id");
String title = event.getString("title");
String address = event.getString("address");
String startDate = event.getString("startDate");
String endDate = event.getString("endDate");
int fee = event.getInt("fee");
int views = event.getInt("views");
//Send data to eventItem Object
EventItem eventObject = new EventItem(id,title,address,startDate,endDate,fee,views);
eventArray.add(eventObject);
/* Log.d("tag", "JSON id " + id);
Log.d("tag", "JSON title " + title);
Log.d("tag", "JSON address " + address);
Log.d("tag", "JSON startDate " + startDate);
Log.d("tag", "JSON endDate " + endDate);
Log.d("tag", "JSON fee " + fee);
Log.d("tag", "JSON views " + views);*/
bufferedReader.close();
inputStream.close();
httpURLConnection.disconnect();
return result;
catch (MalformedURLException e) //added for URL object
e.printStackTrace();
catch (IOException e)
//HTPURLConnection
catch (JSONException e)
e.printStackTrace();
return null;
@Override
protected void onProgressUpdate(Void... values)
super.onProgressUpdate(values);
//results from doInBackground are passed here
@Override
protected void onPostExecute(String result)
Log.d("tag", "onPostExecute called" + result);
alert.setMessage(result);
alert.show();
【问题讨论】:
【参考方案1】:AsyncTask 创建 eventArray 但不做任何事情。 doInBackground() 应该返回 eventArray 并且 onPostExecute() 应该将其设置为适配器内容(通过回调或通过在 AsyncTask 对象中设置适配器实例)。您的适配器应该有一个内容设置器,它应该调用 notifyDataSetChanged()。
【讨论】:
嗨乔纳斯感谢您的回复和解决方案,它运行良好以上是关于RecyclerView 不显示从本地主机发送的 JSON 只是空白屏幕的主要内容,如果未能解决你的问题,请参考以下文章