I am trying to implement the recycler-view-selection library in android, I have implemented most of it, but I am facing an issue when I am trying to refresh my screen. After refreshing my screen using SwipeRefresh, if I try to long press an item in my recycler view the app keeps crashing and I receive this error.
FATAL EXCEPTION: main
Process: com.quicklyservices.restaurants, PID: 4026
java.lang.IllegalArgumentException
at androidx.core.util.Preconditions.checkArgument(Preconditions.java:38)
at androidx.recyclerview.selection.DefaultSelectionTracker.anchorRange(DefaultSelectionTracker.java:288)
at androidx.recyclerview.selection.MotionInputHandler.selectItem(MotionInputHandler.java:60)
at androidx.recyclerview.selection.TouchInputHandler.onLongPress(TouchInputHandler.java:164)
at androidx.recyclerview.selection.GestureRouter.onLongPress(GestureRouter.java:97)
at android.view.GestureDetector.dispatchLongPress(GestureDetector.java:770)
at android.view.GestureDetector.-wrap0(GestureDetector.java)
at android.view.GestureDetector$GestureHandler.handleMessage(GestureDetector.java:293)
at android.os.Handler.dispatchMessage(Handler.java:102)
at android.os.Looper.loop(Looper.java:154)
at android.app.ActivityThread.main(ActivityThread.java:6077)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:865)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:755)
This how I set my onRefreshListener
swipeRefreshLayout.setOnRefreshListener(new SwipeRefreshLayout.OnRefreshListener() {
#Override
public void onRefresh() {
resetTracker();
getPendingCarts();
}
});
getPendingCarts method -
public void getPendingCarts()
{
swipeRefreshLayout.setRefreshing(true);
String token = SharedPrefUtil.getInstance().getApiToken(getActivity());
Call<ResponsePendingCart> call = ApiClient.getInstance().getPendingCarts(token);
call.enqueue(new Callback<ResponsePendingCart>() {
#Override
public void onResponse(Call<ResponsePendingCart> call, Response<ResponsePendingCart> response) {
try{
ResponsePendingCart pendingCart = response.body();
if(pendingCart.getStatus() == -1)
{
HelperClass.getInstance().forceLogout(getActivity());
}
else
{
List<Order> items = pendingCart.getItems();
if(items == null || items.size()==0)
{
container_no_order.setVisibility(View.VISIBLE);
rview_ongoing.setVisibility(View.INVISIBLE);
}
else
{
container_no_order.setVisibility(View.INVISIBLE);
rview_ongoing.setVisibility(View.VISIBLE);
AppData.shopCurrency = Html.fromHtml(pendingCart.getItems().get(0).getShop().getCurrencyHtmlCode()).toString();
for (Order item : items ) {
try{
List<ShopPromotion> promotions = item.getShopPromotion();
for (ShopPromotion promotionItem: promotions) {
List<FreeDishItem> dishItem = promotionItem.getFreeDish();
if (dishItem != null) {
for (int i = 0; i < dishItem.size() && dishItem.get(i) != null; i++) {
Dish orderItemListItem = new Dish();
orderItemListItem.setTitle(dishItem.get(i).getTitle());
orderItemListItem.setQuantity(dishItem.get(i).getQuantity());
orderItemListItem.setDetails(dishItem.get(i).getDetails());
orderItemListItem.setPrice(0.00);
orderItemListItem.setIsFreeDish(1);
item.getOrderItemList().add(orderItemListItem);
}
}
}
}
catch (Exception e) {
FirebaseCrashlytics.getInstance().log(e.toString());
}
}
if(listAdapter == null)
{
listAdapter = new OngoingListAdapter(getActivity(),items);
rview_ongoing.setAdapter(listAdapter);
rview_ongoing.setLayoutManager(new LinearLayoutManager(getActivity()));
int resId = R.anim.layout_animation_from_bottom;
LayoutAnimationController animation = AnimationUtils.loadLayoutAnimation(getActivity(), resId);
rview_ongoing.setLayoutAnimation(animation);
initSelectionTracker(listAdapter,rview_ongoing);
swipeRefreshLayout.setRefreshing(false);
}
else
{
OngoingListAdapter listAdapter = new OngoingListAdapter(getActivity(),items);
rview_ongoing.setAdapter(listAdapter);
rview_ongoing.setLayoutManager(new LinearLayoutManager(getActivity()));
initSelectionTracker(listAdapter,rview_ongoing);
swipeRefreshLayout.setRefreshing(false);
}
}
}
swipeRefreshLayout.setRefreshing(false);
}
catch (Exception e)
{
container_no_order.setVisibility(View.VISIBLE);
swipeRefreshLayout.setRefreshing(false);
FirebaseCrashlytics.getInstance().log(e.toString());
}
}
#Override
public void onFailure(Call<ResponsePendingCart> call, Throwable t) {
swipeRefreshLayout.setRefreshing(false);
}
});
}
initSelectionTracker works as such -
public void initSelectionTracker(OngoingListAdapter adapter,RecyclerView recyclerView){
OngoingListItemKeyProvider keyProvider = new OngoingListItemKeyProvider(adapter);
OngoingListItemDetailsLookup itemDetailsLookup = new OngoingListItemDetailsLookup(recyclerView);
StorageStrategy<Order> storageStrategy = StorageStrategy.createParcelableStorage(Order.class);
SelectionTracker.SelectionPredicate<Order> selectionPredicate = new SelectionTracker.SelectionPredicate<Order>() {
#Override
public boolean canSetStateForKey(#NonNull Order key, boolean nextState) {
return key.getService() == 1 && tracker.getSelection().size()<2;
}
#Override
public boolean canSetStateAtPosition(int position, boolean nextState) {
return listAdapter.getItem(position).getService() == 1 && tracker.getSelection().size()<2;
}
#Override
public boolean canSelectMultiple() {
return true;
}
};
tracker = new SelectionTracker.Builder<Order>(
"my-selection-id",
recyclerView,
keyProvider,
itemDetailsLookup,
storageStrategy).withSelectionPredicate(selectionPredicate)
.build();
adapter.setTracker(tracker);
tracker.addObserver(new SelectionTracker.SelectionObserver<Order>() {
#Override
public void onSelectionChanged() {
try{
super.onSelectionChanged();
selectedItems = tracker.getSelection().size();
if(selectedItems>0){
try{
setActionBarTitle(String.format("%d Order(s) Selected",selectedItems));
Selection<Order> selections = tracker.getSelection();
for(Order selectedOrder:selections){
selectedOrders.add(selectedOrder.getTemporaryOrderId());
}
}catch (Exception e){
FirebaseCrashlytics.getInstance().log(e.toString());
}
}else{
tracker.clearSelection();
selectedOrders.clear();
setActionBarTitle("Ongoing");
}
getActivity().invalidateOptionsMenu();
}catch (Exception e){
e.printStackTrace();
}
}
});
}
Related
I have used rxjava and retrofit to load data from backend and update the UI.
But there is no data displayed on section view. I have tested it, and the backend data load successful and the UI can be updated using fake data.
Are there something wrong when I use Rxjava?
private void retrieveCardInfo(String stripeId, String userToken) {
subscriptions.add(NetworkUtil.getRetrofit(userToken).getCustomerInfo(new GetCustomer(stripeId))
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(this::handleCustomerResponse, this::handleError));
}
private void handleCustomerResponse(CreateStripeCustomerResponse response) {
if (response.getSuccess()) {
updateCardList(response);
bankSection.setState(Section.State.EMPTY);
} else {
Utils.toast(this,"Get credit card failed");
}
}
private void updateCardList(CreateStripeCustomerResponse response) {
List<CardInfo> cardList = response.getCustomer().getSources().getData();
if (cardList == null || cardList.size() == 0) {
cardSection.setState(Section.State.EMPTY);
} else {
list = new ArrayList<>();
for (int i = 0; i < cardList.size(); i++) {
CardInfo cardInfo = cardList.get(i);
String brand = cardInfo.getBrand();
String subTitle = cardInfo.getFunding() + "****" + cardInfo.getLast4();
list.add(new PaymentAccountItem(brand, subTitle, cardDrawable.get(brand)));
}
list.add(new PaymentAccountItem("title", "subtitle", R.drawable.ic__credit_amex_svg));
cardSection.swipeData(list);
}
}
private void handleError(Throwable throwable) {
}
// works fine without sectionedAdapter.notifyDataSetChanged(); when using fake data,
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_payment);
ButterKnife.bind(this);
subscriptions = new CompositeSubscription();
initialToolbar();
initialRecyclerView();
initialPaymentData();
}
private void initialPaymentData() {
stripeIdAndToken = Utils.getStripeIdAndToken(this);
if (TextUtils.isEmpty(stripeIdAndToken.first)) {
cardSection.setState(Section.State.EMPTY);
bankSection.setState(Section.State.EMPTY);
} else {
initialCardDrawableResource();
retrieveCardInfo(stripeIdAndToken.first, stripeIdAndToken.second);
}
// fake data here
// initialCardDrawableResource();
// list = new ArrayList<>();
// list.add(new PaymentCreditCardItem("Visa", "123456", 10, 2018, cardDrawable.get("Visa")));
// cardSection.swipeData(list);
}
private void initialCardDrawableResource() {
cardDrawable = new HashMap<>();
cardDrawable.put("Visa", R.drawable.ic_visa_svg);
cardDrawable.put("Discover", R.drawable.ic_discover_svg);
cardDrawable.put("American Express", R.drawable.ic__credit_amex_svg);
cardDrawable.put("Mastercard", R.drawable.cio_ic_mastercard);
}
private void retrieveCardInfo(String stripeId, String token) {
subscriptions.add(NetworkUtil.getRetrofit(token).getCustomerInfo(new GetCustomer(stripeId))
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(this::handleCustomerResponse, this::handleError));
}
private void handleCustomerResponse(CreateStripeCustomerResponse response) {
if (response.getSuccess()) {
updateCardList(response);
} else {
Utils.toast(this, "Get credit card failed");
}
}
private void updateCardList(CreateStripeCustomerResponse response) {
List<CardInfo> cardList = response.getCustomer().getSources().getData();
if (cardList == null || cardList.size() == 0) {
cardSection.setState(Section.State.EMPTY);
} else {
list = new ArrayList<>();
for (int i = 0; i < cardList.size(); i++) {
CardInfo cardInfo = cardList.get(i);
String brand = cardInfo.getBrand();
String cardNum = cardInfo.getFunding() + "****" + cardInfo.getLast4();
list.add(new PaymentCreditCardItem(brand, cardNum, cardInfo.getExpMonth(), cardInfo.getExpYear(), cardDrawable.get(brand)));
}
cardSection.swipeData(list);
sectionedAdapter.notifyDataSetChanged();
}
}
private void handleError(Throwable throwable) {
}
private void initialRecyclerView() {
sectionedAdapter = new SectionedRecyclerViewAdapter();
cardSection = new PaymentCardAndAccountSection(this, R.layout.header_card, R.layout.payment_card_empty_view);
bankSection = new PaymentCardAndAccountSection(this, R.layout.header_bank, R.layout.payment_account_empty_view);
sectionedAdapter.addSection(cardSection);
sectionedAdapter.addSection(bankSection);
recyclerView.setLayoutManager(new LinearLayoutManager(this));
recyclerView.setAdapter(sectionedAdapter);
bankSection.setState(Section.State.EMPTY);
}
private void initialToolbar() {
toolbar.setTitle("Payment");
toolbar.setNavigationIcon(R.drawable.ic_back_svg);
setSupportActionBar(toolbar);
}
#Override
public boolean onSupportNavigateUp() {
onBackPressed();
return true;
}
#OnClick(R.id.fab_add_payment)
void launchAddPaymentDialog() {
AddPaymentDialogFragment addPaymentDialogFragment = AddPaymentDialogFragment.newInstance();
addPaymentDialogFragment.setStyle(DialogFragment.STYLE_NO_FRAME, 0);
addPaymentDialogFragment.show(getSupportFragmentManager(), "dialog");
}
#Override
public void onPause() {
super.onPause();
if (subscriptions != null) {
subscriptions.clear();
}
}
Do you use an adapter? In this case adapter.notifyDataSetChanged();
Also, print yout error: throwable.printStackTrace(); in order to see if something goes wrong.
You need to add .observeOn(AndroidSchedulers.mainThread()) after you write subsribeOn() to tell your observable to perform your onNext callback on UI thread/MainThread.
I want to check some checkbox with a recieved list from a Rest Service.
Here some code.
REQUEST
private void requestOpcionais() {
OpcionalRequestHelper.opcionaisRequest(Request.Method.GET, EndpointURL.GET_OPCIONAIS, null, new Response.Listener<Opcional[]>() {
#Override
public void onResponse(Opcional[] response) {
ArrayList<Opcional> opcionalArrayList = new ArrayList<>();
opcionalArrayList.addAll(Arrays.asList(response));
mRecyclerView.setHasFixedSize(true);
mLayoutManager = new LinearLayoutManager(getActivity());
mRecyclerView.setLayoutManager(mLayoutManager);
listOpcionalAdapter = new ListOpcionalAdapter(getActivity(), opcionalArrayList, VeiculoFragment.this);
mRecyclerView.setAdapter(listOpcionalAdapter);
if (veiculo != null) {
setOpcionalVeiculoSelected(opcionalArrayList, veiculo.getOpcionais());
}
progressDialogOpcionais.dismiss();
}
}, new Response.ErrorListener() {
#Override
public void onErrorResponse(VolleyError error) {
progressDialogOpcionais.dismiss();
Toast.makeText(getActivity(), "Erro ao carregar opcionais.", Toast.LENGTH_LONG).show();
}
});
}
There is the verification if my opcional list...
private void setOpcionalVeiculoSelected(ArrayList<Opcional> opcionalArrayList, List<Opcional> opcionais) {
for (Opcional opcionalList : opcionalArrayList) {
for (Opcional opcionalVeiculo : opcionais) {
if (opcionalVeiculo.getId() == opcionalList.getId()) {
mOpcionalChecked.add(opcionalVeiculo);
}
}
}
}
How i check those "opcionais" on my recyclerview?
I resolved my issue on this way...
I've sended the array to my adapter.
if (veiculo != null) {
setOpcionalVeiculoSelected(opcionalArrayList, veiculo.getOpcionais());
listOpcionalAdapter = new ListOpcionalAdapter(getActivity(), opcionalArrayList, VeiculoFragment.this, veiculo.getOpcionais());
} else {
listOpcionalAdapter = new ListOpcionalAdapter(getActivity(), opcionalArrayList, VeiculoFragment.this, null);
}
On my onBindViewHolder() I checked if my array is not null.
onBindViewHolder()
if (opcionalsVeiculo != null) {
setOpcionalVeiculoSelected(holder, position);
}
And finally check my array and the position of my other array from adapter.
private void setOpcionalVeiculoSelected(ViewHolder holder, int position) {
for (Opcional opcional : opcionalsVeiculo) {
if (opcionals.get(position).getId() == opcional.getId()) {
holder.chb_opcional.setChecked(true);
}
}
}
I have a list view which is updated with items coming from server.
On this list view I have load more functionality and pull down to refresh both.
Everything is working fine but problem is when I pull down to refresh and and scrolls the listview fast it crashes what I am doing wrong I don't understand.
Here is my code
lv.setOnScrollListener(new AbsListView.OnScrollListener() {
#Override
public void onScrollStateChanged(AbsListView view, int scrollState) {
}
#Override
public void onScroll(AbsListView view, int firstVisibleItem, int visibleItemCount, int totalItemCount) {
//what is the bottom iten that is visible
int lastInScreen = firstVisibleItem + visibleItemCount;
if (lastInScreen != 0) {
if ((lastInScreen == totalItemCount) && !(isLoading)) {// && !(loadingMore)){
if (newsList.size() < total) {
if (isNetworkAvailable()) {
if (!isLoading) {
lv.addFooterView(footerView);
getNews();
}
}
} else {
lv.removeFooterView(footerView);
}
}
}
}
});
This is my OnRefresh method
#Override
public void onRefresh() {
super.onRefresh();
if (!isLoading) { // no query to server is executing
if (isNetworkAvailable()) {
isLoading = true;
clearList = true;
pageNumber = 0;
getNews();
} else {
toast(getString(R.string.no_internet));
swipeRefreshLayout.setRefreshing(false);
}
} else {// a query is already server is executing
swipeRefreshLayout.postDelayed(new Runnable() {
#Override
public void run() {
swipeRefreshLayout.setRefreshing(false);
}
}, 1000);
}
}
private void getNews() {
pageNumber += 1;
isLoading = true;
JsonObjectRequest jsonObjReq = new JsonObjectRequest(Request.Method.GET,
urlNews + pageNumber, null,
this, this);
applicationInstance.addToRequestQueue(jsonObjReq, "News");
}
#Override
public void onResponse(JSONObject jsonObject) {
super.onResponse(jsonObject);
new SaveData().execute(jsonObject);
}
public class SaveData extends AsyncTask<JSONObject, Void, Void> {
#Override
protected Void doInBackground(JSONObject... params) {
JSONObject jsonObject = params[0];
try {
if (jsonObject.getInt("success") == 1) {
if (clearList) {
newsList.clear();
}
JSONArray newsArray = jsonObject.getJSONArray("rooms");
total = jsonObject.getJSONObject("paging").getInt("total");
for (int a = 0; a < newsArray.length(); a++) {
JSONObject obj = newsArray.getJSONObject(a);
int roomID = obj.getInt("id");
String title = obj.getString("name");
String descr = obj.getString("descr");
RoomsData room = Select.from(RoomsData.class).where(Condition.prop("room_id").eq(roomID)).first();
if (room == null) {
room = new RoomsData(roomID, title, descr);
room.save();
} else {
room.name = title;
room.description = descr;
room.save();
}
JSONArray imagesArray = obj.getJSONArray("images");
for (int b = 0; b < imagesArray.length(); b++) {
JSONObject imageObj = imagesArray.getJSONObject(b);
String Imagename = imageObj.getString("name");
String url = imageObj.getString("url");
HotelImages.deleteAll(HotelImages.class, "room_id = ? and name = ? and url = ? ", roomID + "", Imagename, url);
HotelImages image = new HotelImages(0, roomID, 0, 0, 0, 0, 0, Imagename, url);
image.save();
room.imageList.add(image);
}
// tempList.add(room);
newsList.add(room);
}
store.setString(Constants.FACILITIES_AVAILABLE, jsonObject.getJSONArray("facilities").toString());
store.setString(Constants.BOOKING_EMAIL, jsonObject.getJSONObject("reservation").getString("email"));
}
} catch (Exception e) {
} finally {
}
return null;
}
#Override
protected void onPostExecute(Void aVoid) {
super.onPostExecute(aVoid);
runOnUiThread(new Runnable() {
#Override
public void run() {
setListView();
isLoading = false;
swipeRefreshLayout.setRefreshing(false);
}
});
}
}
private void setListView() {
if (newsList.size() == 1) {
Intent it = new Intent(RoomsActivity.this, RoomDetailActivity.class);
RoomsData pro = newsList.get(0);
it.putExtra("RoomID", pro.roomID);
//it.putExtra("rat",rat);
startActivity(it);
finish();
} else {
if (clearList) {
clearList = false;
adapterRooms = new AdapterRooms(this, newsList);
lv.setAdapter(adapterRooms);
if (adapterRooms == null) {
adapterRooms = new AdapterRooms(this, newsList);
lv.setAdapter(adapterRooms);
} else {
adapterRooms.notifyDataSetChanged();
}
} else {
adapterRooms.notifyDataSetChanged();
}
}
swipeRefreshLayout.setRefreshing(false);
lv.removeFooterView(footerView);
}
This is the exception i am getting
01-08 12:45:08.377 2373-2373/hotels.soulvant E/AndroidRuntime﹕ FATAL EXCEPTION: main
Process: hotels.soulvant, PID: 2373
java.lang.IndexOutOfBoundsException: Invalid index 5, size is 0
at java.util.ArrayList.throwIndexOutOfBoundsException(ArrayList.java:255)
at java.util.ArrayList.get(ArrayList.java:308)
at android.widget.HeaderViewListAdapter.getView(HeaderViewListAdapter.java:225)
at android.widget.AbsListView.obtainView(AbsListView.java:2346)
at android.widget.ListView.makeAndAddView(ListView.java:1875)
at android.widget.ListView.fillDown(ListView.java:702)
at android.widget.ListView.fillGap(ListView.java:666)
at android.widget.AbsListView.trackMotionScroll(AbsListView.java:5029)
at android.widget.AbsListView$FlingRunnable.run(AbsListView.java:4577)
at android.view.Choreographer$CallbackRecord.run(Choreographer.java:858)
at android.view.Choreographer.doCallbacks(Choreographer.java:670)
at android.view.Choreographer.doFrame(Choreographer.java:603)
at android.view.Choreographer$FrameDisplayEventReceiver.run(Choreographer.java:844)
at android.os.Handler.handleCallback(Handler.java:739)
at android.os.Handler.dispatchMessage(Handler.java:95)
at android.os.Looper.loop(Looper.java:148)
at android.app.ActivityThread.main(ActivityThread.java:5417)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:726)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:616)
I've created an endless list to deal with my pagination coming from an API, I get the next page data in a JSON and it getting parsed to my activity. But, my adapter is not updating with the new items. I've called notifyDataSetChanged and it's just not updating. Any idea what I'm doing wrong? Here is my code below:
private void loadData(final boolean firstLoad) {
mDataFactory.getPostFeed(mThreads.getId(), mCurrentPage, new PostFeedDataFactory.PostFeedDataFactoryCallback() {
#Override
public void onPostDataReceived(PostResponse response) {
mData = response;
if (mData.getItems() != null) {
for (int i = 0; i < mData.getItems().size(); i++) {
Posts singlePost = response.getItems().get(i);
postList.add(singlePost);
}
if (firstLoad) {
mIsLoading = false;
mData.getItems().clear();
mData.getItems().addAll(postList);
mEmoticonDataFactory.getEmoticonFeed(new EmoticonFeedDataFactory.EmoticonFeedDataFactoryCallback() {
#Override
public void onEmoticonDataReceived(EmoticonResponse response) {
mEmoticon = response;
populateUIWithData();
}
#Override
public void onEmoticonDataFailed(Exception exception) {
}
});
} else {
mIsLoading = false;
refreshPosts(postList);
}
if (mData.getItems().size() > 0) {
if (Integer.valueOf(mData.getTotalPosts()) >= response.getItems().size()) {
mCurrentPage++;
} else {
mIsLastPage = true;
}
}
}
}
#Override
public void onPostDataFailed(Exception exception) {
}
});
}
private void populateUIWithData() {
mThreadText = (TextView) findViewById(R.id.threadText);
if (mThreads != null) {
if (mThreads.getName() != null) {
mThreadText.setText(mThreads.getName());
}
}
if (mAdapter == null){
mAdapter = new PostAdapter(this, mData, mEmoticon);
mRecyclerView.setAdapter(mAdapter);
} else {
mAdapter.setData(postList);
mAdapter.notifyDataSetChanged();
}
mRecyclerView.addOnScrollListener(paginationListener);
}
private RecyclerView.OnScrollListener paginationListener = new RecyclerView.OnScrollListener() {
#Override
public void onScrollStateChanged(RecyclerView recyclerView, int newState) {
super.onScrollStateChanged(recyclerView, newState);
}
#Override
public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
super.onScrolled(recyclerView, dx, dy);
int visibleItemCount = mLayoutManager.getChildCount();
int totalItemCount = mLayoutManager.getItemCount();
int firstVisibleItemPosition = mLayoutManager.findFirstVisibleItemPosition();
if (!mIsLoading && !mIsLastPage) {
if ((visibleItemCount + firstVisibleItemPosition) >= totalItemCount) {
loadMoreItems();
}
}
}
};
private void loadMoreItems() {
mIsLoading = true;
loadData(false);
}
private void refreshPosts(ArrayList<Posts> newObjects) {
postList.addAll(newObjects);
populateUIWithData();
}
Also, here is my adapter
PostAdapter.java
#Override
public void onBindViewHolder(ViewHolder holder, int position) {
Posts posts = mPost.getItem(position);
emoticons = mEmoticon.getItems();
String message = null;
String emoMessage = null;
if (posts.getPost() != null) {
if (posts.getPost().getMessage() != null) {
message = posts.getPost().getMessage();
emoMessage = message;
if (emoticons != null) {
for(Emoticons emoticon : this.emoticons) {
if (message.contains(emoticon.getEmoticon().getCode())) {
emoMessage = message.replaceAll(Constants.EMO_REGEX, emoticon.getEmoticon().getUrl());
}
}
}
}
if (posts.getPost().getUsername() != null) {
holder.mAuthorTextView.setText("Posted by: " + posts.getPost().getUsername());
}
if (posts.getPost().getHighlighting().equals("op")) {
holder.mPostTextView.setTypeface(Typeface.DEFAULT_BOLD);
}
}
holder.mPostTextView.setText(Html.fromHtml(emoMessage, new Html.ImageGetter() {
#Override
public Drawable getDrawable(String source) {
Drawable d = null;
try {
StrictMode.ThreadPolicy policy = new StrictMode.ThreadPolicy.Builder().permitAll().build();
StrictMode.setThreadPolicy(policy);
URL url = new URL(source);
InputStream is = url.openStream();
Bitmap b = BitmapFactory.decodeStream(is);
d = new BitmapDrawable(Resources.getSystem(), b);
d.setBounds(0, 0, d.getIntrinsicWidth(), d.getIntrinsicHeight());
} catch (IOException e) {
e.printStackTrace();
}
return d;
}
}, new Html.TagHandler() {
#Override
public void handleTag(boolean opening, String tag, Editable output, XMLReader xmlReader) {
if(tag.equalsIgnoreCase("strike") || tag.equals("s")) {
processStrike(opening, output);
}
}
private void processStrike(boolean opening, Editable output) {
int len = output.length();
if(opening) {
output.setSpan(new StrikethroughSpan(), len, len, Spannable.SPAN_MARK_MARK);
} else {
Object obj = getLast(output, StrikethroughSpan.class);
int where = output.getSpanStart(obj);
output.removeSpan(obj);
if (where != len) {
output.setSpan(new StrikethroughSpan(), where, len, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
}
}
}
private Object getLast(Editable text, Class kind) {
Object[] objs = text.getSpans(0, text.length(), kind);
if (objs.length == 0) {
return null;
} else {
for(int i = objs.length;i>0;i--) {
if(text.getSpanFlags(objs[i-1]) == Spannable.SPAN_MARK_MARK) {
return objs[i-1];
}
}
return null;
}
}
}));
}
#Override
public int getItemCount() {
return mPost.getItems().size();
}
public void setData(ArrayList<Posts> array) {
ArrayList<Posts> postList = this.mPost.getItems();
postList = array;
}
I found the answer thanks to #cYrixmorten I changed my setData method to look like this
public void setData(ArrayList<Posts> array) {
mPost.getItems().addAll(array);
}
I basically just forgot to update my adapter to populate for me... But I just want to say thank you to those who helped. :)
This question already has answers here:
What is a NullPointerException, and how do I fix it?
(12 answers)
Closed 7 years ago.
I am working on an app which dosen't show me any errors and runs just fine, but after a second just crashes, I tried everything but could not find the error (being new) can someone please tell me where am I doing wrong as
logcat
11-08 12:57:16.011 5886-5886/com.koshur.socialnetwork E/AndroidRuntime﹕ FATAL EXCEPTION: main
Process: com.koshur.socialnetwork, PID: 5886
java.lang.NullPointerException: Attempt to invoke virtual method 'void com.koshur.socialnetwork.adapters.HomeListAdapter.setPosts(java.util.List)' on a null object reference
at com.koshur.socialnetwork.activities.ProfilePreview.updateView(ProfilePreview.java:334)
at com.koshur.socialnetwork.activities.ProfilePreview.access$300(ProfilePreview.java:42)
at com.koshur.socialnetwork.activities.ProfilePreview$5.success(ProfilePreview.java:308)
at com.koshur.socialnetwork.activities.ProfilePreview$5.success(ProfilePreview.java:300)
at retrofit.CallbackRunnable$1.run(CallbackRunnable.java:45)
at android.os.Handler.handleCallback(Handler.java:739)
at android.os.Handler.dispatchMessage(Handler.java:95)
at android.os.Looper.loop(Looper.java:135)
at android.app.ActivityThread.main(ActivityThread.java:5293)
at java.lang.reflect.Method.invoke(Native Method)
at java.lang.reflect.Method.invoke(Method.java:372)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:904)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:699)
java class
public class ProfilePreview extends AppCompatActivity implements View.OnClickListener, SwipeRefreshLayout.OnRefreshListener {
public TextView userProfileName,
userTotalFollowers,
userTotalPosts,
userProfileAddress,
userProfileJob,
followProfileBtn,
contactProfileBtn,
userPostsBtn;
public userItem user;
public RecyclerView postsList;
public LinearLayoutManager layoutManager;
int currentPage = 1;
private HomeListAdapter mHomeListAdapter;
private SwipeRefreshLayout mSwipeRefreshLayout;
public ImageView userProfilePicture, userProfileCover;
public LinearLayout actionProfileArea;
public int userID = 0;
private CacheManager mCacheManager;
private ThinDownloadManager downloadManager;
private Gson mGson;
LoadingView loginLoadingView;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
if (M.getToken(this) == null) {
Intent mIntent = new Intent(this, LoginActivity.class);
startActivity(mIntent);
finish();
} else {
setContentView(R.layout.activity_profile_preview);
initializeView();
loginLoadingView = (LoadingView)findViewById(R.id.loginLoadingView);
if (getIntent().hasExtra("userID")) {
userID = getIntent().getExtras().getInt("userID");
}
mCacheManager = CacheManager.getInstance(getApplicationContext());
mGson = new Gson();
getUser();
getPosts();
}
}
private void initializeView() {
downloadManager = new ThinDownloadManager(AppConst.DOWNLOAD_THREAD_POOL_SIZE);
userProfileName = (TextView) findViewById(R.id.userProfileName);
userProfilePicture = (ImageView) findViewById(R.id.userProfilePicture);
userTotalFollowers = (TextView) findViewById(R.id.userTotalFollowers);
userTotalPosts = (TextView) findViewById(R.id.userTotalPosts);
followProfileBtn = (TextView) findViewById(R.id.followProfileBtn);
contactProfileBtn = (TextView) findViewById(R.id.contactProfileBtn);
actionProfileArea = (LinearLayout) findViewById(R.id.actionProfileArea);
userProfileAddress = (TextView) findViewById(R.id.userProfileAddress);
userProfileJob = (TextView) findViewById(R.id.userProfileJob);
userProfileCover = (ImageView) findViewById(R.id.userProfileCover);
userPostsBtn = (TextView) findViewById(R.id.userPostsBtn);
userPostsBtn.setOnClickListener(this);
followProfileBtn.setOnClickListener(this);
contactProfileBtn.setOnClickListener(this);
postsList = (RecyclerView) findViewById(R.id.postsList);
mSwipeRefreshLayout = (SwipeRefreshLayout) findViewById(R.id.swipeHome);
mSwipeRefreshLayout.setOnRefreshListener(this);
postsList.setOnScrollListener(new HidingScrollListener(layoutManager) {
#Override
public void onHide() {
}
#Override
public void onShow() {
}
#Override
public void onLoadMore(int currentPage) {
setCurrentPage(currentPage);
getPosts();
}
});
}
private void getUser() {
if (M.isNetworkAvailable(getApplicationContext())) {
loginLoadingView.setLoading(true);
UsersAPI mUsersAPI = APIService.createService(UsersAPI.class, M.getToken(this));
mUsersAPI.getUser(userID, new Callback<userItem>() {
#Override
public void success(userItem user, retrofit.client.Response response) {
try {
mCacheManager.write(mGson.toJson(user), "Profile-" + userID + ".json");
} catch (Exception e) {
e.printStackTrace();
}
updateView(user);
}
#Override
public void failure(RetrofitError error) {
loginLoadingView.setLoading(false);
M.T(ProfilePreview.this, getString(R.string.ServerError));
}
});
} else {
try {
String profile = mCacheManager.readString("Profile-" + userID + ".json");
Gson mGson = new Gson();
updateView((userItem) mGson.fromJson(profile, new TypeToken<userItem>() {
}.getType()));
} catch (Exception e) {
M.L(e.getMessage());
}
}
}
private void downloadFile(String url, String hash) {
if (getFilePath(hash) == null) {
Uri downloadUri = Uri.parse(url);
Uri destinationUri = Uri.parse(M.getFilePath(getApplicationContext(), hash));
DownloadRequest downloadRequest = new DownloadRequest(downloadUri)
.setDestinationURI(destinationUri);
downloadManager.add(downloadRequest);
}
}
private void updateView(userItem user) {
this.user = user;
if (user.isMine()) {
actionProfileArea.setVisibility(View.GONE);
} else {
actionProfileArea.setVisibility(View.VISIBLE);
}
if (user.isFollowed()) {
followProfileBtn.setText(getString(R.string.UnFollow));
contactProfileBtn.setVisibility(View.VISIBLE);
} else {
followProfileBtn.setText(getString(R.string.Follow));
contactProfileBtn.setVisibility(View.GONE);
}
if (user.getName() != null) {
userProfileName.setText(user.getName());
} else {
userProfileName.setText(user.getUsername());
}
if (user.getAddress() != null) {
userProfileAddress.setVisibility(View.VISIBLE);
userProfileAddress.setText(user.getAddress());
} else {
userProfileAddress.setVisibility(View.GONE);
}
if (user.getJob() != null) {
userProfileJob.setVisibility(View.VISIBLE);
userProfileJob.setText(user.getJob());
} else {
userProfileJob.setVisibility(View.GONE);
}
if (getFilePath(user.getPicture()) != null) {
Picasso.with(this)
.load(new File(getFilePath(user.getPicture())))
.transform(new CropSquareTransformation())
.placeholder(R.drawable.image_holder)
.error(R.drawable.image_holder)
.into(userProfilePicture);
} else {
Picasso.with(this)
.load(AppConst.IMAGE_PROFILE_URL + user.getPicture())
.transform(new CropSquareTransformation())
.placeholder(R.drawable.image_holder)
.error(R.drawable.image_holder)
.into(userProfilePicture);
downloadFile(AppConst.IMAGE_PROFILE_URL + user.getPicture(), user.getPicture());
}
if (user.getCover() != null) {
if (getFilePath(user.getCover()) != null) {
userProfileCover.setImageURI(Uri.parse(getFilePath(user.getCover())));
} else {
Picasso.with(this)
.load(AppConst.IMAGE_COVER_URL + user.getCover())
.placeholder(R.drawable.header)
.error(R.drawable.header)
.into(userProfileCover);
downloadFile(AppConst.IMAGE_COVER_URL + user.getCover(), user.getCover());
}
} else {
Picasso.with(this)
.load(R.drawable.header)
.into(userProfileCover);
}
userTotalFollowers.setText(user.getTotalFollowers() + "");
userTotalPosts.setText(user.getTotalPosts() + "");
loginLoadingView.setLoading(false);
}
private String getFilePath(String hash) {
return M.filePath(getApplicationContext(), hash);
}
#Override
public void onClick(View v) {
switch (v.getId()) {
case R.id.followProfileBtn:
UsersAPI mUsersAPI = APIService.createService(UsersAPI.class, M.getToken(this));
mUsersAPI.followToggle(userID, new Callback<ResponseModel>() {
#Override
public void success(ResponseModel responseModel, Response response) {
if (responseModel.isDone()) {
if (user.isFollowed()) {
user.setFollowed(false);
followProfileBtn.setText(getString(R.string.Follow));
loginLoadingView.setLoading(true);
contactProfileBtn.setVisibility(View.GONE);
loginLoadingView.setLoading(false);
} else {
user.setFollowed(true);
followProfileBtn.setText(getString(R.string.UnFollow));
contactProfileBtn.setVisibility(View.VISIBLE);
}
} else {
M.T(ProfilePreview.this, responseModel.getMessage());
}
}
#Override
public void failure(RetrofitError error) {
M.T(ProfilePreview.this, getString(R.string.ServerError));
}
});
break;
case R.id.contactProfileBtn:
Intent messagingIntent = new Intent(this, MessagingActivity.class);
messagingIntent.putExtra("conversationID", 0);
messagingIntent.putExtra("recipientID", userID);
startActivity(messagingIntent);
break;
case R.id.userPostsBtn:
Intent userPostsIntent = new Intent(this, UserPosts.class);
userPostsIntent.putExtra("userID", userID);
startActivity(userPostsIntent);
finish();
break;
}
}
public void getPosts() {
if (M.isNetworkAvailable(this)) {
if (!mSwipeRefreshLayout.isRefreshing()) {
mSwipeRefreshLayout.setRefreshing(true);
}
PostsAPI mPostsAPI = APIService.createService(PostsAPI.class, M.getToken(this));
mPostsAPI.getUserPosts(userID, getCurrentPage(), new Callback<List<PostsItem>>() {
#Override
public void success(List<PostsItem> postsItems, retrofit.client.Response response) {
try {
mCacheManager.write(mGson.toJson(postsItems), "UserPosts-" + userID + ".json");
} catch (Exception e) {
e.printStackTrace();
}
updateView(postsItems);
}
#Override
public void failure(RetrofitError error) {
loginLoadingView.setLoading(false);
}
});
} else {
try {
String UserPostsString = mCacheManager.readString("UserPosts-" + userID + ".json");
updateView((List<PostsItem>) mGson.fromJson(UserPostsString, new TypeToken<List<PostsItem>>() {
}.getType()));
} catch (Exception e) {
e.printStackTrace();
}
}
}
private void updateView(List<PostsItem> postsItems) {
if (getCurrentPage() != 1) {
List<PostsItem> oldItems = mHomeListAdapter.getPosts();
oldItems.addAll(postsItems);
mHomeListAdapter.setPosts(oldItems);
} else {
mHomeListAdapter.setPosts(postsItems);
}
if (mSwipeRefreshLayout.isRefreshing()) {
mSwipeRefreshLayout.setRefreshing(false);
}
}
#Override
public void onRefresh() {
setCurrentPage(1);
getPosts();
}
public int getCurrentPage() {
return currentPage;
}
public void setCurrentPage(int currentPage) {
this.currentPage = currentPage;
}
}
At least from the code you posted you are not initialising your mhomelistadapter so it is null when you call setPosts